Skip to content

Commit c845f3d

Browse files
committed
track the kind of async generator we are creating
1 parent f2023ac commit c845f3d

File tree

5 files changed

+52
-15
lines changed

5 files changed

+52
-15
lines changed

src/librustc/hir/lowering/expr.rs

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -89,9 +89,14 @@ impl LoweringContext<'_> {
8989
hir::MatchSource::Normal,
9090
),
9191
ExprKind::Async(capture_clause, closure_node_id, ref block) => {
92-
self.make_async_expr(capture_clause, closure_node_id, None, block.span, |this| {
93-
this.with_new_scopes(|this| this.lower_block_expr(block))
94-
})
92+
self.make_async_expr(
93+
capture_clause,
94+
closure_node_id,
95+
None,
96+
block.span,
97+
hir::AsyncGeneratorKind::Block,
98+
|this| this.with_new_scopes(|this| this.lower_block_expr(block)),
99+
)
95100
}
96101
ExprKind::Await(ref expr) => self.lower_expr_await(e.span, expr),
97102
ExprKind::Closure(
@@ -440,6 +445,7 @@ impl LoweringContext<'_> {
440445
closure_node_id: NodeId,
441446
ret_ty: Option<AstP<Ty>>,
442447
span: Span,
448+
async_gen_kind: hir::AsyncGeneratorKind,
443449
body: impl FnOnce(&mut LoweringContext<'_>) -> hir::Expr,
444450
) -> hir::ExprKind {
445451
let capture_clause = self.lower_capture_clause(capture_clause);
@@ -453,7 +459,7 @@ impl LoweringContext<'_> {
453459
};
454460
let decl = self.lower_fn_decl(&ast_decl, None, /* impl trait allowed */ false, None);
455461
let body_id = self.lower_fn_body(&ast_decl, |this| {
456-
this.generator_kind = Some(hir::GeneratorKind::Async);
462+
this.generator_kind = Some(hir::GeneratorKind::Async(async_gen_kind));
457463
body(this)
458464
});
459465

@@ -505,7 +511,7 @@ impl LoweringContext<'_> {
505511
/// ```
506512
fn lower_expr_await(&mut self, await_span: Span, expr: &Expr) -> hir::ExprKind {
507513
match self.generator_kind {
508-
Some(hir::GeneratorKind::Async) => {},
514+
Some(hir::GeneratorKind::Async(_)) => {},
509515
Some(hir::GeneratorKind::Gen) |
510516
None => {
511517
let mut err = struct_span_err!(
@@ -710,7 +716,7 @@ impl LoweringContext<'_> {
710716
Movability::Static => hir::GeneratorMovability::Static,
711717
})
712718
},
713-
Some(hir::GeneratorKind::Async) => {
719+
Some(hir::GeneratorKind::Async(_)) => {
714720
bug!("non-`async` closure body turned `async` during lowering");
715721
},
716722
None => {
@@ -769,7 +775,7 @@ impl LoweringContext<'_> {
769775
None
770776
};
771777
let async_body = this.make_async_expr(
772-
capture_clause, closure_id, async_ret_ty, body.span,
778+
capture_clause, closure_id, async_ret_ty, body.span, hir::AsyncGeneratorKind::Closure,
773779
|this| {
774780
this.with_new_scopes(|this| this.lower_expr(body))
775781
}
@@ -988,7 +994,7 @@ impl LoweringContext<'_> {
988994
fn lower_expr_yield(&mut self, span: Span, opt_expr: Option<&Expr>) -> hir::ExprKind {
989995
match self.generator_kind {
990996
Some(hir::GeneratorKind::Gen) => {},
991-
Some(hir::GeneratorKind::Async) => {
997+
Some(hir::GeneratorKind::Async(_)) => {
992998
span_err!(
993999
self.sess,
9941000
span,

src/librustc/hir/lowering/item.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1222,7 +1222,11 @@ impl LoweringContext<'_> {
12221222
}
12231223

12241224
let async_expr = this.make_async_expr(
1225-
CaptureBy::Value, closure_id, None, body.span,
1225+
CaptureBy::Value,
1226+
closure_id,
1227+
None,
1228+
body.span,
1229+
hir::AsyncGeneratorKind::Fn,
12261230
|this| {
12271231
// Create a block from the user's function body:
12281232
let user_body = this.lower_block_expr(body);

src/librustc/hir/mod.rs

Lines changed: 31 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1366,17 +1366,43 @@ impl Body {
13661366
#[derive(Clone, PartialEq, Eq, PartialOrd, Ord, HashStable,
13671367
RustcEncodable, RustcDecodable, Hash, Debug, Copy)]
13681368
pub enum GeneratorKind {
1369-
/// An `async` block or function.
1370-
Async,
1369+
/// An explicit `async` block or the body of an async function.
1370+
Async(AsyncGeneratorKind),
1371+
13711372
/// A generator literal created via a `yield` inside a closure.
13721373
Gen,
13731374
}
13741375

13751376
impl fmt::Display for GeneratorKind {
1377+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1378+
match self {
1379+
GeneratorKind::Async(k) => fmt::Display::fmt(k, f),
1380+
GeneratorKind::Gen => f.write_str("generator"),
1381+
}
1382+
}
1383+
}
1384+
1385+
/// The type of source expression that caused this generator to be created.
1386+
// Not `IsAsync` because we want to eventually add support for `AsyncGen`
1387+
#[derive(Clone, PartialEq, Eq, PartialOrd, Ord, HashStable,
1388+
RustcEncodable, RustcDecodable, Hash, Debug, Copy)]
1389+
pub enum AsyncGeneratorKind {
1390+
/// An explicit `async` block written by the user.
1391+
Block,
1392+
1393+
/// An explicit `async` block written by the user.
1394+
Closure,
1395+
1396+
/// The `async` block generated as the body of an async function.
1397+
Fn,
1398+
}
1399+
1400+
impl fmt::Display for AsyncGeneratorKind {
13761401
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
13771402
f.write_str(match self {
1378-
GeneratorKind::Async => "`async` object",
1379-
GeneratorKind::Gen => "generator",
1403+
AsyncGeneratorKind::Block => "`async` block",
1404+
AsyncGeneratorKind::Closure => "`async` closure body",
1405+
AsyncGeneratorKind::Fn => "`async` fn body",
13801406
})
13811407
}
13821408
}
@@ -1758,6 +1784,7 @@ pub struct Destination {
17581784
pub enum GeneratorMovability {
17591785
/// May contain self-references, `!Unpin`.
17601786
Static,
1787+
17611788
/// Must not contain self-references, `Unpin`.
17621789
Movable,
17631790
}

src/librustc_typeck/check/generator_interior.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ impl<'a, 'tcx> InteriorVisitor<'a, 'tcx> {
5555
expr_and_pat_count: 0,
5656
source: match self.kind { // Guess based on the kind of the current generator.
5757
hir::GeneratorKind::Gen => hir::YieldSource::Yield,
58-
hir::GeneratorKind::Async => hir::YieldSource::Await,
58+
hir::GeneratorKind::Async(_) => hir::YieldSource::Await,
5959
},
6060
}));
6161

src/librustc_typeck/check/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4534,7 +4534,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
45344534
let item_id = self.tcx().hir().get_parent_node(self.body_id);
45354535
if let Some(body_id) = self.tcx().hir().maybe_body_owned_by(item_id) {
45364536
let body = self.tcx().hir().body(body_id);
4537-
if let Some(hir::GeneratorKind::Async) = body.generator_kind {
4537+
if let Some(hir::GeneratorKind::Async(_)) = body.generator_kind {
45384538
let sp = expr.span;
45394539
// Check for `Future` implementations by constructing a predicate to
45404540
// prove: `<T as Future>::Output == U`

0 commit comments

Comments
 (0)