1
Fork 0

Auto merge of #116010 - RalfJung:more-typed-immediates, r=oli-obk

interpret: more consistently use ImmTy in operators and casts

The diff in src/tools/miri/src/shims/x86/sse2.rs should hopefully suffice to explain why this is nicer. :)
This commit is contained in:
bors 2023-09-21 14:02:55 +00:00
commit 0fd7ce99b0
23 changed files with 298 additions and 285 deletions

View file

@ -210,7 +210,7 @@ impl<'mir, 'tcx> interpret::Machine<'mir, 'tcx> for ConstPropMachine<'mir, 'tcx>
_bin_op: BinOp,
_left: &ImmTy<'tcx>,
_right: &ImmTy<'tcx>,
) -> InterpResult<'tcx, (Scalar, bool, Ty<'tcx>)> {
) -> InterpResult<'tcx, (ImmTy<'tcx>, bool)> {
// We can't do this because aliasing of memory can differ between const eval and llvm
throw_machine_stop_str!("pointer arithmetic or comparisons aren't supported in ConstProp")
}

View file

@ -322,7 +322,7 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> {
fn check_unary_op(&mut self, op: UnOp, arg: &Operand<'tcx>, location: Location) -> Option<()> {
if let (val, true) = self.use_ecx(location, |this| {
let val = this.ecx.read_immediate(&this.ecx.eval_operand(arg, None)?)?;
let (_res, overflow, _ty) = this.ecx.overflowing_unary_op(op, &val)?;
let (_res, overflow) = this.ecx.overflowing_unary_op(op, &val)?;
Ok((val, overflow))
})? {
// `AssertKind` only has an `OverflowNeg` variant, so make sure that is
@ -390,7 +390,7 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> {
if let (Some(l), Some(r)) = (l, r) {
// The remaining operators are handled through `overflowing_binary_op`.
if self.use_ecx(location, |this| {
let (_res, overflow, _ty) = this.ecx.overflowing_binary_op(op, &l, &r)?;
let (_res, overflow) = this.ecx.overflowing_binary_op(op, &l, &r)?;
Ok(overflow)
})? {
let source_info = self.body().source_info(location);

View file

@ -234,21 +234,27 @@ impl<'tcx> ValueAnalysis<'tcx> for ConstAnalysis<'_, 'tcx> {
}
}
Rvalue::Cast(CastKind::IntToInt | CastKind::IntToFloat, operand, ty) => {
let Ok(layout) = self.tcx.layout_of(self.param_env.and(*ty)) else {
return ValueOrPlace::Value(FlatSet::Top);
};
match self.eval_operand(operand, state) {
FlatSet::Elem(op) => self
.ecx
.int_to_int_or_float(&op, *ty)
.map_or(FlatSet::Top, |result| self.wrap_immediate(result)),
.int_to_int_or_float(&op, layout)
.map_or(FlatSet::Top, |result| self.wrap_immediate(*result)),
FlatSet::Bottom => FlatSet::Bottom,
FlatSet::Top => FlatSet::Top,
}
}
Rvalue::Cast(CastKind::FloatToInt | CastKind::FloatToFloat, operand, ty) => {
let Ok(layout) = self.tcx.layout_of(self.param_env.and(*ty)) else {
return ValueOrPlace::Value(FlatSet::Top);
};
match self.eval_operand(operand, state) {
FlatSet::Elem(op) => self
.ecx
.float_to_float_or_int(&op, *ty)
.map_or(FlatSet::Top, |result| self.wrap_immediate(result)),
.float_to_float_or_int(&op, layout)
.map_or(FlatSet::Top, |result| self.wrap_immediate(*result)),
FlatSet::Bottom => FlatSet::Bottom,
FlatSet::Top => FlatSet::Top,
}
@ -268,7 +274,7 @@ impl<'tcx> ValueAnalysis<'tcx> for ConstAnalysis<'_, 'tcx> {
Rvalue::UnaryOp(op, operand) => match self.eval_operand(operand, state) {
FlatSet::Elem(value) => self
.ecx
.unary_op(*op, &value)
.wrapping_unary_op(*op, &value)
.map_or(FlatSet::Top, |val| self.wrap_immediate(*val)),
FlatSet::Bottom => FlatSet::Bottom,
FlatSet::Top => FlatSet::Top,
@ -439,7 +445,9 @@ impl<'a, 'tcx> ConstAnalysis<'a, 'tcx> {
// Both sides are known, do the actual computation.
(FlatSet::Elem(left), FlatSet::Elem(right)) => {
match self.ecx.overflowing_binary_op(op, &left, &right) {
Ok((val, overflow, _)) => (FlatSet::Elem(val), FlatSet::Elem(overflow)),
Ok((val, overflow)) => {
(FlatSet::Elem(val.to_scalar()), FlatSet::Elem(overflow))
}
_ => (FlatSet::Top, FlatSet::Top),
}
}
@ -783,8 +791,8 @@ impl<'mir, 'tcx: 'mir> rustc_const_eval::interpret::Machine<'mir, 'tcx> for Dumm
_bin_op: BinOp,
_left: &rustc_const_eval::interpret::ImmTy<'tcx, Self::Provenance>,
_right: &rustc_const_eval::interpret::ImmTy<'tcx, Self::Provenance>,
) -> interpret::InterpResult<'tcx, (Scalar<Self::Provenance>, bool, Ty<'tcx>)> {
throw_unsup!(Unsupported("".into()))
) -> interpret::InterpResult<'tcx, (ImmTy<'tcx, Self::Provenance>, bool)> {
crate::const_prop::throw_machine_stop_str!("can't do pointer arithmetic");
}
fn expose_ptr(