]> git.ipfire.org Git - thirdparty/gcc.git/commit
c++, coroutines: Avoid expanding within templates [PR103868]
authorNathan Sidwell <nathan@acm.org>
Sun, 3 Apr 2022 10:35:03 +0000 (11:35 +0100)
committerIain Sandoe <iain@sandoe.co.uk>
Thu, 28 Apr 2022 12:50:59 +0000 (13:50 +0100)
commit9cb1f565a91e2dd57098c43593954b57c065a19b
tree55d535c120e524211424cc60e94a2c750871be28
parentd314907fc47f533ab27e8e1a57c09516ec1ac5e2
c++, coroutines: Avoid expanding within templates [PR103868]

This is a forward-port of a patch by Nathan (against 10.x) which fixes an open
PR.

We are ICEing because we ended up tsubst_copying something that had already
been tsubst, leading to an assert failure (mostly such repeated tsubsting is
harmless).

We had a non-dependent co_await in a non-dependent-type template fn, so we
processed it at definition time, and then reprocessed at instantiation time.
We fix this here by deferring substitution while processing templates.

Additional observations (for a better future fix, in the GCC13 timescale):

Exprs only have dependent type if at least one operand is dependent which was
what the current code was intending to do.  Coroutines have the additional
wrinkle, that the current fn's type is an implicit operand.

So, if the coroutine function's type is not dependent, and the operand is not
dependent, we should determine the type of the co_await expression using the
DEPENDENT_EXPR wrapper machinery.  That allows us to determine the
subexpression type, but leave its operand unchanged and then instantiate it
later.

PR c++/103868

gcc/cp/ChangeLog:

* coroutines.cc (finish_co_await_expr): Do not process non-dependent
coroutine expressions at template definition time.
(finish_co_yield_expr): Likewise.
(finish_co_return_stmt): Likewise.

gcc/testsuite/ChangeLog:

* g++.dg/coroutines/pr103868.C: New test.

Co-Authored-by: Iain Sandoe <iain@sandoe.co.uk>
gcc/cp/coroutines.cc
gcc/testsuite/g++.dg/coroutines/pr103868.C [new file with mode: 0644]