@@ -83,26 +83,41 @@ impl<FileKind, L, R> InFileWrapper<FileKind, Either<L, R>> {
83
83
84
84
// endregion:transpose impls
85
85
86
- // region:specific impls
86
+ trait FileIdToSyntax : Copy {
87
+ fn file_syntax ( self , db : & dyn db:: ExpandDatabase ) -> SyntaxNode ;
88
+ }
87
89
88
- impl < T > InFile < T > {
89
- pub fn file_syntax ( & self , db : & dyn db:: ExpandDatabase ) -> SyntaxNode {
90
- db. parse_or_expand ( self . file_id )
90
+ impl FileIdToSyntax for FileId {
91
+ fn file_syntax ( self , db : & dyn db:: ExpandDatabase ) -> SyntaxNode {
92
+ db. parse ( self ) . syntax_node ( )
93
+ }
94
+ }
95
+ impl FileIdToSyntax for MacroFileId {
96
+ fn file_syntax ( self , db : & dyn db:: ExpandDatabase ) -> SyntaxNode {
97
+ db. parse_macro_expansion ( self ) . value . 0 . syntax_node ( )
98
+ }
99
+ }
100
+ impl FileIdToSyntax for HirFileId {
101
+ fn file_syntax ( self , db : & dyn db:: ExpandDatabase ) -> SyntaxNode {
102
+ db. parse_or_expand ( self )
91
103
}
92
104
}
93
105
94
- impl < T > InRealFile < T > {
106
+ #[ allow( private_bounds) ]
107
+ impl < FileId : FileIdToSyntax , T > InFileWrapper < FileId , T > {
95
108
pub fn file_syntax ( & self , db : & dyn db:: ExpandDatabase ) -> SyntaxNode {
96
- db . parse ( self . file_id ) . syntax_node ( )
109
+ FileIdToSyntax :: file_syntax ( self . file_id , db )
97
110
}
98
111
}
99
112
100
- impl < T > InMacroFile < T > {
101
- pub fn file_syntax ( & self , db : & dyn db :: ExpandDatabase ) -> SyntaxNode {
102
- db . parse_macro_expansion ( self . file_id ) . value . 0 . syntax_node ( )
113
+ impl < FileId : Copy , N : AstNode > InFileWrapper < FileId , N > {
114
+ pub fn syntax ( & self ) -> InFileWrapper < FileId , & SyntaxNode > {
115
+ self . with_value ( self . value . syntax ( ) )
103
116
}
104
117
}
105
118
119
+ // region:specific impls
120
+
106
121
impl InFile < & SyntaxNode > {
107
122
pub fn ancestors_with_macros (
108
123
self ,
@@ -241,9 +256,15 @@ impl InFile<SyntaxToken> {
241
256
match self . file_id . repr ( ) {
242
257
HirFileIdRepr :: FileId ( file_id) => FileRange { file_id, range : self . value . text_range ( ) } ,
243
258
HirFileIdRepr :: MacroFile ( mac_file) => {
244
- if let Some ( res) = self . original_file_range_opt ( db) {
245
- return res;
259
+ let ( range, ctxt) = ExpansionInfo :: new ( db, mac_file)
260
+ . map_token_range_up ( db, self . value . text_range ( ) ) ;
261
+
262
+ // FIXME: Figure out an API that makes proper use of ctx, this only exists to
263
+ // keep pre-token map rewrite behaviour.
264
+ if ctxt. is_root ( ) {
265
+ return range;
246
266
}
267
+
247
268
// Fall back to whole macro call.
248
269
let loc = db. lookup_intern_macro_call ( mac_file. macro_call_id ) ;
249
270
loc. kind . original_call_range ( db)
@@ -257,8 +278,9 @@ impl InFile<SyntaxToken> {
257
278
HirFileIdRepr :: FileId ( file_id) => {
258
279
Some ( FileRange { file_id, range : self . value . text_range ( ) } )
259
280
}
260
- HirFileIdRepr :: MacroFile ( _) => {
261
- let ( range, ctxt) = ascend_range_up_macros ( db, self . map ( |it| it. text_range ( ) ) ) ;
281
+ HirFileIdRepr :: MacroFile ( mac_file) => {
282
+ let ( range, ctxt) = ExpansionInfo :: new ( db, mac_file)
283
+ . map_token_range_up ( db, self . value . text_range ( ) ) ;
262
284
263
285
// FIXME: Figure out an API that makes proper use of ctx, this only exists to
264
286
// keep pre-token map rewrite behaviour.
@@ -275,16 +297,19 @@ impl InFile<SyntaxToken> {
275
297
impl InFile < TextRange > {
276
298
/// Attempts to map the syntax node back up its macro calls.
277
299
pub fn original_file_range ( self , db : & dyn db:: ExpandDatabase ) -> FileRange {
278
- let ( range, _ctxt) = ascend_range_up_macros ( db, self ) ;
300
+ let ( range, _ctxt) = match self . file_id . repr ( ) {
301
+ HirFileIdRepr :: FileId ( file_id) => {
302
+ ( FileRange { file_id, range : self . value } , SyntaxContextId :: ROOT )
303
+ }
304
+ HirFileIdRepr :: MacroFile ( m) => {
305
+ ExpansionInfo :: new ( db, m) . map_token_range_up ( db, self . value )
306
+ }
307
+ } ;
279
308
range
280
309
}
281
310
}
282
311
283
312
impl < N : AstNode > InFile < N > {
284
- pub fn descendants < T : AstNode > ( self ) -> impl Iterator < Item = InFile < T > > {
285
- self . value . syntax ( ) . descendants ( ) . filter_map ( T :: cast) . map ( move |n| self . with_value ( n) )
286
- }
287
-
288
313
pub fn original_ast_node ( self , db : & dyn db:: ExpandDatabase ) -> Option < InRealFile < N > > {
289
314
// This kind of upmapping can only be achieved in attribute expanded files,
290
315
// as we don't have node inputs otherwise and therefore can't find an `N` node in the input
@@ -312,22 +337,4 @@ impl<N: AstNode> InFile<N> {
312
337
let value = anc. ancestors ( ) . find_map ( N :: cast) ?;
313
338
Some ( InRealFile :: new ( file_id, value) )
314
339
}
315
-
316
- pub fn syntax ( & self ) -> InFile < & SyntaxNode > {
317
- self . with_value ( self . value . syntax ( ) )
318
- }
319
- }
320
-
321
- fn ascend_range_up_macros (
322
- db : & dyn db:: ExpandDatabase ,
323
- range : InFile < TextRange > ,
324
- ) -> ( FileRange , SyntaxContextId ) {
325
- match range. file_id . repr ( ) {
326
- HirFileIdRepr :: FileId ( file_id) => {
327
- ( FileRange { file_id, range : range. value } , SyntaxContextId :: ROOT )
328
- }
329
- HirFileIdRepr :: MacroFile ( m) => {
330
- ExpansionInfo :: new ( db, m) . map_token_range_up ( db, range. value )
331
- }
332
- }
333
340
}
0 commit comments