]> granicus.if.org Git - clang/commitdiff
[WinEH] Don't use lifetime markers for MS catch parameters
authorReid Kleckner <rnk@google.com>
Wed, 7 Oct 2015 21:03:41 +0000 (21:03 +0000)
committerReid Kleckner <rnk@google.com>
Wed, 7 Oct 2015 21:03:41 +0000 (21:03 +0000)
We don't have a good place to put them. Our previous spot was causing us
to optimize loads from the exception object to undef, because it was
after the catchpad instruction that models the write to the catch
object.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@249616 91177308-0d34-0410-b5e6-96231b3b80d8

lib/CodeGen/CGDecl.cpp
test/CodeGenCXX/microsoft-abi-eh-catch.cpp

index 07684f9144950354322b32f49bbb57466df8b465..3cff635f94e4a7f0566321d35a0c3925080c9c31 100644 (file)
@@ -974,9 +974,15 @@ CodeGenFunction::EmitAutoVarAlloca(const VarDecl &D) {
       address = CreateTempAlloca(allocaTy, allocaAlignment);
       address.getPointer()->setName(D.getName());
 
+      // Don't emit lifetime markers for MSVC catch parameters. The lifetime of
+      // the catch parameter starts in the catchpad instruction, and we can't
+      // insert code in those basic blocks.
+      bool IsMSCatchParam =
+          D.isExceptionVariable() && getTarget().getCXXABI().isMicrosoft();
+
       // Emit a lifetime intrinsic if meaningful.  There's no point
       // in doing this if we don't have a valid insertion point (?).
-      if (HaveInsertPoint()) {
+      if (HaveInsertPoint() && !IsMSCatchParam) {
         uint64_t size = CGM.getDataLayout().getTypeAllocSize(allocaTy);
         emission.SizeForLifetimeMarkers =
           EmitLifetimeStart(size, address.getPointer());
index d14edf8986bcd3c19e8bb88dc408e49db1471577..e742f8b1c4ad33923a9c9a10b1567f1b8666c015 100644 (file)
@@ -1,5 +1,6 @@
 // RUN: %clang_cc1 -std=c++11 -emit-llvm %s -o - -triple=x86_64-pc-windows-msvc \
 // RUN:     -mconstructor-aliases -fexceptions -fcxx-exceptions -fnew-ms-eh \
+// RUN:     -O1 -disable-llvm-optzns \
 // RUN:     | FileCheck -check-prefix WIN64 %s
 
 extern "C" void might_throw();
@@ -47,8 +48,17 @@ extern "C" void catch_int() {
 
 // WIN64-LABEL: define void @catch_int()
 // WIN64: catchpad [%rtti.TypeDescriptor2* @"\01??_R0H@8", i32 0, i32* %[[e_addr:[^\]]*]]]
+//
+// The catchpad instruction starts the lifetime of 'e'. Unfortunately, that
+// leaves us with nowhere to put lifetime.start, so we don't emit lifetime
+// markers for now.
+// WIN64-NOT: lifetime.start
+//
 // WIN64: %[[e_i8:[^ ]*]] = bitcast i32* %[[e_addr]] to i8*
-// WIN64: call void @handle_exception(i8* %[[e_i8]])
+// WIN64-NOT: lifetime.start
+// WIN64: call void @handle_exception
+// WIN64-SAME: (i8* %[[e_i8]])
+// WIN64-NOT: lifetime.end
 // WIN64: catchret
 
 extern "C" void catch_int_unnamed() {