@@ -26,7 +26,6 @@ use errors::{Applicability, FatalError};
2626use smallvec:: { smallvec, SmallVec } ;
2727use syntax_pos:: { Span , DUMMY_SP , FileName } ;
2828
29- use rustc_data_structures:: fx:: FxHashMap ;
3029use rustc_data_structures:: sync:: Lrc ;
3130use std:: io:: ErrorKind ;
3231use std:: { iter, mem, slice} ;
@@ -75,6 +74,22 @@ macro_rules! ast_fragments {
7574 }
7675
7776 impl AstFragment {
77+ pub fn add_placeholders( & mut self , placeholders: & [ NodeId ] ) {
78+ if placeholders. is_empty( ) {
79+ return ;
80+ }
81+ match self {
82+ $( $( AstFragment :: $Kind( ast) => ast. extend( placeholders. iter( ) . flat_map( |id| {
83+ // We are repeating through arguments with `many`, to do that we have to
84+ // mention some macro variable from those arguments even if it's not used.
85+ #[ cfg_attr( bootstrap, allow( unused_macros) ) ]
86+ macro _repeating( $flat_map_ast_elt) { }
87+ placeholder( AstFragmentKind :: $Kind, * id) . $make_ast( )
88+ } ) ) , ) ?) *
89+ _ => panic!( "unexpected AST fragment kind" )
90+ }
91+ }
92+
7893 pub fn make_opt_expr( self ) -> Option <P <ast:: Expr >> {
7994 match self {
8095 AstFragment :: OptExpr ( expr) => expr,
@@ -342,7 +357,6 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
342357 // Unresolved macros produce dummy outputs as a recovery measure.
343358 invocations. reverse ( ) ;
344359 let mut expanded_fragments = Vec :: new ( ) ;
345- let mut all_derive_placeholders: FxHashMap < ExpnId , Vec < _ > > = FxHashMap :: default ( ) ;
346360 let mut undetermined_invocations = Vec :: new ( ) ;
347361 let ( mut progress, mut force) = ( false , !self . monotonic ) ;
348362 loop {
@@ -420,9 +434,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
420434 self . cx . resolver . add_derives ( invoc. expansion_data . id , SpecialDerives :: COPY ) ;
421435 }
422436
423- let derive_placeholders =
424- all_derive_placeholders. entry ( invoc. expansion_data . id ) . or_default ( ) ;
425- derive_placeholders. reserve ( derives. len ( ) ) ;
437+ let mut derive_placeholders = Vec :: with_capacity ( derives. len ( ) ) ;
426438 invocations. reserve ( derives. len ( ) ) ;
427439 for path in derives {
428440 let expn_id = ExpnId :: fresh ( None ) ;
@@ -438,7 +450,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
438450 }
439451 let fragment = invoc. fragment_kind
440452 . expect_from_annotatables ( :: std:: iter:: once ( item) ) ;
441- self . collect_invocations ( fragment, derive_placeholders)
453+ self . collect_invocations ( fragment, & derive_placeholders)
442454 }
443455 } ;
444456
@@ -457,10 +469,8 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
457469 let mut placeholder_expander = PlaceholderExpander :: new ( self . cx , self . monotonic ) ;
458470 while let Some ( expanded_fragments) = expanded_fragments. pop ( ) {
459471 for ( expn_id, expanded_fragment) in expanded_fragments. into_iter ( ) . rev ( ) {
460- let derive_placeholders =
461- all_derive_placeholders. remove ( & expn_id) . unwrap_or_else ( Vec :: new) ;
462472 placeholder_expander. add ( NodeId :: placeholder_from_expn_id ( expn_id) ,
463- expanded_fragment, derive_placeholders ) ;
473+ expanded_fragment) ;
464474 }
465475 }
466476 fragment_with_placeholders. mut_visit_with ( & mut placeholder_expander) ;
@@ -493,13 +503,14 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
493503 monotonic : self . monotonic ,
494504 } ;
495505 fragment. mut_visit_with ( & mut collector) ;
506+ fragment. add_placeholders ( extra_placeholders) ;
496507 collector. invocations
497508 } ;
498509
499- // FIXME: Merge `extra_placeholders` into the `fragment` as regular placeholders.
500510 if self . monotonic {
501511 self . cx . resolver . visit_ast_fragment_with_placeholders (
502- self . cx . current_expansion . id , & fragment, extra_placeholders) ;
512+ self . cx . current_expansion . id , & fragment
513+ ) ;
503514 }
504515
505516 ( fragment, invocations)
0 commit comments