Skip to content

Commit 4be8c49

Browse files
authored
Rollup merge of #143558 - joshtriplett:mbe-refactors, r=SparrowLii
mbe: Refactors and function extractions in `compile_declarative_macro` These refactors help pave the way for parsing attribute rules. Best reviewed commit-by-commit. - **mbe: Simplify compile_declarative_macro by factoring out some variables** - **mbe: Factor out a helper to check an LHS** - **mbe: Factor out a helper to check for unexpected EOF in definition** - **mbe: Clarify comments about error handling in `compile_declarative_macro`**
2 parents b6015a6 + ef0465a commit 4be8c49

File tree

1 file changed

+27
-23
lines changed

1 file changed

+27
-23
lines changed

compiler/rustc_expand/src/mbe/macro_rules.rs

Lines changed: 27 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -373,17 +373,10 @@ pub fn compile_declarative_macro(
373373
node_id: NodeId,
374374
edition: Edition,
375375
) -> (SyntaxExtension, usize) {
376+
let is_local = node_id != DUMMY_NODE_ID;
376377
let mk_syn_ext = |expander| {
377-
SyntaxExtension::new(
378-
sess,
379-
SyntaxExtensionKind::LegacyBang(expander),
380-
span,
381-
Vec::new(),
382-
edition,
383-
ident.name,
384-
attrs,
385-
node_id != DUMMY_NODE_ID,
386-
)
378+
let kind = SyntaxExtensionKind::LegacyBang(expander);
379+
SyntaxExtension::new(sess, kind, span, Vec::new(), edition, ident.name, attrs, is_local)
387380
};
388381
let dummy_syn_ext = |guar| (mk_syn_ext(Arc::new(DummyExpander(guar))), 0);
389382

@@ -393,7 +386,8 @@ pub fn compile_declarative_macro(
393386
let body = macro_def.body.tokens.clone();
394387
let mut p = Parser::new(&sess.psess, body, rustc_parse::MACRO_ARGUMENTS);
395388

396-
// Don't abort iteration early, so that multiple errors can be reported.
389+
// Don't abort iteration early, so that multiple errors can be reported. We only abort early on
390+
// parse failures we can't recover from.
397391
let mut guar = None;
398392
let mut check_emission = |ret: Result<(), ErrorGuaranteed>| guar = guar.or(ret.err());
399393

@@ -402,20 +396,11 @@ pub fn compile_declarative_macro(
402396
while p.token != token::Eof {
403397
let lhs_tt = p.parse_token_tree();
404398
let lhs_tt = parse_one_tt(lhs_tt, RulePart::Pattern, sess, node_id, features, edition);
405-
// We don't handle errors here, the driver will abort after parsing/expansion. We can
406-
// report every error in every macro this way.
407-
check_emission(check_lhs_nt_follows(sess, node_id, &lhs_tt));
408-
check_emission(check_lhs_no_empty_seq(sess, slice::from_ref(&lhs_tt)));
399+
check_emission(check_lhs(sess, node_id, &lhs_tt));
409400
if let Err(e) = p.expect(exp!(FatArrow)) {
410401
return dummy_syn_ext(e.emit());
411402
}
412-
if p.token == token::Eof {
413-
let err_sp = p.token.span.shrink_to_hi();
414-
let guar = sess
415-
.dcx()
416-
.struct_span_err(err_sp, "macro definition ended unexpectedly")
417-
.with_span_label(err_sp, "expected right-hand side of macro rule")
418-
.emit();
403+
if let Some(guar) = check_no_eof(sess, &p, "expected right-hand side of macro rule") {
419404
return dummy_syn_ext(guar);
420405
}
421406
let rhs_tt = p.parse_token_tree();
@@ -454,13 +439,32 @@ pub fn compile_declarative_macro(
454439
}
455440

456441
// Return the number of rules for unused rule linting, if this is a local macro.
457-
let nrules = if node_id != DUMMY_NODE_ID { rules.len() } else { 0 };
442+
let nrules = if is_local { rules.len() } else { 0 };
458443

459444
let expander =
460445
Arc::new(MacroRulesMacroExpander { name: ident, span, node_id, transparency, rules });
461446
(mk_syn_ext(expander), nrules)
462447
}
463448

449+
fn check_no_eof(sess: &Session, p: &Parser<'_>, msg: &'static str) -> Option<ErrorGuaranteed> {
450+
if p.token == token::Eof {
451+
let err_sp = p.token.span.shrink_to_hi();
452+
let guar = sess
453+
.dcx()
454+
.struct_span_err(err_sp, "macro definition ended unexpectedly")
455+
.with_span_label(err_sp, msg)
456+
.emit();
457+
return Some(guar);
458+
}
459+
None
460+
}
461+
462+
fn check_lhs(sess: &Session, node_id: NodeId, lhs: &mbe::TokenTree) -> Result<(), ErrorGuaranteed> {
463+
let e1 = check_lhs_nt_follows(sess, node_id, lhs);
464+
let e2 = check_lhs_no_empty_seq(sess, slice::from_ref(lhs));
465+
e1.and(e2)
466+
}
467+
464468
fn check_lhs_nt_follows(
465469
sess: &Session,
466470
node_id: NodeId,

0 commit comments

Comments
 (0)