Skip to content

Commit 8dddaed

Browse files
committed
mbe::transcribe: defatalize errors.
1 parent 576c7c9 commit 8dddaed

File tree

9 files changed

+68
-37
lines changed

9 files changed

+68
-37
lines changed

src/librustc_expand/base.rs

Lines changed: 0 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1011,22 +1011,6 @@ impl<'a> ExtCtxt<'a> {
10111011
self.parse_sess.span_diagnostic.struct_span_err(sp, msg)
10121012
}
10131013

1014-
/// Emit `msg` attached to `sp`, and stop compilation immediately.
1015-
///
1016-
/// `span_err` should be strongly preferred where-ever possible:
1017-
/// this should *only* be used when:
1018-
///
1019-
/// - continuing has a high risk of flow-on errors (e.g., errors in
1020-
/// declaring a macro would cause all uses of that macro to
1021-
/// complain about "undefined macro"), or
1022-
/// - there is literally nothing else that can be done (however,
1023-
/// in most cases one can construct a dummy expression/item to
1024-
/// substitute; we never hit resolve/type-checking so the dummy
1025-
/// value doesn't have to match anything)
1026-
pub fn span_fatal<S: Into<MultiSpan>>(&self, sp: S, msg: &str) -> ! {
1027-
self.parse_sess.span_diagnostic.span_fatal(sp, msg).raise();
1028-
}
1029-
10301014
/// Emit `msg` attached to `sp`, without immediately stopping
10311015
/// compilation.
10321016
///

src/librustc_expand/mbe/macro_rules.rs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -255,7 +255,13 @@ fn generic_extension<'cx>(
255255

256256
let rhs_spans = rhs.iter().map(|t| t.span()).collect::<Vec<_>>();
257257
// rhs has holes ( `$id` and `$(...)` that need filled)
258-
let mut tts = transcribe(cx, &named_matches, rhs, transparency);
258+
let mut tts = match transcribe(cx, &named_matches, rhs, transparency) {
259+
Ok(tts) => tts,
260+
Err(mut err) => {
261+
err.emit();
262+
return DummyResult::any(arm_span);
263+
}
264+
};
259265

260266
// Replace all the tokens for the corresponding positions in the macro, to maintain
261267
// proper positions in error reporting, while maintaining the macro_backtrace.

src/librustc_expand/mbe/transcribe.rs

Lines changed: 15 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ use rustc_ast::token::{self, NtTT, Token};
88
use rustc_ast::tokenstream::{DelimSpan, TokenStream, TokenTree, TreeAndJoint};
99
use rustc_data_structures::fx::FxHashMap;
1010
use rustc_data_structures::sync::Lrc;
11-
use rustc_errors::pluralize;
11+
use rustc_errors::{pluralize, PResult};
1212
use rustc_span::hygiene::{ExpnId, Transparency};
1313
use rustc_span::symbol::MacroRulesNormalizedIdent;
1414
use rustc_span::Span;
@@ -80,15 +80,15 @@ impl Iterator for Frame {
8080
/// `transcribe` would return a `TokenStream` containing `println!("{}", stringify!(bar));`.
8181
///
8282
/// Along the way, we do some additional error checking.
83-
pub(super) fn transcribe(
84-
cx: &ExtCtxt<'_>,
83+
pub(super) fn transcribe<'a>(
84+
cx: &ExtCtxt<'a>,
8585
interp: &FxHashMap<MacroRulesNormalizedIdent, NamedMatch>,
8686
src: Vec<mbe::TokenTree>,
8787
transparency: Transparency,
88-
) -> TokenStream {
88+
) -> PResult<'a, TokenStream> {
8989
// Nothing for us to transcribe...
9090
if src.is_empty() {
91-
return TokenStream::default();
91+
return Ok(TokenStream::default());
9292
}
9393

9494
// We descend into the RHS (`src`), expanding things as we go. This stack contains the things
@@ -152,7 +152,7 @@ pub(super) fn transcribe(
152152
Frame::Delimited { forest, span, .. } => {
153153
if result_stack.is_empty() {
154154
// No results left to compute! We are back at the top-level.
155-
return TokenStream::new(result);
155+
return Ok(TokenStream::new(result));
156156
}
157157

158158
// Step back into the parent Delimited.
@@ -173,19 +173,19 @@ pub(super) fn transcribe(
173173
seq @ mbe::TokenTree::Sequence(..) => {
174174
match lockstep_iter_size(&seq, interp, &repeats) {
175175
LockstepIterSize::Unconstrained => {
176-
cx.span_fatal(
176+
return Err(cx.struct_span_err(
177177
seq.span(), /* blame macro writer */
178178
"attempted to repeat an expression containing no syntax variables \
179179
matched as repeating at this depth",
180-
);
180+
));
181181
}
182182

183183
LockstepIterSize::Contradiction(ref msg) => {
184184
// FIXME: this really ought to be caught at macro definition time... It
185185
// happens when two meta-variables are used in the same repetition in a
186186
// sequence, but they come from different sequence matchers and repeat
187187
// different amounts.
188-
cx.span_fatal(seq.span(), &msg[..]);
188+
return Err(cx.struct_span_err(seq.span(), &msg[..]));
189189
}
190190

191191
LockstepIterSize::Constraint(len, _) => {
@@ -203,7 +203,10 @@ pub(super) fn transcribe(
203203
// FIXME: this really ought to be caught at macro definition
204204
// time... It happens when the Kleene operator in the matcher and
205205
// the body for the same meta-variable do not match.
206-
cx.span_fatal(sp.entire(), "this must repeat at least once");
206+
return Err(cx.struct_span_err(
207+
sp.entire(),
208+
"this must repeat at least once",
209+
));
207210
}
208211
} else {
209212
// 0 is the initial counter (we have done 0 repretitions so far). `len`
@@ -242,10 +245,10 @@ pub(super) fn transcribe(
242245
}
243246
} else {
244247
// We were unable to descend far enough. This is an error.
245-
cx.span_fatal(
248+
return Err(cx.struct_span_err(
246249
sp, /* blame the macro writer */
247250
&format!("variable '{}' is still repeating at this depth", ident),
248-
);
251+
));
249252
}
250253
} else {
251254
// If we aren't able to match the meta-var, we push it back into the result but

src/test/ui/macros/issue-61033-1.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
// Regression test for issue #61033.
22

33
macro_rules! test1 {
4-
($x:ident, $($tt:tt)*) => { $($tt)+ } //~ERROR this must repeat at least once
4+
($x:ident, $($tt:tt)*) => { $($tt)+ } //~ ERROR this must repeat at least once
55
}
66

77
fn main() {
88
test1!(x,);
9+
let _recovery_witness: () = 0; //~ ERROR mismatched types
910
}

src/test/ui/macros/issue-61033-1.stderr

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,5 +4,14 @@ error: this must repeat at least once
44
LL | ($x:ident, $($tt:tt)*) => { $($tt)+ }
55
| ^^^^^
66

7-
error: aborting due to previous error
7+
error[E0308]: mismatched types
8+
--> $DIR/issue-61033-1.rs:9:33
9+
|
10+
LL | let _recovery_witness: () = 0;
11+
| -- ^ expected `()`, found integer
12+
| |
13+
| expected due to this
14+
15+
error: aborting due to 2 previous errors
816

17+
For more information about this error, try `rustc --explain E0308`.

src/test/ui/macros/issue-61033-2.rs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,9 @@ macro_rules! test2 {
55
$(* $id1:ident)*
66
$(+ $id2:ident)*
77
) => {
8-
$( //~ERROR meta-variable `id1` repeats 2 times
8+
$(
9+
//~^ ERROR meta-variable `id1` repeats 2 times
10+
//~| ERROR meta-variable `id1` repeats 2 times
911
$id1 + $id2 // $id1 and $id2 may repeat different numbers of times
1012
)*
1113
}
@@ -16,4 +18,8 @@ fn main() {
1618
* a * b
1719
+ a + b + c
1820
}
21+
test2! {
22+
* a * b
23+
+ a + b + c + d
24+
}
1925
}

src/test/ui/macros/issue-61033-2.stderr

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,22 @@ error: meta-variable `id1` repeats 2 times, but `id2` repeats 3 times
33
|
44
LL | $(
55
| __________^
6+
LL | |
7+
LL | |
68
LL | | $id1 + $id2 // $id1 and $id2 may repeat different numbers of times
79
LL | | )*
810
| |_________^
911

10-
error: aborting due to previous error
12+
error: meta-variable `id1` repeats 2 times, but `id2` repeats 4 times
13+
--> $DIR/issue-61033-2.rs:8:10
14+
|
15+
LL | $(
16+
| __________^
17+
LL | |
18+
LL | |
19+
LL | | $id1 + $id2 // $id1 and $id2 may repeat different numbers of times
20+
LL | | )*
21+
| |_________^
22+
23+
error: aborting due to 2 previous errors
1124

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,12 @@
11
macro_rules! mac {
2-
( $($v:tt)* ) => (
3-
$v //~ ERROR still repeating at this depth
4-
)
2+
( $($v:tt)* ) => {
3+
$v
4+
//~^ ERROR still repeating at this depth
5+
//~| ERROR still repeating at this depth
6+
};
57
}
68

79
fn main() {
810
mac!(0);
11+
mac!(1);
912
}

src/test/ui/parser/macro/macro-repeat.stderr

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,5 +4,11 @@ error: variable 'v' is still repeating at this depth
44
LL | $v
55
| ^^
66

7-
error: aborting due to previous error
7+
error: variable 'v' is still repeating at this depth
8+
--> $DIR/macro-repeat.rs:3:9
9+
|
10+
LL | $v
11+
| ^^
12+
13+
error: aborting due to 2 previous errors
814

0 commit comments

Comments
 (0)