-
Notifications
You must be signed in to change notification settings - Fork 14k
Description
UPDATED
We have various safe wrappers that permit aliasable mutability (Cell, RefCell, etc). To be sound, all of them must use markers for invariance and non-freeze. We should factor out these markers and so on into a base type Unsafe<T> that contains the most general (and unsafe) form of interior mutability, which is a function that yields a *mut T:
struct Unsafe<T> {
priv value: T,
}
impl<T> Unsafe<T> {
unsafe fn get(&self) -> *mut T { transmute(&self.value) }
}
It will be undefined behavior to transmute an aliasable reference into something mutable through any other means.
Unsafe<T> wlil be integrated into the compiler as follows:
- Its contents are invariant (variance analysis).
- If an immutable static item contains
Unsafe<T>, you cannot take its address. - If a type contains
Unsafe<T>(interior), the compiler will have to be careful about optimizing aliasing and so on. This may correspond to some existing LLVM compiler concept likevolatile. - Remove the
Freezekind (seemingly orthogonal but...not).
This type replaces transmute_mut as the building block for types like Cell. What is better about this is that it ties together the transmute along with the marker types that are required for soundness, so that they cannot be forgotten.
cc @alexcrichton, with whom I was discussing this
cc @brson, because this relates to our discussion on laying out rules for unsafe code