Skip to content

Commit d118021

Browse files
committedJan 23, 2021
Permit mutable references in all const contexts
·
1.88.01.51.0
1 parent 1986b58 commit d118021

35 files changed

+298
-171
lines changed
 

‎compiler/rustc_mir/src/transform/check_consts/ops.rs

Lines changed: 46 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -268,43 +268,41 @@ impl NonConstOp for CellBorrow {
268268
}
269269

270270
#[derive(Debug)]
271+
/// This op is for `&mut` borrows in the trailing expression of a constant
272+
/// which uses the "enclosing scopes rule" to leak its locals into anonymous
273+
/// static or const items.
271274
pub struct MutBorrow(pub hir::BorrowKind);
272275

273276
impl NonConstOp for MutBorrow {
274277
fn status_in_item(&self, ccx: &ConstCx<'_, '_>) -> Status {
275-
// Forbid everywhere except in const fn with a feature gate
276-
if ccx.const_kind() == hir::ConstContext::ConstFn {
277-
Status::Unstable(sym::const_mut_refs)
278-
} else {
279-
Status::Forbidden
278+
match ccx.const_kind() {
279+
// Mutable statics can handle mutable references in their final value
280+
hir::ConstContext::Static(hir::Mutability::Mut) => Status::Allowed,
281+
_ => Status::Forbidden,
280282
}
281283
}
282284

285+
fn importance(&self) -> DiagnosticImportance {
286+
// If there were primary errors (like non-const function calls), do not emit further
287+
// errors about mutable references.
288+
DiagnosticImportance::Secondary
289+
}
290+
283291
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
284292
let raw = match self.0 {
285293
hir::BorrowKind::Raw => "raw ",
286294
hir::BorrowKind::Ref => "",
287295
};
288296

289-
let mut err = if ccx.const_kind() == hir::ConstContext::ConstFn {
290-
feature_err(
291-
&ccx.tcx.sess.parse_sess,
292-
sym::const_mut_refs,
293-
span,
294-
&format!("{}mutable references are not allowed in {}s", raw, ccx.const_kind()),
295-
)
296-
} else {
297-
let mut err = struct_span_err!(
298-
ccx.tcx.sess,
299-
span,
300-
E0764,
301-
"{}mutable references are not allowed in {}s",
302-
raw,
303-
ccx.const_kind(),
304-
);
305-
err.span_label(span, format!("`&{}mut` is only allowed in `const fn`", raw));
306-
err
307-
};
297+
let mut err = struct_span_err!(
298+
ccx.tcx.sess,
299+
span,
300+
E0764,
301+
"{}mutable references are not allowed in final value of {}s",
302+
raw,
303+
ccx.const_kind(),
304+
);
305+
308306
if ccx.tcx.sess.teach(&err.get_code().unwrap()) {
309307
err.note(
310308
"References in statics and constants may only refer \
@@ -321,6 +319,29 @@ impl NonConstOp for MutBorrow {
321319
}
322320
}
323321

322+
#[derive(Debug)]
323+
pub struct TransientMutBorrow(pub hir::BorrowKind);
324+
325+
impl NonConstOp for TransientMutBorrow {
326+
fn status_in_item(&self, _: &ConstCx<'_, '_>) -> Status {
327+
Status::Unstable(sym::const_mut_refs)
328+
}
329+
330+
fn build_error(&self, ccx: &ConstCx<'_, 'tcx>, span: Span) -> DiagnosticBuilder<'tcx> {
331+
let raw = match self.0 {
332+
hir::BorrowKind::Raw => "raw ",
333+
hir::BorrowKind::Ref => "",
334+
};
335+
336+
feature_err(
337+
&ccx.tcx.sess.parse_sess,
338+
sym::const_mut_refs,
339+
span,
340+
&format!("{}mutable references are not allowed in {}s", raw, ccx.const_kind()),
341+
)
342+
}
343+
}
344+
324345
#[derive(Debug)]
325346
pub struct MutDeref;
326347
impl NonConstOp for MutDeref {
@@ -329,7 +350,7 @@ impl NonConstOp for MutDeref {
329350
}
330351

331352
fn importance(&self) -> DiagnosticImportance {
332-
// Usually a side-effect of a `MutBorrow` somewhere.
353+
// Usually a side-effect of a `TransientMutBorrow` somewhere.
333354
DiagnosticImportance::Secondary
334355
}
335356

‎compiler/rustc_mir/src/transform/check_consts/validation.rs

Lines changed: 26 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -466,6 +466,29 @@ impl Validator<'mir, 'tcx> {
466466
}
467467
}
468468
}
469+
470+
fn check_mut_borrow(&mut self, local: Local, kind: hir::BorrowKind) {
471+
match self.const_kind() {
472+
// In a const fn all borrows are transient or point to the places given via
473+
// references in the arguments (so we already checked them with
474+
// TransientMutBorrow/MutBorrow as appropriate).
475+
// The borrow checker guarantees that no new non-transient borrows are created.
476+
// NOTE: Once we have heap allocations during CTFE we need to figure out
477+
// how to prevent `const fn` to create long-lived allocations that point
478+
// to mutable memory.
479+
hir::ConstContext::ConstFn => self.check_op(ops::TransientMutBorrow(kind)),
480+
_ => {
481+
// Locals with StorageDead do not live beyond the evaluation and can
482+
// thus safely be borrowed without being able to be leaked to the final
483+
// value of the constant.
484+
if self.local_has_storage_dead(local) {
485+
self.check_op(ops::TransientMutBorrow(kind));
486+
} else {
487+
self.check_op(ops::MutBorrow(kind));
488+
}
489+
}
490+
}
491+
}
469492
}
470493

471494
impl Visitor<'tcx> for Validator<'mir, 'tcx> {
@@ -562,15 +585,15 @@ impl Visitor<'tcx> for Validator<'mir, 'tcx> {
562585

563586
if !is_allowed {
564587
if let BorrowKind::Mut { .. } = kind {
565-
self.check_op(ops::MutBorrow(hir::BorrowKind::Ref));
588+
self.check_mut_borrow(place.local, hir::BorrowKind::Ref)
566589
} else {
567590
self.check_op(ops::CellBorrow);
568591
}
569592
}
570593
}
571594

572-
Rvalue::AddressOf(Mutability::Mut, _) => {
573-
self.check_op(ops::MutBorrow(hir::BorrowKind::Raw))
595+
Rvalue::AddressOf(Mutability::Mut, ref place) => {
596+
self.check_mut_borrow(place.local, hir::BorrowKind::Raw)
574597
}
575598

576599
Rvalue::Ref(_, BorrowKind::Shared | BorrowKind::Shallow, ref place)
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
// Checks that immutable static items can't have mutable slices
22

33
static TEST: &'static mut [isize] = &mut [];
4-
//~^ ERROR mutable references are not allowed in statics
4+
//~^ ERROR mutable references are not allowed
55

66
pub fn main() { }

‎src/test/ui/check-static-immutable-mut-slices.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
1-
error[E0764]: mutable references are not allowed in statics
1+
error[E0764]: mutable references are not allowed in final value of statics
22
--> $DIR/check-static-immutable-mut-slices.rs:3:37
33
|
44
LL | static TEST: &'static mut [isize] = &mut [];
5-
| ^^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^^
66

77
error: aborting due to previous error
88

Lines changed: 16 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,29 @@
1-
error[E0764]: raw mutable references are not allowed in constants
1+
error[E0658]: raw mutable references are not allowed in constants
22
--> $DIR/const-address-of-mut.rs:3:32
33
|
44
LL | const A: () = { let mut x = 2; &raw mut x; };
5-
| ^^^^^^^^^^ `&raw mut` is only allowed in `const fn`
5+
| ^^^^^^^^^^
6+
|
7+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
8+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
69

7-
error[E0764]: raw mutable references are not allowed in statics
10+
error[E0658]: raw mutable references are not allowed in statics
811
--> $DIR/const-address-of-mut.rs:5:33
912
|
1013
LL | static B: () = { let mut x = 2; &raw mut x; };
11-
| ^^^^^^^^^^ `&raw mut` is only allowed in `const fn`
14+
| ^^^^^^^^^^
15+
|
16+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
17+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
1218

13-
error[E0764]: raw mutable references are not allowed in statics
19+
error[E0658]: raw mutable references are not allowed in statics
1420
--> $DIR/const-address-of-mut.rs:7:37
1521
|
1622
LL | static mut C: () = { let mut x = 2; &raw mut x; };
17-
| ^^^^^^^^^^ `&raw mut` is only allowed in `const fn`
23+
| ^^^^^^^^^^
24+
|
25+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
26+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
1827

1928
error[E0658]: raw mutable references are not allowed in constant functions
2029
--> $DIR/const-address-of-mut.rs:11:13
@@ -27,5 +36,4 @@ LL | let y = &raw mut x;
2736

2837
error: aborting due to 4 previous errors
2938

30-
Some errors have detailed explanations: E0658, E0764.
31-
For more information about an error, try `rustc --explain E0658`.
39+
For more information about this error, try `rustc --explain E0658`.

‎src/test/ui/consts/const-eval/issue-65394.stderr

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,11 @@
1-
error[E0764]: mutable references are not allowed in constants
1+
error[E0658]: mutable references are not allowed in constants
22
--> $DIR/issue-65394.rs:8:13
33
|
44
LL | let r = &mut x;
5-
| ^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^
6+
|
7+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
8+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
69

710
error[E0493]: destructors cannot be evaluated at compile-time
811
--> $DIR/issue-65394.rs:7:9
@@ -15,5 +18,5 @@ LL | };
1518

1619
error: aborting due to 2 previous errors
1720

18-
Some errors have detailed explanations: E0493, E0764.
21+
Some errors have detailed explanations: E0493, E0658.
1922
For more information about an error, try `rustc --explain E0493`.

‎src/test/ui/consts/const-multi-ref.stderr

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,11 @@
1-
error[E0764]: mutable references are not allowed in constants
1+
error[E0658]: mutable references are not allowed in constants
22
--> $DIR/const-multi-ref.rs:6:13
33
|
44
LL | let p = &mut a;
5-
| ^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^
6+
|
7+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
8+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
69

710
error[E0658]: cannot borrow here, since the borrowed element may contain interior mutability
811
--> $DIR/const-multi-ref.rs:16:13
@@ -15,5 +18,4 @@ LL | let p = &a;
1518

1619
error: aborting due to 2 previous errors
1720

18-
Some errors have detailed explanations: E0658, E0764.
19-
For more information about an error, try `rustc --explain E0658`.
21+
For more information about this error, try `rustc --explain E0658`.

‎src/test/ui/consts/const-mut-refs/const_mut_address_of.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
// check-pass
12
#![feature(const_mut_refs)]
23
#![feature(const_fn)]
34
#![feature(raw_ref_op)]
@@ -22,9 +23,7 @@ const fn baz(foo: &mut Foo)-> *mut usize {
2223

2324
const _: () = {
2425
foo().bar();
25-
//~^ ERROR mutable references are not allowed in constants
2626
baz(&mut foo());
27-
//~^ ERROR mutable references are not allowed in constants
2827
};
2928

3029
fn main() {}

‎src/test/ui/consts/const-mut-refs/const_mut_address_of.stderr

Lines changed: 0 additions & 15 deletions
This file was deleted.

‎src/test/ui/consts/const-mut-refs/const_mut_refs.rs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
// check-pass
12
#![feature(const_mut_refs)]
23

34
struct Foo {
@@ -29,9 +30,6 @@ const fn bazz(foo: &mut Foo) -> usize {
2930

3031
fn main() {
3132
let _: [(); foo().bar()] = [(); 1];
32-
//~^ ERROR mutable references are not allowed in constants
3333
let _: [(); baz(&mut foo())] = [(); 2];
34-
//~^ ERROR mutable references are not allowed in constants
3534
let _: [(); bazz(&mut foo())] = [(); 3];
36-
//~^ ERROR mutable references are not allowed in constants
3735
}

‎src/test/ui/consts/const-mut-refs/const_mut_refs.stderr

Lines changed: 0 additions & 21 deletions
This file was deleted.
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
#![feature(const_mut_refs)]
2+
#![feature(const_fn)]
3+
#![feature(raw_ref_op)]
4+
const NULL: *mut i32 = std::ptr::null_mut();
5+
const A: *const i32 = &4;
6+
7+
// It could be made sound to allow it to compile,
8+
// but we do not want to allow this to compile,
9+
// as that would be an enormous footgun in oli-obk's opinion.
10+
const B: *mut i32 = &mut 4; //~ ERROR mutable references are not allowed
11+
12+
// Could be ok, but the same analysis that prevents the mutable one above will also bail out here
13+
// Using a block with some complex content, because just `&45` would get promoted,
14+
// which is not what we want to test here.
15+
const C: *const i32 = &{
16+
let mut x = 42;
17+
x += 3;
18+
x
19+
};
20+
21+
fn main() {
22+
println!("{}", unsafe { *A });
23+
unsafe { *B = 4 } // Bad news
24+
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
error[E0764]: mutable references are not allowed in final value of constants
2+
--> $DIR/mut_ref_in_final.rs:10:21
3+
|
4+
LL | const B: *mut i32 = &mut 4;
5+
| ^^^^^^
6+
7+
error: aborting due to previous error
8+
9+
For more information about this error, try `rustc --explain E0764`.
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
#![feature(const_mut_refs)]
2+
#![feature(const_fn)]
3+
#![feature(raw_ref_op)]
4+
5+
use std::cell::UnsafeCell;
6+
struct NotAMutex<T>(UnsafeCell<T>);
7+
8+
unsafe impl<T> Sync for NotAMutex<T> {}
9+
10+
const FOO: NotAMutex<&mut i32> = NotAMutex(UnsafeCell::new(&mut 42));
11+
//~^ ERROR temporary value dropped while borrowed
12+
13+
// `BAR` works, because `&42` promotes immediately instead of relying on
14+
// "final value lifetime extension".
15+
const BAR: NotAMutex<&i32> = NotAMutex(UnsafeCell::new(&42));
16+
17+
fn main() {
18+
unsafe {
19+
**FOO.0.get() = 99;
20+
assert_eq!(**FOO.0.get(), 99);
21+
}
22+
}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
error[E0716]: temporary value dropped while borrowed
2+
--> $DIR/mut_ref_in_final_ok.rs:10:65
3+
|
4+
LL | const FOO: NotAMutex<&mut i32> = NotAMutex(UnsafeCell::new(&mut 42));
5+
| -------------------------------^^--
6+
| | | |
7+
| | | temporary value is freed at the end of this statement
8+
| | creates a temporary which is freed while still in use
9+
| using this value as a constant requires that borrow lasts for `'static`
10+
11+
error: aborting due to previous error
12+
13+
For more information about this error, try `rustc --explain E0716`.

‎src/test/ui/consts/const_let_assign3.stderr

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,19 +7,24 @@ LL | const fn foo(&mut self, x: u32) {
77
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
88
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
99

10-
error[E0764]: mutable references are not allowed in constants
10+
error[E0658]: mutable references are not allowed in constants
1111
--> $DIR/const_let_assign3.rs:16:5
1212
|
1313
LL | s.foo(3);
14-
| ^ `&mut` is only allowed in `const fn`
14+
| ^
15+
|
16+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
17+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
1518

16-
error[E0764]: mutable references are not allowed in constants
19+
error[E0658]: mutable references are not allowed in constants
1720
--> $DIR/const_let_assign3.rs:22:13
1821
|
1922
LL | let y = &mut x;
20-
| ^^^^^^ `&mut` is only allowed in `const fn`
23+
| ^^^^^^
24+
|
25+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
26+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
2127

2228
error: aborting due to 3 previous errors
2329

24-
Some errors have detailed explanations: E0658, E0764.
25-
For more information about an error, try `rustc --explain E0658`.
30+
For more information about this error, try `rustc --explain E0658`.
Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,9 @@
11
const C1: &'static mut [usize] = &mut [];
2-
//~^ ERROR: mutable references are not allowed in constants
2+
//~^ ERROR: mutable references are not allowed
33

44
static mut S: usize = 3;
55
const C2: &'static mut usize = unsafe { &mut S };
66
//~^ ERROR: constants cannot refer to statics
77
//~| ERROR: constants cannot refer to statics
8-
//~| ERROR: mutable references are not allowed in constants
98

109
fn main() {}

‎src/test/ui/consts/issue-17718-const-bad-values.stderr

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
1-
error[E0764]: mutable references are not allowed in constants
1+
error[E0764]: mutable references are not allowed in final value of constants
22
--> $DIR/issue-17718-const-bad-values.rs:1:34
33
|
44
LL | const C1: &'static mut [usize] = &mut [];
5-
| ^^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^^
66

77
error[E0013]: constants cannot refer to statics
88
--> $DIR/issue-17718-const-bad-values.rs:5:46
@@ -20,13 +20,7 @@ LL | const C2: &'static mut usize = unsafe { &mut S };
2020
|
2121
= help: consider extracting the value of the `static` to a `const`, and referring to that
2222

23-
error[E0764]: mutable references are not allowed in constants
24-
--> $DIR/issue-17718-const-bad-values.rs:5:41
25-
|
26-
LL | const C2: &'static mut usize = unsafe { &mut S };
27-
| ^^^^^^ `&mut` is only allowed in `const fn`
28-
29-
error: aborting due to 4 previous errors
23+
error: aborting due to 3 previous errors
3024

3125
Some errors have detailed explanations: E0013, E0764.
3226
For more information about an error, try `rustc --explain E0013`.
Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,3 @@
1-
error[E0764]: mutable references are not allowed in constants
2-
--> $DIR/projection_qualif.rs:10:27
3-
|
4-
LL | let b: *mut u32 = &mut a;
5-
| ^^^^^^ `&mut` is only allowed in `const fn`
6-
71
error[E0658]: dereferencing raw pointers in constants is unstable
82
--> $DIR/projection_qualif.rs:11:18
93
|
@@ -13,7 +7,6 @@ LL | unsafe { *b = 5; }
137
= note: see issue #51911 <https://github.com/rust-lang/rust/issues/51911> for more information
148
= help: add `#![feature(const_raw_ptr_deref)]` to the crate attributes to enable
159

16-
error: aborting due to 2 previous errors
10+
error: aborting due to previous error
1711

18-
Some errors have detailed explanations: E0658, E0764.
19-
For more information about an error, try `rustc --explain E0658`.
12+
For more information about this error, try `rustc --explain E0658`.

‎src/test/ui/consts/projection_qualif.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ use std::cell::Cell;
77
const FOO: &u32 = {
88
let mut a = 42;
99
{
10-
let b: *mut u32 = &mut a; //~ ERROR mutable references are not allowed in constants
10+
let b: *mut u32 = &mut a; //[stock]~ ERROR mutable references are not allowed in constants
1111
unsafe { *b = 5; } //~ ERROR dereferencing raw pointers in constants
1212
}
1313
&{a}

‎src/test/ui/consts/projection_qualif.stock.stderr

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,11 @@
1-
error[E0764]: mutable references are not allowed in constants
1+
error[E0658]: mutable references are not allowed in constants
22
--> $DIR/projection_qualif.rs:10:27
33
|
44
LL | let b: *mut u32 = &mut a;
5-
| ^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^
6+
|
7+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
8+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
69

710
error[E0658]: dereferencing raw pointers in constants is unstable
811
--> $DIR/projection_qualif.rs:11:18
@@ -15,5 +18,4 @@ LL | unsafe { *b = 5; }
1518

1619
error: aborting due to 2 previous errors
1720

18-
Some errors have detailed explanations: E0658, E0764.
19-
For more information about an error, try `rustc --explain E0658`.
21+
For more information about this error, try `rustc --explain E0658`.
Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,8 @@
1-
// We are keeping this test in case we decide to allow mutable references in statics again
21
#![feature(const_mut_refs)]
32
#![allow(const_err)]
43

5-
static OH_NO: &mut i32 = &mut 42;
6-
//~^ ERROR mutable references are not allowed in statics
4+
static OH_NO: &mut i32 = &mut 42; //~ ERROR mutable references are not allowed
75
fn main() {
86
assert_eq!(*OH_NO, 42);
7+
*OH_NO = 43; //~ ERROR cannot assign to `*OH_NO`, as `OH_NO` is an immutable static
98
}
Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,16 @@
1-
error[E0764]: mutable references are not allowed in statics
2-
--> $DIR/read_from_static_mut_ref.rs:5:26
1+
error[E0764]: mutable references are not allowed in final value of statics
2+
--> $DIR/read_from_static_mut_ref.rs:4:26
33
|
44
LL | static OH_NO: &mut i32 = &mut 42;
5-
| ^^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^^
66

7-
error: aborting due to previous error
7+
error[E0594]: cannot assign to `*OH_NO`, as `OH_NO` is an immutable static item
8+
--> $DIR/read_from_static_mut_ref.rs:7:5
9+
|
10+
LL | *OH_NO = 43;
11+
| ^^^^^^^^^^^ cannot assign
12+
13+
error: aborting due to 2 previous errors
814

9-
For more information about this error, try `rustc --explain E0764`.
15+
Some errors have detailed explanations: E0594, E0764.
16+
For more information about an error, try `rustc --explain E0594`.
Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,9 @@
1-
error[E0764]: mutable references are not allowed in statics
2-
--> $DIR/static_mut_containing_mut_ref2.rs:7:46
1+
error[E0080]: could not evaluate static initializer
2+
--> $DIR/static_mut_containing_mut_ref2.rs:7:45
33
|
44
LL | pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
5-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ modifying a static's initial value from another static's initializer
66

77
error: aborting due to previous error
88

9-
For more information about this error, try `rustc --explain E0764`.
9+
For more information about this error, try `rustc --explain E0080`.

‎src/test/ui/consts/static_mut_containing_mut_ref2.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
static mut STDERR_BUFFER_SPACE: u8 = 0;
66

77
pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
8-
//~^ ERROR mutable references are not allowed in statics
8+
//[mut_refs]~^ ERROR could not evaluate static initializer
9+
//[stock]~^^ ERROR mutable references are not allowed in statics
910

1011
fn main() {}
Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,12 @@
1-
error[E0764]: mutable references are not allowed in statics
1+
error[E0658]: mutable references are not allowed in statics
22
--> $DIR/static_mut_containing_mut_ref2.rs:7:46
33
|
44
LL | pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
5-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
6+
|
7+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
8+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
69

710
error: aborting due to previous error
811

9-
For more information about this error, try `rustc --explain E0764`.
12+
For more information about this error, try `rustc --explain E0658`.

‎src/test/ui/error-codes/E0017.rs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,13 @@ static X: i32 = 1;
22
const C: i32 = 2;
33
static mut M: i32 = 3;
44

5-
const CR: &'static mut i32 = &mut C; //~ ERROR E0764
5+
const CR: &'static mut i32 = &mut C; //~ ERROR mutable references are not allowed
66
//~| WARN taking a mutable
7-
static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0764
7+
static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0658
88
//~| ERROR cannot borrow
9+
//~| ERROR mutable references are not allowed
910

10-
static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0764
11+
static CONST_REF: &'static mut i32 = &mut C; //~ ERROR mutable references are not allowed
1112
//~| WARN taking a mutable
12-
static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M }; //~ ERROR E0764
13+
static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M }; //~ ERROR mutable references are not
1314
fn main() {}

‎src/test/ui/error-codes/E0017.stderr

Lines changed: 22 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -13,17 +13,26 @@ note: `const` item defined here
1313
LL | const C: i32 = 2;
1414
| ^^^^^^^^^^^^^^^^^
1515

16-
error[E0764]: mutable references are not allowed in constants
16+
error[E0764]: mutable references are not allowed in final value of constants
1717
--> $DIR/E0017.rs:5:30
1818
|
1919
LL | const CR: &'static mut i32 = &mut C;
20-
| ^^^^^^ `&mut` is only allowed in `const fn`
20+
| ^^^^^^
2121

22-
error[E0764]: mutable references are not allowed in statics
22+
error[E0658]: mutation through a reference is not allowed in statics
2323
--> $DIR/E0017.rs:7:39
2424
|
2525
LL | static STATIC_REF: &'static mut i32 = &mut X;
26-
| ^^^^^^ `&mut` is only allowed in `const fn`
26+
| ^^^^^^
27+
|
28+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
29+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
30+
31+
error[E0764]: mutable references are not allowed in final value of statics
32+
--> $DIR/E0017.rs:7:39
33+
|
34+
LL | static STATIC_REF: &'static mut i32 = &mut X;
35+
| ^^^^^^
2736

2837
error[E0596]: cannot borrow immutable static item `X` as mutable
2938
--> $DIR/E0017.rs:7:39
@@ -32,7 +41,7 @@ LL | static STATIC_REF: &'static mut i32 = &mut X;
3241
| ^^^^^^ cannot borrow as mutable
3342

3443
warning: taking a mutable reference to a `const` item
35-
--> $DIR/E0017.rs:10:38
44+
--> $DIR/E0017.rs:11:38
3645
|
3746
LL | static CONST_REF: &'static mut i32 = &mut C;
3847
| ^^^^^^
@@ -45,19 +54,19 @@ note: `const` item defined here
4554
LL | const C: i32 = 2;
4655
| ^^^^^^^^^^^^^^^^^
4756

48-
error[E0764]: mutable references are not allowed in statics
49-
--> $DIR/E0017.rs:10:38
57+
error[E0764]: mutable references are not allowed in final value of statics
58+
--> $DIR/E0017.rs:11:38
5059
|
5160
LL | static CONST_REF: &'static mut i32 = &mut C;
52-
| ^^^^^^ `&mut` is only allowed in `const fn`
61+
| ^^^^^^
5362

54-
error[E0764]: mutable references are not allowed in statics
55-
--> $DIR/E0017.rs:12:52
63+
error[E0764]: mutable references are not allowed in final value of statics
64+
--> $DIR/E0017.rs:13:52
5665
|
5766
LL | static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M };
58-
| ^^^^^^ `&mut` is only allowed in `const fn`
67+
| ^^^^^^
5968

60-
error: aborting due to 5 previous errors; 2 warnings emitted
69+
error: aborting due to 6 previous errors; 2 warnings emitted
6170

62-
Some errors have detailed explanations: E0596, E0764.
71+
Some errors have detailed explanations: E0596, E0658, E0764.
6372
For more information about an error, try `rustc --explain E0596`.

‎src/test/ui/error-codes/E0388.rs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,13 @@
11
static X: i32 = 1;
22
const C: i32 = 2;
33

4-
const CR: &'static mut i32 = &mut C; //~ ERROR E0764
4+
const CR: &'static mut i32 = &mut C; //~ ERROR mutable references are not allowed
55
//~| WARN taking a mutable
66
static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR cannot borrow
7-
//~| ERROR E0764
7+
//~| ERROR E0658
8+
//~| ERROR mutable references are not allowed
89

9-
static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0764
10+
static CONST_REF: &'static mut i32 = &mut C; //~ ERROR mutable references are not allowed
1011
//~| WARN taking a mutable
1112

1213
fn main() {}

‎src/test/ui/error-codes/E0388.stderr

Lines changed: 19 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -13,17 +13,26 @@ note: `const` item defined here
1313
LL | const C: i32 = 2;
1414
| ^^^^^^^^^^^^^^^^^
1515

16-
error[E0764]: mutable references are not allowed in constants
16+
error[E0764]: mutable references are not allowed in final value of constants
1717
--> $DIR/E0388.rs:4:30
1818
|
1919
LL | const CR: &'static mut i32 = &mut C;
20-
| ^^^^^^ `&mut` is only allowed in `const fn`
20+
| ^^^^^^
2121

22-
error[E0764]: mutable references are not allowed in statics
22+
error[E0658]: mutation through a reference is not allowed in statics
2323
--> $DIR/E0388.rs:6:39
2424
|
2525
LL | static STATIC_REF: &'static mut i32 = &mut X;
26-
| ^^^^^^ `&mut` is only allowed in `const fn`
26+
| ^^^^^^
27+
|
28+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
29+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
30+
31+
error[E0764]: mutable references are not allowed in final value of statics
32+
--> $DIR/E0388.rs:6:39
33+
|
34+
LL | static STATIC_REF: &'static mut i32 = &mut X;
35+
| ^^^^^^
2736

2837
error[E0596]: cannot borrow immutable static item `X` as mutable
2938
--> $DIR/E0388.rs:6:39
@@ -32,7 +41,7 @@ LL | static STATIC_REF: &'static mut i32 = &mut X;
3241
| ^^^^^^ cannot borrow as mutable
3342

3443
warning: taking a mutable reference to a `const` item
35-
--> $DIR/E0388.rs:9:38
44+
--> $DIR/E0388.rs:10:38
3645
|
3746
LL | static CONST_REF: &'static mut i32 = &mut C;
3847
| ^^^^^^
@@ -45,13 +54,13 @@ note: `const` item defined here
4554
LL | const C: i32 = 2;
4655
| ^^^^^^^^^^^^^^^^^
4756

48-
error[E0764]: mutable references are not allowed in statics
49-
--> $DIR/E0388.rs:9:38
57+
error[E0764]: mutable references are not allowed in final value of statics
58+
--> $DIR/E0388.rs:10:38
5059
|
5160
LL | static CONST_REF: &'static mut i32 = &mut C;
52-
| ^^^^^^ `&mut` is only allowed in `const fn`
61+
| ^^^^^^
5362

54-
error: aborting due to 4 previous errors; 2 warnings emitted
63+
error: aborting due to 5 previous errors; 2 warnings emitted
5564

56-
Some errors have detailed explanations: E0596, E0764.
65+
Some errors have detailed explanations: E0596, E0658, E0764.
5766
For more information about an error, try `rustc --explain E0596`.

‎src/test/ui/issues/issue-46604.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
static buf: &mut [u8] = &mut [1u8,2,3,4,5,7]; //~ ERROR E0764
1+
static buf: &mut [u8] = &mut [1u8,2,3,4,5,7]; //~ ERROR mutable references are not allowed
22
fn write<T: AsRef<[u8]>>(buffer: T) { }
33

44
fn main() {

‎src/test/ui/issues/issue-46604.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
1-
error[E0764]: mutable references are not allowed in statics
1+
error[E0764]: mutable references are not allowed in final value of statics
22
--> $DIR/issue-46604.rs:1:25
33
|
44
LL | static buf: &mut [u8] = &mut [1u8,2,3,4,5,7];
5-
| ^^^^^^^^^^^^^^^^^^^^ `&mut` is only allowed in `const fn`
5+
| ^^^^^^^^^^^^^^^^^^^^
66

77
error[E0594]: cannot assign to `buf[_]`, as `buf` is an immutable static item
88
--> $DIR/issue-46604.rs:6:5

‎src/test/ui/never_type/issue-52443.stderr

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -39,11 +39,14 @@ error[E0015]: calls in constants are limited to constant functions, tuple struct
3939
LL | [(); { for _ in 0usize.. {}; 0}];
4040
| ^^^^^^^^
4141

42-
error[E0764]: mutable references are not allowed in constants
42+
error[E0658]: mutable references are not allowed in constants
4343
--> $DIR/issue-52443.rs:9:21
4444
|
4545
LL | [(); { for _ in 0usize.. {}; 0}];
46-
| ^^^^^^^^ `&mut` is only allowed in `const fn`
46+
| ^^^^^^^^
47+
|
48+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
49+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
4750

4851
error[E0015]: calls in constants are limited to constant functions, tuple structs and tuple variants
4952
--> $DIR/issue-52443.rs:9:21
@@ -53,5 +56,5 @@ LL | [(); { for _ in 0usize.. {}; 0}];
5356

5457
error: aborting due to 6 previous errors; 1 warning emitted
5558

56-
Some errors have detailed explanations: E0015, E0308, E0744, E0764.
59+
Some errors have detailed explanations: E0015, E0308, E0658, E0744.
5760
For more information about an error, try `rustc --explain E0015`.

‎src/test/ui/unsafe/ranged_ints2_const.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,3 +18,9 @@ const fn bar() -> NonZero<u32> {
1818
let y = unsafe { &mut x.0 }; //~ ERROR mutable references
1919
unsafe { NonZero(1) }
2020
}
21+
22+
const fn boo() -> NonZero<u32> {
23+
let mut x = unsafe { NonZero(1) };
24+
unsafe { let y = &mut x.0; } //~ ERROR mutable references
25+
unsafe { NonZero(1) }
26+
}

‎src/test/ui/unsafe/ranged_ints2_const.stderr

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,15 @@ LL | let y = unsafe { &mut x.0 };
1616
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
1717
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
1818

19+
error[E0658]: mutable references are not allowed in constant functions
20+
--> $DIR/ranged_ints2_const.rs:24:22
21+
|
22+
LL | unsafe { let y = &mut x.0; }
23+
| ^^^^^^^^
24+
|
25+
= note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
26+
= help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
27+
1928
error[E0133]: mutation of layout constrained field is unsafe and requires unsafe function or block
2029
--> $DIR/ranged_ints2_const.rs:11:13
2130
|
@@ -24,7 +33,7 @@ LL | let y = &mut x.0;
2433
|
2534
= note: mutating layout constrained fields cannot statically be checked for valid values
2635

27-
error: aborting due to 3 previous errors
36+
error: aborting due to 4 previous errors
2837

2938
Some errors have detailed explanations: E0133, E0658.
3039
For more information about an error, try `rustc --explain E0133`.

0 commit comments

Comments
 (0)
Please sign in to comment.