Skip to content

Commit 5a8483b

Browse files
committed
Include declared list of features in fingerprint for -Zcheck-cfg
Otherwise changing (add, removing, ...) features from the `[features]` table would not cause rustc to be called with the new `--check-cfg`, showing potentially outdated warnings.
1 parent 2d14354 commit 5a8483b

File tree

3 files changed

+77
-0
lines changed

3 files changed

+77
-0
lines changed

src/cargo/core/compiler/fingerprint/dirty_reason.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,10 @@ pub enum DirtyReason {
1515
old: String,
1616
new: String,
1717
},
18+
DeclaredFeaturesChanged {
19+
old: String,
20+
new: String,
21+
},
1822
TargetConfigurationChanged,
1923
PathToSourceChanged,
2024
ProfileConfigurationChanged,
@@ -141,6 +145,9 @@ impl DirtyReason {
141145
DirtyReason::FeaturesChanged { .. } => {
142146
s.dirty_because(unit, "the list of features changed")
143147
}
148+
DirtyReason::DeclaredFeaturesChanged { .. } => {
149+
s.dirty_because(unit, "the list of declared features changed")
150+
}
144151
DirtyReason::TargetConfigurationChanged => {
145152
s.dirty_because(unit, "the target configuration changed")
146153
}

src/cargo/core/compiler/fingerprint/mod.rs

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,7 @@
6565
//! Target Name | ✓ | ✓
6666
//! TargetKind (bin/lib/etc.) | ✓ | ✓
6767
//! Enabled Features | ✓ | ✓
68+
//! Declared Features | ✓ | ?
6869
//! Immediate dependency’s hashes | ✓[^1] | ✓
6970
//! [`CompileKind`] (host/target) | ✓ | ✓
7071
//! __CARGO_DEFAULT_LIB_METADATA[^4] | | ✓
@@ -572,6 +573,8 @@ pub struct Fingerprint {
572573
rustc: u64,
573574
/// Sorted list of cfg features enabled.
574575
features: String,
576+
/// Sorted list of all the declared cfg features.
577+
declared_features: String,
575578
/// Hash of the `Target` struct, including the target name,
576579
/// package-relative source path, edition, etc.
577580
target: u64,
@@ -876,6 +879,7 @@ impl Fingerprint {
876879
profile: 0,
877880
path: 0,
878881
features: String::new(),
882+
declared_features: String::new(),
879883
deps: Vec::new(),
880884
local: Mutex::new(Vec::new()),
881885
memoized_hash: Mutex::new(None),
@@ -922,6 +926,12 @@ impl Fingerprint {
922926
new: self.features.clone(),
923927
};
924928
}
929+
if self.declared_features != old.declared_features {
930+
return DirtyReason::DeclaredFeaturesChanged {
931+
old: old.declared_features.clone(),
932+
new: self.declared_features.clone(),
933+
};
934+
}
925935
if self.target != old.target {
926936
return DirtyReason::TargetConfigurationChanged;
927937
}
@@ -1200,6 +1210,7 @@ impl hash::Hash for Fingerprint {
12001210
let Fingerprint {
12011211
rustc,
12021212
ref features,
1213+
ref declared_features,
12031214
target,
12041215
path,
12051216
profile,
@@ -1215,6 +1226,7 @@ impl hash::Hash for Fingerprint {
12151226
(
12161227
rustc,
12171228
features,
1229+
declared_features,
12181230
target,
12191231
path,
12201232
profile,
@@ -1439,6 +1451,17 @@ fn calculate_normal(cx: &mut Context<'_, '_>, unit: &Unit) -> CargoResult<Finger
14391451
// actually affect the output artifact so there's no need to hash it.
14401452
path: util::hash_u64(path_args(cx.bcx.ws, unit).0),
14411453
features: format!("{:?}", unit.features),
1454+
// Note we curently only populate `declared_features` when `-Zcheck-cfg`
1455+
// is passed since it's the only user-facing toggle that will make this
1456+
// fingerprint relevant.
1457+
declared_features: if cx.bcx.config.cli_unstable().check_cfg {
1458+
format!(
1459+
"{:?}",
1460+
unit.pkg.summary().features().keys().collect::<Vec<_>>()
1461+
)
1462+
} else {
1463+
"".to_string()
1464+
},
14421465
deps,
14431466
local: Mutex::new(local),
14441467
memoized_hash: Mutex::new(None),

tests/testsuite/check_cfg.rs

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -141,6 +141,53 @@ fn features_with_namespaced_features() {
141141
.run();
142142
}
143143

144+
#[cargo_test(nightly, reason = "--check-cfg is unstable")]
145+
fn features_fingerprint() {
146+
let p = project()
147+
.file(
148+
"Cargo.toml",
149+
r#"
150+
[package]
151+
name = "foo"
152+
version = "0.1.0"
153+
154+
[features]
155+
f_a = []
156+
"#,
157+
)
158+
.file("src/main.rs", "fn main() {}")
159+
.build();
160+
161+
p.cargo("check -v -Zcheck-cfg")
162+
.masquerade_as_nightly_cargo(&["check-cfg"])
163+
.with_stderr_contains(x!("rustc" => "cfg" of "feature" with "f_a"))
164+
.run();
165+
166+
p.cargo("check -v -Zcheck-cfg")
167+
.masquerade_as_nightly_cargo(&["check-cfg"])
168+
.with_stderr_does_not_contain("rustc")
169+
.run();
170+
171+
p.change_file(
172+
"Cargo.toml",
173+
r#"
174+
[package]
175+
name = "foo"
176+
version = "0.1.0"
177+
178+
[features]
179+
f_a = []
180+
f_b = []
181+
"#,
182+
);
183+
184+
p.cargo("check -v -Zcheck-cfg")
185+
.masquerade_as_nightly_cargo(&["check-cfg"])
186+
.with_stderr_contains("[..]Dirty[..]the list of declared features changed")
187+
.with_stderr_contains(x!("rustc" => "cfg" of "feature" with "f_a" "f_b"))
188+
.run();
189+
}
190+
144191
#[cargo_test(nightly, reason = "--check-cfg is unstable")]
145192
fn well_known_names_values() {
146193
let p = project()

0 commit comments

Comments
 (0)