]> git.lizzy.rs Git - rust.git/commitdiff
review, small cleanup
authorBastian Kauschke <bastian_kauschke@hotmail.de>
Fri, 18 Sep 2020 15:11:17 +0000 (17:11 +0200)
committerBastian Kauschke <bastian_kauschke@hotmail.de>
Fri, 18 Sep 2020 15:11:34 +0000 (17:11 +0200)
compiler/rustc_trait_selection/src/traits/const_evaluatable.rs

index db79de06d5e4cb2b74ac191699f38d068c6285a4..6abe62759b6b8570b6e487411accc1db814717ae 100644 (file)
@@ -30,24 +30,24 @@ pub fn is_const_evaluatable<'cx, 'tcx>(
     span: Span,
 ) -> Result<(), ErrorHandled> {
     debug!("is_const_evaluatable({:?}, {:?})", def, substs);
-    if infcx.tcx.features().const_evaluatable_checked {
-        if let Some(ct) = AbstractConst::new(infcx.tcx, def, substs) {
-            for pred in param_env.caller_bounds() {
-                match pred.skip_binders() {
-                    ty::PredicateAtom::ConstEvaluatable(b_def, b_substs) => {
-                        debug!("is_const_evaluatable: caller_bound={:?}, {:?}", b_def, b_substs);
-                        if b_def == def && b_substs == substs {
-                            debug!("is_const_evaluatable: caller_bound ~~> ok");
-                            return Ok(());
-                        } else if AbstractConst::new(infcx.tcx, b_def, b_substs)
-                            .map_or(false, |b_ct| try_unify(infcx.tcx, ct, b_ct))
-                        {
-                            debug!("is_const_evaluatable: abstract_const ~~> ok");
-                            return Ok(());
-                        }
+    // `AbstractConst::new` already returns `None` if `const_evaluatable_checked`
+    // is not active, so we don't have to explicitly check for this here.
+    if let Some(ct) = AbstractConst::new(infcx.tcx, def, substs) {
+        for pred in param_env.caller_bounds() {
+            match pred.skip_binders() {
+                ty::PredicateAtom::ConstEvaluatable(b_def, b_substs) => {
+                    debug!("is_const_evaluatable: caller_bound={:?}, {:?}", b_def, b_substs);
+                    if b_def == def && b_substs == substs {
+                        debug!("is_const_evaluatable: caller_bound ~~> ok");
+                        return Ok(());
+                    } else if AbstractConst::new(infcx.tcx, b_def, b_substs)
+                        .map_or(false, |b_ct| try_unify(infcx.tcx, ct, b_ct))
+                    {
+                        debug!("is_const_evaluatable: abstract_const ~~> ok");
+                        return Ok(());
                     }
-                    _ => {} // don't care
                 }
+                _ => {} // don't care
             }
         }
     }
@@ -394,14 +394,17 @@ pub(super) fn try_unify<'tcx>(
             let a_ct = a_ct.subst(tcx, a.substs);
             let b_ct = b_ct.subst(tcx, b.substs);
             match (a_ct.val, b_ct.val) {
+                // We can just unify errors with everything to reduce the amount of
+                // emitted errors here.
+                (ty::ConstKind::Error(_), _) | (_, ty::ConstKind::Error(_)) => true,
                 (ty::ConstKind::Param(a_param), ty::ConstKind::Param(b_param)) => {
                     a_param == b_param
                 }
                 (ty::ConstKind::Value(a_val), ty::ConstKind::Value(b_val)) => a_val == b_val,
                 // If we have `fn a<const N: usize>() -> [u8; N + 1]` and `fn b<const M: usize>() -> [u8; 1 + M]`
                 // we do not want to use `assert_eq!(a(), b())` to infer that `N` and `M` have to be `1`. This
-                // means that we can't do anything with inference variables here.
-                (ty::ConstKind::Infer(_), _) | (_, ty::ConstKind::Infer(_)) => false,
+                // means that we only allow inference variables if they are equal.
+                (ty::ConstKind::Infer(a_val), ty::ConstKind::Infer(b_val)) => a_val == b_val,
                 // FIXME(const_evaluatable_checked): We may want to either actually try
                 // to evaluate `a_ct` and `b_ct` if they are are fully concrete or something like
                 // this, for now we just return false here.