]> git.lizzy.rs Git - rust.git/commitdiff
make *mut T -> *const T a coercion
authorAriel Ben-Yehuda <arielb1@mail.tau.ac.il>
Thu, 11 Feb 2016 16:31:20 +0000 (18:31 +0200)
committerAriel Ben-Yehuda <ariel.byd@gmail.com>
Fri, 19 Feb 2016 23:54:58 +0000 (01:54 +0200)
rather than being implicit quasi-subtyping. Nothing good can come out
of quasi-subtyping.

src/librustc/middle/expr_use_visitor.rs
src/librustc/middle/mem_categorization.rs
src/librustc/middle/ty/adjustment.rs
src/librustc/util/ppaux.rs
src/librustc_metadata/astencode.rs
src/librustc_mir/hair/cx/expr.rs
src/librustc_passes/consts.rs
src/librustc_trans/trans/consts.rs
src/librustc_trans/trans/expr.rs
src/librustc_typeck/check/coercion.rs
src/librustc_typeck/check/writeback.rs

index 9b315aa46e5d372d9ab250a0be6c71f5d2fa8bea..93cc158cd12f2d6c58858b84a5244d0904dee7d3 100644 (file)
@@ -721,10 +721,11 @@ fn walk_adjustment(&mut self, expr: &hir::Expr) {
         if let Some(adjustment) = adj {
             match adjustment {
                 adjustment::AdjustReifyFnPointer |
         if let Some(adjustment) = adj {
             match adjustment {
                 adjustment::AdjustReifyFnPointer |
-                adjustment::AdjustUnsafeFnPointer => {
+                adjustment::AdjustUnsafeFnPointer |
+                adjustment::AdjustMutToConstPointer => {
                     // Creating a closure/fn-pointer or unsizing consumes
                     // the input and stores it into the resulting rvalue.
                     // Creating a closure/fn-pointer or unsizing consumes
                     // the input and stores it into the resulting rvalue.
-                    debug!("walk_adjustment(AdjustReifyFnPointer|AdjustUnsafeFnPointer)");
+                    debug!("walk_adjustment: trivial adjustment");
                     let cmt_unadjusted =
                         return_if_err!(self.mc.cat_expr_unadjusted(expr));
                     self.delegate_consume(expr.id, expr.span, cmt_unadjusted);
                     let cmt_unadjusted =
                         return_if_err!(self.mc.cat_expr_unadjusted(expr));
                     self.delegate_consume(expr.id, expr.span, cmt_unadjusted);
index c16997157bd9fb9268eeaf9a2f42e6c2ba018ca9..fef35764e1cc13d216b817df350747d9ce631f4d 100644 (file)
@@ -430,6 +430,7 @@ pub fn cat_expr(&self, expr: &hir::Expr) -> McResult<cmt<'tcx>> {
 
                     adjustment::AdjustReifyFnPointer |
                     adjustment::AdjustUnsafeFnPointer |
 
                     adjustment::AdjustReifyFnPointer |
                     adjustment::AdjustUnsafeFnPointer |
+                    adjustment::AdjustMutToConstPointer |
                     adjustment::AdjustDerefRef(_) => {
                         debug!("cat_expr({:?}): {:?}",
                                adjustment,
                     adjustment::AdjustDerefRef(_) => {
                         debug!("cat_expr({:?}): {:?}",
                                adjustment,
index 6cab0baa55325ecebc5adf11ced7205208edbabb..afe177fbdcdcb3aff6ac1440c6af7b326ee42aa4 100644 (file)
@@ -21,8 +21,9 @@
 
 #[derive(Copy, Clone)]
 pub enum AutoAdjustment<'tcx> {
 
 #[derive(Copy, Clone)]
 pub enum AutoAdjustment<'tcx> {
-    AdjustReifyFnPointer,   // go from a fn-item type to a fn-pointer type
-    AdjustUnsafeFnPointer,  // go from a safe fn pointer to an unsafe fn pointer
+    AdjustReifyFnPointer,    // go from a fn-item type to a fn-pointer type
+    AdjustUnsafeFnPointer,   // go from a safe fn pointer to an unsafe fn pointer
+    AdjustMutToConstPointer, // go from a mut raw pointer to a const raw pointer
     AdjustDerefRef(AutoDerefRef<'tcx>),
 }
 
     AdjustDerefRef(AutoDerefRef<'tcx>),
 }
 
@@ -106,7 +107,8 @@ impl<'tcx> AutoAdjustment<'tcx> {
     pub fn is_identity(&self) -> bool {
         match *self {
             AdjustReifyFnPointer |
     pub fn is_identity(&self) -> bool {
         match *self {
             AdjustReifyFnPointer |
-            AdjustUnsafeFnPointer => false,
+            AdjustUnsafeFnPointer |
+            AdjustMutToConstPointer => false,
             AdjustDerefRef(ref r) => r.is_identity(),
         }
     }
             AdjustDerefRef(ref r) => r.is_identity(),
         }
     }
@@ -151,7 +153,7 @@ pub fn adjust<F>(&'tcx self, cx: &ty::ctxt<'tcx>,
         return match adjustment {
             Some(adjustment) => {
                 match *adjustment {
         return match adjustment {
             Some(adjustment) => {
                 match *adjustment {
-                   AdjustReifyFnPointer => {
+                    AdjustReifyFnPointer => {
                         match self.sty {
                             ty::TyBareFn(Some(_), b) => {
                                 cx.mk_fn(None, b)
                         match self.sty {
                             ty::TyBareFn(Some(_), b) => {
                                 cx.mk_fn(None, b)
@@ -164,17 +166,32 @@ pub fn adjust<F>(&'tcx self, cx: &ty::ctxt<'tcx>,
                         }
                     }
 
                         }
                     }
 
-                   AdjustUnsafeFnPointer => {
+                    AdjustUnsafeFnPointer => {
                         match self.sty {
                             ty::TyBareFn(None, b) => cx.safe_to_unsafe_fn_ty(b),
                             ref b => {
                                 cx.sess.bug(
                         match self.sty {
                             ty::TyBareFn(None, b) => cx.safe_to_unsafe_fn_ty(b),
                             ref b => {
                                 cx.sess.bug(
-                                    &format!("AdjustReifyFnPointer adjustment on non-fn-item: \
+                                    &format!("AdjustUnsafeFnPointer adjustment on non-fn-ptr: \
                                              {:?}",
                                             b));
                             }
                         }
                                              {:?}",
                                             b));
                             }
                         }
-                   }
+                    }
+
+                    AdjustMutToConstPointer => {
+                        match self.sty {
+                            ty::TyRawPtr(mt) => cx.mk_ptr(ty::TypeAndMut {
+                                ty: mt.ty,
+                                mutbl: hir::MutImmutable
+                            }),
+                            ref b => {
+                                cx.sess.bug(
+                                    &format!("AdjustMutToConstPointer on non-raw-ptr: \
+                                             {:?}",
+                                            b));
+                            }
+                        }
+                    }
 
                     AdjustDerefRef(ref adj) => {
                         let mut adjusted_ty = self;
 
                     AdjustDerefRef(ref adj) => {
                         let mut adjusted_ty = self;
index a0939dc53dfcf23c3aaf301a56fc8cf59ce0084e..5868f233776c20af519338084f3ad3994f4cb713 100644 (file)
@@ -396,6 +396,9 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
             ty::adjustment::AdjustUnsafeFnPointer => {
                 write!(f, "AdjustUnsafeFnPointer")
             }
             ty::adjustment::AdjustUnsafeFnPointer => {
                 write!(f, "AdjustUnsafeFnPointer")
             }
+            ty::adjustment::AdjustMutToConstPointer => {
+                write!(f, "AdjustMutToConstPointer")
+            }
             ty::adjustment::AdjustDerefRef(ref data) => {
                 write!(f, "{:?}", data)
             }
             ty::adjustment::AdjustDerefRef(ref data) => {
                 write!(f, "{:?}", data)
             }
index 3a0bd3aa2059d35c3d7ad2b281c2de96eddd2aad..fe4df865a0e61cd910bd0613827227256038ce65 100644 (file)
@@ -610,7 +610,7 @@ fn emit_auto_adjustment<'b>(&mut self, ecx: &e::EncodeContext<'b, 'tcx>,
 
         self.emit_enum("AutoAdjustment", |this| {
             match *adj {
 
         self.emit_enum("AutoAdjustment", |this| {
             match *adj {
-                adjustment::AdjustReifyFnPointer=> {
+                adjustment::AdjustReifyFnPointer => {
                     this.emit_enum_variant("AdjustReifyFnPointer", 1, 0, |_| Ok(()))
                 }
 
                     this.emit_enum_variant("AdjustReifyFnPointer", 1, 0, |_| Ok(()))
                 }
 
@@ -620,8 +620,14 @@ fn emit_auto_adjustment<'b>(&mut self, ecx: &e::EncodeContext<'b, 'tcx>,
                     })
                 }
 
                     })
                 }
 
+                adjustment::AdjustMutToConstPointer => {
+                    this.emit_enum_variant("AdjustMutToConstPointer", 3, 0, |_| {
+                        Ok(())
+                    })
+                }
+
                 adjustment::AdjustDerefRef(ref auto_deref_ref) => {
                 adjustment::AdjustDerefRef(ref auto_deref_ref) => {
-                    this.emit_enum_variant("AdjustDerefRef", 3, 2, |this| {
+                    this.emit_enum_variant("AdjustDerefRef", 4, 2, |this| {
                         this.emit_enum_variant_arg(0,
                             |this| Ok(this.emit_auto_deref_ref(ecx, auto_deref_ref)))
                     })
                         this.emit_enum_variant_arg(0,
                             |this| Ok(this.emit_auto_deref_ref(ecx, auto_deref_ref)))
                     })
@@ -1002,12 +1008,14 @@ fn read_upvar_capture(&mut self, dcx: &DecodeContext) -> ty::UpvarCapture {
     fn read_auto_adjustment<'b, 'c>(&mut self, dcx: &DecodeContext<'b, 'c, 'tcx>)
                                     -> adjustment::AutoAdjustment<'tcx> {
         self.read_enum("AutoAdjustment", |this| {
     fn read_auto_adjustment<'b, 'c>(&mut self, dcx: &DecodeContext<'b, 'c, 'tcx>)
                                     -> adjustment::AutoAdjustment<'tcx> {
         self.read_enum("AutoAdjustment", |this| {
-            let variants = ["AdjustReifyFnPointer", "AdjustUnsafeFnPointer", "AdjustDerefRef"];
+            let variants = ["AdjustReifyFnPointer", "AdjustUnsafeFnPointer",
+                            "AdjustMutToConstPointer", "AdjustDerefRef"];
             this.read_enum_variant(&variants, |this, i| {
                 Ok(match i {
                     1 => adjustment::AdjustReifyFnPointer,
                     2 => adjustment::AdjustUnsafeFnPointer,
             this.read_enum_variant(&variants, |this, i| {
                 Ok(match i {
                     1 => adjustment::AdjustReifyFnPointer,
                     2 => adjustment::AdjustUnsafeFnPointer,
-                    3 => {
+                    3 => adjustment::AdjustMutToConstPointer,
+                    4 => {
                         let auto_deref_ref: adjustment::AutoDerefRef =
                             this.read_enum_variant_arg(0,
                                 |this| Ok(this.read_auto_deref_ref(dcx))).unwrap();
                         let auto_deref_ref: adjustment::AutoDerefRef =
                             this.read_enum_variant_arg(0,
                                 |this| Ok(this.read_auto_deref_ref(dcx))).unwrap();
index 769dbe0ab5162472ba5e162b7689512708e39084..324c1e92efc2ed7ba6caea72501dca6741cedc43 100644 (file)
@@ -416,6 +416,9 @@ fn make_mirror<'a>(self, cx: &mut Cx<'a, 'tcx>) -> Expr<'tcx> {
             kind: kind,
         };
 
             kind: kind,
         };
 
+        debug!("unadjusted-expr={:?} applying adjustments={:?}",
+               expr, cx.tcx.tables.borrow().adjustments.get(&self.id));
+
         // Now apply adjustments, if any.
         match cx.tcx.tables.borrow().adjustments.get(&self.id) {
             None => {}
         // Now apply adjustments, if any.
         match cx.tcx.tables.borrow().adjustments.get(&self.id) {
             None => {}
@@ -437,6 +440,15 @@ fn make_mirror<'a>(self, cx: &mut Cx<'a, 'tcx>) -> Expr<'tcx> {
                     kind: ExprKind::UnsafeFnPointer { source: expr.to_ref() },
                 };
             }
                     kind: ExprKind::UnsafeFnPointer { source: expr.to_ref() },
                 };
             }
+            Some(&ty::adjustment::AdjustMutToConstPointer) => {
+                let adjusted_ty = cx.tcx.expr_ty_adjusted(self);
+                expr = Expr {
+                    temp_lifetime: temp_lifetime,
+                    ty: adjusted_ty,
+                    span: self.span,
+                    kind: ExprKind::Cast { source: expr.to_ref() },
+                };
+            }
             Some(&ty::adjustment::AdjustDerefRef(ref adj)) => {
                 for i in 0..adj.autoderefs {
                     let i = i as u32;
             Some(&ty::adjustment::AdjustDerefRef(ref adj)) => {
                 for i in 0..adj.autoderefs {
                     let i = i as u32;
index ee6003f713e7b814b3806af1a3f4b0b7e9916b00..b0d459063ef29a5bccf2c5858d10ce574a3e7368 100644 (file)
@@ -768,7 +768,8 @@ fn check_adjustments<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>, e: &hir::Exp
     match v.tcx.tables.borrow().adjustments.get(&e.id) {
         None |
         Some(&ty::adjustment::AdjustReifyFnPointer) |
     match v.tcx.tables.borrow().adjustments.get(&e.id) {
         None |
         Some(&ty::adjustment::AdjustReifyFnPointer) |
-        Some(&ty::adjustment::AdjustUnsafeFnPointer) => {}
+        Some(&ty::adjustment::AdjustUnsafeFnPointer) |
+        Some(&ty::adjustment::AdjustMutToConstPointer) => {}
 
         Some(&ty::adjustment::AdjustDerefRef(
             ty::adjustment::AutoDerefRef { autoderefs, .. }
 
         Some(&ty::adjustment::AdjustDerefRef(
             ty::adjustment::AutoDerefRef { autoderefs, .. }
index e8c90fa31eac22bf30b9c189b58b1e989a90205c..79c73a83ee7e0e5889152482aa246d0e2f860b05 100644 (file)
@@ -40,7 +40,7 @@
 use trans::Disr;
 use middle::subst::Substs;
 use middle::ty::adjustment::{AdjustDerefRef, AdjustReifyFnPointer};
 use trans::Disr;
 use middle::subst::Substs;
 use middle::ty::adjustment::{AdjustDerefRef, AdjustReifyFnPointer};
-use middle::ty::adjustment::AdjustUnsafeFnPointer;
+use middle::ty::adjustment::{AdjustUnsafeFnPointer, AdjustMutToConstPointer};
 use middle::ty::{self, Ty};
 use middle::ty::cast::{CastTy,IntTy};
 use util::nodemap::NodeMap;
 use middle::ty::{self, Ty};
 use middle::ty::cast::{CastTy,IntTy};
 use util::nodemap::NodeMap;
@@ -354,7 +354,7 @@ pub fn const_expr<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
             // FIXME(#19925) once fn item types are
             // zero-sized, we'll need to do something here
         }
             // FIXME(#19925) once fn item types are
             // zero-sized, we'll need to do something here
         }
-        Some(AdjustUnsafeFnPointer) => {
+        Some(AdjustUnsafeFnPointer) | Some(AdjustMutToConstPointer) => {
             // purely a type-level thing
         }
         Some(AdjustDerefRef(adj)) => {
             // purely a type-level thing
         }
         Some(AdjustDerefRef(adj)) => {
index fac956c1ddd20ea1fd09856220fdde97518508d9..782e38d3af2d4ea6d57d4f59aeb4a7f041281fe9 100644 (file)
@@ -71,7 +71,8 @@
 use trans::type_of;
 use trans::Disr;
 use middle::ty::adjustment::{AdjustDerefRef, AdjustReifyFnPointer};
 use trans::type_of;
 use trans::Disr;
 use middle::ty::adjustment::{AdjustDerefRef, AdjustReifyFnPointer};
-use middle::ty::adjustment::{AdjustUnsafeFnPointer, CustomCoerceUnsized};
+use middle::ty::adjustment::{AdjustUnsafeFnPointer, AdjustMutToConstPointer};
+use middle::ty::adjustment::CustomCoerceUnsized;
 use middle::ty::{self, Ty};
 use middle::ty::MethodCall;
 use middle::ty::cast::{CastKind, CastTy};
 use middle::ty::{self, Ty};
 use middle::ty::MethodCall;
 use middle::ty::cast::{CastKind, CastTy};
@@ -354,7 +355,7 @@ fn adjustment_required<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
             // zero-sized, we'll need to return true here
             false
         }
             // zero-sized, we'll need to return true here
             false
         }
-        AdjustUnsafeFnPointer => {
+        AdjustUnsafeFnPointer | AdjustMutToConstPointer => {
             // purely a type-level thing
             false
         }
             // purely a type-level thing
             false
         }
@@ -391,7 +392,7 @@ fn apply_adjustments<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
             // FIXME(#19925) once fn item types are
             // zero-sized, we'll need to do something here
         }
             // FIXME(#19925) once fn item types are
             // zero-sized, we'll need to do something here
         }
-        AdjustUnsafeFnPointer => {
+        AdjustUnsafeFnPointer | AdjustMutToConstPointer => {
             // purely a type-level thing
         }
         AdjustDerefRef(ref adj) => {
             // purely a type-level thing
         }
         AdjustDerefRef(ref adj) => {
index 8f64e85de4b0f4708d6b481d9b53c0b48139431f..f07464592faacbd887fc3785d97f635bfd07d9b6 100644 (file)
@@ -67,7 +67,7 @@
 use middle::traits::{predicate_for_trait_def, report_selection_error};
 use middle::ty::adjustment::{AutoAdjustment, AutoDerefRef, AdjustDerefRef};
 use middle::ty::adjustment::{AutoPtr, AutoUnsafe, AdjustReifyFnPointer};
 use middle::traits::{predicate_for_trait_def, report_selection_error};
 use middle::ty::adjustment::{AutoAdjustment, AutoDerefRef, AdjustDerefRef};
 use middle::ty::adjustment::{AutoPtr, AutoUnsafe, AdjustReifyFnPointer};
-use middle::ty::adjustment::{AdjustUnsafeFnPointer};
+use middle::ty::adjustment::{AdjustUnsafeFnPointer, AdjustMutToConstPointer};
 use middle::ty::{self, LvaluePreference, TypeAndMut, Ty};
 use middle::ty::fold::TypeFoldable;
 use middle::ty::error::TypeError;
 use middle::ty::{self, LvaluePreference, TypeAndMut, Ty};
 use middle::ty::fold::TypeFoldable;
 use middle::ty::error::TypeError;
@@ -427,6 +427,8 @@ fn coerce_unsafe_ptr(&self,
                 autoref: Some(AutoUnsafe(mutbl_b)),
                 unsize: None
             })))
                 autoref: Some(AutoUnsafe(mutbl_b)),
                 unsize: None
             })))
+        } else if mt_a.mutbl != mutbl_b {
+            Ok(Some(AdjustMutToConstPointer))
         } else {
             Ok(None)
         }
         } else {
             Ok(None)
         }
index e663e449cfc4a3cd922e636ed4ef7f3796daa680..513532397903445c33eaa9fe3be5bf6f5662dacd 100644 (file)
@@ -305,6 +305,10 @@ fn visit_adjustments(&self, reason: ResolveReason, id: ast::NodeId) {
                         adjustment::AdjustReifyFnPointer
                     }
 
                         adjustment::AdjustReifyFnPointer
                     }
 
+                    adjustment::AdjustMutToConstPointer => {
+                        adjustment::AdjustMutToConstPointer
+                    }
+
                     adjustment::AdjustUnsafeFnPointer => {
                         adjustment::AdjustUnsafeFnPointer
                     }
                     adjustment::AdjustUnsafeFnPointer => {
                         adjustment::AdjustUnsafeFnPointer
                     }