@@ -11,7 +11,7 @@ use crate::ast::*;
1111use crate :: ptr:: P ;
1212use crate :: token:: { self , Token } ;
1313use crate :: tokenstream:: * ;
14- use crate :: visit:: { AssocCtxt , BoundKind } ;
14+ use crate :: visit:: { AssocCtxt , BoundKind , FnCtxt } ;
1515
1616use rustc_data_structures:: flat_map_in_place:: FlatMapInPlace ;
1717use rustc_data_structures:: stack:: ensure_sufficient_stack;
@@ -36,7 +36,7 @@ impl<A: Array> ExpectOne<A> for SmallVec<A> {
3636}
3737
3838pub trait NoopVisitItemKind {
39- fn noop_visit ( & mut self , visitor : & mut impl MutVisitor ) ;
39+ fn noop_visit ( & mut self , ctxt : Option < AssocCtxt > , visitor : & mut impl MutVisitor ) ;
4040}
4141
4242pub trait MutVisitor : Sized {
@@ -95,11 +95,11 @@ pub trait MutVisitor: Sized {
9595 }
9696
9797 fn flat_map_foreign_item ( & mut self , ni : P < ForeignItem > ) -> SmallVec < [ P < ForeignItem > ; 1 ] > {
98- noop_flat_map_item ( ni, self )
98+ noop_flat_map_item ( ni, None , self )
9999 }
100100
101101 fn flat_map_item ( & mut self , i : P < Item > ) -> SmallVec < [ P < Item > ; 1 ] > {
102- noop_flat_map_item ( i, self )
102+ noop_flat_map_item ( i, None , self )
103103 }
104104
105105 fn visit_fn_header ( & mut self , header : & mut FnHeader ) {
@@ -113,15 +113,19 @@ pub trait MutVisitor: Sized {
113113 fn flat_map_assoc_item (
114114 & mut self ,
115115 i : P < AssocItem > ,
116- _ctxt : AssocCtxt ,
116+ ctxt : AssocCtxt ,
117117 ) -> SmallVec < [ P < AssocItem > ; 1 ] > {
118- noop_flat_map_item ( i, self )
118+ noop_flat_map_item ( i, Some ( ctxt ) , self )
119119 }
120120
121121 fn visit_fn_decl ( & mut self , d : & mut P < FnDecl > ) {
122122 noop_visit_fn_decl ( d, self ) ;
123123 }
124124
125+ fn visit_fn ( & mut self , fk : FnKind < ' _ > ) {
126+ noop_visit_fn ( fk, self )
127+ }
128+
125129 fn visit_coroutine_kind ( & mut self , a : & mut CoroutineKind ) {
126130 noop_visit_coroutine_kind ( a, self ) ;
127131 }
@@ -390,13 +394,6 @@ fn visit_bounds<T: MutVisitor>(bounds: &mut GenericBounds, ctxt: BoundKind, vis:
390394 visit_vec ( bounds, |bound| vis. visit_param_bound ( bound, ctxt) ) ;
391395}
392396
393- // No `noop_` prefix because there isn't a corresponding method in `MutVisitor`.
394- fn visit_fn_sig < T : MutVisitor > ( FnSig { header, decl, span } : & mut FnSig , vis : & mut T ) {
395- vis. visit_fn_header ( header) ;
396- vis. visit_fn_decl ( decl) ;
397- vis. visit_span ( span) ;
398- }
399-
400397// No `noop_` prefix because there isn't a corresponding method in `MutVisitor`.
401398fn visit_attr_args < T : MutVisitor > ( args : & mut AttrArgs , vis : & mut T ) {
402399 match args {
@@ -891,6 +888,26 @@ fn noop_visit_coroutine_kind<T: MutVisitor>(coroutine_kind: &mut CoroutineKind,
891888 }
892889}
893890
891+ fn noop_visit_fn < T : MutVisitor > ( kind : FnKind < ' _ > , vis : & mut T ) {
892+ match kind {
893+ FnKind :: Fn ( _ctxt, FnSig { header, decl, span } , generics, body) => {
894+ // Identifier and visibility are visited as a part of the item.
895+ vis. visit_fn_header ( header) ;
896+ vis. visit_generics ( generics) ;
897+ vis. visit_fn_decl ( decl) ;
898+ if let Some ( body) = body {
899+ vis. visit_block ( body) ;
900+ }
901+ vis. visit_span ( span) ;
902+ }
903+ FnKind :: Closure ( binder, decl, body) => {
904+ vis. visit_closure_binder ( binder) ;
905+ vis. visit_fn_decl ( decl) ;
906+ vis. visit_expr ( body) ;
907+ }
908+ }
909+ }
910+
894911fn noop_visit_fn_decl < T : MutVisitor > ( decl : & mut P < FnDecl > , vis : & mut T ) {
895912 let FnDecl { inputs, output } = decl. deref_mut ( ) ;
896913 inputs. flat_map_in_place ( |param| vis. flat_map_param ( param) ) ;
@@ -1073,11 +1090,12 @@ pub fn noop_visit_block<T: MutVisitor>(block: &mut P<Block>, vis: &mut T) {
10731090}
10741091
10751092pub fn noop_visit_item_kind ( kind : & mut impl NoopVisitItemKind , vis : & mut impl MutVisitor ) {
1076- kind. noop_visit ( vis)
1093+ kind. noop_visit ( None , vis)
10771094}
10781095
10791096impl NoopVisitItemKind for ItemKind {
1080- fn noop_visit ( & mut self , vis : & mut impl MutVisitor ) {
1097+ fn noop_visit ( & mut self , ctxt : Option < AssocCtxt > , vis : & mut impl MutVisitor ) {
1098+ assert_eq ! ( ctxt, None ) ;
10811099 match self {
10821100 ItemKind :: ExternCrate ( _orig_name) => { }
10831101 ItemKind :: Use ( use_tree) => vis. visit_use_tree ( use_tree) ,
@@ -1090,9 +1108,7 @@ impl NoopVisitItemKind for ItemKind {
10901108 }
10911109 ItemKind :: Fn ( box Fn { defaultness, generics, sig, body } ) => {
10921110 visit_defaultness ( defaultness, vis) ;
1093- vis. visit_generics ( generics) ;
1094- visit_fn_sig ( sig, vis) ;
1095- visit_opt ( body, |body| vis. visit_block ( body) ) ;
1111+ vis. visit_fn ( FnKind :: Fn ( FnCtxt :: Free , sig, generics, body) ) ;
10961112 }
10971113 ItemKind :: Mod ( safety, mod_kind) => {
10981114 visit_safety ( safety, vis) ;
@@ -1191,16 +1207,15 @@ impl NoopVisitItemKind for ItemKind {
11911207}
11921208
11931209impl NoopVisitItemKind for AssocItemKind {
1194- fn noop_visit ( & mut self , visitor : & mut impl MutVisitor ) {
1210+ fn noop_visit ( & mut self , ctxt : Option < AssocCtxt > , visitor : & mut impl MutVisitor ) {
1211+ let ctxt = ctxt. unwrap ( ) ;
11951212 match self {
11961213 AssocItemKind :: Const ( item) => {
11971214 visit_const_item ( item, visitor) ;
11981215 }
11991216 AssocItemKind :: Fn ( box Fn { defaultness, generics, sig, body } ) => {
12001217 visit_defaultness ( defaultness, visitor) ;
1201- visitor. visit_generics ( generics) ;
1202- visit_fn_sig ( sig, visitor) ;
1203- visit_opt ( body, |body| visitor. visit_block ( body) ) ;
1218+ visitor. visit_fn ( FnKind :: Fn ( FnCtxt :: Assoc ( ctxt) , sig, generics, body) ) ;
12041219 }
12051220 AssocItemKind :: Type ( box TyAlias {
12061221 defaultness,
@@ -1283,31 +1298,31 @@ pub fn noop_visit_crate<T: MutVisitor>(krate: &mut Crate, vis: &mut T) {
12831298// Mutates one item into possibly many items.
12841299pub fn noop_flat_map_item < K : NoopVisitItemKind > (
12851300 mut item : P < Item < K > > ,
1301+ ctxt : Option < AssocCtxt > ,
12861302 visitor : & mut impl MutVisitor ,
12871303) -> SmallVec < [ P < Item < K > > ; 1 ] > {
12881304 let Item { ident, attrs, id, kind, vis, span, tokens } = item. deref_mut ( ) ;
12891305 visitor. visit_id ( id) ;
12901306 visit_attrs ( attrs, visitor) ;
12911307 visitor. visit_vis ( vis) ;
12921308 visitor. visit_ident ( ident) ;
1293- kind. noop_visit ( visitor) ;
1309+ kind. noop_visit ( ctxt , visitor) ;
12941310 visit_lazy_tts ( tokens, visitor) ;
12951311 visitor. visit_span ( span) ;
12961312 smallvec ! [ item]
12971313}
12981314
12991315impl NoopVisitItemKind for ForeignItemKind {
1300- fn noop_visit ( & mut self , visitor : & mut impl MutVisitor ) {
1316+ fn noop_visit ( & mut self , ctxt : Option < AssocCtxt > , visitor : & mut impl MutVisitor ) {
1317+ assert_eq ! ( ctxt, None ) ;
13011318 match self {
13021319 ForeignItemKind :: Static ( box StaticItem { ty, mutability : _, expr, safety : _ } ) => {
13031320 visitor. visit_ty ( ty) ;
13041321 visit_opt ( expr, |expr| visitor. visit_expr ( expr) ) ;
13051322 }
13061323 ForeignItemKind :: Fn ( box Fn { defaultness, generics, sig, body } ) => {
13071324 visit_defaultness ( defaultness, visitor) ;
1308- visitor. visit_generics ( generics) ;
1309- visit_fn_sig ( sig, visitor) ;
1310- visit_opt ( body, |body| visitor. visit_block ( body) ) ;
1325+ visitor. visit_fn ( FnKind :: Fn ( FnCtxt :: Foreign , sig, generics, body) ) ;
13111326 }
13121327 ForeignItemKind :: TyAlias ( box TyAlias {
13131328 defaultness,
@@ -1517,12 +1532,10 @@ pub fn noop_visit_expr<T: MutVisitor>(
15171532 fn_decl_span,
15181533 fn_arg_span,
15191534 } ) => {
1520- vis. visit_closure_binder ( binder) ;
15211535 visit_constness ( constness, vis) ;
15221536 coroutine_kind. as_mut ( ) . map ( |coroutine_kind| vis. visit_coroutine_kind ( coroutine_kind) ) ;
15231537 vis. visit_capture_by ( capture_clause) ;
1524- vis. visit_fn_decl ( fn_decl) ;
1525- vis. visit_expr ( body) ;
1538+ vis. visit_fn ( FnKind :: Closure ( binder, fn_decl, body) ) ;
15261539 vis. visit_span ( fn_decl_span) ;
15271540 vis. visit_span ( fn_arg_span) ;
15281541 }
@@ -1779,3 +1792,12 @@ impl<N: DummyAstNode, T: DummyAstNode> DummyAstNode for crate::ast_traits::AstNo
17791792 crate :: ast_traits:: AstNodeWrapper :: new ( N :: dummy ( ) , T :: dummy ( ) )
17801793 }
17811794}
1795+
1796+ #[ derive( Debug ) ]
1797+ pub enum FnKind < ' a > {
1798+ /// E.g., `fn foo()`, `fn foo(&self)`, or `extern "Abi" fn foo()`.
1799+ Fn ( FnCtxt , & ' a mut FnSig , & ' a mut Generics , & ' a mut Option < P < Block > > ) ,
1800+
1801+ /// E.g., `|x, y| body`.
1802+ Closure ( & ' a mut ClosureBinder , & ' a mut P < FnDecl > , & ' a mut P < Expr > ) ,
1803+ }
0 commit comments