Skip to content

Commit 35cca74

Browse files
committed
defatalize BangProcMacro::expand
1 parent b0537e2 commit 35cca74

File tree

8 files changed

+52
-25
lines changed

8 files changed

+52
-25
lines changed

src/librustc_expand/base.rs

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ use rustc_ast::visit::{AssocCtxt, Visitor};
1010
use rustc_attr::{self as attr, Deprecation, HasAttrs, Stability};
1111
use rustc_data_structures::fx::FxHashMap;
1212
use rustc_data_structures::sync::{self, Lrc};
13-
use rustc_errors::{DiagnosticBuilder, DiagnosticId};
13+
use rustc_errors::{DiagnosticBuilder, DiagnosticId, ErrorReported};
1414
use rustc_parse::{self, parser, MACRO_ARGUMENTS};
1515
use rustc_session::parse::ParseSess;
1616
use rustc_span::edition::Edition;
@@ -296,16 +296,26 @@ where
296296
}
297297

298298
pub trait ProcMacro {
299-
fn expand<'cx>(&self, ecx: &'cx mut ExtCtxt<'_>, span: Span, ts: TokenStream) -> TokenStream;
299+
fn expand<'cx>(
300+
&self,
301+
ecx: &'cx mut ExtCtxt<'_>,
302+
span: Span,
303+
ts: TokenStream,
304+
) -> Result<TokenStream, ErrorReported>;
300305
}
301306

302307
impl<F> ProcMacro for F
303308
where
304309
F: Fn(TokenStream) -> TokenStream,
305310
{
306-
fn expand<'cx>(&self, _ecx: &'cx mut ExtCtxt<'_>, _span: Span, ts: TokenStream) -> TokenStream {
311+
fn expand<'cx>(
312+
&self,
313+
_ecx: &'cx mut ExtCtxt<'_>,
314+
_span: Span,
315+
ts: TokenStream,
316+
) -> Result<TokenStream, ErrorReported> {
307317
// FIXME setup implicit context in TLS before calling self.
308-
(*self)(ts)
318+
Ok((*self)(ts))
309319
}
310320
}
311321

src/librustc_expand/expand.rs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -682,7 +682,10 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
682682
InvocationKind::Bang { mac, .. } => match ext {
683683
SyntaxExtensionKind::Bang(expander) => {
684684
self.gate_proc_macro_expansion_kind(span, fragment_kind);
685-
let tok_result = expander.expand(self.cx, span, mac.args.inner_tokens());
685+
let tok_result = match expander.expand(self.cx, span, mac.args.inner_tokens()) {
686+
Err(_) => return ExpandResult::Ready(fragment_kind.dummy(span)),
687+
Ok(ts) => ts,
688+
};
686689
self.parse_ast_fragment(tok_result, fragment_kind, &mac.path, span)
687690
}
688691
SyntaxExtensionKind::LegacyBang(expander) => {

src/librustc_expand/proc_macro.rs

Lines changed: 9 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ use rustc_ast::ast::{self, ItemKind, MetaItemKind, NestedMetaItem};
55
use rustc_ast::token;
66
use rustc_ast::tokenstream::{self, TokenStream};
77
use rustc_data_structures::sync::Lrc;
8-
use rustc_errors::{Applicability, FatalError};
8+
use rustc_errors::{Applicability, ErrorReported, FatalError};
99
use rustc_span::symbol::sym;
1010
use rustc_span::{Span, DUMMY_SP};
1111

@@ -21,21 +21,16 @@ impl base::ProcMacro for BangProcMacro {
2121
ecx: &'cx mut ExtCtxt<'_>,
2222
span: Span,
2323
input: TokenStream,
24-
) -> TokenStream {
24+
) -> Result<TokenStream, ErrorReported> {
2525
let server = proc_macro_server::Rustc::new(ecx);
26-
match self.client.run(&EXEC_STRATEGY, server, input) {
27-
Ok(stream) => stream,
28-
Err(e) => {
29-
let msg = "proc macro panicked";
30-
let mut err = ecx.struct_span_fatal(span, msg);
31-
if let Some(s) = e.as_str() {
32-
err.help(&format!("message: {}", s));
33-
}
34-
35-
err.emit();
36-
FatalError.raise();
26+
self.client.run(&EXEC_STRATEGY, server, input).map_err(|e| {
27+
let mut err = ecx.struct_span_err(span, "proc macro panicked");
28+
if let Some(s) = e.as_str() {
29+
err.help(&format!("message: {}", s));
3730
}
38-
}
31+
err.emit();
32+
ErrorReported
33+
})
3934
}
4035
}
4136

src/test/ui/proc-macro/invalid-punct-ident-1.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,3 +14,5 @@
1414
extern crate invalid_punct_ident;
1515

1616
invalid_punct!(); //~ ERROR proc macro panicked
17+
18+
fn main() {}

src/test/ui/proc-macro/invalid-punct-ident-2.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,3 +14,5 @@
1414
extern crate invalid_punct_ident;
1515

1616
invalid_ident!(); //~ ERROR proc macro panicked
17+
18+
fn main() {}

src/test/ui/proc-macro/invalid-punct-ident-3.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,3 +14,5 @@
1414
extern crate invalid_punct_ident;
1515

1616
invalid_raw_ident!(); //~ ERROR proc macro panicked
17+
18+
fn main() {}
Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,10 @@
11
// aux-build:invalid-punct-ident.rs
22

3-
#[macro_use]
3+
// We use `main` not found below as a witness for error recovery in proc macro expansion.
4+
5+
#[macro_use] //~ ERROR `main` function not found
46
extern crate invalid_punct_ident;
57

6-
lexer_failure!(); //~ ERROR proc macro panicked
7-
//~| ERROR unexpected closing delimiter: `)`
8+
lexer_failure!();
9+
//~^ ERROR proc macro panicked
10+
//~| ERROR unexpected closing delimiter: `)`
Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,26 @@
11
error: unexpected closing delimiter: `)`
2-
--> $DIR/invalid-punct-ident-4.rs:6:1
2+
--> $DIR/invalid-punct-ident-4.rs:8:1
33
|
44
LL | lexer_failure!();
55
| ^^^^^^^^^^^^^^^^^ unexpected closing delimiter
66
|
77
= note: this error originates in a macro (in Nightly builds, run with -Z macro-backtrace for more info)
88

99
error: proc macro panicked
10-
--> $DIR/invalid-punct-ident-4.rs:6:1
10+
--> $DIR/invalid-punct-ident-4.rs:8:1
1111
|
1212
LL | lexer_failure!();
1313
| ^^^^^^^^^^^^^^^^^
1414

15-
error: aborting due to 2 previous errors
15+
error[E0601]: `main` function not found in crate `invalid_punct_ident_4`
16+
--> $DIR/invalid-punct-ident-4.rs:5:1
17+
|
18+
LL | / #[macro_use]
19+
LL | | extern crate invalid_punct_ident;
20+
LL | |
21+
LL | | lexer_failure!();
22+
| |_________________^ consider adding a `main` function to `$DIR/invalid-punct-ident-4.rs`
23+
24+
error: aborting due to 3 previous errors
1625

26+
For more information about this error, try `rustc --explain E0601`.

0 commit comments

Comments
 (0)