hir_ty/next_solver/
opaques.rs1use intern::Interned;
4use rustc_ast_ir::try_visit;
5
6use crate::next_solver::SolverDefId;
7
8use super::{CanonicalVarKind, DbInterner, interned_vec_nolifetime_salsa};
9
10pub type OpaqueTypeKey<'db> = rustc_type_ir::OpaqueTypeKey<DbInterner<'db>>;
11pub type PredefinedOpaquesData<'db> = rustc_type_ir::solve::PredefinedOpaquesData<DbInterner<'db>>;
12pub type ExternalConstraintsData<'db> =
13 rustc_type_ir::solve::ExternalConstraintsData<DbInterner<'db>>;
14
15#[salsa::interned(constructor = new_, debug)]
16pub struct PredefinedOpaques<'db> {
17 #[returns(ref)]
18 kind_: rustc_type_ir::solve::PredefinedOpaquesData<DbInterner<'db>>,
19}
20
21impl<'db> PredefinedOpaques<'db> {
22 pub fn new(interner: DbInterner<'db>, data: PredefinedOpaquesData<'db>) -> Self {
23 PredefinedOpaques::new_(interner.db(), data)
24 }
25
26 pub fn inner(&self) -> &PredefinedOpaquesData<'db> {
27 salsa::with_attached_database(|db| {
28 let inner = self.kind_(db);
29 unsafe { std::mem::transmute(inner) }
31 })
32 .unwrap()
33 }
34}
35
36impl<'db> rustc_type_ir::TypeVisitable<DbInterner<'db>> for PredefinedOpaques<'db> {
37 fn visit_with<V: rustc_type_ir::TypeVisitor<DbInterner<'db>>>(
38 &self,
39 visitor: &mut V,
40 ) -> V::Result {
41 self.opaque_types.visit_with(visitor)
42 }
43}
44
45impl<'db> rustc_type_ir::TypeFoldable<DbInterner<'db>> for PredefinedOpaques<'db> {
46 fn try_fold_with<F: rustc_type_ir::FallibleTypeFolder<DbInterner<'db>>>(
47 self,
48 folder: &mut F,
49 ) -> Result<Self, F::Error> {
50 Ok(PredefinedOpaques::new(
51 folder.cx(),
52 PredefinedOpaquesData {
53 opaque_types: self
54 .opaque_types
55 .iter()
56 .cloned()
57 .map(|opaque| opaque.try_fold_with(folder))
58 .collect::<Result<_, F::Error>>()?,
59 },
60 ))
61 }
62 fn fold_with<F: rustc_type_ir::TypeFolder<DbInterner<'db>>>(self, folder: &mut F) -> Self {
63 PredefinedOpaques::new(
64 folder.cx(),
65 PredefinedOpaquesData {
66 opaque_types: self
67 .opaque_types
68 .iter()
69 .cloned()
70 .map(|opaque| opaque.fold_with(folder))
71 .collect(),
72 },
73 )
74 }
75}
76
77impl<'db> std::ops::Deref for PredefinedOpaques<'db> {
78 type Target = PredefinedOpaquesData<'db>;
79
80 fn deref(&self) -> &Self::Target {
81 self.inner()
82 }
83}
84
85interned_vec_nolifetime_salsa!(SolverDefIds, SolverDefId);
86
87#[salsa::interned(constructor = new_, debug)]
88pub struct ExternalConstraints<'db> {
89 #[returns(ref)]
90 kind_: rustc_type_ir::solve::ExternalConstraintsData<DbInterner<'db>>,
91}
92
93impl<'db> ExternalConstraints<'db> {
94 pub fn new(interner: DbInterner<'db>, data: ExternalConstraintsData<'db>) -> Self {
95 ExternalConstraints::new_(interner.db(), data)
96 }
97
98 pub fn inner(&self) -> &ExternalConstraintsData<'db> {
99 salsa::with_attached_database(|db| {
100 let inner = self.kind_(db);
101 unsafe { std::mem::transmute(inner) }
103 })
104 .unwrap()
105 }
106}
107
108impl<'db> std::ops::Deref for ExternalConstraints<'db> {
109 type Target = ExternalConstraintsData<'db>;
110
111 fn deref(&self) -> &Self::Target {
112 self.inner()
113 }
114}
115
116impl<'db> rustc_type_ir::TypeVisitable<DbInterner<'db>> for ExternalConstraints<'db> {
117 fn visit_with<V: rustc_type_ir::TypeVisitor<DbInterner<'db>>>(
118 &self,
119 visitor: &mut V,
120 ) -> V::Result {
121 try_visit!(self.region_constraints.visit_with(visitor));
122 try_visit!(self.opaque_types.visit_with(visitor));
123 self.normalization_nested_goals.visit_with(visitor)
124 }
125}
126
127impl<'db> rustc_type_ir::TypeFoldable<DbInterner<'db>> for ExternalConstraints<'db> {
128 fn try_fold_with<F: rustc_type_ir::FallibleTypeFolder<DbInterner<'db>>>(
129 self,
130 folder: &mut F,
131 ) -> Result<Self, F::Error> {
132 Ok(ExternalConstraints::new(
133 folder.cx(),
134 ExternalConstraintsData {
135 region_constraints: self.region_constraints.clone().try_fold_with(folder)?,
136 opaque_types: self
137 .opaque_types
138 .iter()
139 .cloned()
140 .map(|opaque| opaque.try_fold_with(folder))
141 .collect::<Result<_, F::Error>>()?,
142 normalization_nested_goals: self
143 .normalization_nested_goals
144 .clone()
145 .try_fold_with(folder)?,
146 },
147 ))
148 }
149 fn fold_with<F: rustc_type_ir::TypeFolder<DbInterner<'db>>>(self, folder: &mut F) -> Self {
150 ExternalConstraints::new(
151 folder.cx(),
152 ExternalConstraintsData {
153 region_constraints: self.region_constraints.clone().fold_with(folder),
154 opaque_types: self
155 .opaque_types
156 .iter()
157 .cloned()
158 .map(|opaque| opaque.fold_with(folder))
159 .collect(),
160 normalization_nested_goals: self
161 .normalization_nested_goals
162 .clone()
163 .fold_with(folder),
164 },
165 )
166 }
167}