Skip to content

Commit 3797f29

Browse files
committed
[WIP] give better errors for broken intra doc links
1 parent 7d289ae commit 3797f29

10 files changed

+476
-94
lines changed

compiler/rustc_hir/src/def.rs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ use rustc_ast::NodeId;
66
use rustc_macros::HashStable_Generic;
77
use rustc_span::hygiene::MacroKind;
88

9+
use std::array::IntoIter;
910
use std::fmt::Debug;
1011

1112
/// Encodes if a `DefKind::Ctor` is the constructor of an enum variant or a struct.
@@ -291,6 +292,14 @@ impl<T> PerNS<T> {
291292
pub fn map<U, F: FnMut(T) -> U>(self, mut f: F) -> PerNS<U> {
292293
PerNS { value_ns: f(self.value_ns), type_ns: f(self.type_ns), macro_ns: f(self.macro_ns) }
293294
}
295+
296+
pub fn into_iter(self) -> IntoIter<T, 3> {
297+
IntoIter::new([self.value_ns, self.type_ns, self.macro_ns])
298+
}
299+
300+
pub fn iter(&self) -> IntoIter<&T, 3> {
301+
IntoIter::new([&self.value_ns, &self.type_ns, &self.macro_ns])
302+
}
294303
}
295304

296305
impl<T> ::std::ops::Index<Namespace> for PerNS<T> {

compiler/rustc_hir/src/lib.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
//!
33
//! [rustc dev guide]: https://rustc-dev-guide.rust-lang.org/hir.html
44
5+
#![feature(array_value_iter)]
56
#![feature(crate_visibility_modifier)]
67
#![feature(const_fn)] // For the unsizing cast on `&[]`
78
#![feature(const_panic)]

src/librustdoc/passes/collect_intra_doc_links.rs

Lines changed: 290 additions & 71 deletions
Large diffs are not rendered by default.

src/test/rustdoc-ui/deny-intra-link-resolution-failure.stderr

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,14 @@ error: unresolved link to `v2`
22
--> $DIR/deny-intra-link-resolution-failure.rs:3:6
33
|
44
LL | /// [v2]
5-
| ^^ unresolved link
5+
| ^^
66
|
77
note: the lint level is defined here
88
--> $DIR/deny-intra-link-resolution-failure.rs:1:9
99
|
1010
LL | #![deny(broken_intra_doc_links)]
1111
| ^^^^^^^^^^^^^^^^^^^^^^
12+
= note: no item named `v2` is in scope
1213
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
1314

1415
error: aborting due to previous error

src/test/rustdoc-ui/intra-doc-alias-ice.stderr

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,14 +2,15 @@ error: unresolved link to `TypeAlias::hoge`
22
--> $DIR/intra-doc-alias-ice.rs:5:30
33
|
44
LL | /// [broken cross-reference](TypeAlias::hoge)
5-
| ^^^^^^^^^^^^^^^ unresolved link
5+
| ^^^^^^^^^^^^^^^
66
|
77
note: the lint level is defined here
88
--> $DIR/intra-doc-alias-ice.rs:1:9
99
|
1010
LL | #![deny(broken_intra_doc_links)]
1111
| ^^^^^^^^^^^^^^^^^^^^^^
12-
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
12+
= note: this link partially resolves to the type alias `TypeAlias`,
13+
= note: `TypeAlias` has no field, variant, or associated item named `hoge`
1314

1415
error: aborting due to previous error
1516

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
#![deny(broken_intra_doc_links)]
2+
//~^ NOTE lint level is defined
3+
4+
//! [std::io::oops]
5+
//! [std::io::oops::not::here]
6+
7+
// FIXME: this should say that it was skipped (maybe an allowed by default lint?)
8+
/// [<invalid syntax>]
9+
10+
// FIXME: this could say which path was the first to not be found (in this case, `path`)
11+
/// [path::to::nonexistent::module]
12+
//~^ ERROR unresolved link
13+
//~| NOTE no item named `path::to::nonexistent` is in scope
14+
//~| HELP to escape
15+
16+
// TODO: why does this say `f` and not `f::A`??
17+
/// [f::A]
18+
//~^ ERROR unresolved link
19+
//~| NOTE no item named `f` is in scope
20+
//~| HELP to escape
21+
22+
/// [S::A]
23+
//~^ ERROR unresolved link
24+
//~| NOTE this link partially resolves
25+
//~| NOTE `S` has no field
26+
27+
/// [S::fmt]
28+
//~^ ERROR unresolved link
29+
//~| NOTE this link partially resolves
30+
//~| NOTE `S` has no field
31+
32+
/// [E::D]
33+
//~^ ERROR unresolved link
34+
//~| NOTE this link partially resolves
35+
//~| NOTE `E` has no field
36+
37+
/// [u8::not_found]
38+
//~^ ERROR unresolved link
39+
//~| NOTE the builtin type `u8` does not have an associated item named `not_found`
40+
41+
/// [S!]
42+
//~^ ERROR unresolved link
43+
//~| HELP to link to the unit struct, use its disambiguator
44+
//~| NOTE this link resolves to the unit struct `S`
45+
pub fn f() {}
46+
#[derive(Debug)]
47+
pub struct S;
48+
49+
pub enum E { A, B, C }
50+
51+
/// [type@S::h]
52+
impl S {
53+
pub fn h() {}
54+
}
55+
56+
/// [type@T::g]
57+
pub trait T {
58+
fn g() {}
59+
}
Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
error: unresolved link to `path::to::nonexistent::module`
2+
--> $DIR/intra-link-errors.rs:8:6
3+
|
4+
LL | /// [path::to::nonexistent::module]
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
6+
|
7+
note: the lint level is defined here
8+
--> $DIR/intra-link-errors.rs:1:9
9+
|
10+
LL | #![deny(broken_intra_doc_links)]
11+
| ^^^^^^^^^^^^^^^^^^^^^^
12+
= note: no item named `path::to::nonexistent` is in scope
13+
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
14+
15+
error: unresolved link to `f::A`
16+
--> $DIR/intra-link-errors.rs:14:6
17+
|
18+
LL | /// [f::A]
19+
| ^^^^
20+
|
21+
= note: no item named `f` is in scope
22+
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
23+
24+
error: unresolved link to `S::A`
25+
--> $DIR/intra-link-errors.rs:19:6
26+
|
27+
LL | /// [S::A]
28+
| ^^^^
29+
|
30+
= note: this link partially resolves to the struct `S`,
31+
= note: `S` has no field, variant, or associated item named `A`
32+
33+
error: unresolved link to `S::fmt`
34+
--> $DIR/intra-link-errors.rs:24:6
35+
|
36+
LL | /// [S::fmt]
37+
| ^^^^^^
38+
|
39+
= note: this link partially resolves to the struct `S`,
40+
= note: `S` has no field, variant, or associated item named `fmt`
41+
42+
error: unresolved link to `E::D`
43+
--> $DIR/intra-link-errors.rs:29:6
44+
|
45+
LL | /// [E::D]
46+
| ^^^^
47+
|
48+
= note: this link partially resolves to the enum `E`,
49+
= note: `E` has no field, variant, or associated item named `D`
50+
51+
error: unresolved link to `u8::not_found`
52+
--> $DIR/intra-link-errors.rs:34:6
53+
|
54+
LL | /// [u8::not_found]
55+
| ^^^^^^^^^^^^^
56+
|
57+
= note: the builtin type `u8` does not have an associated item named `not_found`
58+
59+
error: unresolved link to `S`
60+
--> $DIR/intra-link-errors.rs:38:6
61+
|
62+
LL | /// [S!]
63+
| ^^ help: to link to the unit struct, use its disambiguator: `value@S`
64+
|
65+
= note: this link resolves to the unit struct `S`, which is not in the value namespace
66+
67+
error: aborting due to 7 previous errors
68+

src/test/rustdoc-ui/intra-link-span-ice-55723.stderr

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,14 @@ error: unresolved link to `i`
22
--> $DIR/intra-link-span-ice-55723.rs:9:10
33
|
44
LL | /// (arr[i])
5-
| ^ unresolved link
5+
| ^
66
|
77
note: the lint level is defined here
88
--> $DIR/intra-link-span-ice-55723.rs:1:9
99
|
1010
LL | #![deny(broken_intra_doc_links)]
1111
| ^^^^^^^^^^^^^^^^^^^^^^
12+
= note: no item named `i` is in scope
1213
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
1314

1415
error: aborting due to previous error

src/test/rustdoc-ui/intra-links-warning-crlf.stderr

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,33 +2,37 @@ warning: unresolved link to `error`
22
--> $DIR/intra-links-warning-crlf.rs:7:6
33
|
44
LL | /// [error]
5-
| ^^^^^ unresolved link
5+
| ^^^^^
66
|
77
= note: `#[warn(broken_intra_doc_links)]` on by default
8+
= note: no item named `error` is in scope
89
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
910

1011
warning: unresolved link to `error1`
1112
--> $DIR/intra-links-warning-crlf.rs:12:11
1213
|
1314
LL | /// docs [error1]
14-
| ^^^^^^ unresolved link
15+
| ^^^^^^
1516
|
17+
= note: no item named `error1` is in scope
1618
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
1719

1820
warning: unresolved link to `error2`
1921
--> $DIR/intra-links-warning-crlf.rs:15:11
2022
|
2123
LL | /// docs [error2]
22-
| ^^^^^^ unresolved link
24+
| ^^^^^^
2325
|
26+
= note: no item named `error2` is in scope
2427
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
2528

2629
warning: unresolved link to `error`
2730
--> $DIR/intra-links-warning-crlf.rs:23:20
2831
|
2932
LL | * It also has an [error].
30-
| ^^^^^ unresolved link
33+
| ^^^^^
3134
|
35+
= note: no item named `error` is in scope
3236
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
3337

3438
warning: 4 warnings emitted

0 commit comments

Comments
 (0)