| OLD | NEW |
| 1 // -*- C++ -*- Exception handling routines for PNaCl. | 1 // -*- C++ -*- Exception handling routines for PNaCl. |
| 2 // Copyright (C) 2013 | 2 // Copyright (C) 2013 |
| 3 // Free Software Foundation, Inc. | 3 // Free Software Foundation, Inc. |
| 4 // | 4 // |
| 5 // This file is part of GCC. | 5 // This file is part of GCC. |
| 6 // | 6 // |
| 7 // GCC is free software; you can redistribute it and/or modify | 7 // GCC is free software; you can redistribute it and/or modify |
| 8 // it under the terms of the GNU General Public License as published by | 8 // it under the terms of the GNU General Public License as published by |
| 9 // the Free Software Foundation; either version 3, or (at your option) | 9 // the Free Software Foundation; either version 3, or (at your option) |
| 10 // any later version. | 10 // any later version. |
| (...skipping 222 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 233 // UE_HEADER to __cxa_exception immediately. | 233 // UE_HEADER to __cxa_exception immediately. |
| 234 // | 234 // |
| 235 // This function returns if stack unwinding did not find any stack | 235 // This function returns if stack unwinding did not find any stack |
| 236 // frames that match the exception being thrown. | 236 // frames that match the exception being thrown. |
| 237 static void | 237 static void |
| 238 handle_exception (struct _Unwind_Exception *ue_header, bool check_for_catch) | 238 handle_exception (struct _Unwind_Exception *ue_header, bool check_for_catch) |
| 239 { | 239 { |
| 240 __cxa_exception *xh = __get_exception_header_from_ue (ue_header); | 240 __cxa_exception *xh = __get_exception_header_from_ue (ue_header); |
| 241 | 241 |
| 242 void *obj = __get_object_from_ue (ue_header); | 242 void *obj = __get_object_from_ue (ue_header); |
| 243 // We must get exceptionType via OBJ rather than from XH in order to |
| 244 // handle dependent exceptions. |
| 245 const std::type_info *throw_type = |
| 246 __get_exception_header_from_obj (obj)->exceptionType; |
| 243 struct exception_frame *frame; | 247 struct exception_frame *frame; |
| 244 int32_t clause_id; | 248 int32_t clause_id; |
| 245 if (find_match (xh->exceptionType, &obj, __pnacl_eh_stack, | 249 if (find_match (throw_type, &obj, __pnacl_eh_stack, &frame, &clause_id)) |
| 246 &frame, &clause_id)) | |
| 247 { | 250 { |
| 248 // Check that there is a non-cleanup handler for the exception. | 251 // Check that there is a non-cleanup handler for the exception. |
| 249 // If not, we should abort before running cleanup handlers | 252 // If not, we should abort before running cleanup handlers |
| 250 // (i.e. destructors). | 253 // (i.e. destructors). |
| 251 // | 254 // |
| 252 // This is mainly a convenience for debugging. It means that if | 255 // This is mainly a convenience for debugging. It means that if |
| 253 // the program throws an uncaught exception, the location of the | 256 // the program throws an uncaught exception, the location of the |
| 254 // "throw" will be on the stack when the program aborts. If we | 257 // "throw" will be on the stack when the program aborts. If we |
| 255 // ran cleanup handlers before aborting, this context would be | 258 // ran cleanup handlers before aborting, this context would be |
| 256 // lost. | 259 // lost. |
| 257 // | 260 // |
| 258 // This is optional in the C++ standard, which says "If no | 261 // This is optional in the C++ standard, which says "If no |
| 259 // matching handler is found, the function std::terminate() is | 262 // matching handler is found, the function std::terminate() is |
| 260 // called; whether or not the stack is unwound before this call | 263 // called; whether or not the stack is unwound before this call |
| 261 // to std::terminate() is implementation-defined". | 264 // to std::terminate() is implementation-defined". |
| 262 if (check_for_catch && clause_id == 0 && | 265 if (check_for_catch && clause_id == 0 && |
| 263 !is_exception_caught (xh->exceptionType, obj, frame->next)) | 266 !is_exception_caught (throw_type, obj, frame->next)) |
| 264 return; | 267 return; |
| 265 | 268 |
| 266 __pnacl_eh_stack = frame->next; | 269 __pnacl_eh_stack = frame->next; |
| 267 | 270 |
| 268 // Save adjusted exception pointer so that it can be returned by | 271 // Save adjusted exception pointer so that it can be returned by |
| 269 // __cxa_begin_catch() when entering a catch() block. | 272 // __cxa_begin_catch() when entering a catch() block. |
| 270 xh->adjustedPtr = obj; | 273 xh->adjustedPtr = obj; |
| 271 | 274 |
| 272 // Save the clause ID so that if the landingpad block calls | 275 // Save the clause ID so that if the landingpad block calls |
| 273 // __cxa_call_unexpected() and the std::set_unexpected() handler | 276 // __cxa_call_unexpected() and the std::set_unexpected() handler |
| (...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 418 // If the exception spec allows std::bad_exception, throw that. | 421 // If the exception spec allows std::bad_exception, throw that. |
| 419 // We don't have a thrown object to compare against, but since | 422 // We don't have a thrown object to compare against, but since |
| 420 // bad_exception doesn't have virtual bases, that's OK; just pass 0. | 423 // bad_exception doesn't have virtual bases, that's OK; just pass 0. |
| 421 const std::type_info *bad_exc = &typeid (std::bad_exception); | 424 const std::type_info *bad_exc = &typeid (std::bad_exception); |
| 422 if (check_exception_spec (bad_exc, NULL, xh_switch_value)) | 425 if (check_exception_spec (bad_exc, NULL, xh_switch_value)) |
| 423 throw std::bad_exception (); | 426 throw std::bad_exception (); |
| 424 | 427 |
| 425 __terminate (xh_terminate_handler); | 428 __terminate (xh_terminate_handler); |
| 426 } | 429 } |
| 427 } | 430 } |
| OLD | NEW |