Skip to content

Commit

Permalink
Remove control_flow_destroyed and properly lower && and ||
Browse files Browse the repository at this point in the history
  • Loading branch information
ecstatic-morse committed Jun 28, 2020
1 parent 66f0cef commit f33a75c
Show file tree
Hide file tree
Showing 8 changed files with 0 additions and 77 deletions.
11 changes: 0 additions & 11 deletions src/librustc_middle/mir/mod.rs
Expand Up @@ -148,14 +148,6 @@ pub struct Body<'tcx> {
/// Debug information pertaining to user variables, including captures.
pub var_debug_info: Vec<VarDebugInfo<'tcx>>,

/// Mark this MIR of a const context other than const functions as having converted a `&&` or
/// `||` expression into `&` or `|` respectively. This is problematic because if we ever stop
/// this conversion from happening and use short circuiting, we will cause the following code
/// to change the value of `x`: `let mut x = 42; false && { x = 55; true };`
///
/// List of places where control flow was destroyed. Used for error reporting.
pub control_flow_destroyed: Vec<(Span, String)>,

/// A span representing this MIR, for error reporting.
pub span: Span,

Expand Down Expand Up @@ -185,7 +177,6 @@ impl<'tcx> Body<'tcx> {
arg_count: usize,
var_debug_info: Vec<VarDebugInfo<'tcx>>,
span: Span,
control_flow_destroyed: Vec<(Span, String)>,
generator_kind: Option<GeneratorKind>,
) -> Self {
// We need `arg_count` locals, and one for the return place.
Expand All @@ -212,7 +203,6 @@ impl<'tcx> Body<'tcx> {
span,
required_consts: Vec::new(),
ignore_interior_mut_in_const_validation: false,
control_flow_destroyed,
predecessor_cache: PredecessorCache::new(),
}
}
Expand All @@ -236,7 +226,6 @@ impl<'tcx> Body<'tcx> {
spread_arg: None,
span: DUMMY_SP,
required_consts: Vec::new(),
control_flow_destroyed: Vec::new(),
generator_kind: None,
var_debug_info: Vec::new(),
ignore_interior_mut_in_const_validation: false,
Expand Down
1 change: 0 additions & 1 deletion src/librustc_mir/shim.rs
Expand Up @@ -251,7 +251,6 @@ fn new_body<'tcx>(
arg_count,
vec![],
span,
vec![],
None,
)
}
Expand Down
40 changes: 0 additions & 40 deletions src/librustc_mir/transform/check_consts/validation.rs
Expand Up @@ -207,8 +207,6 @@ impl Validator<'mir, 'tcx> {
}
}

check_short_circuiting_in_const_local(self.ccx);

if body.is_cfg_cyclic() {
// We can't provide a good span for the error here, but this should be caught by the
// HIR const-checker anyways.
Expand Down Expand Up @@ -626,44 +624,6 @@ fn error_min_const_fn_violation(tcx: TyCtxt<'_>, span: Span, msg: Cow<'_, str>)
.emit();
}

fn check_short_circuiting_in_const_local(ccx: &ConstCx<'_, 'tcx>) {
let body = ccx.body;

if body.control_flow_destroyed.is_empty() {
return;
}

let mut locals = body.vars_iter();
if let Some(local) = locals.next() {
let span = body.local_decls[local].source_info.span;
let mut error = ccx.tcx.sess.struct_span_err(
span,
&format!(
"new features like let bindings are not permitted in {}s \
which also use short circuiting operators",
ccx.const_kind(),
),
);
for (span, kind) in body.control_flow_destroyed.iter() {
error.span_note(
*span,
&format!(
"use of {} here does not actually short circuit due to \
the const evaluator presently not being able to do control flow. \
See issue #49146 <https://github.com/rust-lang/rust/issues/49146> \
for more information.",
kind
),
);
}
for local in locals {
let span = body.local_decls[local].source_info.span;
error.span_note(span, "more locals are defined here");
}
error.emit();
}
}

fn check_return_ty_is_sync(tcx: TyCtxt<'tcx>, body: &Body<'tcx>, hir_id: HirId) {
let ty = body.return_ty();
tcx.infer_ctxt().enter(|infcx| {
Expand Down
1 change: 0 additions & 1 deletion src/librustc_mir/transform/const_prop.rs
Expand Up @@ -133,7 +133,6 @@ impl<'tcx> MirPass<'tcx> for ConstProp {
body.arg_count,
Default::default(),
tcx.def_span(source.def_id()),
Default::default(),
body.generator_kind,
);

Expand Down
1 change: 0 additions & 1 deletion src/librustc_mir/transform/promote_consts.rs
Expand Up @@ -1142,7 +1142,6 @@ pub fn promote_candidates<'tcx>(
0,
vec![],
body.span,
vec![],
body.generator_kind,
);
promoted.ignore_interior_mut_in_const_validation = true;
Expand Down
1 change: 0 additions & 1 deletion src/librustc_mir_build/build/mod.rs
Expand Up @@ -778,7 +778,6 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
self.arg_count,
self.var_debug_info,
self.fn_span,
self.hir.control_flow_destroyed(),
self.generator_kind,
)
}
Expand Down
14 changes: 0 additions & 14 deletions src/librustc_mir_build/hair/cx/expr.rs
Expand Up @@ -255,20 +255,6 @@ fn make_mirror_unadjusted<'a, 'tcx>(
} else {
// FIXME overflow
match (op.node, cx.constness) {
// Destroy control flow if `#![feature(const_if_match)]` is not enabled.
(hir::BinOpKind::And, hir::Constness::Const)
if !cx.tcx.features().const_if_match =>
{
cx.control_flow_destroyed.push((op.span, "`&&` operator".into()));
ExprKind::Binary { op: BinOp::BitAnd, lhs: lhs.to_ref(), rhs: rhs.to_ref() }
}
(hir::BinOpKind::Or, hir::Constness::Const)
if !cx.tcx.features().const_if_match =>
{
cx.control_flow_destroyed.push((op.span, "`||` operator".into()));
ExprKind::Binary { op: BinOp::BitOr, lhs: lhs.to_ref(), rhs: rhs.to_ref() }
}

(hir::BinOpKind::And, _) => ExprKind::LogicalOp {
op: LogicalOp::And,
lhs: lhs.to_ref(),
Expand Down
8 changes: 0 additions & 8 deletions src/librustc_mir_build/hair/cx/mod.rs
Expand Up @@ -47,9 +47,6 @@ crate struct Cx<'a, 'tcx> {

/// Whether this constant/function needs overflow checks.
check_overflow: bool,

/// See field with the same name on `mir::Body`.
control_flow_destroyed: Vec<(Span, String)>,
}

impl<'a, 'tcx> Cx<'a, 'tcx> {
Expand Down Expand Up @@ -89,13 +86,8 @@ impl<'a, 'tcx> Cx<'a, 'tcx> {
body_owner: src_def_id.to_def_id(),
body_owner_kind,
check_overflow,
control_flow_destroyed: Vec::new(),
}
}

crate fn control_flow_destroyed(self) -> Vec<(Span, String)> {
self.control_flow_destroyed
}
}

impl<'a, 'tcx> Cx<'a, 'tcx> {
Expand Down

0 comments on commit f33a75c

Please sign in to comment.