@@ -155,6 +155,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
155
155
self . lower_expr_await ( span, expr)
156
156
}
157
157
ExprKind :: Closure (
158
+ ref binder,
158
159
capture_clause,
159
160
asyncness,
160
161
movability,
@@ -164,6 +165,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
164
165
) => {
165
166
if let Async :: Yes { closure_id, .. } = asyncness {
166
167
self . lower_expr_async_closure (
168
+ binder,
167
169
capture_clause,
168
170
e. id ,
169
171
closure_id,
@@ -173,6 +175,7 @@ impl<'hir> LoweringContext<'_, 'hir> {
173
175
)
174
176
} else {
175
177
self . lower_expr_closure (
178
+ binder,
176
179
capture_clause,
177
180
e. id ,
178
181
movability,
@@ -605,13 +608,18 @@ impl<'hir> LoweringContext<'_, 'hir> {
605
608
} ) ;
606
609
607
610
// `static |_task_context| -> <ret_ty> { body }`:
608
- let generator_kind = hir:: ExprKind :: Closure {
609
- capture_clause,
610
- bound_generic_params : & [ ] ,
611
- fn_decl,
612
- body,
613
- fn_decl_span : self . lower_span ( span) ,
614
- movability : Some ( hir:: Movability :: Static ) ,
611
+ let generator_kind = {
612
+ let c = self . arena . alloc ( hir:: Closure {
613
+ binder : hir:: ClosureBinder :: Default ,
614
+ capture_clause,
615
+ bound_generic_params : & [ ] ,
616
+ fn_decl,
617
+ body,
618
+ fn_decl_span : self . lower_span ( span) ,
619
+ movability : Some ( hir:: Movability :: Static ) ,
620
+ } ) ;
621
+
622
+ hir:: ExprKind :: Closure ( c)
615
623
} ;
616
624
let generator = hir:: Expr {
617
625
hir_id : self . lower_node_id ( closure_node_id) ,
@@ -831,14 +839,17 @@ impl<'hir> LoweringContext<'_, 'hir> {
831
839
832
840
fn lower_expr_closure (
833
841
& mut self ,
842
+ binder : & ClosureBinder ,
834
843
capture_clause : CaptureBy ,
835
844
closure_id : NodeId ,
836
845
movability : Movability ,
837
846
decl : & FnDecl ,
838
847
body : & Expr ,
839
848
fn_decl_span : Span ,
840
849
) -> hir:: ExprKind < ' hir > {
841
- let ( body, generator_option) = self . with_new_scopes ( move |this| {
850
+ let ( binder_clause, generic_params) = self . lower_closure_binder ( binder) ;
851
+
852
+ let ( body_id, generator_option) = self . with_new_scopes ( move |this| {
842
853
let prev = this. current_item ;
843
854
this. current_item = Some ( fn_decl_span) ;
844
855
let mut generator_kind = None ;
@@ -853,18 +864,21 @@ impl<'hir> LoweringContext<'_, 'hir> {
853
864
( body_id, generator_option)
854
865
} ) ;
855
866
856
- self . with_lifetime_binder ( closure_id, & [ ] , |this, bound_generic_params| {
867
+ self . with_lifetime_binder ( closure_id, generic_params , |this, bound_generic_params| {
857
868
// Lower outside new scope to preserve `is_in_loop_condition`.
858
869
let fn_decl = this. lower_fn_decl ( decl, None , FnDeclKind :: Closure , None ) ;
859
870
860
- hir:: ExprKind :: Closure {
871
+ let c = self . arena . alloc ( hir:: Closure {
872
+ binder : binder_clause,
861
873
capture_clause,
862
874
bound_generic_params,
863
875
fn_decl,
864
- body,
876
+ body : body_id ,
865
877
fn_decl_span : this. lower_span ( fn_decl_span) ,
866
878
movability : generator_option,
867
- }
879
+ } ) ;
880
+
881
+ hir:: ExprKind :: Closure ( c)
868
882
} )
869
883
}
870
884
@@ -906,15 +920,40 @@ impl<'hir> LoweringContext<'_, 'hir> {
906
920
}
907
921
}
908
922
923
+ fn lower_closure_binder < ' c > (
924
+ & mut self ,
925
+ binder : & ' c ClosureBinder ,
926
+ ) -> ( hir:: ClosureBinder , & ' c [ GenericParam ] ) {
927
+ let ( binder, params) = match binder {
928
+ ClosureBinder :: NotPresent => ( hir:: ClosureBinder :: Default , & [ ] [ ..] ) ,
929
+ & ClosureBinder :: For { span, ref generic_params } => {
930
+ let span = self . lower_span ( span) ;
931
+ ( hir:: ClosureBinder :: For { span } , & * * generic_params)
932
+ }
933
+ } ;
934
+
935
+ ( binder, params)
936
+ }
937
+
909
938
fn lower_expr_async_closure (
910
939
& mut self ,
940
+ binder : & ClosureBinder ,
911
941
capture_clause : CaptureBy ,
912
942
closure_id : NodeId ,
913
943
inner_closure_id : NodeId ,
914
944
decl : & FnDecl ,
915
945
body : & Expr ,
916
946
fn_decl_span : Span ,
917
947
) -> hir:: ExprKind < ' hir > {
948
+ if let & ClosureBinder :: For { span, .. } = binder {
949
+ self . tcx . sess . span_err (
950
+ span,
951
+ "`for<...>` binders on `async` closures are not currently supported" ,
952
+ ) ;
953
+ }
954
+
955
+ let ( binder_clause, generic_params) = self . lower_closure_binder ( binder) ;
956
+
918
957
let outer_decl =
919
958
FnDecl { inputs : decl. inputs . clone ( ) , output : FnRetTy :: Default ( fn_decl_span) } ;
920
959
@@ -952,20 +991,22 @@ impl<'hir> LoweringContext<'_, 'hir> {
952
991
body_id
953
992
} ) ;
954
993
955
- self . with_lifetime_binder ( closure_id, & [ ] , |this, bound_generic_params| {
994
+ self . with_lifetime_binder ( closure_id, generic_params , |this, bound_generic_params| {
956
995
// We need to lower the declaration outside the new scope, because we
957
996
// have to conserve the state of being inside a loop condition for the
958
997
// closure argument types.
959
998
let fn_decl = this. lower_fn_decl ( & outer_decl, None , FnDeclKind :: Closure , None ) ;
960
999
961
- hir:: ExprKind :: Closure {
1000
+ let c = self . arena . alloc ( hir:: Closure {
1001
+ binder : binder_clause,
962
1002
capture_clause,
963
1003
bound_generic_params,
964
1004
fn_decl,
965
1005
body,
966
1006
fn_decl_span : this. lower_span ( fn_decl_span) ,
967
1007
movability : None ,
968
- }
1008
+ } ) ;
1009
+ hir:: ExprKind :: Closure ( c)
969
1010
} )
970
1011
}
971
1012
0 commit comments