]>
Commit | Line | Data |
---|---|---|
ff7c6d11 XL |
1 | //! This module contains implements of the `Lift` and `TypeFoldable` |
2 | //! traits for various types in the Rust compiler. Most are written by | |
60c5eb7d | 3 | //! hand, though we've recently added some macros and proc-macros to help with the tedium. |
ff7c6d11 | 4 | |
532ac7d7 | 5 | use crate::hir::def::Namespace; |
60c5eb7d | 6 | use crate::hir::def_id::CRATE_DEF_INDEX; |
9fa01778 | 7 | use crate::mir::ProjectionKind; |
60c5eb7d | 8 | use crate::mir::interpret; |
dc9dc135 | 9 | use crate::ty::{self, Lift, Ty, TyCtxt, InferConst}; |
9fa01778 | 10 | use crate::ty::fold::{TypeFoldable, TypeFolder, TypeVisitor}; |
532ac7d7 | 11 | use crate::ty::print::{FmtPrinter, Printer}; |
60c5eb7d | 12 | |
e74abb32 | 13 | use rustc_index::vec::{IndexVec, Idx}; |
b7449926 | 14 | use smallvec::SmallVec; |
e9174d1e | 15 | |
532ac7d7 | 16 | use std::fmt; |
e9174d1e | 17 | use std::rc::Rc; |
dc9dc135 | 18 | use std::sync::Arc; |
e9174d1e | 19 | |
532ac7d7 XL |
20 | impl fmt::Debug for ty::GenericParamDef { |
21 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
22 | let type_name = match self.kind { | |
23 | ty::GenericParamDefKind::Lifetime => "Lifetime", | |
24 | ty::GenericParamDefKind::Type {..} => "Type", | |
25 | ty::GenericParamDefKind::Const => "Const", | |
26 | }; | |
27 | write!(f, "{}({}, {:?}, {})", | |
28 | type_name, | |
29 | self.name, | |
30 | self.def_id, | |
31 | self.index) | |
32 | } | |
33 | } | |
34 | ||
35 | impl fmt::Debug for ty::TraitDef { | |
36 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
37 | ty::tls::with(|tcx| { | |
38 | FmtPrinter::new(tcx, f, Namespace::TypeNS) | |
39 | .print_def_path(self.def_id, &[])?; | |
40 | Ok(()) | |
41 | }) | |
42 | } | |
43 | } | |
44 | ||
45 | impl fmt::Debug for ty::AdtDef { | |
46 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
47 | ty::tls::with(|tcx| { | |
48 | FmtPrinter::new(tcx, f, Namespace::TypeNS) | |
49 | .print_def_path(self.did, &[])?; | |
50 | Ok(()) | |
51 | }) | |
52 | } | |
53 | } | |
54 | ||
55 | impl fmt::Debug for ty::ClosureUpvar<'tcx> { | |
56 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
57 | write!(f, "ClosureUpvar({:?},{:?})", | |
48663c56 | 58 | self.res, |
532ac7d7 XL |
59 | self.ty) |
60 | } | |
61 | } | |
62 | ||
63 | impl fmt::Debug for ty::UpvarId { | |
64 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
65 | let name = ty::tls::with(|tcx| { | |
dc9dc135 | 66 | tcx.hir().name(self.var_path.hir_id) |
532ac7d7 XL |
67 | }); |
68 | write!(f, "UpvarId({:?};`{}`;{:?})", | |
69 | self.var_path.hir_id, | |
70 | name, | |
71 | self.closure_expr_id) | |
72 | } | |
73 | } | |
74 | ||
75 | impl fmt::Debug for ty::UpvarBorrow<'tcx> { | |
76 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
77 | write!(f, "UpvarBorrow({:?}, {:?})", | |
78 | self.kind, self.region) | |
79 | } | |
80 | } | |
81 | ||
82 | impl fmt::Debug for ty::ExistentialTraitRef<'tcx> { | |
83 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
84 | fmt::Display::fmt(self, f) | |
85 | } | |
86 | } | |
87 | ||
88 | impl fmt::Debug for ty::adjustment::Adjustment<'tcx> { | |
89 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
90 | write!(f, "{:?} -> {}", self.kind, self.target) | |
91 | } | |
92 | } | |
93 | ||
94 | impl fmt::Debug for ty::BoundRegion { | |
95 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
96 | match *self { | |
97 | ty::BrAnon(n) => write!(f, "BrAnon({:?})", n), | |
532ac7d7 | 98 | ty::BrNamed(did, name) => { |
60c5eb7d XL |
99 | if did.index == CRATE_DEF_INDEX { |
100 | write!(f, "BrNamed({})", name) | |
101 | } else { | |
102 | write!(f, "BrNamed({:?}, {})", did, name) | |
103 | } | |
532ac7d7 XL |
104 | } |
105 | ty::BrEnv => write!(f, "BrEnv"), | |
106 | } | |
107 | } | |
108 | } | |
109 | ||
110 | impl fmt::Debug for ty::RegionKind { | |
111 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
112 | match *self { | |
113 | ty::ReEarlyBound(ref data) => { | |
114 | write!(f, "ReEarlyBound({}, {})", | |
115 | data.index, | |
116 | data.name) | |
117 | } | |
118 | ||
119 | ty::ReClosureBound(ref vid) => { | |
120 | write!(f, "ReClosureBound({:?})", vid) | |
121 | } | |
122 | ||
123 | ty::ReLateBound(binder_id, ref bound_region) => { | |
124 | write!(f, "ReLateBound({:?}, {:?})", binder_id, bound_region) | |
125 | } | |
126 | ||
127 | ty::ReFree(ref fr) => fr.fmt(f), | |
128 | ||
129 | ty::ReScope(id) => write!(f, "ReScope({:?})", id), | |
130 | ||
131 | ty::ReStatic => write!(f, "ReStatic"), | |
132 | ||
133 | ty::ReVar(ref vid) => vid.fmt(f), | |
134 | ||
135 | ty::RePlaceholder(placeholder) => { | |
136 | write!(f, "RePlaceholder({:?})", placeholder) | |
137 | } | |
138 | ||
139 | ty::ReEmpty => write!(f, "ReEmpty"), | |
140 | ||
141 | ty::ReErased => write!(f, "ReErased"), | |
142 | } | |
143 | } | |
144 | } | |
145 | ||
146 | impl fmt::Debug for ty::FreeRegion { | |
147 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
148 | write!(f, "ReFree({:?}, {:?})", self.scope, self.bound_region) | |
149 | } | |
150 | } | |
151 | ||
152 | impl fmt::Debug for ty::Variance { | |
153 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
154 | f.write_str(match *self { | |
155 | ty::Covariant => "+", | |
156 | ty::Contravariant => "-", | |
157 | ty::Invariant => "o", | |
158 | ty::Bivariant => "*", | |
159 | }) | |
160 | } | |
161 | } | |
162 | ||
163 | impl fmt::Debug for ty::FnSig<'tcx> { | |
164 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
165 | write!(f, "({:?}; c_variadic: {})->{:?}", | |
166 | self.inputs(), self.c_variadic, self.output()) | |
167 | } | |
168 | } | |
169 | ||
170 | impl fmt::Debug for ty::TyVid { | |
171 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
172 | write!(f, "_#{}t", self.index) | |
173 | } | |
174 | } | |
175 | ||
176 | impl<'tcx> fmt::Debug for ty::ConstVid<'tcx> { | |
177 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
178 | write!(f, "_#{}c", self.index) | |
179 | } | |
180 | } | |
181 | ||
182 | impl fmt::Debug for ty::IntVid { | |
183 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
184 | write!(f, "_#{}i", self.index) | |
185 | } | |
186 | } | |
187 | ||
188 | impl fmt::Debug for ty::FloatVid { | |
189 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
190 | write!(f, "_#{}f", self.index) | |
191 | } | |
192 | } | |
193 | ||
194 | impl fmt::Debug for ty::RegionVid { | |
195 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
196 | write!(f, "'_#{}r", self.index()) | |
197 | } | |
198 | } | |
199 | ||
200 | impl fmt::Debug for ty::InferTy { | |
201 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
202 | match *self { | |
203 | ty::TyVar(ref v) => v.fmt(f), | |
204 | ty::IntVar(ref v) => v.fmt(f), | |
205 | ty::FloatVar(ref v) => v.fmt(f), | |
206 | ty::FreshTy(v) => write!(f, "FreshTy({:?})", v), | |
207 | ty::FreshIntTy(v) => write!(f, "FreshIntTy({:?})", v), | |
208 | ty::FreshFloatTy(v) => write!(f, "FreshFloatTy({:?})", v), | |
209 | } | |
210 | } | |
211 | } | |
212 | ||
213 | impl fmt::Debug for ty::IntVarValue { | |
214 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
215 | match *self { | |
216 | ty::IntType(ref v) => v.fmt(f), | |
217 | ty::UintType(ref v) => v.fmt(f), | |
218 | } | |
219 | } | |
220 | } | |
221 | ||
222 | impl fmt::Debug for ty::FloatVarValue { | |
223 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
224 | self.0.fmt(f) | |
225 | } | |
226 | } | |
227 | ||
228 | impl fmt::Debug for ty::TraitRef<'tcx> { | |
229 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
60c5eb7d | 230 | fmt::Display::fmt(self, f) |
532ac7d7 XL |
231 | } |
232 | } | |
233 | ||
234 | impl fmt::Debug for Ty<'tcx> { | |
235 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
236 | fmt::Display::fmt(self, f) | |
237 | } | |
238 | } | |
239 | ||
240 | impl fmt::Debug for ty::ParamTy { | |
241 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
48663c56 | 242 | write!(f, "{}/#{}", self.name, self.index) |
532ac7d7 XL |
243 | } |
244 | } | |
245 | ||
246 | impl fmt::Debug for ty::ParamConst { | |
247 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
248 | write!(f, "{}/#{}", self.name, self.index) | |
249 | } | |
250 | } | |
251 | ||
252 | impl fmt::Debug for ty::TraitPredicate<'tcx> { | |
253 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
254 | write!(f, "TraitPredicate({:?})", self.trait_ref) | |
255 | } | |
256 | } | |
257 | ||
258 | impl fmt::Debug for ty::ProjectionPredicate<'tcx> { | |
259 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
260 | write!(f, "ProjectionPredicate({:?}, {:?})", self.projection_ty, self.ty) | |
261 | } | |
262 | } | |
263 | ||
264 | impl fmt::Debug for ty::Predicate<'tcx> { | |
265 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { | |
266 | match *self { | |
267 | ty::Predicate::Trait(ref a) => a.fmt(f), | |
268 | ty::Predicate::Subtype(ref pair) => pair.fmt(f), | |
269 | ty::Predicate::RegionOutlives(ref pair) => pair.fmt(f), | |
270 | ty::Predicate::TypeOutlives(ref pair) => pair.fmt(f), | |
271 | ty::Predicate::Projection(ref pair) => pair.fmt(f), | |
272 | ty::Predicate::WellFormed(ty) => write!(f, "WellFormed({:?})", ty), | |
273 | ty::Predicate::ObjectSafe(trait_def_id) => { | |
274 | write!(f, "ObjectSafe({:?})", trait_def_id) | |
275 | } | |
276 | ty::Predicate::ClosureKind(closure_def_id, closure_substs, kind) => { | |
277 | write!(f, "ClosureKind({:?}, {:?}, {:?})", | |
278 | closure_def_id, closure_substs, kind) | |
279 | } | |
280 | ty::Predicate::ConstEvaluatable(def_id, substs) => { | |
281 | write!(f, "ConstEvaluatable({:?}, {:?})", def_id, substs) | |
282 | } | |
283 | } | |
284 | } | |
285 | } | |
286 | ||
ff7c6d11 XL |
287 | /////////////////////////////////////////////////////////////////////////// |
288 | // Atomic structs | |
289 | // | |
290 | // For things that don't carry any arena-allocated data (and are | |
291 | // copy...), just add them to this list. | |
292 | ||
0531ce1d | 293 | CloneTypeFoldableAndLiftImpls! { |
ff7c6d11 | 294 | (), |
0531ce1d XL |
295 | bool, |
296 | usize, | |
9fa01778 | 297 | crate::ty::layout::VariantIdx, |
0531ce1d | 298 | u64, |
0731742a | 299 | String, |
9fa01778 | 300 | crate::middle::region::Scope, |
0531ce1d XL |
301 | ::syntax::ast::FloatTy, |
302 | ::syntax::ast::NodeId, | |
303 | ::syntax_pos::symbol::Symbol, | |
48663c56 | 304 | crate::hir::def::Res, |
9fa01778 | 305 | crate::hir::def_id::DefId, |
60c5eb7d | 306 | crate::hir::InlineAsmInner, |
9fa01778 XL |
307 | crate::hir::MatchSource, |
308 | crate::hir::Mutability, | |
309 | crate::hir::Unsafety, | |
83c7162d | 310 | ::rustc_target::spec::abi::Abi, |
9fa01778 XL |
311 | crate::mir::Local, |
312 | crate::mir::Promoted, | |
313 | crate::traits::Reveal, | |
314 | crate::ty::adjustment::AutoBorrowMutability, | |
315 | crate::ty::AdtKind, | |
0531ce1d XL |
316 | // Including `BoundRegion` is a *bit* dubious, but direct |
317 | // references to bound region appear in `ty::Error`, and aren't | |
318 | // really meant to be folded. In general, we can only fold a fully | |
319 | // general `Region`. | |
9fa01778 | 320 | crate::ty::BoundRegion, |
532ac7d7 | 321 | crate::ty::Placeholder<crate::ty::BoundRegion>, |
9fa01778 | 322 | crate::ty::ClosureKind, |
532ac7d7 XL |
323 | crate::ty::FreeRegion, |
324 | crate::ty::InferTy, | |
9fa01778 | 325 | crate::ty::IntVarValue, |
532ac7d7 | 326 | crate::ty::ParamConst, |
9fa01778 | 327 | crate::ty::ParamTy, |
48663c56 | 328 | crate::ty::adjustment::PointerCast, |
532ac7d7 | 329 | crate::ty::RegionVid, |
9fa01778 XL |
330 | crate::ty::UniverseIndex, |
331 | crate::ty::Variance, | |
ff7c6d11 XL |
332 | ::syntax_pos::Span, |
333 | } | |
334 | ||
e9174d1e SL |
335 | /////////////////////////////////////////////////////////////////////////// |
336 | // Lift implementations | |
337 | ||
532ac7d7 | 338 | // FIXME(eddyb) replace all the uses of `Option::map` with `?`. |
e9174d1e SL |
339 | impl<'tcx, A: Lift<'tcx>, B: Lift<'tcx>> Lift<'tcx> for (A, B) { |
340 | type Lifted = (A::Lifted, B::Lifted); | |
dc9dc135 | 341 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
e9174d1e SL |
342 | tcx.lift(&self.0).and_then(|a| tcx.lift(&self.1).map(|b| (a, b))) |
343 | } | |
344 | } | |
345 | ||
ea8adc8c XL |
346 | impl<'tcx, A: Lift<'tcx>, B: Lift<'tcx>, C: Lift<'tcx>> Lift<'tcx> for (A, B, C) { |
347 | type Lifted = (A::Lifted, B::Lifted, C::Lifted); | |
dc9dc135 | 348 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
ea8adc8c XL |
349 | tcx.lift(&self.0).and_then(|a| { |
350 | tcx.lift(&self.1).and_then(|b| tcx.lift(&self.2).map(|c| (a, b, c))) | |
351 | }) | |
dc9dc135 | 352 | } |
ea8adc8c XL |
353 | } |
354 | ||
a7813a04 XL |
355 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for Option<T> { |
356 | type Lifted = Option<T::Lifted>; | |
dc9dc135 | 357 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
a7813a04 XL |
358 | match *self { |
359 | Some(ref x) => tcx.lift(x).map(Some), | |
360 | None => Some(None) | |
361 | } | |
362 | } | |
363 | } | |
364 | ||
365 | impl<'tcx, T: Lift<'tcx>, E: Lift<'tcx>> Lift<'tcx> for Result<T, E> { | |
366 | type Lifted = Result<T::Lifted, E::Lifted>; | |
dc9dc135 | 367 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
a7813a04 XL |
368 | match *self { |
369 | Ok(ref x) => tcx.lift(x).map(Ok), | |
370 | Err(ref e) => tcx.lift(e).map(Err) | |
371 | } | |
372 | } | |
373 | } | |
374 | ||
ea8adc8c XL |
375 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for Box<T> { |
376 | type Lifted = Box<T::Lifted>; | |
dc9dc135 | 377 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
ea8adc8c XL |
378 | tcx.lift(&**self).map(Box::new) |
379 | } | |
380 | } | |
381 | ||
dc9dc135 XL |
382 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for Rc<T> { |
383 | type Lifted = Rc<T::Lifted>; | |
384 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { | |
385 | tcx.lift(&**self).map(Rc::new) | |
386 | } | |
387 | } | |
388 | ||
389 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for Arc<T> { | |
390 | type Lifted = Arc<T::Lifted>; | |
391 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { | |
392 | tcx.lift(&**self).map(Arc::new) | |
393 | } | |
394 | } | |
395 | ||
e9174d1e SL |
396 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for [T] { |
397 | type Lifted = Vec<T::Lifted>; | |
dc9dc135 | 398 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
b039eaaf SL |
399 | // type annotation needed to inform `projection_must_outlive` |
400 | let mut result : Vec<<T as Lift<'tcx>>::Lifted> | |
401 | = Vec::with_capacity(self.len()); | |
e9174d1e SL |
402 | for x in self { |
403 | if let Some(value) = tcx.lift(x) { | |
404 | result.push(value); | |
405 | } else { | |
406 | return None; | |
407 | } | |
408 | } | |
409 | Some(result) | |
410 | } | |
411 | } | |
412 | ||
a7813a04 XL |
413 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for Vec<T> { |
414 | type Lifted = Vec<T::Lifted>; | |
dc9dc135 | 415 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
a7813a04 XL |
416 | tcx.lift(&self[..]) |
417 | } | |
418 | } | |
419 | ||
ff7c6d11 XL |
420 | impl<'tcx, I: Idx, T: Lift<'tcx>> Lift<'tcx> for IndexVec<I, T> { |
421 | type Lifted = IndexVec<I, T::Lifted>; | |
dc9dc135 | 422 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
ff7c6d11 XL |
423 | self.iter() |
424 | .map(|e| tcx.lift(e)) | |
425 | .collect() | |
426 | } | |
427 | } | |
428 | ||
9e0c209e SL |
429 | impl<'a, 'tcx> Lift<'tcx> for ty::TraitRef<'a> { |
430 | type Lifted = ty::TraitRef<'tcx>; | |
dc9dc135 | 431 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
9e0c209e SL |
432 | tcx.lift(&self.substs).map(|substs| ty::TraitRef { |
433 | def_id: self.def_id, | |
041b39d2 | 434 | substs, |
9e0c209e | 435 | }) |
e9174d1e SL |
436 | } |
437 | } | |
438 | ||
9e0c209e SL |
439 | impl<'a, 'tcx> Lift<'tcx> for ty::ExistentialTraitRef<'a> { |
440 | type Lifted = ty::ExistentialTraitRef<'tcx>; | |
dc9dc135 | 441 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
9e0c209e | 442 | tcx.lift(&self.substs).map(|substs| ty::ExistentialTraitRef { |
e9174d1e | 443 | def_id: self.def_id, |
041b39d2 | 444 | substs, |
e9174d1e SL |
445 | }) |
446 | } | |
447 | } | |
448 | ||
532ac7d7 XL |
449 | impl<'a, 'tcx> Lift<'tcx> for ty::ExistentialPredicate<'a> { |
450 | type Lifted = ty::ExistentialPredicate<'tcx>; | |
dc9dc135 | 451 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
532ac7d7 XL |
452 | match self { |
453 | ty::ExistentialPredicate::Trait(x) => { | |
454 | tcx.lift(x).map(ty::ExistentialPredicate::Trait) | |
455 | } | |
456 | ty::ExistentialPredicate::Projection(x) => { | |
457 | tcx.lift(x).map(ty::ExistentialPredicate::Projection) | |
458 | } | |
459 | ty::ExistentialPredicate::AutoTrait(def_id) => { | |
460 | Some(ty::ExistentialPredicate::AutoTrait(*def_id)) | |
461 | } | |
462 | } | |
463 | } | |
464 | } | |
465 | ||
e9174d1e SL |
466 | impl<'a, 'tcx> Lift<'tcx> for ty::TraitPredicate<'a> { |
467 | type Lifted = ty::TraitPredicate<'tcx>; | |
dc9dc135 | 468 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<ty::TraitPredicate<'tcx>> { |
e9174d1e | 469 | tcx.lift(&self.trait_ref).map(|trait_ref| ty::TraitPredicate { |
041b39d2 | 470 | trait_ref, |
e9174d1e SL |
471 | }) |
472 | } | |
473 | } | |
474 | ||
cc61c64b XL |
475 | impl<'a, 'tcx> Lift<'tcx> for ty::SubtypePredicate<'a> { |
476 | type Lifted = ty::SubtypePredicate<'tcx>; | |
dc9dc135 | 477 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<ty::SubtypePredicate<'tcx>> { |
cc61c64b XL |
478 | tcx.lift(&(self.a, self.b)).map(|(a, b)| ty::SubtypePredicate { |
479 | a_is_expected: self.a_is_expected, | |
041b39d2 XL |
480 | a, |
481 | b, | |
cc61c64b XL |
482 | }) |
483 | } | |
484 | } | |
485 | ||
dc9dc135 | 486 | impl<'tcx, A: Copy + Lift<'tcx>, B: Copy + Lift<'tcx>> Lift<'tcx> for ty::OutlivesPredicate<A, B> { |
e9174d1e | 487 | type Lifted = ty::OutlivesPredicate<A::Lifted, B::Lifted>; |
dc9dc135 | 488 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
e9174d1e SL |
489 | tcx.lift(&(self.0, self.1)).map(|(a, b)| ty::OutlivesPredicate(a, b)) |
490 | } | |
491 | } | |
492 | ||
5bcae85e SL |
493 | impl<'a, 'tcx> Lift<'tcx> for ty::ProjectionTy<'a> { |
494 | type Lifted = ty::ProjectionTy<'tcx>; | |
dc9dc135 | 495 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<ty::ProjectionTy<'tcx>> { |
041b39d2 XL |
496 | tcx.lift(&self.substs).map(|substs| { |
497 | ty::ProjectionTy { | |
498 | item_def_id: self.item_def_id, | |
3b2f2976 | 499 | substs, |
041b39d2 | 500 | } |
5bcae85e SL |
501 | }) |
502 | } | |
503 | } | |
504 | ||
e9174d1e SL |
505 | impl<'a, 'tcx> Lift<'tcx> for ty::ProjectionPredicate<'a> { |
506 | type Lifted = ty::ProjectionPredicate<'tcx>; | |
dc9dc135 | 507 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<ty::ProjectionPredicate<'tcx>> { |
5bcae85e | 508 | tcx.lift(&(self.projection_ty, self.ty)).map(|(projection_ty, ty)| { |
e9174d1e | 509 | ty::ProjectionPredicate { |
041b39d2 XL |
510 | projection_ty, |
511 | ty, | |
e9174d1e SL |
512 | } |
513 | }) | |
514 | } | |
515 | } | |
516 | ||
9e0c209e SL |
517 | impl<'a, 'tcx> Lift<'tcx> for ty::ExistentialProjection<'a> { |
518 | type Lifted = ty::ExistentialProjection<'tcx>; | |
dc9dc135 | 519 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
041b39d2 | 520 | tcx.lift(&self.substs).map(|substs| { |
9e0c209e | 521 | ty::ExistentialProjection { |
041b39d2 XL |
522 | substs, |
523 | ty: tcx.lift(&self.ty).expect("type must lift when substs do"), | |
524 | item_def_id: self.item_def_id, | |
9e0c209e SL |
525 | } |
526 | }) | |
527 | } | |
528 | } | |
529 | ||
a7813a04 XL |
530 | impl<'a, 'tcx> Lift<'tcx> for ty::Predicate<'a> { |
531 | type Lifted = ty::Predicate<'tcx>; | |
dc9dc135 | 532 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
a7813a04 XL |
533 | match *self { |
534 | ty::Predicate::Trait(ref binder) => { | |
535 | tcx.lift(binder).map(ty::Predicate::Trait) | |
536 | } | |
cc61c64b XL |
537 | ty::Predicate::Subtype(ref binder) => { |
538 | tcx.lift(binder).map(ty::Predicate::Subtype) | |
539 | } | |
a7813a04 XL |
540 | ty::Predicate::RegionOutlives(ref binder) => { |
541 | tcx.lift(binder).map(ty::Predicate::RegionOutlives) | |
542 | } | |
543 | ty::Predicate::TypeOutlives(ref binder) => { | |
544 | tcx.lift(binder).map(ty::Predicate::TypeOutlives) | |
545 | } | |
546 | ty::Predicate::Projection(ref binder) => { | |
547 | tcx.lift(binder).map(ty::Predicate::Projection) | |
548 | } | |
549 | ty::Predicate::WellFormed(ty) => { | |
550 | tcx.lift(&ty).map(ty::Predicate::WellFormed) | |
551 | } | |
ff7c6d11 XL |
552 | ty::Predicate::ClosureKind(closure_def_id, closure_substs, kind) => { |
553 | tcx.lift(&closure_substs) | |
554 | .map(|closure_substs| ty::Predicate::ClosureKind(closure_def_id, | |
555 | closure_substs, | |
556 | kind)) | |
a7813a04 XL |
557 | } |
558 | ty::Predicate::ObjectSafe(trait_def_id) => { | |
559 | Some(ty::Predicate::ObjectSafe(trait_def_id)) | |
560 | } | |
ea8adc8c XL |
561 | ty::Predicate::ConstEvaluatable(def_id, substs) => { |
562 | tcx.lift(&substs).map(|substs| { | |
563 | ty::Predicate::ConstEvaluatable(def_id, substs) | |
564 | }) | |
565 | } | |
a7813a04 XL |
566 | } |
567 | } | |
568 | } | |
569 | ||
e9174d1e SL |
570 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for ty::Binder<T> { |
571 | type Lifted = ty::Binder<T::Lifted>; | |
dc9dc135 | 572 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
83c7162d | 573 | tcx.lift(self.skip_binder()).map(ty::Binder::bind) |
e9174d1e SL |
574 | } |
575 | } | |
576 | ||
ea8adc8c XL |
577 | impl<'a, 'tcx> Lift<'tcx> for ty::ParamEnv<'a> { |
578 | type Lifted = ty::ParamEnv<'tcx>; | |
dc9dc135 | 579 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
ea8adc8c XL |
580 | tcx.lift(&self.caller_bounds).map(|caller_bounds| { |
581 | ty::ParamEnv { | |
582 | reveal: self.reveal, | |
583 | caller_bounds, | |
0731742a | 584 | def_id: self.def_id, |
ea8adc8c XL |
585 | } |
586 | }) | |
587 | } | |
588 | } | |
589 | ||
590 | impl<'a, 'tcx, T: Lift<'tcx>> Lift<'tcx> for ty::ParamEnvAnd<'a, T> { | |
591 | type Lifted = ty::ParamEnvAnd<'tcx, T::Lifted>; | |
dc9dc135 | 592 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
ea8adc8c XL |
593 | tcx.lift(&self.param_env).and_then(|param_env| { |
594 | tcx.lift(&self.value).map(|value| { | |
595 | ty::ParamEnvAnd { | |
596 | param_env, | |
597 | value, | |
598 | } | |
599 | }) | |
600 | }) | |
601 | } | |
602 | } | |
603 | ||
a7813a04 XL |
604 | impl<'a, 'tcx> Lift<'tcx> for ty::ClosureSubsts<'a> { |
605 | type Lifted = ty::ClosureSubsts<'tcx>; | |
dc9dc135 | 606 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
476ff2be | 607 | tcx.lift(&self.substs).map(|substs| { |
94b46f34 | 608 | ty::ClosureSubsts { substs } |
a7813a04 XL |
609 | }) |
610 | } | |
611 | } | |
612 | ||
94b46f34 XL |
613 | impl<'a, 'tcx> Lift<'tcx> for ty::GeneratorSubsts<'a> { |
614 | type Lifted = ty::GeneratorSubsts<'tcx>; | |
dc9dc135 | 615 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
94b46f34 XL |
616 | tcx.lift(&self.substs).map(|substs| { |
617 | ty::GeneratorSubsts { substs } | |
ea8adc8c XL |
618 | }) |
619 | } | |
620 | } | |
621 | ||
7cac9316 XL |
622 | impl<'a, 'tcx> Lift<'tcx> for ty::adjustment::Adjustment<'a> { |
623 | type Lifted = ty::adjustment::Adjustment<'tcx>; | |
dc9dc135 | 624 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
7cac9316 XL |
625 | tcx.lift(&self.kind).and_then(|kind| { |
626 | tcx.lift(&self.target).map(|target| { | |
627 | ty::adjustment::Adjustment { kind, target } | |
628 | }) | |
629 | }) | |
630 | } | |
631 | } | |
632 | ||
633 | impl<'a, 'tcx> Lift<'tcx> for ty::adjustment::Adjust<'a> { | |
634 | type Lifted = ty::adjustment::Adjust<'tcx>; | |
dc9dc135 | 635 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
7cac9316 XL |
636 | match *self { |
637 | ty::adjustment::Adjust::NeverToAny => | |
638 | Some(ty::adjustment::Adjust::NeverToAny), | |
48663c56 XL |
639 | ty::adjustment::Adjust::Pointer(ptr) => |
640 | Some(ty::adjustment::Adjust::Pointer(ptr)), | |
7cac9316 XL |
641 | ty::adjustment::Adjust::Deref(ref overloaded) => { |
642 | tcx.lift(overloaded).map(ty::adjustment::Adjust::Deref) | |
643 | } | |
644 | ty::adjustment::Adjust::Borrow(ref autoref) => { | |
645 | tcx.lift(autoref).map(ty::adjustment::Adjust::Borrow) | |
646 | } | |
647 | } | |
648 | } | |
649 | } | |
650 | ||
651 | impl<'a, 'tcx> Lift<'tcx> for ty::adjustment::OverloadedDeref<'a> { | |
652 | type Lifted = ty::adjustment::OverloadedDeref<'tcx>; | |
dc9dc135 | 653 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
7cac9316 XL |
654 | tcx.lift(&self.region).map(|region| { |
655 | ty::adjustment::OverloadedDeref { | |
656 | region, | |
657 | mutbl: self.mutbl, | |
a7813a04 XL |
658 | } |
659 | }) | |
660 | } | |
661 | } | |
662 | ||
c30ab7b3 SL |
663 | impl<'a, 'tcx> Lift<'tcx> for ty::adjustment::AutoBorrow<'a> { |
664 | type Lifted = ty::adjustment::AutoBorrow<'tcx>; | |
dc9dc135 | 665 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
a7813a04 | 666 | match *self { |
c30ab7b3 SL |
667 | ty::adjustment::AutoBorrow::Ref(r, m) => { |
668 | tcx.lift(&r).map(|r| ty::adjustment::AutoBorrow::Ref(r, m)) | |
a7813a04 | 669 | } |
c30ab7b3 SL |
670 | ty::adjustment::AutoBorrow::RawPtr(m) => { |
671 | Some(ty::adjustment::AutoBorrow::RawPtr(m)) | |
a7813a04 XL |
672 | } |
673 | } | |
674 | } | |
675 | } | |
676 | ||
ea8adc8c XL |
677 | impl<'a, 'tcx> Lift<'tcx> for ty::GenSig<'a> { |
678 | type Lifted = ty::GenSig<'tcx>; | |
dc9dc135 | 679 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
ea8adc8c | 680 | tcx.lift(&(self.yield_ty, self.return_ty)) |
0bf4aa26 XL |
681 | .map(|(yield_ty, return_ty)| { |
682 | ty::GenSig { | |
683 | yield_ty, | |
684 | return_ty, | |
685 | } | |
686 | }) | |
ea8adc8c XL |
687 | } |
688 | } | |
689 | ||
a7813a04 XL |
690 | impl<'a, 'tcx> Lift<'tcx> for ty::FnSig<'a> { |
691 | type Lifted = ty::FnSig<'tcx>; | |
dc9dc135 | 692 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
476ff2be SL |
693 | tcx.lift(&self.inputs_and_output).map(|x| { |
694 | ty::FnSig { | |
695 | inputs_and_output: x, | |
532ac7d7 | 696 | c_variadic: self.c_variadic, |
a7813a04 | 697 | unsafety: self.unsafety, |
8bb4bdeb | 698 | abi: self.abi, |
a7813a04 XL |
699 | } |
700 | }) | |
701 | } | |
702 | } | |
703 | ||
704 | impl<'tcx, T: Lift<'tcx>> Lift<'tcx> for ty::error::ExpectedFound<T> { | |
705 | type Lifted = ty::error::ExpectedFound<T::Lifted>; | |
dc9dc135 | 706 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
a7813a04 XL |
707 | tcx.lift(&self.expected).and_then(|expected| { |
708 | tcx.lift(&self.found).map(|found| { | |
709 | ty::error::ExpectedFound { | |
041b39d2 XL |
710 | expected, |
711 | found, | |
a7813a04 XL |
712 | } |
713 | }) | |
714 | }) | |
715 | } | |
716 | } | |
717 | ||
a7813a04 XL |
718 | impl<'a, 'tcx> Lift<'tcx> for ty::error::TypeError<'a> { |
719 | type Lifted = ty::error::TypeError<'tcx>; | |
dc9dc135 | 720 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
9fa01778 | 721 | use crate::ty::error::TypeError::*; |
a7813a04 XL |
722 | |
723 | Some(match *self { | |
724 | Mismatch => Mismatch, | |
725 | UnsafetyMismatch(x) => UnsafetyMismatch(x), | |
726 | AbiMismatch(x) => AbiMismatch(x), | |
727 | Mutability => Mutability, | |
a7813a04 XL |
728 | TupleSize(x) => TupleSize(x), |
729 | FixedArraySize(x) => FixedArraySize(x), | |
a7813a04 | 730 | ArgCount => ArgCount, |
9e0c209e SL |
731 | RegionsDoesNotOutlive(a, b) => { |
732 | return tcx.lift(&(a, b)).map(|(a, b)| RegionsDoesNotOutlive(a, b)) | |
733 | } | |
ea8adc8c XL |
734 | RegionsInsufficientlyPolymorphic(a, b) => { |
735 | return tcx.lift(&b).map(|b| RegionsInsufficientlyPolymorphic(a, b)) | |
9e0c209e | 736 | } |
ea8adc8c XL |
737 | RegionsOverlyPolymorphic(a, b) => { |
738 | return tcx.lift(&b).map(|b| RegionsOverlyPolymorphic(a, b)) | |
a7813a04 | 739 | } |
0731742a | 740 | RegionsPlaceholderMismatch => RegionsPlaceholderMismatch, |
a7813a04 XL |
741 | IntMismatch(x) => IntMismatch(x), |
742 | FloatMismatch(x) => FloatMismatch(x), | |
743 | Traits(x) => Traits(x), | |
a7813a04 | 744 | VariadicMismatch(x) => VariadicMismatch(x), |
ff7c6d11 | 745 | CyclicTy(t) => return tcx.lift(&t).map(|t| CyclicTy(t)), |
041b39d2 | 746 | ProjectionMismatched(x) => ProjectionMismatched(x), |
a7813a04 | 747 | ProjectionBoundsLength(x) => ProjectionBoundsLength(x), |
a7813a04 | 748 | Sorts(ref x) => return tcx.lift(x).map(Sorts), |
48663c56 XL |
749 | ExistentialMismatch(ref x) => return tcx.lift(x).map(ExistentialMismatch), |
750 | ConstMismatch(ref x) => return tcx.lift(x).map(ConstMismatch), | |
e1599b0c | 751 | IntrinsicCast => IntrinsicCast, |
e74abb32 | 752 | ObjectUnsafeCoercion(ref x) => return tcx.lift(x).map(ObjectUnsafeCoercion), |
a7813a04 XL |
753 | }) |
754 | } | |
755 | } | |
756 | ||
0531ce1d XL |
757 | impl<'a, 'tcx> Lift<'tcx> for ty::InstanceDef<'a> { |
758 | type Lifted = ty::InstanceDef<'tcx>; | |
dc9dc135 | 759 | fn lift_to_tcx(&self, tcx: TyCtxt<'tcx>) -> Option<Self::Lifted> { |
0531ce1d XL |
760 | match *self { |
761 | ty::InstanceDef::Item(def_id) => | |
762 | Some(ty::InstanceDef::Item(def_id)), | |
a1dfa0c6 XL |
763 | ty::InstanceDef::VtableShim(def_id) => |
764 | Some(ty::InstanceDef::VtableShim(def_id)), | |
e74abb32 XL |
765 | ty::InstanceDef::ReifyShim(def_id) => |
766 | Some(ty::InstanceDef::ReifyShim(def_id)), | |
0531ce1d XL |
767 | ty::InstanceDef::Intrinsic(def_id) => |
768 | Some(ty::InstanceDef::Intrinsic(def_id)), | |
769 | ty::InstanceDef::FnPtrShim(def_id, ref ty) => | |
770 | Some(ty::InstanceDef::FnPtrShim(def_id, tcx.lift(ty)?)), | |
771 | ty::InstanceDef::Virtual(def_id, n) => | |
772 | Some(ty::InstanceDef::Virtual(def_id, n)), | |
773 | ty::InstanceDef::ClosureOnceShim { call_once } => | |
774 | Some(ty::InstanceDef::ClosureOnceShim { call_once }), | |
775 | ty::InstanceDef::DropGlue(def_id, ref ty) => | |
776 | Some(ty::InstanceDef::DropGlue(def_id, tcx.lift(ty)?)), | |
777 | ty::InstanceDef::CloneShim(def_id, ref ty) => | |
778 | Some(ty::InstanceDef::CloneShim(def_id, tcx.lift(ty)?)), | |
779 | } | |
780 | } | |
781 | } | |
782 | ||
e9174d1e SL |
783 | /////////////////////////////////////////////////////////////////////////// |
784 | // TypeFoldable implementations. | |
785 | // | |
786 | // Ideally, each type should invoke `folder.fold_foo(self)` and | |
787 | // nothing else. In some cases, though, we haven't gotten around to | |
788 | // adding methods on the `folder` yet, and thus the folding is | |
789 | // hard-coded here. This is less-flexible, because folders cannot | |
790 | // override the behavior, but there are a lot of random types and one | |
791 | // can easily refactor the folding into the TypeFolder trait as | |
792 | // needed. | |
793 | ||
0531ce1d XL |
794 | /// AdtDefs are basically the same as a DefId. |
795 | impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::AdtDef { | |
dc9dc135 | 796 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, _folder: &mut F) -> Self { |
0531ce1d XL |
797 | *self |
798 | } | |
799 | ||
800 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, _visitor: &mut V) -> bool { | |
801 | false | |
802 | } | |
803 | } | |
804 | ||
dc9dc135 XL |
805 | impl<'tcx, T: TypeFoldable<'tcx>, U: TypeFoldable<'tcx>> TypeFoldable<'tcx> for (T, U) { |
806 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> (T, U) { | |
e9174d1e SL |
807 | (self.0.fold_with(folder), self.1.fold_with(folder)) |
808 | } | |
9cc50fc6 SL |
809 | |
810 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
811 | self.0.visit_with(visitor) || self.1.visit_with(visitor) | |
812 | } | |
e9174d1e SL |
813 | } |
814 | ||
0531ce1d XL |
815 | EnumTypeFoldableImpl! { |
816 | impl<'tcx, T> TypeFoldable<'tcx> for Option<T> { | |
817 | (Some)(a), | |
818 | (None), | |
819 | } where T: TypeFoldable<'tcx> | |
e9174d1e SL |
820 | } |
821 | ||
dc9dc135 XL |
822 | EnumTypeFoldableImpl! { |
823 | impl<'tcx, T, E> TypeFoldable<'tcx> for Result<T, E> { | |
824 | (Ok)(a), | |
825 | (Err)(a), | |
826 | } where T: TypeFoldable<'tcx>, E: TypeFoldable<'tcx>, | |
827 | } | |
828 | ||
e9174d1e | 829 | impl<'tcx, T: TypeFoldable<'tcx>> TypeFoldable<'tcx> for Rc<T> { |
dc9dc135 | 830 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e9174d1e SL |
831 | Rc::new((**self).fold_with(folder)) |
832 | } | |
9cc50fc6 SL |
833 | |
834 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
835 | (**self).visit_with(visitor) | |
836 | } | |
e9174d1e SL |
837 | } |
838 | ||
dc9dc135 XL |
839 | impl<'tcx, T: TypeFoldable<'tcx>> TypeFoldable<'tcx> for Arc<T> { |
840 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { | |
841 | Arc::new((**self).fold_with(folder)) | |
842 | } | |
843 | ||
844 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
845 | (**self).visit_with(visitor) | |
846 | } | |
847 | } | |
848 | ||
e9174d1e | 849 | impl<'tcx, T: TypeFoldable<'tcx>> TypeFoldable<'tcx> for Box<T> { |
dc9dc135 | 850 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e9174d1e SL |
851 | let content: T = (**self).fold_with(folder); |
852 | box content | |
853 | } | |
9cc50fc6 SL |
854 | |
855 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
856 | (**self).visit_with(visitor) | |
857 | } | |
e9174d1e SL |
858 | } |
859 | ||
860 | impl<'tcx, T: TypeFoldable<'tcx>> TypeFoldable<'tcx> for Vec<T> { | |
dc9dc135 | 861 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e9174d1e SL |
862 | self.iter().map(|t| t.fold_with(folder)).collect() |
863 | } | |
9cc50fc6 SL |
864 | |
865 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
866 | self.iter().any(|t| t.visit_with(visitor)) | |
867 | } | |
e9174d1e SL |
868 | } |
869 | ||
0bf4aa26 | 870 | impl<'tcx, T: TypeFoldable<'tcx>> TypeFoldable<'tcx> for Box<[T]> { |
dc9dc135 | 871 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
0bf4aa26 XL |
872 | self.iter().map(|t| t.fold_with(folder)).collect::<Vec<_>>().into_boxed_slice() |
873 | } | |
874 | ||
875 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
876 | self.iter().any(|t| t.visit_with(visitor)) | |
877 | } | |
878 | } | |
879 | ||
dc9dc135 XL |
880 | impl<'tcx, T: TypeFoldable<'tcx>> TypeFoldable<'tcx> for ty::Binder<T> { |
881 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { | |
83c7162d | 882 | self.map_bound_ref(|ty| ty.fold_with(folder)) |
9cc50fc6 SL |
883 | } |
884 | ||
dc9dc135 | 885 | fn fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e9174d1e SL |
886 | folder.fold_binder(self) |
887 | } | |
9cc50fc6 SL |
888 | |
889 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
83c7162d | 890 | self.skip_binder().visit_with(visitor) |
54a0048b SL |
891 | } |
892 | ||
893 | fn visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
894 | visitor.visit_binder(self) | |
9cc50fc6 | 895 | } |
e9174d1e SL |
896 | } |
897 | ||
b7449926 | 898 | impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::List<ty::ExistentialPredicate<'tcx>> { |
dc9dc135 | 899 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
b7449926 | 900 | let v = self.iter().map(|p| p.fold_with(folder)).collect::<SmallVec<[_; 8]>>(); |
476ff2be SL |
901 | folder.tcx().intern_existential_predicates(&v) |
902 | } | |
903 | ||
904 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
905 | self.iter().any(|p| p.visit_with(visitor)) | |
906 | } | |
907 | } | |
908 | ||
b7449926 | 909 | impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::List<Ty<'tcx>> { |
dc9dc135 | 910 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
b7449926 | 911 | let v = self.iter().map(|t| t.fold_with(folder)).collect::<SmallVec<[_; 8]>>(); |
0531ce1d XL |
912 | folder.tcx().intern_type_list(&v) |
913 | } | |
914 | ||
915 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
916 | self.iter().any(|t| t.visit_with(visitor)) | |
917 | } | |
918 | } | |
919 | ||
532ac7d7 | 920 | impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::List<ProjectionKind> { |
dc9dc135 | 921 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
0bf4aa26 XL |
922 | let v = self.iter().map(|t| t.fold_with(folder)).collect::<SmallVec<[_; 8]>>(); |
923 | folder.tcx().intern_projs(&v) | |
924 | } | |
925 | ||
926 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
927 | self.iter().any(|t| t.visit_with(visitor)) | |
928 | } | |
929 | } | |
930 | ||
0531ce1d | 931 | impl<'tcx> TypeFoldable<'tcx> for ty::instance::Instance<'tcx> { |
dc9dc135 | 932 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
9fa01778 | 933 | use crate::ty::InstanceDef::*; |
0531ce1d XL |
934 | Self { |
935 | substs: self.substs.fold_with(folder), | |
936 | def: match self.def { | |
937 | Item(did) => Item(did.fold_with(folder)), | |
a1dfa0c6 | 938 | VtableShim(did) => VtableShim(did.fold_with(folder)), |
e74abb32 | 939 | ReifyShim(did) => ReifyShim(did.fold_with(folder)), |
0531ce1d XL |
940 | Intrinsic(did) => Intrinsic(did.fold_with(folder)), |
941 | FnPtrShim(did, ty) => FnPtrShim( | |
942 | did.fold_with(folder), | |
943 | ty.fold_with(folder), | |
944 | ), | |
945 | Virtual(did, i) => Virtual( | |
946 | did.fold_with(folder), | |
947 | i, | |
948 | ), | |
949 | ClosureOnceShim { call_once } => ClosureOnceShim { | |
950 | call_once: call_once.fold_with(folder), | |
951 | }, | |
952 | DropGlue(did, ty) => DropGlue( | |
953 | did.fold_with(folder), | |
954 | ty.fold_with(folder), | |
955 | ), | |
956 | CloneShim(did, ty) => CloneShim( | |
957 | did.fold_with(folder), | |
958 | ty.fold_with(folder), | |
959 | ), | |
960 | }, | |
9cc50fc6 SL |
961 | } |
962 | } | |
963 | ||
964 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
9fa01778 | 965 | use crate::ty::InstanceDef::*; |
0531ce1d XL |
966 | self.substs.visit_with(visitor) || |
967 | match self.def { | |
e74abb32 | 968 | Item(did) | VtableShim(did) | ReifyShim(did) | Intrinsic(did) | Virtual(did, _) => { |
0bf4aa26 | 969 | did.visit_with(visitor) |
0531ce1d | 970 | }, |
0bf4aa26 XL |
971 | FnPtrShim(did, ty) | CloneShim(did, ty) => { |
972 | did.visit_with(visitor) || ty.visit_with(visitor) | |
0531ce1d | 973 | }, |
0bf4aa26 XL |
974 | DropGlue(did, ty) => { |
975 | did.visit_with(visitor) || ty.visit_with(visitor) | |
0531ce1d | 976 | }, |
0bf4aa26 | 977 | ClosureOnceShim { call_once } => call_once.visit_with(visitor), |
476ff2be | 978 | } |
9cc50fc6 | 979 | } |
e9174d1e SL |
980 | } |
981 | ||
0531ce1d | 982 | impl<'tcx> TypeFoldable<'tcx> for interpret::GlobalId<'tcx> { |
dc9dc135 | 983 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
0531ce1d XL |
984 | Self { |
985 | instance: self.instance.fold_with(folder), | |
986 | promoted: self.promoted | |
987 | } | |
a7813a04 XL |
988 | } |
989 | ||
990 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
0531ce1d | 991 | self.instance.visit_with(visitor) |
a7813a04 XL |
992 | } |
993 | } | |
994 | ||
e9174d1e | 995 | impl<'tcx> TypeFoldable<'tcx> for Ty<'tcx> { |
dc9dc135 | 996 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e74abb32 | 997 | let kind = match self.kind { |
b7449926 XL |
998 | ty::RawPtr(tm) => ty::RawPtr(tm.fold_with(folder)), |
999 | ty::Array(typ, sz) => ty::Array(typ.fold_with(folder), sz.fold_with(folder)), | |
1000 | ty::Slice(typ) => ty::Slice(typ.fold_with(folder)), | |
1001 | ty::Adt(tid, substs) => ty::Adt(tid, substs.fold_with(folder)), | |
1002 | ty::Dynamic(ref trait_ty, ref region) => | |
1003 | ty::Dynamic(trait_ty.fold_with(folder), region.fold_with(folder)), | |
1004 | ty::Tuple(ts) => ty::Tuple(ts.fold_with(folder)), | |
1005 | ty::FnDef(def_id, substs) => { | |
1006 | ty::FnDef(def_id, substs.fold_with(folder)) | |
9cc50fc6 | 1007 | } |
b7449926 XL |
1008 | ty::FnPtr(f) => ty::FnPtr(f.fold_with(folder)), |
1009 | ty::Ref(ref r, ty, mutbl) => { | |
1010 | ty::Ref(r.fold_with(folder), ty.fold_with(folder), mutbl) | |
9cc50fc6 | 1011 | } |
b7449926 XL |
1012 | ty::Generator(did, substs, movability) => { |
1013 | ty::Generator( | |
94b46f34 XL |
1014 | did, |
1015 | substs.fold_with(folder), | |
1016 | movability) | |
ea8adc8c | 1017 | } |
b7449926 XL |
1018 | ty::GeneratorWitness(types) => ty::GeneratorWitness(types.fold_with(folder)), |
1019 | ty::Closure(did, substs) => ty::Closure(did, substs.fold_with(folder)), | |
1020 | ty::Projection(ref data) => ty::Projection(data.fold_with(folder)), | |
0bf4aa26 XL |
1021 | ty::UnnormalizedProjection(ref data) => { |
1022 | ty::UnnormalizedProjection(data.fold_with(folder)) | |
1023 | } | |
b7449926 | 1024 | ty::Opaque(did, substs) => ty::Opaque(did, substs.fold_with(folder)), |
a1dfa0c6 XL |
1025 | |
1026 | ty::Bool | | |
1027 | ty::Char | | |
1028 | ty::Str | | |
1029 | ty::Int(_) | | |
1030 | ty::Uint(_) | | |
1031 | ty::Float(_) | | |
1032 | ty::Error | | |
1033 | ty::Infer(_) | | |
1034 | ty::Param(..) | | |
1035 | ty::Bound(..) | | |
1036 | ty::Placeholder(..) | | |
1037 | ty::Never | | |
e74abb32 | 1038 | ty::Foreign(..) => return self, |
9cc50fc6 | 1039 | }; |
476ff2be | 1040 | |
e74abb32 | 1041 | if self.kind == kind { |
476ff2be SL |
1042 | self |
1043 | } else { | |
e74abb32 | 1044 | folder.tcx().mk_ty(kind) |
476ff2be | 1045 | } |
9cc50fc6 SL |
1046 | } |
1047 | ||
dc9dc135 | 1048 | fn fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e9174d1e SL |
1049 | folder.fold_ty(*self) |
1050 | } | |
9cc50fc6 SL |
1051 | |
1052 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
e74abb32 | 1053 | match self.kind { |
b7449926 XL |
1054 | ty::RawPtr(ref tm) => tm.visit_with(visitor), |
1055 | ty::Array(typ, sz) => typ.visit_with(visitor) || sz.visit_with(visitor), | |
1056 | ty::Slice(typ) => typ.visit_with(visitor), | |
1057 | ty::Adt(_, substs) => substs.visit_with(visitor), | |
1058 | ty::Dynamic(ref trait_ty, ref reg) => | |
476ff2be | 1059 | trait_ty.visit_with(visitor) || reg.visit_with(visitor), |
b7449926 XL |
1060 | ty::Tuple(ts) => ts.visit_with(visitor), |
1061 | ty::FnDef(_, substs) => substs.visit_with(visitor), | |
1062 | ty::FnPtr(ref f) => f.visit_with(visitor), | |
1063 | ty::Ref(r, ty, _) => r.visit_with(visitor) || ty.visit_with(visitor), | |
1064 | ty::Generator(_did, ref substs, _) => { | |
94b46f34 | 1065 | substs.visit_with(visitor) |
ea8adc8c | 1066 | } |
b7449926 XL |
1067 | ty::GeneratorWitness(ref types) => types.visit_with(visitor), |
1068 | ty::Closure(_did, ref substs) => substs.visit_with(visitor), | |
0bf4aa26 XL |
1069 | ty::Projection(ref data) | ty::UnnormalizedProjection(ref data) => { |
1070 | data.visit_with(visitor) | |
1071 | } | |
b7449926 | 1072 | ty::Opaque(_, ref substs) => substs.visit_with(visitor), |
a1dfa0c6 XL |
1073 | |
1074 | ty::Bool | | |
1075 | ty::Char | | |
1076 | ty::Str | | |
1077 | ty::Int(_) | | |
1078 | ty::Uint(_) | | |
1079 | ty::Float(_) | | |
1080 | ty::Error | | |
1081 | ty::Infer(_) | | |
1082 | ty::Bound(..) | | |
1083 | ty::Placeholder(..) | | |
1084 | ty::Param(..) | | |
1085 | ty::Never | | |
1086 | ty::Foreign(..) => false, | |
9cc50fc6 SL |
1087 | } |
1088 | } | |
1089 | ||
1090 | fn visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
1091 | visitor.visit_ty(self) | |
1092 | } | |
e9174d1e SL |
1093 | } |
1094 | ||
7cac9316 | 1095 | impl<'tcx> TypeFoldable<'tcx> for ty::Region<'tcx> { |
dc9dc135 | 1096 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, _folder: &mut F) -> Self { |
9cc50fc6 SL |
1097 | *self |
1098 | } | |
1099 | ||
dc9dc135 | 1100 | fn fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e9174d1e SL |
1101 | folder.fold_region(*self) |
1102 | } | |
9cc50fc6 SL |
1103 | |
1104 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, _visitor: &mut V) -> bool { | |
1105 | false | |
1106 | } | |
1107 | ||
1108 | fn visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
1109 | visitor.visit_region(*self) | |
1110 | } | |
e9174d1e SL |
1111 | } |
1112 | ||
b7449926 | 1113 | impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::List<ty::Predicate<'tcx>> { |
dc9dc135 | 1114 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
e74abb32 XL |
1115 | // This code is hot enough that it's worth specializing for a list of |
1116 | // length 0. (No other length is common enough to be worth singling | |
1117 | // out). | |
1118 | if self.len() == 0 { | |
1119 | self | |
1120 | } else { | |
1121 | // Don't bother interning if nothing changed, which is the common | |
1122 | // case. | |
1123 | let v = self.iter().map(|p| p.fold_with(folder)).collect::<SmallVec<[_; 8]>>(); | |
1124 | if v[..] == self[..] { | |
1125 | self | |
1126 | } else { | |
1127 | folder.tcx().intern_predicates(&v) | |
1128 | } | |
1129 | } | |
7cac9316 XL |
1130 | } |
1131 | ||
1132 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
1133 | self.iter().any(|p| p.visit_with(visitor)) | |
1134 | } | |
1135 | } | |
1136 | ||
8bb4bdeb | 1137 | impl<'tcx, T: TypeFoldable<'tcx>, I: Idx> TypeFoldable<'tcx> for IndexVec<I, T> { |
dc9dc135 | 1138 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
8bb4bdeb XL |
1139 | self.iter().map(|x| x.fold_with(folder)).collect() |
1140 | } | |
1141 | ||
1142 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
1143 | self.iter().any(|t| t.visit_with(visitor)) | |
1144 | } | |
1145 | } | |
041b39d2 | 1146 | |
532ac7d7 | 1147 | impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::Const<'tcx> { |
dc9dc135 | 1148 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
532ac7d7 XL |
1149 | let ty = self.ty.fold_with(folder); |
1150 | let val = self.val.fold_with(folder); | |
1151 | folder.tcx().mk_const(ty::Const { | |
1152 | ty, | |
1153 | val | |
1154 | }) | |
0731742a XL |
1155 | } |
1156 | ||
dc9dc135 | 1157 | fn fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
0731742a | 1158 | folder.fold_const(*self) |
ea8adc8c XL |
1159 | } |
1160 | ||
1161 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
532ac7d7 | 1162 | self.ty.visit_with(visitor) || self.val.visit_with(visitor) |
ea8adc8c | 1163 | } |
0731742a XL |
1164 | |
1165 | fn visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
1166 | visitor.visit_const(self) | |
1167 | } | |
ea8adc8c XL |
1168 | } |
1169 | ||
60c5eb7d | 1170 | impl<'tcx> TypeFoldable<'tcx> for ty::ConstKind<'tcx> { |
dc9dc135 | 1171 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, folder: &mut F) -> Self { |
532ac7d7 | 1172 | match *self { |
60c5eb7d XL |
1173 | ty::ConstKind::Infer(ic) => ty::ConstKind::Infer(ic.fold_with(folder)), |
1174 | ty::ConstKind::Param(p) => ty::ConstKind::Param(p.fold_with(folder)), | |
1175 | ty::ConstKind::Unevaluated(did, substs) | |
1176 | => ty::ConstKind::Unevaluated(did, substs.fold_with(folder)), | |
1177 | ty::ConstKind::Value(_) | ty::ConstKind::Bound(..) | |
1178 | | ty::ConstKind::Placeholder(..) => *self, | |
0731742a | 1179 | } |
ea8adc8c XL |
1180 | } |
1181 | ||
1182 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool { | |
532ac7d7 | 1183 | match *self { |
60c5eb7d XL |
1184 | ty::ConstKind::Infer(ic) => ic.visit_with(visitor), |
1185 | ty::ConstKind::Param(p) => p.visit_with(visitor), | |
1186 | ty::ConstKind::Unevaluated(_, substs) => substs.visit_with(visitor), | |
1187 | ty::ConstKind::Value(_) | ty::ConstKind::Bound(..) | |
1188 | | ty::ConstKind::Placeholder(_) => false, | |
532ac7d7 | 1189 | } |
ea8adc8c XL |
1190 | } |
1191 | } | |
48663c56 XL |
1192 | |
1193 | impl<'tcx> TypeFoldable<'tcx> for InferConst<'tcx> { | |
dc9dc135 | 1194 | fn super_fold_with<F: TypeFolder<'tcx>>(&self, _folder: &mut F) -> Self { |
48663c56 XL |
1195 | *self |
1196 | } | |
1197 | ||
1198 | fn super_visit_with<V: TypeVisitor<'tcx>>(&self, _visitor: &mut V) -> bool { | |
1199 | false | |
1200 | } | |
1201 | } |