@@ -974,15 +974,22 @@ impl<'a> Parser<'a> {
974974 /// This version of parse param doesn't necessarily require identifier names.
975975 fn parse_param_general (
976976 & mut self ,
977+ is_self_allowed : bool ,
977978 is_trait_item : bool ,
978979 allow_c_variadic : bool ,
979980 is_name_required : impl Fn ( & token:: Token ) -> bool ,
980981 ) -> PResult < ' a , Param > {
981982 let lo = self . token . span ;
982983 let attrs = self . parse_outer_attributes ( ) ?;
984+
985+ // Possibly parse `self`. Recover if we parsed it and it wasn't allowed here.
983986 if let Some ( mut param) = self . parse_self_param ( ) ? {
984987 param. attrs = attrs. into ( ) ;
985- return self . recover_bad_self_param ( param, is_trait_item) ;
988+ return if is_self_allowed {
989+ Ok ( param)
990+ } else {
991+ self . recover_bad_self_param ( param, is_trait_item)
992+ } ;
986993 }
987994
988995 let is_name_required = is_name_required ( & self . token ) ;
@@ -1207,6 +1214,7 @@ impl<'a> Parser<'a> {
12071214 }
12081215 } ;
12091216 match p. parse_param_general (
1217+ false ,
12101218 false ,
12111219 allow_c_variadic,
12121220 do_not_enforce_named_arguments_for_c_variadic
@@ -1361,60 +1369,25 @@ impl<'a> Parser<'a> {
13611369 Ok ( Some ( Param :: from_self ( ThinVec :: default ( ) , eself, eself_ident) ) )
13621370 }
13631371
1364- /// Returns the parsed optional self parameter with attributes and whether a self
1365- /// shortcut was used.
1366- fn parse_self_parameter_with_attrs ( & mut self ) -> PResult < ' a , Option < Param > > {
1367- let attrs = self . parse_outer_attributes ( ) ?;
1368- let param_opt = self . parse_self_param ( ) ?;
1369- Ok ( param_opt. map ( |mut param| {
1370- param. attrs = attrs. into ( ) ;
1371- param
1372- } ) )
1373- }
1374-
13751372 /// Parses the parameter list and result type of a function that may have a `self` parameter.
1376- fn parse_fn_decl_with_self < F > ( & mut self , parse_param_fn : F ) -> PResult < ' a , P < FnDecl > >
1377- where F : FnMut ( & mut Parser < ' a > ) -> PResult < ' a , Param > ,
1378- {
1379- self . expect ( & token:: OpenDelim ( token:: Paren ) ) ?;
1380-
1381- // Parse optional self argument.
1382- let self_param = self . parse_self_parameter_with_attrs ( ) ?;
1383-
1384- // Parse the rest of the function parameter list.
1385- let sep = SeqSep :: trailing_allowed ( token:: Comma ) ;
1386- let ( mut fn_inputs, recovered) = if let Some ( self_param) = self_param {
1387- if self . check ( & token:: CloseDelim ( token:: Paren ) ) {
1388- ( vec ! [ self_param] , false )
1389- } else if self . eat ( & token:: Comma ) {
1390- let mut fn_inputs = vec ! [ self_param] ;
1391- let ( mut input, _, recovered) = self . parse_seq_to_before_end (
1392- & token:: CloseDelim ( token:: Paren ) , sep, parse_param_fn) ?;
1393- fn_inputs. append ( & mut input) ;
1394- ( fn_inputs, recovered)
1395- } else {
1396- match self . expect_one_of ( & [ ] , & [ ] ) {
1397- Err ( err) => return Err ( err) ,
1398- Ok ( recovered) => ( vec ! [ self_param] , recovered) ,
1399- }
1400- }
1401- } else {
1402- let ( input, _, recovered) =
1403- self . parse_seq_to_before_end ( & token:: CloseDelim ( token:: Paren ) ,
1404- sep,
1405- parse_param_fn) ?;
1406- ( input, recovered)
1407- } ;
1373+ fn parse_fn_decl_with_self (
1374+ & mut self ,
1375+ is_name_required : impl Copy + Fn ( & token:: Token ) -> bool ,
1376+ ) -> PResult < ' a , P < FnDecl > > {
1377+ // Parse the arguments, starting out with `self` being allowed...
1378+ let mut is_self_allowed = true ;
1379+ let ( mut inputs, _) : ( Vec < _ > , _ ) = self . parse_paren_comma_seq ( |p| {
1380+ let res = p. parse_param_general ( is_self_allowed, true , false , is_name_required) ;
1381+ // ...but now that we've parsed the first argument, `self` is no longer allowed.
1382+ is_self_allowed = false ;
1383+ res
1384+ } ) ?;
14081385
1409- if !recovered {
1410- // Parse closing paren and return type.
1411- self . expect ( & token:: CloseDelim ( token:: Paren ) ) ?;
1412- }
14131386 // Replace duplicated recovered params with `_` pattern to avoid unecessary errors.
1414- self . deduplicate_recovered_params_names ( & mut fn_inputs ) ;
1387+ self . deduplicate_recovered_params_names ( & mut inputs ) ;
14151388
14161389 Ok ( P ( FnDecl {
1417- inputs : fn_inputs ,
1390+ inputs,
14181391 output : self . parse_ret_ty ( true ) ?,
14191392 } ) )
14201393 }
0 commit comments