Skip to content

Commit 55f3acf

Browse files
committed
rustc_mir: disallow global mutable state in proc macros.
1 parent c9edc02 commit 55f3acf

File tree

3 files changed

+54
-0
lines changed

3 files changed

+54
-0
lines changed

src/librustc_mir/transform/qualify_consts.rs

+13
Original file line numberDiff line numberDiff line change
@@ -1648,6 +1648,19 @@ impl<'tcx> MirPass<'tcx> for QualifyAndPromoteConstants<'tcx> {
16481648
remove_drop_and_storage_dead_on_promoted_locals(body, promoted_temps);
16491649
}
16501650

1651+
// HACK(eddyb) try to prevent global mutable state in proc macros.
1652+
// (this is not perfect and could also have false positives)
1653+
if mode == Mode::Static || mode == Mode::StaticMut {
1654+
use rustc::session::config::CrateType;
1655+
if tcx.sess.crate_types.borrow().contains(&CrateType::ProcMacro) {
1656+
let ty = body.return_ty();
1657+
let param_env = ty::ParamEnv::empty();
1658+
if mode == Mode::StaticMut || !ty.is_freeze(tcx, param_env, DUMMY_SP) {
1659+
tcx.sess.span_err(body.span, "mutable global state in a proc-macro");
1660+
}
1661+
}
1662+
}
1663+
16511664
if mode == Mode::Static && !tcx.has_attr(def_id, sym::thread_local) {
16521665
// `static`s (not `static mut`s) which are not `#[thread_local]` must be `Sync`.
16531666
check_static_is_sync(tcx, body, hir_id);
+19
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
// force-host
2+
// no-prefer-dynamic
3+
4+
#![crate_type = "proc-macro"]
5+
#![allow(warnings)]
6+
7+
use std::cell::Cell;
8+
use std::sync::atomic::AtomicBool;
9+
10+
static mut FOO: u8 = 0;
11+
//~^ ERROR mutable global state in a proc-macro
12+
13+
static BAR: AtomicBool = AtomicBool::new(false);
14+
//~^ ERROR mutable global state in a proc-macro
15+
16+
thread_local!(static BAZ: Cell<String> = Cell::new(String::new()));
17+
//~^ ERROR mutable global state in a proc-macro
18+
19+
static FROZEN: &str = "snow";
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
error: mutable global state in a proc-macro
2+
--> $DIR/global-mut-state.rs:10:1
3+
|
4+
LL | static mut FOO: u8 = 0;
5+
| ^^^^^^^^^^^^^^^^^^^^^^^
6+
7+
error: mutable global state in a proc-macro
8+
--> $DIR/global-mut-state.rs:13:1
9+
|
10+
LL | static BAR: AtomicBool = AtomicBool::new(false);
11+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
12+
13+
error: mutable global state in a proc-macro
14+
--> $DIR/global-mut-state.rs:16:1
15+
|
16+
LL | thread_local!(static BAZ: Cell<String> = Cell::new(String::new()));
17+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
18+
|
19+
= note: this error originates in a macro outside of the current crate (in Nightly builds, run with -Z external-macro-backtrace for more info)
20+
21+
error: aborting due to 3 previous errors
22+

0 commit comments

Comments
 (0)