Skip to content

Commit

Permalink
more things are const evaluatable *sparkles*
Browse files Browse the repository at this point in the history
  • Loading branch information
BoxyUwU committed Jan 31, 2021
1 parent 04caa63 commit f6bab65
Show file tree
Hide file tree
Showing 4 changed files with 41 additions and 12 deletions.
31 changes: 22 additions & 9 deletions compiler/rustc_trait_selection/src/traits/const_evaluatable.rs
Original file line number Diff line number Diff line change
Expand Up @@ -50,11 +50,24 @@ pub fn is_const_evaluatable<'cx, 'tcx>(
if b_def == def && b_substs == substs {
debug!("is_const_evaluatable: caller_bound ~~> ok");
return Ok(());
} else if AbstractConst::new(tcx, b_def, b_substs)?
.map_or(false, |b_ct| try_unify(tcx, ct, b_ct))
{
debug!("is_const_evaluatable: abstract_const ~~> ok");
return Ok(());
}

if let Some(b_ct) = AbstractConst::new(tcx, b_def, b_substs)? {
// Try to unify with each subtree in the AbstractConst to allow for
// `N + 1` being const evaluatable even if theres only a `ConstEvaluatable`
// predicate for `(N + 1) * 2`
let result =
walk_abstract_const(tcx, b_ct, |b_ct| {
match try_unify(tcx, ct, b_ct) {
true => ControlFlow::BREAK,
false => ControlFlow::CONTINUE,
}
});

if let ControlFlow::Break(()) = result {
debug!("is_const_evaluatable: abstract_const ~~> ok");
return Ok(());
}
}
}
_ => {} // don't care
Expand All @@ -78,7 +91,7 @@ pub fn is_const_evaluatable<'cx, 'tcx>(
Concrete,
}
let mut failure_kind = FailureKind::Concrete;
walk_abstract_const::<!, _>(tcx, ct, |node| match node {
walk_abstract_const::<!, _>(tcx, ct, |node| match node.root() {
Node::Leaf(leaf) => {
let leaf = leaf.subst(tcx, ct.substs);
if leaf.has_infer_types_or_consts() {
Expand Down Expand Up @@ -580,15 +593,15 @@ pub fn walk_abstract_const<'tcx, R, F>(
mut f: F,
) -> ControlFlow<R>
where
F: FnMut(Node<'tcx>) -> ControlFlow<R>,
F: FnMut(AbstractConst<'tcx>) -> ControlFlow<R>,
{
fn recurse<'tcx, R>(
tcx: TyCtxt<'tcx>,
ct: AbstractConst<'tcx>,
f: &mut dyn FnMut(Node<'tcx>) -> ControlFlow<R>,
f: &mut dyn FnMut(AbstractConst<'tcx>) -> ControlFlow<R>,
) -> ControlFlow<R> {
f(ct)?;
let root = ct.root();
f(root)?;
match root {
Node::Leaf(_) => ControlFlow::CONTINUE,
Node::Binop(_, l, r) => {
Expand Down
4 changes: 2 additions & 2 deletions compiler/rustc_trait_selection/src/traits/object_safety.rs
Original file line number Diff line number Diff line change
Expand Up @@ -828,7 +828,7 @@ fn contains_illegal_self_type_reference<'tcx, T: TypeFoldable<'tcx>>(
// constants which are not considered const evaluatable.
use rustc_middle::mir::abstract_const::Node;
if let Ok(Some(ct)) = AbstractConst::from_const(self.tcx, ct) {
const_evaluatable::walk_abstract_const(self.tcx, ct, |node| match node {
const_evaluatable::walk_abstract_const(self.tcx, ct, |node| match node.root() {
Node::Leaf(leaf) => {
let leaf = leaf.subst(self.tcx, ct.substs);
self.visit_const(leaf)
Expand All @@ -849,7 +849,7 @@ fn contains_illegal_self_type_reference<'tcx, T: TypeFoldable<'tcx>>(
// take a `ty::Const` instead.
use rustc_middle::mir::abstract_const::Node;
if let Ok(Some(ct)) = AbstractConst::new(self.tcx, def, substs) {
const_evaluatable::walk_abstract_const(self.tcx, ct, |node| match node {
const_evaluatable::walk_abstract_const(self.tcx, ct, |node| match node.root() {
Node::Leaf(leaf) => {
let leaf = leaf.subst(self.tcx, ct.substs);
self.visit_const(leaf)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@ where

fn substs3<const L: usize>() -> Substs1<{ (L - 1) * 2 }>
where
[(); (L - 1)]: ,
[(); (L - 1) * 2 + 1]: ,
{
substs2::<{ L - 1 }>()
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
// run-pass
#![feature(const_generics, const_evaluatable_checked)]
#![allow(incomplete_features)]

fn make_array<const M: usize>() -> [(); M + 1] {
[(); M + 1]
}

fn foo<const N: usize>() -> [(); (N * 2) + 1] {
make_array::<{ N * 2 }>()
}

fn main() {
assert_eq!(foo::<10>(), [(); 10 * 2 + 1])
}

// Tests that N * 2 is considered const_evalutable by appearing as part of the (N * 2) + 1 const

0 comments on commit f6bab65

Please sign in to comment.