diff --git a/src/lvalue.rs b/src/lvalue.rs index 9660b8f4eec8..cad4ca9d0290 100644 --- a/src/lvalue.rs +++ b/src/lvalue.rs @@ -104,6 +104,15 @@ impl<'tcx> Global<'tcx> { initialized: false, } } + + pub(super) fn initialized(ty: Ty<'tcx>, value: Value, mutable: bool) -> Self { + Global { + value, + mutable, + ty, + initialized: true, + } + } } impl<'a, 'tcx> EvalContext<'a, 'tcx> { diff --git a/src/step.rs b/src/step.rs index 27eb26e333ac..110a7b2252a8 100644 --- a/src/step.rs +++ b/src/step.rs @@ -13,6 +13,7 @@ use error::{EvalResult, EvalError}; use eval_context::{EvalContext, StackPopCleanup}; use lvalue::{Global, GlobalId, Lvalue}; use value::{Value, PrimVal}; +use memory::Pointer; use syntax::codemap::Span; impl<'a, 'tcx> EvalContext<'a, 'tcx> { @@ -158,6 +159,11 @@ impl<'a, 'b, 'tcx> ConstantExtractor<'a, 'b, 'tcx> { if self.ecx.globals.contains_key(&cid) { return; } + if self.ecx.tcx.has_attr(def_id, "linkage") { + trace!("Initializing an extern global with NULL"); + self.ecx.globals.insert(cid, Global::initialized(self.ecx.tcx.type_of(def_id), Value::ByVal(PrimVal::Ptr(Pointer::from_int(0))), !shared)); + return; + } self.try(|this| { let mir = this.ecx.load_mir(instance.def)?; this.ecx.globals.insert(cid, Global::uninitialized(mir.return_ty)); @@ -178,6 +184,7 @@ impl<'a, 'b, 'tcx> ConstantExtractor<'a, 'b, 'tcx> { ) }); } + fn try EvalResult<'tcx>>(&mut self, f: F) { if let Ok(ref mut n) = *self.new_constants { *n += 1;