about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--src/librustc_trans/mir/constant.rs10
-rw-r--r--src/test/run-pass/mir_constval_adts.rs13
2 files changed, 23 insertions, 0 deletions
diff --git a/src/librustc_trans/mir/constant.rs b/src/librustc_trans/mir/constant.rs
index 0097bca2306..93206179837 100644
--- a/src/librustc_trans/mir/constant.rs
+++ b/src/librustc_trans/mir/constant.rs
@@ -140,6 +140,9 @@ enum Base {
     /// A constant value without an unique address.
     Value(ValueRef),
 
+    /// String literal base pointer (cast from array).
+    Str(ValueRef),
+
     /// The address of a static.
     Static(ValueRef)
 }
@@ -156,6 +159,10 @@ impl<'tcx> ConstLvalue<'tcx> {
     fn to_const(&self, span: Span) -> Const<'tcx> {
         match self.base {
             Base::Value(val) => Const::new(val, self.ty),
+            Base::Str(ptr) => {
+                span_bug!(span, "loading from `str` ({:?}) in constant",
+                          Value(ptr))
+            }
             Base::Static(val) => {
                 span_bug!(span, "loading from `static` ({:?}) in constant",
                           Value(val))
@@ -375,6 +382,8 @@ impl<'a, 'tcx> MirConstContext<'a, 'tcx> {
                         };
                         if self.ccx.statics().borrow().contains_key(&base) {
                             (Base::Static(base), extra)
+                        } else if let ty::TyStr = projected_ty.sty {
+                            (Base::Str(base), extra)
                         } else {
                             let val = consts::load_const(self.ccx, base, projected_ty);
                             if val.is_null() {
@@ -669,6 +678,7 @@ impl<'a, 'tcx> MirConstContext<'a, 'tcx> {
                             consts::addr_of(self.ccx, llval, align, "ref")
                         }
                     }
+                    Base::Str(llval) |
                     Base::Static(llval) => llval
                 };
 
diff --git a/src/test/run-pass/mir_constval_adts.rs b/src/test/run-pass/mir_constval_adts.rs
index 8a1f68dbea3..4e9c0bce646 100644
--- a/src/test/run-pass/mir_constval_adts.rs
+++ b/src/test/run-pass/mir_constval_adts.rs
@@ -14,6 +14,7 @@ struct Point {
     _x: i32,
     _y: i32,
 }
+
 const STRUCT: Point = Point { _x: 42, _y: 42 };
 const TUPLE1: (i32, i32) = (42, 42);
 const TUPLE2: (&'static str, &'static str) = ("hello","world");
@@ -26,7 +27,19 @@ fn mir() -> (Point, (i32, i32), (&'static str, &'static str)){
     (struct1, tuple1, tuple2)
 }
 
+#[derive(PartialEq, Eq, Debug)]
+struct Newtype<T>(T);
+
+const NEWTYPE: Newtype<&'static str> = Newtype("foobar");
+
+#[rustc_mir]
+fn test_promoted_newtype_str_ref() {
+    let x = &NEWTYPE;
+    assert_eq!(x, &Newtype("foobar"));
+}
+
 fn main(){
     assert_eq!(mir(), (STRUCT, TUPLE1, TUPLE2));
+    test_promoted_newtype_str_ref();
 }