]> git.proxmox.com Git - cargo.git/commitdiff
Add -Z check-cfg-features support for rustdoc
authorLoïc BRANSTETT <lolo.branstett@numericable.fr>
Fri, 25 Feb 2022 14:59:39 +0000 (15:59 +0100)
committerLoïc BRANSTETT <lolo.branstett@numericable.fr>
Sat, 26 Feb 2022 13:10:17 +0000 (14:10 +0100)
src/cargo/core/compiler/context/mod.rs
src/cargo/core/compiler/mod.rs
src/doc/src/reference/unstable.md
tests/testsuite/doc.rs
tests/testsuite/test.rs

index 872a4d5446020ab210bfe227d98b60acb36b6814..7efe77ef91f071509a20bc19b8aa8c88faa40db0 100644 (file)
@@ -224,11 +224,8 @@ impl<'a, 'cfg> Context<'a, 'cfg> {
                 let mut unstable_opts = false;
                 let mut args = compiler::extern_args(&self, unit, &mut unstable_opts)?;
                 args.extend(compiler::lto_args(&self, unit));
+                args.extend(compiler::features_args(&self, unit));
 
-                for feature in &unit.features {
-                    args.push("--cfg".into());
-                    args.push(format!("feature=\"{}\"", feature).into());
-                }
                 let script_meta = self.find_build_script_metadata(unit);
                 if let Some(meta) = script_meta {
                     if let Some(output) = self.build_script_outputs.lock().unwrap().get(meta) {
index 750981c95282392756d22ad5afe2da025a9d150b..14916f1e59183e0d6bad8d513aac71d8c8e02d2f 100644 (file)
@@ -645,10 +645,7 @@ fn rustdoc(cx: &mut Context<'_, '_>, unit: &Unit) -> CargoResult<Work> {
     paths::create_dir_all(&doc_dir)?;
 
     rustdoc.arg("-o").arg(&doc_dir);
-
-    for feat in &unit.features {
-        rustdoc.arg("--cfg").arg(&format!("feature=\"{}\"", feat));
-    }
+    rustdoc.args(&features_args(cx, unit));
 
     add_error_format_and_color(cx, &mut rustdoc, unit);
     add_allow_features(cx, &mut rustdoc);
@@ -791,28 +788,6 @@ fn add_allow_features(cx: &Context<'_, '_>, cmd: &mut ProcessBuilder) {
     }
 }
 
-/// Add all features as cfg
-fn add_features(cx: &Context<'_, '_>, cmd: &mut ProcessBuilder, unit: &Unit) {
-    for feat in &unit.features {
-        cmd.arg("--cfg").arg(&format!("feature=\"{}\"", feat));
-    }
-
-    if cx.bcx.config.cli_unstable().check_cfg_features {
-        // This generate something like this:
-        //  - values(feature)
-        //  - values(feature, "foo", "bar")
-        let mut arg = String::from("values(feature");
-        for (&feat, _) in unit.pkg.summary().features() {
-            arg.push_str(", \"");
-            arg.push_str(&feat);
-            arg.push_str("\"");
-        }
-        arg.push(')');
-
-        cmd.arg("-Zunstable-options").arg("--check-cfg").arg(&arg);
-    }
-}
-
 /// Add error-format flags to the command.
 ///
 /// Cargo always uses JSON output. This has several benefits, such as being
@@ -1009,7 +984,7 @@ fn build_base_args(
         cmd.arg("--cfg").arg("test");
     }
 
-    add_features(cx, cmd, unit);
+    cmd.args(&features_args(cx, unit));
 
     let meta = cx.files().metadata(unit);
     cmd.arg("-C").arg(&format!("metadata={}", meta));
@@ -1083,6 +1058,35 @@ fn build_base_args(
     Ok(())
 }
 
+/// Features with --cfg and all features with --check-cfg
+fn features_args(cx: &Context<'_, '_>, unit: &Unit) -> Vec<OsString> {
+    let mut args = Vec::with_capacity(unit.features.len() + 2);
+
+    for feat in &unit.features {
+        args.push(OsString::from("--cfg"));
+        args.push(OsString::from(format!("feature=\"{}\"", feat)));
+    }
+
+    if cx.bcx.config.cli_unstable().check_cfg_features {
+        // This generate something like this:
+        //  - values(feature)
+        //  - values(feature, "foo", "bar")
+        let mut arg = OsString::from("values(feature");
+        for (&feat, _) in unit.pkg.summary().features() {
+            arg.push(", \"");
+            arg.push(&feat);
+            arg.push("\"");
+        }
+        arg.push(")");
+
+        args.push(OsString::from("-Zunstable-options"));
+        args.push(OsString::from("--check-cfg"));
+        args.push(arg);
+    }
+
+    args
+}
+
 fn lto_args(cx: &Context<'_, '_>, unit: &Unit) -> Vec<OsString> {
     let mut result = Vec::new();
     let mut push = |arg: &str| {
index 6de7da901009fde4b05d5055433eba99d30fafab..aa439016f1452d75d37c6c55221e1b4b5d4ee546 100644 (file)
@@ -1132,9 +1132,9 @@ cargo doc -Z unstable-options -Z rustdoc-scrape-examples=examples
 * RFC: [#3013](https://github.com/rust-lang/rfcs/pull/3013)
 
 The `-Z check-cfg-features` argument tells Cargo to pass all possible features of a package to
-`rustc` unstable `--check-cfg` command line as `--check-cfg=values(feature, ...)`. This enables
-compile time checking of feature values in `#[cfg]`, `cfg!` and `#[cfg_attr]`. Note than this
-command line options will probably become the default when stabilizing.
+`rustc` and `rustdoc` unstable `--check-cfg` command line as `--check-cfg=values(feature, ...)`.
+This enables compile time checking of feature values in `#[cfg]`, `cfg!` and `#[cfg_attr]`.
+Note than this command line options will probably become the default when stabilizing.
 For instance:
 
 ```
index 1e069c85f0bf1737ac0277a3e97dff593adc5e0f..917981d49493349aabf9247fbc636ffdb8feae0d 100644 (file)
@@ -2697,3 +2697,40 @@ fn doc_lib_false_dep() {
     assert!(p.build_dir().join("doc/foo").exists());
     assert!(!p.build_dir().join("doc/bar").exists());
 }
+
+#[cfg_attr(windows, ignore)] // weird normalization issue with windows and cargo-test-support
+#[cargo_test]
+fn doc_check_cfg_features() {
+    if !is_nightly() {
+        // --check-cfg is a nightly only rustdoc command line
+        return;
+    }
+
+    let p = project()
+        .file(
+            "Cargo.toml",
+            r#"
+                [project]
+                name = "foo"
+                version = "0.1.0"
+
+                [features]
+                default = ["f_a"]
+                f_a = []
+                f_b = []
+            "#,
+        )
+        .file("src/lib.rs", "#[allow(dead_code)] fn foo() {}")
+        .build();
+
+    p.cargo("doc -v -Z check-cfg-features")
+        .masquerade_as_nightly_cargo()
+        .with_stderr(
+            "\
+[DOCUMENTING] foo v0.1.0 [..]
+[RUNNING] `rustdoc [..] --check-cfg 'values(feature, \"default\", \"f_a\", \"f_b\")' [..]
+[FINISHED] [..]
+",
+        )
+        .run();
+}
index b8cebb9cd13533345b3348f70df24ef4a40708ca..cdb2a914304b88357909c1048fbe5edd99a21940 100644 (file)
@@ -4536,3 +4536,42 @@ fn check_cfg_features() {
         )
         .run();
 }
+
+#[cfg_attr(windows, ignore)] // weird normalization issue with windows and cargo-test-support
+#[cargo_test]
+fn check_cfg_features_doc() {
+    if !is_nightly() {
+        // --check-cfg is a nightly only rustc and rustdoc command line
+        return;
+    }
+
+    let p = project()
+        .file(
+            "Cargo.toml",
+            r#"
+                [project]
+                name = "foo"
+                version = "0.1.0"
+
+                [features]
+                default = ["f_a"]
+                f_a = []
+                f_b = []
+            "#,
+        )
+        .file("src/lib.rs", "#[allow(dead_code)] fn foo() {}")
+        .build();
+
+    p.cargo("test -v --doc -Z check-cfg-features")
+        .masquerade_as_nightly_cargo()
+        .with_stderr(
+            "\
+[COMPILING] foo v0.1.0 [..]
+[RUNNING] `rustc [..] --check-cfg 'values(feature, \"default\", \"f_a\", \"f_b\")' [..]
+[FINISHED] test [unoptimized + debuginfo] target(s) in [..]
+[DOCTEST] foo
+[RUNNING] `rustdoc [..] --check-cfg 'values(feature, \"default\", \"f_a\", \"f_b\")' [..]
+",
+        )
+        .run();
+}