From 84cb71c6fac5f1356fb981afdd791a11bde5ce22 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Wed, 16 Sep 2020 16:41:45 +0200 Subject: [PATCH 1/4] Forbid some characters to be used as doc alias --- compiler/rustc_passes/src/check_attr.rs | 34 ++++++++++++++++++++----- 1 file changed, 27 insertions(+), 7 deletions(-) diff --git a/compiler/rustc_passes/src/check_attr.rs b/compiler/rustc_passes/src/check_attr.rs index efe947daa2866..852310ab1221c 100644 --- a/compiler/rustc_passes/src/check_attr.rs +++ b/compiler/rustc_passes/src/check_attr.rs @@ -252,23 +252,42 @@ impl CheckAttrVisitor<'tcx> { } } + fn doc_alias_str_error(&self, meta: &NestedMetaItem) { + self.tcx + .sess + .struct_span_err( + meta.span(), + "doc alias attribute expects a string: #[doc(alias = \"0\")]", + ) + .emit(); + } + fn check_doc_alias(&self, attr: &Attribute, hir_id: HirId, target: Target) -> bool { if let Some(mi) = attr.meta() { if let Some(list) = mi.meta_item_list() { for meta in list { if meta.has_name(sym::alias) { - if !meta.is_value_str() - || meta - .value_str() - .map(|s| s.to_string()) - .unwrap_or_else(String::new) - .is_empty() + if !meta.is_value_str() { + self.doc_alias_str_error(meta); + return false; + } + let doc_alias = + meta.value_str().map(|s| s.to_string()).unwrap_or_else(String::new); + if doc_alias.is_empty() { + self.doc_alias_str_error(meta); + return false; + } + if let Some(c) = + doc_alias.chars().find(|&c| c == '"' || c == '\'' || c.is_whitespace()) { self.tcx .sess .struct_span_err( meta.span(), - "doc alias attribute expects a string: #[doc(alias = \"0\")]", + &format!( + "{:?} character isn't allowed in `#[doc(alias = \"...\")]`", + c, + ), ) .emit(); return false; @@ -304,6 +323,7 @@ impl CheckAttrVisitor<'tcx> { &format!("`#[doc(alias = \"...\")]` isn't allowed on {}", err), ) .emit(); + return false; } } } From fe415ff4125a3abd87d44c36526ddcd68b804f55 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Thu, 17 Sep 2020 00:20:14 +0200 Subject: [PATCH 2/4] Remove unneeded replace --- src/librustdoc/clean/types.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/librustdoc/clean/types.rs b/src/librustdoc/clean/types.rs index 223fda84871e9..8fbfb04bac3e4 100644 --- a/src/librustdoc/clean/types.rs +++ b/src/librustdoc/clean/types.rs @@ -695,7 +695,7 @@ impl Attributes { self.other_attrs .lists(sym::doc) .filter(|a| a.has_name(sym::alias)) - .filter_map(|a| a.value_str().map(|s| s.to_string().replace("\"", ""))) + .filter_map(|a| a.value_str().map(|s| s.to_string())) .filter(|v| !v.is_empty()) .collect::>() } From 414aecb13efe13e2a163cc08e07fdaed3a407ae7 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Wed, 16 Sep 2020 16:42:06 +0200 Subject: [PATCH 3/4] Update tests --- src/test/rustdoc-ui/check-doc-alias-attr.rs | 6 ++++ .../rustdoc-ui/check-doc-alias-attr.stderr | 34 ++++++++++++++++++- src/test/ui/check-doc-alias-attr.rs | 6 ++++ src/test/ui/check-doc-alias-attr.stderr | 34 ++++++++++++++++++- 4 files changed, 78 insertions(+), 2 deletions(-) diff --git a/src/test/rustdoc-ui/check-doc-alias-attr.rs b/src/test/rustdoc-ui/check-doc-alias-attr.rs index b02cc1a4545b1..c8bec39fad613 100644 --- a/src/test/rustdoc-ui/check-doc-alias-attr.rs +++ b/src/test/rustdoc-ui/check-doc-alias-attr.rs @@ -7,4 +7,10 @@ pub struct Bar; #[doc(alias)] //~ ERROR #[doc(alias = 0)] //~ ERROR #[doc(alias("bar"))] //~ ERROR +#[doc(alias = "\"")] //~ ERROR +#[doc(alias = "\n")] //~ ERROR +#[doc(alias = " +")] //~^ ERROR +#[doc(alias = " ")] //~ ERROR +#[doc(alias = "\t")] //~ ERROR pub struct Foo; diff --git a/src/test/rustdoc-ui/check-doc-alias-attr.stderr b/src/test/rustdoc-ui/check-doc-alias-attr.stderr index 268230ab44a0a..be7d7b3dbea93 100644 --- a/src/test/rustdoc-ui/check-doc-alias-attr.stderr +++ b/src/test/rustdoc-ui/check-doc-alias-attr.stderr @@ -16,5 +16,37 @@ error: doc alias attribute expects a string: #[doc(alias = "0")] LL | #[doc(alias("bar"))] | ^^^^^^^^^^^^ -error: aborting due to 3 previous errors +error: '\"' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:10:7 + | +LL | #[doc(alias = "\"")] + | ^^^^^^^^^^^^ + +error: '\n' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:11:7 + | +LL | #[doc(alias = "\n")] + | ^^^^^^^^^^^^ + +error: '\n' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:12:7 + | +LL | #[doc(alias = " + | _______^ +LL | | ")] + | |_^ + +error: ' ' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:14:7 + | +LL | #[doc(alias = " ")] + | ^^^^^^^^^^^ + +error: '\t' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:15:7 + | +LL | #[doc(alias = "\t")] + | ^^^^^^^^^^^^ + +error: aborting due to 8 previous errors diff --git a/src/test/ui/check-doc-alias-attr.rs b/src/test/ui/check-doc-alias-attr.rs index b02cc1a4545b1..c8bec39fad613 100644 --- a/src/test/ui/check-doc-alias-attr.rs +++ b/src/test/ui/check-doc-alias-attr.rs @@ -7,4 +7,10 @@ pub struct Bar; #[doc(alias)] //~ ERROR #[doc(alias = 0)] //~ ERROR #[doc(alias("bar"))] //~ ERROR +#[doc(alias = "\"")] //~ ERROR +#[doc(alias = "\n")] //~ ERROR +#[doc(alias = " +")] //~^ ERROR +#[doc(alias = " ")] //~ ERROR +#[doc(alias = "\t")] //~ ERROR pub struct Foo; diff --git a/src/test/ui/check-doc-alias-attr.stderr b/src/test/ui/check-doc-alias-attr.stderr index 268230ab44a0a..be7d7b3dbea93 100644 --- a/src/test/ui/check-doc-alias-attr.stderr +++ b/src/test/ui/check-doc-alias-attr.stderr @@ -16,5 +16,37 @@ error: doc alias attribute expects a string: #[doc(alias = "0")] LL | #[doc(alias("bar"))] | ^^^^^^^^^^^^ -error: aborting due to 3 previous errors +error: '\"' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:10:7 + | +LL | #[doc(alias = "\"")] + | ^^^^^^^^^^^^ + +error: '\n' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:11:7 + | +LL | #[doc(alias = "\n")] + | ^^^^^^^^^^^^ + +error: '\n' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:12:7 + | +LL | #[doc(alias = " + | _______^ +LL | | ")] + | |_^ + +error: ' ' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:14:7 + | +LL | #[doc(alias = " ")] + | ^^^^^^^^^^^ + +error: '\t' character isn't allowed in `#[doc(alias = "...")]` + --> $DIR/check-doc-alias-attr.rs:15:7 + | +LL | #[doc(alias = "\t")] + | ^^^^^^^^^^^^ + +error: aborting due to 8 previous errors From 4427b2d52c42d3eb7a7aecddcbbeff59ce613ab1 Mon Sep 17 00:00:00 2001 From: Guillaume Gomez Date: Wed, 16 Sep 2020 16:43:22 +0200 Subject: [PATCH 4/4] Update doc alias documentation --- src/doc/rustdoc/src/advanced-features.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/doc/rustdoc/src/advanced-features.md b/src/doc/rustdoc/src/advanced-features.md index c9a0dff5ab303..8c7926f116b71 100644 --- a/src/doc/rustdoc/src/advanced-features.md +++ b/src/doc/rustdoc/src/advanced-features.md @@ -46,3 +46,5 @@ pub struct BigX; Then, when looking for it through the `rustdoc` search, if you enter "x" or "big", search will show the `BigX` struct first. + +There are some limitations on the doc alias names though: you can't use `"` or whitespace.