1use rustc_data_structures::sso::SsoHashMap;
6use rustc_infer::traits::PredicateObligations;
7use rustc_macros::extension;
8pub use rustc_middle::traits::query::NormalizationResult;
9use rustc_middle::ty::{
10 self, FallibleTypeFolder, Flags, PredicateProxy, Ty, TyCtxt, TypeFoldable, TypeSuperFoldable,
11 TypeSuperVisitable, TypeVisitable, TypeVisitableExt, TypeVisitor, TypingMode, Unnormalized,
12};
13use rustc_span::DUMMY_SP;
14use tracing::{debug, info, instrument};
15
16use super::NoSolution;
17use crate::error_reporting::InferCtxtErrorExt;
18use crate::error_reporting::traits::OverflowCause;
19use crate::infer::at::At;
20use crate::infer::canonical::OriginalQueryValues;
21use crate::infer::{InferCtxt, InferOk};
22use crate::traits::normalize::needs_normalization;
23use crate::traits::{
24 BoundVarReplacer, FulfillmentError, FulfillmentErrorCode, Normalized, ObligationCause,
25 PlaceholderReplacer,
26};
27
28pub trait QueryNormalizeExt<'tcx> {
#[doc = " Normalize `value` in the context of the inference context,"]
#[doc = " yielding a resulting type, or an error if `value` cannot be"]
#[doc =
" normalized. If you don\'t care about regions, you should prefer"]
#[doc = " `normalize_erasing_regions`, which is more efficient."]
#[doc = ""]
#[doc = " If the normalization succeeds, returns back the normalized"]
#[doc = " value along with various outlives relations (in the form of"]
#[doc = " obligations that must be discharged)."]
#[doc = ""]
#[doc =
" This normalization should *only* be used when the projection is well-formed and"]
#[doc =
" does not have possible ambiguity (contains inference variables)."]
#[doc = ""]
#[doc =
" After codegen, when lifetimes do not matter, it is preferable to instead"]
#[doc =
" use [`TyCtxt::normalize_erasing_regions`], which wraps this procedure."]
#[doc = ""]
#[doc =
" N.B. Once the new solver is stabilized this method of normalization will"]
#[doc =
" likely be removed as trait solver operations are already cached by the query"]
#[doc = " system making this redundant."]
fn query_normalize<T>(self, value: T)
-> Result<Normalized<'tcx, T>, NoSolution>
where
T: TypeFoldable<TyCtxt<'tcx>>;
}
impl<'a, 'tcx> QueryNormalizeExt<'tcx> for At<'a, 'tcx> {
#[doc = " Normalize `value` in the context of the inference context,"]
#[doc = " yielding a resulting type, or an error if `value` cannot be"]
#[doc =
" normalized. If you don\'t care about regions, you should prefer"]
#[doc = " `normalize_erasing_regions`, which is more efficient."]
#[doc = ""]
#[doc = " If the normalization succeeds, returns back the normalized"]
#[doc = " value along with various outlives relations (in the form of"]
#[doc = " obligations that must be discharged)."]
#[doc = ""]
#[doc =
" This normalization should *only* be used when the projection is well-formed and"]
#[doc =
" does not have possible ambiguity (contains inference variables)."]
#[doc = ""]
#[doc =
" After codegen, when lifetimes do not matter, it is preferable to instead"]
#[doc =
" use [`TyCtxt::normalize_erasing_regions`], which wraps this procedure."]
#[doc = ""]
#[doc =
" N.B. Once the new solver is stabilized this method of normalization will"]
#[doc =
" likely be removed as trait solver operations are already cached by the query"]
#[doc = " system making this redundant."]
fn query_normalize<T>(self, value: T)
-> Result<Normalized<'tcx, T>, NoSolution> where
T: TypeFoldable<TyCtxt<'tcx>> {
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:52",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(52u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&format_args!("normalize::<{0}>(value={1:?}, param_env={2:?}, cause={3:?})",
std::any::type_name::<T>(), value, self.param_env,
self.cause) as &dyn ::tracing::field::Value))])
});
} else { ; }
};
let universes =
if value.has_escaping_bound_vars() {
let mut max_visitor =
MaxEscapingBoundVarVisitor {
outer_index: ty::INNERMOST,
escaping: 0,
};
value.visit_with(&mut max_visitor);
::alloc::vec::from_elem(None, max_visitor.escaping)
} else { ::alloc::vec::Vec::new() };
if self.infcx.next_trait_solver() {
match crate::solve::deeply_normalize_with_skipped_universes::<_,
FulfillmentError<'tcx>>(self, Unnormalized::new_wip(value),
universes) {
Ok(value) => {
return Ok(Normalized {
value,
obligations: PredicateObligations::new(),
});
}
Err(errors) => {
if let Some((overflowed_obligation, suggest_higher_limit)) =
errors.into_iter().find_map(|e|
match e.code {
FulfillmentErrorCode::Ambiguity {
overflow: Some(suggest_higher_limit) } =>
Some((e.root_obligation, suggest_higher_limit)),
_ => None,
}) {
self.infcx.err_ctxt().report_overflow_obligation(&overflowed_obligation,
suggest_higher_limit);
} else { return Err(NoSolution); }
}
}
}
if !needs_normalization(self.infcx, &value) {
return Ok(Normalized {
value,
obligations: PredicateObligations::new(),
});
}
let mut normalizer =
QueryNormalizer {
infcx: self.infcx,
cause: self.cause,
param_env: self.param_env,
obligations: PredicateObligations::new(),
cache: SsoHashMap::new(),
anon_depth: 0,
universes,
};
let result = value.try_fold_with(&mut normalizer);
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:125",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::INFO,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(125u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::INFO <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::INFO <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&format_args!("normalize::<{0}>: result={1:?} with {2} obligations",
std::any::type_name::<T>(), result,
normalizer.obligations.len()) as
&dyn ::tracing::field::Value))])
});
} else { ; }
};
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:131",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(131u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&format_args!("normalize::<{0}>: obligations={1:?}",
std::any::type_name::<T>(), normalizer.obligations) as
&dyn ::tracing::field::Value))])
});
} else { ; }
};
result.map(|value|
Normalized { value, obligations: normalizer.obligations })
}
}#[extension(pub trait QueryNormalizeExt<'tcx>)]
29impl<'a, 'tcx> At<'a, 'tcx> {
30 fn query_normalize<T>(self, value: T) -> Result<Normalized<'tcx, T>, NoSolution>
49 where
50 T: TypeFoldable<TyCtxt<'tcx>>,
51 {
52 debug!(
53 "normalize::<{}>(value={:?}, param_env={:?}, cause={:?})",
54 std::any::type_name::<T>(),
55 value,
56 self.param_env,
57 self.cause,
58 );
59
60 let universes = if value.has_escaping_bound_vars() {
71 let mut max_visitor =
72 MaxEscapingBoundVarVisitor { outer_index: ty::INNERMOST, escaping: 0 };
73 value.visit_with(&mut max_visitor);
74 vec![None; max_visitor.escaping]
75 } else {
76 vec![]
77 };
78
79 if self.infcx.next_trait_solver() {
80 match crate::solve::deeply_normalize_with_skipped_universes::<_, FulfillmentError<'tcx>>(
81 self,
82 Unnormalized::new_wip(value),
83 universes,
84 ) {
85 Ok(value) => {
86 return Ok(Normalized { value, obligations: PredicateObligations::new() });
87 }
88 Err(errors) => {
89 if let Some((overflowed_obligation, suggest_higher_limit)) =
92 errors.into_iter().find_map(|e| match e.code {
93 FulfillmentErrorCode::Ambiguity {
94 overflow: Some(suggest_higher_limit),
95 } => Some((e.root_obligation, suggest_higher_limit)),
96 _ => None,
97 })
98 {
99 self.infcx.err_ctxt().report_overflow_obligation(
100 &overflowed_obligation,
101 suggest_higher_limit,
102 );
103 } else {
104 return Err(NoSolution);
105 }
106 }
107 }
108 }
109
110 if !needs_normalization(self.infcx, &value) {
111 return Ok(Normalized { value, obligations: PredicateObligations::new() });
112 }
113
114 let mut normalizer = QueryNormalizer {
115 infcx: self.infcx,
116 cause: self.cause,
117 param_env: self.param_env,
118 obligations: PredicateObligations::new(),
119 cache: SsoHashMap::new(),
120 anon_depth: 0,
121 universes,
122 };
123
124 let result = value.try_fold_with(&mut normalizer);
125 info!(
126 "normalize::<{}>: result={:?} with {} obligations",
127 std::any::type_name::<T>(),
128 result,
129 normalizer.obligations.len(),
130 );
131 debug!(
132 "normalize::<{}>: obligations={:?}",
133 std::any::type_name::<T>(),
134 normalizer.obligations,
135 );
136 result.map(|value| Normalized { value, obligations: normalizer.obligations })
137 }
138}
139
140struct MaxEscapingBoundVarVisitor {
142 outer_index: ty::DebruijnIndex,
144 escaping: usize,
145}
146
147impl<'tcx> TypeVisitor<TyCtxt<'tcx>> for MaxEscapingBoundVarVisitor {
148 fn visit_binder<T: TypeVisitable<TyCtxt<'tcx>>>(&mut self, t: &ty::Binder<'tcx, T>) {
149 self.outer_index.shift_in(1);
150 t.super_visit_with(self);
151 self.outer_index.shift_out(1);
152 }
153
154 #[inline]
155 fn visit_ty(&mut self, t: Ty<'tcx>) {
156 if t.outer_exclusive_binder() > self.outer_index {
157 self.escaping = self
158 .escaping
159 .max(t.outer_exclusive_binder().as_usize() - self.outer_index.as_usize());
160 }
161 }
162
163 #[inline]
164 fn visit_region(&mut self, r: ty::Region<'tcx>) {
165 match r.kind() {
166 ty::ReBound(ty::BoundVarIndexKind::Bound(debruijn), _)
167 if debruijn > self.outer_index =>
168 {
169 self.escaping =
170 self.escaping.max(debruijn.as_usize() - self.outer_index.as_usize());
171 }
172 _ => {}
173 }
174 }
175
176 fn visit_const(&mut self, ct: ty::Const<'tcx>) {
177 if ct.outer_exclusive_binder() > self.outer_index {
178 self.escaping = self
179 .escaping
180 .max(ct.outer_exclusive_binder().as_usize() - self.outer_index.as_usize());
181 }
182 }
183}
184
185struct QueryNormalizer<'a, 'tcx> {
186 infcx: &'a InferCtxt<'tcx>,
187 cause: &'a ObligationCause<'tcx>,
188 param_env: ty::ParamEnv<'tcx>,
189 obligations: PredicateObligations<'tcx>,
190 cache: SsoHashMap<Ty<'tcx>, Ty<'tcx>>,
191 anon_depth: usize,
192 universes: Vec<Option<ty::UniverseIndex>>,
193}
194
195impl<'a, 'tcx> FallibleTypeFolder<TyCtxt<'tcx>> for QueryNormalizer<'a, 'tcx> {
196 type Error = NoSolution;
197
198 fn cx(&self) -> TyCtxt<'tcx> {
199 self.infcx.tcx
200 }
201
202 fn try_fold_binder<T: TypeFoldable<TyCtxt<'tcx>>>(
203 &mut self,
204 t: ty::Binder<'tcx, T>,
205 ) -> Result<ty::Binder<'tcx, T>, Self::Error> {
206 self.universes.push(None);
207 let t = t.try_super_fold_with(self);
208 self.universes.pop();
209 t
210 }
211
212 {}
#[allow(clippy :: suspicious_else_formatting)]
{
let __tracing_attr_span;
let __tracing_attr_guard;
if ::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() ||
{ false } {
__tracing_attr_span =
{
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("try_fold_ty",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(212u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&[{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("ty")
}> =
::tracing::__macro_support::FieldName::new("ty");
NAME.as_str()
}], ::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::SPAN)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let mut interest = ::tracing::subscriber::Interest::never();
if ::tracing::Level::DEBUG <=
::tracing::level_filters::STATIC_MAX_LEVEL &&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{ interest = __CALLSITE.interest(); !interest.is_never() }
&&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest) {
let meta = __CALLSITE.metadata();
::tracing::Span::new(meta,
&{
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
meta.fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&ty)
as &dyn ::tracing::field::Value))])
})
} else {
let span =
::tracing::__macro_support::__disabled_span(__CALLSITE.metadata());
{};
span
}
};
__tracing_attr_guard = __tracing_attr_span.enter();
}
#[warn(clippy :: suspicious_else_formatting)]
{
#[allow(unknown_lints, unreachable_code, clippy ::
diverging_sub_expression, clippy :: empty_loop, clippy ::
let_unit_value, clippy :: let_with_type_underscore, clippy ::
needless_return, clippy :: unreachable)]
if false {
let __tracing_attr_fake_return: Result<Ty<'tcx>, Self::Error> =
loop {};
return __tracing_attr_fake_return;
}
{
if !needs_normalization(self.infcx, &ty) { return Ok(ty); }
if let Some(ty) = self.cache.get(&ty) { return Ok(*ty); }
let &ty::Alias(_, data) =
ty.kind() else {
let res = ty.try_super_fold_with(self)?;
self.cache.insert(ty, res);
return Ok(res);
};
let res =
match data.kind {
ty::Opaque { def_id } => {
match self.infcx.typing_mode_raw().assert_not_erased() {
TypingMode::Coherence | TypingMode::Typeck { .. } |
TypingMode::PostTypeckUntilBorrowck { .. } |
TypingMode::PostBorrowck { .. } =>
ty.try_super_fold_with(self)?,
TypingMode::Reflection | TypingMode::PostAnalysis |
TypingMode::Codegen => {
let args = data.args.try_fold_with(self)?;
let recursion_limit = self.cx().recursion_limit();
if !recursion_limit.value_within_limit(self.anon_depth) {
let guar =
self.infcx.err_ctxt().build_overflow_error(OverflowCause::DeeplyNormalize(data.into()),
self.cause.span, true).delay_as_bug();
return Ok(Ty::new_error(self.cx(), guar));
}
let generic_ty = self.cx().type_of(def_id);
let mut concrete_ty =
generic_ty.instantiate(self.cx(), args).skip_norm_wip();
self.anon_depth += 1;
if concrete_ty == ty {
concrete_ty =
Ty::new_error_with_message(self.cx(), DUMMY_SP,
"recursive opaque type");
}
let folded_ty = self.try_fold_ty(concrete_ty);
self.anon_depth -= 1;
folded_ty?
}
}
}
kind @
(ty::Projection { .. } | ty::Inherent { .. } | ty::Free { ..
}) =>
self.try_fold_free_or_assoc(ty::AliasTerm::new(self.cx(),
kind.into(), data.args))?.expect_type(),
};
self.cache.insert(ty, res);
Ok(res)
}
}
}#[instrument(level = "debug", skip(self))]
213 fn try_fold_ty(&mut self, ty: Ty<'tcx>) -> Result<Ty<'tcx>, Self::Error> {
214 if !needs_normalization(self.infcx, &ty) {
215 return Ok(ty);
216 }
217
218 if let Some(ty) = self.cache.get(&ty) {
219 return Ok(*ty);
220 }
221
222 let &ty::Alias(_, data) = ty.kind() else {
223 let res = ty.try_super_fold_with(self)?;
224 self.cache.insert(ty, res);
225 return Ok(res);
226 };
227
228 let res = match data.kind {
231 ty::Opaque { def_id } => {
232 match self.infcx.typing_mode_raw().assert_not_erased() {
234 TypingMode::Coherence
235 | TypingMode::Typeck { .. }
236 | TypingMode::PostTypeckUntilBorrowck { .. }
237 | TypingMode::PostBorrowck { .. } => ty.try_super_fold_with(self)?,
238
239 TypingMode::Reflection | TypingMode::PostAnalysis | TypingMode::Codegen => {
240 let args = data.args.try_fold_with(self)?;
241 let recursion_limit = self.cx().recursion_limit();
242
243 if !recursion_limit.value_within_limit(self.anon_depth) {
244 let guar = self
245 .infcx
246 .err_ctxt()
247 .build_overflow_error(
248 OverflowCause::DeeplyNormalize(data.into()),
249 self.cause.span,
250 true,
251 )
252 .delay_as_bug();
253 return Ok(Ty::new_error(self.cx(), guar));
254 }
255
256 let generic_ty = self.cx().type_of(def_id);
257 let mut concrete_ty =
258 generic_ty.instantiate(self.cx(), args).skip_norm_wip();
259 self.anon_depth += 1;
260 if concrete_ty == ty {
261 concrete_ty = Ty::new_error_with_message(
262 self.cx(),
263 DUMMY_SP,
264 "recursive opaque type",
265 );
266 }
267 let folded_ty = self.try_fold_ty(concrete_ty);
268 self.anon_depth -= 1;
269 folded_ty?
270 }
271 }
272 }
273
274 kind @ (ty::Projection { .. } | ty::Inherent { .. } | ty::Free { .. }) => self
275 .try_fold_free_or_assoc(ty::AliasTerm::new(self.cx(), kind.into(), data.args))?
276 .expect_type(),
277 };
278
279 self.cache.insert(ty, res);
280 Ok(res)
281 }
282
283 fn try_fold_const(
284 &mut self,
285 constant: ty::Const<'tcx>,
286 ) -> Result<ty::Const<'tcx>, Self::Error> {
287 if !needs_normalization(self.infcx, &constant) {
288 return Ok(constant);
289 }
290
291 let alias_const = match constant.kind() {
292 ty::ConstKind::Alias(_, alias_const) => alias_const,
293 _ => return constant.try_super_fold_with(self),
294 };
295
296 let constant = match alias_const.kind {
297 ty::AliasConstKind::Anon { .. } => crate::traits::with_replaced_escaping_bound_vars(
298 self.infcx,
299 &mut self.universes,
300 constant,
301 |constant| crate::traits::evaluate_const(&self.infcx, constant, self.param_env),
302 ),
303 _ => self.try_fold_free_or_assoc(alias_const.into())?.expect_const(),
304 };
305 {
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:305",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(305u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&[{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("constant")
}> =
::tracing::__macro_support::FieldName::new("constant");
NAME.as_str()
},
{
const NAME:
::tracing::__macro_support::FieldName<{
::tracing::__macro_support::FieldName::len("self.param_env")
}> =
::tracing::__macro_support::FieldName::new("self.param_env");
NAME.as_str()
}], ::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&constant)
as &dyn ::tracing::field::Value)),
(::tracing::__macro_support::Option::Some(&::tracing::field::debug(&self.param_env)
as &dyn ::tracing::field::Value))])
});
} else { ; }
};debug!(?constant, ?self.param_env);
306 constant.try_super_fold_with(self)
307 }
308
309 #[inline]
310 fn try_fold_predicate<P: PredicateProxy<TyCtxt<'tcx>>>(
311 &mut self,
312 p: P,
313 ) -> Result<P, Self::Error> {
314 if p.allow_normalization() && needs_normalization(self.infcx, &p) {
315 p.try_super_fold_with(self)
316 } else {
317 Ok(p)
318 }
319 }
320}
321
322impl<'a, 'tcx> QueryNormalizer<'a, 'tcx> {
323 fn try_fold_free_or_assoc(
324 &mut self,
325 term: ty::AliasTerm<'tcx>,
326 ) -> Result<ty::Term<'tcx>, NoSolution> {
327 let infcx = self.infcx;
328 let tcx = infcx.tcx;
329 let (term, maps) = if term.has_escaping_bound_vars() {
332 let (term, mapped_regions, mapped_types, mapped_consts) =
333 BoundVarReplacer::replace_bound_vars(infcx, &mut self.universes, term);
334 (term, Some((mapped_regions, mapped_types, mapped_consts)))
335 } else {
336 (term, None)
337 };
338 let term = term.try_fold_with(self)?;
339
340 let mut orig_values = OriginalQueryValues::default();
341 let c_term = infcx.canonicalize_query(self.param_env.and(term), &mut orig_values);
342 {
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:342",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(342u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&format_args!("QueryNormalizer: c_term = {0:#?}",
c_term) as &dyn ::tracing::field::Value))])
});
} else { ; }
};debug!("QueryNormalizer: c_term = {:#?}", c_term);
343 {
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:343",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(343u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&format_args!("QueryNormalizer: orig_values = {0:#?}",
orig_values) as &dyn ::tracing::field::Value))])
});
} else { ; }
};debug!("QueryNormalizer: orig_values = {:#?}", orig_values);
344 let result = match term.kind {
345 ty::AliasTermKind::ProjectionTy { .. } | ty::AliasTermKind::ProjectionConst { .. } => {
346 tcx.normalize_canonicalized_projection(c_term)
347 }
348 ty::AliasTermKind::FreeTy { .. } | ty::AliasTermKind::FreeConst { .. } => {
349 tcx.normalize_canonicalized_free_alias(c_term)
350 }
351 ty::AliasTermKind::InherentTy { .. }
352 | ty::AliasTermKind::InherentConstSelf { .. }
353 | ty::AliasTermKind::InherentConstImpl { .. } => {
354 tcx.normalize_canonicalized_inherent_projection(c_term)
355 }
356 kind @ (ty::AliasTermKind::OpaqueTy { .. } | ty::AliasTermKind::AnonConst { .. }) => {
357 {
::core::panicking::panic_fmt(format_args!("internal error: entered unreachable code: {0}",
format_args!("did not expect {0:?} due to match arm above",
kind)));
}unreachable!("did not expect {kind:?} due to match arm above")
358 }
359 }?;
360 if !result.value.is_proven() {
362 if !tcx.sess.opts.actually_rustdoc {
365 tcx.dcx().delayed_bug(::alloc::__export::must_use({
::alloc::fmt::format(format_args!("unexpected ambiguity: {0:?} {1:?}",
c_term, result))
})format!("unexpected ambiguity: {c_term:?} {result:?}"));
366 }
367 return Err(NoSolution);
368 }
369 let InferOk { value: result, obligations } = infcx
370 .instantiate_query_response_and_region_obligations(
371 self.cause,
372 self.param_env,
373 &orig_values,
374 result,
375 )?;
376 {
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:376",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(376u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&format_args!("QueryNormalizer: result = {0:#?}",
result) as &dyn ::tracing::field::Value))])
});
} else { ; }
};debug!("QueryNormalizer: result = {:#?}", result);
377 {
use ::tracing::__macro_support::Callsite as _;
static __CALLSITE: ::tracing::callsite::DefaultCallsite =
{
static META: ::tracing::Metadata<'static> =
{
::tracing_core::metadata::Metadata::new("event /rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs:377",
"rustc_trait_selection::traits::query::normalize",
::tracing::Level::DEBUG,
::tracing_core::__macro_support::Option::Some("/rustc-dev/4b6d04e706108ccfeafe2547fbe857dfe8972bad/compiler/rustc_trait_selection/src/traits/query/normalize.rs"),
::tracing_core::__macro_support::Option::Some(377u32),
::tracing_core::__macro_support::Option::Some("rustc_trait_selection::traits::query::normalize"),
::tracing_core::field::FieldSet::new(&["message"],
::tracing_core::callsite::Identifier(&__CALLSITE)),
::tracing::metadata::Kind::EVENT)
};
::tracing::callsite::DefaultCallsite::new(&META)
};
let enabled =
::tracing::Level::DEBUG <= ::tracing::level_filters::STATIC_MAX_LEVEL
&&
::tracing::Level::DEBUG <=
::tracing::level_filters::LevelFilter::current() &&
{
let interest = __CALLSITE.interest();
!interest.is_never() &&
::tracing::__macro_support::__is_enabled(__CALLSITE.metadata(),
interest)
};
if enabled {
(|value_set: ::tracing::field::ValueSet|
{
let meta = __CALLSITE.metadata();
::tracing::Event::dispatch(meta, &value_set);
;
})({
#[allow(unused_imports)]
use ::tracing::field::{debug, display, Value};
__CALLSITE.metadata().fields().value_set_all(&[(::tracing::__macro_support::Option::Some(&format_args!("QueryNormalizer: obligations = {0:#?}",
obligations) as &dyn ::tracing::field::Value))])
});
} else { ; }
};debug!("QueryNormalizer: obligations = {:#?}", obligations);
378 self.obligations.extend(obligations);
379 let res = if let Some((mapped_regions, mapped_types, mapped_consts)) = maps {
380 PlaceholderReplacer::replace_placeholders(
381 infcx,
382 mapped_regions,
383 mapped_types,
384 mapped_consts,
385 &self.universes,
386 result.normalized_term,
387 )
388 } else {
389 result.normalized_term
390 };
391 if res != term.to_term(tcx, ty::IsRigid::No)
397 && (res.has_type_flags(ty::TypeFlags::HAS_CONST_ALIAS)
398 || #[allow(non_exhaustive_omitted_patterns)] match term.kind {
ty::AliasTermKind::FreeTy { .. } | ty::AliasTermKind::FreeConst { .. } =>
true,
_ => false,
}matches!(
399 term.kind,
400 ty::AliasTermKind::FreeTy { .. } | ty::AliasTermKind::FreeConst { .. }
401 ))
402 {
403 res.try_fold_with(self)
404 } else {
405 Ok(res)
406 }
407 }
408}