The check was intended to assert that we had visited contained
ternary expressions with embedded co_awaits, but had been made
too general - and therefore was ICEing on code that was actually
OK. Fixed by checking specifically that no co_awaits embedded.
PR c++/109283
gcc/cp/ChangeLog:
* coroutines.cc (find_any_await): Only save the statement
pointer if the caller passes a place for it.
(flatten_await_stmt): When checking that ternary expressions
have been handled, also check that they contain a co_await.
gcc/testsuite/ChangeLog:
* g++.dg/coroutines/pr109283.C: New test.
Signed-off-by: Iain Sandoe <iain@sandoe.co.uk>
(cherry picked from commit
977fadd69776e2a8a6daca43e1c898bc4f87154d)
if (TREE_CODE (*stmt) == CO_AWAIT_EXPR)
{
*dosub = 0; /* We don't need to consider this any further. */
- tree **p = (tree **) d;
- *p = stmt;
+ if (d)
+ *(tree **)d = stmt;
return *stmt;
}
return NULL_TREE;
bool already_present = promoted->add (var);
gcc_checking_assert (!already_present);
tree inner = TARGET_EXPR_INITIAL (init);
- gcc_checking_assert (TREE_CODE (inner) != COND_EXPR);
+ gcc_checking_assert
+ (TREE_CODE (inner) != COND_EXPR
+ || !cp_walk_tree (&inner, find_any_await, nullptr, nullptr));
init = cp_build_modify_expr (input_location, var, INIT_EXPR, init,
tf_warning_or_error);
/* Simplify for the case that we have an init containing the temp
--- /dev/null
+// PR 109283.
+// This used to ICE from a check set too widely.
+#include <coroutine>
+
+struct foo
+{ ~foo(); };
+
+struct task
+{
+ struct promise_type
+ {
+ std::suspend_never initial_suspend();
+ std::suspend_never final_suspend() noexcept;
+ std::suspend_never yield_value(foo);
+ void return_void();
+ void unhandled_exception();
+ task get_return_object();
+ };
+};
+
+task source(int b) {
+ co_yield b ? foo{} : foo{};
+}