Skip to content

Commit

Permalink
use RawConst in miri
Browse files Browse the repository at this point in the history
  • Loading branch information
RalfJung committed Nov 19, 2018
1 parent b50c1b2 commit ba82f54
Show file tree
Hide file tree
Showing 5 changed files with 32 additions and 40 deletions.
14 changes: 10 additions & 4 deletions src/librustc_mir/const_eval.rs
Original file line number Diff line number Diff line change
Expand Up @@ -99,8 +99,7 @@ pub(crate) fn eval_promoted<'a, 'mir, 'tcx>(
eval_body_using_ecx(&mut ecx, cid, Some(mir), param_env)
}

// FIXME: This thing is a bad hack. We should get rid of it. Ideally constants are always
// in an allocation.
// FIXME: These two conversion functions are bad hacks. We should just always use allocations.
pub fn op_to_const<'tcx>(
ecx: &CompileTimeEvalContext<'_, '_, 'tcx>,
op: OpTy<'tcx>,
Expand Down Expand Up @@ -146,6 +145,13 @@ pub fn op_to_const<'tcx>(
};
Ok(ty::Const::from_const_value(ecx.tcx.tcx, val, op.layout.ty))
}
pub fn const_to_op<'tcx>(
ecx: &CompileTimeEvalContext<'_, '_, 'tcx>,
cnst: &ty::Const<'tcx>,
) -> EvalResult<'tcx, OpTy<'tcx>> {
let op = ecx.const_value_to_op(cnst.val)?;
Ok(OpTy { op, layout: ecx.layout_of(cnst.ty)? })
}

fn eval_body_and_ecx<'a, 'mir, 'tcx>(
tcx: TyCtxt<'a, 'tcx, 'tcx>,
Expand Down Expand Up @@ -496,7 +502,7 @@ pub fn const_field<'a, 'tcx>(
let ecx = mk_eval_cx(tcx, instance, param_env).unwrap();
let result = (|| {
// get the operand again
let op = ecx.const_to_op(value)?;
let op = const_to_op(&ecx, value)?;
// downcast
let down = match variant {
None => op,
Expand All @@ -523,7 +529,7 @@ pub fn const_variant_index<'a, 'tcx>(
) -> EvalResult<'tcx, VariantIdx> {
trace!("const_variant_index: {:?}, {:?}", instance, val);
let ecx = mk_eval_cx(tcx, instance, param_env).unwrap();
let op = ecx.const_to_op(val)?;
let op = const_to_op(&ecx, val)?;
Ok(ecx.read_discriminant(op)?.1)
}

Expand Down
14 changes: 9 additions & 5 deletions src/librustc_mir/interpret/eval_context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -588,18 +588,22 @@ impl<'a, 'mir, 'tcx: 'mir, M: Machine<'a, 'mir, 'tcx>> EvalContext<'a, 'mir, 'tc
Ok(())
}

pub fn const_eval(&self, gid: GlobalId<'tcx>) -> EvalResult<'tcx, &'tcx ty::Const<'tcx>> {
pub fn const_eval_raw(
&self,
gid: GlobalId<'tcx>,
) -> EvalResult<'tcx, MPlaceTy<'tcx, M::PointerTag>> {
let param_env = if self.tcx.is_static(gid.instance.def_id()).is_some() {
ty::ParamEnv::reveal_all()
} else {
self.param_env
};
self.tcx.const_eval(param_env.and(gid)).map_err(|err| {
let val = self.tcx.const_eval_raw(param_env.and(gid)).map_err(|err| {
match err {
ErrorHandled::Reported => EvalErrorKind::ReferencedConstant.into(),
ErrorHandled::TooGeneric => EvalErrorKind::TooGeneric.into(),
ErrorHandled::Reported => EvalErrorKind::ReferencedConstant,
ErrorHandled::TooGeneric => EvalErrorKind::TooGeneric,
}
})
})?;
self.raw_const_to_mplace(val)
}

pub fn dump_place(&self, place: Place<M::PointerTag>) {
Expand Down
28 changes: 7 additions & 21 deletions src/librustc_mir/interpret/operand.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
use std::convert::TryInto;

use rustc::{mir, ty};
use rustc::mir;
use rustc::ty::layout::{self, Size, LayoutOf, TyLayout, HasDataLayout, IntegerExt, VariantIdx};

use rustc::mir::interpret::{
Expand Down Expand Up @@ -535,20 +535,21 @@ impl<'a, 'mir, 'tcx, M: Machine<'a, 'mir, 'tcx>> EvalContext<'a, 'mir, 'tcx, M>
.collect()
}

// Also used e.g. when miri runs into a constant.
// FIXME: Can we avoid converting with ConstValue and Const? We should be using RawConst.
fn const_value_to_op(
// Used when miri runs into a constant, and by CTFE.
// FIXME: CTFE should use allocations, then we can make this private (embed it into
// `eval_operand`, ideally).
pub(crate) fn const_value_to_op(
&self,
val: ConstValue<'tcx>,
) -> EvalResult<'tcx, Operand<M::PointerTag>> {
trace!("const_value_to_op: {:?}", val);
match val {
ConstValue::Unevaluated(def_id, substs) => {
let instance = self.resolve(def_id, substs)?;
self.global_to_op(GlobalId {
Ok(*OpTy::from(self.const_eval_raw(GlobalId {
instance,
promoted: None,
})
})?))
}
ConstValue::ByRef(id, alloc, offset) => {
// We rely on mutability being set correctly in that allocation to prevent writes
Expand All @@ -566,21 +567,6 @@ impl<'a, 'mir, 'tcx, M: Machine<'a, 'mir, 'tcx>> EvalContext<'a, 'mir, 'tcx, M>
Ok(Operand::Immediate(Immediate::Scalar(x.into())).with_default_tag()),
}
}
pub fn const_to_op(
&self,
cnst: &ty::Const<'tcx>,
) -> EvalResult<'tcx, OpTy<'tcx, M::PointerTag>> {
let op = self.const_value_to_op(cnst.val)?;
Ok(OpTy { op, layout: self.layout_of(cnst.ty)? })
}

pub(super) fn global_to_op(
&self,
gid: GlobalId<'tcx>
) -> EvalResult<'tcx, Operand<M::PointerTag>> {
let cv = self.const_eval(gid)?;
self.const_value_to_op(cv.val)
}

/// Read discriminant, return the runtime value as well as the variant index.
pub fn read_discriminant(
Expand Down
10 changes: 2 additions & 8 deletions src/librustc_mir/interpret/place.rs
Original file line number Diff line number Diff line change
Expand Up @@ -553,16 +553,10 @@ where
Ok(match *mir_place {
Promoted(ref promoted) => {
let instance = self.frame().instance;
let op = self.global_to_op(GlobalId {
self.const_eval_raw(GlobalId {
instance,
promoted: Some(promoted.0),
})?;
let mplace = op.to_mem_place(); // these are always in memory
let ty = self.monomorphize(promoted.1, self.substs());
MPlaceTy {
mplace,
layout: self.layout_of(ty)?,
}
})?
}

Static(ref static_) => {
Expand Down
6 changes: 4 additions & 2 deletions src/librustc_mir/transform/const_prop.rs
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,9 @@ use rustc::ty::layout::{
};

use interpret::{self, EvalContext, ScalarMaybeUndef, Immediate, OpTy, MemoryKind};
use const_eval::{CompileTimeInterpreter, error_to_const_error, eval_promoted, mk_borrowck_eval_cx};
use const_eval::{
CompileTimeInterpreter, const_to_op, error_to_const_error, eval_promoted, mk_borrowck_eval_cx
};
use transform::{MirPass, MirSource};

pub struct ConstProp;
Expand Down Expand Up @@ -262,7 +264,7 @@ impl<'a, 'mir, 'tcx> ConstPropagator<'a, 'mir, 'tcx> {
source_info: SourceInfo,
) -> Option<Const<'tcx>> {
self.ecx.tcx.span = source_info.span;
match self.ecx.const_to_op(c.literal) {
match const_to_op(&self.ecx, c.literal) {
Ok(op) => {
Some((op, c.span))
},
Expand Down

0 comments on commit ba82f54

Please sign in to comment.