diff options
| author | bors <bors@rust-lang.org> | 2023-12-08 19:13:57 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2023-12-08 19:13:57 +0000 |
| commit | f967532a47eb728ada44473a5c4c2eca1a45fe30 (patch) | |
| tree | 91c956dc1e6855e56e9422b32d3419bb540fb27d /src/tools/rustfmt | |
| parent | 2b399b52753eac351067e73f4ff0de829443b9a7 (diff) | |
| parent | 11375c86571ce58646e84cf47df884a3bc2a9934 (diff) | |
| download | rust-f967532a47eb728ada44473a5c4c2eca1a45fe30.tar.gz rust-f967532a47eb728ada44473a5c4c2eca1a45fe30.zip | |
Auto merge of #118420 - compiler-errors:async-gen, r=eholk
Introduce support for `async gen` blocks I'm delighted to demonstrate that `async gen` block are not very difficult to support. They're simply coroutines that yield `Poll<Option<T>>` and return `()`. **This PR is WIP and in draft mode for now** -- I'm mostly putting it up to show folks that it's possible. This PR needs a lang-team experiment associated with it or possible an RFC, since I don't think it falls under the jurisdiction of the `gen` RFC that was recently authored by oli (https://github.com/rust-lang/rfcs/pull/3513, https://github.com/rust-lang/rust/issues/117078). ### Technical note on the pre-generator-transform yield type: The reason that the underlying coroutines yield `Poll<Option<T>>` and not `Poll<T>` (which would make more sense, IMO, for the pre-transformed coroutine), is because the `TransformVisitor` that is used to turn coroutines into built-in state machine functions would have to destructure and reconstruct the latter into the former, which requires at least inserting a new basic block (for a `switchInt` terminator, to match on the `Poll` discriminant). This does mean that the desugaring (at the `rustc_ast_lowering` level) of `async gen` blocks is a bit more involved. However, since we already need to intercept both `.await` and `yield` operators, I don't consider it much of a technical burden. r? `@ghost`
Diffstat (limited to 'src/tools/rustfmt')
| -rw-r--r-- | src/tools/rustfmt/src/closures.rs | 22 | ||||
| -rw-r--r-- | src/tools/rustfmt/src/expr.rs | 2 | ||||
| -rw-r--r-- | src/tools/rustfmt/src/items.rs | 10 | ||||
| -rw-r--r-- | src/tools/rustfmt/src/utils.rs | 5 |
4 files changed, 25 insertions, 14 deletions
diff --git a/src/tools/rustfmt/src/closures.rs b/src/tools/rustfmt/src/closures.rs index c1ce87eadcb..f698f494ae5 100644 --- a/src/tools/rustfmt/src/closures.rs +++ b/src/tools/rustfmt/src/closures.rs @@ -29,7 +29,7 @@ pub(crate) fn rewrite_closure( binder: &ast::ClosureBinder, constness: ast::Const, capture: ast::CaptureBy, - coro_kind: &Option<ast::CoroutineKind>, + coroutine_kind: &Option<ast::CoroutineKind>, movability: ast::Movability, fn_decl: &ast::FnDecl, body: &ast::Expr, @@ -40,7 +40,16 @@ pub(crate) fn rewrite_closure( debug!("rewrite_closure {:?}", body); let (prefix, extra_offset) = rewrite_closure_fn_decl( - binder, constness, capture, coro_kind, movability, fn_decl, body, span, context, shape, + binder, + constness, + capture, + coroutine_kind, + movability, + fn_decl, + body, + span, + context, + shape, )?; // 1 = space between `|...|` and body. let body_shape = shape.offset_left(extra_offset)?; @@ -233,7 +242,7 @@ fn rewrite_closure_fn_decl( binder: &ast::ClosureBinder, constness: ast::Const, capture: ast::CaptureBy, - coro_kind: &Option<ast::CoroutineKind>, + coroutine_kind: &Option<ast::CoroutineKind>, movability: ast::Movability, fn_decl: &ast::FnDecl, body: &ast::Expr, @@ -263,9 +272,10 @@ fn rewrite_closure_fn_decl( } else { "" }; - let coro = match coro_kind { + let coro = match coroutine_kind { Some(ast::CoroutineKind::Async { .. }) => "async ", Some(ast::CoroutineKind::Gen { .. }) => "gen ", + Some(ast::CoroutineKind::AsyncGen { .. }) => "async gen ", None => "", }; let mover = if matches!(capture, ast::CaptureBy::Value { .. }) { @@ -343,7 +353,7 @@ pub(crate) fn rewrite_last_closure( ref binder, constness, capture_clause, - ref coro_kind, + ref coroutine_kind, movability, ref fn_decl, ref body, @@ -364,7 +374,7 @@ pub(crate) fn rewrite_last_closure( binder, constness, capture_clause, - coro_kind, + coroutine_kind, movability, fn_decl, body, diff --git a/src/tools/rustfmt/src/expr.rs b/src/tools/rustfmt/src/expr.rs index 4515c27be37..a68bd6694ba 100644 --- a/src/tools/rustfmt/src/expr.rs +++ b/src/tools/rustfmt/src/expr.rs @@ -212,7 +212,7 @@ pub(crate) fn format_expr( &cl.binder, cl.constness, cl.capture_clause, - &cl.coro_kind, + &cl.coroutine_kind, cl.movability, &cl.fn_decl, &cl.body, diff --git a/src/tools/rustfmt/src/items.rs b/src/tools/rustfmt/src/items.rs index 4dff65f8cd0..a4256730f19 100644 --- a/src/tools/rustfmt/src/items.rs +++ b/src/tools/rustfmt/src/items.rs @@ -287,7 +287,7 @@ pub(crate) struct FnSig<'a> { decl: &'a ast::FnDecl, generics: &'a ast::Generics, ext: ast::Extern, - coro_kind: Cow<'a, Option<ast::CoroutineKind>>, + coroutine_kind: Cow<'a, Option<ast::CoroutineKind>>, constness: ast::Const, defaultness: ast::Defaultness, unsafety: ast::Unsafe, @@ -302,7 +302,7 @@ impl<'a> FnSig<'a> { ) -> FnSig<'a> { FnSig { unsafety: method_sig.header.unsafety, - coro_kind: Cow::Borrowed(&method_sig.header.coro_kind), + coroutine_kind: Cow::Borrowed(&method_sig.header.coroutine_kind), constness: method_sig.header.constness, defaultness: ast::Defaultness::Final, ext: method_sig.header.ext, @@ -328,7 +328,7 @@ impl<'a> FnSig<'a> { generics, ext: fn_sig.header.ext, constness: fn_sig.header.constness, - coro_kind: Cow::Borrowed(&fn_sig.header.coro_kind), + coroutine_kind: Cow::Borrowed(&fn_sig.header.coroutine_kind), defaultness, unsafety: fn_sig.header.unsafety, visibility: vis, @@ -343,8 +343,8 @@ impl<'a> FnSig<'a> { result.push_str(&*format_visibility(context, self.visibility)); result.push_str(format_defaultness(self.defaultness)); result.push_str(format_constness(self.constness)); - self.coro_kind - .map(|coro_kind| result.push_str(format_coro(&coro_kind))); + self.coroutine_kind + .map(|coroutine_kind| result.push_str(format_coro(&coroutine_kind))); result.push_str(format_unsafety(self.unsafety)); result.push_str(&format_extern( self.ext, diff --git a/src/tools/rustfmt/src/utils.rs b/src/tools/rustfmt/src/utils.rs index 5805e417c04..7d7bbf11529 100644 --- a/src/tools/rustfmt/src/utils.rs +++ b/src/tools/rustfmt/src/utils.rs @@ -75,10 +75,11 @@ pub(crate) fn format_visibility( } #[inline] -pub(crate) fn format_coro(coro_kind: &ast::CoroutineKind) -> &'static str { - match coro_kind { +pub(crate) fn format_coro(coroutine_kind: &ast::CoroutineKind) -> &'static str { + match coroutine_kind { ast::CoroutineKind::Async { .. } => "async ", ast::CoroutineKind::Gen { .. } => "gen ", + ast::CoroutineKind::AsyncGen { .. } => "async gen ", } } |
