Skip to main content

rustc_middle/ty/context/
impl_interner.rs

1//! Implementation of [`rustc_type_ir::Interner`] for [`TyCtxt`].
2
3use std::{debug_assert_matches, fmt};
4
5use rustc_abi::ExternAbi;
6use rustc_errors::ErrorGuaranteed;
7use rustc_hir as hir;
8use rustc_hir::def::{CtorKind, CtorOf, DefKind};
9use rustc_hir::def_id::{DefId, LocalDefId};
10use rustc_hir::lang_items::LangItem;
11use rustc_span::{DUMMY_SP, Span, Symbol};
12use rustc_type_ir::lang_items::{SolverAdtLangItem, SolverLangItem, SolverTraitLangItem};
13use rustc_type_ir::{CollectAndApply, Interner, TypeFoldable, search_graph};
14
15use crate::dep_graph::{DepKind, DepNodeIndex};
16use crate::infer::canonical::CanonicalVarKinds;
17use crate::traits::cache::WithDepNode;
18use crate::traits::solve::{
19    self, CanonicalInput, ExternalConstraints, ExternalConstraintsData, QueryResult, inspect,
20};
21use crate::ty::{
22    self, Clause, Const, List, ParamTy, Pattern, PolyExistentialPredicate, Predicate, Region, Ty,
23    TyCtxt,
24};
25
26#[allow(rustc::usage_of_ty_tykind)]
27impl<'tcx> Interner for TyCtxt<'tcx> {
28    fn next_trait_solver_globally(self) -> bool {
29        self.next_trait_solver_globally()
30    }
31
32    type DefId = DefId;
33    type LocalDefId = LocalDefId;
34    type TraitId = DefId;
35    type ForeignId = DefId;
36    type FunctionId = DefId;
37    type ClosureId = DefId;
38    type CoroutineClosureId = DefId;
39    type CoroutineId = DefId;
40    type AdtId = DefId;
41    type ImplId = DefId;
42    type UnevaluatedConstId = DefId;
43    type Span = Span;
44
45    type GenericArgs = ty::GenericArgsRef<'tcx>;
46
47    type GenericArgsSlice = &'tcx [ty::GenericArg<'tcx>];
48    type GenericArg = ty::GenericArg<'tcx>;
49    type Term = ty::Term<'tcx>;
50    type BoundVarKinds = &'tcx List<ty::BoundVariableKind<'tcx>>;
51
52    type PredefinedOpaques = solve::PredefinedOpaques<'tcx>;
53
54    fn mk_predefined_opaques_in_body(
55        self,
56        data: &[(ty::OpaqueTypeKey<'tcx>, Ty<'tcx>)],
57    ) -> Self::PredefinedOpaques {
58        self.mk_predefined_opaques_in_body(data)
59    }
60    type LocalDefIds = &'tcx ty::List<LocalDefId>;
61    type CanonicalVarKinds = CanonicalVarKinds<'tcx>;
62    fn mk_canonical_var_kinds(
63        self,
64        kinds: &[ty::CanonicalVarKind<Self>],
65    ) -> Self::CanonicalVarKinds {
66        self.mk_canonical_var_kinds(kinds)
67    }
68
69    type ExternalConstraints = ExternalConstraints<'tcx>;
70    fn mk_external_constraints(
71        self,
72        data: ExternalConstraintsData<Self>,
73    ) -> ExternalConstraints<'tcx> {
74        self.mk_external_constraints(data)
75    }
76    type DepNodeIndex = DepNodeIndex;
77    fn with_cached_task<T>(self, task: impl FnOnce() -> T) -> (T, DepNodeIndex) {
78        self.dep_graph.with_anon_task(self, DepKind::TraitSelect, task)
79    }
80    type Ty = Ty<'tcx>;
81    type Tys = &'tcx List<Ty<'tcx>>;
82
83    type FnInputTys = &'tcx [Ty<'tcx>];
84    type ParamTy = ParamTy;
85    type Symbol = Symbol;
86
87    type ErrorGuaranteed = ErrorGuaranteed;
88    type BoundExistentialPredicates = &'tcx List<PolyExistentialPredicate<'tcx>>;
89
90    type AllocId = crate::mir::interpret::AllocId;
91    type Pat = Pattern<'tcx>;
92    type PatList = &'tcx List<Pattern<'tcx>>;
93    type Safety = hir::Safety;
94    type Abi = ExternAbi;
95    type Const = ty::Const<'tcx>;
96    type Consts = &'tcx List<Self::Const>;
97
98    type ParamConst = ty::ParamConst;
99    type ValueConst = ty::Value<'tcx>;
100    type ExprConst = ty::Expr<'tcx>;
101    type ValTree = ty::ValTree<'tcx>;
102    type ScalarInt = ty::ScalarInt;
103
104    type Region = Region<'tcx>;
105    type EarlyParamRegion = ty::EarlyParamRegion;
106    type LateParamRegion = ty::LateParamRegion;
107
108    type RegionAssumptions = &'tcx ty::List<ty::ArgOutlivesPredicate<'tcx>>;
109
110    type ParamEnv = ty::ParamEnv<'tcx>;
111    type Predicate = Predicate<'tcx>;
112
113    type Clause = Clause<'tcx>;
114    type Clauses = ty::Clauses<'tcx>;
115
116    type Tracked<T: fmt::Debug + Clone> = WithDepNode<T>;
117    fn mk_tracked<T: fmt::Debug + Clone>(
118        self,
119        data: T,
120        dep_node: DepNodeIndex,
121    ) -> Self::Tracked<T> {
122        WithDepNode::new(dep_node, data)
123    }
124    fn get_tracked<T: fmt::Debug + Clone>(self, tracked: &Self::Tracked<T>) -> T {
125        tracked.get(self)
126    }
127
128    fn with_global_cache<R>(self, f: impl FnOnce(&mut search_graph::GlobalCache<Self>) -> R) -> R {
129        f(&mut *self.new_solver_evaluation_cache.lock())
130    }
131
132    fn canonical_param_env_cache_get_or_insert<R>(
133        self,
134        param_env: ty::ParamEnv<'tcx>,
135        f: impl FnOnce() -> ty::CanonicalParamEnvCacheEntry<Self>,
136        from_entry: impl FnOnce(&ty::CanonicalParamEnvCacheEntry<Self>) -> R,
137    ) -> R {
138        let mut cache = self.new_solver_canonical_param_env_cache.lock();
139        let entry = cache.entry(param_env).or_insert_with(f);
140        from_entry(entry)
141    }
142
143    fn assert_evaluation_is_concurrent(&self) {
144        // Turns out, the assumption for this function isn't perfect.
145        // See trait-system-refactor-initiative#234.
146    }
147
148    fn expand_abstract_consts<T: TypeFoldable<TyCtxt<'tcx>>>(self, t: T) -> T {
149        self.expand_abstract_consts(t)
150    }
151
152    type GenericsOf = &'tcx ty::Generics;
153
154    fn generics_of(self, def_id: DefId) -> &'tcx ty::Generics {
155        self.generics_of(def_id)
156    }
157
158    type VariancesOf = &'tcx [ty::Variance];
159
160    fn variances_of(self, def_id: DefId) -> Self::VariancesOf {
161        self.variances_of(def_id)
162    }
163
164    fn opt_alias_variances(
165        self,
166        kind: impl Into<ty::AliasTermKind>,
167        def_id: DefId,
168    ) -> Option<&'tcx [ty::Variance]> {
169        self.opt_alias_variances(kind, def_id)
170    }
171
172    fn type_of(self, def_id: DefId) -> ty::EarlyBinder<'tcx, Ty<'tcx>> {
173        self.type_of(def_id)
174    }
175    fn type_of_opaque_hir_typeck(self, def_id: LocalDefId) -> ty::EarlyBinder<'tcx, Ty<'tcx>> {
176        self.type_of_opaque_hir_typeck(def_id)
177    }
178    fn const_of_item(self, def_id: DefId) -> ty::EarlyBinder<'tcx, Const<'tcx>> {
179        self.const_of_item(def_id)
180    }
181    fn anon_const_kind(self, def_id: DefId) -> ty::AnonConstKind {
182        self.anon_const_kind(def_id)
183    }
184
185    type AdtDef = ty::AdtDef<'tcx>;
186    fn adt_def(self, adt_def_id: DefId) -> Self::AdtDef {
187        self.adt_def(adt_def_id)
188    }
189
190    fn alias_ty_kind_from_def_id(self, def_id: DefId) -> ty::AliasTyKind<'tcx> {
191        match self.def_kind(def_id) {
192            DefKind::AssocTy
193                if let DefKind::Impl { of_trait: false } = self.def_kind(self.parent(def_id)) =>
194            {
195                ty::Inherent { def_id }
196            }
197            DefKind::AssocTy => ty::Projection { def_id },
198
199            DefKind::OpaqueTy => ty::Opaque { def_id },
200            DefKind::TyAlias => ty::Free { def_id },
201            kind => crate::util::bug::bug_fmt(format_args!("unexpected DefKind in AliasTy: {0:?}",
        kind))bug!("unexpected DefKind in AliasTy: {kind:?}"),
202        }
203    }
204
205    fn alias_term_kind(self, alias: ty::AliasTerm<'tcx>) -> ty::AliasTermKind {
206        match self.def_kind(alias.def_id) {
207            DefKind::AssocTy => {
208                if let DefKind::Impl { of_trait: false } = self.def_kind(self.parent(alias.def_id))
209                {
210                    ty::AliasTermKind::InherentTy
211                } else {
212                    ty::AliasTermKind::ProjectionTy
213                }
214            }
215            DefKind::AssocConst { .. } => {
216                if let DefKind::Impl { of_trait: false } = self.def_kind(self.parent(alias.def_id))
217                {
218                    ty::AliasTermKind::InherentConst
219                } else {
220                    ty::AliasTermKind::ProjectionConst
221                }
222            }
223            DefKind::OpaqueTy => ty::AliasTermKind::OpaqueTy,
224            DefKind::TyAlias => ty::AliasTermKind::FreeTy,
225            DefKind::Const { .. } => ty::AliasTermKind::FreeConst,
226            DefKind::AnonConst | DefKind::Ctor(_, CtorKind::Const) => {
227                ty::AliasTermKind::UnevaluatedConst
228            }
229            kind => crate::util::bug::bug_fmt(format_args!("unexpected DefKind in AliasTy: {0:?}",
        kind))bug!("unexpected DefKind in AliasTy: {kind:?}"),
230        }
231    }
232
233    fn trait_ref_and_own_args_for_alias(
234        self,
235        def_id: DefId,
236        args: ty::GenericArgsRef<'tcx>,
237    ) -> (ty::TraitRef<'tcx>, &'tcx [ty::GenericArg<'tcx>]) {
238        if true {
    match self.def_kind(def_id) {
        DefKind::AssocTy | DefKind::AssocConst { .. } => {}
        ref left_val => {
            ::core::panicking::assert_matches_failed(left_val,
                "DefKind::AssocTy | DefKind::AssocConst { .. }",
                ::core::option::Option::None);
        }
    };
};debug_assert_matches!(self.def_kind(def_id), DefKind::AssocTy | DefKind::AssocConst { .. });
239        let trait_def_id = self.parent(def_id);
240        if true {
    match self.def_kind(trait_def_id) {
        DefKind::Trait => {}
        ref left_val => {
            ::core::panicking::assert_matches_failed(left_val,
                "DefKind::Trait", ::core::option::Option::None);
        }
    };
};debug_assert_matches!(self.def_kind(trait_def_id), DefKind::Trait);
241        let trait_ref = ty::TraitRef::from_assoc(self, trait_def_id, args);
242        (trait_ref, &args[trait_ref.args.len()..])
243    }
244
245    fn mk_args(self, args: &[Self::GenericArg]) -> ty::GenericArgsRef<'tcx> {
246        self.mk_args(args)
247    }
248
249    fn mk_args_from_iter<I, T>(self, args: I) -> T::Output
250    where
251        I: Iterator<Item = T>,
252        T: CollectAndApply<Self::GenericArg, ty::GenericArgsRef<'tcx>>,
253    {
254        self.mk_args_from_iter(args)
255    }
256
257    fn check_args_compatible(self, def_id: DefId, args: ty::GenericArgsRef<'tcx>) -> bool {
258        self.check_args_compatible(def_id, args)
259    }
260
261    fn debug_assert_args_compatible(self, def_id: DefId, args: ty::GenericArgsRef<'tcx>) {
262        self.debug_assert_args_compatible(def_id, args);
263    }
264
265    /// Assert that the args from an `ExistentialTraitRef` or `ExistentialProjection`
266    /// are compatible with the `DefId`. Since we're missing a `Self` type, stick on
267    /// a dummy self type and forward to `debug_assert_args_compatible`.
268    fn debug_assert_existential_args_compatible(
269        self,
270        def_id: Self::DefId,
271        args: Self::GenericArgs,
272    ) {
273        // FIXME: We could perhaps add a `skip: usize` to `debug_assert_args_compatible`
274        // to avoid needing to reintern the set of args...
275        if truecfg!(debug_assertions) {
276            self.debug_assert_args_compatible(
277                def_id,
278                self.mk_args_from_iter(
279                    [self.types.trait_object_dummy_self.into()].into_iter().chain(args.iter()),
280                ),
281            );
282        }
283    }
284
285    fn mk_type_list_from_iter<I, T>(self, args: I) -> T::Output
286    where
287        I: Iterator<Item = T>,
288        T: CollectAndApply<Ty<'tcx>, &'tcx List<Ty<'tcx>>>,
289    {
290        self.mk_type_list_from_iter(args)
291    }
292
293    fn parent(self, def_id: DefId) -> DefId {
294        self.parent(def_id)
295    }
296
297    fn recursion_limit(self) -> usize {
298        self.recursion_limit().0
299    }
300
301    type Features = &'tcx rustc_feature::Features;
302
303    fn features(self) -> Self::Features {
304        self.features()
305    }
306
307    fn coroutine_hidden_types(
308        self,
309        def_id: DefId,
310    ) -> ty::EarlyBinder<'tcx, ty::Binder<'tcx, ty::CoroutineWitnessTypes<TyCtxt<'tcx>>>> {
311        self.coroutine_hidden_types(def_id)
312    }
313
314    fn fn_sig(self, def_id: DefId) -> ty::EarlyBinder<'tcx, ty::PolyFnSig<'tcx>> {
315        self.fn_sig(def_id)
316    }
317
318    fn coroutine_movability(self, def_id: DefId) -> rustc_ast::Movability {
319        self.coroutine_movability(def_id)
320    }
321
322    fn coroutine_for_closure(self, def_id: DefId) -> DefId {
323        self.coroutine_for_closure(def_id)
324    }
325
326    fn generics_require_sized_self(self, def_id: DefId) -> bool {
327        self.generics_require_sized_self(def_id)
328    }
329
330    fn item_bounds(
331        self,
332        def_id: DefId,
333    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Clause<'tcx>>> {
334        self.item_bounds(def_id).map_bound(IntoIterator::into_iter)
335    }
336
337    fn item_self_bounds(
338        self,
339        def_id: DefId,
340    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Clause<'tcx>>> {
341        self.item_self_bounds(def_id).map_bound(IntoIterator::into_iter)
342    }
343
344    fn item_non_self_bounds(
345        self,
346        def_id: DefId,
347    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Clause<'tcx>>> {
348        self.item_non_self_bounds(def_id).map_bound(IntoIterator::into_iter)
349    }
350
351    fn predicates_of(
352        self,
353        def_id: DefId,
354    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Clause<'tcx>>> {
355        ty::EarlyBinder::bind(
356            self.predicates_of(def_id).instantiate_identity(self).predicates.into_iter(),
357        )
358    }
359
360    fn own_predicates_of(
361        self,
362        def_id: DefId,
363    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Clause<'tcx>>> {
364        ty::EarlyBinder::bind(
365            self.predicates_of(def_id).instantiate_own_identity().map(|(clause, _)| clause),
366        )
367    }
368
369    fn explicit_super_predicates_of(
370        self,
371        def_id: DefId,
372    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = (ty::Clause<'tcx>, Span)>> {
373        self.explicit_super_predicates_of(def_id).map_bound(|preds| preds.into_iter().copied())
374    }
375
376    fn explicit_implied_predicates_of(
377        self,
378        def_id: DefId,
379    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = (ty::Clause<'tcx>, Span)>> {
380        self.explicit_implied_predicates_of(def_id).map_bound(|preds| preds.into_iter().copied())
381    }
382
383    fn impl_super_outlives(
384        self,
385        impl_def_id: DefId,
386    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Clause<'tcx>>> {
387        self.impl_super_outlives(impl_def_id)
388    }
389
390    fn impl_is_const(self, def_id: DefId) -> bool {
391        if true {
    match self.def_kind(def_id) {
        DefKind::Impl { of_trait: true } => {}
        ref left_val => {
            ::core::panicking::assert_matches_failed(left_val,
                "DefKind::Impl { of_trait: true }",
                ::core::option::Option::None);
        }
    };
};debug_assert_matches!(self.def_kind(def_id), DefKind::Impl { of_trait: true });
392        self.is_conditionally_const(def_id)
393    }
394
395    fn fn_is_const(self, def_id: DefId) -> bool {
396        if true {
    match self.def_kind(def_id) {
        DefKind::Fn | DefKind::AssocFn |
            DefKind::Ctor(CtorOf::Struct, CtorKind::Fn) => {}
        ref left_val => {
            ::core::panicking::assert_matches_failed(left_val,
                "DefKind::Fn | DefKind::AssocFn | DefKind::Ctor(CtorOf::Struct, CtorKind::Fn)",
                ::core::option::Option::None);
        }
    };
};debug_assert_matches!(
397            self.def_kind(def_id),
398            DefKind::Fn | DefKind::AssocFn | DefKind::Ctor(CtorOf::Struct, CtorKind::Fn)
399        );
400        self.is_conditionally_const(def_id)
401    }
402
403    fn closure_is_const(self, def_id: DefId) -> bool {
404        if true {
    match self.def_kind(def_id) {
        DefKind::Closure => {}
        ref left_val => {
            ::core::panicking::assert_matches_failed(left_val,
                "DefKind::Closure", ::core::option::Option::None);
        }
    };
};debug_assert_matches!(self.def_kind(def_id), DefKind::Closure);
405        self.constness(def_id) == hir::Constness::Const
406    }
407
408    fn alias_has_const_conditions(self, def_id: DefId) -> bool {
409        if true {
    match self.def_kind(def_id) {
        DefKind::AssocTy | DefKind::OpaqueTy => {}
        ref left_val => {
            ::core::panicking::assert_matches_failed(left_val,
                "DefKind::AssocTy | DefKind::OpaqueTy",
                ::core::option::Option::None);
        }
    };
};debug_assert_matches!(self.def_kind(def_id), DefKind::AssocTy | DefKind::OpaqueTy);
410        self.is_conditionally_const(def_id)
411    }
412
413    fn const_conditions(
414        self,
415        def_id: DefId,
416    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Binder<'tcx, ty::TraitRef<'tcx>>>> {
417        ty::EarlyBinder::bind(
418            self.const_conditions(def_id).instantiate_identity(self).into_iter().map(|(c, _)| c),
419        )
420    }
421
422    fn explicit_implied_const_bounds(
423        self,
424        def_id: DefId,
425    ) -> ty::EarlyBinder<'tcx, impl IntoIterator<Item = ty::Binder<'tcx, ty::TraitRef<'tcx>>>> {
426        ty::EarlyBinder::bind(
427            self.explicit_implied_const_bounds(def_id).iter_identity_copied().map(|(c, _)| c),
428        )
429    }
430
431    fn impl_self_is_guaranteed_unsized(self, impl_def_id: DefId) -> bool {
432        self.impl_self_is_guaranteed_unsized(impl_def_id)
433    }
434
435    fn has_target_features(self, def_id: DefId) -> bool {
436        !self.codegen_fn_attrs(def_id).target_features.is_empty()
437    }
438
439    fn require_lang_item(self, lang_item: SolverLangItem) -> DefId {
440        self.require_lang_item(solver_lang_item_to_lang_item(lang_item), DUMMY_SP)
441    }
442
443    fn require_trait_lang_item(self, lang_item: SolverTraitLangItem) -> DefId {
444        self.require_lang_item(solver_trait_lang_item_to_lang_item(lang_item), DUMMY_SP)
445    }
446
447    fn require_adt_lang_item(self, lang_item: SolverAdtLangItem) -> DefId {
448        self.require_lang_item(solver_adt_lang_item_to_lang_item(lang_item), DUMMY_SP)
449    }
450
451    fn is_lang_item(self, def_id: DefId, lang_item: SolverLangItem) -> bool {
452        self.is_lang_item(def_id, solver_lang_item_to_lang_item(lang_item))
453    }
454
455    fn is_trait_lang_item(self, def_id: DefId, lang_item: SolverTraitLangItem) -> bool {
456        self.is_lang_item(def_id, solver_trait_lang_item_to_lang_item(lang_item))
457    }
458
459    fn is_adt_lang_item(self, def_id: DefId, lang_item: SolverAdtLangItem) -> bool {
460        self.is_lang_item(def_id, solver_adt_lang_item_to_lang_item(lang_item))
461    }
462
463    fn is_default_trait(self, def_id: DefId) -> bool {
464        self.is_default_trait(def_id)
465    }
466
467    fn is_sizedness_trait(self, def_id: DefId) -> bool {
468        self.is_sizedness_trait(def_id)
469    }
470
471    fn as_lang_item(self, def_id: DefId) -> Option<SolverLangItem> {
472        lang_item_to_solver_lang_item(self.lang_items().from_def_id(def_id)?)
473    }
474
475    fn as_trait_lang_item(self, def_id: DefId) -> Option<SolverTraitLangItem> {
476        lang_item_to_solver_trait_lang_item(self.lang_items().from_def_id(def_id)?)
477    }
478
479    fn as_adt_lang_item(self, def_id: DefId) -> Option<SolverAdtLangItem> {
480        lang_item_to_solver_adt_lang_item(self.lang_items().from_def_id(def_id)?)
481    }
482
483    fn associated_type_def_ids(self, def_id: DefId) -> impl IntoIterator<Item = DefId> {
484        self.associated_items(def_id)
485            .in_definition_order()
486            .filter(|assoc_item| assoc_item.is_type())
487            .map(|assoc_item| assoc_item.def_id)
488    }
489
490    // This implementation is a bit different from `TyCtxt::for_each_relevant_impl`,
491    // since we want to skip over blanket impls for non-rigid aliases, and also we
492    // only want to consider types that *actually* unify with float/int vars.
493    fn for_each_relevant_impl(
494        self,
495        trait_def_id: DefId,
496        self_ty: Ty<'tcx>,
497        mut f: impl FnMut(DefId),
498    ) {
499        let tcx = self;
500        let trait_impls = tcx.trait_impls_of(trait_def_id);
501        let mut consider_impls_for_simplified_type = |simp| {
502            if let Some(impls_for_type) = trait_impls.non_blanket_impls().get(&simp) {
503                for &impl_def_id in impls_for_type {
504                    f(impl_def_id);
505                }
506            }
507        };
508
509        match self_ty.kind() {
510            ty::Bool
511            | ty::Char
512            | ty::Int(_)
513            | ty::Uint(_)
514            | ty::Float(_)
515            | ty::Adt(_, _)
516            | ty::Foreign(_)
517            | ty::Str
518            | ty::Array(_, _)
519            | ty::Pat(_, _)
520            | ty::Slice(_)
521            | ty::RawPtr(_, _)
522            | ty::Ref(_, _, _)
523            | ty::FnDef(_, _)
524            | ty::FnPtr(..)
525            | ty::Dynamic(_, _)
526            | ty::Closure(..)
527            | ty::CoroutineClosure(..)
528            | ty::Coroutine(_, _)
529            | ty::Never
530            | ty::Tuple(_)
531            | ty::UnsafeBinder(_) => {
532                if let Some(simp) = ty::fast_reject::simplify_type(
533                    tcx,
534                    self_ty,
535                    ty::fast_reject::TreatParams::AsRigid,
536                ) {
537                    consider_impls_for_simplified_type(simp);
538                }
539            }
540
541            // HACK: For integer and float variables we have to manually look at all impls
542            // which have some integer or float as a self type.
543            ty::Infer(ty::IntVar(_)) => {
544                use ty::IntTy::*;
545                use ty::UintTy::*;
546                // This causes a compiler error if any new integer kinds are added.
547                let (I8 | I16 | I32 | I64 | I128 | Isize): ty::IntTy;
548                let (U8 | U16 | U32 | U64 | U128 | Usize): ty::UintTy;
549                let possible_integers = [
550                    // signed integers
551                    ty::SimplifiedType::Int(I8),
552                    ty::SimplifiedType::Int(I16),
553                    ty::SimplifiedType::Int(I32),
554                    ty::SimplifiedType::Int(I64),
555                    ty::SimplifiedType::Int(I128),
556                    ty::SimplifiedType::Int(Isize),
557                    // unsigned integers
558                    ty::SimplifiedType::Uint(U8),
559                    ty::SimplifiedType::Uint(U16),
560                    ty::SimplifiedType::Uint(U32),
561                    ty::SimplifiedType::Uint(U64),
562                    ty::SimplifiedType::Uint(U128),
563                    ty::SimplifiedType::Uint(Usize),
564                ];
565                for simp in possible_integers {
566                    consider_impls_for_simplified_type(simp);
567                }
568            }
569
570            ty::Infer(ty::FloatVar(_)) => {
571                // This causes a compiler error if any new float kinds are added.
572                let (ty::FloatTy::F16 | ty::FloatTy::F32 | ty::FloatTy::F64 | ty::FloatTy::F128);
573                let possible_floats = [
574                    ty::SimplifiedType::Float(ty::FloatTy::F16),
575                    ty::SimplifiedType::Float(ty::FloatTy::F32),
576                    ty::SimplifiedType::Float(ty::FloatTy::F64),
577                    ty::SimplifiedType::Float(ty::FloatTy::F128),
578                ];
579
580                for simp in possible_floats {
581                    consider_impls_for_simplified_type(simp);
582                }
583            }
584
585            // The only traits applying to aliases and placeholders are blanket impls.
586            //
587            // Impls which apply to an alias after normalization are handled by
588            // `assemble_candidates_after_normalizing_self_ty`.
589            ty::Alias(_) | ty::Placeholder(..) | ty::Error(_) => (),
590
591            // FIXME: These should ideally not exist as a self type. It would be nice for
592            // the builtin auto trait impls of coroutines to instead directly recurse
593            // into the witness.
594            ty::CoroutineWitness(..) => (),
595
596            // These variants should not exist as a self type.
597            ty::Infer(ty::TyVar(_) | ty::FreshTy(_) | ty::FreshIntTy(_) | ty::FreshFloatTy(_))
598            | ty::Param(_)
599            | ty::Bound(_, _) => crate::util::bug::bug_fmt(format_args!("unexpected self type: {0}", self_ty))bug!("unexpected self type: {self_ty}"),
600        }
601
602        #[allow(rustc::usage_of_type_ir_traits)]
603        self.for_each_blanket_impl(trait_def_id, f)
604    }
605    fn for_each_blanket_impl(self, trait_def_id: DefId, mut f: impl FnMut(DefId)) {
606        let trait_impls = self.trait_impls_of(trait_def_id);
607        for &impl_def_id in trait_impls.blanket_impls() {
608            f(impl_def_id);
609        }
610    }
611
612    fn has_item_definition(self, def_id: DefId) -> bool {
613        self.defaultness(def_id).has_value()
614    }
615
616    fn impl_specializes(self, impl_def_id: Self::DefId, victim_def_id: Self::DefId) -> bool {
617        self.specializes((impl_def_id, victim_def_id))
618    }
619
620    fn impl_is_default(self, impl_def_id: DefId) -> bool {
621        self.defaultness(impl_def_id).is_default()
622    }
623
624    fn impl_trait_ref(self, impl_def_id: DefId) -> ty::EarlyBinder<'tcx, ty::TraitRef<'tcx>> {
625        self.impl_trait_ref(impl_def_id)
626    }
627
628    fn impl_polarity(self, impl_def_id: DefId) -> ty::ImplPolarity {
629        self.impl_polarity(impl_def_id)
630    }
631
632    fn trait_is_auto(self, trait_def_id: DefId) -> bool {
633        self.trait_is_auto(trait_def_id)
634    }
635
636    fn trait_is_coinductive(self, trait_def_id: DefId) -> bool {
637        self.trait_is_coinductive(trait_def_id)
638    }
639
640    fn trait_is_alias(self, trait_def_id: DefId) -> bool {
641        self.trait_is_alias(trait_def_id)
642    }
643
644    fn trait_is_dyn_compatible(self, trait_def_id: DefId) -> bool {
645        self.is_dyn_compatible(trait_def_id)
646    }
647
648    fn trait_is_fundamental(self, def_id: DefId) -> bool {
649        self.trait_def(def_id).is_fundamental
650    }
651
652    fn trait_is_unsafe(self, trait_def_id: Self::DefId) -> bool {
653        self.trait_def(trait_def_id).safety.is_unsafe()
654    }
655
656    fn is_impl_trait_in_trait(self, def_id: DefId) -> bool {
657        self.is_impl_trait_in_trait(def_id)
658    }
659
660    fn delay_bug(self, msg: impl ToString) -> ErrorGuaranteed {
661        self.dcx().span_delayed_bug(DUMMY_SP, msg.to_string())
662    }
663
664    fn is_general_coroutine(self, coroutine_def_id: DefId) -> bool {
665        self.is_general_coroutine(coroutine_def_id)
666    }
667
668    fn coroutine_is_async(self, coroutine_def_id: DefId) -> bool {
669        self.coroutine_is_async(coroutine_def_id)
670    }
671
672    fn coroutine_is_gen(self, coroutine_def_id: DefId) -> bool {
673        self.coroutine_is_gen(coroutine_def_id)
674    }
675
676    fn coroutine_is_async_gen(self, coroutine_def_id: DefId) -> bool {
677        self.coroutine_is_async_gen(coroutine_def_id)
678    }
679
680    type UnsizingParams = &'tcx rustc_index::bit_set::DenseBitSet<u32>;
681    fn unsizing_params_for_adt(self, adt_def_id: DefId) -> Self::UnsizingParams {
682        self.unsizing_params_for_adt(adt_def_id)
683    }
684
685    fn anonymize_bound_vars<T: TypeFoldable<TyCtxt<'tcx>>>(
686        self,
687        binder: ty::Binder<'tcx, T>,
688    ) -> ty::Binder<'tcx, T> {
689        self.anonymize_bound_vars(binder)
690    }
691
692    fn opaque_types_defined_by(self, defining_anchor: LocalDefId) -> Self::LocalDefIds {
693        self.opaque_types_defined_by(defining_anchor)
694    }
695
696    fn opaque_types_and_coroutines_defined_by(
697        self,
698        defining_anchor: Self::LocalDefId,
699    ) -> Self::LocalDefIds {
700        let coroutines_defined_by = self
701            .nested_bodies_within(defining_anchor)
702            .iter()
703            .filter(|def_id| self.is_coroutine(def_id.to_def_id()));
704        self.mk_local_def_ids_from_iter(
705            self.opaque_types_defined_by(defining_anchor).iter().chain(coroutines_defined_by),
706        )
707    }
708
709    type Probe = &'tcx inspect::Probe<TyCtxt<'tcx>>;
710    fn mk_probe(self, probe: inspect::Probe<Self>) -> &'tcx inspect::Probe<TyCtxt<'tcx>> {
711        self.arena.alloc(probe)
712    }
713    fn evaluate_root_goal_for_proof_tree_raw(
714        self,
715        canonical_goal: CanonicalInput<'tcx>,
716    ) -> (QueryResult<'tcx>, &'tcx inspect::Probe<TyCtxt<'tcx>>) {
717        self.evaluate_root_goal_for_proof_tree_raw(canonical_goal)
718    }
719
720    fn item_name(self, id: DefId) -> Symbol {
721        self.opt_item_name(id).unwrap_or_else(|| {
722            crate::util::bug::bug_fmt(format_args!("item_name: no name for {0:?}",
        self.def_path(id)));bug!("item_name: no name for {:?}", self.def_path(id));
723        })
724    }
725}
726
727/// Defines trivial conversion functions between the main [`LangItem`] enum,
728/// and some other lang-item enum that is a subset of it.
729macro_rules! bidirectional_lang_item_map {
730    (
731        $solver_ty:ident, fn $to_solver:ident, fn $from_solver:ident;
732        $($name:ident),+ $(,)?
733    ) => {
734        fn $from_solver(lang_item: $solver_ty) -> LangItem {
735            match lang_item {
736                $($solver_ty::$name => LangItem::$name,)+
737            }
738        }
739
740        fn $to_solver(lang_item: LangItem) -> Option<$solver_ty> {
741            Some(match lang_item {
742                $(LangItem::$name => $solver_ty::$name,)+
743                _ => return None,
744            })
745        }
746    }
747}
748
749fn solver_lang_item_to_lang_item(lang_item: SolverLangItem) -> LangItem {
    match lang_item {
        SolverLangItem::AsyncFnKindUpvars => LangItem::AsyncFnKindUpvars,
        SolverLangItem::AsyncFnOnceOutput => LangItem::AsyncFnOnceOutput,
        SolverLangItem::CallOnceFuture => LangItem::CallOnceFuture,
        SolverLangItem::CallRefFuture => LangItem::CallRefFuture,
        SolverLangItem::CoroutineReturn => LangItem::CoroutineReturn,
        SolverLangItem::CoroutineYield => LangItem::CoroutineYield,
        SolverLangItem::DynMetadata => LangItem::DynMetadata,
        SolverLangItem::FieldBase => LangItem::FieldBase,
        SolverLangItem::FieldType => LangItem::FieldType,
        SolverLangItem::FutureOutput => LangItem::FutureOutput,
        SolverLangItem::Metadata => LangItem::Metadata,
    }
}
fn lang_item_to_solver_lang_item(lang_item: LangItem)
    -> Option<SolverLangItem> {
    Some(match lang_item {
            LangItem::AsyncFnKindUpvars => SolverLangItem::AsyncFnKindUpvars,
            LangItem::AsyncFnOnceOutput => SolverLangItem::AsyncFnOnceOutput,
            LangItem::CallOnceFuture => SolverLangItem::CallOnceFuture,
            LangItem::CallRefFuture => SolverLangItem::CallRefFuture,
            LangItem::CoroutineReturn => SolverLangItem::CoroutineReturn,
            LangItem::CoroutineYield => SolverLangItem::CoroutineYield,
            LangItem::DynMetadata => SolverLangItem::DynMetadata,
            LangItem::FieldBase => SolverLangItem::FieldBase,
            LangItem::FieldType => SolverLangItem::FieldType,
            LangItem::FutureOutput => SolverLangItem::FutureOutput,
            LangItem::Metadata => SolverLangItem::Metadata,
            _ => return None,
        })
}bidirectional_lang_item_map! {
750    SolverLangItem, fn lang_item_to_solver_lang_item, fn solver_lang_item_to_lang_item;
751
752// tidy-alphabetical-start
753    AsyncFnKindUpvars,
754    AsyncFnOnceOutput,
755    CallOnceFuture,
756    CallRefFuture,
757    CoroutineReturn,
758    CoroutineYield,
759    DynMetadata,
760    FieldBase,
761    FieldType,
762    FutureOutput,
763    Metadata,
764// tidy-alphabetical-end
765}
766
767fn solver_adt_lang_item_to_lang_item(lang_item: SolverAdtLangItem)
    -> LangItem {
    match lang_item {
        SolverAdtLangItem::Option => LangItem::Option,
        SolverAdtLangItem::Poll => LangItem::Poll,
    }
}
fn lang_item_to_solver_adt_lang_item(lang_item: LangItem)
    -> Option<SolverAdtLangItem> {
    Some(match lang_item {
            LangItem::Option => SolverAdtLangItem::Option,
            LangItem::Poll => SolverAdtLangItem::Poll,
            _ => return None,
        })
}bidirectional_lang_item_map! {
768    SolverAdtLangItem, fn lang_item_to_solver_adt_lang_item, fn solver_adt_lang_item_to_lang_item;
769
770// tidy-alphabetical-start
771    Option,
772    Poll,
773// tidy-alphabetical-end
774}
775
776fn solver_trait_lang_item_to_lang_item(lang_item: SolverTraitLangItem)
    -> LangItem {
    match lang_item {
        SolverTraitLangItem::AsyncFn => LangItem::AsyncFn,
        SolverTraitLangItem::AsyncFnKindHelper => LangItem::AsyncFnKindHelper,
        SolverTraitLangItem::AsyncFnMut => LangItem::AsyncFnMut,
        SolverTraitLangItem::AsyncFnOnce => LangItem::AsyncFnOnce,
        SolverTraitLangItem::AsyncFnOnceOutput => LangItem::AsyncFnOnceOutput,
        SolverTraitLangItem::AsyncIterator => LangItem::AsyncIterator,
        SolverTraitLangItem::BikeshedGuaranteedNoDrop =>
            LangItem::BikeshedGuaranteedNoDrop,
        SolverTraitLangItem::Clone => LangItem::Clone,
        SolverTraitLangItem::Copy => LangItem::Copy,
        SolverTraitLangItem::Coroutine => LangItem::Coroutine,
        SolverTraitLangItem::Destruct => LangItem::Destruct,
        SolverTraitLangItem::DiscriminantKind => LangItem::DiscriminantKind,
        SolverTraitLangItem::Drop => LangItem::Drop,
        SolverTraitLangItem::Field => LangItem::Field,
        SolverTraitLangItem::Fn => LangItem::Fn,
        SolverTraitLangItem::FnMut => LangItem::FnMut,
        SolverTraitLangItem::FnOnce => LangItem::FnOnce,
        SolverTraitLangItem::FnPtrTrait => LangItem::FnPtrTrait,
        SolverTraitLangItem::FusedIterator => LangItem::FusedIterator,
        SolverTraitLangItem::Future => LangItem::Future,
        SolverTraitLangItem::Iterator => LangItem::Iterator,
        SolverTraitLangItem::MetaSized => LangItem::MetaSized,
        SolverTraitLangItem::PointeeSized => LangItem::PointeeSized,
        SolverTraitLangItem::PointeeTrait => LangItem::PointeeTrait,
        SolverTraitLangItem::Sized => LangItem::Sized,
        SolverTraitLangItem::TransmuteTrait => LangItem::TransmuteTrait,
        SolverTraitLangItem::TrivialClone => LangItem::TrivialClone,
        SolverTraitLangItem::Tuple => LangItem::Tuple,
        SolverTraitLangItem::Unpin => LangItem::Unpin,
        SolverTraitLangItem::Unsize => LangItem::Unsize,
    }
}
fn lang_item_to_solver_trait_lang_item(lang_item: LangItem)
    -> Option<SolverTraitLangItem> {
    Some(match lang_item {
            LangItem::AsyncFn => SolverTraitLangItem::AsyncFn,
            LangItem::AsyncFnKindHelper =>
                SolverTraitLangItem::AsyncFnKindHelper,
            LangItem::AsyncFnMut => SolverTraitLangItem::AsyncFnMut,
            LangItem::AsyncFnOnce => SolverTraitLangItem::AsyncFnOnce,
            LangItem::AsyncFnOnceOutput =>
                SolverTraitLangItem::AsyncFnOnceOutput,
            LangItem::AsyncIterator => SolverTraitLangItem::AsyncIterator,
            LangItem::BikeshedGuaranteedNoDrop =>
                SolverTraitLangItem::BikeshedGuaranteedNoDrop,
            LangItem::Clone => SolverTraitLangItem::Clone,
            LangItem::Copy => SolverTraitLangItem::Copy,
            LangItem::Coroutine => SolverTraitLangItem::Coroutine,
            LangItem::Destruct => SolverTraitLangItem::Destruct,
            LangItem::DiscriminantKind =>
                SolverTraitLangItem::DiscriminantKind,
            LangItem::Drop => SolverTraitLangItem::Drop,
            LangItem::Field => SolverTraitLangItem::Field,
            LangItem::Fn => SolverTraitLangItem::Fn,
            LangItem::FnMut => SolverTraitLangItem::FnMut,
            LangItem::FnOnce => SolverTraitLangItem::FnOnce,
            LangItem::FnPtrTrait => SolverTraitLangItem::FnPtrTrait,
            LangItem::FusedIterator => SolverTraitLangItem::FusedIterator,
            LangItem::Future => SolverTraitLangItem::Future,
            LangItem::Iterator => SolverTraitLangItem::Iterator,
            LangItem::MetaSized => SolverTraitLangItem::MetaSized,
            LangItem::PointeeSized => SolverTraitLangItem::PointeeSized,
            LangItem::PointeeTrait => SolverTraitLangItem::PointeeTrait,
            LangItem::Sized => SolverTraitLangItem::Sized,
            LangItem::TransmuteTrait => SolverTraitLangItem::TransmuteTrait,
            LangItem::TrivialClone => SolverTraitLangItem::TrivialClone,
            LangItem::Tuple => SolverTraitLangItem::Tuple,
            LangItem::Unpin => SolverTraitLangItem::Unpin,
            LangItem::Unsize => SolverTraitLangItem::Unsize,
            _ => return None,
        })
}bidirectional_lang_item_map! {
777    SolverTraitLangItem, fn lang_item_to_solver_trait_lang_item, fn solver_trait_lang_item_to_lang_item;
778
779// tidy-alphabetical-start
780    AsyncFn,
781    AsyncFnKindHelper,
782    AsyncFnMut,
783    AsyncFnOnce,
784    AsyncFnOnceOutput,
785    AsyncIterator,
786    BikeshedGuaranteedNoDrop,
787    Clone,
788    Copy,
789    Coroutine,
790    Destruct,
791    DiscriminantKind,
792    Drop,
793    Field,
794    Fn,
795    FnMut,
796    FnOnce,
797    FnPtrTrait,
798    FusedIterator,
799    Future,
800    Iterator,
801    MetaSized,
802    PointeeSized,
803    PointeeTrait,
804    Sized,
805    TransmuteTrait,
806    TrivialClone,
807    Tuple,
808    Unpin,
809    Unsize,
810// tidy-alphabetical-end
811}