about summary refs log tree commit diff
path: root/tests
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2024-01-09 14:50:14 +0000
committerbors <bors@rust-lang.org>2024-01-09 14:50:14 +0000
commit5876c8cdfd3df742c334d6447d44d760c77103b6 (patch)
treeb2437656721ba0a5f4068566975525a9bab87974 /tests
parentbe00c5a9b89161b7f45ba80340f709e8e41122f9 (diff)
parentf41d7739880e72743a74722ae6fcc1be9f7b4e5c (diff)
downloadrust-5876c8cdfd3df742c334d6447d44d760c77103b6.tar.gz
rust-5876c8cdfd3df742c334d6447d44d760c77103b6.zip
Auto merge of #119767 - GuillaumeGomez:rollup-fbp26yb, r=GuillaumeGomez
Rollup of 9 pull requests

Successful merges:

 - #117556 (Disallow reference to `static mut` and adding `static_mut_ref` lint)
 - #118748 (std: getrandom simplification for freebsd.)
 - #119282 (Rework and improve the unstable documentation of check-cfg)
 - #119527 (don't reexport atomic::ordering via rustc_data_structures, use std import)
 - #119668 (Simplify implementation of MIR promotion)
 - #119699 (Merge dead bb pruning and unreachable bb deduplication.)
 - #119723 (Remove `-Zdont-buffer-diagnostics`.)
 - #119756 (rustdoc-search: reuse individual types in function signatures)
 - #119758 (GNU/Hurd: unconditionally use inline stack probes)

r? `@ghost`
`@rustbot` modify labels: rollup
Diffstat (limited to 'tests')
-rw-r--r--tests/mir-opt/building/async_await.b-{closure#0}.coroutine_resume.0.mir6
-rw-r--r--tests/mir-opt/jump_threading.identity.JumpThreading.panic-abort.diff10
-rw-r--r--tests/mir-opt/jump_threading.identity.JumpThreading.panic-unwind.diff10
-rw-r--r--tests/mir-opt/jump_threading.rs8
-rw-r--r--tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-abort.diff24
-rw-r--r--tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-unwind.diff18
-rw-r--r--tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-abort.diff24
-rw-r--r--tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-unwind.diff18
-rw-r--r--tests/mir-opt/separate_const_switch.identity.SeparateConstSwitch.diff22
-rw-r--r--tests/mir-opt/separate_const_switch.too_complex.SeparateConstSwitch.diff28
-rw-r--r--tests/ui/abi/statics/static-mut-foreign.rs2
-rw-r--r--tests/ui/abi/statics/static-mut-foreign.stderr31
-rw-r--r--tests/ui/borrowck/borrowck-access-permissions.rs36
-rw-r--r--tests/ui/borrowck/borrowck-access-permissions.stderr33
-rw-r--r--tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.rs9
-rw-r--r--tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr17
-rw-r--r--tests/ui/borrowck/issue-20801.rs1
-rw-r--r--tests/ui/borrowck/issue-20801.stderr25
-rw-r--r--tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.rs41
-rw-r--r--tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.stderr75
-rw-r--r--tests/ui/consts/const_let_assign2.rs1
-rw-r--r--tests/ui/consts/const_let_assign2.stderr17
-rw-r--r--tests/ui/consts/issue-17718-const-bad-values.rs3
-rw-r--r--tests/ui/consts/issue-17718-const-bad-values.stderr17
-rw-r--r--tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.32bit.stderr77
-rw-r--r--tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.64bit.stderr77
-rw-r--r--tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.rs22
-rw-r--r--tests/ui/consts/static_mut_containing_mut_ref.rs1
-rw-r--r--tests/ui/consts/static_mut_containing_mut_ref.stderr17
-rw-r--r--tests/ui/consts/static_mut_containing_mut_ref2.mut_refs.stderr23
-rw-r--r--tests/ui/consts/static_mut_containing_mut_ref2.rs10
-rw-r--r--tests/ui/consts/static_mut_containing_mut_ref2.stock.stderr23
-rw-r--r--tests/ui/drop/issue-23338-ensure-param-drop-order.rs90
-rw-r--r--tests/ui/drop/issue-23338-ensure-param-drop-order.stderr17
-rw-r--r--tests/ui/error-codes/E0017.rs12
-rw-r--r--tests/ui/error-codes/E0017.stderr29
-rw-r--r--tests/ui/impl-header-lifetime-elision/bare_type.rs (renamed from tests/ui/issues/issue-20616.rs)9
-rw-r--r--tests/ui/issues/issue-23611-enum-swap-in-drop.rs44
-rw-r--r--tests/ui/issues/issue-23611-enum-swap-in-drop.stderr17
-rw-r--r--tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.rs5
-rw-r--r--tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr17
-rw-r--r--tests/ui/static/reference-of-mut-static-safe.e2021.stderr26
-rw-r--r--tests/ui/static/reference-of-mut-static-safe.e2024.stderr15
-rw-r--r--tests/ui/static/reference-of-mut-static-safe.rs13
-rw-r--r--tests/ui/static/reference-of-mut-static-unsafe-fn.rs23
-rw-r--r--tests/ui/static/reference-of-mut-static-unsafe-fn.stderr63
-rw-r--r--tests/ui/static/reference-of-mut-static.e2021.stderr91
-rw-r--r--tests/ui/static/reference-of-mut-static.e2024.stderr75
-rw-r--r--tests/ui/static/reference-of-mut-static.rs50
-rw-r--r--tests/ui/static/safe-extern-statics-mut.rs2
-rw-r--r--tests/ui/static/safe-extern-statics-mut.stderr35
-rw-r--r--tests/ui/statics/issue-15261.rs3
-rw-r--r--tests/ui/statics/issue-15261.stderr17
-rw-r--r--tests/ui/statics/static-mut-xc.rs3
-rw-r--r--tests/ui/statics/static-mut-xc.stderr31
-rw-r--r--tests/ui/statics/static-recursive.rs27
-rw-r--r--tests/ui/statics/static-recursive.stderr17
-rw-r--r--tests/ui/thread-local/thread-local-static.rs3
-rw-r--r--tests/ui/thread-local/thread-local-static.stderr17
-rw-r--r--tests/ui/thread-local/thread-local-static.thir.stderr59
60 files changed, 1210 insertions, 326 deletions
diff --git a/tests/mir-opt/building/async_await.b-{closure#0}.coroutine_resume.0.mir b/tests/mir-opt/building/async_await.b-{closure#0}.coroutine_resume.0.mir
index 3a9c80caa1e..3c0d4008c90 100644
--- a/tests/mir-opt/building/async_await.b-{closure#0}.coroutine_resume.0.mir
+++ b/tests/mir-opt/building/async_await.b-{closure#0}.coroutine_resume.0.mir
@@ -108,7 +108,7 @@ fn b::{closure#0}(_1: Pin<&mut {async fn body@$DIR/async_await.rs:15:18: 18:2}>,
 
     bb0: {
         _39 = discriminant((*(_1.0: &mut {async fn body@$DIR/async_await.rs:15:18: 18:2})));
-        switchInt(move _39) -> [0: bb1, 1: bb29, 3: bb27, 4: bb28, otherwise: bb30];
+        switchInt(move _39) -> [0: bb1, 1: bb29, 3: bb27, 4: bb28, otherwise: bb9];
     }
 
     bb1: {
@@ -345,8 +345,4 @@ fn b::{closure#0}(_1: Pin<&mut {async fn body@$DIR/async_await.rs:15:18: 18:2}>,
     bb29: {
         assert(const false, "`async fn` resumed after completion") -> [success: bb29, unwind unreachable];
     }
-
-    bb30: {
-        unreachable;
-    }
 }
diff --git a/tests/mir-opt/jump_threading.identity.JumpThreading.panic-abort.diff b/tests/mir-opt/jump_threading.identity.JumpThreading.panic-abort.diff
index f50603a66a5..f04ca72dd6d 100644
--- a/tests/mir-opt/jump_threading.identity.JumpThreading.panic-abort.diff
+++ b/tests/mir-opt/jump_threading.identity.JumpThreading.panic-abort.diff
@@ -56,7 +56,7 @@
           StorageLive(_11);
           StorageLive(_12);
           _10 = discriminant(_4);
-          switchInt(move _10) -> [0: bb8, 1: bb6, otherwise: bb7];
+          switchInt(move _10) -> [0: bb7, 1: bb6, otherwise: bb2];
       }
   
       bb1: {
@@ -114,20 +114,16 @@
           _3 = ControlFlow::<Result<Infallible, i32>, i32>::Break(move _13);
           StorageDead(_13);
 -         goto -> bb5;
-+         goto -> bb9;
++         goto -> bb8;
       }
   
       bb7: {
-          unreachable;
-      }
-  
-      bb8: {
           _11 = move ((_4 as Ok).0: i32);
           _3 = ControlFlow::<Result<Infallible, i32>, i32>::Continue(move _11);
           goto -> bb5;
 +     }
 + 
-+     bb9: {
++     bb8: {
 +         StorageDead(_12);
 +         StorageDead(_11);
 +         StorageDead(_10);
diff --git a/tests/mir-opt/jump_threading.identity.JumpThreading.panic-unwind.diff b/tests/mir-opt/jump_threading.identity.JumpThreading.panic-unwind.diff
index f50603a66a5..f04ca72dd6d 100644
--- a/tests/mir-opt/jump_threading.identity.JumpThreading.panic-unwind.diff
+++ b/tests/mir-opt/jump_threading.identity.JumpThreading.panic-unwind.diff
@@ -56,7 +56,7 @@
           StorageLive(_11);
           StorageLive(_12);
           _10 = discriminant(_4);
-          switchInt(move _10) -> [0: bb8, 1: bb6, otherwise: bb7];
+          switchInt(move _10) -> [0: bb7, 1: bb6, otherwise: bb2];
       }
   
       bb1: {
@@ -114,20 +114,16 @@
           _3 = ControlFlow::<Result<Infallible, i32>, i32>::Break(move _13);
           StorageDead(_13);
 -         goto -> bb5;
-+         goto -> bb9;
++         goto -> bb8;
       }
   
       bb7: {
-          unreachable;
-      }
-  
-      bb8: {
           _11 = move ((_4 as Ok).0: i32);
           _3 = ControlFlow::<Result<Infallible, i32>, i32>::Continue(move _11);
           goto -> bb5;
 +     }
 + 
-+     bb9: {
++     bb8: {
 +         StorageDead(_12);
 +         StorageDead(_11);
 +         StorageDead(_10);
diff --git a/tests/mir-opt/jump_threading.rs b/tests/mir-opt/jump_threading.rs
index 66e5c5d3c11..0cbdaa085bc 100644
--- a/tests/mir-opt/jump_threading.rs
+++ b/tests/mir-opt/jump_threading.rs
@@ -50,7 +50,7 @@ fn identity(x: Result<i32, i32>) -> Result<i32, i32> {
     // CHECK-LABEL: fn identity(
     // CHECK: bb0: {
     // CHECK:     [[x:_.*]] = _1;
-    // CHECK:     switchInt(move {{_.*}}) -> [0: bb8, 1: bb6, otherwise: bb7];
+    // CHECK:     switchInt(move {{_.*}}) -> [0: bb7, 1: bb6, otherwise: bb2];
     // CHECK: bb1: {
     // CHECK:     {{_.*}} = (([[controlflow:_.*]] as Continue).0: i32);
     // CHECK:     _0 = Result::<i32, i32>::Ok(
@@ -68,14 +68,12 @@ fn identity(x: Result<i32, i32>) -> Result<i32, i32> {
     // CHECK: bb6: {
     // CHECK:     {{_.*}} = move (([[x]] as Err).0: i32);
     // CHECK:     [[controlflow]] = ControlFlow::<Result<Infallible, i32>, i32>::Break(
-    // CHECK:     goto -> bb9;
+    // CHECK:     goto -> bb8;
     // CHECK: bb7: {
-    // CHECK:     unreachable;
-    // CHECK: bb8: {
     // CHECK:     {{_.*}} = move (([[x]] as Ok).0: i32);
     // CHECK:     [[controlflow]] = ControlFlow::<Result<Infallible, i32>, i32>::Continue(
     // CHECK:     goto -> bb5;
-    // CHECK: bb9: {
+    // CHECK: bb8: {
     // CHECK:     goto -> bb3;
     Ok(x?)
 }
diff --git a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-abort.diff b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-abort.diff
index 5cb528c0d5f..47e0d402347 100644
--- a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-abort.diff
+++ b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-abort.diff
@@ -56,9 +56,9 @@
 +         _2 = const Option::<Layout>::None;
           StorageLive(_10);
 -         _10 = discriminant(_2);
--         switchInt(move _10) -> [0: bb1, 1: bb3, otherwise: bb2];
+-         switchInt(move _10) -> [0: bb1, 1: bb2, otherwise: bb6];
 +         _10 = const 0_isize;
-+         switchInt(const 0_isize) -> [0: bb1, 1: bb3, otherwise: bb2];
++         switchInt(const 0_isize) -> [0: bb1, 1: bb2, otherwise: bb6];
       }
   
       bb1: {
@@ -66,10 +66,6 @@
       }
   
       bb2: {
-          unreachable;
-      }
-  
-      bb3: {
 -         _1 = move ((_2 as Some).0: std::alloc::Layout);
 +         _1 = const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(4 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x00000000): std::ptr::alignment::AlignmentEnum32) }};
           StorageDead(_10);
@@ -79,18 +75,18 @@
           StorageLive(_5);
           StorageLive(_6);
           _9 = const _;
--         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb4, unwind unreachable];
-+         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(4 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x00000000): std::ptr::alignment::AlignmentEnum32) }}, const false) -> [return: bb4, unwind unreachable];
+-         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb3, unwind unreachable];
++         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(4 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x00000000): std::ptr::alignment::AlignmentEnum32) }}, const false) -> [return: bb3, unwind unreachable];
       }
   
-      bb4: {
+      bb3: {
           StorageLive(_12);
           StorageLive(_15);
           _12 = discriminant(_6);
-          switchInt(move _12) -> [0: bb6, 1: bb5, otherwise: bb2];
+          switchInt(move _12) -> [0: bb5, 1: bb4, otherwise: bb6];
       }
   
-      bb5: {
+      bb4: {
           _15 = const "called `Result::unwrap()` on an `Err` value";
           StorageLive(_16);
           StorageLive(_17);
@@ -100,7 +96,7 @@
           _14 = result::unwrap_failed(move _15, move _16) -> unwind unreachable;
       }
   
-      bb6: {
+      bb5: {
           _5 = move ((_6 as Ok).0: std::ptr::NonNull<[u8]>);
           StorageDead(_15);
           StorageDead(_12);
@@ -115,6 +111,10 @@
           StorageDead(_3);
           return;
       }
+  
+      bb6: {
+          unreachable;
+      }
   }
 + 
 + ALLOC0 (size: 8, align: 4) {
diff --git a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-unwind.diff b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-unwind.diff
index 1e1585f20ae..dee57ce6c27 100644
--- a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-unwind.diff
+++ b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.32bit.panic-unwind.diff
@@ -41,9 +41,9 @@
 +         _2 = const Option::<Layout>::None;
           StorageLive(_10);
 -         _10 = discriminant(_2);
--         switchInt(move _10) -> [0: bb2, 1: bb4, otherwise: bb3];
+-         switchInt(move _10) -> [0: bb2, 1: bb3, otherwise: bb5];
 +         _10 = const 0_isize;
-+         switchInt(const 0_isize) -> [0: bb2, 1: bb4, otherwise: bb3];
++         switchInt(const 0_isize) -> [0: bb2, 1: bb3, otherwise: bb5];
       }
   
       bb1: {
@@ -64,10 +64,6 @@
       }
   
       bb3: {
-          unreachable;
-      }
-  
-      bb4: {
 -         _1 = move ((_2 as Some).0: std::alloc::Layout);
 +         _1 = const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(4 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x00000000): std::ptr::alignment::AlignmentEnum32) }};
           StorageDead(_10);
@@ -77,13 +73,17 @@
           StorageLive(_5);
           StorageLive(_6);
           _9 = const _;
--         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb5, unwind continue];
-+         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(4 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x00000000): std::ptr::alignment::AlignmentEnum32) }}, const false) -> [return: bb5, unwind continue];
+-         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb4, unwind continue];
++         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(4 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x00000000): std::ptr::alignment::AlignmentEnum32) }}, const false) -> [return: bb4, unwind continue];
       }
   
-      bb5: {
+      bb4: {
           _5 = Result::<NonNull<[u8]>, std::alloc::AllocError>::unwrap(move _6) -> [return: bb1, unwind continue];
       }
+  
+      bb5: {
+          unreachable;
+      }
   }
 + 
 + ALLOC0 (size: 8, align: 4) {
diff --git a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-abort.diff b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-abort.diff
index e655af559a1..a255b15920c 100644
--- a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-abort.diff
+++ b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-abort.diff
@@ -56,9 +56,9 @@
 +         _2 = const Option::<Layout>::None;
           StorageLive(_10);
 -         _10 = discriminant(_2);
--         switchInt(move _10) -> [0: bb1, 1: bb3, otherwise: bb2];
+-         switchInt(move _10) -> [0: bb1, 1: bb2, otherwise: bb6];
 +         _10 = const 0_isize;
-+         switchInt(const 0_isize) -> [0: bb1, 1: bb3, otherwise: bb2];
++         switchInt(const 0_isize) -> [0: bb1, 1: bb2, otherwise: bb6];
       }
   
       bb1: {
@@ -66,10 +66,6 @@
       }
   
       bb2: {
-          unreachable;
-      }
-  
-      bb3: {
 -         _1 = move ((_2 as Some).0: std::alloc::Layout);
 +         _1 = const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(8 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x0000000000000000): std::ptr::alignment::AlignmentEnum64) }};
           StorageDead(_10);
@@ -79,18 +75,18 @@
           StorageLive(_5);
           StorageLive(_6);
           _9 = const _;
--         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb4, unwind unreachable];
-+         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(8 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x0000000000000000): std::ptr::alignment::AlignmentEnum64) }}, const false) -> [return: bb4, unwind unreachable];
+-         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb3, unwind unreachable];
++         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(8 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x0000000000000000): std::ptr::alignment::AlignmentEnum64) }}, const false) -> [return: bb3, unwind unreachable];
       }
   
-      bb4: {
+      bb3: {
           StorageLive(_12);
           StorageLive(_15);
           _12 = discriminant(_6);
-          switchInt(move _12) -> [0: bb6, 1: bb5, otherwise: bb2];
+          switchInt(move _12) -> [0: bb5, 1: bb4, otherwise: bb6];
       }
   
-      bb5: {
+      bb4: {
           _15 = const "called `Result::unwrap()` on an `Err` value";
           StorageLive(_16);
           StorageLive(_17);
@@ -100,7 +96,7 @@
           _14 = result::unwrap_failed(move _15, move _16) -> unwind unreachable;
       }
   
-      bb6: {
+      bb5: {
           _5 = move ((_6 as Ok).0: std::ptr::NonNull<[u8]>);
           StorageDead(_15);
           StorageDead(_12);
@@ -115,6 +111,10 @@
           StorageDead(_3);
           return;
       }
+  
+      bb6: {
+          unreachable;
+      }
   }
 + 
 + ALLOC0 (size: 16, align: 8) {
diff --git a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-unwind.diff b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-unwind.diff
index a6658713a02..192ffea2591 100644
--- a/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-unwind.diff
+++ b/tests/mir-opt/pre-codegen/issue_117368_print_invalid_constant.main.GVN.64bit.panic-unwind.diff
@@ -41,9 +41,9 @@
 +         _2 = const Option::<Layout>::None;
           StorageLive(_10);
 -         _10 = discriminant(_2);
--         switchInt(move _10) -> [0: bb2, 1: bb4, otherwise: bb3];
+-         switchInt(move _10) -> [0: bb2, 1: bb3, otherwise: bb5];
 +         _10 = const 0_isize;
-+         switchInt(const 0_isize) -> [0: bb2, 1: bb4, otherwise: bb3];
++         switchInt(const 0_isize) -> [0: bb2, 1: bb3, otherwise: bb5];
       }
   
       bb1: {
@@ -64,10 +64,6 @@
       }
   
       bb3: {
-          unreachable;
-      }
-  
-      bb4: {
 -         _1 = move ((_2 as Some).0: std::alloc::Layout);
 +         _1 = const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(8 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x0000000000000000): std::ptr::alignment::AlignmentEnum64) }};
           StorageDead(_10);
@@ -77,13 +73,17 @@
           StorageLive(_5);
           StorageLive(_6);
           _9 = const _;
--         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb5, unwind continue];
-+         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(8 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x0000000000000000): std::ptr::alignment::AlignmentEnum64) }}, const false) -> [return: bb5, unwind continue];
+-         _6 = std::alloc::Global::alloc_impl(_9, _1, const false) -> [return: bb4, unwind continue];
++         _6 = std::alloc::Global::alloc_impl(const {ALLOC1<imm>: &std::alloc::Global}, const Layout {{ size: Indirect { alloc_id: ALLOC0, offset: Size(8 bytes) }: usize, align: std::ptr::Alignment(Scalar(0x0000000000000000): std::ptr::alignment::AlignmentEnum64) }}, const false) -> [return: bb4, unwind continue];
       }
   
-      bb5: {
+      bb4: {
           _5 = Result::<NonNull<[u8]>, std::alloc::AllocError>::unwrap(move _6) -> [return: bb1, unwind continue];
       }
+  
+      bb5: {
+          unreachable;
+      }
   }
 + 
 + ALLOC0 (size: 16, align: 8) {
diff --git a/tests/mir-opt/separate_const_switch.identity.SeparateConstSwitch.diff b/tests/mir-opt/separate_const_switch.identity.SeparateConstSwitch.diff
index d287b20c4ea..a12db0a730c 100644
--- a/tests/mir-opt/separate_const_switch.identity.SeparateConstSwitch.diff
+++ b/tests/mir-opt/separate_const_switch.identity.SeparateConstSwitch.diff
@@ -52,7 +52,7 @@
           StorageLive(_10);
           StorageLive(_11);
           _9 = discriminant(_1);
-          switchInt(move _9) -> [0: bb6, 1: bb5, otherwise: bb2];
+          switchInt(move _9) -> [0: bb5, 1: bb4, otherwise: bb6];
       }
   
       bb1: {
@@ -63,10 +63,6 @@
       }
   
       bb2: {
-          unreachable;
-      }
-  
-      bb3: {
           _6 = ((_3 as Break).0: std::result::Result<std::convert::Infallible, i32>);
           _13 = ((_6 as Err).0: i32);
           _0 = Result::<i32, i32>::Err(move _13);
@@ -74,27 +70,31 @@
           return;
       }
   
-      bb4: {
+      bb3: {
           StorageDead(_11);
           StorageDead(_10);
           StorageDead(_9);
           _5 = discriminant(_3);
-          switchInt(move _5) -> [0: bb1, 1: bb3, otherwise: bb2];
+          switchInt(move _5) -> [0: bb1, 1: bb2, otherwise: bb6];
       }
   
-      bb5: {
+      bb4: {
           _11 = ((_1 as Err).0: i32);
           StorageLive(_12);
           _12 = Result::<Infallible, i32>::Err(move _11);
           _3 = ControlFlow::<Result<Infallible, i32>, i32>::Break(move _12);
           StorageDead(_12);
-          goto -> bb4;
+          goto -> bb3;
       }
   
-      bb6: {
+      bb5: {
           _10 = ((_1 as Ok).0: i32);
           _3 = ControlFlow::<Result<Infallible, i32>, i32>::Continue(move _10);
-          goto -> bb4;
+          goto -> bb3;
+      }
+  
+      bb6: {
+          unreachable;
       }
   }
   
diff --git a/tests/mir-opt/separate_const_switch.too_complex.SeparateConstSwitch.diff b/tests/mir-opt/separate_const_switch.too_complex.SeparateConstSwitch.diff
index e2bf33f7fbc..80f40b86919 100644
--- a/tests/mir-opt/separate_const_switch.too_complex.SeparateConstSwitch.diff
+++ b/tests/mir-opt/separate_const_switch.too_complex.SeparateConstSwitch.diff
@@ -30,47 +30,47 @@
       bb0: {
           StorageLive(_2);
           _3 = discriminant(_1);
-          switchInt(move _3) -> [0: bb3, 1: bb1, otherwise: bb2];
+          switchInt(move _3) -> [0: bb2, 1: bb1, otherwise: bb7];
       }
   
       bb1: {
           _6 = ((_1 as Err).0: usize);
           _2 = ControlFlow::<usize, i32>::Break(_6);
-          goto -> bb4;
+          goto -> bb3;
       }
   
       bb2: {
-          unreachable;
-      }
-  
-      bb3: {
           _4 = ((_1 as Ok).0: i32);
           _2 = ControlFlow::<usize, i32>::Continue(_4);
-          goto -> bb4;
+          goto -> bb3;
       }
   
-      bb4: {
+      bb3: {
           _8 = discriminant(_2);
-          switchInt(move _8) -> [0: bb6, 1: bb5, otherwise: bb2];
+          switchInt(move _8) -> [0: bb5, 1: bb4, otherwise: bb7];
       }
   
-      bb5: {
+      bb4: {
           StorageLive(_11);
           _11 = ((_2 as Break).0: usize);
           _0 = Option::<i32>::None;
           StorageDead(_11);
-          goto -> bb7;
+          goto -> bb6;
       }
   
-      bb6: {
+      bb5: {
           _9 = ((_2 as Continue).0: i32);
           _0 = Option::<i32>::Some(_9);
-          goto -> bb7;
+          goto -> bb6;
       }
   
-      bb7: {
+      bb6: {
           StorageDead(_2);
           return;
       }
+  
+      bb7: {
+          unreachable;
+      }
   }
   
diff --git a/tests/ui/abi/statics/static-mut-foreign.rs b/tests/ui/abi/statics/static-mut-foreign.rs
index ecd8ee94a01..eb732e7c2c3 100644
--- a/tests/ui/abi/statics/static-mut-foreign.rs
+++ b/tests/ui/abi/statics/static-mut-foreign.rs
@@ -33,7 +33,9 @@ unsafe fn run() {
     rust_dbg_static_mut = -3;
     assert_eq!(rust_dbg_static_mut, -3);
     static_bound(&rust_dbg_static_mut);
+    //~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
     static_bound_set(&mut rust_dbg_static_mut);
+    //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
 }
 
 pub fn main() {
diff --git a/tests/ui/abi/statics/static-mut-foreign.stderr b/tests/ui/abi/statics/static-mut-foreign.stderr
new file mode 100644
index 00000000000..144ac056f87
--- /dev/null
+++ b/tests/ui/abi/statics/static-mut-foreign.stderr
@@ -0,0 +1,31 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/static-mut-foreign.rs:35:18
+   |
+LL |     static_bound(&rust_dbg_static_mut);
+   |                  ^^^^^^^^^^^^^^^^^^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     static_bound(addr_of!(rust_dbg_static_mut));
+   |                  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/static-mut-foreign.rs:37:22
+   |
+LL |     static_bound_set(&mut rust_dbg_static_mut);
+   |                      ^^^^^^^^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     static_bound_set(addr_of_mut!(rust_dbg_static_mut));
+   |                      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+warning: 2 warnings emitted
+
diff --git a/tests/ui/borrowck/borrowck-access-permissions.rs b/tests/ui/borrowck/borrowck-access-permissions.rs
index 469ad508b0e..1638644103b 100644
--- a/tests/ui/borrowck/borrowck-access-permissions.rs
+++ b/tests/ui/borrowck/borrowck-access-permissions.rs
@@ -1,21 +1,27 @@
-static static_x : i32 = 1;
-static mut static_x_mut : i32 = 1;
+static static_x: i32 = 1;
+static mut static_x_mut: i32 = 1;
 
 fn main() {
     let x = 1;
     let mut x_mut = 1;
 
-    { // borrow of local
+    {
+        // borrow of local
         let _y1 = &mut x; //~ ERROR [E0596]
         let _y2 = &mut x_mut; // No error
     }
 
-    { // borrow of static
+    {
+        // borrow of static
         let _y1 = &mut static_x; //~ ERROR [E0596]
-        unsafe { let _y2 = &mut static_x_mut; } // No error
+        unsafe {
+            let _y2 = &mut static_x_mut;
+            //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+        }
     }
 
-    { // borrow of deref to box
+    {
+        // borrow of deref to box
         let box_x = Box::new(1);
         let mut box_x_mut = Box::new(1);
 
@@ -23,7 +29,8 @@ fn main() {
         let _y2 = &mut *box_x_mut; // No error
     }
 
-    { // borrow of deref to reference
+    {
+        // borrow of deref to reference
         let ref_x = &x;
         let ref_x_mut = &mut x_mut;
 
@@ -31,9 +38,10 @@ fn main() {
         let _y2 = &mut *ref_x_mut; // No error
     }
 
-    { // borrow of deref to pointer
-        let ptr_x : *const _ = &x;
-        let ptr_mut_x : *mut _ = &mut x_mut;
+    {
+        // borrow of deref to pointer
+        let ptr_x: *const _ = &x;
+        let ptr_mut_x: *mut _ = &mut x_mut;
 
         unsafe {
             let _y1 = &mut *ptr_x; //~ ERROR [E0596]
@@ -41,8 +49,12 @@ fn main() {
         }
     }
 
-    { // borrowing mutably through an immutable reference
-        struct Foo<'a> { f: &'a mut i32, g: &'a i32 };
+    {
+        // borrowing mutably through an immutable reference
+        struct Foo<'a> {
+            f: &'a mut i32,
+            g: &'a i32,
+        };
         let mut foo = Foo { f: &mut x_mut, g: &x };
         let foo_ref = &foo;
         let _y = &mut *foo_ref.f; //~ ERROR [E0596]
diff --git a/tests/ui/borrowck/borrowck-access-permissions.stderr b/tests/ui/borrowck/borrowck-access-permissions.stderr
index c161e2d95b4..93d92295dd9 100644
--- a/tests/ui/borrowck/borrowck-access-permissions.stderr
+++ b/tests/ui/borrowck/borrowck-access-permissions.stderr
@@ -1,5 +1,20 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/borrowck-access-permissions.rs:18:23
+   |
+LL |             let _y2 = &mut static_x_mut;
+   |                       ^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |             let _y2 = addr_of_mut!(static_x_mut);
+   |                       ~~~~~~~~~~~~~~~~~~~~~~~~~~
+
 error[E0596]: cannot borrow `x` as mutable, as it is not declared as mutable
-  --> $DIR/borrowck-access-permissions.rs:9:19
+  --> $DIR/borrowck-access-permissions.rs:10:19
    |
 LL |         let _y1 = &mut x;
    |                   ^^^^^^ cannot borrow as mutable
@@ -10,13 +25,13 @@ LL |     let mut x = 1;
    |         +++
 
 error[E0596]: cannot borrow immutable static item `static_x` as mutable
-  --> $DIR/borrowck-access-permissions.rs:14:19
+  --> $DIR/borrowck-access-permissions.rs:16:19
    |
 LL |         let _y1 = &mut static_x;
    |                   ^^^^^^^^^^^^^ cannot borrow as mutable
 
 error[E0596]: cannot borrow `*box_x` as mutable, as `box_x` is not declared as mutable
-  --> $DIR/borrowck-access-permissions.rs:22:19
+  --> $DIR/borrowck-access-permissions.rs:28:19
    |
 LL |         let _y1 = &mut *box_x;
    |                   ^^^^^^^^^^^ cannot borrow as mutable
@@ -27,7 +42,7 @@ LL |         let mut box_x = Box::new(1);
    |             +++
 
 error[E0596]: cannot borrow `*ref_x` as mutable, as it is behind a `&` reference
-  --> $DIR/borrowck-access-permissions.rs:30:19
+  --> $DIR/borrowck-access-permissions.rs:37:19
    |
 LL |         let _y1 = &mut *ref_x;
    |                   ^^^^^^^^^^^ `ref_x` is a `&` reference, so the data it refers to cannot be borrowed as mutable
@@ -38,18 +53,18 @@ LL |         let ref_x = &mut x;
    |                      +++
 
 error[E0596]: cannot borrow `*ptr_x` as mutable, as it is behind a `*const` pointer
-  --> $DIR/borrowck-access-permissions.rs:39:23
+  --> $DIR/borrowck-access-permissions.rs:47:23
    |
 LL |             let _y1 = &mut *ptr_x;
    |                       ^^^^^^^^^^^ `ptr_x` is a `*const` pointer, so the data it refers to cannot be borrowed as mutable
    |
 help: consider changing this to be a mutable pointer
    |
-LL |         let ptr_x : *const _ = &mut x;
-   |                                 +++
+LL |         let ptr_x: *const _ = &mut x;
+   |                                +++
 
 error[E0596]: cannot borrow `*foo_ref.f` as mutable, as it is behind a `&` reference
-  --> $DIR/borrowck-access-permissions.rs:48:18
+  --> $DIR/borrowck-access-permissions.rs:60:18
    |
 LL |         let _y = &mut *foo_ref.f;
    |                  ^^^^^^^^^^^^^^^ `foo_ref` is a `&` reference, so the data it refers to cannot be borrowed as mutable
@@ -59,6 +74,6 @@ help: consider changing this to be a mutable reference
 LL |         let foo_ref = &mut foo;
    |                        +++
 
-error: aborting due to 6 previous errors
+error: aborting due to 6 previous errors; 1 warning emitted
 
 For more information about this error, try `rustc --explain E0596`.
diff --git a/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.rs b/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.rs
index adc7dfd541f..1bf079e24ca 100644
--- a/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.rs
+++ b/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.rs
@@ -2,17 +2,22 @@
 
 // Test file taken from issue 45129 (https://github.com/rust-lang/rust/issues/45129)
 
-struct Foo { x: [usize; 2] }
+struct Foo {
+    x: [usize; 2],
+}
 
 static mut SFOO: Foo = Foo { x: [23, 32] };
 
 impl Foo {
-    fn x(&mut self) -> &mut usize { &mut self.x[0] }
+    fn x(&mut self) -> &mut usize {
+        &mut self.x[0]
+    }
 }
 
 fn main() {
     unsafe {
         let sfoo: *mut Foo = &mut SFOO;
+        //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
         let x = (*sfoo).x();
         (*sfoo).x[1] += 1;
         *x += 1;
diff --git a/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr b/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr
new file mode 100644
index 00000000000..7a3824f79a4
--- /dev/null
+++ b/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr
@@ -0,0 +1,17 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/borrowck-unsafe-static-mutable-borrows.rs:19:30
+   |
+LL |         let sfoo: *mut Foo = &mut SFOO;
+   |                              ^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |         let sfoo: *mut Foo = addr_of_mut!(SFOO);
+   |                              ~~~~~~~~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/borrowck/issue-20801.rs b/tests/ui/borrowck/issue-20801.rs
index c3f136f2876..ec83af5d5df 100644
--- a/tests/ui/borrowck/issue-20801.rs
+++ b/tests/ui/borrowck/issue-20801.rs
@@ -12,6 +12,7 @@ fn imm_ref() -> &'static T {
 
 fn mut_ref() -> &'static mut T {
     unsafe { &mut GLOBAL_MUT_T }
+    //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
 }
 
 fn mut_ptr() -> *mut T {
diff --git a/tests/ui/borrowck/issue-20801.stderr b/tests/ui/borrowck/issue-20801.stderr
index 215bf010063..b2bee2d8803 100644
--- a/tests/ui/borrowck/issue-20801.stderr
+++ b/tests/ui/borrowck/issue-20801.stderr
@@ -1,5 +1,20 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/issue-20801.rs:14:14
+   |
+LL |     unsafe { &mut GLOBAL_MUT_T }
+   |              ^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     unsafe { addr_of_mut!(GLOBAL_MUT_T) }
+   |              ~~~~~~~~~~~~~~~~~~~~~~~~~~
+
 error[E0507]: cannot move out of a mutable reference
-  --> $DIR/issue-20801.rs:26:22
+  --> $DIR/issue-20801.rs:27:22
    |
 LL |     let a = unsafe { *mut_ref() };
    |                      ^^^^^^^^^^ move occurs because value has type `T`, which does not implement the `Copy` trait
@@ -11,7 +26,7 @@ LL +     let a = unsafe { mut_ref() };
    |
 
 error[E0507]: cannot move out of a shared reference
-  --> $DIR/issue-20801.rs:29:22
+  --> $DIR/issue-20801.rs:30:22
    |
 LL |     let b = unsafe { *imm_ref() };
    |                      ^^^^^^^^^^ move occurs because value has type `T`, which does not implement the `Copy` trait
@@ -23,7 +38,7 @@ LL +     let b = unsafe { imm_ref() };
    |
 
 error[E0507]: cannot move out of a raw pointer
-  --> $DIR/issue-20801.rs:32:22
+  --> $DIR/issue-20801.rs:33:22
    |
 LL |     let c = unsafe { *mut_ptr() };
    |                      ^^^^^^^^^^ move occurs because value has type `T`, which does not implement the `Copy` trait
@@ -35,7 +50,7 @@ LL +     let c = unsafe { mut_ptr() };
    |
 
 error[E0507]: cannot move out of a raw pointer
-  --> $DIR/issue-20801.rs:35:22
+  --> $DIR/issue-20801.rs:36:22
    |
 LL |     let d = unsafe { *const_ptr() };
    |                      ^^^^^^^^^^^^ move occurs because value has type `T`, which does not implement the `Copy` trait
@@ -46,6 +61,6 @@ LL -     let d = unsafe { *const_ptr() };
 LL +     let d = unsafe { const_ptr() };
    |
 
-error: aborting due to 4 previous errors
+error: aborting due to 4 previous errors; 1 warning emitted
 
 For more information about this error, try `rustc --explain E0507`.
diff --git a/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.rs b/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.rs
index b3cce1b3a06..9b172b41319 100644
--- a/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.rs
+++ b/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.rs
@@ -8,7 +8,10 @@ mod borrowck_closures_unique {
         static mut Y: isize = 3;
         let mut c1 = |y: &'static mut isize| x = y;
         //~^ ERROR is not declared as mutable
-        unsafe { c1(&mut Y); }
+        unsafe {
+            c1(&mut Y);
+            //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+        }
     }
 }
 
@@ -17,36 +20,50 @@ mod borrowck_closures_unique_grandparent {
         static mut Z: isize = 3;
         let mut c1 = |z: &'static mut isize| {
             let mut c2 = |y: &'static mut isize| x = y;
-        //~^ ERROR is not declared as mutable
+            //~^ ERROR is not declared as mutable
             c2(z);
         };
-        unsafe { c1(&mut Z); }
+        unsafe {
+            c1(&mut Z);
+            //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+        }
     }
 }
 
 // adapted from mutability_errors.rs
 mod mutability_errors {
     pub fn capture_assign_whole(x: (i32,)) {
-        || { x = (1,); };
-        //~^ ERROR is not declared as mutable
+        || {
+            x = (1,);
+            //~^ ERROR is not declared as mutable
+        };
     }
     pub fn capture_assign_part(x: (i32,)) {
-        || { x.0 = 1; };
-        //~^ ERROR is not declared as mutable
+        || {
+            x.0 = 1;
+            //~^ ERROR is not declared as mutable
+        };
     }
     pub fn capture_reborrow_whole(x: (i32,)) {
-        || { &mut x; };
-        //~^ ERROR is not declared as mutable
+        || {
+            &mut x;
+            //~^ ERROR is not declared as mutable
+        };
     }
     pub fn capture_reborrow_part(x: (i32,)) {
-        || { &mut x.0; };
-        //~^ ERROR is not declared as mutable
+        || {
+            &mut x.0;
+            //~^ ERROR is not declared as mutable
+        };
     }
 }
 
 fn main() {
     static mut X: isize = 2;
-    unsafe { borrowck_closures_unique::e(&mut X); }
+    unsafe {
+        borrowck_closures_unique::e(&mut X);
+        //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+    }
 
     mutability_errors::capture_assign_whole((1000,));
     mutability_errors::capture_assign_part((2000,));
diff --git a/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.stderr b/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.stderr
index 4c299cdc455..e4e4947fce1 100644
--- a/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.stderr
+++ b/tests/ui/borrowck/issue-55492-borrowck-migrate-scans-parents.stderr
@@ -1,3 +1,46 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:12:16
+   |
+LL |             c1(&mut Y);
+   |                ^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |             c1(addr_of_mut!(Y));
+   |                ~~~~~~~~~~~~~~~
+
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:27:16
+   |
+LL |             c1(&mut Z);
+   |                ^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |             c1(addr_of_mut!(Z));
+   |                ~~~~~~~~~~~~~~~
+
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:64:37
+   |
+LL |         borrowck_closures_unique::e(&mut X);
+   |                                     ^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |         borrowck_closures_unique::e(addr_of_mut!(X));
+   |                                     ~~~~~~~~~~~~~~~
+
 error[E0594]: cannot assign to `x`, as it is not declared as mutable
   --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:9:46
    |
@@ -8,7 +51,7 @@ LL |         let mut c1 = |y: &'static mut isize| x = y;
    |                                              ^^^^^ cannot assign
 
 error[E0594]: cannot assign to `x`, as it is not declared as mutable
-  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:19:50
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:22:50
    |
 LL |     pub fn ee(x: &'static mut isize) {
    |               - help: consider changing this to be mutable: `mut x`
@@ -17,38 +60,42 @@ LL |             let mut c2 = |y: &'static mut isize| x = y;
    |                                                  ^^^^^ cannot assign
 
 error[E0594]: cannot assign to `x`, as it is not declared as mutable
-  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:30:14
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:37:13
    |
 LL |     pub fn capture_assign_whole(x: (i32,)) {
    |                                 - help: consider changing this to be mutable: `mut x`
-LL |         || { x = (1,); };
-   |              ^^^^^^^^ cannot assign
+LL |         || {
+LL |             x = (1,);
+   |             ^^^^^^^^ cannot assign
 
 error[E0594]: cannot assign to `x.0`, as `x` is not declared as mutable
-  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:34:14
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:43:13
    |
 LL |     pub fn capture_assign_part(x: (i32,)) {
    |                                - help: consider changing this to be mutable: `mut x`
-LL |         || { x.0 = 1; };
-   |              ^^^^^^^ cannot assign
+LL |         || {
+LL |             x.0 = 1;
+   |             ^^^^^^^ cannot assign
 
 error[E0596]: cannot borrow `x` as mutable, as it is not declared as mutable
-  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:38:14
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:49:13
    |
 LL |     pub fn capture_reborrow_whole(x: (i32,)) {
    |                                   - help: consider changing this to be mutable: `mut x`
-LL |         || { &mut x; };
-   |              ^^^^^^ cannot borrow as mutable
+LL |         || {
+LL |             &mut x;
+   |             ^^^^^^ cannot borrow as mutable
 
 error[E0596]: cannot borrow `x.0` as mutable, as `x` is not declared as mutable
-  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:42:14
+  --> $DIR/issue-55492-borrowck-migrate-scans-parents.rs:55:13
    |
 LL |     pub fn capture_reborrow_part(x: (i32,)) {
    |                                  - help: consider changing this to be mutable: `mut x`
-LL |         || { &mut x.0; };
-   |              ^^^^^^^^ cannot borrow as mutable
+LL |         || {
+LL |             &mut x.0;
+   |             ^^^^^^^^ cannot borrow as mutable
 
-error: aborting due to 6 previous errors
+error: aborting due to 6 previous errors; 3 warnings emitted
 
 Some errors have detailed explanations: E0594, E0596.
 For more information about an error, try `rustc --explain E0594`.
diff --git a/tests/ui/consts/const_let_assign2.rs b/tests/ui/consts/const_let_assign2.rs
index 28265c85dd1..1c7afe0e3d6 100644
--- a/tests/ui/consts/const_let_assign2.rs
+++ b/tests/ui/consts/const_let_assign2.rs
@@ -16,6 +16,7 @@ static mut BB: AA = AA::new();
 
 fn main() {
     let ptr = unsafe { &mut BB };
+    //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
     for a in ptr.data.iter() {
         println!("{}", a);
     }
diff --git a/tests/ui/consts/const_let_assign2.stderr b/tests/ui/consts/const_let_assign2.stderr
new file mode 100644
index 00000000000..2764153a8a5
--- /dev/null
+++ b/tests/ui/consts/const_let_assign2.stderr
@@ -0,0 +1,17 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/const_let_assign2.rs:18:24
+   |
+LL |     let ptr = unsafe { &mut BB };
+   |                        ^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     let ptr = unsafe { addr_of_mut!(BB) };
+   |                        ~~~~~~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/consts/issue-17718-const-bad-values.rs b/tests/ui/consts/issue-17718-const-bad-values.rs
index 62bbb3b569c..4fedc48452b 100644
--- a/tests/ui/consts/issue-17718-const-bad-values.rs
+++ b/tests/ui/consts/issue-17718-const-bad-values.rs
@@ -3,7 +3,8 @@ const C1: &'static mut [usize] = &mut [];
 
 static mut S: usize = 3;
 const C2: &'static mut usize = unsafe { &mut S };
-//~^ ERROR: constants cannot refer to statics
+//~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+//~^^ ERROR: constants cannot refer to statics
 //~| ERROR: constants cannot refer to statics
 
 fn main() {}
diff --git a/tests/ui/consts/issue-17718-const-bad-values.stderr b/tests/ui/consts/issue-17718-const-bad-values.stderr
index 405c2195dec..2dc91f52669 100644
--- a/tests/ui/consts/issue-17718-const-bad-values.stderr
+++ b/tests/ui/consts/issue-17718-const-bad-values.stderr
@@ -1,3 +1,18 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/issue-17718-const-bad-values.rs:5:41
+   |
+LL | const C2: &'static mut usize = unsafe { &mut S };
+   |                                         ^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL | const C2: &'static mut usize = unsafe { addr_of_mut!(S) };
+   |                                         ~~~~~~~~~~~~~~~
+
 error[E0764]: mutable references are not allowed in the final value of constants
   --> $DIR/issue-17718-const-bad-values.rs:1:34
    |
@@ -21,7 +36,7 @@ LL | const C2: &'static mut usize = unsafe { &mut S };
    = help: consider extracting the value of the `static` to a `const`, and referring to that
    = note: duplicate diagnostic emitted due to `-Z deduplicate-diagnostics=no`
 
-error: aborting due to 3 previous errors
+error: aborting due to 3 previous errors; 1 warning emitted
 
 Some errors have detailed explanations: E0013, E0764.
 For more information about an error, try `rustc --explain E0013`.
diff --git a/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.32bit.stderr b/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.32bit.stderr
index 7960648ce3a..ed9db675426 100644
--- a/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.32bit.stderr
+++ b/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.32bit.stderr
@@ -1,3 +1,18 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/const_refers_to_static_cross_crate.rs:13:14
+   |
+LL |     unsafe { &static_cross_crate::ZERO }
+   |              ^^^^^^^^^^^^^^^^^^^^^^^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     unsafe { addr_of!(static_cross_crate::ZERO) }
+   |              ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
 error[E0080]: it is undefined behavior to use this value
   --> $DIR/const_refers_to_static_cross_crate.rs:10:1
    |
@@ -10,13 +25,13 @@ LL | const SLICE_MUT: &[u8; 1] = {
            }
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:34:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:42:9
    |
 LL |         SLICE_MUT => true,
    |         ^^^^^^^^^
 
 error[E0080]: it is undefined behavior to use this value
-  --> $DIR/const_refers_to_static_cross_crate.rs:15:1
+  --> $DIR/const_refers_to_static_cross_crate.rs:17:1
    |
 LL | const U8_MUT: &u8 = {
    | ^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a reference pointing to a static variable in a constant
@@ -27,31 +42,31 @@ LL | const U8_MUT: &u8 = {
            }
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:42:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:50:9
    |
 LL |         U8_MUT => true,
    |         ^^^^^^
 
 error[E0080]: evaluation of constant value failed
-  --> $DIR/const_refers_to_static_cross_crate.rs:22:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:25:15
    |
 LL |     unsafe { &(*static_cross_crate::ZERO_REF)[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constant accesses static
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:52:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:60:9
    |
 LL |         U8_MUT2 => true,
    |         ^^^^^^^
 
 error[E0080]: evaluation of constant value failed
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constant accesses static
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constant accesses static
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:59:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:67:9
    |
 LL |         U8_MUT3 => true,
    |         ^^^^^^^
@@ -59,61 +74,61 @@ LL |         U8_MUT3 => true,
 warning: skipping const checks
    |
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:12:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:13:15
    |
 LL |     unsafe { &static_cross_crate::ZERO }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:12:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:13:15
    |
 LL |     unsafe { &static_cross_crate::ZERO }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:17:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:20:15
    |
 LL |     unsafe { &static_cross_crate::ZERO[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:17:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:20:15
    |
 LL |     unsafe { &static_cross_crate::ZERO[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:17:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:20:15
    |
 LL |     unsafe { &static_cross_crate::ZERO[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:22:17
+  --> $DIR/const_refers_to_static_cross_crate.rs:25:17
    |
 LL |     unsafe { &(*static_cross_crate::ZERO_REF)[0] }
    |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: aborting due to 8 previous errors; 1 warning emitted
+error: aborting due to 8 previous errors; 2 warnings emitted
 
 For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.64bit.stderr b/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.64bit.stderr
index 6ae0b2d1bfe..275323bc286 100644
--- a/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.64bit.stderr
+++ b/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.64bit.stderr
@@ -1,3 +1,18 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/const_refers_to_static_cross_crate.rs:13:14
+   |
+LL |     unsafe { &static_cross_crate::ZERO }
+   |              ^^^^^^^^^^^^^^^^^^^^^^^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     unsafe { addr_of!(static_cross_crate::ZERO) }
+   |              ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
 error[E0080]: it is undefined behavior to use this value
   --> $DIR/const_refers_to_static_cross_crate.rs:10:1
    |
@@ -10,13 +25,13 @@ LL | const SLICE_MUT: &[u8; 1] = {
            }
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:34:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:42:9
    |
 LL |         SLICE_MUT => true,
    |         ^^^^^^^^^
 
 error[E0080]: it is undefined behavior to use this value
-  --> $DIR/const_refers_to_static_cross_crate.rs:15:1
+  --> $DIR/const_refers_to_static_cross_crate.rs:17:1
    |
 LL | const U8_MUT: &u8 = {
    | ^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a reference pointing to a static variable in a constant
@@ -27,31 +42,31 @@ LL | const U8_MUT: &u8 = {
            }
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:42:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:50:9
    |
 LL |         U8_MUT => true,
    |         ^^^^^^
 
 error[E0080]: evaluation of constant value failed
-  --> $DIR/const_refers_to_static_cross_crate.rs:22:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:25:15
    |
 LL |     unsafe { &(*static_cross_crate::ZERO_REF)[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constant accesses static
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:52:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:60:9
    |
 LL |         U8_MUT2 => true,
    |         ^^^^^^^
 
 error[E0080]: evaluation of constant value failed
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constant accesses static
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constant accesses static
 
 error: could not evaluate constant pattern
-  --> $DIR/const_refers_to_static_cross_crate.rs:59:9
+  --> $DIR/const_refers_to_static_cross_crate.rs:67:9
    |
 LL |         U8_MUT3 => true,
    |         ^^^^^^^
@@ -59,61 +74,61 @@ LL |         U8_MUT3 => true,
 warning: skipping const checks
    |
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:12:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:13:15
    |
 LL |     unsafe { &static_cross_crate::ZERO }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:12:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:13:15
    |
 LL |     unsafe { &static_cross_crate::ZERO }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:17:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:20:15
    |
 LL |     unsafe { &static_cross_crate::ZERO[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:17:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:20:15
    |
 LL |     unsafe { &static_cross_crate::ZERO[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:17:15
+  --> $DIR/const_refers_to_static_cross_crate.rs:20:15
    |
 LL |     unsafe { &static_cross_crate::ZERO[0] }
    |               ^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:22:17
+  --> $DIR/const_refers_to_static_cross_crate.rs:25:17
    |
 LL |     unsafe { &(*static_cross_crate::ZERO_REF)[0] }
    |                 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 help: skipping check that does not even have a feature gate
-  --> $DIR/const_refers_to_static_cross_crate.rs:27:20
+  --> $DIR/const_refers_to_static_cross_crate.rs:31:15
    |
-LL |     unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-   |                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |         match static_cross_crate::OPT_ZERO {
+   |               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
-error: aborting due to 8 previous errors; 1 warning emitted
+error: aborting due to 8 previous errors; 2 warnings emitted
 
 For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.rs b/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.rs
index bbaa32ddfd1..3eafa58d9f9 100644
--- a/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.rs
+++ b/tests/ui/consts/miri_unleashed/const_refers_to_static_cross_crate.rs
@@ -7,13 +7,16 @@ extern crate static_cross_crate;
 
 // Sneaky: reference to a mutable static.
 // Allowing this would be a disaster for pattern matching, we could violate exhaustiveness checking!
-const SLICE_MUT: &[u8; 1] = { //~ ERROR undefined behavior to use this value
-//~| encountered a reference pointing to a static variable
+const SLICE_MUT: &[u8; 1] = {
+    //~^ ERROR undefined behavior to use this value
+    //~| encountered a reference pointing to a static variable
     unsafe { &static_cross_crate::ZERO }
+    //~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
 };
 
-const U8_MUT: &u8 = { //~ ERROR undefined behavior to use this value
-//~| encountered a reference pointing to a static variable
+const U8_MUT: &u8 = {
+    //~^ ERROR undefined behavior to use this value
+    //~| encountered a reference pointing to a static variable
     unsafe { &static_cross_crate::ZERO[0] }
 };
 
@@ -24,9 +27,14 @@ const U8_MUT2: &u8 = {
     //~| constant accesses static
 };
 const U8_MUT3: &u8 = {
-    unsafe { match static_cross_crate::OPT_ZERO { Some(ref u) => u, None => panic!() } }
-    //~^ ERROR evaluation of constant value failed
-    //~| constant accesses static
+    unsafe {
+        match static_cross_crate::OPT_ZERO {
+            //~^ ERROR evaluation of constant value failed
+            //~| constant accesses static
+            Some(ref u) => u,
+            None => panic!(),
+        }
+    }
 };
 
 pub fn test(x: &[u8; 1]) -> bool {
diff --git a/tests/ui/consts/static_mut_containing_mut_ref.rs b/tests/ui/consts/static_mut_containing_mut_ref.rs
index df09c76c558..874aa59df0b 100644
--- a/tests/ui/consts/static_mut_containing_mut_ref.rs
+++ b/tests/ui/consts/static_mut_containing_mut_ref.rs
@@ -3,5 +3,6 @@
 static mut STDERR_BUFFER_SPACE: [u8; 42] = [0u8; 42];
 
 pub static mut STDERR_BUFFER: *mut [u8] = unsafe { &mut STDERR_BUFFER_SPACE };
+//~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
 
 fn main() {}
diff --git a/tests/ui/consts/static_mut_containing_mut_ref.stderr b/tests/ui/consts/static_mut_containing_mut_ref.stderr
new file mode 100644
index 00000000000..56ceba41cf8
--- /dev/null
+++ b/tests/ui/consts/static_mut_containing_mut_ref.stderr
@@ -0,0 +1,17 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/static_mut_containing_mut_ref.rs:5:52
+   |
+LL | pub static mut STDERR_BUFFER: *mut [u8] = unsafe { &mut STDERR_BUFFER_SPACE };
+   |                                                    ^^^^^^^^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL | pub static mut STDERR_BUFFER: *mut [u8] = unsafe { addr_of_mut!(STDERR_BUFFER_SPACE) };
+   |                                                    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/consts/static_mut_containing_mut_ref2.mut_refs.stderr b/tests/ui/consts/static_mut_containing_mut_ref2.mut_refs.stderr
index 3d0de233569..bc32ecc2c35 100644
--- a/tests/ui/consts/static_mut_containing_mut_ref2.mut_refs.stderr
+++ b/tests/ui/consts/static_mut_containing_mut_ref2.mut_refs.stderr
@@ -1,9 +1,24 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/static_mut_containing_mut_ref2.rs:8:6
+   |
+LL |     *(&mut STDERR_BUFFER_SPACE) = 42;
+   |      ^^^^^^^^^^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     *addr_of_mut!(STDERR_BUFFER_SPACE) = 42;
+   |      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
 error[E0080]: could not evaluate static initializer
-  --> $DIR/static_mut_containing_mut_ref2.rs:7:45
+  --> $DIR/static_mut_containing_mut_ref2.rs:8:5
    |
-LL | pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
-   |                                             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ modifying a static's initial value from another static's initializer
+LL |     *(&mut STDERR_BUFFER_SPACE) = 42;
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ modifying a static's initial value from another static's initializer
 
-error: aborting due to 1 previous error
+error: aborting due to 1 previous error; 1 warning emitted
 
 For more information about this error, try `rustc --explain E0080`.
diff --git a/tests/ui/consts/static_mut_containing_mut_ref2.rs b/tests/ui/consts/static_mut_containing_mut_ref2.rs
index 61368546083..fa79a78eab4 100644
--- a/tests/ui/consts/static_mut_containing_mut_ref2.rs
+++ b/tests/ui/consts/static_mut_containing_mut_ref2.rs
@@ -4,8 +4,12 @@
 
 static mut STDERR_BUFFER_SPACE: u8 = 0;
 
-pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
-//[mut_refs]~^ ERROR could not evaluate static initializer
-//[stock]~^^ ERROR mutable references are not allowed in statics
+pub static mut STDERR_BUFFER: () = unsafe {
+    *(&mut STDERR_BUFFER_SPACE) = 42;
+    //[mut_refs]~^ ERROR could not evaluate static initializer
+    //[stock]~^^ ERROR mutable references are not allowed in statics
+    //[mut_refs]~^^^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+    //[stock]~^^^^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+};
 
 fn main() {}
diff --git a/tests/ui/consts/static_mut_containing_mut_ref2.stock.stderr b/tests/ui/consts/static_mut_containing_mut_ref2.stock.stderr
index 3d5b012d42f..c6e5b07e3b7 100644
--- a/tests/ui/consts/static_mut_containing_mut_ref2.stock.stderr
+++ b/tests/ui/consts/static_mut_containing_mut_ref2.stock.stderr
@@ -1,12 +1,27 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/static_mut_containing_mut_ref2.rs:8:6
+   |
+LL |     *(&mut STDERR_BUFFER_SPACE) = 42;
+   |      ^^^^^^^^^^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     *addr_of_mut!(STDERR_BUFFER_SPACE) = 42;
+   |      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
 error[E0658]: mutable references are not allowed in statics
-  --> $DIR/static_mut_containing_mut_ref2.rs:7:46
+  --> $DIR/static_mut_containing_mut_ref2.rs:8:6
    |
-LL | pub static mut STDERR_BUFFER: () = unsafe { *(&mut STDERR_BUFFER_SPACE) = 42; };
-   |                                              ^^^^^^^^^^^^^^^^^^^^^^^^^^
+LL |     *(&mut STDERR_BUFFER_SPACE) = 42;
+   |      ^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
    = help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
 
-error: aborting due to 1 previous error
+error: aborting due to 1 previous error; 1 warning emitted
 
 For more information about this error, try `rustc --explain E0658`.
diff --git a/tests/ui/drop/issue-23338-ensure-param-drop-order.rs b/tests/ui/drop/issue-23338-ensure-param-drop-order.rs
index a99f260dde3..52603744c45 100644
--- a/tests/ui/drop/issue-23338-ensure-param-drop-order.rs
+++ b/tests/ui/drop/issue-23338-ensure-param-drop-order.rs
@@ -13,38 +13,39 @@ pub fn main() {
     d::println("created empty log");
     test(&log);
 
-    assert_eq!(&log.borrow()[..],
-               [
-                   //                                    created empty log
-                   //    +-- Make D(da_0, 0)
-                   //    | +-- Make D(de_1, 1)
-                   //    | |                             calling foo
-                   //    | |                             entered foo
-                   //    | | +-- Make D(de_2, 2)
-                   //    | | | +-- Make D(da_1, 3)
-                   //    | | | | +-- Make D(de_3, 4)
-                   //    | | | | | +-- Make D(de_4, 5)
-                   3, // | | | +-- Drop D(da_1, 3)
-                   //    | | |   | |
-                   4, // | | |   +-- Drop D(de_3, 4)
-                   //    | | |     |
-                   //    | | |     |                     eval tail of foo
-                   //    | | | +-- Make D(de_5, 6)
-                   //    | | | | +-- Make D(de_6, 7)
-                   5, // | | | | | +-- Drop D(de_4, 5)
-                   //    | | | | |
-                   2, // | | +-- Drop D(de_2, 2)
-                   //    | |   | |
-                   6, // | |   +-- Drop D(de_5, 6)
-                   //    | |     |
-                   1, // | +-- Drop D(de_1, 1)
-                   //    |       |
-                   0, // +-- Drop D(da_0, 0)
-                   //            |
-                   //            |                       result D(de_6, 7)
-                   7 //          +-- Drop D(de_6, 7)
-
-                       ]);
+    assert_eq!(
+        &log.borrow()[..],
+        [
+            //                                    created empty log
+            //    +-- Make D(da_0, 0)
+            //    | +-- Make D(de_1, 1)
+            //    | |                             calling foo
+            //    | |                             entered foo
+            //    | | +-- Make D(de_2, 2)
+            //    | | | +-- Make D(da_1, 3)
+            //    | | | | +-- Make D(de_3, 4)
+            //    | | | | | +-- Make D(de_4, 5)
+            3, // | | | +-- Drop D(da_1, 3)
+            //    | | |   | |
+            4, // | | |   +-- Drop D(de_3, 4)
+            //    | | |     |
+            //    | | |     |                     eval tail of foo
+            //    | | | +-- Make D(de_5, 6)
+            //    | | | | +-- Make D(de_6, 7)
+            5, // | | | | | +-- Drop D(de_4, 5)
+            //    | | | | |
+            2, // | | +-- Drop D(de_2, 2)
+            //    | |   | |
+            6, // | |   +-- Drop D(de_5, 6)
+            //    | |     |
+            1, // | +-- Drop D(de_1, 1)
+            //    |       |
+            0, // +-- Drop D(da_0, 0)
+            //            |
+            //            |                       result D(de_6, 7)
+            7 //          +-- Drop D(de_6, 7)
+        ]
+    );
 }
 
 fn test<'a>(log: d::Log<'a>) {
@@ -57,13 +58,13 @@ fn test<'a>(log: d::Log<'a>) {
 
 fn foo<'a>(da0: D<'a>, de1: D<'a>) -> D<'a> {
     d::println("entered foo");
-    let de2 = de1.incr();      // creates D(de_2, 2)
+    let de2 = de1.incr(); // creates D(de_2, 2)
     let de4 = {
         let _da1 = da0.incr(); // creates D(da_1, 3)
-        de2.incr().incr()      // creates D(de_3, 4) and D(de_4, 5)
+        de2.incr().incr() // creates D(de_3, 4) and D(de_4, 5)
     };
     d::println("eval tail of foo");
-    de4.incr().incr()          // creates D(de_5, 6) and D(de_6, 7)
+    de4.incr().incr() // creates D(de_5, 6) and D(de_6, 7)
 }
 
 // This module provides simultaneous printouts of the dynamic extents
@@ -74,9 +75,9 @@ const PREF_INDENT: u32 = 16;
 
 pub mod d {
     #![allow(unused_parens)]
+    use std::cell::RefCell;
     use std::fmt;
     use std::mem;
-    use std::cell::RefCell;
 
     static mut counter: u32 = 0;
     static mut trails: u64 = 0;
@@ -89,7 +90,8 @@ pub mod d {
 
     pub fn max_width() -> u32 {
         unsafe {
-            (mem::size_of_val(&trails)*8) as u32
+            (mem::size_of_val(&trails) * 8) as u32
+            //~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
         }
     }
 
@@ -123,7 +125,11 @@ pub mod d {
     }
 
     pub struct D<'a> {
-        name: &'static str, i: u32, uid: u32, trail: u32, log: Log<'a>
+        name: &'static str,
+        i: u32,
+        uid: u32,
+        trail: u32,
+        log: Log<'a>,
     }
 
     impl<'a> fmt::Display for D<'a> {
@@ -139,9 +145,7 @@ pub mod d {
                 let ctr = counter;
                 counter += 1;
                 trails |= (1 << trail);
-                let ret = D {
-                    name: name, i: i, log: log, uid: ctr, trail: trail
-                };
+                let ret = D { name: name, i: i, log: log, uid: ctr, trail: trail };
                 indent_println(trail, &format!("+-- Make {}", ret));
                 ret
             }
@@ -153,7 +157,9 @@ pub mod d {
 
     impl<'a> Drop for D<'a> {
         fn drop(&mut self) {
-            unsafe { trails &= !(1 << self.trail); };
+            unsafe {
+                trails &= !(1 << self.trail);
+            };
             self.log.borrow_mut().push(self.uid);
             indent_println(self.trail, &format!("+-- Drop {}", self));
             indent_println(::PREF_INDENT, "");
diff --git a/tests/ui/drop/issue-23338-ensure-param-drop-order.stderr b/tests/ui/drop/issue-23338-ensure-param-drop-order.stderr
new file mode 100644
index 00000000000..fd36ccbcbee
--- /dev/null
+++ b/tests/ui/drop/issue-23338-ensure-param-drop-order.stderr
@@ -0,0 +1,17 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/issue-23338-ensure-param-drop-order.rs:93:31
+   |
+LL |             (mem::size_of_val(&trails) * 8) as u32
+   |                               ^^^^^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |             (mem::size_of_val(addr_of!(trails)) * 8) as u32
+   |                               ~~~~~~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/error-codes/E0017.rs b/tests/ui/error-codes/E0017.rs
index c211ad1a2f8..9d3433fa543 100644
--- a/tests/ui/error-codes/E0017.rs
+++ b/tests/ui/error-codes/E0017.rs
@@ -3,12 +3,16 @@ const C: i32 = 2;
 static mut M: i32 = 3;
 
 const CR: &'static mut i32 = &mut C; //~ ERROR mutable references are not allowed
-                                     //~| WARN taking a mutable
+//~| WARN taking a mutable
+
 static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0658
-                                              //~| ERROR cannot borrow
-                                              //~| ERROR mutable references are not allowed
+//~| ERROR cannot borrow
+//~| ERROR mutable references are not allowed
 
 static CONST_REF: &'static mut i32 = &mut C; //~ ERROR mutable references are not allowed
-                                              //~| WARN taking a mutable
+//~| WARN taking a mutable
+
 static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M }; //~ ERROR mutable references are not
+//~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+
 fn main() {}
diff --git a/tests/ui/error-codes/E0017.stderr b/tests/ui/error-codes/E0017.stderr
index 6e48f9582f1..ea6055da1c1 100644
--- a/tests/ui/error-codes/E0017.stderr
+++ b/tests/ui/error-codes/E0017.stderr
@@ -1,3 +1,18 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/E0017.rs:15:52
+   |
+LL | static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M };
+   |                                                    ^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL | static STATIC_MUT_REF: &'static mut i32 = unsafe { addr_of_mut!(M) };
+   |                                                    ~~~~~~~~~~~~~~~
+
 warning: taking a mutable reference to a `const` item
   --> $DIR/E0017.rs:5:30
    |
@@ -20,7 +35,7 @@ LL | const CR: &'static mut i32 = &mut C;
    |                              ^^^^^^
 
 error[E0658]: mutation through a reference is not allowed in statics
-  --> $DIR/E0017.rs:7:39
+  --> $DIR/E0017.rs:8:39
    |
 LL | static STATIC_REF: &'static mut i32 = &mut X;
    |                                       ^^^^^^
@@ -29,19 +44,19 @@ LL | static STATIC_REF: &'static mut i32 = &mut X;
    = help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
 
 error[E0764]: mutable references are not allowed in the final value of statics
-  --> $DIR/E0017.rs:7:39
+  --> $DIR/E0017.rs:8:39
    |
 LL | static STATIC_REF: &'static mut i32 = &mut X;
    |                                       ^^^^^^
 
 error[E0596]: cannot borrow immutable static item `X` as mutable
-  --> $DIR/E0017.rs:7:39
+  --> $DIR/E0017.rs:8:39
    |
 LL | static STATIC_REF: &'static mut i32 = &mut X;
    |                                       ^^^^^^ cannot borrow as mutable
 
 warning: taking a mutable reference to a `const` item
-  --> $DIR/E0017.rs:11:38
+  --> $DIR/E0017.rs:12:38
    |
 LL | static CONST_REF: &'static mut i32 = &mut C;
    |                                      ^^^^^^
@@ -55,18 +70,18 @@ LL | const C: i32 = 2;
    | ^^^^^^^^^^^^
 
 error[E0764]: mutable references are not allowed in the final value of statics
-  --> $DIR/E0017.rs:11:38
+  --> $DIR/E0017.rs:12:38
    |
 LL | static CONST_REF: &'static mut i32 = &mut C;
    |                                      ^^^^^^
 
 error[E0764]: mutable references are not allowed in the final value of statics
-  --> $DIR/E0017.rs:13:52
+  --> $DIR/E0017.rs:15:52
    |
 LL | static STATIC_MUT_REF: &'static mut i32 = unsafe { &mut M };
    |                                                    ^^^^^^
 
-error: aborting due to 6 previous errors; 2 warnings emitted
+error: aborting due to 6 previous errors; 3 warnings emitted
 
 Some errors have detailed explanations: E0596, E0658, E0764.
 For more information about an error, try `rustc --explain E0596`.
diff --git a/tests/ui/issues/issue-20616.rs b/tests/ui/impl-header-lifetime-elision/bare_type.rs
index 6c24d437272..9af98f870d2 100644
--- a/tests/ui/issues/issue-20616.rs
+++ b/tests/ui/impl-header-lifetime-elision/bare_type.rs
@@ -33,12 +33,11 @@ type TypeI<T,> = T;
 static STATIC: () = ();
 
 fn main() {
-
     // ensure token `>=` works fine
-    let _: TypeA<'static>= &STATIC;
-    let _: TypeA<'static,>= &STATIC;
+    let _: TypeA<'static> = &STATIC;
+    let _: TypeA<'static,> = &STATIC;
 
     // ensure token `>>=` works fine
-    let _: Box<TypeA<'static>>= Box::new(&STATIC);
-    let _: Box<TypeA<'static,>>= Box::new(&STATIC);
+    let _: Box<TypeA<'static>> = Box::new(&STATIC);
+    let _: Box<TypeA<'static,>> = Box::new(&STATIC);
 }
diff --git a/tests/ui/issues/issue-23611-enum-swap-in-drop.rs b/tests/ui/issues/issue-23611-enum-swap-in-drop.rs
index cdb130d600c..b967e6aecdd 100644
--- a/tests/ui/issues/issue-23611-enum-swap-in-drop.rs
+++ b/tests/ui/issues/issue-23611-enum-swap-in-drop.rs
@@ -37,11 +37,9 @@ pub fn main() {
             // | | | +-- Make D(g_b_5, 50000005)
             // | | | |                                 in g_B(b4b2) from GaspB::drop
             // | | | +-- Drop D(g_b_5, 50000005)
-            50000005,
-            // | | |
+            50000005, // | | |
             // | | +-- Drop D(GaspB::drop_3, 30000004)
-            30000004,
-            // | |
+            30000004, // | |
             // +-- Drop D(test_1, 10000000)
             10000000,
             //   |
@@ -49,15 +47,13 @@ pub fn main() {
             // | | +-- Make D(f_a_4, 40000007)
             // | | |                                   in f_A(a3a0) from GaspA::drop
             // | | +-- Drop D(f_a_4, 40000007)
-            40000007,
-            // | |
+            40000007, // | |
             // +-- Drop D(GaspA::drop_2, 20000006)
-            20000006,
-            //   |
+            20000006, //   |
             //   +-- Drop D(drop_6, 60000002)
-            60000002
-            //
-                ]);
+            60000002 //
+        ]
+    );
 
     // For reference purposes, the old (incorrect) behavior would produce the following
     // output, which you can compare to the above:
@@ -106,8 +102,8 @@ fn test<'a>(log: d::Log<'a>) {
     let _e = E::B(GaspB(g_b, 0xB4B0, log, D::new("test", 1, log)), true);
 }
 
-struct GaspA<'a>(for <'b> fn(u32, &'b str, d::Log<'a>), u32, d::Log<'a>, d::D<'a>);
-struct GaspB<'a>(for <'b> fn(u32, &'b str, d::Log<'a>), u32, d::Log<'a>, d::D<'a>);
+struct GaspA<'a>(for<'b> fn(u32, &'b str, d::Log<'a>), u32, d::Log<'a>, d::D<'a>);
+struct GaspB<'a>(for<'b> fn(u32, &'b str, d::Log<'a>), u32, d::Log<'a>, d::D<'a>);
 
 impl<'a> Drop for GaspA<'a> {
     fn drop(&mut self) {
@@ -124,7 +120,8 @@ impl<'a> Drop for GaspB<'a> {
 }
 
 enum E<'a> {
-    A(GaspA<'a>, bool), B(GaspB<'a>, bool),
+    A(GaspA<'a>, bool),
+    B(GaspB<'a>, bool),
 }
 
 fn f_a(x: u32, ctxt: &str, log: d::Log) {
@@ -174,9 +171,9 @@ const PREF_INDENT: u32 = 20;
 
 pub mod d {
     #![allow(unused_parens)]
+    use std::cell::RefCell;
     use std::fmt;
     use std::mem;
-    use std::cell::RefCell;
 
     static mut counter: u16 = 0;
     static mut trails: u64 = 0;
@@ -189,7 +186,8 @@ pub mod d {
 
     pub fn max_width() -> u32 {
         unsafe {
-            (mem::size_of_val(&trails)*8) as u32
+            (mem::size_of_val(&trails) * 8) as u32
+            //~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
         }
     }
 
@@ -223,7 +221,11 @@ pub mod d {
     }
 
     pub struct D<'a> {
-        name: &'static str, i: u8, uid: u32, trail: u32, log: Log<'a>
+        name: &'static str,
+        i: u8,
+        uid: u32,
+        trail: u32,
+        log: Log<'a>,
     }
 
     impl<'a> fmt::Display for D<'a> {
@@ -239,9 +241,7 @@ pub mod d {
                 let ctr = ((i as u32) * 10_000_000) + (counter as u32);
                 counter += 1;
                 trails |= (1 << trail);
-                let ret = D {
-                    name: name, i: i, log: log, uid: ctr, trail: trail
-                };
+                let ret = D { name: name, i: i, log: log, uid: ctr, trail: trail };
                 indent_println(trail, &format!("+-- Make {}", ret));
                 ret
             }
@@ -250,7 +250,9 @@ pub mod d {
 
     impl<'a> Drop for D<'a> {
         fn drop(&mut self) {
-            unsafe { trails &= !(1 << self.trail); };
+            unsafe {
+                trails &= !(1 << self.trail);
+            };
             self.log.borrow_mut().push(self.uid);
             indent_println(self.trail, &format!("+-- Drop {}", self));
             indent_println(::PREF_INDENT, "");
diff --git a/tests/ui/issues/issue-23611-enum-swap-in-drop.stderr b/tests/ui/issues/issue-23611-enum-swap-in-drop.stderr
new file mode 100644
index 00000000000..14a986a3332
--- /dev/null
+++ b/tests/ui/issues/issue-23611-enum-swap-in-drop.stderr
@@ -0,0 +1,17 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/issue-23611-enum-swap-in-drop.rs:189:31
+   |
+LL |             (mem::size_of_val(&trails) * 8) as u32
+   |                               ^^^^^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |             (mem::size_of_val(addr_of!(trails)) * 8) as u32
+   |                               ~~~~~~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.rs b/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.rs
index 7d3b00dfc71..8eb544e8ab9 100644
--- a/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.rs
+++ b/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.rs
@@ -14,9 +14,8 @@ struct S1 {
 
 impl S1 {
     fn new(_x: u64) -> S1 {
-        S1 {
-            a: unsafe { &mut X1 },
-        }
+        S1 { a: unsafe { &mut X1 } }
+        //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
     }
 }
 
diff --git a/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr b/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr
new file mode 100644
index 00000000000..17217cd5859
--- /dev/null
+++ b/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr
@@ -0,0 +1,17 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/borrowck-thread-local-static-mut-borrow-outlives-fn.rs:17:26
+   |
+LL |         S1 { a: unsafe { &mut X1 } }
+   |                          ^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |         S1 { a: unsafe { addr_of_mut!(X1) } }
+   |                          ~~~~~~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/static/reference-of-mut-static-safe.e2021.stderr b/tests/ui/static/reference-of-mut-static-safe.e2021.stderr
new file mode 100644
index 00000000000..16f47ace3a9
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static-safe.e2021.stderr
@@ -0,0 +1,26 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/reference-of-mut-static-safe.rs:9:14
+   |
+LL |     let _x = &X;
+   |              ^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let _x = addr_of!(X);
+   |              ~~~~~~~~~~~
+
+error[E0133]: use of mutable static is unsafe and requires unsafe function or block
+  --> $DIR/reference-of-mut-static-safe.rs:9:15
+   |
+LL |     let _x = &X;
+   |               ^ use of mutable static
+   |
+   = note: mutable statics can be mutated by multiple threads: aliasing violations or data races will cause undefined behavior
+
+error: aborting due to 1 previous error; 1 warning emitted
+
+For more information about this error, try `rustc --explain E0133`.
diff --git a/tests/ui/static/reference-of-mut-static-safe.e2024.stderr b/tests/ui/static/reference-of-mut-static-safe.e2024.stderr
new file mode 100644
index 00000000000..53f81179de5
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static-safe.e2024.stderr
@@ -0,0 +1,15 @@
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static-safe.rs:9:14
+   |
+LL |     let _x = &X;
+   |              ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let _x = addr_of!(X);
+   |              ~~~~~~~~~~~
+
+error: aborting due to 1 previous error
+
+For more information about this error, try `rustc --explain E0796`.
diff --git a/tests/ui/static/reference-of-mut-static-safe.rs b/tests/ui/static/reference-of-mut-static-safe.rs
new file mode 100644
index 00000000000..5cb1a03bef5
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static-safe.rs
@@ -0,0 +1,13 @@
+// revisions: e2021 e2024
+
+// [e2021] edition:2021
+// [e2024] compile-flags: --edition 2024 -Z unstable-options
+
+fn main() {
+    static mut X: i32 = 1;
+
+    let _x = &X;
+    //[e2024]~^ reference of mutable static is disallowed [E0796]
+    //[e2021]~^^ use of mutable static is unsafe and requires unsafe function or block [E0133]
+    //[e2021]~^^^ shared reference of mutable static is discouraged [static_mut_ref]
+}
diff --git a/tests/ui/static/reference-of-mut-static-unsafe-fn.rs b/tests/ui/static/reference-of-mut-static-unsafe-fn.rs
new file mode 100644
index 00000000000..6b1e77850e5
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static-unsafe-fn.rs
@@ -0,0 +1,23 @@
+// compile-flags: --edition 2024 -Z unstable-options
+
+fn main() {}
+
+unsafe fn _foo() {
+    static mut X: i32 = 1;
+    static mut Y: i32 = 1;
+
+    let _y = &X;
+    //~^ ERROR reference of mutable static is disallowed
+
+    let ref _a = X;
+    //~^ ERROR reference of mutable static is disallowed
+
+    let (_b, _c) = (&X, &Y);
+    //~^ ERROR reference of mutable static is disallowed
+    //~^^ ERROR reference of mutable static is disallowed
+
+    foo(&X);
+    //~^ ERROR reference of mutable static is disallowed
+}
+
+fn foo<'a>(_x: &'a i32) {}
diff --git a/tests/ui/static/reference-of-mut-static-unsafe-fn.stderr b/tests/ui/static/reference-of-mut-static-unsafe-fn.stderr
new file mode 100644
index 00000000000..5c6fdedfa96
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static-unsafe-fn.stderr
@@ -0,0 +1,63 @@
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static-unsafe-fn.rs:9:14
+   |
+LL |     let _y = &X;
+   |              ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let _y = addr_of!(X);
+   |              ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static-unsafe-fn.rs:12:18
+   |
+LL |     let ref _a = X;
+   |                  ^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let ref _a = addr_of!(X);
+   |                  ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static-unsafe-fn.rs:15:21
+   |
+LL |     let (_b, _c) = (&X, &Y);
+   |                     ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let (_b, _c) = (addr_of!(X), &Y);
+   |                     ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static-unsafe-fn.rs:15:25
+   |
+LL |     let (_b, _c) = (&X, &Y);
+   |                         ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let (_b, _c) = (&X, addr_of!(Y));
+   |                         ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static-unsafe-fn.rs:19:9
+   |
+LL |     foo(&X);
+   |         ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     foo(addr_of!(X));
+   |         ~~~~~~~~~~~
+
+error: aborting due to 5 previous errors
+
+For more information about this error, try `rustc --explain E0796`.
diff --git a/tests/ui/static/reference-of-mut-static.e2021.stderr b/tests/ui/static/reference-of-mut-static.e2021.stderr
new file mode 100644
index 00000000000..77a6b3d304b
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static.e2021.stderr
@@ -0,0 +1,91 @@
+error: shared reference of mutable static is discouraged
+  --> $DIR/reference-of-mut-static.rs:16:18
+   |
+LL |         let _y = &X;
+   |                  ^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+note: the lint level is defined here
+  --> $DIR/reference-of-mut-static.rs:6:9
+   |
+LL | #![deny(static_mut_ref)]
+   |         ^^^^^^^^^^^^^^
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let _y = addr_of!(X);
+   |                  ~~~~~~~~~~~
+
+error: mutable reference of mutable static is discouraged
+  --> $DIR/reference-of-mut-static.rs:20:18
+   |
+LL |         let _y = &mut X;
+   |                  ^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |         let _y = addr_of_mut!(X);
+   |                  ~~~~~~~~~~~~~~~
+
+error: shared reference of mutable static is discouraged
+  --> $DIR/reference-of-mut-static.rs:28:22
+   |
+LL |         let ref _a = X;
+   |                      ^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let ref _a = addr_of!(X);
+   |                      ~~~~~~~~~~~
+
+error: shared reference of mutable static is discouraged
+  --> $DIR/reference-of-mut-static.rs:32:25
+   |
+LL |         let (_b, _c) = (&X, &Y);
+   |                         ^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let (_b, _c) = (addr_of!(X), &Y);
+   |                         ~~~~~~~~~~~
+
+error: shared reference of mutable static is discouraged
+  --> $DIR/reference-of-mut-static.rs:32:29
+   |
+LL |         let (_b, _c) = (&X, &Y);
+   |                             ^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let (_b, _c) = (&X, addr_of!(Y));
+   |                             ~~~~~~~~~~~
+
+error: shared reference of mutable static is discouraged
+  --> $DIR/reference-of-mut-static.rs:38:13
+   |
+LL |         foo(&X);
+   |             ^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         foo(addr_of!(X));
+   |             ~~~~~~~~~~~
+
+error: aborting due to 6 previous errors
+
diff --git a/tests/ui/static/reference-of-mut-static.e2024.stderr b/tests/ui/static/reference-of-mut-static.e2024.stderr
new file mode 100644
index 00000000000..f445ec65a5d
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static.e2024.stderr
@@ -0,0 +1,75 @@
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static.rs:16:18
+   |
+LL |         let _y = &X;
+   |                  ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let _y = addr_of!(X);
+   |                  ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static.rs:20:18
+   |
+LL |         let _y = &mut X;
+   |                  ^^^^^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |         let _y = addr_of_mut!(X);
+   |                  ~~~~~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static.rs:28:22
+   |
+LL |         let ref _a = X;
+   |                      ^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let ref _a = addr_of!(X);
+   |                      ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static.rs:32:25
+   |
+LL |         let (_b, _c) = (&X, &Y);
+   |                         ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let (_b, _c) = (addr_of!(X), &Y);
+   |                         ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static.rs:32:29
+   |
+LL |         let (_b, _c) = (&X, &Y);
+   |                             ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         let (_b, _c) = (&X, addr_of!(Y));
+   |                             ~~~~~~~~~~~
+
+error[E0796]: reference of mutable static is disallowed
+  --> $DIR/reference-of-mut-static.rs:38:13
+   |
+LL |         foo(&X);
+   |             ^^ reference of mutable static
+   |
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |         foo(addr_of!(X));
+   |             ~~~~~~~~~~~
+
+error: aborting due to 6 previous errors
+
+For more information about this error, try `rustc --explain E0796`.
diff --git a/tests/ui/static/reference-of-mut-static.rs b/tests/ui/static/reference-of-mut-static.rs
new file mode 100644
index 00000000000..01a3b1fbd9b
--- /dev/null
+++ b/tests/ui/static/reference-of-mut-static.rs
@@ -0,0 +1,50 @@
+// revisions: e2021 e2024
+
+// [e2021] edition:2021
+// [e2024] compile-flags: --edition 2024 -Z unstable-options
+
+#![deny(static_mut_ref)]
+
+use std::ptr::{addr_of, addr_of_mut};
+
+fn main() {
+    static mut X: i32 = 1;
+
+    static mut Y: i32 = 1;
+
+    unsafe {
+        let _y = &X;
+        //[e2024]~^ ERROR reference of mutable static is disallowed
+        //[e2021]~^^ ERROR shared reference of mutable static is discouraged [static_mut_ref]
+
+        let _y = &mut X;
+        //[e2024]~^ ERROR reference of mutable static is disallowed
+        //[e2021]~^^ ERROR mutable reference of mutable static is discouraged [static_mut_ref]
+
+        let _z = addr_of_mut!(X);
+
+        let _p = addr_of!(X);
+
+        let ref _a = X;
+        //[e2024]~^ ERROR reference of mutable static is disallowed
+        //[e2021]~^^ ERROR shared reference of mutable static is discouraged [static_mut_ref]
+
+        let (_b, _c) = (&X, &Y);
+        //[e2024]~^ ERROR reference of mutable static is disallowed
+        //[e2021]~^^ ERROR shared reference of mutable static is discouraged [static_mut_ref]
+        //[e2024]~^^^ ERROR reference of mutable static is disallowed
+        //[e2021]~^^^^ ERROR shared reference of mutable static is discouraged [static_mut_ref]
+
+        foo(&X);
+        //[e2024]~^ ERROR reference of mutable static is disallowed
+        //[e2021]~^^ ERROR shared reference of mutable static is discouraged [static_mut_ref]
+
+        static mut Z: &[i32; 3] = &[0, 1, 2];
+
+        let _ = Z.len();
+        let _ = Z[0];
+        let _ = format!("{:?}", Z);
+    }
+}
+
+fn foo<'a>(_x: &'a i32) {}
diff --git a/tests/ui/static/safe-extern-statics-mut.rs b/tests/ui/static/safe-extern-statics-mut.rs
index 324fa443aa5..1c0662e0a6c 100644
--- a/tests/ui/static/safe-extern-statics-mut.rs
+++ b/tests/ui/static/safe-extern-statics-mut.rs
@@ -10,6 +10,8 @@ extern "C" {
 fn main() {
     let b = B; //~ ERROR use of mutable static is unsafe
     let rb = &B; //~ ERROR use of mutable static is unsafe
+    //~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
     let xb = XB; //~ ERROR use of mutable static is unsafe
     let xrb = &XB; //~ ERROR use of mutable static is unsafe
+    //~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
 }
diff --git a/tests/ui/static/safe-extern-statics-mut.stderr b/tests/ui/static/safe-extern-statics-mut.stderr
index e390625f20a..eda353ce673 100644
--- a/tests/ui/static/safe-extern-statics-mut.stderr
+++ b/tests/ui/static/safe-extern-statics-mut.stderr
@@ -1,3 +1,32 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/safe-extern-statics-mut.rs:12:14
+   |
+LL |     let rb = &B;
+   |              ^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let rb = addr_of!(B);
+   |              ~~~~~~~~~~~
+
+warning: shared reference of mutable static is discouraged
+  --> $DIR/safe-extern-statics-mut.rs:15:15
+   |
+LL |     let xrb = &XB;
+   |               ^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     let xrb = addr_of!(XB);
+   |               ~~~~~~~~~~~~
+
 error[E0133]: use of mutable static is unsafe and requires unsafe function or block
   --> $DIR/safe-extern-statics-mut.rs:11:13
    |
@@ -15,7 +44,7 @@ LL |     let rb = &B;
    = note: mutable statics can be mutated by multiple threads: aliasing violations or data races will cause undefined behavior
 
 error[E0133]: use of mutable static is unsafe and requires unsafe function or block
-  --> $DIR/safe-extern-statics-mut.rs:13:14
+  --> $DIR/safe-extern-statics-mut.rs:14:14
    |
 LL |     let xb = XB;
    |              ^^ use of mutable static
@@ -23,13 +52,13 @@ LL |     let xb = XB;
    = note: mutable statics can be mutated by multiple threads: aliasing violations or data races will cause undefined behavior
 
 error[E0133]: use of mutable static is unsafe and requires unsafe function or block
-  --> $DIR/safe-extern-statics-mut.rs:14:16
+  --> $DIR/safe-extern-statics-mut.rs:15:16
    |
 LL |     let xrb = &XB;
    |                ^^ use of mutable static
    |
    = note: mutable statics can be mutated by multiple threads: aliasing violations or data races will cause undefined behavior
 
-error: aborting due to 4 previous errors
+error: aborting due to 4 previous errors; 2 warnings emitted
 
 For more information about this error, try `rustc --explain E0133`.
diff --git a/tests/ui/statics/issue-15261.rs b/tests/ui/statics/issue-15261.rs
index ec413f6d1d2..14422329b7d 100644
--- a/tests/ui/statics/issue-15261.rs
+++ b/tests/ui/statics/issue-15261.rs
@@ -6,6 +6,7 @@
 
 static mut n_mut: usize = 0;
 
-static n: &'static usize = unsafe{ &n_mut };
+static n: &'static usize = unsafe { &n_mut };
+//~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
 
 fn main() {}
diff --git a/tests/ui/statics/issue-15261.stderr b/tests/ui/statics/issue-15261.stderr
new file mode 100644
index 00000000000..72d88ce1b38
--- /dev/null
+++ b/tests/ui/statics/issue-15261.stderr
@@ -0,0 +1,17 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/issue-15261.rs:9:37
+   |
+LL | static n: &'static usize = unsafe { &n_mut };
+   |                                     ^^^^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL | static n: &'static usize = unsafe { addr_of!(n_mut) };
+   |                                     ~~~~~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/statics/static-mut-xc.rs b/tests/ui/statics/static-mut-xc.rs
index 1d172d26a59..2fc265e02ea 100644
--- a/tests/ui/statics/static-mut-xc.rs
+++ b/tests/ui/statics/static-mut-xc.rs
@@ -7,7 +7,6 @@
 
 // aux-build:static_mut_xc.rs
 
-
 extern crate static_mut_xc;
 
 unsafe fn static_bound(_: &'static isize) {}
@@ -27,7 +26,9 @@ unsafe fn run() {
     static_mut_xc::a = -3;
     assert_eq!(static_mut_xc::a, -3);
     static_bound(&static_mut_xc::a);
+    //~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
     static_bound_set(&mut static_mut_xc::a);
+    //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
 }
 
 pub fn main() {
diff --git a/tests/ui/statics/static-mut-xc.stderr b/tests/ui/statics/static-mut-xc.stderr
new file mode 100644
index 00000000000..37aa336bc50
--- /dev/null
+++ b/tests/ui/statics/static-mut-xc.stderr
@@ -0,0 +1,31 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/static-mut-xc.rs:28:18
+   |
+LL |     static_bound(&static_mut_xc::a);
+   |                  ^^^^^^^^^^^^^^^^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL |     static_bound(addr_of!(static_mut_xc::a));
+   |                  ~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/static-mut-xc.rs:30:22
+   |
+LL |     static_bound_set(&mut static_mut_xc::a);
+   |                      ^^^^^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     static_bound_set(addr_of_mut!(static_mut_xc::a));
+   |                      ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+warning: 2 warnings emitted
+
diff --git a/tests/ui/statics/static-recursive.rs b/tests/ui/statics/static-recursive.rs
index 95dadc81f81..216beb0206d 100644
--- a/tests/ui/statics/static-recursive.rs
+++ b/tests/ui/statics/static-recursive.rs
@@ -1,36 +1,43 @@
 // run-pass
+
 static mut S: *const u8 = unsafe { &S as *const *const u8 as *const u8 };
+//~^ WARN shared reference of mutable static is discouraged [static_mut_ref]
 
 struct StaticDoubleLinked {
     prev: &'static StaticDoubleLinked,
     next: &'static StaticDoubleLinked,
     data: i32,
-    head: bool
+    head: bool,
 }
 
-static L1: StaticDoubleLinked = StaticDoubleLinked{prev: &L3, next: &L2, data: 1, head: true};
-static L2: StaticDoubleLinked = StaticDoubleLinked{prev: &L1, next: &L3, data: 2, head: false};
-static L3: StaticDoubleLinked = StaticDoubleLinked{prev: &L2, next: &L1, data: 3, head: false};
-
+static L1: StaticDoubleLinked = StaticDoubleLinked { prev: &L3, next: &L2, data: 1, head: true };
+static L2: StaticDoubleLinked = StaticDoubleLinked { prev: &L1, next: &L3, data: 2, head: false };
+static L3: StaticDoubleLinked = StaticDoubleLinked { prev: &L2, next: &L1, data: 3, head: false };
 
 pub fn main() {
-    unsafe { assert_eq!(S, *(S as *const *const u8)); }
+    unsafe {
+        assert_eq!(S, *(S as *const *const u8));
+    }
 
     let mut test_vec = Vec::new();
     let mut cur = &L1;
     loop {
         test_vec.push(cur.data);
         cur = cur.next;
-        if cur.head { break }
+        if cur.head {
+            break;
+        }
     }
-    assert_eq!(&test_vec, &[1,2,3]);
+    assert_eq!(&test_vec, &[1, 2, 3]);
 
     let mut test_vec = Vec::new();
     let mut cur = &L1;
     loop {
         cur = cur.prev;
         test_vec.push(cur.data);
-        if cur.head { break }
+        if cur.head {
+            break;
+        }
     }
-    assert_eq!(&test_vec, &[3,2,1]);
+    assert_eq!(&test_vec, &[3, 2, 1]);
 }
diff --git a/tests/ui/statics/static-recursive.stderr b/tests/ui/statics/static-recursive.stderr
new file mode 100644
index 00000000000..15888e5c68d
--- /dev/null
+++ b/tests/ui/statics/static-recursive.stderr
@@ -0,0 +1,17 @@
+warning: shared reference of mutable static is discouraged
+  --> $DIR/static-recursive.rs:3:36
+   |
+LL | static mut S: *const u8 = unsafe { &S as *const *const u8 as *const u8 };
+   |                                    ^^ shared reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: shared references are dangerous since if there's any kind of mutation of that static while the reference lives, that's UB; use `addr_of!` instead to create a raw pointer
+   |
+LL | static mut S: *const u8 = unsafe { addr_of!(S) as *const *const u8 as *const u8 };
+   |                                    ~~~~~~~~~~~
+
+warning: 1 warning emitted
+
diff --git a/tests/ui/thread-local/thread-local-static.rs b/tests/ui/thread-local/thread-local-static.rs
index e6cd4839dda..f5fb0984897 100644
--- a/tests/ui/thread-local/thread-local-static.rs
+++ b/tests/ui/thread-local/thread-local-static.rs
@@ -8,7 +8,8 @@ static mut STATIC_VAR_2: [u32; 8] = [4; 8];
 const fn g(x: &mut [u32; 8]) {
     //~^ ERROR mutable references are not allowed
     std::mem::swap(x, &mut STATIC_VAR_2)
-    //~^ ERROR thread-local statics cannot be accessed
+    //~^ WARN mutable reference of mutable static is discouraged [static_mut_ref]
+    //~^^ ERROR thread-local statics cannot be accessed
     //~| ERROR mutable references are not allowed
     //~| ERROR use of mutable static is unsafe
     //~| constant functions cannot refer to statics
diff --git a/tests/ui/thread-local/thread-local-static.stderr b/tests/ui/thread-local/thread-local-static.stderr
index c1777dd60db..b03f4580c2c 100644
--- a/tests/ui/thread-local/thread-local-static.stderr
+++ b/tests/ui/thread-local/thread-local-static.stderr
@@ -1,3 +1,18 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/thread-local-static.rs:10:23
+   |
+LL |     std::mem::swap(x, &mut STATIC_VAR_2)
+   |                       ^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     std::mem::swap(x, addr_of_mut!(STATIC_VAR_2))
+   |                       ~~~~~~~~~~~~~~~~~~~~~~~~~~
+
 error[E0133]: use of mutable static is unsafe and requires unsafe function or block
   --> $DIR/thread-local-static.rs:10:28
    |
@@ -38,7 +53,7 @@ LL |     std::mem::swap(x, &mut STATIC_VAR_2)
    = note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
    = help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
 
-error: aborting due to 5 previous errors
+error: aborting due to 5 previous errors; 1 warning emitted
 
 Some errors have detailed explanations: E0013, E0133, E0625, E0658.
 For more information about an error, try `rustc --explain E0013`.
diff --git a/tests/ui/thread-local/thread-local-static.thir.stderr b/tests/ui/thread-local/thread-local-static.thir.stderr
new file mode 100644
index 00000000000..2043b268c09
--- /dev/null
+++ b/tests/ui/thread-local/thread-local-static.thir.stderr
@@ -0,0 +1,59 @@
+warning: mutable reference of mutable static is discouraged
+  --> $DIR/thread-local-static.rs:12:23
+   |
+LL |     std::mem::swap(x, &mut STATIC_VAR_2)
+   |                       ^^^^^^^^^^^^^^^^^ mutable reference of mutable static
+   |
+   = note: for more information, see issue #114447 <https://github.com/rust-lang/rust/issues/114447>
+   = note: reference of mutable static is a hard error from 2024 edition
+   = note: mutable statics can be written to by multiple threads: aliasing violations or data races will cause undefined behavior
+   = note: `#[warn(static_mut_ref)]` on by default
+help: mutable references are dangerous since if there's any other pointer or reference used for that static while the reference lives, that's UB; use `addr_of_mut!` instead to create a raw pointer
+   |
+LL |     std::mem::swap(x, addr_of_mut!(STATIC_VAR_2))
+   |                       ~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+error[E0658]: mutable references are not allowed in constant functions
+  --> $DIR/thread-local-static.rs:10:12
+   |
+LL | const fn g(x: &mut [u32; 8]) {
+   |            ^
+   |
+   = note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
+   = help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
+
+error[E0625]: thread-local statics cannot be accessed at compile-time
+  --> $DIR/thread-local-static.rs:12:28
+   |
+LL |     std::mem::swap(x, &mut STATIC_VAR_2)
+   |                            ^^^^^^^^^^^^
+
+error[E0013]: constant functions cannot refer to statics
+  --> $DIR/thread-local-static.rs:12:28
+   |
+LL |     std::mem::swap(x, &mut STATIC_VAR_2)
+   |                            ^^^^^^^^^^^^
+   |
+   = help: consider extracting the value of the `static` to a `const`, and referring to that
+
+error[E0658]: mutable references are not allowed in constant functions
+  --> $DIR/thread-local-static.rs:12:23
+   |
+LL |     std::mem::swap(x, &mut STATIC_VAR_2)
+   |                       ^^^^^^^^^^^^^^^^^
+   |
+   = note: see issue #57349 <https://github.com/rust-lang/rust/issues/57349> for more information
+   = help: add `#![feature(const_mut_refs)]` to the crate attributes to enable
+
+error[E0133]: use of mutable static is unsafe and requires unsafe function or block
+  --> $DIR/thread-local-static.rs:12:23
+   |
+LL |     std::mem::swap(x, &mut STATIC_VAR_2)
+   |                       ^^^^^^^^^^^^^^^^^ use of mutable static
+   |
+   = note: mutable statics can be mutated by multiple threads: aliasing violations or data races will cause undefined behavior
+
+error: aborting due to 5 previous errors; 1 warning emitted
+
+Some errors have detailed explanations: E0013, E0133, E0625, E0658.
+For more information about an error, try `rustc --explain E0013`.