diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 1940fe52aea..8198504b856 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2009-03-12 David Ayers + + PR libobjc/27466 + * objc/execute/exceptions/handler-1.m. New test. + 2008-03-12 Jakub Jelinek PR target/39431 diff --git a/gcc/testsuite/objc/execute/exceptions/handler-1.m b/gcc/testsuite/objc/execute/exceptions/handler-1.m new file mode 100644 index 00000000000..9cd8df19c44 --- /dev/null +++ b/gcc/testsuite/objc/execute/exceptions/handler-1.m @@ -0,0 +1,38 @@ +/* Test custom exception handlers */ +/* Author: David Ayers */ + +#include +#include +#include +#include + +static unsigned int handlerExpected = 0; + +void +my_exception_handler(id excp) +{ + /* Returning from the handler would abort. */ + if (handlerExpected) + exit(0); + + abort(); +} + +int +main(int argc, char *argv[]) +{ + _objc_unexpected_exception = my_exception_handler; + + @try + { + @throw [Object new]; + } + @catch (id exc) + { + handlerExpected = 1; + } + + @throw [Object new]; + abort(); + return 0; +} diff --git a/libobjc/ChangeLog b/libobjc/ChangeLog index 6b7c07e7bd1..1dc81be7a84 100644 --- a/libobjc/ChangeLog +++ b/libobjc/ChangeLog @@ -1,3 +1,14 @@ +2009-03-12 Richard Frith-Macdonald + David Ayers + + PR libobjc/27466 + * objc/objc-api.h (_objc_unexpected_exception): Declare + new hook. Update copyright dates. + * exception.c (objc_exception_throw): Use hook. Update + copyright dates. + * libobjc.def (_objc_unexpected_exception): Export hook. + Update copyright dates. + 2009-03-01 Ralf Wildenhues * configure: Regenerate. diff --git a/libobjc/exception.c b/libobjc/exception.c index bc59aa743cb..5af63103762 100644 --- a/libobjc/exception.c +++ b/libobjc/exception.c @@ -1,5 +1,5 @@ /* The implementation of exception handling primitives for Objective-C. - Copyright (C) 2004 Free Software Foundation, Inc. + Copyright (C) 2004, 2005, 2007, 2008, 2009 Free Software Foundation, Inc. This file is part of GCC. @@ -86,6 +86,11 @@ struct lsda_header_info unsigned char call_site_encoding; }; +/* This hook allows libraries to sepecify special actions when an + exception is thrown without a handler in place. + */ +void (*_objc_unexpected_exception) (id exception); /* !T:SAFE */ + static const unsigned char * parse_lsda_header (struct _Unwind_Context *context, const unsigned char *p, struct lsda_header_info *info) @@ -486,5 +491,9 @@ objc_exception_throw (id value) #endif /* Some sort of unwinding error. */ + if (_objc_unexpected_exception != 0) + { + (*_objc_unexpected_exception) (value); + } abort (); } diff --git a/libobjc/libobjc.def b/libobjc/libobjc.def index a80fb615589..9aca6d8f77c 100644 --- a/libobjc/libobjc.def +++ b/libobjc/libobjc.def @@ -1,5 +1,5 @@ ; GNU Objective C Runtime DLL Export Definitions -; Copyright (C) 1997 Free Software Foundation, Inc. +; Copyright (C) 1997, 2001, 2003, 2005, 2009 Free Software Foundation, Inc. ; Contributed by Scott Christley ; ; This file is part of GCC. @@ -38,6 +38,7 @@ objc_mutex_deallocate objc_mutex_lock objc_mutex_trylock objc_mutex_unlock +_objc_unexpected_exception objc_thread_detach objc_thread_exit objc_thread_get_data diff --git a/libobjc/objc/objc-api.h b/libobjc/objc/objc-api.h index 8100c6cfa27..02a8c7afa3d 100644 --- a/libobjc/objc/objc-api.h +++ b/libobjc/objc/objc-api.h @@ -1,5 +1,6 @@ /* GNU Objective-C Runtime API. - Copyright (C) 1993, 1995, 1996, 1997, 2002, 2004 Free Software Foundation, Inc. + Copyright (C) 1993, 1995, 1996, 1997, 2001, 2002, 2003, 2004, 2005, + 2007, 2009 Free Software Foundation, Inc. This file is part of GCC. @@ -430,6 +431,15 @@ objc_EXPORT void (*_objc_free)(void *); objc_EXPORT IMP (*__objc_msg_forward)(SEL); objc_EXPORT IMP (*__objc_msg_forward2)(id, SEL); +/* +** Hook for uncaught exceptions. This hook is called when an exception +** is thrown and no valid exception handler is in place. The function +** is expected never to return. If the function returns the result is +** currently undefined. +*/ +objc_EXPORT void (*_objc_unexpected_exception)(id); + + Method_t class_get_class_method(MetaClass _class, SEL aSel); Method_t class_get_instance_method(Class _class, SEL aSel);