Skip to content

Commit

Permalink
Fix an accidental raw access of field
Browse files Browse the repository at this point in the history
The manifest has a few different ways of specifying whether a crate is a
procedural macro, and there's a `TomlTarget::proc_macro()` method to
unify these various lines. Unfortunately though we had a bug where one
location forgot to call the method and read the raw field! This led to
surprising behavior where the different ways to specify a proc macro
would have subtly different changes in behavior. The fix here in this PR
is to ensure that we access the property always via the method.

Closes #8315
  • Loading branch information
alexcrichton committed Jun 3, 2020
1 parent 0e8a8df commit 442f629
Show file tree
Hide file tree
Showing 3 changed files with 73 additions and 4 deletions.
6 changes: 3 additions & 3 deletions src/cargo/util/toml/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1767,9 +1767,9 @@ struct TomlTarget {
doc: Option<bool>,
plugin: Option<bool>,
#[serde(rename = "proc-macro")]
proc_macro: Option<bool>,
proc_macro_raw: Option<bool>,
#[serde(rename = "proc_macro")]
proc_macro2: Option<bool>,
proc_macro_raw2: Option<bool>,
harness: Option<bool>,
#[serde(rename = "required-features")]
required_features: Option<Vec<String>>,
Expand Down Expand Up @@ -1824,7 +1824,7 @@ impl TomlTarget {
}

fn proc_macro(&self) -> Option<bool> {
self.proc_macro.or(self.proc_macro2).or_else(|| {
self.proc_macro_raw.or(self.proc_macro_raw2).or_else(|| {
if let Some(types) = self.crate_types() {
if types.contains(&"proc-macro".to_string()) {
return Some(true);
Expand Down
2 changes: 1 addition & 1 deletion src/cargo/util/toml/targets.rs
Original file line number Diff line number Diff line change
Expand Up @@ -774,7 +774,7 @@ fn configure(features: &Features, toml: &TomlTarget, target: &mut Target) -> Car
.set_doctest(toml.doctest.unwrap_or_else(|| t2.doctested()))
.set_benched(toml.bench.unwrap_or_else(|| t2.benched()))
.set_harness(toml.harness.unwrap_or_else(|| t2.harness()))
.set_proc_macro(toml.proc_macro.unwrap_or_else(|| t2.proc_macro()))
.set_proc_macro(toml.proc_macro().unwrap_or_else(|| t2.proc_macro()))
.set_for_host(match (toml.plugin, toml.proc_macro()) {
(None, None) => t2.for_host(),
(Some(true), _) | (_, Some(true)) => true,
Expand Down
69 changes: 69 additions & 0 deletions tests/testsuite/proc_macro.rs
Original file line number Diff line number Diff line change
Expand Up @@ -470,3 +470,72 @@ fn proc_macro_extern_prelude() {
p.cargo("test").run();
p.cargo("doc").run();
}

#[cargo_test]
fn proc_macro_built_once() {
let p = project()
.file(
"Cargo.toml",
r#"
[workspace]
members = ['a', 'b']
"#,
)
.file(
"a/Cargo.toml",
r#"
[package]
name = "a"
version = "0.1.0"
[build-dependencies]
the-macro = { path = '../the-macro' }
"#,
)
.file("a/build.rs", "fn main() {}")
.file("a/src/main.rs", "fn main() {}")
.file(
"b/Cargo.toml",
r#"
[package]
name = "b"
version = "0.1.0"
[dependencies]
the-macro = { path = '../the-macro', features = ['a'] }
"#,
)
.file("b/src/main.rs", "fn main() {}")
.file(
"the-macro/Cargo.toml",
r#"
[package]
name = "the-macro"
version = "0.1.0"
[lib]
proc_macro = true
[features]
a = []
"#,
)
.file("the-macro/src/lib.rs", "")
.build();
p.cargo("build -Zfeatures=all --verbose")
.masquerade_as_nightly_cargo()
.with_stderr_unordered(
"\
[COMPILING] the-macro [..]
[RUNNING] `rustc --crate-name the_macro [..]`
[COMPILING] b [..]
[RUNNING] `rustc --crate-name b [..]`
[COMPILING] a [..]
[RUNNING] `rustc --crate-name build_script_build [..]`
[RUNNING] `[..]build[..]script[..]build[..]`
[RUNNING] `rustc --crate-name a [..]`
[FINISHED] [..]
",
)
.run();
}

0 comments on commit 442f629

Please sign in to comment.