Skip to content

Commit acda261

Browse files
committed
Auto merge of #61437 - christianpoveda:const-eval-indirects, r=wesleywiser,oli-obk
Add const-eval support for indirects r? @wesleywiser
2 parents 021a503 + b253678 commit acda261

File tree

4 files changed

+58
-13
lines changed

4 files changed

+58
-13
lines changed

src/librustc_mir/interpret/operand.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -268,7 +268,7 @@ impl<'a, 'mir, 'tcx, M: Machine<'a, 'mir, 'tcx>> InterpretCx<'a, 'mir, 'tcx, M>
268268
/// Note that for a given layout, this operation will either always fail or always
269269
/// succeed! Whether it succeeds depends on whether the layout can be represented
270270
/// in a `Immediate`, not on which data is stored there currently.
271-
pub(super) fn try_read_immediate(
271+
pub(crate) fn try_read_immediate(
272272
&self,
273273
src: OpTy<'tcx, M::PointerTag>,
274274
) -> EvalResult<'tcx, Result<Immediate<M::PointerTag>, MemPlace<M::PointerTag>>> {

src/librustc_mir/transform/const_prop.rs

+31-10
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@
33
44
use rustc::hir::def::DefKind;
55
use rustc::mir::{
6-
AggregateKind, Constant, Location, Place, PlaceBase, Body, Operand, Rvalue, Local,
7-
NullOp, UnOp, StatementKind, Statement, LocalKind, Static, StaticKind,
6+
AggregateKind, Constant, Location, Place, PlaceBase, Body, Operand, Rvalue,
7+
Local, NullOp, UnOp, StatementKind, Statement, LocalKind, Static, StaticKind,
88
TerminatorKind, Terminator, ClearCrossCrate, SourceInfo, BinOp, ProjectionElem,
99
SourceScope, SourceScopeLocalData, LocalDecl, Promoted,
1010
};
@@ -21,7 +21,9 @@ use rustc::ty::layout::{
2121
HasTyCtxt, TargetDataLayout, HasDataLayout,
2222
};
2323

24-
use crate::interpret::{self, InterpretCx, ScalarMaybeUndef, Immediate, OpTy, ImmTy, MemoryKind};
24+
use crate::interpret::{
25+
self, InterpretCx, ScalarMaybeUndef, Immediate, OpTy, ImmTy, MemoryKind,
26+
};
2527
use crate::const_eval::{
2628
CompileTimeInterpreter, error_to_const_error, eval_promoted, mk_eval_cx,
2729
};
@@ -516,7 +518,12 @@ impl<'a, 'mir, 'tcx> ConstPropagator<'a, 'mir, 'tcx> {
516518
))
517519
}
518520

519-
fn replace_with_const(&self, rval: &mut Rvalue<'tcx>, value: Const<'tcx>, span: Span) {
521+
fn replace_with_const(
522+
&mut self,
523+
rval: &mut Rvalue<'tcx>,
524+
value: Const<'tcx>,
525+
source_info: SourceInfo,
526+
) {
520527
trace!("attepting to replace {:?} with {:?}", rval, value);
521528
self.ecx.validate_operand(
522529
value,
@@ -525,10 +532,16 @@ impl<'a, 'mir, 'tcx> ConstPropagator<'a, 'mir, 'tcx> {
525532
true,
526533
).expect("value should already be a valid const");
527534

528-
if let interpret::Operand::Immediate(im) = *value {
529-
match im {
535+
// FIXME> figure out what tho do when try_read_immediate fails
536+
let imm = self.use_ecx(source_info, |this| {
537+
this.ecx.try_read_immediate(value)
538+
});
539+
540+
if let Some(Ok(imm)) = imm {
541+
match imm {
530542
interpret::Immediate::Scalar(ScalarMaybeUndef::Scalar(scalar)) => {
531-
*rval = Rvalue::Use(self.operand_from_scalar(scalar, value.layout.ty, span));
543+
*rval = Rvalue::Use(
544+
self.operand_from_scalar(scalar, value.layout.ty, source_info.span));
532545
},
533546
Immediate::ScalarPair(
534547
ScalarMaybeUndef::Scalar(one),
@@ -539,8 +552,12 @@ impl<'a, 'mir, 'tcx> ConstPropagator<'a, 'mir, 'tcx> {
539552
*rval = Rvalue::Aggregate(
540553
Box::new(AggregateKind::Tuple),
541554
vec![
542-
self.operand_from_scalar(one, substs[0].expect_ty(), span),
543-
self.operand_from_scalar(two, substs[1].expect_ty(), span),
555+
self.operand_from_scalar(
556+
one, substs[0].expect_ty(), source_info.span
557+
),
558+
self.operand_from_scalar(
559+
two, substs[1].expect_ty(), source_info.span
560+
),
544561
],
545562
);
546563
}
@@ -655,7 +672,11 @@ impl<'b, 'a, 'tcx> MutVisitor<'tcx> for ConstPropagator<'b, 'a, 'tcx> {
655672
self.places[local] = Some(value);
656673

657674
if self.should_const_prop() {
658-
self.replace_with_const(rval, value, statement.source_info.span);
675+
self.replace_with_const(
676+
rval,
677+
value,
678+
statement.source_info,
679+
);
659680
}
660681
}
661682
}

src/test/mir-opt/const_prop/const_prop_fails_gracefully.rs

+3-2
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,9 @@ fn main() {
2323
// START rustc.main.ConstProp.after.mir
2424
// bb0: {
2525
// ...
26-
// _3 = _4;
27-
// _2 = move _3 as *const i32 (Misc);
26+
// _4 = const Scalar(AllocId(1).0x0) : &i32;
27+
// _3 = const Scalar(AllocId(1).0x0) : &i32;
28+
// _2 = const Scalar(AllocId(1).0x0) : *const i32;
2829
// ...
2930
// _1 = move _2 as usize (Misc);
3031
// ...
+23
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
// compile-flags: -C overflow-checks=on
2+
3+
fn main() {
4+
let x = (2u32 as u8) + 1;
5+
}
6+
7+
// END RUST SOURCE
8+
// START rustc.main.ConstProp.before.mir
9+
// bb0: {
10+
// ...
11+
// _2 = const 2u32 as u8 (Misc);
12+
// _3 = CheckedAdd(move _2, const 1u8);
13+
// assert(!move (_3.1: bool), "attempt to add with overflow") -> bb1;
14+
//}
15+
// END rustc.main.ConstProp.before.mir
16+
// START rustc.main.ConstProp.after.mir
17+
// bb0: {
18+
// ...
19+
// _2 = const 2u8;
20+
// _3 = (const 3u8, const false);
21+
// assert(!const false, "attempt to add with overflow") -> bb1;
22+
// }
23+
// END rustc.main.ConstProp.after.mir

0 commit comments

Comments
 (0)