[PATCH] D115219: [C++20] [Coroutines] Mark coroutine done if unhandled_exception throws
Chuanqi Xu via Phabricator via llvm-commits
llvm-commits at lists.llvm.org
Mon Dec 6 22:15:09 PST 2021
ChuanqiXu created this revision.
ChuanqiXu added reviewers: rjmccall, lxfind, junparser, ychen, aaron.ballman.
ChuanqiXu added projects: clang, LLVM.
Herald added a subscriber: hiraditya.
ChuanqiXu requested review of this revision.
Herald added subscribers: llvm-commits, cfe-commits, jdoerfert.
[[dcl.fct.def.coroutine]/p14](https://eel.is/c++draft/dcl.fct.def.coroutine#14) says:
> If the evaluation of the expression promise.unhandled_exception() exits via an exception, the coroutine is considered suspended at the final suspend point.
However, this is not implemented in clang. We could observe this from: https://godbolt.org/z/Edr59d5Y6.
This patch tries to implement [dcl.fct.def.coroutine]/p14 by rewrite the call to `promise.unhandled_exception()` into:
C++
try {
promise.unhandled_exception();
} catch(...) {
__builtin_coro_mark_done();
throw;
}
And this patch introduces another coroutine intrinsic: `llvm.coro.mark.done()`. This would mark the coroutine done (suspended at the final suspend). Previously, this is done by the call to `llvm.coro.suspend(frame, /*IsFinal=*/true)`. There are two reasons why I choose to create a new intrinsic:
- The semantic isn't correct if we try to use `llvm.coro.suspend(, /*IsFinal=*/true)`. First, there is nothing to suspend. Second, `llvm.coro.suspend` has more semantics than `llvm.coro.mark.done`. So it seems inappropriate to reuse `llvm.coro.suspend`.
- The implementation would be more simple and robust if we use new intrinsics. There are codes treating `llvm.coro.suspend` specially. It is necessary to construct the structure of the coroutine. And it would be complicated if we reuse `llvm.coro.suspend(, /*IsFinal*/true)` in an inappropriate place.
After this patch, the behavior of this example would be the same with GCC: https://godbolt.org/z/rh86xKf85.
Test Plan: check-all, https://godbolt.org/z/rh86xKf85 and an internal coroutine library
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D115219
Files:
clang/docs/LanguageExtensions.rst
clang/include/clang/Basic/Builtins.def
clang/lib/CodeGen/CGBuiltin.cpp
clang/lib/Sema/SemaCoroutine.cpp
clang/test/CodeGenCoroutines/coro-await-resume-eh-exp-namespace.cpp
clang/test/CodeGenCoroutines/coro-await-resume-eh.cpp
clang/test/CodeGenCoroutines/coro-throw-from-unhandled_exception.cpp
llvm/docs/Coroutines.rst
llvm/include/llvm/Analysis/TargetTransformInfoImpl.h
llvm/include/llvm/IR/Intrinsics.td
llvm/lib/Transforms/Coroutines/CoroInstr.h
llvm/lib/Transforms/Coroutines/CoroInternal.h
llvm/lib/Transforms/Coroutines/CoroSplit.cpp
llvm/lib/Transforms/Coroutines/Coroutines.cpp
llvm/test/Transforms/Coroutines/coro-mark-done.ll
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D115219.392265.patch
Type: text/x-patch
Size: 15186 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20211207/13b3d0b2/attachment.bin>
More information about the llvm-commits
mailing list