about summary refs log tree commit diff
path: root/compiler
diff options
context:
space:
mode:
authorkadmin <julianknodt@gmail.com>2022-01-28 18:14:27 +0000
committerkadmin <julianknodt@gmail.com>2022-01-31 18:30:33 +0000
commitc654e4d6f4abd794707c9e4e046b2e7f852e642f (patch)
tree86e48fe59ebbbb254ef88dedbb6ee4e92dfa0e8a /compiler
parentbd03d8167f856044df6430f1dd69142f7511aca8 (diff)
downloadrust-c654e4d6f4abd794707c9e4e046b2e7f852e642f.tar.gz
rust-c654e4d6f4abd794707c9e4e046b2e7f852e642f.zip
Add ValuePairs::Terms & Fix compile error
And use correct substs.
Diffstat (limited to 'compiler')
-rw-r--r--compiler/rustc_infer/src/infer/at.rs12
-rw-r--r--compiler/rustc_infer/src/infer/error_reporting/mod.rs1
-rw-r--r--compiler/rustc_infer/src/infer/mod.rs1
-rw-r--r--compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs25
-rw-r--r--compiler/rustc_trait_selection/src/traits/project.rs39
-rw-r--r--compiler/rustc_typeck/src/astconv/mod.rs14
6 files changed, 43 insertions, 49 deletions
diff --git a/compiler/rustc_infer/src/infer/at.rs b/compiler/rustc_infer/src/infer/at.rs
index 248e7ef82e4..aa74a92ad1f 100644
--- a/compiler/rustc_infer/src/infer/at.rs
+++ b/compiler/rustc_infer/src/infer/at.rs
@@ -288,21 +288,13 @@ impl<'tcx> ToTrace<'tcx> for &'tcx Const<'tcx> {
 
 impl<'tcx> ToTrace<'tcx> for ty::Term<'tcx> {
     fn to_trace(
-        tcx: TyCtxt<'tcx>,
+        _: TyCtxt<'tcx>,
         cause: &ObligationCause<'tcx>,
         a_is_expected: bool,
         a: Self,
         b: Self,
     ) -> TypeTrace<'tcx> {
-        match (a, b) {
-            (ty::Term::Ty(a), ty::Term::Ty(b)) => {
-                ToTrace::to_trace(tcx, cause, a_is_expected, a, b)
-            }
-            (ty::Term::Const(a), ty::Term::Const(b)) => {
-                ToTrace::to_trace(tcx, cause, a_is_expected, a, b)
-            }
-            (_, _) => span_bug!(cause.span, "Unexpected type/const mismatch"),
-        }
+        TypeTrace { cause: cause.clone(), values: Terms(ExpectedFound::new(a_is_expected, a, b)) }
     }
 }
 
diff --git a/compiler/rustc_infer/src/infer/error_reporting/mod.rs b/compiler/rustc_infer/src/infer/error_reporting/mod.rs
index 1eb8190bd7d..24a5f55d53c 100644
--- a/compiler/rustc_infer/src/infer/error_reporting/mod.rs
+++ b/compiler/rustc_infer/src/infer/error_reporting/mod.rs
@@ -2127,6 +2127,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
             infer::Types(exp_found) => self.expected_found_str_ty(exp_found),
             infer::Regions(exp_found) => self.expected_found_str(exp_found),
             infer::Consts(exp_found) => self.expected_found_str(exp_found),
+            infer::Terms(exp_found) => self.expected_found_str(exp_found),
             infer::TraitRefs(exp_found) => {
                 let pretty_exp_found = ty::error::ExpectedFound {
                     expected: exp_found.expected.print_only_trait_path(),
diff --git a/compiler/rustc_infer/src/infer/mod.rs b/compiler/rustc_infer/src/infer/mod.rs
index 266eec08ceb..330c99f6073 100644
--- a/compiler/rustc_infer/src/infer/mod.rs
+++ b/compiler/rustc_infer/src/infer/mod.rs
@@ -371,6 +371,7 @@ pub enum ValuePairs<'tcx> {
     Types(ExpectedFound<Ty<'tcx>>),
     Regions(ExpectedFound<ty::Region<'tcx>>),
     Consts(ExpectedFound<&'tcx ty::Const<'tcx>>),
+    Terms(ExpectedFound<ty::Term<'tcx>>),
     TraitRefs(ExpectedFound<ty::TraitRef<'tcx>>),
     PolyTraitRefs(ExpectedFound<ty::PolyTraitRef<'tcx>>),
 }
diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs
index d06e8496f59..f16601dd08e 100644
--- a/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs
+++ b/compiler/rustc_trait_selection/src/traits/error_reporting/mod.rs
@@ -1356,26 +1356,11 @@ impl<'a, 'tcx> InferCtxtPrivExt<'a, 'tcx> for InferCtxt<'a, 'tcx> {
                     normalized_ty,
                     data.term,
                 ) {
-                    values = Some(match (normalized_ty, data.term) {
-                        (ty::Term::Ty(normalized_ty), ty::Term::Ty(ty)) => {
-                            infer::ValuePairs::Types(ExpectedFound::new(
-                                is_normalized_ty_expected,
-                                normalized_ty,
-                                ty,
-                            ))
-                        }
-                        (ty::Term::Const(normalized_ct), ty::Term::Const(ct)) => {
-                            infer::ValuePairs::Consts(ExpectedFound::new(
-                                is_normalized_ty_expected,
-                                normalized_ct,
-                                ct,
-                            ))
-                        }
-                        (_, _) => span_bug!(
-                            obligation.cause.span,
-                            "found const or type where other expected"
-                        ),
-                    });
+                    values = Some(infer::ValuePairs::Terms(ExpectedFound::new(
+                        is_normalized_ty_expected,
+                        normalized_ty,
+                        data.term,
+                    )));
                     err_buf = error;
                     err = &err_buf;
                 }
diff --git a/compiler/rustc_trait_selection/src/traits/project.rs b/compiler/rustc_trait_selection/src/traits/project.rs
index ec495bcd655..11cde60f075 100644
--- a/compiler/rustc_trait_selection/src/traits/project.rs
+++ b/compiler/rustc_trait_selection/src/traits/project.rs
@@ -22,6 +22,7 @@ use crate::traits::error_reporting::InferCtxtExt as _;
 use rustc_data_structures::sso::SsoHashSet;
 use rustc_data_structures::stack::ensure_sufficient_stack;
 use rustc_errors::ErrorReported;
+use rustc_hir::def::DefKind;
 use rustc_hir::def_id::DefId;
 use rustc_hir::lang_items::LangItem;
 use rustc_infer::infer::resolve::OpportunisticRegionResolver;
@@ -200,7 +201,7 @@ fn project_and_unify_type<'cx, 'tcx>(
     let infcx = selcx.infcx();
     match obligation.predicate.term {
         ty::Term::Ty(obligation_pred_ty) => {
-            let normalized_ty = match opt_normalize_projection_type::<false>(
+            let normalized_ty = match opt_normalize_projection_type(
                 selcx,
                 obligation.param_env,
                 obligation.predicate.projection_ty,
@@ -215,7 +216,7 @@ fn project_and_unify_type<'cx, 'tcx>(
             debug!(?normalized_ty, ?obligations, "project_and_unify_type result");
             match infcx
                 .at(&obligation.cause, obligation.param_env)
-                .eq(normalized_ty, obligation_pred_ty.into())
+                .eq(normalized_ty, obligation_pred_ty)
             {
                 Ok(InferOk { obligations: inferred_obligations, value: () }) => {
                     obligations.extend(inferred_obligations);
@@ -228,7 +229,7 @@ fn project_and_unify_type<'cx, 'tcx>(
             }
         }
         ty::Term::Const(obligation_pred_const) => {
-            let normalized_const = match opt_normalize_projection_type::<true>(
+            let normalized_const = match opt_normalize_projection_type(
                 selcx,
                 obligation.param_env,
                 obligation.predicate.projection_ty,
@@ -492,7 +493,7 @@ impl<'a, 'b, 'tcx> TypeFolder<'tcx> for AssocTypeNormalizer<'a, 'b, 'tcx> {
                 let (data, mapped_regions, mapped_types, mapped_consts) =
                     BoundVarReplacer::replace_bound_vars(infcx, &mut self.universes, data);
                 let data = data.super_fold_with(self);
-                let normalized_ty = opt_normalize_projection_type::<false>(
+                let normalized_ty = opt_normalize_projection_type(
                     self.selcx,
                     self.param_env,
                     data,
@@ -826,7 +827,7 @@ pub fn normalize_projection_type<'a, 'b, 'tcx>(
     depth: usize,
     obligations: &mut Vec<PredicateObligation<'tcx>>,
 ) -> Term<'tcx> {
-    opt_normalize_projection_type::<false>(
+    opt_normalize_projection_type(
         selcx,
         param_env,
         projection_ty,
@@ -859,7 +860,7 @@ pub fn normalize_projection_type<'a, 'b, 'tcx>(
 /// function takes an obligations vector and appends to it directly, which is
 /// slightly uglier but avoids the need for an extra short-lived allocation.
 #[instrument(level = "debug", skip(selcx, param_env, cause, obligations))]
-fn opt_normalize_projection_type<'a, 'b, 'tcx, const INTO_CONST: bool>(
+fn opt_normalize_projection_type<'a, 'b, 'tcx>(
     selcx: &'a mut SelectionContext<'b, 'tcx>,
     param_env: ty::ParamEnv<'tcx>,
     projection_ty: ty::ProjectionTy<'tcx>,
@@ -946,7 +947,7 @@ fn opt_normalize_projection_type<'a, 'b, 'tcx, const INTO_CONST: bool>(
 
     let obligation = Obligation::with_depth(cause.clone(), depth, param_env, projection_ty);
 
-    match project::<INTO_CONST>(selcx, &obligation) {
+    match project(selcx, &obligation) {
         Ok(Projected::Progress(Progress {
             term: projected_term,
             obligations: mut projected_obligations,
@@ -1087,7 +1088,7 @@ impl<'tcx> Progress<'tcx> {
 /// IMPORTANT:
 /// - `obligation` must be fully normalized
 #[tracing::instrument(level = "info", skip(selcx))]
-fn project<'cx, 'tcx, const INTO_CONST: bool>(
+fn project<'cx, 'tcx>(
     selcx: &mut SelectionContext<'cx, 'tcx>,
     obligation: &ProjectionTyObligation<'tcx>,
 ) -> Result<Projected<'tcx>, ProjectionError<'tcx>> {
@@ -1123,7 +1124,7 @@ fn project<'cx, 'tcx, const INTO_CONST: bool>(
 
     match candidates {
         ProjectionCandidateSet::Single(candidate) => {
-            Ok(Projected::Progress(confirm_candidate::<INTO_CONST>(selcx, obligation, candidate)))
+            Ok(Projected::Progress(confirm_candidate(selcx, obligation, candidate)))
         }
         ProjectionCandidateSet::None => Ok(Projected::NoProgress(
             selcx
@@ -1525,7 +1526,7 @@ fn assemble_candidates_from_impls<'cx, 'tcx>(
     });
 }
 
-fn confirm_candidate<'cx, 'tcx, const INTO_CONST: bool>(
+fn confirm_candidate<'cx, 'tcx>(
     selcx: &mut SelectionContext<'cx, 'tcx>,
     obligation: &ProjectionTyObligation<'tcx>,
     candidate: ProjectionCandidate<'tcx>,
@@ -1542,7 +1543,7 @@ fn confirm_candidate<'cx, 'tcx, const INTO_CONST: bool>(
         }
 
         ProjectionCandidate::Select(impl_source) => {
-            confirm_select_candidate::<INTO_CONST>(selcx, obligation, impl_source)
+            confirm_select_candidate(selcx, obligation, impl_source)
         }
     };
 
@@ -1558,15 +1559,13 @@ fn confirm_candidate<'cx, 'tcx, const INTO_CONST: bool>(
     progress
 }
 
-fn confirm_select_candidate<'cx, 'tcx, const INTO_CONST: bool>(
+fn confirm_select_candidate<'cx, 'tcx>(
     selcx: &mut SelectionContext<'cx, 'tcx>,
     obligation: &ProjectionTyObligation<'tcx>,
     impl_source: Selection<'tcx>,
 ) -> Progress<'tcx> {
     match impl_source {
-        super::ImplSource::UserDefined(data) => {
-            confirm_impl_candidate::<INTO_CONST>(selcx, obligation, data)
-        }
+        super::ImplSource::UserDefined(data) => confirm_impl_candidate(selcx, obligation, data),
         super::ImplSource::Generator(data) => confirm_generator_candidate(selcx, obligation, data),
         super::ImplSource::Closure(data) => confirm_closure_candidate(selcx, obligation, data),
         super::ImplSource::FnPointer(data) => confirm_fn_pointer_candidate(selcx, obligation, data),
@@ -1836,7 +1835,7 @@ fn confirm_param_env_candidate<'cx, 'tcx>(
     }
 }
 
-fn confirm_impl_candidate<'cx, 'tcx, const INTO_CONST: bool>(
+fn confirm_impl_candidate<'cx, 'tcx>(
     selcx: &mut SelectionContext<'cx, 'tcx>,
     obligation: &ProjectionTyObligation<'tcx>,
     impl_impl_source: ImplSourceUserDefinedData<'tcx, PredicateObligation<'tcx>>,
@@ -1874,10 +1873,12 @@ fn confirm_impl_candidate<'cx, 'tcx, const INTO_CONST: bool>(
     let substs =
         translate_substs(selcx.infcx(), param_env, impl_def_id, substs, assoc_ty.defining_node);
     let ty = tcx.type_of(assoc_ty.item.def_id);
-    let term: ty::Term<'tcx> = if INTO_CONST {
-        // FIXME(associated_const_equality): what are the right substs?
+    let is_const = matches!(tcx.def_kind(assoc_ty.item.def_id), DefKind::AssocConst);
+    let term: ty::Term<'tcx> = if is_const {
+        let identity_substs =
+            crate::traits::InternalSubsts::identity_for_item(tcx, assoc_ty.item.def_id);
         let did = ty::WithOptConstParam::unknown(assoc_ty.item.def_id);
-        let val = ty::ConstKind::Unevaluated(ty::Unevaluated::new(did, substs));
+        let val = ty::ConstKind::Unevaluated(ty::Unevaluated::new(did, identity_substs));
         tcx.mk_const(ty::Const { ty, val }).into()
     } else {
         ty.into()
diff --git a/compiler/rustc_typeck/src/astconv/mod.rs b/compiler/rustc_typeck/src/astconv/mod.rs
index 6124d2906ff..06d472214e4 100644
--- a/compiler/rustc_typeck/src/astconv/mod.rs
+++ b/compiler/rustc_typeck/src/astconv/mod.rs
@@ -1244,6 +1244,20 @@ impl<'o, 'tcx> dyn AstConv<'tcx> + 'o {
                 // the "projection predicate" for:
                 //
                 // `<T as Iterator>::Item = u32`
+                let def_kind = tcx.def_kind(projection_ty.skip_binder().item_def_id);
+                match (def_kind, term) {
+                    (hir::def::DefKind::AssocTy, ty::Term::Ty(_))
+                    | (hir::def::DefKind::AssocConst, ty::Term::Const(_)) => (),
+                    (_, _) => {
+                        tcx.sess
+                            .struct_span_err(
+                                binding.span,
+                                "type/const mismatch in equality bind of associated field",
+                            )
+                            .span_label(binding.span, "type/const Mismatch")
+                            .emit();
+                    }
+                }
                 bounds.projection_bounds.push((
                     projection_ty.map_bound(|projection_ty| ty::ProjectionPredicate {
                         projection_ty,