llvm.org GIT mirror llvm / 7f45519
Move language independent exception handling routines OUT of C++Exception.cpp git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@8232 91177308-0d34-0410-b5e6-96231b3b80d8 Chris Lattner 16 years ago
6 changed file(s) with 160 addition(s) and 112 deletion(s). Raw diff Collapse all Expand all
1616 #include
1717 #endif
1818
19 //===----------------------------------------------------------------------===//
20 // Generic exception support
21 //
22
23 // Thread local state for exception handling.
24 // FIXME: This should really be made thread-local!
25 //
26
2719 // LastCaughtException - The last exception caught by this handler. This is for
2820 // implementation of _rethrow and _get_last_caught.
2921 //
22 // FIXME: This should be thread-local!
23 //
3024 static llvm_exception *LastCaughtException = 0;
3125
32 // UncaughtExceptionStack - The stack of exceptions currently being thrown.
33 static llvm_exception *UncaughtExceptionStack = 0;
34
35 // __llvm_eh_has_uncaught_exception - This is used to implement
36 // std::uncaught_exception.
37 //
38 bool __llvm_eh_has_uncaught_exception() throw() {
39 return UncaughtExceptionStack != 0;
40 }
41
42 // __llvm_eh_current_uncaught_exception - This function checks to see if the
43 // current uncaught exception is of the specified language type. If so, it
44 // returns a pointer to the exception area data.
45 //
46 void *__llvm_eh_current_uncaught_exception_type(unsigned HandlerType) throw() {
47 assert(UncaughtExceptionStack && "No uncaught exception!");
48 if (UncaughtExceptionStack->ExceptionType == HandlerType)
49 return UncaughtExceptionStack+1;
50 return 0;
51 }
52
53
54 //===----------------------------------------------------------------------===//
55 // C++ Specific exception handling support...
56 //
26
5727 using namespace __cxxabiv1;
5828
5929 // __llvm_cxxeh_allocate_exception - This function allocates space for the
11282 llvm_cxx_exception *E = (llvm_cxx_exception *)ObjectPtr - 1;
11383 E->BaseException.ExceptionDestructor = cxx_destructor;
11484 E->BaseException.ExceptionType = CXXException;
115 E->BaseException.Next = UncaughtExceptionStack;
116 UncaughtExceptionStack = &E->BaseException;
11785 E->BaseException.HandlerCount = 0;
11886 E->BaseException.isRethrown = 0;
11987
12189 E->ExceptionObjectDestructor = DtorPtr;
12290 E->UnexpectedHandler = __unexpected_handler;
12391 E->TerminateHandler = __terminate_handler;
92
93 __llvm_eh_add_uncaught_exception(&E->BaseException);
12494 }
12595
12696
162132 // appropriate, otherwise it returns null.
163133 //
164134 void *__llvm_cxxeh_current_uncaught_exception_isa(void *CatchType) throw() {
165 assert(UncaughtExceptionStack && "No uncaught exception!");
166 if (UncaughtExceptionStack->ExceptionType != CXXException)
167 return 0; // If it's not a c++ exception, it doesn't match!
135 void *EPtr = __llvm_eh_current_uncaught_exception_type(CXXException);
136 if (EPtr == 0) return 0; // If it's not a c++ exception, it doesn't match!
168137
169138 // If it is a C++ exception, use the type info object stored in the exception
170139 // to see if TypeID matches and, if so, to adjust the exception object
171140 // pointer.
172141 //
173142 const std::type_info *Info = (const std::type_info *)CatchType;
174 return CXXExceptionISA(get_cxx_exception(UncaughtExceptionStack), Info);
143 return CXXExceptionISA((llvm_cxx_exception*)EPtr - 1, Info);
175144 }
176145
177146
181150 // function must work with foreign exceptions.
182151 //
183152 void *__llvm_cxxeh_begin_catch() throw() {
184 llvm_exception *E = UncaughtExceptionStack;
185 assert(UncaughtExceptionStack && "There are no uncaught exceptions!?!?");
186
187 // The exception is now no longer uncaught.
188 UncaughtExceptionStack = E->Next;
189
153 llvm_exception *E = __llvm_eh_pop_from_uncaught_stack();
154
190155 // The exception is now caught.
191156 LastCaughtException = E;
192157 E->Next = 0;
253218 // time.
254219 void __llvm_cxxeh_call_terminate() throw() {
255220 void (*Handler)(void) = __terminate_handler;
256 if (UncaughtExceptionStack)
257 if (UncaughtExceptionStack->ExceptionType == CXXException)
258 Handler = get_cxx_exception(UncaughtExceptionStack)->TerminateHandler;
221 if (__llvm_eh_has_uncaught_exception())
222 if (void *EPtr = __llvm_eh_current_uncaught_exception_type(CXXException))
223 Handler = ((llvm_cxx_exception*)EPtr - 1)->TerminateHandler;
259224 __terminate(Handler);
260225 }
261226
278243
279244 // Add the exception to the top of the uncaught stack, to preserve the
280245 // invariant that the top of the uncaught stack is the current exception.
281 E->Next = UncaughtExceptionStack;
282 UncaughtExceptionStack = E;
246 __llvm_eh_add_uncaught_exception(E);
283247
284248 // Return to the caller, which should perform the unwind now.
285249 }
319283 //
320284 void __llvm_cxxeh_check_eh_spec(void *Info, ...) {
321285 const std::type_info *TypeInfo = (const std::type_info *)Info;
322 llvm_exception *E = UncaughtExceptionStack;
323 assert(E && "No uncaught exceptions!");
324286
325287 if (TypeInfo == 0) { // Empty exception specification
326288 // Whatever exception this is, it is not allowed by the (empty) spec, call
336298 }
337299 }
338300
301 llvm_exception *E = __llvm_eh_get_uncaught_exception();
302 assert(E && "No uncaught exceptions!");
303
339304 // Check to see if the exception matches one of the types allowed by the
340305 // exception specification. If so, return to the caller to have the
341306 // exception rethrown.
368333
369334 // Grab the newly caught exception. If this exception is permitted by the
370335 // specification, allow it to be thrown.
371 E = UncaughtExceptionStack;
372 assert(E && "No uncaught exceptions!");
336 E = __llvm_eh_get_uncaught_exception();
373337
374338 va_start(Args, Info);
375339 Ok = ExceptionSpecificationPermitsException(E, TypeInfo, Args);
384348 }
385349
386350 // Grab the new bad_exception...
387 E = UncaughtExceptionStack;
388 assert(E && "No uncaught exceptions!");
351 E = __llvm_eh_get_uncaught_exception();
389352
390353 // If it's permitted, allow it to be thrown instead.
391354 va_start(Args, Info);
0 //===- Exception.cpp - Generic language-independent exceptions ------------===//
1 //
2 // This file defines the the shared data structures used by all language
3 // specific exception handling runtime libraries.
4 //
5 //===----------------------------------------------------------------------===//
6
7 #include "Exception.h"
8 #include
9
10 // Thread local state for exception handling. FIXME: This should really be made
11 // thread-local!
12
13 // UncaughtExceptionStack - The stack of exceptions currently being thrown.
14 static llvm_exception *UncaughtExceptionStack = 0;
15
16 // __llvm_eh_has_uncaught_exception - This is used to implement
17 // std::uncaught_exception.
18 //
19 bool __llvm_eh_has_uncaught_exception() throw() {
20 return UncaughtExceptionStack != 0;
21 }
22
23 // __llvm_eh_current_uncaught_exception - This function checks to see if the
24 // current uncaught exception is of the specified language type. If so, it
25 // returns a pointer to the exception area data.
26 //
27 void *__llvm_eh_current_uncaught_exception_type(unsigned HandlerType) throw() {
28 assert(UncaughtExceptionStack && "No uncaught exception!");
29 if (UncaughtExceptionStack->ExceptionType == HandlerType)
30 return UncaughtExceptionStack+1;
31 return 0;
32 }
33
34 // __llvm_eh_add_uncaught_exception - This adds the specified exception to the
35 // top of the uncaught exception stack. The exception should not already be on
36 // the stack!
37 void __llvm_eh_add_uncaught_exception(llvm_exception *E) throw() {
38 E->Next = UncaughtExceptionStack;
39 UncaughtExceptionStack = E;
40 }
41
42
43 // __llvm_eh_get_uncaught_exception - Returns the current uncaught exception.
44 // There must be an uncaught exception for this to work!
45 llvm_exception *__llvm_eh_get_uncaught_exception() throw() {
46 assert(UncaughtExceptionStack && "There are no uncaught exceptions!?!?");
47 return UncaughtExceptionStack;
48 }
49
50 // __llvm_eh_pop_from_uncaught_stack - Remove the current uncaught exception
51 // from the top of the stack.
52 llvm_exception *__llvm_eh_pop_from_uncaught_stack() throw() {
53 llvm_exception *E = __llvm_eh_get_uncaught_exception();
54 UncaughtExceptionStack = E->Next;
55 return E;
56 }
5151 extern "C" {
5252 bool __llvm_eh_has_uncaught_exception() throw();
5353 void *__llvm_eh_current_uncaught_exception_type(unsigned HandlerType) throw();
54 void __llvm_eh_add_uncaught_exception(llvm_exception *E) throw();
55
56 llvm_exception *__llvm_eh_get_uncaught_exception() throw();
57 llvm_exception *__llvm_eh_pop_from_uncaught_stack() throw();
5458 }
5559
5660 #endif
1616 #include
1717 #endif
1818
19 //===----------------------------------------------------------------------===//
20 // Generic exception support
21 //
22
23 // Thread local state for exception handling.
24 // FIXME: This should really be made thread-local!
25 //
26
2719 // LastCaughtException - The last exception caught by this handler. This is for
2820 // implementation of _rethrow and _get_last_caught.
2921 //
22 // FIXME: This should be thread-local!
23 //
3024 static llvm_exception *LastCaughtException = 0;
3125
32 // UncaughtExceptionStack - The stack of exceptions currently being thrown.
33 static llvm_exception *UncaughtExceptionStack = 0;
34
35 // __llvm_eh_has_uncaught_exception - This is used to implement
36 // std::uncaught_exception.
37 //
38 bool __llvm_eh_has_uncaught_exception() throw() {
39 return UncaughtExceptionStack != 0;
40 }
41
42 // __llvm_eh_current_uncaught_exception - This function checks to see if the
43 // current uncaught exception is of the specified language type. If so, it
44 // returns a pointer to the exception area data.
45 //
46 void *__llvm_eh_current_uncaught_exception_type(unsigned HandlerType) throw() {
47 assert(UncaughtExceptionStack && "No uncaught exception!");
48 if (UncaughtExceptionStack->ExceptionType == HandlerType)
49 return UncaughtExceptionStack+1;
50 return 0;
51 }
52
53
54 //===----------------------------------------------------------------------===//
55 // C++ Specific exception handling support...
56 //
26
5727 using namespace __cxxabiv1;
5828
5929 // __llvm_cxxeh_allocate_exception - This function allocates space for the
11282 llvm_cxx_exception *E = (llvm_cxx_exception *)ObjectPtr - 1;
11383 E->BaseException.ExceptionDestructor = cxx_destructor;
11484 E->BaseException.ExceptionType = CXXException;
115 E->BaseException.Next = UncaughtExceptionStack;
116 UncaughtExceptionStack = &E->BaseException;
11785 E->BaseException.HandlerCount = 0;
11886 E->BaseException.isRethrown = 0;
11987
12189 E->ExceptionObjectDestructor = DtorPtr;
12290 E->UnexpectedHandler = __unexpected_handler;
12391 E->TerminateHandler = __terminate_handler;
92
93 __llvm_eh_add_uncaught_exception(&E->BaseException);
12494 }
12595
12696
162132 // appropriate, otherwise it returns null.
163133 //
164134 void *__llvm_cxxeh_current_uncaught_exception_isa(void *CatchType) throw() {
165 assert(UncaughtExceptionStack && "No uncaught exception!");
166 if (UncaughtExceptionStack->ExceptionType != CXXException)
167 return 0; // If it's not a c++ exception, it doesn't match!
135 void *EPtr = __llvm_eh_current_uncaught_exception_type(CXXException);
136 if (EPtr == 0) return 0; // If it's not a c++ exception, it doesn't match!
168137
169138 // If it is a C++ exception, use the type info object stored in the exception
170139 // to see if TypeID matches and, if so, to adjust the exception object
171140 // pointer.
172141 //
173142 const std::type_info *Info = (const std::type_info *)CatchType;
174 return CXXExceptionISA(get_cxx_exception(UncaughtExceptionStack), Info);
143 return CXXExceptionISA((llvm_cxx_exception*)EPtr - 1, Info);
175144 }
176145
177146
181150 // function must work with foreign exceptions.
182151 //
183152 void *__llvm_cxxeh_begin_catch() throw() {
184 llvm_exception *E = UncaughtExceptionStack;
185 assert(UncaughtExceptionStack && "There are no uncaught exceptions!?!?");
186
187 // The exception is now no longer uncaught.
188 UncaughtExceptionStack = E->Next;
189
153 llvm_exception *E = __llvm_eh_pop_from_uncaught_stack();
154
190155 // The exception is now caught.
191156 LastCaughtException = E;
192157 E->Next = 0;
253218 // time.
254219 void __llvm_cxxeh_call_terminate() throw() {
255220 void (*Handler)(void) = __terminate_handler;
256 if (UncaughtExceptionStack)
257 if (UncaughtExceptionStack->ExceptionType == CXXException)
258 Handler = get_cxx_exception(UncaughtExceptionStack)->TerminateHandler;
221 if (__llvm_eh_has_uncaught_exception())
222 if (void *EPtr = __llvm_eh_current_uncaught_exception_type(CXXException))
223 Handler = ((llvm_cxx_exception*)EPtr - 1)->TerminateHandler;
259224 __terminate(Handler);
260225 }
261226
278243
279244 // Add the exception to the top of the uncaught stack, to preserve the
280245 // invariant that the top of the uncaught stack is the current exception.
281 E->Next = UncaughtExceptionStack;
282 UncaughtExceptionStack = E;
246 __llvm_eh_add_uncaught_exception(E);
283247
284248 // Return to the caller, which should perform the unwind now.
285249 }
319283 //
320284 void __llvm_cxxeh_check_eh_spec(void *Info, ...) {
321285 const std::type_info *TypeInfo = (const std::type_info *)Info;
322 llvm_exception *E = UncaughtExceptionStack;
323 assert(E && "No uncaught exceptions!");
324286
325287 if (TypeInfo == 0) { // Empty exception specification
326288 // Whatever exception this is, it is not allowed by the (empty) spec, call
336298 }
337299 }
338300
301 llvm_exception *E = __llvm_eh_get_uncaught_exception();
302 assert(E && "No uncaught exceptions!");
303
339304 // Check to see if the exception matches one of the types allowed by the
340305 // exception specification. If so, return to the caller to have the
341306 // exception rethrown.
368333
369334 // Grab the newly caught exception. If this exception is permitted by the
370335 // specification, allow it to be thrown.
371 E = UncaughtExceptionStack;
372 assert(E && "No uncaught exceptions!");
336 E = __llvm_eh_get_uncaught_exception();
373337
374338 va_start(Args, Info);
375339 Ok = ExceptionSpecificationPermitsException(E, TypeInfo, Args);
384348 }
385349
386350 // Grab the new bad_exception...
387 E = UncaughtExceptionStack;
388 assert(E && "No uncaught exceptions!");
351 E = __llvm_eh_get_uncaught_exception();
389352
390353 // If it's permitted, allow it to be thrown instead.
391354 va_start(Args, Info);
0 //===- Exception.cpp - Generic language-independent exceptions ------------===//
1 //
2 // This file defines the the shared data structures used by all language
3 // specific exception handling runtime libraries.
4 //
5 //===----------------------------------------------------------------------===//
6
7 #include "Exception.h"
8 #include
9
10 // Thread local state for exception handling. FIXME: This should really be made
11 // thread-local!
12
13 // UncaughtExceptionStack - The stack of exceptions currently being thrown.
14 static llvm_exception *UncaughtExceptionStack = 0;
15
16 // __llvm_eh_has_uncaught_exception - This is used to implement
17 // std::uncaught_exception.
18 //
19 bool __llvm_eh_has_uncaught_exception() throw() {
20 return UncaughtExceptionStack != 0;
21 }
22
23 // __llvm_eh_current_uncaught_exception - This function checks to see if the
24 // current uncaught exception is of the specified language type. If so, it
25 // returns a pointer to the exception area data.
26 //
27 void *__llvm_eh_current_uncaught_exception_type(unsigned HandlerType) throw() {
28 assert(UncaughtExceptionStack && "No uncaught exception!");
29 if (UncaughtExceptionStack->ExceptionType == HandlerType)
30 return UncaughtExceptionStack+1;
31 return 0;
32 }
33
34 // __llvm_eh_add_uncaught_exception - This adds the specified exception to the
35 // top of the uncaught exception stack. The exception should not already be on
36 // the stack!
37 void __llvm_eh_add_uncaught_exception(llvm_exception *E) throw() {
38 E->Next = UncaughtExceptionStack;
39 UncaughtExceptionStack = E;
40 }
41
42
43 // __llvm_eh_get_uncaught_exception - Returns the current uncaught exception.
44 // There must be an uncaught exception for this to work!
45 llvm_exception *__llvm_eh_get_uncaught_exception() throw() {
46 assert(UncaughtExceptionStack && "There are no uncaught exceptions!?!?");
47 return UncaughtExceptionStack;
48 }
49
50 // __llvm_eh_pop_from_uncaught_stack - Remove the current uncaught exception
51 // from the top of the stack.
52 llvm_exception *__llvm_eh_pop_from_uncaught_stack() throw() {
53 llvm_exception *E = __llvm_eh_get_uncaught_exception();
54 UncaughtExceptionStack = E->Next;
55 return E;
56 }
5151 extern "C" {
5252 bool __llvm_eh_has_uncaught_exception() throw();
5353 void *__llvm_eh_current_uncaught_exception_type(unsigned HandlerType) throw();
54 void __llvm_eh_add_uncaught_exception(llvm_exception *E) throw();
55
56 llvm_exception *__llvm_eh_get_uncaught_exception() throw();
57 llvm_exception *__llvm_eh_pop_from_uncaught_stack() throw();
5458 }
5559
5660 #endif