@@ -31,9 +31,10 @@ use attr;
31
31
use attr:: AttrMetaMethods ;
32
32
use codemap:: { CodeMap , Span } ;
33
33
use diagnostic:: SpanHandler ;
34
+ use ext:: tt;
34
35
use visit;
35
36
use visit:: Visitor ;
36
- use parse:: token:: { self , InternedString } ;
37
+ use parse:: token:: { self , InternedString , IdentStyle } ;
37
38
38
39
use std:: slice;
39
40
use std:: ascii:: AsciiExt ;
@@ -225,29 +226,44 @@ struct MacroVisitor<'a> {
225
226
context : & ' a Context < ' a >
226
227
}
227
228
229
+ impl < ' a > MacroVisitor < ' a > {
230
+ fn check_ident ( & self , id : ast:: Ident , span : Span ) {
231
+ for & ( s, readable) in & [ ( "asm" , "inline assembly" ) ,
232
+ ( "log_syntax" , "`log_syntax!`" ) ,
233
+ ( "trace_macros" , "`trace_macros`" ) ,
234
+ ( "concat_idents" , "`concat_idents`" ) ] {
235
+ if id. as_str ( ) == s {
236
+ self . context . gate_feature (
237
+ s, span, & format ! ( "{} is not stable enough for use \
238
+ and is subject to change", readable) ) ;
239
+ }
240
+ }
241
+ }
242
+ }
243
+
228
244
impl < ' a , ' v > Visitor < ' v > for MacroVisitor < ' a > {
229
245
fn visit_mac ( & mut self , mac : & ast:: Mac ) {
230
- let ast:: MacInvocTT ( ref path, _ , _) = mac. node ;
246
+ let ast:: MacInvocTT ( ref path, ref tts , _) = mac. node ;
231
247
let id = path. segments . last ( ) . unwrap ( ) . identifier ;
232
-
233
- if id == token :: str_to_ident ( "asm" ) {
234
- self . context . gate_feature ( "asm" , path . span , "inline assembly is not \
235
- stable enough for use and is subject to change" ) ;
236
- }
237
-
238
- else if id == token :: str_to_ident ( "log_syntax" ) {
239
- self . context . gate_feature ( "log_syntax" , path . span , "`log_syntax!` is not \
240
- stable enough for use and is subject to change" ) ;
241
- }
242
-
243
- else if id == token:: str_to_ident ( "trace_macros" ) {
244
- self . context . gate_feature ( "trace_macros" , path . span , "`trace_macros` is not \
245
- stable enough for use and is subject to change" ) ;
246
- }
247
-
248
- else if id == token :: str_to_ident ( "concat_idents" ) {
249
- self . context . gate_feature ( "concat_idents" , path . span , "`concat_idents` is not \
250
- stable enough for use and is subject to change" ) ;
248
+ self . check_ident ( id , path . span ) ;
249
+
250
+ // Issue 22234: process arguments to macro invocation as well,
251
+ // searching for use of feature-gated macros there.
252
+ let mut tt_reader = tt :: transcribe :: new_tt_reader (
253
+ self . context . span_handler , None , None , tts . clone ( ) ) ;
254
+ let mut curr = tt :: transcribe :: tt_next_token ( & mut tt_reader ) ;
255
+ if curr . tok != token :: Eof {
256
+ loop {
257
+ let next = tt :: transcribe :: tt_next_token ( & mut tt_reader ) ;
258
+ if next . tok == token :: Eof { break ; }
259
+ if next . tok == token:: Whitespace { continue ; }
260
+ if next . tok == token :: Not {
261
+ if let token :: Ident ( id , IdentStyle :: Plain ) = curr . tok {
262
+ self . check_ident ( id , curr . sp ) ;
263
+ }
264
+ }
265
+ curr = next ;
266
+ }
251
267
}
252
268
}
253
269
}
0 commit comments