@@ -49,7 +49,7 @@ use rustc_errors::ErrorGuaranteed;
4949use rustc_hir as hir;
5050use rustc_hir:: def_id:: DefId ;
5151use rustc_middle:: span_bug;
52- use rustc_middle:: ty:: ResolverAstLowering ;
52+ use rustc_middle:: ty:: { Asyncness , ResolverAstLowering } ;
5353use rustc_span:: { symbol:: Ident , Span } ;
5454use rustc_target:: spec:: abi;
5555use std:: iter;
@@ -67,7 +67,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
6767 return false ;
6868 } ;
6969 if let Some ( local_sig_id) = sig_id. as_local ( ) {
70- self . resolver . has_self . contains ( & local_sig_id)
70+ self . resolver . delegation_fn_sigs [ & local_sig_id] . has_self
7171 } else {
7272 match self . tcx . def_kind ( sig_id) {
7373 DefKind :: Fn => false ,
@@ -82,13 +82,14 @@ impl<'hir> LoweringContext<'_, 'hir> {
8282 delegation : & Delegation ,
8383 item_id : NodeId ,
8484 ) -> DelegationResults < ' hir > {
85- let span = delegation. path . segments . last ( ) . unwrap ( ) . ident . span ;
85+ let span = self . lower_span ( delegation. path . segments . last ( ) . unwrap ( ) . ident . span ) ;
8686 let sig_id = self . get_delegation_sig_id ( item_id, delegation. id , span) ;
8787 match sig_id {
8888 Ok ( sig_id) => {
89- let decl = self . lower_delegation_decl ( sig_id, span) ;
90- let sig = self . lower_delegation_sig ( span, decl) ;
91- let body_id = self . lower_delegation_body ( sig. decl , delegation) ;
89+ let ( param_count, c_variadic) = self . param_count ( sig_id) ;
90+ let decl = self . lower_delegation_decl ( sig_id, param_count, c_variadic, span) ;
91+ let sig = self . lower_delegation_sig ( sig_id, decl, span) ;
92+ let body_id = self . lower_delegation_body ( delegation, param_count, span) ;
9293
9394 let generics = self . lower_delegation_generics ( span) ;
9495 DelegationResults { body_id, sig, generics }
@@ -123,70 +124,92 @@ impl<'hir> LoweringContext<'_, 'hir> {
123124 } )
124125 }
125126
127+ fn param_count ( & self , sig_id : DefId ) -> ( usize , bool /*c_variadic*/ ) {
128+ if let Some ( local_sig_id) = sig_id. as_local ( ) {
129+ // Map may be filled incorrectly due to recursive delegation.
130+ // Error will be emmited later in astconv.
131+ match self . resolver . delegation_fn_sigs . get ( & local_sig_id) {
132+ Some ( sig) => ( sig. param_count , sig. c_variadic ) ,
133+ None => ( 0 , false ) ,
134+ }
135+ } else {
136+ let sig = self . tcx . fn_sig ( sig_id) . skip_binder ( ) . skip_binder ( ) ;
137+ ( sig. inputs ( ) . len ( ) , sig. c_variadic )
138+ }
139+ }
140+
126141 fn lower_delegation_decl (
127142 & mut self ,
128143 sig_id : DefId ,
129- param_span : Span ,
144+ param_count : usize ,
145+ c_variadic : bool ,
146+ span : Span ,
130147 ) -> & ' hir hir:: FnDecl < ' hir > {
131- let args_count = if let Some ( local_sig_id) = sig_id. as_local ( ) {
132- // Map may be filled incorrectly due to recursive delegation.
133- // Error will be emitted later during HIR ty lowering.
134- self . resolver . fn_parameter_counts . get ( & local_sig_id) . cloned ( ) . unwrap_or_default ( )
135- } else {
136- self . tcx . fn_arg_names ( sig_id) . len ( )
137- } ;
138- let inputs = self . arena . alloc_from_iter ( ( 0 ..args_count) . map ( |arg| hir:: Ty {
148+ // The last parameter in C variadic functions is skipped in the signature,
149+ // like during regular lowering.
150+ let decl_param_count = param_count - c_variadic as usize ;
151+ let inputs = self . arena . alloc_from_iter ( ( 0 ..decl_param_count) . map ( |arg| hir:: Ty {
139152 hir_id : self . next_id ( ) ,
140153 kind : hir:: TyKind :: InferDelegation ( sig_id, hir:: InferDelegationKind :: Input ( arg) ) ,
141- span : self . lower_span ( param_span ) ,
154+ span,
142155 } ) ) ;
143156
144157 let output = self . arena . alloc ( hir:: Ty {
145158 hir_id : self . next_id ( ) ,
146159 kind : hir:: TyKind :: InferDelegation ( sig_id, hir:: InferDelegationKind :: Output ) ,
147- span : self . lower_span ( param_span ) ,
160+ span,
148161 } ) ;
149162
150163 self . arena . alloc ( hir:: FnDecl {
151164 inputs,
152165 output : hir:: FnRetTy :: Return ( output) ,
153- c_variadic : false ,
166+ c_variadic,
154167 lifetime_elision_allowed : true ,
155168 implicit_self : hir:: ImplicitSelfKind :: None ,
156169 } )
157170 }
158171
159172 fn lower_delegation_sig (
160173 & mut self ,
161- span : Span ,
174+ sig_id : DefId ,
162175 decl : & ' hir hir:: FnDecl < ' hir > ,
176+ span : Span ,
163177 ) -> hir:: FnSig < ' hir > {
164- hir:: FnSig {
165- decl,
166- header : hir:: FnHeader {
167- unsafety : hir:: Unsafety :: Normal ,
168- constness : hir:: Constness :: NotConst ,
169- asyncness : hir:: IsAsync :: NotAsync ,
170- abi : abi:: Abi :: Rust ,
171- } ,
172- span : self . lower_span ( span) ,
173- }
178+ let header = if let Some ( local_sig_id) = sig_id. as_local ( ) {
179+ match self . resolver . delegation_fn_sigs . get ( & local_sig_id) {
180+ Some ( sig) => self . lower_fn_header ( sig. header ) ,
181+ None => self . generate_header_error ( ) ,
182+ }
183+ } else {
184+ let sig = self . tcx . fn_sig ( sig_id) . skip_binder ( ) . skip_binder ( ) ;
185+ let asyncness = match self . tcx . asyncness ( sig_id) {
186+ Asyncness :: Yes => hir:: IsAsync :: Async ( span) ,
187+ Asyncness :: No => hir:: IsAsync :: NotAsync ,
188+ } ;
189+ hir:: FnHeader {
190+ unsafety : sig. unsafety ,
191+ constness : self . tcx . constness ( sig_id) ,
192+ asyncness,
193+ abi : sig. abi ,
194+ }
195+ } ;
196+ hir:: FnSig { decl, header, span }
174197 }
175198
176- fn generate_param ( & mut self , ty : & ' hir hir :: Ty < ' hir > ) -> ( hir:: Param < ' hir > , NodeId ) {
199+ fn generate_param ( & mut self , span : Span ) -> ( hir:: Param < ' hir > , NodeId ) {
177200 let pat_node_id = self . next_node_id ( ) ;
178201 let pat_id = self . lower_node_id ( pat_node_id) ;
179202 let pat = self . arena . alloc ( hir:: Pat {
180203 hir_id : pat_id,
181204 kind : hir:: PatKind :: Binding ( hir:: BindingAnnotation :: NONE , pat_id, Ident :: empty ( ) , None ) ,
182- span : ty . span ,
205+ span,
183206 default_binding_modes : false ,
184207 } ) ;
185208
186- ( hir:: Param { hir_id : self . next_id ( ) , pat, ty_span : ty . span , span : ty . span } , pat_node_id)
209+ ( hir:: Param { hir_id : self . next_id ( ) , pat, ty_span : span, span } , pat_node_id)
187210 }
188211
189- fn generate_arg ( & mut self , ty : & ' hir hir :: Ty < ' hir > , param_id : HirId ) -> hir:: Expr < ' hir > {
212+ fn generate_arg ( & mut self , param_id : HirId , span : Span ) -> hir:: Expr < ' hir > {
190213 let segments = self . arena . alloc_from_iter ( iter:: once ( hir:: PathSegment {
191214 ident : Ident :: empty ( ) ,
192215 hir_id : self . next_id ( ) ,
@@ -195,20 +218,20 @@ impl<'hir> LoweringContext<'_, 'hir> {
195218 infer_args : false ,
196219 } ) ) ;
197220
198- let path =
199- self . arena . alloc ( hir:: Path { span : ty. span , res : Res :: Local ( param_id) , segments } ) ;
221+ let path = self . arena . alloc ( hir:: Path { span, res : Res :: Local ( param_id) , segments } ) ;
200222
201223 hir:: Expr {
202224 hir_id : self . next_id ( ) ,
203225 kind : hir:: ExprKind :: Path ( hir:: QPath :: Resolved ( None , path) ) ,
204- span : ty . span ,
226+ span,
205227 }
206228 }
207229
208230 fn lower_delegation_body (
209231 & mut self ,
210- decl : & ' hir hir:: FnDecl < ' hir > ,
211232 delegation : & Delegation ,
233+ param_count : usize ,
234+ span : Span ,
212235 ) -> BodyId {
213236 let path = self . lower_qpath (
214237 delegation. id ,
@@ -224,8 +247,8 @@ impl<'hir> LoweringContext<'_, 'hir> {
224247 let mut parameters: Vec < hir:: Param < ' _ > > = Vec :: new ( ) ;
225248 let mut args: Vec < hir:: Expr < ' hir > > = Vec :: new ( ) ;
226249
227- for ( idx, param_ty ) in decl . inputs . iter ( ) . enumerate ( ) {
228- let ( param, pat_node_id) = this. generate_param ( param_ty ) ;
250+ for idx in 0 ..param_count {
251+ let ( param, pat_node_id) = this. generate_param ( span ) ;
229252 parameters. push ( param) ;
230253
231254 let arg = if let Some ( block) = block
@@ -245,7 +268,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
245268 }
246269 } else {
247270 let pat_hir_id = this. lower_node_id ( pat_node_id) ;
248- this. generate_arg ( param_ty , pat_hir_id )
271+ this. generate_arg ( pat_hir_id , span )
249272 } ;
250273 args. push ( arg) ;
251274 }
@@ -304,14 +327,25 @@ impl<'hir> LoweringContext<'_, 'hir> {
304327 implicit_self : hir:: ImplicitSelfKind :: None ,
305328 } ) ;
306329
307- let sig = self . lower_delegation_sig ( span, decl) ;
330+ let header = self . generate_header_error ( ) ;
331+ let sig = hir:: FnSig { decl, header, span } ;
332+
308333 let body_id = self . lower_body ( |this| {
309334 let expr =
310335 hir:: Expr { hir_id : this. next_id ( ) , kind : hir:: ExprKind :: Err ( err) , span : span } ;
311336 ( & [ ] , expr)
312337 } ) ;
313338 DelegationResults { generics, body_id, sig }
314339 }
340+
341+ fn generate_header_error ( & self ) -> hir:: FnHeader {
342+ hir:: FnHeader {
343+ unsafety : hir:: Unsafety :: Normal ,
344+ constness : hir:: Constness :: NotConst ,
345+ asyncness : hir:: IsAsync :: NotAsync ,
346+ abi : abi:: Abi :: Rust ,
347+ }
348+ }
315349}
316350
317351struct SelfResolver < ' a > {
0 commit comments