11use log:: info;
22use rustc_ast:: ast:: { AttrVec , BlockCheckMode } ;
3- use rustc_ast:: mut_visit:: { /*visit_clobber,*/ MutVisitor , * } ;
3+ use rustc_ast:: mut_visit:: { MutVisitor , * } ;
44use rustc_ast:: ptr:: P ;
55use rustc_ast:: util:: lev_distance:: find_best_match_for_name;
66use rustc_ast:: { self , ast} ;
@@ -29,7 +29,6 @@ use smallvec::SmallVec;
2929use std:: env;
3030use std:: io:: { self , Write } ;
3131use std:: mem;
32- //use std::ops::DerefMut;
3332use std:: path:: { Path , PathBuf } ;
3433use std:: sync:: { Arc , Mutex , Once } ;
3534#[ cfg( not( parallel_compiler) ) ]
@@ -593,21 +592,21 @@ pub fn build_output_filenames(
593592// [#34511]: https://github.com/rust-lang/rust/issues/34511#issuecomment-322340401
594593pub struct ReplaceBodyWithLoop < ' a , ' b > {
595594 within_static_or_const : bool ,
596- nested_blocks : Option < Vec < ast:: Stmt > > ,
595+ nested_items : Option < Vec < ast:: Stmt > > ,
597596 resolver : & ' a mut Resolver < ' b > ,
598597}
599598
600599impl < ' a , ' b > ReplaceBodyWithLoop < ' a , ' b > {
601600 pub fn new ( resolver : & ' a mut Resolver < ' b > ) -> ReplaceBodyWithLoop < ' a , ' b > {
602- ReplaceBodyWithLoop { within_static_or_const : false , nested_blocks : None , resolver }
601+ ReplaceBodyWithLoop { within_static_or_const : false , nested_items : None , resolver }
603602 }
604603
605604 fn run < R , F : FnOnce ( & mut Self ) -> R > ( & mut self , is_const : bool , action : F ) -> R {
606605 let old_const = mem:: replace ( & mut self . within_static_or_const , is_const) ;
607- let old_blocks = self . nested_blocks . take ( ) ;
606+ let old_blocks = self . nested_items . take ( ) ;
608607 let ret = action ( self ) ;
609608 self . within_static_or_const = old_const;
610- self . nested_blocks = old_blocks;
609+ self . nested_items = old_blocks;
611610 ret
612611 }
613612
@@ -694,6 +693,8 @@ impl<'a> MutVisitor for ReplaceBodyWithLoop<'a, '_> {
694693 }
695694
696695 fn visit_block ( & mut self , b : & mut P < ast:: Block > ) {
696+ // WARNING: this generates a dummy span and so should not be made the parent of any stmt that is not a dummy.
697+ // See https://github.com/rust-lang/rust/issues/71104.
697698 fn stmt_to_block (
698699 rules : ast:: BlockCheckMode ,
699700 s : Option < ast:: Stmt > ,
@@ -707,24 +708,6 @@ impl<'a> MutVisitor for ReplaceBodyWithLoop<'a, '_> {
707708 }
708709 }
709710
710- /*
711- fn block_to_stmt(b: ast::Block, resolver: &mut Resolver<'_>) -> ast::Stmt {
712- let expr = P(ast::Expr {
713- id: resolver.next_node_id(),
714- kind: ast::ExprKind::Block(P(b), None),
715- span: rustc_span::DUMMY_SP,
716- attrs: AttrVec::new(),
717- tokens: None,
718- });
719-
720- ast::Stmt {
721- id: resolver.next_node_id(),
722- kind: ast::StmtKind::Expr(expr),
723- span: rustc_span::DUMMY_SP,
724- }
725- }
726- */
727-
728711 let empty_block = stmt_to_block ( BlockCheckMode :: Default , None , self . resolver ) ;
729712 let loop_expr = P ( ast:: Expr {
730713 kind : ast:: ExprKind :: Loop ( P ( empty_block) , None ) ,
@@ -741,39 +724,33 @@ impl<'a> MutVisitor for ReplaceBodyWithLoop<'a, '_> {
741724 } ;
742725
743726 if self . within_static_or_const {
744- noop_visit_block ( b, self )
745- } else {
746- //visit_clobber(b.deref_mut(), |b| {
747- let mut stmts = vec ! [ ] ;
748- for s in b. stmts . drain ( ..) {
749- let old_blocks = self . nested_blocks . replace ( vec ! [ ] ) ;
727+ return noop_visit_block ( b, self ) ;
728+ }
750729
751- stmts. extend ( self . flat_map_stmt ( s) . into_iter ( ) . filter ( |s| s. is_item ( ) ) ) ;
730+ let mut items = vec ! [ ] ;
731+ for s in b. stmts . drain ( ..) {
732+ let old_items = self . nested_items . replace ( vec ! [ ] ) ;
752733
753- // we put a Some in there earlier with that replace(), so this is valid
754- let new_blocks = self . nested_blocks . take ( ) . unwrap ( ) ;
755- self . nested_blocks = old_blocks;
756- stmts. extend ( new_blocks) ; //.into_iter().map(|b| block_to_stmt(b, self.resolver)));
757- }
734+ items. extend ( self . flat_map_stmt ( s) . into_iter ( ) . filter ( |s| s. is_item ( ) ) ) ;
758735
759- //let mut new_block = ast::Block { stmts, ..b };
736+ // we put a Some in there earlier with that replace(), so this is valid
737+ let nested_items = self . nested_items . take ( ) . unwrap ( ) ;
738+ self . nested_items = old_items;
739+ items. extend ( nested_items) ;
740+ }
760741
761- if let Some ( old_blocks) = self . nested_blocks . as_mut ( ) {
762- //push our fresh block onto the cache and yield an empty block with `loop {}`
763- if !stmts. is_empty ( ) {
764- //old_blocks.push(new_block);
765- old_blocks. extend ( stmts) ;
766- }
742+ if let Some ( nested_items) = self . nested_items . as_mut ( ) {
743+ // add our items to the existing statements and yield an empty block with `loop {}`
744+ if !items. is_empty ( ) {
745+ nested_items. extend ( items) ;
746+ }
767747
768- b. stmts = vec ! [ loop_stmt] ;
769- //stmt_to_block(b.rules, Some(loop_stmt), &mut self.resolver)
770- } else {
771- //push `loop {}` onto the end of our fresh block and yield that
772- stmts. push ( loop_stmt) ;
748+ b. stmts = vec ! [ loop_stmt] ;
749+ } else {
750+ // push `loop {}` onto the end of our fresh block and yield that
751+ items. push ( loop_stmt) ;
773752
774- b. stmts = stmts;
775- }
776- //})
753+ b. stmts = items;
777754 }
778755 }
779756
0 commit comments