Clean up config mess.
`parse_cfgspecs` and `parse_check_cfg` run very early, before the main interner is running. They each use a short-lived interner and convert all interned symbols to strings in their output data structures. Once the main interner starts up, these data structures get converted into new data structures that are identical except with the strings converted to symbols. All is not obvious from the current code, which is a mess, particularly with inconsistent naming that obscures the parallel string/symbol data structures. This commit clean things up a lot. - The existing `CheckCfg` type is generic, allowing both `CheckCfg<String>` and `CheckCfg<Symbol>` forms. This is really useful, but it defaults to `String`. The commit removes the default so we have to use `CheckCfg<String>` and `CheckCfg<Symbol>` explicitly, which makes things clearer. - Introduces `Cfg`, which is generic over `String` and `Symbol`, similar to `CheckCfg`. - Renames some things. - `parse_cfgspecs` -> `parse_cfg` - `CfgSpecs` -> `Cfg<String>`, plus it's used in more places, rather than the underlying `FxHashSet` type. - `CrateConfig` -> `Cfg<Symbol>`. - `CrateCheckConfig` -> `CheckCfg<Symbol>` - Adds some comments explaining the string-to-symbol conversions. - `to_crate_check_config`, which converts `CheckCfg<String>` to `CheckCfg<Symbol>`, is inlined and removed and combined with the overly-general `CheckCfg::map_data` to produce `CheckCfg::<String>::intern`. - `build_configuration` now does the `Cfg<String>`-to-`Cfg<Symbol>` conversion, so callers don't need to, which removes the need for `to_crate_config`. The diff for two of the fields in `Config` is a good example of the improved clarity: ``` - pub crate_cfg: FxHashSet<(String, Option<String>)>, - pub crate_check_cfg: CheckCfg, + pub crate_cfg: Cfg<String>, + pub crate_check_cfg: CheckCfg<String>, ``` Compare that with the diff for the corresponding fields in `ParseSess`, and the relationship to `Config` is much clearer than before: ``` - pub config: CrateConfig, - pub check_config: CrateCheckConfig, + pub config: Cfg<Symbol>, + pub check_config: CheckCfg<Symbol>, ```
This commit is contained in:
parent
75e415ba86
commit
5e54997157
8 changed files with 65 additions and 71 deletions
|
@ -16,7 +16,6 @@ use rustc_target::spec::LinkSelfContainedComponents;
|
|||
use rustc_target::spec::{PanicStrategy, RelocModel, SanitizerSet, SplitDebuginfo};
|
||||
use rustc_target::spec::{Target, TargetTriple, TargetWarnings, TARGETS};
|
||||
|
||||
use crate::parse::{CrateCheckConfig, CrateConfig};
|
||||
use rustc_feature::UnstableFeatures;
|
||||
use rustc_span::edition::{Edition, DEFAULT_EDITION, EDITION_NAME_LIST, LATEST_STABLE_EDITION};
|
||||
use rustc_span::source_map::{FileName, FilePathMapping};
|
||||
|
@ -1248,8 +1247,8 @@ pub const fn default_lib_output() -> CrateType {
|
|||
CrateType::Rlib
|
||||
}
|
||||
|
||||
fn default_configuration(sess: &Session) -> CrateConfig {
|
||||
// NOTE: This should be kept in sync with `CrateCheckConfig::fill_well_known` below.
|
||||
fn default_configuration(sess: &Session) -> Cfg<Symbol> {
|
||||
// NOTE: This should be kept in sync with `CheckCfg::<Symbol>::fill_well_known` below.
|
||||
let end = &sess.target.endian;
|
||||
let arch = &sess.target.arch;
|
||||
let wordsz = sess.target.pointer_width.to_string();
|
||||
|
@ -1265,7 +1264,7 @@ fn default_configuration(sess: &Session) -> CrateConfig {
|
|||
sess.emit_fatal(err);
|
||||
});
|
||||
|
||||
let mut ret = CrateConfig::default();
|
||||
let mut ret = Cfg::default();
|
||||
ret.reserve(7); // the minimum number of insertions
|
||||
// Target bindings.
|
||||
ret.insert((sym::target_os, Some(Symbol::intern(os))));
|
||||
|
@ -1358,15 +1357,14 @@ fn default_configuration(sess: &Session) -> CrateConfig {
|
|||
ret
|
||||
}
|
||||
|
||||
/// Converts the crate `cfg!` configuration from `String` to `Symbol`.
|
||||
/// `rustc_interface::interface::Config` accepts this in the compiler configuration,
|
||||
/// but the symbol interner is not yet set up then, so we must convert it later.
|
||||
pub fn to_crate_config(cfg: FxHashSet<(String, Option<String>)>) -> CrateConfig {
|
||||
cfg.into_iter().map(|(a, b)| (Symbol::intern(&a), b.map(|b| Symbol::intern(&b)))).collect()
|
||||
}
|
||||
/// The parsed `--cfg` options that define the compilation environment of the
|
||||
/// crate, used to drive conditional compilation. `T` is always `String` or
|
||||
/// `Symbol`. Strings are used temporarily very early on. Once the the main
|
||||
/// symbol interner is running, they are converted to symbols.
|
||||
pub type Cfg<T> = FxHashSet<(T, Option<T>)>;
|
||||
|
||||
/// The parsed `--check-cfg` options
|
||||
pub struct CheckCfg<T = String> {
|
||||
/// The parsed `--check-cfg` options. The `<T>` structure is similar to `Cfg`.
|
||||
pub struct CheckCfg<T> {
|
||||
/// Is well known names activated
|
||||
pub exhaustive_names: bool,
|
||||
/// Is well known values activated
|
||||
|
@ -1385,8 +1383,8 @@ impl<T> Default for CheckCfg<T> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<T> CheckCfg<T> {
|
||||
fn map_data<O: Eq + Hash>(self, f: impl Fn(T) -> O) -> CheckCfg<O> {
|
||||
impl CheckCfg<String> {
|
||||
pub fn intern(self) -> CheckCfg<Symbol> {
|
||||
CheckCfg {
|
||||
exhaustive_names: self.exhaustive_names,
|
||||
exhaustive_values: self.exhaustive_values,
|
||||
|
@ -1395,10 +1393,10 @@ impl<T> CheckCfg<T> {
|
|||
.into_iter()
|
||||
.map(|(name, values)| {
|
||||
(
|
||||
f(name),
|
||||
Symbol::intern(&name),
|
||||
match values {
|
||||
ExpectedValues::Some(values) => ExpectedValues::Some(
|
||||
values.into_iter().map(|b| b.map(|b| f(b))).collect(),
|
||||
values.into_iter().map(|b| b.map(|b| Symbol::intern(&b))).collect(),
|
||||
),
|
||||
ExpectedValues::Any => ExpectedValues::Any,
|
||||
},
|
||||
|
@ -1441,14 +1439,7 @@ impl<'a, T: Eq + Hash + Copy + 'a> Extend<&'a T> for ExpectedValues<T> {
|
|||
}
|
||||
}
|
||||
|
||||
/// Converts the crate `--check-cfg` options from `String` to `Symbol`.
|
||||
/// `rustc_interface::interface::Config` accepts this in the compiler configuration,
|
||||
/// but the symbol interner is not yet set up then, so we must convert it later.
|
||||
pub fn to_crate_check_config(cfg: CheckCfg) -> CrateCheckConfig {
|
||||
cfg.map_data(|s| Symbol::intern(&s))
|
||||
}
|
||||
|
||||
impl CrateCheckConfig {
|
||||
impl CheckCfg<Symbol> {
|
||||
pub fn fill_well_known(&mut self, current_target: &Target) {
|
||||
if !self.exhaustive_values && !self.exhaustive_names {
|
||||
return;
|
||||
|
@ -1588,7 +1579,13 @@ impl CrateCheckConfig {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn build_configuration(sess: &Session, mut user_cfg: CrateConfig) -> CrateConfig {
|
||||
pub fn build_configuration(sess: &Session, user_cfg: Cfg<String>) -> Cfg<Symbol> {
|
||||
// We can now intern these strings.
|
||||
let mut user_cfg: Cfg<Symbol> = user_cfg
|
||||
.into_iter()
|
||||
.map(|(a, b)| (Symbol::intern(&a), b.map(|b| Symbol::intern(&b))))
|
||||
.collect();
|
||||
|
||||
// Combine the configuration requested by the session (command line) with
|
||||
// some default and generated configuration items.
|
||||
let default_cfg = default_configuration(sess);
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
//! Contains `ParseSess` which holds state living beyond what one `Parser` might.
|
||||
//! It also serves as an input to the parser itself.
|
||||
|
||||
use crate::config::CheckCfg;
|
||||
use crate::config::{Cfg, CheckCfg};
|
||||
use crate::errors::{
|
||||
CliFeatureDiagnosticHelp, FeatureDiagnosticForIssue, FeatureDiagnosticHelp, FeatureGateError,
|
||||
};
|
||||
|
@ -25,11 +25,6 @@ use rustc_span::{Span, Symbol};
|
|||
use rustc_ast::attr::AttrIdGenerator;
|
||||
use std::str;
|
||||
|
||||
/// The set of keys (and, optionally, values) that define the compilation
|
||||
/// environment of the crate, used to drive conditional compilation.
|
||||
pub type CrateConfig = FxHashSet<(Symbol, Option<Symbol>)>;
|
||||
pub type CrateCheckConfig = CheckCfg<Symbol>;
|
||||
|
||||
/// Collected spans during parsing for places where a certain feature was
|
||||
/// used and should be feature gated accordingly in `check_crate`.
|
||||
#[derive(Default)]
|
||||
|
@ -193,8 +188,8 @@ pub fn add_feature_diagnostics_for_issue(
|
|||
pub struct ParseSess {
|
||||
pub span_diagnostic: Handler,
|
||||
pub unstable_features: UnstableFeatures,
|
||||
pub config: CrateConfig,
|
||||
pub check_config: CrateCheckConfig,
|
||||
pub config: Cfg<Symbol>,
|
||||
pub check_config: CheckCfg<Symbol>,
|
||||
pub edition: Edition,
|
||||
/// Places where raw identifiers were used. This is used to avoid complaining about idents
|
||||
/// clashing with keywords in new editions.
|
||||
|
@ -237,8 +232,8 @@ impl ParseSess {
|
|||
Self {
|
||||
span_diagnostic: handler,
|
||||
unstable_features: UnstableFeatures::from_environment(None),
|
||||
config: FxHashSet::default(),
|
||||
check_config: CrateCheckConfig::default(),
|
||||
config: Cfg::default(),
|
||||
check_config: CheckCfg::default(),
|
||||
edition: ExpnId::root().expn_data().edition,
|
||||
raw_identifier_spans: Default::default(),
|
||||
bad_unicode_identifiers: Lock::new(Default::default()),
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue