mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-03-23 00:51:19 +08:00
Although the note in the text [expr.await] / 5.1.1 is not normative, it is asserted by users that an implementation that is unable to perform unlimited symmetric transfers is not terribly useful. This relates to the following circumstance: try { users-function-body: { .... { some suspend context continuation_handle = await_suspend (another handle); continuation_handle.resume (); 'return' (actually a suspension operation). } } } catch (...) {} The call to 'continuation_handle.resume ()' needs to be a tail- call in order that an arbitrary number of coroutines can be handled in this manner. There are two issues with this: 1. That the user's function body is wrapped in a try/catch block and one cannot tail-call from within those. 2. That GCC doesn't usually produce tail-calls when the optimisation level is < O2. After considerable discussion at WG21 meetings, it has been determined that the intent is that the operation behaves as if the resume call is executed in the context of the caller. So, we can remap the fragment above like this: { void_coroutine_handle continuation; try { users-function-body: { .... { some suspend context continuation = await_suspend (another handle); <scope exit without cleanup> symmetric_transfer; } } } catch (...) {} symmetric_transfer: continuation.resume(); [tail call] [must tail call] } Thus we take the call outside the try-catch block which solves issue (1) and mark it as a tail call and as "must tail call" for correctness which solves (2). As bonuses, since we no longer need to differentiate handle types returned from await_suspend() methods, nor do we need to keep them in the coroutine frame, since they are ephemeral, we save entries in the frame and reduce some code too. gcc/cp/ChangeLog: 2020-03-26 Iain Sandoe <iain@sandoe.co.uk> * coroutines.cc (coro_init_identifiers): Initialize an identifier for the cororoutine handle 'address' method name. (struct coro_aw_data): Add fields to cover the continuations. (co_await_expander): Determine the kind of await_suspend in use. If we have the case that returns a continuation handle, then save this and make the target for 'scope exit without cleanup' be the continuation resume label. (expand_co_awaits): Remove. (struct suspend_point_info): Remove fields that kept the returned await_suspend handle type. (transform_await_expr): Remove code tracking continuation handles. (build_actor_fn): Add the continuation handle as an actor-function scope var. Build the symmetric transfer continuation point. Call the tree walk for co_await expansion directly, rather than via a trivial shim function. (register_await_info): Remove fields tracking continuation handles. (get_await_suspend_return_type): Remove. (register_awaits): Remove code tracking continuation handles. (morph_fn_to_coro): Remove code tracking continuation handles. gcc/testsuite/ChangeLog: 2020-03-26 Iain Sandoe <iain@sandoe.co.uk> * g++.dg/coroutines/torture/co-ret-09-bool-await-susp.C: Amend to n4849 behaviour. * g++.dg/coroutines/torture/symmetric-transfer-00-basic.C: New test.
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
…
This directory contains the GNU Compiler Collection (GCC). The GNU Compiler Collection is free software. See the files whose names start with COPYING for copying permission. The manuals, and some of the runtime libraries, are under different terms; see the individual source files for details. The directory INSTALL contains copies of the installation information as HTML and plain text. The source of this information is gcc/doc/install.texi. The installation information includes details of what is included in the GCC sources and what files GCC installs. See the file gcc/doc/gcc.texi (together with other files that it includes) for usage and porting information. An online readable version of the manual is in the files gcc/doc/gcc.info*. See http://gcc.gnu.org/bugs/ for how to report bugs usefully. Copyright years on GCC source files may be listed using range notation, e.g., 1987-2012, indicating that every year in the range, inclusive, is a copyrightable year that could otherwise be listed individually.
Description
Languages
C++
31.9%
C
31.3%
Ada
12%
D
6.5%
Go
6.4%
Other
11.5%