Skip to content

Commit 98cfdde

Browse files
committed
Thinner TokenMap
1 parent 92d447f commit 98cfdde

File tree

13 files changed

+123
-259
lines changed

13 files changed

+123
-259
lines changed

Cargo.lock

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

crates/base-db/src/span.rs

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,10 +33,11 @@ impl SyntaxContext for SyntaxContextId {
3333
impl SyntaxContextId {
3434
// TODO: This is very much UB, salsa exposes no way to create an InternId in a const context
3535
// currently (which kind of makes sense but we need it here!)
36-
pub const ROOT: Self = SyntaxContextId(unsafe { core::mem::transmute(1) });
36+
pub const ROOT: Self = SyntaxContextId(unsafe { InternId::new_unchecked(0) });
3737
// TODO: This is very much UB, salsa exposes no way to create an InternId in a const context
3838
// currently (which kind of makes sense but we need it here!)
39-
pub const SELF_REF: Self = SyntaxContextId(unsafe { core::mem::transmute(!0u32) });
39+
pub const SELF_REF: Self =
40+
SyntaxContextId(unsafe { InternId::new_unchecked(InternId::MAX - 1) });
4041

4142
pub fn is_root(self) -> bool {
4243
self == Self::ROOT
@@ -107,6 +108,7 @@ impl fmt::Debug for HirFileId {
107108
pub struct MacroFileId {
108109
pub macro_call_id: MacroCallId,
109110
}
111+
110112
/// `MacroCallId` identifies a particular macro invocation, like
111113
/// `println!("Hello, {}", world)`.
112114
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]

crates/hir-def/src/macro_expansion_tests/mbe.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ macro_rules! f {
3636
}
3737
3838
struct#FileId(0):[email protected]\2# MyTraitMap2#FileId(0):[email protected]\0# {#FileId(0):[email protected]\2#
39-
map#FileId(0):[email protected]\2#:#FileId(0):[email protected]\2# #FileId(0):[email protected]\2#::#FileId(0):1@92..93\2#std#FileId(0):[email protected]\2#::#FileId(0):1@97..98\2#collections#FileId(0):[email protected]\2#::#FileId(0):1@110..111\2#HashSet#FileId(0):[email protected]\2#<#FileId(0):[email protected]\2#(#FileId(0):[email protected]\2#)#FileId(0):[email protected]\2#>#FileId(0):[email protected]\2#,#FileId(0):[email protected]\2#
39+
map#FileId(0):[email protected]\2#:#FileId(0):[email protected]\2# #FileId(0):[email protected]\2#::#FileId(0):1@91..92\2#std#FileId(0):[email protected]\2#::#FileId(0):1@96..97\2#collections#FileId(0):[email protected]\2#::#FileId(0):1@109..110\2#HashSet#FileId(0):[email protected]\2#<#FileId(0):[email protected]\2#(#FileId(0):[email protected]\2#)#FileId(0):[email protected]\2#>#FileId(0):[email protected]\2#,#FileId(0):[email protected]\2#
4040
}#FileId(0):[email protected]\2#
4141
"#]],
4242
);

crates/hir-expand/src/attrs.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -308,7 +308,7 @@ impl Attr {
308308
return None;
309309
}
310310
let path = meta.path()?;
311-
let call_site = span_map.span_for_range(path.syntax().text_range()).ctx;
311+
let call_site = span_map.span_at(path.syntax().text_range().start()).ctx;
312312
Some((
313313
ModPath::from_src(db, path, SpanMapRef::ExpansionSpanMap(&span_map))?,
314314
call_site,

crates/hir-expand/src/db.rs

Lines changed: 3 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -254,7 +254,7 @@ pub fn expand_speculative(
254254
};
255255

256256
let expand_to = macro_expand_to(db, actual_macro_call);
257-
let (node, rev_tmap) = token_tree_to_syntax_node(db, &speculative_expansion.value, expand_to);
257+
let (node, rev_tmap) = token_tree_to_syntax_node(&speculative_expansion.value, expand_to);
258258

259259
let syntax_node = node.syntax_node();
260260
let token = rev_tmap
@@ -312,7 +312,7 @@ fn parse_macro_expansion(
312312
tracing::debug!("expanded = {}", tt.as_debug_string());
313313
tracing::debug!("kind = {:?}", expand_to);
314314

315-
let (parse, rev_token_map) = token_tree_to_syntax_node(db, &tt, expand_to);
315+
let (parse, rev_token_map) = token_tree_to_syntax_node(&tt, expand_to);
316316

317317
ExpandResult { value: (parse, Arc::new(rev_token_map)), err }
318318
}
@@ -674,7 +674,6 @@ fn macro_expand_to(db: &dyn ExpandDatabase, id: MacroCallId) -> ExpandTo {
674674
}
675675

676676
fn token_tree_to_syntax_node(
677-
db: &dyn ExpandDatabase,
678677
tt: &tt::Subtree,
679678
expand_to: ExpandTo,
680679
) -> (Parse<SyntaxNode>, ExpansionSpanMap) {
@@ -685,18 +684,7 @@ fn token_tree_to_syntax_node(
685684
ExpandTo::Type => mbe::TopEntryPoint::Type,
686685
ExpandTo::Expr => mbe::TopEntryPoint::Expr,
687686
};
688-
let (parse, mut span_map) = mbe::token_tree_to_syntax_node(tt, entry_point);
689-
// FIXME: now what the hell is going on here
690-
span_map.span_map.sort_by(|(_, a), (_, b)| {
691-
a.anchor.file_id.cmp(&b.anchor.file_id).then_with(|| {
692-
let map = db.ast_id_map(a.anchor.file_id.into());
693-
map.get_erased(a.anchor.ast_id)
694-
.text_range()
695-
.start()
696-
.cmp(&map.get_erased(b.anchor.ast_id).text_range().start())
697-
})
698-
});
699-
(parse, span_map)
687+
mbe::token_tree_to_syntax_node(tt, entry_point)
700688
}
701689

702690
fn check_tt_count(tt: &tt::Subtree) -> Result<(), ExpandResult<Arc<tt::Subtree>>> {

crates/hir-expand/src/lib.rs

Lines changed: 39 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ use crate::{
4444
db::TokenExpander,
4545
mod_path::ModPath,
4646
proc_macro::ProcMacroExpander,
47-
span::ExpansionSpanMap,
47+
span::{ExpansionSpanMap, SpanMap},
4848
};
4949

5050
pub use crate::ast_id_map::{AstId, ErasedAstId, ErasedFileAstId};
@@ -172,7 +172,6 @@ pub trait HirFileIdExt {
172172
/// For macro-expansion files, returns the file original source file the
173173
/// expansion originated from.
174174
fn original_file(self, db: &dyn db::ExpandDatabase) -> FileId;
175-
fn expansion_level(self, db: &dyn db::ExpandDatabase) -> u32;
176175

177176
/// If this is a macro call, returns the syntax node of the call.
178177
fn call_node(self, db: &dyn db::ExpandDatabase) -> Option<InFile<SyntaxNode>>;
@@ -218,18 +217,6 @@ impl HirFileIdExt for HirFileId {
218217
}
219218
}
220219

221-
fn expansion_level(self, db: &dyn db::ExpandDatabase) -> u32 {
222-
let mut level = 0;
223-
let mut curr = self;
224-
while let Some(macro_file) = curr.macro_file() {
225-
let loc: MacroCallLoc = db.lookup_intern_macro_call(macro_file.macro_call_id);
226-
227-
level += 1;
228-
curr = loc.kind.file_id();
229-
}
230-
level
231-
}
232-
233220
fn call_node(self, db: &dyn db::ExpandDatabase) -> Option<InFile<SyntaxNode>> {
234221
let macro_file = self.macro_file()?;
235222
let loc: MacroCallLoc = db.lookup_intern_macro_call(macro_file.macro_call_id);
@@ -330,6 +317,32 @@ impl HirFileIdExt for HirFileId {
330317
}
331318
}
332319

320+
pub trait MacroFileIdExt {
321+
fn expansion_level(self, db: &dyn db::ExpandDatabase) -> u32;
322+
fn expansion_info(self, db: &dyn db::ExpandDatabase) -> ExpansionInfo;
323+
}
324+
325+
impl MacroFileIdExt for MacroFileId {
326+
fn expansion_level(self, db: &dyn db::ExpandDatabase) -> u32 {
327+
let mut level = 0;
328+
let mut macro_file = self;
329+
loop {
330+
let loc: MacroCallLoc = db.lookup_intern_macro_call(macro_file.macro_call_id);
331+
332+
level += 1;
333+
macro_file = match loc.kind.file_id().repr() {
334+
HirFileIdRepr::FileId(_) => break level,
335+
HirFileIdRepr::MacroFile(it) => it,
336+
};
337+
}
338+
}
339+
340+
/// Return expansion information if it is a macro-expansion file
341+
fn expansion_info(self, db: &dyn db::ExpandDatabase) -> ExpansionInfo {
342+
ExpansionInfo::new(db, self)
343+
}
344+
}
345+
333346
impl MacroDefId {
334347
pub fn as_lazy_macro(
335348
self,
@@ -398,7 +411,7 @@ impl MacroCallLoc {
398411
match file_id.repr() {
399412
HirFileIdRepr::FileId(file_id) => db.real_span_map(file_id).span_for_range(range),
400413
HirFileIdRepr::MacroFile(m) => {
401-
db.parse_macro_expansion(m).value.1.span_for_range(range)
414+
db.parse_macro_expansion(m).value.1.span_at(range.start())
402415
}
403416
}
404417
}
@@ -565,9 +578,8 @@ pub struct ExpansionInfo {
565578

566579
macro_def: TokenExpander,
567580
macro_arg: Arc<tt::Subtree>,
568-
exp_map: Arc<ExpansionSpanMap>,
569-
/// [`None`] if the call is in a real file
570-
arg_map: Option<Arc<ExpansionSpanMap>>,
581+
pub exp_map: Arc<ExpansionSpanMap>,
582+
arg_map: SpanMap,
571583
}
572584

573585
impl ExpansionInfo {
@@ -582,38 +594,14 @@ impl ExpansionInfo {
582594
/// Maps the passed in file range down into a macro expansion if it is the input to a macro call.
583595
pub fn map_range_down<'a>(
584596
&'a self,
585-
db: &'a dyn db::ExpandDatabase,
586-
FileRange { file_id, range: absolute_range }: FileRange,
597+
span: SpanData,
587598
// FIXME: use this for range mapping, so that we can resolve inline format args
588599
_relative_token_offset: Option<TextSize>,
589600
// FIXME: ret ty should be wrapped in InMacroFile
590601
) -> Option<impl Iterator<Item = InFile<SyntaxToken>> + 'a> {
591-
// search for all entries in the span map that have the given span and return the
592-
// corresponding text ranges inside the expansion
593-
// FIXME: Make this proper
594-
let span_map = &self.exp_map.span_map;
595-
let (start, end) = if span_map
596-
.first()
597-
.map_or(false, |(_, span)| span.anchor.file_id == file_id)
598-
{
599-
(0, span_map.partition_point(|a| a.1.anchor.file_id == file_id))
600-
} else {
601-
let start = span_map.partition_point(|a| a.1.anchor.file_id != file_id);
602-
(start, start + span_map[start..].partition_point(|a| a.1.anchor.file_id == file_id))
603-
};
604-
let tokens = span_map[start..end]
605-
.iter()
606-
.filter_map(move |(range, span)| {
607-
// we need to resolve the relative ranges here to make sure that we are in fact
608-
// considering differently anchored spans (this might occur with proc-macros)
609-
let offset = db
610-
.ast_id_map(span.anchor.file_id.into())
611-
.get_erased(span.anchor.ast_id)
612-
.text_range()
613-
.start();
614-
let abs_range = span.range + offset;
615-
absolute_range.eq(&abs_range).then_some(*range)
616-
})
602+
let tokens = self
603+
.exp_map
604+
.ranges_with_span(span)
617605
.flat_map(move |range| self.expanded.value.covering_element(range).into_token());
618606

619607
Some(tokens.map(move |token| InFile::new(self.expanded.file_id.into(), token)))
@@ -626,7 +614,7 @@ impl ExpansionInfo {
626614
range: TextRange,
627615
) -> (FileRange, SyntaxContextId) {
628616
debug_assert!(self.expanded.value.text_range().contains_range(range));
629-
let span = self.exp_map.span_for_range(range);
617+
let span = self.exp_map.span_at(range.start());
630618
let anchor_offset = db
631619
.ast_id_map(span.anchor.file_id.into())
632620
.get_erased(span.anchor.ast_id)
@@ -672,15 +660,15 @@ impl ExpansionInfo {
672660
token: TextRange,
673661
) -> InFile<smallvec::SmallVec<[TextRange; 1]>> {
674662
debug_assert!(self.expanded.value.text_range().contains_range(token));
675-
let span = self.exp_map.span_for_range(token);
663+
let span = self.exp_map.span_at(token.start());
676664
match &self.arg_map {
677-
None => {
665+
SpanMap::RealSpanMap(_) => {
678666
let file_id = span.anchor.file_id.into();
679667
let anchor_offset =
680668
db.ast_id_map(file_id).get_erased(span.anchor.ast_id).text_range().start();
681669
InFile { file_id, value: smallvec::smallvec![span.range + anchor_offset] }
682670
}
683-
Some(arg_map) => {
671+
SpanMap::ExpansionSpanMap(arg_map) => {
684672
let arg_range = self
685673
.arg
686674
.value
@@ -701,8 +689,7 @@ impl ExpansionInfo {
701689
let loc: MacroCallLoc = db.lookup_intern_macro_call(macro_file.macro_call_id);
702690

703691
let arg_tt = loc.kind.arg(db);
704-
let arg_map =
705-
arg_tt.file_id.macro_file().map(|file| db.parse_macro_expansion(file).value.1);
692+
let arg_map = db.span_map(arg_tt.file_id);
706693

707694
let macro_def = db.macro_expander(loc.def);
708695
let (parse, exp_map) = db.parse_macro_expansion(macro_file).value;

crates/hir-expand/src/span.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ use crate::db::ExpandDatabase;
1111
pub type ExpansionSpanMap = TokenMap<SpanData>;
1212

1313
/// Spanmap for a macro file or a real file
14-
#[derive(Clone, Debug)]
14+
#[derive(Clone, Debug, PartialEq, Eq)]
1515
pub enum SpanMap {
1616
/// Spanmap for a macro file
1717
ExpansionSpanMap(Arc<ExpansionSpanMap>),
@@ -46,7 +46,7 @@ impl mbe::SpanMapper<SpanData> for RealSpanMap {
4646
impl SpanMap {
4747
pub fn span_for_range(&self, range: TextRange) -> SpanData {
4848
match self {
49-
Self::ExpansionSpanMap(span_map) => span_map.span_for_range(range),
49+
Self::ExpansionSpanMap(span_map) => span_map.span_at(range.start()),
5050
Self::RealSpanMap(span_map) => span_map.span_for_range(range),
5151
}
5252
}
@@ -62,7 +62,7 @@ impl SpanMap {
6262
impl SpanMapRef<'_> {
6363
pub fn span_for_range(self, range: TextRange) -> SpanData {
6464
match self {
65-
Self::ExpansionSpanMap(span_map) => span_map.span_for_range(range),
65+
Self::ExpansionSpanMap(span_map) => span_map.span_at(range.start()),
6666
Self::RealSpanMap(span_map) => span_map.span_for_range(range),
6767
}
6868
}

0 commit comments

Comments
 (0)