about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMark Mansi <markm@cs.wisc.edu>2020-03-13 13:28:25 -0500
committerMark Mansi <markm@cs.wisc.edu>2020-03-13 13:28:25 -0500
commitda4e33a9e659071ae5e7418242dea38d951a260d (patch)
treea5efcc8f0b99c4b74fef72bff0f809396d6c300f
parent508d4a24d1f4ba79bfa01fd6af919609ebeaccbe (diff)
downloadrust-da4e33a9e659071ae5e7418242dea38d951a260d.tar.gz
rust-da4e33a9e659071ae5e7418242dea38d951a260d.zip
move frozen to rustc_data_structures
-rw-r--r--src/librustc_data_structures/frozen.rs57
-rw-r--r--src/librustc_data_structures/lib.rs1
-rw-r--r--src/librustc_mir/borrow_check/mod.rs28
-rw-r--r--src/librustc_mir/borrow_check/region_infer/mod.rs2
-rw-r--r--src/librustc_mir/borrow_check/type_check/free_region_relations.rs2
-rw-r--r--src/librustc_mir/borrow_check/type_check/mod.rs2
6 files changed, 66 insertions, 26 deletions
diff --git a/src/librustc_data_structures/frozen.rs b/src/librustc_data_structures/frozen.rs
new file mode 100644
index 00000000000..835fa7d839c
--- /dev/null
+++ b/src/librustc_data_structures/frozen.rs
@@ -0,0 +1,57 @@
+//! An immutable, owned value.
+//!
+//! The purpose of `Frozen` is to make a value immutable for the sake of defensive programming. For example,
+//! suppose we have the following:
+//!
+//! ```rust
+//! struct Bar { /* some data */ }
+//!
+//! struct Foo {
+//!     /// Some computed data that should never change after construction.
+//!     pub computed: Bar,
+//!
+//!     /* some other fields */
+//! }
+//!
+//! impl Bar {
+//!     /// Mutate the `Bar`.
+//!     pub fn mutate(&mut self) { }
+//! }
+//! ```
+//!
+//! Now suppose we want to pass around a mutable `Foo` instance but, we want to make sure that
+//! `computed` does not change accidentally (e.g. somebody might accidentally call
+//! `foo.computed.mutate()`). This is what `Frozen` is for. We can do the following:
+//!
+//! ```rust
+//! use rustc_data_structures::frozen::Frozen;
+//!
+//! struct Foo {
+//!     /// Some computed data that should never change after construction.
+//!     pub computed: Frozen<Bar>,
+//!
+//!     /* some other fields */
+//! }
+//! ```
+//!
+//! `Frozen` impls `Deref`, so we can ergonomically call methods on `Bar`, but it doesn't `impl
+//! DerefMut`.  Now calling `foo.compute.mutate()` will result in a compile-time error stating that
+//! `mutate` requires a mutable reference but we don't have one.
+
+/// An owned immutable value.
+#[derive(Debug)]
+pub struct Frozen<T>(T);
+
+impl<T> Frozen<T> {
+    pub fn freeze(val: T) -> Self {
+        Frozen(val)
+    }
+}
+
+impl<T> std::ops::Deref for Frozen<T> {
+    type Target = T;
+
+    fn deref(&self) -> &T {
+        &self.0
+    }
+}
diff --git a/src/librustc_data_structures/lib.rs b/src/librustc_data_structures/lib.rs
index 13792a0c890..f9f8ff5303e 100644
--- a/src/librustc_data_structures/lib.rs
+++ b/src/librustc_data_structures/lib.rs
@@ -94,6 +94,7 @@ pub mod profiling;
 pub mod vec_linked_list;
 pub mod work_queue;
 pub use atomic_ref::AtomicRef;
+pub mod frozen;
 
 pub struct OnDrop<F: Fn()>(pub F);
 
diff --git a/src/librustc_mir/borrow_check/mod.rs b/src/librustc_mir/borrow_check/mod.rs
index 8dc6ee7ea3b..a61d00b0120 100644
--- a/src/librustc_mir/borrow_check/mod.rs
+++ b/src/librustc_mir/borrow_check/mod.rs
@@ -73,24 +73,6 @@ crate use place_ext::PlaceExt;
 crate use places_conflict::{places_conflict, PlaceConflictBias};
 crate use region_infer::RegionInferenceContext;
 
-/// An owned immutable value.
-#[derive(Debug)]
-struct Frozen<T>(T);
-
-impl<T> Frozen<T> {
-    pub fn freeze(val: T) -> Self {
-        Frozen(val)
-    }
-}
-
-impl<T> std::ops::Deref for Frozen<T> {
-    type Target = T;
-
-    fn deref(&self) -> &T {
-        &self.0
-    }
-}
-
 // FIXME(eddyb) perhaps move this somewhere more centrally.
 #[derive(Debug)]
 crate struct Upvar {
@@ -1595,11 +1577,11 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
                 mpi,
             );
         } // Only query longest prefix with a MovePath, not further
-          // ancestors; dataflow recurs on children when parents
-          // move (to support partial (re)inits).
-          //
-          // (I.e., querying parents breaks scenario 7; but may want
-          // to do such a query based on partial-init feature-gate.)
+        // ancestors; dataflow recurs on children when parents
+        // move (to support partial (re)inits).
+        //
+        // (I.e., querying parents breaks scenario 7; but may want
+        // to do such a query based on partial-init feature-gate.)
     }
 
     /// Subslices correspond to multiple move paths, so we iterate through the
diff --git a/src/librustc_mir/borrow_check/region_infer/mod.rs b/src/librustc_mir/borrow_check/region_infer/mod.rs
index 089a9b7328e..fe96b3e34a2 100644
--- a/src/librustc_mir/borrow_check/region_infer/mod.rs
+++ b/src/librustc_mir/borrow_check/region_infer/mod.rs
@@ -7,6 +7,7 @@ use rustc::mir::{
 };
 use rustc::ty::{self, subst::SubstsRef, RegionVid, Ty, TyCtxt, TypeFoldable};
 use rustc_data_structures::binary_search_util;
+use rustc_data_structures::frozen::Frozen;
 use rustc_data_structures::fx::{FxHashMap, FxHashSet};
 use rustc_data_structures::graph::scc::Sccs;
 use rustc_hir::def_id::DefId;
@@ -31,7 +32,6 @@ use crate::borrow_check::{
     },
     type_check::{free_region_relations::UniversalRegionRelations, Locations},
     universal_regions::UniversalRegions,
-    Frozen,
 };
 
 mod dump_mir;
diff --git a/src/librustc_mir/borrow_check/type_check/free_region_relations.rs b/src/librustc_mir/borrow_check/type_check/free_region_relations.rs
index a18004ce191..ca61df018bc 100644
--- a/src/librustc_mir/borrow_check/type_check/free_region_relations.rs
+++ b/src/librustc_mir/borrow_check/type_check/free_region_relations.rs
@@ -1,6 +1,7 @@
 use rustc::mir::ConstraintCategory;
 use rustc::ty::free_region_map::FreeRegionRelations;
 use rustc::ty::{self, RegionVid, Ty, TyCtxt};
+use rustc_data_structures::frozen::Frozen;
 use rustc_data_structures::transitive_relation::TransitiveRelation;
 use rustc_infer::infer::canonical::QueryRegionConstraints;
 use rustc_infer::infer::region_constraints::GenericKind;
@@ -15,7 +16,6 @@ use crate::borrow_check::{
     type_check::constraint_conversion,
     type_check::{Locations, MirTypeckRegionConstraints},
     universal_regions::UniversalRegions,
-    Frozen,
 };
 
 #[derive(Debug)]
diff --git a/src/librustc_mir/borrow_check/type_check/mod.rs b/src/librustc_mir/borrow_check/type_check/mod.rs
index f4656673fec..37d179d3d16 100644
--- a/src/librustc_mir/borrow_check/type_check/mod.rs
+++ b/src/librustc_mir/borrow_check/type_check/mod.rs
@@ -18,6 +18,7 @@ use rustc::ty::{
     self, CanonicalUserTypeAnnotation, CanonicalUserTypeAnnotations, RegionVid, ToPolyTraitRef, Ty,
     TyCtxt, UserType, UserTypeAnnotationIndex,
 };
+use rustc_data_structures::frozen::Frozen;
 use rustc_data_structures::fx::{FxHashMap, FxHashSet};
 use rustc_errors::struct_span_err;
 use rustc_hir as hir;
@@ -55,7 +56,6 @@ use crate::borrow_check::{
     renumber,
     type_check::free_region_relations::{CreateResult, UniversalRegionRelations},
     universal_regions::{DefiningTy, UniversalRegions},
-    Frozen,
 };
 
 macro_rules! span_mirbug {