Hi howard.hinnant,

Fix std::uncaught_exception() to return true during exception initialization

std::uncaught_exception() should return true during the call to the
copy constructor that "throw X" does to initialize the exception
object after the expression X has been evaluated (or during the call
to the normal constructor if the compiler has done copy elision).

Fix this by incrementing uncaughtExceptions earlier, in
__cxa_allocate_exception() rather than in __cxa_throw().

This fixes PR18193.


http://llvm-reviews.chandlerc.com/D2366

Files:
  src/cxa_exception.cpp

Index: src/cxa_exception.cpp
===================================================================
--- src/cxa_exception.cpp
+++ src/cxa_exception.cpp
@@ -160,6 +160,11 @@
     if (NULL == exception_header)
         std::terminate();
     std::memset(exception_header, 0, actual_size);
+    // Increment uncaughtExceptions now so that
+    // std::uncaught_exception() returns true in the copy constructor
+    // that "throw" calls to initialize the exception.  The increment
+    // here is not atomic because the globals are thread-local.
+    __cxa_get_globals()->uncaughtExceptions += 1;
     return thrown_object_from_cxa_exception(exception_header);
 }
 
@@ -229,7 +234,6 @@
     exception_header->exceptionDestructor = dest;
     setExceptionClass(&exception_header->unwindHeader);
     exception_header->referenceCount = 1;  // This is a newly allocated 
exception, no need for thread safety.
-    globals->uncaughtExceptions += 1;   // Not atomically, since globals are 
thread-local
 
     exception_header->unwindHeader.exception_cleanup = exception_cleanup_func;
 #if __arm__
Index: src/cxa_exception.cpp
===================================================================
--- src/cxa_exception.cpp
+++ src/cxa_exception.cpp
@@ -160,6 +160,11 @@
     if (NULL == exception_header)
         std::terminate();
     std::memset(exception_header, 0, actual_size);
+    // Increment uncaughtExceptions now so that
+    // std::uncaught_exception() returns true in the copy constructor
+    // that "throw" calls to initialize the exception.  The increment
+    // here is not atomic because the globals are thread-local.
+    __cxa_get_globals()->uncaughtExceptions += 1;
     return thrown_object_from_cxa_exception(exception_header);
 }
 
@@ -229,7 +234,6 @@
     exception_header->exceptionDestructor = dest;
     setExceptionClass(&exception_header->unwindHeader);
     exception_header->referenceCount = 1;  // This is a newly allocated exception, no need for thread safety.
-    globals->uncaughtExceptions += 1;   // Not atomically, since globals are thread-local
 
     exception_header->unwindHeader.exception_cleanup = exception_cleanup_func;
 #if __arm__
_______________________________________________
cfe-commits mailing list
[email protected]
http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits

Reply via email to