Skip to content

Commit e04c0f4

Browse files
committed
Fix panic on eager expansion
1 parent 074474f commit e04c0f4

File tree

2 files changed

+39
-2
lines changed

2 files changed

+39
-2
lines changed

crates/ra_hir_expand/src/eager.rs

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,9 +37,25 @@ pub fn expand_eager_macro(
3737
) -> Option<EagerMacroId> {
3838
let args = macro_call.value.token_tree()?;
3939
let parsed_args = mbe::ast_to_token_tree(&args)?.0;
40-
let parsed_args = mbe::token_tree_to_syntax_node(&parsed_args, FragmentKind::Expr).ok()?.0;
41-
let result = eager_macro_recur(db, macro_call.with_value(parsed_args.syntax_node()), resolver)?;
4240

41+
// Note:
42+
// When `lazy_expand` is called, its *parent* file must be already exists.
43+
// Here we store an eager macro id for the argument expaned here
44+
// for that purpose.
45+
let arg_id: MacroCallId = db
46+
.intern_eager_expansion({
47+
EagerCallLoc {
48+
def,
49+
fragment: FragmentKind::Expr,
50+
subtree: Arc::new(parsed_args.clone()),
51+
file_id: macro_call.file_id,
52+
}
53+
})
54+
.into();
55+
56+
let parsed_args = mbe::token_tree_to_syntax_node(&parsed_args, FragmentKind::Expr).ok()?.0;
57+
let result =
58+
eager_macro_recur(db, InFile::new(arg_id.as_file(), parsed_args.syntax_node()), resolver)?;
4359
let subtree = to_subtree(&result)?;
4460

4561
if let MacroDefKind::BuiltInEager(eager) = def.kind {

crates/ra_hir_ty/src/tests/macros.rs

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -438,6 +438,27 @@ fn main() {
438438
);
439439
}
440440

441+
#[test]
442+
fn infer_builtin_macros_concat_with_lazy() {
443+
assert_snapshot!(
444+
infer(r#"
445+
macro_rules! hello {() => {"hello"}}
446+
447+
#[rustc_builtin_macro]
448+
macro_rules! concat {() => {}}
449+
450+
fn main() {
451+
let x = concat!(hello!(), concat!("world", "!"));
452+
}
453+
"#),
454+
@r###"
455+
![0; 13) '"helloworld!"': &str
456+
[104; 161) '{ ...")); }': ()
457+
[114; 115) 'x': &str
458+
"###
459+
);
460+
}
461+
441462
#[test]
442463
fn infer_derive_clone_simple() {
443464
let (db, pos) = TestDB::with_position(

0 commit comments

Comments
 (0)