diff --git a/src/librustc/middle/borrowck/doc.rs b/src/librustc/middle/borrowck/doc.rs index f95547ea933..38e93cd39fa 100644 --- a/src/librustc/middle/borrowck/doc.rs +++ b/src/librustc/middle/borrowck/doc.rs @@ -790,7 +790,15 @@ particular, if the referent is frozen, there is no harm in it: In this case, creating the alias `t2` of `t0` is safe because the only thing `t2` can be used for is to further freeze `*t0`, which is -already frozen. +already frozen. In particular, we cannot assign to `*t0` through the +new alias `t2`, as demonstrated in this test case: + + // src/test/run-pass/borrowck-borrow-mut-base-ptr-in-aliasable-loc.rs + fn foo(t0: & &mut int) { + let t1 = t0; + let p: &int = &**t0; + **t1 = 22; //~ ERROR cannot assign + } This distinction is reflected in the rules. When doing an `&mut` borrow -- as in the first example -- the set `ACTIONS` will be @@ -805,6 +813,8 @@ the referent implies that it cannot be claimed or mutated but permits others to freeze. Hence when these restrictions are propagated back to the base path, it will still be considered freezable. + + **FIXME #10520: Restrictions against mutating the base pointer.** When an `&mut` pointer is frozen or claimed, we currently pass along the restriction against MUTATE to the base pointer. I do not believe this diff --git a/src/test/compile-fail/borrowck-borrow-mut-base-ptr-in-aliasable-loc.rs b/src/test/compile-fail/borrowck-borrow-mut-base-ptr-in-aliasable-loc.rs index 843b5436d84..f72dacc2d81 100644 --- a/src/test/compile-fail/borrowck-borrow-mut-base-ptr-in-aliasable-loc.rs +++ b/src/test/compile-fail/borrowck-borrow-mut-base-ptr-in-aliasable-loc.rs @@ -1,3 +1,13 @@ +// Copyright 2012 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or +// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license +// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + // Test that attempt to reborrow an `&mut` pointer in an aliasable // location yields an error. // @@ -7,7 +17,7 @@ use std::util::swap; fn foo(t0: & &mut int) { let t1 = t0; - let p: &int = &**t0; //~ ERROR cannot borrow an `&mut` in a `&` pointer + let p: &int = &**t0; **t1 = 22; //~ ERROR cannot assign } diff --git a/src/test/compile-fail/borrowck-borrow-of-mut-base-ptr.rs b/src/test/compile-fail/borrowck-borrow-of-mut-base-ptr.rs index fd6fda22be2..3f67952fa8e 100644 --- a/src/test/compile-fail/borrowck-borrow-of-mut-base-ptr.rs +++ b/src/test/compile-fail/borrowck-borrow-of-mut-base-ptr.rs @@ -19,7 +19,7 @@ fn foo<'a>(mut t0: &'a mut int, mut t1: &'a mut int) { let p: &mut int = &mut *t0; // Claims `*t0` let mut t2 = &t0; //~ ERROR cannot borrow `t0` - let q: &int = &*t2; // Freezes `*t0` but not through `*p` + let q: &int = &**t2; // Freezes `*t0` but not through `*p` *p += 1; // violates type of `*q` }