diff --git a/clang/lib/CodeGen/CGCall.cpp b/clang/lib/CodeGen/CGCall.cpp index e8235c775d8f..3f27e1bb8955 100644 --- a/clang/lib/CodeGen/CGCall.cpp +++ b/clang/lib/CodeGen/CGCall.cpp @@ -4841,6 +4841,10 @@ RValue CodeGenFunction::EmitCall(const CGFunctionInfo &CallInfo, } else { // Otherwise, nounwind call sites will never throw. CannotThrow = Attrs.hasFnAttribute(llvm::Attribute::NoUnwind); + + if (auto *FPtr = dyn_cast(CalleePtr)) + if (FPtr->hasFnAttribute(llvm::Attribute::NoUnwind)) + CannotThrow = true; } // If we made a temporary, be sure to clean up after ourselves. Note that we diff --git a/clang/test/CodeGenCXX/debug-info-class.cpp b/clang/test/CodeGenCXX/debug-info-class.cpp index b3e79c37923d..94d5a0f1f082 100644 --- a/clang/test/CodeGenCXX/debug-info-class.cpp +++ b/clang/test/CodeGenCXX/debug-info-class.cpp @@ -13,7 +13,7 @@ public: virtual ~B(); }; -B::~B() { +B::~B() { extern void mayThrow(); mayThrow(); } struct C { diff --git a/clang/test/CodeGenObjCXX/arc-list-init-destruct.mm b/clang/test/CodeGenObjCXX/arc-list-init-destruct.mm index 09a66458c260..513af64d5203 100644 --- a/clang/test/CodeGenObjCXX/arc-list-init-destruct.mm +++ b/clang/test/CodeGenObjCXX/arc-list-init-destruct.mm @@ -16,6 +16,8 @@ struct Container { }; bool getBool() { + extern void mayThrow(); + mayThrow(); return false; } diff --git a/clang/test/CodeGenObjCXX/os_log.mm b/clang/test/CodeGenObjCXX/os_log.mm index b6e0bc25ca80..c9efe329b587 100644 --- a/clang/test/CodeGenObjCXX/os_log.mm +++ b/clang/test/CodeGenObjCXX/os_log.mm @@ -6,13 +6,14 @@ namespace no_eh_cleanup { void release(int *lock); // CHECK-LABEL: define {{.*}} @_ZN13no_eh_cleanup3logERiPcS1_( + // CHECK: call void @__os_log_helper_1_2_2_4_0_8_34( + void log(int &i, char *data, char *buf) { int lock __attribute__((cleanup(release))); __builtin_os_log_format(buf, "%d %{public}s", i, data); } - // An `invoke` of a `nounwind` callee is simplified to a direct - // call by an optimization in llvm. Just check that we emit `nounwind`. + // Check that the os_log_helper is marked `nounwind`. // CHECK: define {{.*}} @__os_log_helper_1_2_2_4_0_8_34({{.*}} [[NUW:#[0-9]+]] } diff --git a/clang/test/OpenMP/atomic_codegen.cpp b/clang/test/OpenMP/atomic_codegen.cpp index 4377213e6d82..47371fe912aa 100644 --- a/clang/test/OpenMP/atomic_codegen.cpp +++ b/clang/test/OpenMP/atomic_codegen.cpp @@ -82,7 +82,7 @@ void parallel_atomic_ewc() { } } -int &foo() { return a; } +int &foo() { extern void mayThrow(); mayThrow(); return a; } // TERM_DEBUG-LABEL: parallel_atomic void parallel_atomic() { diff --git a/clang/test/OpenMP/critical_codegen.cpp b/clang/test/OpenMP/critical_codegen.cpp index f49c9cc9c21a..4b2566bbf364 100644 --- a/clang/test/OpenMP/critical_codegen.cpp +++ b/clang/test/OpenMP/critical_codegen.cpp @@ -22,7 +22,7 @@ // ALL: define {{.*}}void [[FOO:@.+]]() -void foo() {} +void foo() { extern void mayThrow(); mayThrow(); } // ALL-LABEL: @main // TERM_DEBUG-LABEL: @main diff --git a/clang/test/OpenMP/distribute_parallel_for_num_threads_codegen.cpp b/clang/test/OpenMP/distribute_parallel_for_num_threads_codegen.cpp index 8d941391c75b..953d52b35f9b 100644 --- a/clang/test/OpenMP/distribute_parallel_for_num_threads_codegen.cpp +++ b/clang/test/OpenMP/distribute_parallel_for_num_threads_codegen.cpp @@ -22,7 +22,7 @@ void foo(); struct S { intptr_t a, b, c; S(intptr_t a) : a(a) {} - operator char() { return a; } + operator char() { extern void mayThrow(); mayThrow(); return a; } ~S() {} }; diff --git a/clang/test/OpenMP/distribute_parallel_for_simd_num_threads_codegen.cpp b/clang/test/OpenMP/distribute_parallel_for_simd_num_threads_codegen.cpp index 318fc1401963..69b833eaed24 100644 --- a/clang/test/OpenMP/distribute_parallel_for_simd_num_threads_codegen.cpp +++ b/clang/test/OpenMP/distribute_parallel_for_simd_num_threads_codegen.cpp @@ -22,7 +22,7 @@ void foo(); struct S { intptr_t a, b, c; S(intptr_t a) : a(a) {} - operator char() { return a; } + operator char() { extern void mayThrow(); mayThrow(); return a; } ~S() {} }; diff --git a/clang/test/OpenMP/for_codegen.cpp b/clang/test/OpenMP/for_codegen.cpp index 26b09c574f3c..71e481b3cd78 100644 --- a/clang/test/OpenMP/for_codegen.cpp +++ b/clang/test/OpenMP/for_codegen.cpp @@ -536,7 +536,7 @@ void test_precond() { } // TERM_DEBUG-LABEL: foo -int foo() {return 0;}; +int foo() { extern void mayThrow(); mayThrow(); return 0;}; // TERM_DEBUG-LABEL: parallel_for void parallel_for(float *a) { diff --git a/clang/test/OpenMP/for_simd_codegen.cpp b/clang/test/OpenMP/for_simd_codegen.cpp index a668cb77a068..5bb9811bcedf 100644 --- a/clang/test/OpenMP/for_simd_codegen.cpp +++ b/clang/test/OpenMP/for_simd_codegen.cpp @@ -20,7 +20,7 @@ #ifndef HEADER #define HEADER -long long get_val() { return 0; } +long long get_val() { extern void mayThrow(); mayThrow(); return 0; } double *g_ptr; // CHECK-LABEL: define {{.*void}} @{{.*}}simple{{.*}}(float* {{.+}}, float* {{.+}}, float* {{.+}}, float* {{.+}}) @@ -785,7 +785,7 @@ void widened(float *a, float *b, float *c, float *d) { } // TERM_DEBUG-LABEL: bar -int bar() {return 0;}; +int bar() { extern void mayThrow(); mayThrow(); return 0; }; // TERM_DEBUG-LABEL: parallel_simd void parallel_simd(float *a) { diff --git a/clang/test/OpenMP/master_codegen.cpp b/clang/test/OpenMP/master_codegen.cpp index 9a33f2f53b0d..8554ad8e7dec 100644 --- a/clang/test/OpenMP/master_codegen.cpp +++ b/clang/test/OpenMP/master_codegen.cpp @@ -19,7 +19,7 @@ // ALL: define {{.*}}void [[FOO:@.+]]() -void foo() {} +void foo() { extern void mayThrow(); mayThrow(); } // ALL-LABEL: @main // TERM_DEBUG-LABEL: @main diff --git a/clang/test/OpenMP/parallel_for_codegen.cpp b/clang/test/OpenMP/parallel_for_codegen.cpp index de445634470b..4ef6e8228808 100644 --- a/clang/test/OpenMP/parallel_for_codegen.cpp +++ b/clang/test/OpenMP/parallel_for_codegen.cpp @@ -372,7 +372,7 @@ void runtime(float *a, float *b, float *c, float *d) { } // TERM_DEBUG-LABEL: foo -int foo() {return 0;}; +int foo() { extern void mayThrow(); mayThrow(); return 0; }; // TERM_DEBUG-LABEL: parallel_for // CLEANUP: parallel_for diff --git a/clang/test/OpenMP/parallel_for_simd_codegen.cpp b/clang/test/OpenMP/parallel_for_simd_codegen.cpp index e9cc2f302eaf..715328771ccc 100644 --- a/clang/test/OpenMP/parallel_for_simd_codegen.cpp +++ b/clang/test/OpenMP/parallel_for_simd_codegen.cpp @@ -22,7 +22,7 @@ #ifndef HEADER #define HEADER -long long get_val() { return 0; } +long long get_val() { extern void mayThrow(); mayThrow(); return 0; } double *g_ptr; // CHECK-LABEL: define {{.*void}} @{{.*}}simple{{.*}}(float* {{.+}}, float* {{.+}}, float* {{.+}}, float* {{.+}}) @@ -801,7 +801,7 @@ for (int i = 0; i < 10; ++i); // OMP50-DAG: ![[NOVM]] = !{!"llvm.loop.vectorize.enable", i1 false} // TERM_DEBUG-LABEL: bar -int bar() {return 0;}; +int bar() { extern void mayThrow(); mayThrow(); return 0; }; // TERM_DEBUG-LABEL: parallel_simd void parallel_simd(float *a) { diff --git a/clang/test/OpenMP/parallel_master_codegen.cpp b/clang/test/OpenMP/parallel_master_codegen.cpp index 82e18c80f103..98993e05c853 100644 --- a/clang/test/OpenMP/parallel_master_codegen.cpp +++ b/clang/test/OpenMP/parallel_master_codegen.cpp @@ -18,7 +18,7 @@ // CK1-DAG: [[DEF_LOC:@.+]] = private unnamed_addr global %struct.ident_t { i32 0, i32 2, i32 0, i32 0, i8* getelementptr inbounds ([23 x i8], [23 x i8]* [[STR]], i32 0, i32 0) } // CK1-LABEL: foo -void foo() {} +void foo() { extern void mayThrow(); mayThrow(); } void parallel_master() { #pragma omp parallel master diff --git a/clang/test/OpenMP/parallel_num_threads_codegen.cpp b/clang/test/OpenMP/parallel_num_threads_codegen.cpp index 79615b934168..47109ffc7af3 100644 --- a/clang/test/OpenMP/parallel_num_threads_codegen.cpp +++ b/clang/test/OpenMP/parallel_num_threads_codegen.cpp @@ -22,7 +22,7 @@ void foo(); struct S { intptr_t a, b, c; S(intptr_t a) : a(a) {} - operator char() { return a; } + operator char() { extern void mayThrow(); mayThrow(); return a; } ~S() {} }; diff --git a/clang/test/OpenMP/parallel_sections_codegen.cpp b/clang/test/OpenMP/parallel_sections_codegen.cpp index eadc4937203a..bee078050256 100644 --- a/clang/test/OpenMP/parallel_sections_codegen.cpp +++ b/clang/test/OpenMP/parallel_sections_codegen.cpp @@ -10,9 +10,9 @@ #ifndef HEADER #define HEADER // CHECK-LABEL: foo -void foo() {}; +void foo() { extern void mayThrow(); mayThrow(); }; // CHECK-LABEL: bar -void bar() {}; +void bar() { extern void mayThrow(); mayThrow(); }; template T tmain() { diff --git a/clang/test/OpenMP/sections_codegen.cpp b/clang/test/OpenMP/sections_codegen.cpp index 68fd38f7d0bb..d33e79238459 100644 --- a/clang/test/OpenMP/sections_codegen.cpp +++ b/clang/test/OpenMP/sections_codegen.cpp @@ -12,9 +12,9 @@ // CHECK-DAG: [[IMPLICIT_BARRIER_SECTIONS_LOC:@.+]] = private unnamed_addr global %{{.+}} { i32 0, i32 194, i32 0, i32 0, i8* // CHECK-DAG: [[SECTIONS_LOC:@.+]] = private unnamed_addr global %{{.+}} { i32 0, i32 1026, i32 0, i32 0, i8* // CHECK-LABEL: foo -void foo() {}; +void foo() { extern void mayThrow(); mayThrow(); }; // CHECK-LABEL: bar -void bar() {}; +void bar() { extern void mayThrow(); mayThrow(); }; template T tmain() { diff --git a/clang/test/OpenMP/simd_codegen.cpp b/clang/test/OpenMP/simd_codegen.cpp index 3440225673c4..335dfd78cace 100644 --- a/clang/test/OpenMP/simd_codegen.cpp +++ b/clang/test/OpenMP/simd_codegen.cpp @@ -26,7 +26,7 @@ // OMP50-DAG: [[LAST_IV:@.+]] = {{.*}}common global i64 0 // OMP50-DAG: [[LAST_A:@.+]] = {{.*}}common global i32 0 -long long get_val() { return 0; } +long long get_val() { extern void mayThrow(); mayThrow(); return 0; } double *g_ptr; struct S { @@ -798,7 +798,7 @@ void bartfoo() { #endif // OMP5 // TERM_DEBUG-LABEL: bar -int bar() {return 0;}; +int bar() { extern void mayThrow(); mayThrow(); return 0; }; // TERM_DEBUG-LABEL: parallel_simd void parallel_simd(float *a) { diff --git a/clang/test/OpenMP/single_codegen.cpp b/clang/test/OpenMP/single_codegen.cpp index a56cdb0ae81a..1d88c2808ed2 100644 --- a/clang/test/OpenMP/single_codegen.cpp +++ b/clang/test/OpenMP/single_codegen.cpp @@ -42,7 +42,7 @@ TestClass tc; TestClass tc2[2]; #pragma omp threadprivate(tc, tc2) -void foo() {} +void foo() { extern void mayThrow(); mayThrow(); } struct SS { int a; diff --git a/clang/test/OpenMP/taskgroup_codegen.cpp b/clang/test/OpenMP/taskgroup_codegen.cpp index f672ab17fd59..31ecb80b1a20 100644 --- a/clang/test/OpenMP/taskgroup_codegen.cpp +++ b/clang/test/OpenMP/taskgroup_codegen.cpp @@ -16,7 +16,7 @@ // CHECK: define {{.*}}void [[FOO:@.+]]() -void foo() {} +void foo() { extern void mayThrow(); mayThrow(); } // CHECK-LABEL: @main // TERM_DEBUG-LABEL: @main