Skip to content

Commit c67193b

Browse files
committed
Merge Async and Gen into CoroutineKind
1 parent 4f03c3f commit c67193b

File tree

25 files changed

+246
-239
lines changed

25 files changed

+246
-239
lines changed

compiler/rustc_ast/src/ast.rs

+30-24
Original file line numberDiff line numberDiff line change
@@ -1296,7 +1296,7 @@ pub struct Closure {
12961296
pub binder: ClosureBinder,
12971297
pub capture_clause: CaptureBy,
12981298
pub constness: Const,
1299-
pub asyncness: Async,
1299+
pub coro_kind: CoroutineKind,
13001300
pub movability: Movability,
13011301
pub fn_decl: P<FnDecl>,
13021302
pub body: P<Expr>,
@@ -2379,28 +2379,38 @@ pub enum Unsafe {
23792379
No,
23802380
}
23812381

2382+
/// Describes what kind of coroutine markers, if any, a function has.
2383+
///
2384+
/// Coroutine markers are things that cause the function to generate a coroutine, such as `async`,
2385+
/// which makes the function return `impl Future`, or `gen`, which makes the function return `impl
2386+
/// Iterator`.
23822387
#[derive(Copy, Clone, Encodable, Decodable, Debug)]
2383-
pub enum Async {
2384-
Yes { span: Span, closure_id: NodeId, return_impl_trait_id: NodeId },
2385-
No,
2386-
}
2387-
2388-
#[derive(Copy, Clone, Encodable, Decodable, Debug)]
2389-
pub enum Gen {
2390-
Yes { span: Span, closure_id: NodeId, return_impl_trait_id: NodeId },
2391-
No,
2388+
pub enum CoroutineKind {
2389+
/// `async`, which evaluates to `impl Future`
2390+
Async { span: Span, closure_id: NodeId, return_impl_trait_id: NodeId },
2391+
/// `gen`, which evaluates to `impl Iterator`
2392+
Gen { span: Span, closure_id: NodeId, return_impl_trait_id: NodeId },
2393+
/// Neither `async` nor `gen`
2394+
None,
23922395
}
23932396

2394-
impl Async {
2397+
impl CoroutineKind {
23952398
pub fn is_async(self) -> bool {
2396-
matches!(self, Async::Yes { .. })
2399+
matches!(self, CoroutineKind::Async { .. })
2400+
}
2401+
2402+
pub fn is_gen(self) -> bool {
2403+
matches!(self, CoroutineKind::Gen { .. })
23972404
}
23982405

23992406
/// In this case this is an `async` return, the `NodeId` for the generated `impl Trait` item.
24002407
pub fn opt_return_id(self) -> Option<(NodeId, Span)> {
24012408
match self {
2402-
Async::Yes { return_impl_trait_id, span, .. } => Some((return_impl_trait_id, span)),
2403-
Async::No => None,
2409+
CoroutineKind::Async { return_impl_trait_id, span, .. }
2410+
| CoroutineKind::Gen { return_impl_trait_id, span, .. } => {
2411+
Some((return_impl_trait_id, span))
2412+
}
2413+
CoroutineKind::None => None,
24042414
}
24052415
}
24062416
}
@@ -2804,36 +2814,32 @@ impl Extern {
28042814
pub struct FnHeader {
28052815
/// The `unsafe` keyword, if any
28062816
pub unsafety: Unsafe,
2807-
/// The `async` keyword, if any
2808-
pub asyncness: Async,
2817+
/// Whether this is `async`, `gen`, or nothing.
2818+
pub coro_kind: CoroutineKind,
28092819
/// The `const` keyword, if any
28102820
pub constness: Const,
28112821
/// The `extern` keyword and corresponding ABI string, if any
28122822
pub ext: Extern,
2813-
/// The `gen` keyword, if any
2814-
pub genness: Gen,
28152823
}
28162824

28172825
impl FnHeader {
28182826
/// Does this function header have any qualifiers or is it empty?
28192827
pub fn has_qualifiers(&self) -> bool {
2820-
let Self { unsafety, asyncness, constness, ext, genness } = self;
2828+
let Self { unsafety, coro_kind, constness, ext } = self;
28212829
matches!(unsafety, Unsafe::Yes(_))
2822-
|| asyncness.is_async()
2830+
|| !matches!(coro_kind, CoroutineKind::None)
28232831
|| matches!(constness, Const::Yes(_))
28242832
|| !matches!(ext, Extern::None)
2825-
|| matches!(genness, Gen::Yes { .. })
28262833
}
28272834
}
28282835

28292836
impl Default for FnHeader {
28302837
fn default() -> FnHeader {
28312838
FnHeader {
28322839
unsafety: Unsafe::No,
2833-
asyncness: Async::No,
2840+
coro_kind: CoroutineKind::None,
28342841
constness: Const::No,
28352842
ext: Extern::None,
2836-
genness: Gen::No,
28372843
}
28382844
}
28392845
}
@@ -3154,7 +3160,7 @@ mod size_asserts {
31543160
static_assert_size!(Block, 32);
31553161
static_assert_size!(Expr, 72);
31563162
static_assert_size!(ExprKind, 40);
3157-
static_assert_size!(Fn, 168);
3163+
static_assert_size!(Fn, 160);
31583164
static_assert_size!(ForeignItem, 96);
31593165
static_assert_size!(ForeignItemKind, 24);
31603166
static_assert_size!(GenericArg, 24);

compiler/rustc_ast/src/mut_visit.rs

+11-25
Original file line numberDiff line numberDiff line change
@@ -121,12 +121,8 @@ pub trait MutVisitor: Sized {
121121
noop_visit_fn_decl(d, self);
122122
}
123123

124-
fn visit_asyncness(&mut self, a: &mut Async) {
125-
noop_visit_asyncness(a, self);
126-
}
127-
128-
fn visit_genness(&mut self, a: &mut Gen) {
129-
noop_visit_genness(a, self);
124+
fn visit_coro_kind(&mut self, a: &mut CoroutineKind) {
125+
noop_visit_coro_kind(a, self);
130126
}
131127

132128
fn visit_closure_binder(&mut self, b: &mut ClosureBinder) {
@@ -875,23 +871,14 @@ pub fn noop_visit_closure_binder<T: MutVisitor>(binder: &mut ClosureBinder, vis:
875871
}
876872
}
877873

878-
pub fn noop_visit_asyncness<T: MutVisitor>(asyncness: &mut Async, vis: &mut T) {
879-
match asyncness {
880-
Async::Yes { span: _, closure_id, return_impl_trait_id } => {
881-
vis.visit_id(closure_id);
882-
vis.visit_id(return_impl_trait_id);
883-
}
884-
Async::No => {}
885-
}
886-
}
887-
888-
pub fn noop_visit_genness<T: MutVisitor>(genness: &mut Gen, vis: &mut T) {
889-
match genness {
890-
Gen::Yes { span: _, closure_id, return_impl_trait_id } => {
874+
pub fn noop_visit_coro_kind<T: MutVisitor>(coro_kind: &mut CoroutineKind, vis: &mut T) {
875+
match coro_kind {
876+
CoroutineKind::Async { span: _, closure_id, return_impl_trait_id }
877+
| CoroutineKind::Gen { span: _, closure_id, return_impl_trait_id } => {
891878
vis.visit_id(closure_id);
892879
vis.visit_id(return_impl_trait_id);
893880
}
894-
Gen::No => {}
881+
CoroutineKind::None => {}
895882
}
896883
}
897884

@@ -1184,10 +1171,9 @@ fn visit_const_item<T: MutVisitor>(
11841171
}
11851172

11861173
pub fn noop_visit_fn_header<T: MutVisitor>(header: &mut FnHeader, vis: &mut T) {
1187-
let FnHeader { unsafety, asyncness, constness, ext: _, genness } = header;
1174+
let FnHeader { unsafety, coro_kind, constness, ext: _ } = header;
11881175
visit_constness(constness, vis);
1189-
vis.visit_asyncness(asyncness);
1190-
vis.visit_genness(genness);
1176+
vis.visit_coro_kind(coro_kind);
11911177
visit_unsafety(unsafety, vis);
11921178
}
11931179

@@ -1421,7 +1407,7 @@ pub fn noop_visit_expr<T: MutVisitor>(
14211407
binder,
14221408
capture_clause,
14231409
constness,
1424-
asyncness,
1410+
coro_kind,
14251411
movability: _,
14261412
fn_decl,
14271413
body,
@@ -1430,7 +1416,7 @@ pub fn noop_visit_expr<T: MutVisitor>(
14301416
}) => {
14311417
vis.visit_closure_binder(binder);
14321418
visit_constness(constness, vis);
1433-
vis.visit_asyncness(asyncness);
1419+
vis.visit_coro_kind(coro_kind);
14341420
vis.visit_capture_by(capture_clause);
14351421
vis.visit_fn_decl(fn_decl);
14361422
vis.visit_expr(body);

compiler/rustc_ast/src/visit.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -861,7 +861,7 @@ pub fn walk_expr<'a, V: Visitor<'a>>(visitor: &mut V, expression: &'a Expr) {
861861
ExprKind::Closure(box Closure {
862862
binder,
863863
capture_clause,
864-
asyncness: _,
864+
coro_kind: _,
865865
constness: _,
866866
movability: _,
867867
fn_decl,

compiler/rustc_ast_lowering/src/expr.rs

+42-30
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ use rustc_data_structures::stack::ensure_sufficient_stack;
1414
use rustc_hir as hir;
1515
use rustc_hir::def::{DefKind, Res};
1616
use rustc_hir::definitions::DefPathData;
17+
use rustc_middle::span_bug;
1718
use rustc_session::errors::report_lit_error;
1819
use rustc_span::source_map::{respan, Spanned};
1920
use rustc_span::symbol::{sym, Ident, Symbol};
@@ -196,39 +197,39 @@ impl<'hir> LoweringContext<'_, 'hir> {
196197
binder,
197198
capture_clause,
198199
constness,
199-
asyncness,
200+
coro_kind,
200201
movability,
201202
fn_decl,
202203
body,
203204
fn_decl_span,
204205
fn_arg_span,
205-
}) => {
206-
if let Async::Yes { closure_id, .. } = asyncness {
207-
self.lower_expr_async_closure(
208-
binder,
209-
*capture_clause,
210-
e.id,
211-
hir_id,
212-
*closure_id,
213-
fn_decl,
214-
body,
215-
*fn_decl_span,
216-
*fn_arg_span,
217-
)
218-
} else {
219-
self.lower_expr_closure(
220-
binder,
221-
*capture_clause,
222-
e.id,
223-
*constness,
224-
*movability,
225-
fn_decl,
226-
body,
227-
*fn_decl_span,
228-
*fn_arg_span,
229-
)
206+
}) => match coro_kind {
207+
CoroutineKind::Async { closure_id, .. } => self.lower_expr_async_closure(
208+
binder,
209+
*capture_clause,
210+
e.id,
211+
hir_id,
212+
*closure_id,
213+
fn_decl,
214+
body,
215+
*fn_decl_span,
216+
*fn_arg_span,
217+
),
218+
CoroutineKind::Gen { .. } => {
219+
span_bug!(e.span, "generator closures are not allowed")
230220
}
231-
}
221+
CoroutineKind::None => self.lower_expr_closure(
222+
binder,
223+
*capture_clause,
224+
e.id,
225+
*constness,
226+
*movability,
227+
fn_decl,
228+
body,
229+
*fn_decl_span,
230+
*fn_arg_span,
231+
),
232+
},
232233
ExprKind::Block(blk, opt_label) => {
233234
let opt_label = self.lower_label(*opt_label);
234235
hir::ExprKind::Block(self.lower_block(blk, opt_label.is_some()), opt_label)
@@ -958,7 +959,13 @@ impl<'hir> LoweringContext<'_, 'hir> {
958959

959960
let bound_generic_params = self.lower_lifetime_binder(closure_id, generic_params);
960961
// Lower outside new scope to preserve `is_in_loop_condition`.
961-
let fn_decl = self.lower_fn_decl(decl, closure_id, fn_decl_span, FnDeclKind::Closure, None);
962+
let fn_decl = self.lower_fn_decl(
963+
decl,
964+
closure_id,
965+
fn_decl_span,
966+
FnDeclKind::Closure,
967+
CoroutineKind::None,
968+
);
962969

963970
let c = self.arena.alloc(hir::Closure {
964971
def_id: self.local_def_id(closure_id),
@@ -1073,8 +1080,13 @@ impl<'hir> LoweringContext<'_, 'hir> {
10731080
// We need to lower the declaration outside the new scope, because we
10741081
// have to conserve the state of being inside a loop condition for the
10751082
// closure argument types.
1076-
let fn_decl =
1077-
self.lower_fn_decl(&outer_decl, closure_id, fn_decl_span, FnDeclKind::Closure, None);
1083+
let fn_decl = self.lower_fn_decl(
1084+
&outer_decl,
1085+
closure_id,
1086+
fn_decl_span,
1087+
FnDeclKind::Closure,
1088+
CoroutineKind::None,
1089+
);
10781090

10791091
let c = self.arena.alloc(hir::Closure {
10801092
def_id: self.local_def_id(closure_id),

0 commit comments

Comments
 (0)