llvmbot wrote:

<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-clang-codegen

Author: Heejin Ahn (aheejin)

<details>
<summary>Changes</summary>

When an exception thrown ends up calling `std::terminate`, for example, because 
an exception is thrown within a `noexcept` function or an exception is thrown 
from `__cxa_end_catch` during handling the previous exception, the libc++abi 
spec says we are supposed to call `__cxa_begin_catch` before `std::terminate`:
https://libcxxabi.llvm.org/spec.html
&gt;  When the personality routine encounters a termination condition, it will 
call `__cxa_begin_catch()` to mark the exception as handled and then call 
`terminate()`, which shall not return to its caller.

The default Itanium ABI generates a call to `__clang_call_terminate()`, which 
is a function that calls `__cxa_begin_catch` and then `std::terminate`:
```ll
define void @<!-- -->__clang_call_terminate(ptr noundef %0) {
  %2 = call ptr @<!-- -->__cxa_begin_catch(ptr %0)
  call void @<!-- -->_ZSt9terminatev()
  unreachable
}
```

But we replaced this with just a call to `std::terminate` in 
https://github.com/llvm/llvm-project/commit/561abd83ffecc8d4ba8fcbbbcadb31efc55985c2
 because this caused some tricky transformation problems for Wasm EH. The 
detailed explanation why is in the commit description, but the summary is for 
Wasm EH it needed a `try` with both `catch` and `catch_all` and it was tricky 
to deal with.

But that commit replaced `__clang_call_terminate` with `std::terminate` for all 
Wasm programs and not only the ones that use Wasm EH. So Emscripten EH was also 
affected by that commit. Emscripten EH is not able to catch foreign exceptions 
anyway, so this is unnecessary compromise.

This makes we use `__clang_call_terminate` as in the default Itanium EH for 
Emscripten EH. We may later fix Wasm EH too but that requires more efforts in 
the backend.

Related issue:
https://github.com/emscripten-core/emscripten/issues/23720

---
Full diff: https://github.com/llvm/llvm-project/pull/129020.diff


3 Files Affected:

- (modified) clang/lib/CodeGen/ItaniumCXXABI.cpp (+7-2) 
- (modified) clang/test/CodeGenCXX/wasm-eh.cpp (+12) 
- (added) clang/test/CodeGenCXX/wasm-em-eh.cpp (+13) 


``````````diff
diff --git a/clang/lib/CodeGen/ItaniumCXXABI.cpp 
b/clang/lib/CodeGen/ItaniumCXXABI.cpp
index bcd171724c41d..f3ffa0b2e84c1 100644
--- a/clang/lib/CodeGen/ItaniumCXXABI.cpp
+++ b/clang/lib/CodeGen/ItaniumCXXABI.cpp
@@ -5150,9 +5150,14 @@ 
WebAssemblyCXXABI::emitTerminateForUnexpectedException(CodeGenFunction &CGF,
   // Itanium ABI calls __clang_call_terminate(), which __cxa_begin_catch() on
   // the violating exception to mark it handled, but it is currently hard to do
   // with wasm EH instruction structure with catch/catch_all, we just call
-  // std::terminate and ignore the violating exception as in CGCXXABI.
+  // std::terminate and ignore the violating exception as in CGCXXABI in Wasm 
EH
+  // and calls __clang_call_terminate only in Emscripten EH.
   // TODO Consider code transformation that makes calling 
__clang_call_terminate
-  // possible.
+  // in Wasm EH possible.
+  if (Exn && !EHPersonality::get(CGF).isWasmPersonality()) {
+    assert(CGF.CGM.getLangOpts().CPlusPlus);
+    return CGF.EmitNounwindRuntimeCall(getClangCallTerminateFn(CGF.CGM), Exn);
+  }
   return CGCXXABI::emitTerminateForUnexpectedException(CGF, Exn);
 }
 
diff --git a/clang/test/CodeGenCXX/wasm-eh.cpp 
b/clang/test/CodeGenCXX/wasm-eh.cpp
index 9dc15633bfed9..e8797794e7c1e 100644
--- a/clang/test/CodeGenCXX/wasm-eh.cpp
+++ b/clang/test/CodeGenCXX/wasm-eh.cpp
@@ -6,6 +6,9 @@
 // RUN: %clang_cc1 %s -triple wasm32-unknown-unknown -fms-extensions 
-fexceptions -fcxx-exceptions -mllvm -wasm-enable-eh -exception-model=wasm 
-target-feature +exception-handling -emit-llvm -o - -std=c++11 | FileCheck %s
 // RUN: %clang_cc1 %s -triple wasm64-unknown-unknown -fms-extensions 
-fexceptions -fcxx-exceptions -mllvm -wasm-enable-eh -exception-model=wasm 
-target-feature +exception-handling -emit-llvm -o - -std=c++11 | FileCheck %s
 
+// Test code generation for Wasm EH using WebAssembly EH proposal.
+// 
(https://github.com/WebAssembly/exception-handling/blob/main/proposals/exception-handling/Exceptions.md)
+
 void may_throw();
 void dont_throw() noexcept;
 
@@ -381,6 +384,15 @@ void test8() {
 
 // CHECK:   unreachable
 
+void noexcept_throw() noexcept {
+  throw 3;
+}
+
+// CATCH-LABEL: define void @_Z14noexcept_throwv()
+// CHECK: %{{.*}} = cleanuppad within none []
+// CHECK-NEXT:  call void @_ZSt9terminatev()
+
+
 // RUN: %clang_cc1 %s -triple wasm32-unknown-unknown -fms-extensions 
-fexceptions -fcxx-exceptions -exception-model=wasm -target-feature 
+exception-handling -emit-llvm -o - -std=c++11 2>&1 | FileCheck %s 
--check-prefix=WARNING-DEFAULT
 // RUN: %clang_cc1 %s -triple wasm32-unknown-unknown -fms-extensions 
-fexceptions -fcxx-exceptions -exception-model=wasm -target-feature 
+exception-handling -Wwasm-exception-spec -emit-llvm -o - -std=c++11 2>&1 | 
FileCheck %s --check-prefix=WARNING-ON
 // RUN: %clang_cc1 %s -triple wasm32-unknown-unknown -fms-extensions 
-fexceptions -fcxx-exceptions -exception-model=wasm -target-feature 
+exception-handling -Wno-wasm-exception-spec -emit-llvm -o - -std=c++11 2>&1 | 
FileCheck %s --check-prefix=WARNING-OFF
diff --git a/clang/test/CodeGenCXX/wasm-em-eh.cpp 
b/clang/test/CodeGenCXX/wasm-em-eh.cpp
new file mode 100644
index 0000000000000..9b2ccb2103bbc
--- /dev/null
+++ b/clang/test/CodeGenCXX/wasm-em-eh.cpp
@@ -0,0 +1,13 @@
+// RUN: %clang_cc1 %s -triple wasm32-unknown-unknown -fexceptions 
-fcxx-exceptions -emit-llvm -o - -std=c++11 2>&1 | FileCheck %s
+
+// Test code generation for Wasm's Emscripten (JavaScript-style) EH.
+
+void noexcept_throw() noexcept {
+  throw 3;
+}
+
+// CATCH-LABEL: define void @_Z14noexcept_throwv()
+// CHECK:       %[[LPAD:.*]] = landingpad { ptr, i32 }
+// CHECK-NEXT:                    catch ptr null
+// CHECK-NEXT:  %[[EXN:.*]] = extractvalue { ptr, i32 } %[[LPAD]], 0
+// CHECK-NEXT:  call void @__clang_call_terminate(ptr %[[EXN]])

``````````

</details>


https://github.com/llvm/llvm-project/pull/129020
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to