about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorDylan DPC <dylan.dpc@gmail.com>2021-06-23 00:20:21 +0200
committerGitHub <noreply@github.com>2021-06-23 00:20:21 +0200
commitf9ebf1edb51f257e73586d429800e3a1914b873a (patch)
treead3c893f44259ffc80f95607a224f134eece20aa /src
parent6023ac2c8d10661f7a4f405edf795d956c927620 (diff)
parentf387e8c207b47f0da4fcaa675460745ab325f3f8 (diff)
downloadrust-f9ebf1edb51f257e73586d429800e3a1914b873a.tar.gz
rust-f9ebf1edb51f257e73586d429800e3a1914b873a.zip
Rollup merge of #86523 - LeSeulArtichaut:macros-disambiguators, r=jyn514
Improvements to intra-doc link macro disambiguators

A few small improvements around macro disambiguators:
- display the link text as it was entered: previously `[macro!()]` would be displayed without the parantheses (fixes #86309)
- support `!{}` and `![]` as macro disambiguators (fixes #86310)

r? `@jyn514` cc `@Manishearth` `@camelid`
Diffstat (limited to 'src')
-rw-r--r--src/librustdoc/passes/collect_intra_doc_links.rs39
-rw-r--r--src/test/rustdoc/intra-doc/macros-disambiguators.rs25
2 files changed, 37 insertions, 27 deletions
diff --git a/src/librustdoc/passes/collect_intra_doc_links.rs b/src/librustdoc/passes/collect_intra_doc_links.rs
index fb82a075de0..c7e2ce74019 100644
--- a/src/librustdoc/passes/collect_intra_doc_links.rs
+++ b/src/librustdoc/passes/collect_intra_doc_links.rs
@@ -992,9 +992,9 @@ fn preprocess_link<'a>(
     }
 
     // Parse and strip the disambiguator from the link, if present.
-    let (path_str, disambiguator) = match Disambiguator::from_str(&link) {
-        Ok(Some((d, path))) => (path.trim(), Some(d)),
-        Ok(None) => (link.trim(), None),
+    let (disambiguator, path_str, link_text) = match Disambiguator::from_str(&link) {
+        Ok(Some((d, path, link_text))) => (Some(d), path.trim(), link_text.trim()),
+        Ok(None) => (None, link.trim(), link.trim()),
         Err((err_msg, relative_range)) => {
             // Only report error if we would not have ignored this link. See issue #83859.
             if !should_ignore_link_with_disambiguators(link) {
@@ -1012,11 +1012,6 @@ fn preprocess_link<'a>(
         return None;
     }
 
-    // We stripped `()` and `!` when parsing the disambiguator.
-    // Add them back to be displayed, but not prefix disambiguators.
-    let link_text =
-        disambiguator.map(|d| d.display_for(path_str)).unwrap_or_else(|| path_str.to_owned());
-
     // Strip generics from the path.
     let path_str = if path_str.contains(['<', '>'].as_slice()) {
         match strip_generics_from_path(&path_str) {
@@ -1046,7 +1041,7 @@ fn preprocess_link<'a>(
         path_str,
         disambiguator,
         extra_fragment: extra_fragment.map(String::from),
-        link_text,
+        link_text: link_text.to_owned(),
     }))
 }
 
@@ -1554,24 +1549,12 @@ enum Disambiguator {
 }
 
 impl Disambiguator {
-    /// The text that should be displayed when the path is rendered as HTML.
-    ///
-    /// NOTE: `path` is not the original link given by the user, but a name suitable for passing to `resolve`.
-    fn display_for(&self, path: &str) -> String {
-        match self {
-            // FIXME: this will have different output if the user had `m!()` originally.
-            Self::Kind(DefKind::Macro(MacroKind::Bang)) => format!("{}!", path),
-            Self::Kind(DefKind::Fn) => format!("{}()", path),
-            _ => path.to_owned(),
-        }
-    }
-
-    /// Given a link, parse and return `(disambiguator, path_str)`.
+    /// Given a link, parse and return `(disambiguator, path_str, link_text)`.
     ///
     /// This returns `Ok(Some(...))` if a disambiguator was found,
     /// `Ok(None)` if no disambiguator was found, or `Err(...)`
     /// if there was a problem with the disambiguator.
-    fn from_str(link: &str) -> Result<Option<(Self, &str)>, (String, Range<usize>)> {
+    fn from_str(link: &str) -> Result<Option<(Self, &str, &str)>, (String, Range<usize>)> {
         use Disambiguator::{Kind, Namespace as NS, Primitive};
 
         if let Some(idx) = link.find('@') {
@@ -1592,18 +1575,20 @@ impl Disambiguator {
                 "prim" | "primitive" => Primitive,
                 _ => return Err((format!("unknown disambiguator `{}`", prefix), 0..idx)),
             };
-            Ok(Some((d, &rest[1..])))
+            Ok(Some((d, &rest[1..], &rest[1..])))
         } else {
             let suffixes = [
                 ("!()", DefKind::Macro(MacroKind::Bang)),
+                ("!{}", DefKind::Macro(MacroKind::Bang)),
+                ("![]", DefKind::Macro(MacroKind::Bang)),
                 ("()", DefKind::Fn),
                 ("!", DefKind::Macro(MacroKind::Bang)),
             ];
             for (suffix, kind) in suffixes {
-                if let Some(link) = link.strip_suffix(suffix) {
+                if let Some(path_str) = link.strip_suffix(suffix) {
                     // Avoid turning `!` or `()` into an empty string
-                    if !link.is_empty() {
-                        return Ok(Some((Kind(kind), link)));
+                    if !path_str.is_empty() {
+                        return Ok(Some((Kind(kind), path_str, link)));
                     }
                 }
             }
diff --git a/src/test/rustdoc/intra-doc/macros-disambiguators.rs b/src/test/rustdoc/intra-doc/macros-disambiguators.rs
new file mode 100644
index 00000000000..cd4caa6a894
--- /dev/null
+++ b/src/test/rustdoc/intra-doc/macros-disambiguators.rs
@@ -0,0 +1,25 @@
+#![crate_name = "foo"]
+#![deny(rustdoc::broken_intra_doc_links)]
+
+//! [foo!()]
+// @has foo/index.html '//a[@href="macro.foo.html"]' 'foo!()'
+
+//! [foo!{}]
+// @has - '//a[@href="macro.foo.html"]' 'foo!{}'
+
+//! [foo![]](foo![])
+// @has - '//a[@href="macro.foo.html"]' 'foo![]'
+
+//! [foo1](foo!())
+// @has - '//a[@href="macro.foo.html"]' 'foo1'
+
+//! [foo2](foo!{})
+// @has - '//a[@href="macro.foo.html"]' 'foo2'
+
+//! [foo3](foo![])
+// @has - '//a[@href="macro.foo.html"]' 'foo3'
+
+#[macro_export]
+macro_rules! foo {
+    () => {};
+}