diff --git a/src/test/rustdoc-ui/cfg-rustdoc.rs b/src/test/rustdoc-ui/cfg-rustdoc.rs new file mode 100644 index 0000000000000..bf664ac51e6ed --- /dev/null +++ b/src/test/rustdoc-ui/cfg-rustdoc.rs @@ -0,0 +1,8 @@ +// check-pass + +#[cfg(doc)] +pub struct Foo; + +fn main() { + let f = Foo; +} diff --git a/src/test/rustdoc-ui/deny-invalid-doc-attrs.rs b/src/test/rustdoc-ui/deny-invalid-doc-attrs.rs new file mode 100644 index 0000000000000..02e9c67915f15 --- /dev/null +++ b/src/test/rustdoc-ui/deny-invalid-doc-attrs.rs @@ -0,0 +1,7 @@ +#![deny(invalid_doc_attributes)] +//~^ NOTE defined here +#![doc(x)] +//~^ ERROR unknown `doc` attribute `x` +//~| WARNING will become a hard error +//~| NOTE see issue #82730 +fn main() {} diff --git a/src/test/rustdoc-ui/deny-invalid-doc-attrs.stderr b/src/test/rustdoc-ui/deny-invalid-doc-attrs.stderr new file mode 100644 index 0000000000000..a14ab8fe4bc04 --- /dev/null +++ b/src/test/rustdoc-ui/deny-invalid-doc-attrs.stderr @@ -0,0 +1,16 @@ +error: unknown `doc` attribute `x` + --> $DIR/deny-invalid-doc-attrs.rs:3:8 + | +LL | #![doc(x)] + | ^ + | +note: the lint level is defined here + --> $DIR/deny-invalid-doc-attrs.rs:1:9 + | +LL | #![deny(invalid_doc_attributes)] + | ^^^^^^^^^^^^^^^^^^^^^^ + = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! + = note: for more information, see issue #82730 + +error: aborting due to previous error + diff --git a/src/test/rustdoc-ui/doc-inline-extern-crate.rs b/src/test/rustdoc-ui/doc-inline-extern-crate.rs new file mode 100644 index 0000000000000..0eb4c149060db --- /dev/null +++ b/src/test/rustdoc-ui/doc-inline-extern-crate.rs @@ -0,0 +1,9 @@ +#[doc(inline)] +//~^ ERROR conflicting +#[doc(no_inline)] +pub extern crate core; + +// no warning +pub extern crate alloc; + +fn main() {} diff --git a/src/test/rustdoc-ui/doc-inline-extern-crate.stderr b/src/test/rustdoc-ui/doc-inline-extern-crate.stderr new file mode 100644 index 0000000000000..41518295b1224 --- /dev/null +++ b/src/test/rustdoc-ui/doc-inline-extern-crate.stderr @@ -0,0 +1,13 @@ +error: conflicting doc inlining attributes + --> $DIR/doc-inline-extern-crate.rs:1:7 + | +LL | #[doc(inline)] + | ^^^^^^ this attribute... +LL | +LL | #[doc(no_inline)] + | ^^^^^^^^^ ...conflicts with this attribute + | + = help: remove one of the conflicting attributes + +error: aborting due to previous error + diff --git a/src/test/rustdoc-ui/doc_keyword.rs b/src/test/rustdoc-ui/doc_keyword.rs new file mode 100644 index 0000000000000..4518f77ef933d --- /dev/null +++ b/src/test/rustdoc-ui/doc_keyword.rs @@ -0,0 +1,20 @@ +#![crate_type = "lib"] +#![feature(doc_keyword)] + +#![doc(keyword = "hello")] //~ ERROR + +#[doc(keyword = "hell")] //~ ERROR +mod foo { + fn hell() {} +} + +#[doc(keyword = "hall")] //~ ERROR +fn foo() {} + + +// Regression test for the ICE described in #83512. +trait Foo { + #[doc(keyword = "match")] + //~^ ERROR: `#[doc(keyword = "...")]` can only be used on modules + fn quux() {} +} diff --git a/src/test/rustdoc-ui/doc_keyword.stderr b/src/test/rustdoc-ui/doc_keyword.stderr new file mode 100644 index 0000000000000..6ba7034d54122 --- /dev/null +++ b/src/test/rustdoc-ui/doc_keyword.stderr @@ -0,0 +1,26 @@ +error: `#[doc(keyword = "...")]` can only be used on empty modules + --> $DIR/doc_keyword.rs:6:7 + | +LL | #[doc(keyword = "hell")] + | ^^^^^^^^^^^^^^^^ + +error: `#[doc(keyword = "...")]` can only be used on modules + --> $DIR/doc_keyword.rs:11:7 + | +LL | #[doc(keyword = "hall")] + | ^^^^^^^^^^^^^^^^ + +error: `#[doc(keyword = "...")]` can only be used on modules + --> $DIR/doc_keyword.rs:17:11 + | +LL | #[doc(keyword = "match")] + | ^^^^^^^^^^^^^^^^^ + +error: `#![doc(keyword = "...")]` isn't allowed as a crate-level attribute + --> $DIR/doc_keyword.rs:4:8 + | +LL | #![doc(keyword = "hello")] + | ^^^^^^^^^^^^^^^^^ + +error: aborting due to 4 previous errors + diff --git a/src/test/rustdoc-ui/unterminated-doc-comment.rs b/src/test/rustdoc-ui/unterminated-doc-comment.rs new file mode 100644 index 0000000000000..82546fe73da4f --- /dev/null +++ b/src/test/rustdoc-ui/unterminated-doc-comment.rs @@ -0,0 +1 @@ +/*! //~ ERROR E0758 diff --git a/src/test/rustdoc-ui/unterminated-doc-comment.stderr b/src/test/rustdoc-ui/unterminated-doc-comment.stderr new file mode 100644 index 0000000000000..2d5e537973ea8 --- /dev/null +++ b/src/test/rustdoc-ui/unterminated-doc-comment.stderr @@ -0,0 +1,9 @@ +error[E0758]: unterminated block doc-comment + --> $DIR/unterminated-doc-comment.rs:1:1 + | +LL | /*! + | ^^^^^^^^^^^^^^^^^^^^ + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0758`. diff --git a/src/tools/tidy/src/lib.rs b/src/tools/tidy/src/lib.rs index a1c41eb99810e..7363a5056c545 100644 --- a/src/tools/tidy/src/lib.rs +++ b/src/tools/tidy/src/lib.rs @@ -46,6 +46,7 @@ pub mod errors; pub mod extdeps; pub mod features; pub mod pal; +pub mod rustdoc_ui_test_parity; pub mod style; pub mod target_specific_tests; pub mod ui_tests; diff --git a/src/tools/tidy/src/main.rs b/src/tools/tidy/src/main.rs index 440c352ea5320..70bfde9f78300 100644 --- a/src/tools/tidy/src/main.rs +++ b/src/tools/tidy/src/main.rs @@ -64,6 +64,7 @@ fn main() { // Checks over tests. check!(debug_artifacts, &src_path); check!(ui_tests, &src_path); + check!(rustdoc_ui_test_parity, &src_path); // Checks that only make sense for the compiler. check!(errors, &compiler_path); diff --git a/src/tools/tidy/src/rustdoc_ui_test_parity.rs b/src/tools/tidy/src/rustdoc_ui_test_parity.rs new file mode 100644 index 0000000000000..4c7a7538f923b --- /dev/null +++ b/src/tools/tidy/src/rustdoc_ui_test_parity.rs @@ -0,0 +1,37 @@ +//! Tidy check to ensure that `src/test/ui/rustdoc` tests are all present in `src/test/rustdoc-ui`. + +use std::collections::HashSet; +use std::path::Path; + +pub fn check(path: &Path, bad: &mut bool) { + let rustdoc_ui_folder = "src/test/rustdoc-ui"; + let ui_rustdoc_folder = "src/test/ui/rustdoc"; + let mut rustdoc_ui_tests = HashSet::new(); + super::walk_no_read(&path.join("test/rustdoc-ui"), &mut |_| false, &mut |entry| { + let file_path = entry.path(); + if let Some(ext) = file_path.extension() { + if ext == "rs" { + let testname = file_path.file_name().unwrap().to_str().unwrap().to_owned(); + rustdoc_ui_tests.insert(testname); + } + } + }); + super::walk_no_read(&path.join("test/ui/rustdoc"), &mut |_| false, &mut |entry| { + let file_path = entry.path(); + if let Some(ext) = file_path.extension() { + if ext == "rs" { + let testname = file_path.file_name().unwrap().to_str().unwrap().to_owned(); + if !rustdoc_ui_tests.contains(&testname) { + tidy_error!( + bad, + "{}", + &format!( + "`{}/{}` is missing from `{}`", + ui_rustdoc_folder, testname, rustdoc_ui_folder, + ), + ); + } + } + } + }); +}