Skip to content

Commit 51bf9a3

Browse files
committed
Return ConstAllocation from eval_static_initializer query directly
1 parent cf9f444 commit 51bf9a3

File tree

18 files changed

+53
-82
lines changed

18 files changed

+53
-82
lines changed

compiler/rustc_const_eval/src/const_eval/eval_queries.rs

+26
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ use rustc_middle::traits::Reveal;
88
use rustc_middle::ty::layout::LayoutOf;
99
use rustc_middle::ty::print::with_no_trimmed_paths;
1010
use rustc_middle::ty::{self, TyCtxt};
11+
use rustc_span::def_id::LocalDefId;
1112
use rustc_span::Span;
1213
use rustc_target::abi::{self, Abi};
1314

@@ -249,11 +250,36 @@ pub fn eval_to_const_value_raw_provider<'tcx>(
249250
tcx.eval_to_allocation_raw(key).map(|val| turn_into_const_value(tcx, val, key))
250251
}
251252

253+
#[instrument(skip(tcx), level = "debug")]
254+
pub fn eval_static_initializer_provider<'tcx>(
255+
tcx: TyCtxt<'tcx>,
256+
def_id: LocalDefId,
257+
) -> ::rustc_middle::mir::interpret::EvalStaticInitializerRawResult<'tcx> {
258+
assert!(tcx.is_static(def_id.to_def_id()));
259+
260+
let instance = ty::Instance::mono(tcx, def_id.to_def_id());
261+
let cid = rustc_middle::mir::interpret::GlobalId { instance, promoted: None };
262+
let ecx = InterpCx::new(
263+
tcx,
264+
tcx.def_span(def_id),
265+
ty::ParamEnv::reveal_all(),
266+
// Statics (and promoteds inside statics) may access other statics, because unlike consts
267+
// they do not have to behave "as if" they were evaluated at runtime.
268+
CompileTimeInterpreter::new(CanAccessMutGlobal::Yes, CheckAlignment::Error),
269+
);
270+
let alloc_id = eval_in_interpreter(ecx, cid, true)?.alloc_id;
271+
let alloc = tcx.global_alloc(alloc_id).unwrap_memory();
272+
Ok(alloc)
273+
}
274+
252275
#[instrument(skip(tcx), level = "debug")]
253276
pub fn eval_to_allocation_raw_provider<'tcx>(
254277
tcx: TyCtxt<'tcx>,
255278
key: ty::ParamEnvAnd<'tcx, GlobalId<'tcx>>,
256279
) -> ::rustc_middle::mir::interpret::EvalToAllocationRawResult<'tcx> {
280+
// This shouldn't be used for statics, since statics are conceptually places,
281+
// not values -- so what we do here could break pointer identity.
282+
assert!(key.value.promoted.is_some() || !tcx.is_static(key.value.instance.def_id()));
257283
// Const eval always happens in Reveal::All mode in order to be able to use the hidden types of
258284
// opaque types. This is needed for trivial things like `size_of`, but also for using associated
259285
// types that are not specified in the opaque type.

compiler/rustc_const_eval/src/lib.rs

+1-7
Original file line numberDiff line numberDiff line change
@@ -40,13 +40,7 @@ pub fn provide(providers: &mut Providers) {
4040
const_eval::provide(providers);
4141
providers.eval_to_const_value_raw = const_eval::eval_to_const_value_raw_provider;
4242
providers.eval_to_allocation_raw = const_eval::eval_to_allocation_raw_provider;
43-
providers.eval_static_initializer_raw = |tcx, def_id| {
44-
assert!(tcx.is_static(def_id.to_def_id()));
45-
let instance = ty::Instance::mono(tcx, def_id.to_def_id());
46-
let gid = rustc_middle::mir::interpret::GlobalId { instance, promoted: None };
47-
let param_env = ty::ParamEnv::reveal_all();
48-
Ok(tcx.eval_to_allocation_raw(param_env.and(gid))?.alloc_id)
49-
};
43+
providers.eval_static_initializer = const_eval::eval_static_initializer_provider;
5044
providers.hooks.const_caller_location = util::caller_location::const_caller_location_provider;
5145
providers.eval_to_valtree = |tcx, param_env_and_value| {
5246
let (param_env, raw) = param_env_and_value.into_parts();

compiler/rustc_metadata/src/rmeta/decoder/cstore_impl.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -250,14 +250,14 @@ provide! { tcx, def_id, other, cdata,
250250
fn_arg_names => { table }
251251
coroutine_kind => { table_direct }
252252
coroutine_for_closure => { table }
253-
eval_static_initializer_raw => {
253+
eval_static_initializer => {
254254
Ok(cdata
255255
.root
256256
.tables
257-
.eval_static_initializer_raw
257+
.eval_static_initializer
258258
.get(cdata, def_id.index)
259259
.map(|lazy| lazy.decode((cdata, tcx)))
260-
.unwrap_or_else(|| panic!("{def_id:?} does not have eval_static_initializer_raw")))
260+
.unwrap_or_else(|| panic!("{def_id:?} does not have eval_static_initializer")))
261261
}
262262
trait_def => { table }
263263
deduced_param_attrs => { table }

compiler/rustc_metadata/src/rmeta/encoder.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -1454,8 +1454,8 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
14541454
}
14551455
if let DefKind::Static(_) = def_kind {
14561456
if !self.tcx.is_foreign_item(def_id) {
1457-
let data = self.tcx.eval_static_initializer_raw(def_id).unwrap();
1458-
record!(self.tables.eval_static_initializer_raw[def_id] <- data);
1457+
let data = self.tcx.eval_static_initializer(def_id).unwrap();
1458+
record!(self.tables.eval_static_initializer[def_id] <- data);
14591459
}
14601460
}
14611461
if let DefKind::Enum | DefKind::Struct | DefKind::Union = def_kind {

compiler/rustc_metadata/src/rmeta/mod.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -443,7 +443,7 @@ define_tables! {
443443
fn_arg_names: Table<DefIndex, LazyArray<Ident>>,
444444
coroutine_kind: Table<DefIndex, hir::CoroutineKind>,
445445
coroutine_for_closure: Table<DefIndex, RawDefId>,
446-
eval_static_initializer_raw: Table<DefIndex, LazyValue<mir::interpret::AllocId>>,
446+
eval_static_initializer: Table<DefIndex, LazyValue<mir::interpret::ConstAllocation<'static>>>,
447447
trait_def: Table<DefIndex, LazyValue<ty::TraitDef>>,
448448
trait_item_def_id: Table<DefIndex, RawDefId>,
449449
expn_that_defined: Table<DefIndex, LazyValue<ExpnId>>,

compiler/rustc_middle/src/mir/interpret/error.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use super::{AllocId, AllocRange, Pointer, Scalar};
1+
use super::{AllocId, AllocRange, ConstAllocation, Pointer, Scalar};
22

33
use crate::error;
44
use crate::mir::{ConstAlloc, ConstValue};
@@ -83,7 +83,7 @@ impl Into<ErrorGuaranteed> for ReportedErrorInfo {
8383
TrivialTypeTraversalImpls! { ErrorHandled }
8484

8585
pub type EvalToAllocationRawResult<'tcx> = Result<ConstAlloc<'tcx>, ErrorHandled>;
86-
pub type EvalStaticInitializerRawResult = Result<AllocId, ErrorHandled>;
86+
pub type EvalStaticInitializerRawResult<'tcx> = Result<ConstAllocation<'tcx>, ErrorHandled>;
8787
pub type EvalToConstValueResult<'tcx> = Result<ConstValue<'tcx>, ErrorHandled>;
8888
/// `Ok(None)` indicates the constant was fine, but the valtree couldn't be constructed.
8989
/// This is needed in `thir::pattern::lower_inline_const`.

compiler/rustc_middle/src/mir/interpret/queries.rs

+1-32
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
use super::{ErrorHandled, EvalToConstValueResult, EvalToValTreeResult, GlobalId};
22

33
use crate::mir;
4-
use crate::query::{TyCtxtAt, TyCtxtEnsure};
4+
use crate::query::TyCtxtEnsure;
55
use crate::ty::visit::TypeVisitableExt;
66
use crate::ty::GenericArgs;
77
use crate::ty::{self, TyCtxt};
@@ -173,30 +173,6 @@ impl<'tcx> TyCtxt<'tcx> {
173173
self.eval_to_valtree(inputs)
174174
}
175175
}
176-
177-
/// Evaluate a static's initializer, returning the allocation of the initializer's memory.
178-
#[inline(always)]
179-
pub fn eval_static_initializer(
180-
self,
181-
def_id: DefId,
182-
) -> Result<mir::ConstAllocation<'tcx>, ErrorHandled> {
183-
self.at(DUMMY_SP).eval_static_initializer(def_id)
184-
}
185-
}
186-
187-
impl<'tcx> TyCtxtAt<'tcx> {
188-
/// Evaluate a static's initializer, returning the allocation of the initializer's memory.
189-
///
190-
/// The span is entirely ignored here, but still helpful for better query cycle errors.
191-
pub fn eval_static_initializer(
192-
self,
193-
def_id: DefId,
194-
) -> Result<mir::ConstAllocation<'tcx>, ErrorHandled> {
195-
trace!("eval_static_initializer: Need to compute {:?}", def_id);
196-
assert!(self.is_static(def_id));
197-
let alloc_id = self.eval_static_initializer_raw(def_id)?;
198-
Ok(self.global_alloc(alloc_id).unwrap_memory())
199-
}
200176
}
201177

202178
impl<'tcx> TyCtxtEnsure<'tcx> {
@@ -218,11 +194,4 @@ impl<'tcx> TyCtxtEnsure<'tcx> {
218194
let inputs = self.tcx.erase_regions(param_env.and(cid));
219195
self.eval_to_const_value_raw(inputs)
220196
}
221-
222-
/// Evaluate a static's initializer, returning the allocation of the initializer's memory.
223-
pub fn eval_static_initializer(self, def_id: DefId) {
224-
trace!("eval_static_initializer: Need to compute {:?}", def_id);
225-
assert!(self.tcx.is_static(def_id));
226-
self.eval_static_initializer_raw(def_id);
227-
}
228197
}

compiler/rustc_middle/src/mir/mod.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
//!
33
//! [rustc dev guide]: https://rustc-dev-guide.rust-lang.org/mir/index.html
44
5-
use crate::mir::interpret::{AllocRange, ConstAllocation, Scalar};
5+
use crate::mir::interpret::{AllocRange, Scalar};
66
use crate::mir::visit::MirVisitable;
77
use crate::ty::codec::{TyDecoder, TyEncoder};
88
use crate::ty::fold::{FallibleTypeFolder, TypeFoldable};

compiler/rustc_middle/src/mir/pretty.rs

+2
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@ use std::fs;
44
use std::io::{self, Write as _};
55
use std::path::{Path, PathBuf};
66

7+
use crate::mir::interpret::ConstAllocation;
8+
79
use super::graphviz::write_mir_fn_graphviz;
810
use rustc_ast::InlineAsmTemplatePiece;
911
use rustc_middle::mir::interpret::{

compiler/rustc_middle/src/query/erase.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -277,7 +277,6 @@ trivial! {
277277
rustc_middle::mir::interpret::CtfeProvenance,
278278
rustc_middle::mir::interpret::ErrorHandled,
279279
rustc_middle::mir::interpret::LitToConstError,
280-
rustc_middle::mir::interpret::EvalStaticInitializerRawResult,
281280
rustc_middle::thir::ExprId,
282281
rustc_middle::traits::CodegenObligationError,
283282
rustc_middle::traits::EvaluationResult,
@@ -338,6 +337,7 @@ tcx_lifetime! {
338337
rustc_middle::mir::ConstValue,
339338
rustc_middle::mir::interpret::GlobalId,
340339
rustc_middle::mir::interpret::LitToConstInput,
340+
rustc_middle::mir::interpret::EvalStaticInitializerRawResult,
341341
rustc_middle::traits::query::MethodAutoderefStepsResult,
342342
rustc_middle::traits::query::type_op::AscribeUserType,
343343
rustc_middle::traits::query::type_op::Eq,

compiler/rustc_middle/src/query/mod.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1073,7 +1073,7 @@ rustc_queries! {
10731073
}
10741074

10751075
/// Evaluate a static's initializer, returning the allocation of the initializer's memory.
1076-
query eval_static_initializer_raw(key: DefId) -> EvalStaticInitializerRawResult {
1076+
query eval_static_initializer(key: DefId) -> EvalStaticInitializerRawResult<'tcx> {
10771077
desc { |tcx|
10781078
"evaluating initializer of static `{}`",
10791079
tcx.def_path_str(key)

compiler/rustc_middle/src/ty/parameterized.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,6 @@ trivially_parameterized_over_tcx! {
6363
crate::middle::lib_features::FeatureStability,
6464
crate::middle::resolve_bound_vars::ObjectLifetimeDefault,
6565
crate::mir::ConstQualifs,
66-
crate::mir::interpret::AllocId,
6766
ty::AssocItemContainer,
6867
ty::Asyncness,
6968
ty::DeducedParamAttrs,
@@ -127,6 +126,7 @@ parameterized_over_tcx! {
127126
crate::middle::exported_symbols::ExportedSymbol,
128127
crate::mir::Body,
129128
crate::mir::CoroutineLayout,
129+
crate::mir::interpret::ConstAllocation,
130130
ty::Ty,
131131
ty::FnSig,
132132
ty::GenericPredicates,

tests/ui/consts/recursive-zst-static.default.stderr

+2-7
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,10 @@
11
error[E0391]: cycle detected when evaluating initializer of static `FOO`
2-
--> $DIR/recursive-zst-static.rs:10:1
3-
|
4-
LL | static FOO: () = FOO;
5-
| ^^^^^^^^^^^^^^
6-
|
7-
note: ...which requires const-evaluating + checking `FOO`...
82
--> $DIR/recursive-zst-static.rs:10:18
93
|
104
LL | static FOO: () = FOO;
115
| ^^^
12-
= note: ...which again requires evaluating initializer of static `FOO`, completing the cycle
6+
|
7+
= note: ...which immediately requires evaluating initializer of static `FOO` again
138
note: cycle used when linting top-level module
149
--> $DIR/recursive-zst-static.rs:10:1
1510
|

tests/ui/consts/recursive-zst-static.unleash.stderr

+2-7
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,10 @@
11
error[E0391]: cycle detected when evaluating initializer of static `FOO`
2-
--> $DIR/recursive-zst-static.rs:10:1
3-
|
4-
LL | static FOO: () = FOO;
5-
| ^^^^^^^^^^^^^^
6-
|
7-
note: ...which requires const-evaluating + checking `FOO`...
82
--> $DIR/recursive-zst-static.rs:10:18
93
|
104
LL | static FOO: () = FOO;
115
| ^^^
12-
= note: ...which again requires evaluating initializer of static `FOO`, completing the cycle
6+
|
7+
= note: ...which immediately requires evaluating initializer of static `FOO` again
138
note: cycle used when linting top-level module
149
--> $DIR/recursive-zst-static.rs:10:1
1510
|

tests/ui/consts/write-to-static-mut-in-static.stderr

+2-7
Original file line numberDiff line numberDiff line change
@@ -5,17 +5,12 @@ LL | pub static mut B: () = unsafe { A = 1; };
55
| ^^^^^ modifying a static's initial value from another static's initializer
66

77
error[E0391]: cycle detected when evaluating initializer of static `C`
8-
--> $DIR/write-to-static-mut-in-static.rs:5:1
9-
|
10-
LL | pub static mut C: u32 = unsafe { C = 1; 0 };
11-
| ^^^^^^^^^^^^^^^^^^^^^
12-
|
13-
note: ...which requires const-evaluating + checking `C`...
148
--> $DIR/write-to-static-mut-in-static.rs:5:34
159
|
1610
LL | pub static mut C: u32 = unsafe { C = 1; 0 };
1711
| ^^^^^
18-
= note: ...which again requires evaluating initializer of static `C`, completing the cycle
12+
|
13+
= note: ...which immediately requires evaluating initializer of static `C` again
1914
note: cycle used when linting top-level module
2015
--> $DIR/write-to-static-mut-in-static.rs:1:1
2116
|

tests/ui/recursion/recursive-static-definition.stderr

+2-7
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,10 @@
11
error[E0391]: cycle detected when evaluating initializer of static `FOO`
2-
--> $DIR/recursive-static-definition.rs:1:1
3-
|
4-
LL | pub static FOO: u32 = FOO;
5-
| ^^^^^^^^^^^^^^^^^^^
6-
|
7-
note: ...which requires const-evaluating + checking `FOO`...
82
--> $DIR/recursive-static-definition.rs:1:23
93
|
104
LL | pub static FOO: u32 = FOO;
115
| ^^^
12-
= note: ...which again requires evaluating initializer of static `FOO`, completing the cycle
6+
|
7+
= note: ...which immediately requires evaluating initializer of static `FOO` again
138
note: cycle used when linting top-level module
149
--> $DIR/recursive-static-definition.rs:1:1
1510
|

tests/ui/treat-err-as-bug/err.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
// compile-flags: -Ztreat-err-as-bug
22
// failure-status: 101
33
// error-pattern: aborting due to `-Z treat-err-as-bug=1`
4-
// error-pattern: [eval_to_allocation_raw] const-evaluating + checking `C`
4+
// error-pattern: [eval_static_initializer] evaluating initializer of static `C`
55
// normalize-stderr-test "note: .*\n\n" -> ""
66
// normalize-stderr-test "thread 'rustc' panicked.*:\n.*\n" -> ""
77
// rustc-env:RUST_BACKTRACE=0

tests/ui/treat-err-as-bug/err.stderr

+2-2
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,6 @@ LL | pub static C: u32 = 0 - 1;
77
error: the compiler unexpectedly panicked. this is a bug.
88

99
query stack during panic:
10-
#0 [eval_to_allocation_raw] const-evaluating + checking `C`
11-
#1 [eval_static_initializer_raw] evaluating initializer of static `C`
10+
#0 [eval_static_initializer] evaluating initializer of static `C`
11+
#1 [lint_mod] linting top-level module
1212
end of query stack

0 commit comments

Comments
 (0)