@@ -6,13 +6,15 @@ use codeql_extractor::trap::{self};
6
6
use log:: Level ;
7
7
use ra_ap_hir:: db:: ExpandDatabase ;
8
8
use ra_ap_hir:: Semantics ;
9
+ use ra_ap_hir_expand:: ExpandTo ;
9
10
use ra_ap_ide_db:: line_index:: { LineCol , LineIndex } ;
10
11
use ra_ap_ide_db:: RootDatabase ;
11
12
use ra_ap_parser:: SyntaxKind ;
12
13
use ra_ap_span:: { EditionedFileId , TextSize } ;
13
14
use ra_ap_syntax:: ast:: RangeItem ;
14
15
use ra_ap_syntax:: {
15
- ast, AstNode , NodeOrToken , SyntaxElementChildren , SyntaxError , SyntaxToken , TextRange ,
16
+ ast, AstNode , NodeOrToken , SyntaxElementChildren , SyntaxError , SyntaxNode , SyntaxToken ,
17
+ TextRange ,
16
18
} ;
17
19
18
20
#[ macro_export]
@@ -80,7 +82,7 @@ pub struct Translator<'a> {
80
82
label : trap:: Label ,
81
83
line_index : LineIndex ,
82
84
file_id : Option < EditionedFileId > ,
83
- pub semi : Option < Semantics < ' a , RootDatabase > > ,
85
+ pub semantics : Option < Semantics < ' a , RootDatabase > > ,
84
86
}
85
87
86
88
impl < ' a > Translator < ' a > {
@@ -90,15 +92,15 @@ impl<'a> Translator<'a> {
90
92
label : trap:: Label ,
91
93
line_index : LineIndex ,
92
94
file_id : Option < EditionedFileId > ,
93
- semi : Option < Semantics < ' a , RootDatabase > > ,
95
+ semantics : Option < Semantics < ' a , RootDatabase > > ,
94
96
) -> Translator < ' a > {
95
97
Translator {
96
98
trap,
97
99
path,
98
100
label,
99
101
line_index,
100
102
file_id,
101
- semi ,
103
+ semantics ,
102
104
}
103
105
}
104
106
fn location ( & self , range : TextRange ) -> ( LineCol , LineCol ) {
@@ -122,8 +124,8 @@ impl<'a> Translator<'a> {
122
124
}
123
125
124
126
pub fn text_range_for_node ( & mut self , node : & impl ast:: AstNode ) -> Option < TextRange > {
125
- if let Some ( semi ) = self . semi . as_ref ( ) {
126
- let file_range = semi . original_range ( node. syntax ( ) ) ;
127
+ if let Some ( semantics ) = self . semantics . as_ref ( ) {
128
+ let file_range = semantics . original_range ( node. syntax ( ) ) ;
127
129
let file_id = self . file_id ?;
128
130
if file_id == file_range. file_id {
129
131
Some ( file_range. range )
@@ -235,86 +237,95 @@ impl<'a> Translator<'a> {
235
237
}
236
238
}
237
239
}
240
+ fn emit_macro_expansion_parse_errors ( & mut self , mcall : & ast:: MacroCall , expanded : & SyntaxNode ) {
241
+ let semantics = self . semantics . as_ref ( ) . unwrap ( ) ;
242
+ if let Some ( value) = semantics
243
+ . hir_file_for ( expanded)
244
+ . macro_file ( )
245
+ . and_then ( |macro_file| {
246
+ semantics
247
+ . db
248
+ . parse_macro_expansion_error ( macro_file. macro_call_id )
249
+ } )
250
+ {
251
+ if let Some ( err) = & value. err {
252
+ let ( message, _error) = err. render_to_string ( semantics. db ) ;
253
+
254
+ if err. span ( ) . anchor . file_id == semantics. hir_file_for ( mcall. syntax ( ) ) {
255
+ let location = err. span ( ) . range
256
+ + semantics
257
+ . db
258
+ . ast_id_map ( err. span ( ) . anchor . file_id . into ( ) )
259
+ . get_erased ( err. span ( ) . anchor . ast_id )
260
+ . text_range ( )
261
+ . start ( ) ;
262
+ self . emit_parse_error ( mcall, & SyntaxError :: new ( message, location) ) ;
263
+ } ;
264
+ }
265
+ for err in value. value . iter ( ) {
266
+ self . emit_parse_error ( mcall, err) ;
267
+ }
268
+ }
269
+ }
270
+
271
+ fn emit_expanded_as (
272
+ & mut self ,
273
+ expand_to : ExpandTo ,
274
+ expanded : SyntaxNode ,
275
+ ) -> Option < Label < generated:: AstNode > > {
276
+ match expand_to {
277
+ ra_ap_hir_expand:: ExpandTo :: Statements => {
278
+ ast:: MacroStmts :: cast ( expanded) . map ( |x| self . emit_macro_stmts ( x) . into ( ) )
279
+ }
280
+ ra_ap_hir_expand:: ExpandTo :: Items => {
281
+ ast:: MacroItems :: cast ( expanded) . map ( |x| self . emit_macro_items ( x) . into ( ) )
282
+ }
283
+
284
+ ra_ap_hir_expand:: ExpandTo :: Pattern => {
285
+ ast:: Pat :: cast ( expanded) . map ( |x| self . emit_pat ( x) . into ( ) )
286
+ }
287
+ ra_ap_hir_expand:: ExpandTo :: Type => {
288
+ ast:: Type :: cast ( expanded) . map ( |x| self . emit_type ( x) . into ( ) )
289
+ }
290
+ ra_ap_hir_expand:: ExpandTo :: Expr => {
291
+ ast:: Expr :: cast ( expanded) . map ( |x| self . emit_expr ( x) . into ( ) )
292
+ }
293
+ }
294
+ }
238
295
pub ( crate ) fn extract_macro_call_expanded (
239
296
& mut self ,
240
297
mcall : & ast:: MacroCall ,
241
298
label : Label < generated:: MacroCall > ,
242
299
) {
243
- if let Some ( semi) = & self . semi {
244
- if let Some ( expanded) = semi. expand ( mcall) {
245
- if let Some ( value) =
246
- semi. hir_file_for ( & expanded)
247
- . macro_file ( )
248
- . and_then ( |macro_file| {
249
- semi. db
250
- . parse_macro_expansion_error ( macro_file. macro_call_id )
251
- } )
252
- {
253
- if let Some ( err) = & value. err {
254
- let ( message, _error) = err. render_to_string ( semi. db ) ;
255
-
256
- if err. span ( ) . anchor . file_id == semi. hir_file_for ( mcall. syntax ( ) ) {
257
- let location = err. span ( ) . range
258
- + semi
259
- . db
260
- . ast_id_map ( err. span ( ) . anchor . file_id . into ( ) )
261
- . get_erased ( err. span ( ) . anchor . ast_id )
262
- . text_range ( )
263
- . start ( ) ;
264
- self . emit_parse_error ( mcall, & SyntaxError :: new ( message, location) ) ;
265
- } ;
266
- }
267
- for err in value. value . iter ( ) {
268
- self . emit_parse_error ( mcall, err) ;
269
- }
270
- }
271
- let expand_to = ra_ap_hir_expand:: ExpandTo :: from_call_site ( mcall) ;
272
- let kind = expanded. kind ( ) ;
273
- let value: Option < Label < crate :: generated:: AstNode > > = match expand_to {
274
- ra_ap_hir_expand:: ExpandTo :: Statements => {
275
- ast:: MacroStmts :: cast ( expanded) . map ( |x| self . emit_macro_stmts ( x) . into ( ) )
276
- }
277
- ra_ap_hir_expand:: ExpandTo :: Items => {
278
- ast:: MacroItems :: cast ( expanded) . map ( |x| self . emit_macro_items ( x) . into ( ) )
279
- }
280
-
281
- ra_ap_hir_expand:: ExpandTo :: Pattern => {
282
- ast:: Pat :: cast ( expanded) . map ( |x| self . emit_pat ( x) . into ( ) )
283
- }
284
- ra_ap_hir_expand:: ExpandTo :: Type => {
285
- ast:: Type :: cast ( expanded) . map ( |x| self . emit_type ( x) . into ( ) )
286
- }
287
- ra_ap_hir_expand:: ExpandTo :: Expr => {
288
- ast:: Expr :: cast ( expanded) . map ( |x| self . emit_expr ( x) . into ( ) )
289
- }
290
- } ;
291
- if let Some ( value) = value {
292
- MacroCall :: emit_expanded ( label, value, & mut self . trap . writer ) ;
293
- } else {
294
- let range = self . text_range_for_node ( mcall) ;
295
- self . emit_parse_error ( mcall, & SyntaxError :: new (
300
+ if let Some ( expanded) = self . semantics . as_ref ( ) . and_then ( |s| s. expand ( mcall) ) {
301
+ self . emit_macro_expansion_parse_errors ( mcall, & expanded) ;
302
+ let expand_to = ra_ap_hir_expand:: ExpandTo :: from_call_site ( mcall) ;
303
+ let kind = expanded. kind ( ) ;
304
+ if let Some ( value) = self . emit_expanded_as ( expand_to, expanded) {
305
+ MacroCall :: emit_expanded ( label, value, & mut self . trap . writer ) ;
306
+ } else {
307
+ let range = self . text_range_for_node ( mcall) ;
308
+ self . emit_parse_error ( mcall, & SyntaxError :: new (
296
309
format ! (
297
310
"macro expansion failed: the macro '{}' expands to {:?} but a {:?} was expected" ,
298
311
mcall. path( ) . map( |p| p. to_string( ) ) . unwrap_or_default( ) ,
299
312
kind, expand_to
300
313
) ,
301
314
range. unwrap_or_else ( || TextRange :: empty ( TextSize :: from ( 0 ) ) ) ,
302
315
) ) ;
303
- }
304
- } else {
305
- let range = self . text_range_for_node ( mcall) ;
306
-
307
- self . emit_parse_error (
308
- mcall,
309
- & SyntaxError :: new (
310
- format ! (
311
- "macro expansion failed: could not resolve macro '{}'" ,
312
- mcall. path( ) . map( |p| p. to_string( ) ) . unwrap_or_default( )
313
- ) ,
314
- range. unwrap_or_else ( || TextRange :: empty ( TextSize :: from ( 0 ) ) ) ,
315
- ) ,
316
- ) ;
317
316
}
317
+ } else {
318
+ let range = self . text_range_for_node ( mcall) ;
319
+ self . emit_parse_error (
320
+ mcall,
321
+ & SyntaxError :: new (
322
+ format ! (
323
+ "macro expansion failed: could not resolve macro '{}'" ,
324
+ mcall. path( ) . map( |p| p. to_string( ) ) . unwrap_or_default( )
325
+ ) ,
326
+ range. unwrap_or_else ( || TextRange :: empty ( TextSize :: from ( 0 ) ) ) ,
327
+ ) ,
328
+ ) ;
318
329
}
319
330
}
320
331
}
0 commit comments