Skip to content

Commit e8d152d

Browse files
committed
Move TypeVisitableExt from ir module
1 parent b409329 commit e8d152d

File tree

1 file changed

+127
-130
lines changed

1 file changed

+127
-130
lines changed

compiler/rustc_middle/src/ty/visit.rs

+127-130
Original file line numberDiff line numberDiff line change
@@ -39,24 +39,22 @@
3939
//! - u.visit_with(visitor)
4040
//! ```
4141
use crate::ty::{self, flags::FlagComputation, Binder, Ty, TyCtxt, TypeFlags};
42+
use rustc_errors::ErrorGuaranteed;
4243

4344
use rustc_data_structures::fx::FxHashSet;
4445
use rustc_data_structures::sso::SsoHashSet;
4546
use std::ops::ControlFlow;
4647

47-
pub trait TypeVisitable<'tcx> = ir::TypeVisitable<'tcx> + ir::TypeVisitableExt<'tcx>;
48+
pub trait TypeVisitable<'tcx> = ir::TypeVisitable<'tcx> + TypeVisitableExt<'tcx>;
4849
pub trait TypeSuperVisitable<'tcx> = ir::TypeSuperVisitable<'tcx>;
4950
pub trait TypeVisitor<'tcx> = ir::TypeVisitor<'tcx>;
5051

5152
pub mod ir {
52-
use crate::ty::{self, Binder, Ty, TypeFlags};
53-
use rustc_errors::ErrorGuaranteed;
53+
use crate::ty::{self, Binder, Ty};
5454

5555
use std::fmt;
5656
use std::ops::ControlFlow;
5757

58-
use super::{FoundFlags, HasEscapingVarsVisitor, HasTypeFlagsVisitor};
59-
6058
/// This trait is implemented for every type that can be visited,
6159
/// providing the skeleton of the traversal.
6260
///
@@ -76,131 +74,6 @@ pub mod ir {
7674
fn visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> ControlFlow<V::BreakTy>;
7775
}
7876

79-
pub trait TypeVisitableExt<'tcx>: TypeVisitable<'tcx> {
80-
/// Returns `true` if `self` has any late-bound regions that are either
81-
/// bound by `binder` or bound by some binder outside of `binder`.
82-
/// If `binder` is `ty::INNERMOST`, this indicates whether
83-
/// there are any late-bound regions that appear free.
84-
fn has_vars_bound_at_or_above(&self, binder: ty::DebruijnIndex) -> bool {
85-
self.visit_with(&mut HasEscapingVarsVisitor { outer_index: binder }).is_break()
86-
}
87-
88-
/// Returns `true` if this type has any regions that escape `binder` (and
89-
/// hence are not bound by it).
90-
fn has_vars_bound_above(&self, binder: ty::DebruijnIndex) -> bool {
91-
self.has_vars_bound_at_or_above(binder.shifted_in(1))
92-
}
93-
94-
/// Return `true` if this type has regions that are not a part of the type.
95-
/// For example, `for<'a> fn(&'a i32)` return `false`, while `fn(&'a i32)`
96-
/// would return `true`. The latter can occur when traversing through the
97-
/// former.
98-
///
99-
/// See [`HasEscapingVarsVisitor`] for more information.
100-
fn has_escaping_bound_vars(&self) -> bool {
101-
self.has_vars_bound_at_or_above(ty::INNERMOST)
102-
}
103-
104-
fn has_type_flags(&self, flags: TypeFlags) -> bool {
105-
let res = self.visit_with(&mut HasTypeFlagsVisitor { flags }).break_value()
106-
== Some(FoundFlags);
107-
trace!(?self, ?flags, ?res, "has_type_flags");
108-
res
109-
}
110-
fn has_projections(&self) -> bool {
111-
self.has_type_flags(TypeFlags::HAS_PROJECTION)
112-
}
113-
fn has_opaque_types(&self) -> bool {
114-
self.has_type_flags(TypeFlags::HAS_TY_OPAQUE)
115-
}
116-
fn has_generators(&self) -> bool {
117-
self.has_type_flags(TypeFlags::HAS_TY_GENERATOR)
118-
}
119-
fn references_error(&self) -> bool {
120-
self.has_type_flags(TypeFlags::HAS_ERROR)
121-
}
122-
fn error_reported(&self) -> Result<(), ErrorGuaranteed> {
123-
if self.references_error() {
124-
if let Some(reported) = ty::tls::with(|tcx| tcx.sess.is_compilation_going_to_fail())
125-
{
126-
Err(reported)
127-
} else {
128-
bug!("expect tcx.sess.is_compilation_going_to_fail return `Some`");
129-
}
130-
} else {
131-
Ok(())
132-
}
133-
}
134-
fn has_non_region_param(&self) -> bool {
135-
self.has_type_flags(TypeFlags::NEEDS_SUBST - TypeFlags::HAS_RE_PARAM)
136-
}
137-
fn has_infer_regions(&self) -> bool {
138-
self.has_type_flags(TypeFlags::HAS_RE_INFER)
139-
}
140-
fn has_infer_types(&self) -> bool {
141-
self.has_type_flags(TypeFlags::HAS_TY_INFER)
142-
}
143-
fn has_non_region_infer(&self) -> bool {
144-
self.has_type_flags(TypeFlags::NEEDS_INFER - TypeFlags::HAS_RE_INFER)
145-
}
146-
fn needs_infer(&self) -> bool {
147-
self.has_type_flags(TypeFlags::NEEDS_INFER)
148-
}
149-
fn has_placeholders(&self) -> bool {
150-
self.has_type_flags(
151-
TypeFlags::HAS_RE_PLACEHOLDER
152-
| TypeFlags::HAS_TY_PLACEHOLDER
153-
| TypeFlags::HAS_CT_PLACEHOLDER,
154-
)
155-
}
156-
fn needs_subst(&self) -> bool {
157-
self.has_type_flags(TypeFlags::NEEDS_SUBST)
158-
}
159-
/// "Free" regions in this context means that it has any region
160-
/// that is not (a) erased or (b) late-bound.
161-
fn has_free_regions(&self) -> bool {
162-
self.has_type_flags(TypeFlags::HAS_FREE_REGIONS)
163-
}
164-
165-
fn has_erased_regions(&self) -> bool {
166-
self.has_type_flags(TypeFlags::HAS_RE_ERASED)
167-
}
168-
169-
/// True if there are any un-erased free regions.
170-
fn has_erasable_regions(&self) -> bool {
171-
self.has_type_flags(TypeFlags::HAS_FREE_REGIONS)
172-
}
173-
174-
/// Indicates whether this value references only 'global'
175-
/// generic parameters that are the same regardless of what fn we are
176-
/// in. This is used for caching.
177-
fn is_global(&self) -> bool {
178-
!self.has_type_flags(TypeFlags::HAS_FREE_LOCAL_NAMES)
179-
}
180-
181-
/// True if there are any late-bound regions
182-
fn has_late_bound_regions(&self) -> bool {
183-
self.has_type_flags(TypeFlags::HAS_RE_LATE_BOUND)
184-
}
185-
/// True if there are any late-bound non-region variables
186-
fn has_non_region_late_bound(&self) -> bool {
187-
self.has_type_flags(TypeFlags::HAS_LATE_BOUND - TypeFlags::HAS_RE_LATE_BOUND)
188-
}
189-
/// True if there are any late-bound variables
190-
fn has_late_bound_vars(&self) -> bool {
191-
self.has_type_flags(TypeFlags::HAS_LATE_BOUND)
192-
}
193-
194-
/// Indicates whether this value still has parameters/placeholders/inference variables
195-
/// which could be replaced later, in a way that would change the results of `impl`
196-
/// specialization.
197-
fn still_further_specializable(&self) -> bool {
198-
self.has_type_flags(TypeFlags::STILL_FURTHER_SPECIALIZABLE)
199-
}
200-
}
201-
202-
impl<'tcx, T: TypeVisitable<'tcx>> TypeVisitableExt<'tcx> for T {}
203-
20477
pub trait TypeSuperVisitable<'tcx>: TypeVisitable<'tcx> {
20578
/// Provides a default visit for a type of interest. This should only be
20679
/// called within `TypeVisitor` methods, when a non-custom traversal is
@@ -245,6 +118,130 @@ pub mod ir {
245118
}
246119
}
247120

121+
pub trait TypeVisitableExt<'tcx>: ir::TypeVisitable<'tcx> {
122+
/// Returns `true` if `self` has any late-bound regions that are either
123+
/// bound by `binder` or bound by some binder outside of `binder`.
124+
/// If `binder` is `ty::INNERMOST`, this indicates whether
125+
/// there are any late-bound regions that appear free.
126+
fn has_vars_bound_at_or_above(&self, binder: ty::DebruijnIndex) -> bool {
127+
self.visit_with(&mut HasEscapingVarsVisitor { outer_index: binder }).is_break()
128+
}
129+
130+
/// Returns `true` if this type has any regions that escape `binder` (and
131+
/// hence are not bound by it).
132+
fn has_vars_bound_above(&self, binder: ty::DebruijnIndex) -> bool {
133+
self.has_vars_bound_at_or_above(binder.shifted_in(1))
134+
}
135+
136+
/// Return `true` if this type has regions that are not a part of the type.
137+
/// For example, `for<'a> fn(&'a i32)` return `false`, while `fn(&'a i32)`
138+
/// would return `true`. The latter can occur when traversing through the
139+
/// former.
140+
///
141+
/// See [`HasEscapingVarsVisitor`] for more information.
142+
fn has_escaping_bound_vars(&self) -> bool {
143+
self.has_vars_bound_at_or_above(ty::INNERMOST)
144+
}
145+
146+
fn has_type_flags(&self, flags: TypeFlags) -> bool {
147+
let res =
148+
self.visit_with(&mut HasTypeFlagsVisitor { flags }).break_value() == Some(FoundFlags);
149+
trace!(?self, ?flags, ?res, "has_type_flags");
150+
res
151+
}
152+
fn has_projections(&self) -> bool {
153+
self.has_type_flags(TypeFlags::HAS_PROJECTION)
154+
}
155+
fn has_opaque_types(&self) -> bool {
156+
self.has_type_flags(TypeFlags::HAS_TY_OPAQUE)
157+
}
158+
fn has_generators(&self) -> bool {
159+
self.has_type_flags(TypeFlags::HAS_TY_GENERATOR)
160+
}
161+
fn references_error(&self) -> bool {
162+
self.has_type_flags(TypeFlags::HAS_ERROR)
163+
}
164+
fn error_reported(&self) -> Result<(), ErrorGuaranteed> {
165+
if self.references_error() {
166+
if let Some(reported) = ty::tls::with(|tcx| tcx.sess.is_compilation_going_to_fail()) {
167+
Err(reported)
168+
} else {
169+
bug!("expect tcx.sess.is_compilation_going_to_fail return `Some`");
170+
}
171+
} else {
172+
Ok(())
173+
}
174+
}
175+
fn has_non_region_param(&self) -> bool {
176+
self.has_type_flags(TypeFlags::NEEDS_SUBST - TypeFlags::HAS_RE_PARAM)
177+
}
178+
fn has_infer_regions(&self) -> bool {
179+
self.has_type_flags(TypeFlags::HAS_RE_INFER)
180+
}
181+
fn has_infer_types(&self) -> bool {
182+
self.has_type_flags(TypeFlags::HAS_TY_INFER)
183+
}
184+
fn has_non_region_infer(&self) -> bool {
185+
self.has_type_flags(TypeFlags::NEEDS_INFER - TypeFlags::HAS_RE_INFER)
186+
}
187+
fn needs_infer(&self) -> bool {
188+
self.has_type_flags(TypeFlags::NEEDS_INFER)
189+
}
190+
fn has_placeholders(&self) -> bool {
191+
self.has_type_flags(
192+
TypeFlags::HAS_RE_PLACEHOLDER
193+
| TypeFlags::HAS_TY_PLACEHOLDER
194+
| TypeFlags::HAS_CT_PLACEHOLDER,
195+
)
196+
}
197+
fn needs_subst(&self) -> bool {
198+
self.has_type_flags(TypeFlags::NEEDS_SUBST)
199+
}
200+
/// "Free" regions in this context means that it has any region
201+
/// that is not (a) erased or (b) late-bound.
202+
fn has_free_regions(&self) -> bool {
203+
self.has_type_flags(TypeFlags::HAS_FREE_REGIONS)
204+
}
205+
206+
fn has_erased_regions(&self) -> bool {
207+
self.has_type_flags(TypeFlags::HAS_RE_ERASED)
208+
}
209+
210+
/// True if there are any un-erased free regions.
211+
fn has_erasable_regions(&self) -> bool {
212+
self.has_type_flags(TypeFlags::HAS_FREE_REGIONS)
213+
}
214+
215+
/// Indicates whether this value references only 'global'
216+
/// generic parameters that are the same regardless of what fn we are
217+
/// in. This is used for caching.
218+
fn is_global(&self) -> bool {
219+
!self.has_type_flags(TypeFlags::HAS_FREE_LOCAL_NAMES)
220+
}
221+
222+
/// True if there are any late-bound regions
223+
fn has_late_bound_regions(&self) -> bool {
224+
self.has_type_flags(TypeFlags::HAS_RE_LATE_BOUND)
225+
}
226+
/// True if there are any late-bound non-region variables
227+
fn has_non_region_late_bound(&self) -> bool {
228+
self.has_type_flags(TypeFlags::HAS_LATE_BOUND - TypeFlags::HAS_RE_LATE_BOUND)
229+
}
230+
/// True if there are any late-bound variables
231+
fn has_late_bound_vars(&self) -> bool {
232+
self.has_type_flags(TypeFlags::HAS_LATE_BOUND)
233+
}
234+
235+
/// Indicates whether this value still has parameters/placeholders/inference variables
236+
/// which could be replaced later, in a way that would change the results of `impl`
237+
/// specialization.
238+
fn still_further_specializable(&self) -> bool {
239+
self.has_type_flags(TypeFlags::STILL_FURTHER_SPECIALIZABLE)
240+
}
241+
}
242+
243+
impl<'tcx, T: ir::TypeVisitable<'tcx>> TypeVisitableExt<'tcx> for T {}
244+
248245
///////////////////////////////////////////////////////////////////////////
249246
// Region folder
250247

0 commit comments

Comments
 (0)