mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-25 16:24:46 +00:00
fix const_prop ICE
This commit is contained in:
parent
58a56cc8c0
commit
7a73b879cb
@ -34,11 +34,9 @@ impl fmt::Display for ConstEvalErrKind {
|
||||
write!(f, "\"{}\" needs an rfc before being allowed inside constants", msg)
|
||||
}
|
||||
ConstAccessesStatic => write!(f, "constant accesses static"),
|
||||
ModifiedGlobal => write!(
|
||||
f,
|
||||
"modifying a static's initial value from another static's \
|
||||
initializer"
|
||||
),
|
||||
ModifiedGlobal => {
|
||||
write!(f, "modifying a static's initial value from another static's initializer")
|
||||
}
|
||||
AssertFailure(ref msg) => write!(f, "{:?}", msg),
|
||||
Panic { msg, line, col, file } => {
|
||||
write!(f, "the evaluated program panicked at '{}', {}:{}:{}", msg, file, line, col)
|
||||
|
@ -358,6 +358,7 @@ impl<'mir, 'tcx> interpret::Machine<'mir, 'tcx> for CompileTimeInterpreter {
|
||||
} else if is_write {
|
||||
Err(ConstEvalErrKind::ModifiedGlobal.into())
|
||||
} else if memory_extra.can_access_statics || def_id.is_none() {
|
||||
// `def_id.is_none()` indicates this is not a static, but a const or so.
|
||||
Ok(())
|
||||
} else {
|
||||
Err(ConstEvalErrKind::ConstAccessesStatic.into())
|
||||
|
@ -209,6 +209,7 @@ pub trait Machine<'mir, 'tcx>: Sized {
|
||||
}
|
||||
|
||||
/// Called before a global allocation is accessed.
|
||||
/// `def_id` is `Some` if this is the "lazy" allocation of a static.
|
||||
#[inline]
|
||||
fn before_access_global(
|
||||
_memory_extra: &Self::MemoryExtra,
|
||||
|
@ -416,7 +416,10 @@ impl<'mir, 'tcx, M: Machine<'mir, 'tcx>> Memory<'mir, 'tcx, M> {
|
||||
) -> InterpResult<'tcx, Cow<'tcx, Allocation<M::PointerTag, M::AllocExtra>>> {
|
||||
let alloc = tcx.alloc_map.lock().get(id);
|
||||
let (alloc, def_id) = match alloc {
|
||||
Some(GlobalAlloc::Memory(mem)) => (mem, None),
|
||||
Some(GlobalAlloc::Memory(mem)) => {
|
||||
// Memory of a constant or promoted or anonymous memory referenced by a static.
|
||||
(mem, None)
|
||||
}
|
||||
Some(GlobalAlloc::Function(..)) => throw_ub!(DerefFunctionPointer(id)),
|
||||
None => throw_ub!(PointerUseAfterFree(id)),
|
||||
Some(GlobalAlloc::Static(def_id)) => {
|
||||
|
@ -274,7 +274,7 @@ impl<'mir, 'tcx> interpret::Machine<'mir, 'tcx> for ConstPropMachine {
|
||||
_memory_extra: &(),
|
||||
_alloc_id: AllocId,
|
||||
allocation: &Allocation<Self::PointerTag, Self::AllocExtra>,
|
||||
_def_id: Option<DefId>,
|
||||
def_id: Option<DefId>,
|
||||
is_write: bool,
|
||||
) -> InterpResult<'tcx> {
|
||||
if is_write {
|
||||
@ -282,7 +282,11 @@ impl<'mir, 'tcx> interpret::Machine<'mir, 'tcx> for ConstPropMachine {
|
||||
}
|
||||
// If the static allocation is mutable or if it has relocations (it may be legal to mutate
|
||||
// the memory behind that in the future), then we can't const prop it.
|
||||
if allocation.mutability == Mutability::Mut || allocation.relocations().len() > 0 {
|
||||
// FIXME: we only check statics here (that have a `DefId`), not other mutable allocations.
|
||||
// Why that?
|
||||
if def_id.is_some()
|
||||
&& (allocation.mutability == Mutability::Mut || allocation.relocations().len() > 0)
|
||||
{
|
||||
throw_machine_stop_str!("can't eval mutable statics in ConstProp");
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user