Merge pull request #19880 from Veykril/push-xmpxumsrkymk

fix: Handle included files better in IDE layer
This commit is contained in:
Lukas Wirth 2025-05-28 08:49:42 +00:00 committed by GitHub
commit 5900e25edc
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
3 changed files with 97 additions and 31 deletions

View file

@ -769,6 +769,31 @@ impl<'db> SemanticsImpl<'db> {
})
}
/// Descends the token into the include expansion, if its file is an included file.
pub fn descend_token_into_include_expansion(
&self,
tok: InRealFile<SyntaxToken>,
) -> InFile<SyntaxToken> {
let Some(include) =
self.s2d_cache.borrow_mut().get_or_insert_include_for(self.db, tok.file_id)
else {
return tok.into();
};
let span = self.db.real_span_map(tok.file_id).span_for_range(tok.value.text_range());
let Some(InMacroFile { file_id, value: mut mapped_tokens }) = self.with_ctx(|ctx| {
Some(
ctx.cache
.get_or_insert_expansion(ctx.db, include)
.map_range_down(span)?
.map(SmallVec::<[_; 2]>::from_iter),
)
}) else {
return tok.into();
};
// We should only get one result at most
mapped_tokens.pop().map_or_else(|| tok.into(), |(tok, _)| InFile::new(file_id.into(), tok))
}
/// Maps a node down by mapping its first and last token down.
pub fn descend_node_into_attributes<N: AstNode>(&self, node: N) -> SmallVec<[N; 1]> {
// This might not be the correct way to do this, but it works for now
@ -1528,11 +1553,9 @@ impl<'db> SemanticsImpl<'db> {
}
pub fn resolve_macro_call2(&self, macro_call: InFile<&ast::MacroCall>) -> Option<Macro> {
self.with_ctx(|ctx| {
ctx.macro_call_to_macro_call(macro_call)
.and_then(|call| macro_call_to_macro_id(ctx, call))
.map(Into::into)
})
self.to_def2(macro_call)
.and_then(|call| self.with_ctx(|ctx| macro_call_to_macro_id(ctx, call)))
.map(Into::into)
}
pub fn is_proc_macro_call(&self, macro_call: InFile<&ast::MacroCall>) -> bool {
@ -1647,6 +1670,10 @@ impl<'db> SemanticsImpl<'db> {
T::to_def(self, src)
}
pub fn to_def2<T: ToDef>(&self, src: InFile<&T>) -> Option<T::Def> {
T::to_def(self, src)
}
fn file_to_module_defs(&self, file: FileId) -> impl Iterator<Item = Module> {
self.with_ctx(|ctx| ctx.file_to_def(file).to_owned()).into_iter().map(Module::from)
}

View file

@ -399,19 +399,6 @@ impl SourceToDefCtx<'_, '_> {
Some((container, label?))
}
pub(super) fn item_to_macro_call(&mut self, src: InFile<&ast::Item>) -> Option<MacroCallId> {
let map = self.dyn_map(src)?;
map[keys::ATTR_MACRO_CALL].get(&AstPtr::new(src.value)).copied()
}
pub(super) fn macro_call_to_macro_call(
&mut self,
src: InFile<&ast::MacroCall>,
) -> Option<MacroCallId> {
let map = self.dyn_map(src)?;
map[keys::MACRO_CALL].get(&AstPtr::new(src.value)).copied()
}
/// (AttrId, derive attribute call id, derive call ids)
pub(super) fn attr_to_derive_macro_call(
&mut self,
@ -449,6 +436,17 @@ impl SourceToDefCtx<'_, '_> {
.or_insert_with(|| container.child_by_source(db, file_id))
}
pub(super) fn item_to_macro_call(&mut self, src: InFile<&ast::Item>) -> Option<MacroCallId> {
self.to_def(src, keys::ATTR_MACRO_CALL)
}
pub(super) fn macro_call_to_macro_call(
&mut self,
src: InFile<&ast::MacroCall>,
) -> Option<MacroCallId> {
self.to_def(src, keys::MACRO_CALL)
}
pub(super) fn type_param_to_def(
&mut self,
src: InFile<&ast::TypeParam>,