[Substrate-commits] SF.net SVN: substrate: [281] trunk
Brought to you by:
landonf
|
From: <la...@us...> - 2006-08-31 22:26:27
|
Revision: 281
http://svn.sourceforge.net/substrate/?rev=281&view=rev
Author: landonf
Date: 2006-08-31 15:26:13 -0700 (Thu, 31 Aug 2006)
Log Message:
-----------
r5712@zadder: landonf | 2006-08-31 14:44:59 -0700
Checkpoint commit of old-style exception stack handling
Modified Paths:
--------------
trunk/Foundation/LFObjCRuntime.h.in
trunk/Foundation/Makefile.in
trunk/Foundation/NSConcreteData.m
trunk/Foundation/NSException.h
trunk/Foundation/NSException.m
Added Paths:
-----------
trunk/Foundation/LFObjCExceptionStack.m
trunk/Foundation/LFObjCGNUException.m
Removed Paths:
-------------
trunk/Foundation/LFObjCAppleRuntime.m
trunk/Foundation/LFObjCGNURuntime.m
trunk/Foundation/NSClassicException.h
trunk/Foundation/NSFuncallException.h
Property Changed:
----------------
trunk/
Property changes on: trunk
___________________________________________________________________
Name: svk:merge
- 11572a18-12fc-0310-9209-f8edcc8181a7:/local/substrate/trunk:5684
+ 11572a18-12fc-0310-9209-f8edcc8181a7:/local/substrate/trunk:5712
Deleted: trunk/Foundation/LFObjCAppleRuntime.m
===================================================================
--- trunk/Foundation/LFObjCAppleRuntime.m 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/LFObjCAppleRuntime.m 2006-08-31 22:26:13 UTC (rev 281)
@@ -1,288 +0,0 @@
-/*
- * LFObjCAppleRuntime.m vi:ts=4:sw=4:expandtab:
- * Apple Objective-C Runtime Abstraction and Support Code
- *
- * Copyright (C) 2005 - 2006 Landon Fuller <la...@op...>
- * All rights reserved.
- *
- * Author: Landon Fuller <la...@op...>
- *
- * This file is part of libFoundation.
- *
- * Permission to use, copy, modify, and distribute this software and its
- * documentation for any purpose and without fee is hereby granted, provided
- * that the above copyright notice appear in all copies and that both that
- * copyright notice and this permission notice appear in supporting
- * documentation.
- *
- * We disclaim all warranties with regard to this software, including all
- * implied warranties of merchantability and fitness, in no event shall
- * we be liable for any special, indirect or consequential damages or any
- * damages whatsoever resulting from loss of use, data or profits, whether in
- * an action of contract, negligence or other tortious action, arising out of
- * or in connection with the use or performance of this software.
- */
-
-/*!
- * @file
- * @internal
- * @brief LFObjCRuntime
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#ifdef APPLE_RUNTIME
-
-/******************************************************************************
- * Supporting exceptions on Apple's runtime requires maintaining a per-thread
- * stack of exception handlers. Handlers are pushed and popped off the stack
- * at the beginning and end of every try/catch block, via a runtime function
- * call. When an exception occurs, our LFObjC_ExceptionThrow() function is
- * called, and we need to longjmp to the current exception handler at the top
- * of the per-thread handler stack.
- *****************************************************************************/
-
-#include <Foundation/NSZone.h>
-#include <Foundation/NSException.h>
-#include <Foundation/LFObjCRuntime.h>
-#include <Foundation/spin.h>
-
-#include <sys/types.h>
-#include <unistd.h>
-#include <assert.h>
-#include <stdlib.h>
-#include <pthread.h>
-#include <setjmp.h>
-
-/* Number of exception handlers to store in each bucket.
- * Selected arbitrarily. */
-#define EHS_BUCKET_SIZE 16
-
-/* Forward declarations */
-static void LFObjC_ExceptionThrow (id);
-static void LFObjC_ExceptionTryEnter (void *);
-static void LFObjC_ExceptionTryExit (void *);
-static id LFObjC_ExceptionExtract (void *);
-static int LFObjC_ExceptionMatch (Class, id);
-static void free_exception_handler_stack_tls (void *);
-
-/* The compiler will pass this structure to LFObjC_ExceptionThrow() */
-typedef struct LFObjCLocalExceptionData {
- jmp_buf buf;
- id *pointers[4];
-} LFObjCLocalExceptionData;
-
-/* Per-thread stack of exception handler buckets, each bucket
- * holds EHS_BUCKET_SIZE handlers */
-typedef struct LFExceptionHandlerBucket {
- int count;
- LFObjCLocalExceptionData *excData[EHS_BUCKET_SIZE];
- struct LFExceptionHandlerBucket *next;
-} LFExceptionHandlerBucket;
-
-/* We modify the pointer in this structure so that we don't
- * have to call pthread_setspecific() repeatedly */
-typedef struct LFExceptionHandler_TLS {
- LFExceptionHandlerBucket *bucket;
-} LFExceptionHandler_TLS;
-
-/* Per-thread EH stack key */
-static pthread_key_t LFExceptionHandlerStack_key;
-
-/*!
- * Exception handling functions for the Apple Objective-C runtime.
- * @internal
- */
-objc_exception_functions_t objc_exc_funcs = {
- 0,
- LFObjC_ExceptionThrow,
- LFObjC_ExceptionTryEnter,
- LFObjC_ExceptionTryExit,
- LFObjC_ExceptionExtract,
- LFObjC_ExceptionMatch
-};
-
-
-/* Uncaught exception handler */
-static LFUncaughtExceptionHandler *ueh_handler;
-static slock_t ueh_lock;
-
-/*!
- * Set Objective-C Uncaught Exception Handler.
- * @internal
- */
-LF_PRIVATE void LFObjCSetUncaughtExceptionHandler (LFUncaughtExceptionHandler *handler) {
- SpinLockAcquire(&ueh_lock);
- ueh_handler = handler;
- SpinLockRelease(&ueh_lock);
-}
-
-/*!
- * Get Objective-C Uncaught Exception Handler.
- * @internal
- */
-LF_PRIVATE LFUncaughtExceptionHandler *LFObjCGetUncaughtExceptionHandler (void) {
- LFUncaughtExceptionHandler *handler;
- SpinLockAcquire(&ueh_lock);
- handler = ueh_handler;
- SpinLockRelease(&ueh_lock);
-
- return handler;
-}
-
-/*!
- * Initialize the Objective-C Exception Handler.
- * @internal
- */
-LF_PRIVATE void LFObjCInitExceptionHandler (LFUncaughtExceptionHandler *handler) {
- /* Initialize the lock */
- SpinLockInit(&ueh_lock);
- ueh_handler = handler;
-
- /* Initialize our pthread key */
- pthread_key_create(&LFExceptionHandlerStack_key, free_exception_handler_stack_tls);
-
- /* Set up exception handling functions */
- objc_exception_set_functions((objc_exception_functions_t *) &objc_exc_funcs);
-}
-
-/*!
- * Throw an exception.
- * @internal
- */
-static void LFObjC_ExceptionThrow (id exception) {
- LFExceptionHandler_TLS *ehsTLS;
- LFObjCLocalExceptionData *lfexcData;
- LFExceptionHandlerBucket *bucket;
-
- /* Grab the stack */
- ehsTLS = (LFExceptionHandler_TLS *) pthread_getspecific(LFExceptionHandlerStack_key);
-
- /* If the stack is NULL or the bucket is empty, someone forgot to catch
- * the exception. Call the uncaught exception handler and fire SIGTRAP */
- if (!ehsTLS || !ehsTLS->bucket || ehsTLS->bucket->count == 0) {
- LFUncaughtExceptionHandler *handler;
-
- /* Acquire a lock and get the current ueh_handler */
- SpinLockAcquire(&ueh_lock);
- handler = ueh_handler;
- SpinLockRelease(&ueh_lock);
-
- /* Call and then fire SIGTRAP */
- handler(exception);
- kill(getpid(), SIGTRAP);
- }
-
- /* Pop our exception data */
- bucket = ehsTLS->bucket;
- assert(bucket);
- lfexcData = bucket->excData[bucket->count - 1];
- assert(lfexcData);
- bucket->count--;
-
- /* Store the exception in the first pointer */
- lfexcData->pointers[0] = (void *) exception;
-
- /* On my mark. */
- _longjmp(lfexcData->buf, 1);
-}
-
-/*!
- * Enter a @try/@catch block.
- * @internal
- */
-static void LFObjC_ExceptionTryEnter (void *excData) {
- LFExceptionHandler_TLS *ehsTLS;
- LFExceptionHandlerBucket *new, *bucket;
-
- /* Grab the stack */
- ehsTLS = (LFExceptionHandler_TLS *) pthread_getspecific(LFExceptionHandlerStack_key);
-
- /* Allocate and initialize the stack TLS holder if needed */
- if (!ehsTLS) {
- ehsTLS = NSZoneMalloc(NULL, sizeof(LFExceptionHandler_TLS));
- ehsTLS->bucket = NULL;
- pthread_setspecific(LFExceptionHandlerStack_key, ehsTLS);
- }
-
- /* Allocate and initialize a bucket if needed */
- if (!ehsTLS->bucket || ehsTLS->bucket->count == EHS_BUCKET_SIZE) {
- new = NSZoneMalloc(NULL, sizeof(LFExceptionHandlerBucket));
-
- /* Will either get set to NULL or the next bucket */
- new->next = ehsTLS->bucket;
- new->count = 0;
-
- ehsTLS->bucket = new;
- }
-
- /* Add our data to the bucket */
- bucket = ehsTLS->bucket;
- bucket->excData[bucket->count] = excData;
- bucket->count++;
-
- return;
-}
-
-/*!
- * Exit a @try/@catch block.
- * @internal
- */
-static void LFObjC_ExceptionTryExit (void *excData) {
- LFExceptionHandler_TLS *ehsTLS;
- LFExceptionHandlerBucket *bucket;
-
- /* Grab the stack */
- ehsTLS = (LFExceptionHandler_TLS *) pthread_getspecific(LFExceptionHandlerStack_key);
- assert(ehsTLS);
-
- /* Decrease the bucket count (ie, pop the excData) */
- bucket = ehsTLS->bucket;
- assert(bucket->excData[bucket->count - 1] == excData);
- bucket->count--;
-
- /* If the bucket is empty, and this isn't the last bucket available,
- * free the current bucket. */
- if (bucket->count == 0 && bucket->next != NULL) {
- ehsTLS->bucket = bucket->next;
- NSZoneFree(NULL, bucket);
- }
-
- return;
-}
-
-/*!
- * Extract the Objective-C object from the local exception data.
- * @internal
- */
-static id LFObjC_ExceptionExtract (void *excData) {
- LFObjCLocalExceptionData *lfexcData = (LFObjCLocalExceptionData *) excData;
- /* We stored the exception in the first pointer */
- return (id) lfexcData->pointers[0];
-}
-
-/*!
- * Match a given exception against the supplied class.
- * @internal
- */
-static int LFObjC_ExceptionMatch (Class excClass, id exception) {
- return [exception isKindOfClass: excClass];
-}
-
-/*!
- * Deallocate the exception stack TLS.
- * @internal
- */
-static void free_exception_handler_stack_tls (void *keyData) {
- LFExceptionHandler_TLS *ehsTLS = (LFExceptionHandler_TLS *) keyData;
-
- /* There will only ever be one bucket left behind by LFObjC_ExceptionTryExit() */
- if (ehsTLS->bucket)
- NSZoneFree(NULL, ehsTLS->bucket);
-
- NSZoneFree(NULL, ehsTLS);
-}
-
-#endif /* APPLE_RUNTIME */
Added: trunk/Foundation/LFObjCExceptionStack.m
===================================================================
--- trunk/Foundation/LFObjCExceptionStack.m (rev 0)
+++ trunk/Foundation/LFObjCExceptionStack.m 2006-08-31 22:26:13 UTC (rev 281)
@@ -0,0 +1,310 @@
+/*
+ * LFObjCExceptionStack.m vi:ts=4:sw=4:expandtab:
+ *
+ * Generic Exception Stack Implementation.
+ * Compatible with both new-style language exceptions as implemented by
+ * the Apple runtime, and old-style NS_DURING exceptions in both runtimes.
+ *
+ * Copyright (C) 2005 - 2006 Landon Fuller <la...@op...>
+ * All rights reserved.
+ *
+ * Author: Landon Fuller <la...@op...>
+ *
+ * This file is part of libFoundation.
+ *
+ * Permission to use, copy, modify, and distribute this software and its
+ * documentation for any purpose and without fee is hereby granted, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation.
+ *
+ * We disclaim all warranties with regard to this software, including all
+ * implied warranties of merchantability and fitness, in no event shall
+ * we be liable for any special, indirect or consequential damages or any
+ * damages whatsoever resulting from loss of use, data or profits, whether in
+ * an action of contract, negligence or other tortious action, arising out of
+ * or in connection with the use or performance of this software.
+ */
+
+/*!
+ * @file
+ * @internal
+ * @brief LFObjCRuntime
+ */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#if defined(APPLE_RUNTIME) || (defined(GNU_RUNTIME) && !defined(OBJC_EXCEPTIONS))
+
+/******************************************************************************
+ * This code implementions binary-compatible exception handling for both
+ * new and old-style exceptions in the Apple Objective-C runtime.
+ *
+ * It also implements non-binary compatible exception handling support for
+ * old-style exceptions in GNU's Objective-C runtime.
+ *
+ * We maintain a per-thread stack of exception handlers. Handlers are pushed
+ * and popped off the stack at the beginning and end of every try/catch block,
+ * via a runtime function call. When an exception occurs, our
+ * LFObjC_ExceptionThrow() function is called, and we need to longjmp to the
+ * current exception handler at the top of the per-thread handler stack.
+ *
+ * The push/pop runtime function calls are handled automatically by the
+ * new-style exception support in Apple's runtime. With old-style exceptions,
+ * we manually implement the equivalent using preprocessor macros.
+ *****************************************************************************/
+
+#include <Foundation/NSZone.h>
+#include <Foundation/NSException.h>
+#include <Foundation/LFObjCRuntime.h>
+#include <Foundation/spin.h>
+
+#include <sys/types.h>
+#include <unistd.h>
+#include <assert.h>
+#include <stdlib.h>
+#include <pthread.h>
+#include <setjmp.h>
+
+/* Number of exception handlers to store in each bucket.
+ * Selected arbitrarily. */
+#define EHS_BUCKET_SIZE 16
+
+/* Forward declarations */
+static void LFObjC_ExceptionThrow (id);
+static void LFObjC_ExceptionTryEnter (void *);
+static void LFObjC_ExceptionTryExit (void *);
+static id LFObjC_ExceptionExtract (void *);
+static int LFObjC_ExceptionMatch (Class, id);
+static void free_exception_handler_stack_tls (void *);
+
+/* Per-thread stack of exception handler buckets, each bucket
+ * holds EHS_BUCKET_SIZE handlers */
+typedef struct LFExceptionHandlerBucket {
+ int count;
+ LFObjCLocalExceptionData *excData[EHS_BUCKET_SIZE];
+ struct LFExceptionHandlerBucket *next;
+} LFExceptionHandlerBucket;
+
+/* We modify the pointer in this structure so that we don't
+ * have to call pthread_setspecific() repeatedly */
+typedef struct LFExceptionHandler_TLS {
+ LFExceptionHandlerBucket *bucket;
+} LFExceptionHandler_TLS;
+
+/* Per-thread EH stack key */
+static pthread_key_t LFExceptionHandlerStack_key;
+
+/* Uncaught exception handler */
+static LFUncaughtExceptionHandler *ueh_handler;
+static slock_t ueh_lock;
+
+/* Expose our exception stack functions */
+#if defined APPLE_RUNTIME
+/*!
+ * Exception handling functions for the Apple Objective-C runtime.
+ * @internal
+ */
+objc_exception_functions_t objc_exc_funcs = {
+ 0,
+ LFObjC_ExceptionThrow,
+ LFObjC_ExceptionTryEnter,
+ LFObjC_ExceptionTryExit,
+ LFObjC_ExceptionExtract,
+ LFObjC_ExceptionMatch
+};
+#endif /* APPLE_RUNTIME */
+
+void _NSAddHandler (LFObjCLocalExceptionData *excData) {
+ LFObjC_ExceptionTryEnter(excData);
+}
+
+void _NSRemoveHandler (LFObjCLocalExceptionData *excData) {
+ LFObjC_ExceptionTryExit(excData);
+}
+
+NSException *_NSExceptionFromHandler (LFObjCLocalExceptionData *excData) {
+ return LFObjC_ExceptionExtract(excData);
+}
+
+/*!
+ * Set Objective-C Uncaught Exception Handler.
+ * @internal
+ */
+LF_PRIVATE void LFObjCSetUncaughtExceptionHandler (LFUncaughtExceptionHandler *handler) {
+ SpinLockAcquire(&ueh_lock);
+ ueh_handler = handler;
+ SpinLockRelease(&ueh_lock);
+}
+
+/*!
+ * Get Objective-C Uncaught Exception Handler.
+ * @internal
+ */
+LF_PRIVATE LFUncaughtExceptionHandler *LFObjCGetUncaughtExceptionHandler (void) {
+ LFUncaughtExceptionHandler *handler;
+ SpinLockAcquire(&ueh_lock);
+ handler = ueh_handler;
+ SpinLockRelease(&ueh_lock);
+
+ return handler;
+}
+
+/*!
+ * Initialize the Objective-C Exception Handler.
+ * @internal
+ */
+LF_PRIVATE void LFObjCInitExceptionHandler (LFUncaughtExceptionHandler *handler) {
+ /* Initialize the lock */
+ SpinLockInit(&ueh_lock);
+ ueh_handler = handler;
+
+ /* Initialize our pthread key */
+ pthread_key_create(&LFExceptionHandlerStack_key, free_exception_handler_stack_tls);
+
+#if defined(APPLE_RUNTIME) && defined(OBJC_EXCEPTIONS)
+ /* Set up exception handling functions for the Apple runtime */
+ objc_exception_set_functions((objc_exception_functions_t *) &objc_exc_funcs);
+#endif
+}
+
+/*!
+ * Throw an exception.
+ * @internal
+ */
+LF_PRIVATE void LFObjC_ExceptionThrow (id exception) {
+ LFExceptionHandler_TLS *ehsTLS;
+ LFObjCLocalExceptionData *lfexcData;
+ LFExceptionHandlerBucket *bucket;
+
+ /* Grab the stack */
+ ehsTLS = (LFExceptionHandler_TLS *) pthread_getspecific(LFExceptionHandlerStack_key);
+
+ /* If the stack is NULL or the bucket is empty, someone forgot to catch
+ * the exception. Call the uncaught exception handler and fire SIGTRAP */
+ if (!ehsTLS || !ehsTLS->bucket || ehsTLS->bucket->count == 0) {
+ LFUncaughtExceptionHandler *handler;
+
+ /* Acquire a lock and get the current ueh_handler */
+ SpinLockAcquire(&ueh_lock);
+ handler = ueh_handler;
+ SpinLockRelease(&ueh_lock);
+
+ /* Call and then fire SIGTRAP */
+ handler(exception);
+ kill(getpid(), SIGTRAP);
+ }
+
+ /* Pop our exception data */
+ bucket = ehsTLS->bucket;
+ assert(bucket);
+ lfexcData = bucket->excData[bucket->count - 1];
+ assert(lfexcData);
+ bucket->count--;
+
+ /* Store the exception in the first pointer */
+ lfexcData->pointers[0] = (void *) exception;
+
+ /* On my mark. */
+ _longjmp(lfexcData->buf, 1);
+}
+
+/*!
+ * Enter a @try/@catch block.
+ * @internal
+ */
+static void LFObjC_ExceptionTryEnter (void *excData) {
+ LFExceptionHandler_TLS *ehsTLS;
+ LFExceptionHandlerBucket *new, *bucket;
+
+ /* Grab the stack */
+ ehsTLS = (LFExceptionHandler_TLS *) pthread_getspecific(LFExceptionHandlerStack_key);
+
+ /* Allocate and initialize the stack TLS holder if needed */
+ if (!ehsTLS) {
+ ehsTLS = NSZoneMalloc(NULL, sizeof(LFExceptionHandler_TLS));
+ ehsTLS->bucket = NULL;
+ pthread_setspecific(LFExceptionHandlerStack_key, ehsTLS);
+ }
+
+ /* Allocate and initialize a bucket if needed */
+ if (!ehsTLS->bucket || ehsTLS->bucket->count == EHS_BUCKET_SIZE) {
+ new = NSZoneMalloc(NULL, sizeof(LFExceptionHandlerBucket));
+
+ /* Will either get set to NULL or the next bucket */
+ new->next = ehsTLS->bucket;
+ new->count = 0;
+
+ ehsTLS->bucket = new;
+ }
+
+ /* Add our data to the bucket */
+ bucket = ehsTLS->bucket;
+ bucket->excData[bucket->count] = excData;
+ bucket->count++;
+
+ return;
+}
+
+/*!
+ * Exit a @try/@catch block.
+ * @internal
+ */
+static void LFObjC_ExceptionTryExit (void *excData) {
+ LFExceptionHandler_TLS *ehsTLS;
+ LFExceptionHandlerBucket *bucket;
+
+ /* Grab the stack */
+ ehsTLS = (LFExceptionHandler_TLS *) pthread_getspecific(LFExceptionHandlerStack_key);
+ assert(ehsTLS);
+
+ /* Decrease the bucket count (ie, pop the excData) */
+ bucket = ehsTLS->bucket;
+ assert(bucket->excData[bucket->count - 1] == excData);
+ bucket->count--;
+
+ /* If the bucket is empty, and this isn't the last bucket available,
+ * free the current bucket. */
+ if (bucket->count == 0 && bucket->next != NULL) {
+ ehsTLS->bucket = bucket->next;
+ NSZoneFree(NULL, bucket);
+ }
+
+ return;
+}
+
+/*!
+ * Extract the Objective-C object from the local exception data.
+ * @internal
+ */
+static id LFObjC_ExceptionExtract (void *excData) {
+ LFObjCLocalExceptionData *lfexcData = (LFObjCLocalExceptionData *) excData;
+ /* We stored the exception in the first pointer */
+ return (id) lfexcData->pointers[0];
+}
+
+/*!
+ * Match a given exception against the supplied class.
+ * @internal
+ */
+static int LFObjC_ExceptionMatch (Class excClass, id exception) {
+ return [exception isKindOfClass: excClass];
+}
+
+/*!
+ * Deallocate the exception stack TLS.
+ * @internal
+ */
+static void free_exception_handler_stack_tls (void *keyData) {
+ LFExceptionHandler_TLS *ehsTLS = (LFExceptionHandler_TLS *) keyData;
+
+ /* There will only ever be one bucket left behind by LFObjC_ExceptionTryExit() */
+ if (ehsTLS->bucket)
+ NSZoneFree(NULL, ehsTLS->bucket);
+
+ NSZoneFree(NULL, ehsTLS);
+}
+
+#endif /* APPLE_RUNTIME || (GNU_RUNTIME && !OBJC_EXCEPTIONS) */
Property changes on: trunk/Foundation/LFObjCExceptionStack.m
___________________________________________________________________
Name: svn:eol-style
+ native
Added: trunk/Foundation/LFObjCGNUException.m
===================================================================
--- trunk/Foundation/LFObjCGNUException.m (rev 0)
+++ trunk/Foundation/LFObjCGNUException.m 2006-08-31 22:26:13 UTC (rev 281)
@@ -0,0 +1,160 @@
+/*
+ * LFObjCGNUException.m vi:ts=4:sw=4:expandtab:
+ * New-style language exception handling for the GNU Objective-C runtime.
+ *
+ * Copyright (C) 2005 - 2006 Landon Fuller <la...@op...>
+ * All rights reserved.
+ *
+ * Author: Landon Fuller <la...@op...>
+ *
+ * This file is part of libFoundation.
+ *
+ * Permission to use, copy, modify, and distribute this software and its
+ * documentation for any purpose and without fee is hereby granted, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation.
+ *
+ * We disclaim all warranties with regard to this software, including all
+ * implied warranties of merchantability and fitness, in no event shall
+ * we be liable for any special, indirect or consequential damages or any
+ * damages whatsoever resulting from loss of use, data or profits, whether in
+ * an action of contract, negligence or other tortious action, arising out of
+ * or in connection with the use or performance of this software.
+ */
+
+/*!
+ * @file
+ * @internal
+ * @brief LFObjCRuntime
+ */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#if defined(GNU_RUNTIME) && defined(LF_OBJC_LANGUAGE_EXCEPTIONS)
+
+/* This is unfortunately required to use RTLD_NEXT on Linux systems */
+#define _GNU_SOURCE
+
+#include <Foundation/NSZone.h>
+#include <Foundation/NSException.h>
+#include <Foundation/LFObjCRuntime.h>
+#include <Foundation/spin.h>
+
+#include <sys/types.h>
+#include <unistd.h>
+#include <signal.h>
+
+# include <dlfcn.h>
+/* GCC's exception handling and stack unwinding routines */
+# include <unwind.h>
+
+/* Uncaught exception handler */
+static LFUncaughtExceptionHandler *ueh_handler;
+static slock_t ueh_lock;
+
+/*! libgcc's _Unwind_RaiseException()
+ * @internal */
+static _Unwind_Reason_Code (*_real_Unwind_RaiseException)(struct _Unwind_Exception *e);
+
+/*!
+ * Set Objective-C Uncaught Exception Handler.
+ * @internal
+ */
+LF_PRIVATE void LFObjCSetUncaughtExceptionHandler (LFUncaughtExceptionHandler *handler) {
+ SpinLockAcquire(&ueh_lock);
+ ueh_handler = handler;
+ SpinLockRelease(&ueh_lock);
+}
+
+/*!
+ * Get Objective-C Uncaught Exception Handler.
+ * @internal
+ */
+LF_PRIVATE LFUncaughtExceptionHandler *LFObjCGetUncaughtExceptionHandler (void) {
+ LFUncaughtExceptionHandler *handler;
+ SpinLockAcquire(&ueh_lock);
+ handler = ueh_handler;
+ SpinLockRelease(&ueh_lock);
+
+ return handler;
+}
+
+/*!
+ * Initialize the Objective-C Exception Handler.
+ * @internal
+ */
+LF_PRIVATE void LFObjCInitExceptionHandler (LFUncaughtExceptionHandler *handler) {
+ /* Initialize the lock */
+ SpinLockInit(&ueh_lock);
+ ueh_handler = handler;
+
+#ifdef RTLD_NEXT
+ /* Locate the _Unwind_RaiseException symbol */
+ _real_Unwind_RaiseException = dlsym(RTLD_NEXT, "_Unwind_RaiseException");
+#endif /* RTLD_NEXT */
+
+}
+
+/*!
+ * Throw an exception.
+ * @internal
+ */
+LF_PRIVATE void LFObjC_ExceptionThrow (id exception) {
+ @throw exception;
+}
+
+/******************************************************************************
+ * XXX: Temporary Hack.
+ *
+ * When using the GNU Objective-C runtime, support for a default
+ * Objective-C exception handler is implemented by overriding gcc's
+ * _Unwind_RaiseException, calling the true _Unwind_RaiseException,
+ * and checking for _URC_END_OF_STACK, which signals that no exception
+ * handler was found.
+ *
+ * This is wrong, wrong, wrong, (really wrong!), but there is currently
+ * no other way to implement this functionality.
+ *
+ * See http://gcc.gnu.org/bugzilla/show_bug.cgi?id=27466 for my libobjc
+ * enhancement request.
+ ******************************************************************************/
+
+/*! Our _Unwind_RaiseException()
+ * @internal */
+_Unwind_Reason_Code _Unwind_RaiseException (struct _Unwind_Exception *uwe) {
+ _Unwind_Reason_Code err;
+
+ err = _real_Unwind_RaiseException(uwe);
+ if (err == _URC_END_OF_STACK) {
+ LFUncaughtExceptionHandler *handler;
+
+ /* Acquire a lock and get the current ueh_handler */
+ SpinLockAcquire(&ueh_lock);
+ handler = ueh_handler;
+ SpinLockRelease(&ueh_lock);
+
+ /* If a handler is available, call it.
+ * We manually re-raise the _Unwind_Exception so that we can get
+ * access to the thrown Objective-C object without digging
+ * into the private libobjc structures */
+ @try {
+ _real_Unwind_RaiseException(uwe);
+ }
+ @catch (id exc) {
+ ueh_handler(exc);
+ }
+ }
+
+ /* Fire SIGTRAP */
+ kill(getpid(), SIGTRAP);
+
+ /* We're going to return objc_exception_throw(), where abort() will be
+ * called immediately. Unless someone caught SIGTRAP, this should
+ * be unreachable */
+ return err;
+}
+
+#endif /* GNU_RUNTIME && LF_OBJC_LANGUAGE_EXCEPTIONS */
Property changes on: trunk/Foundation/LFObjCGNUException.m
___________________________________________________________________
Name: svn:eol-style
+ native
Deleted: trunk/Foundation/LFObjCGNURuntime.m
===================================================================
--- trunk/Foundation/LFObjCGNURuntime.m 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/LFObjCGNURuntime.m 2006-08-31 22:26:13 UTC (rev 281)
@@ -1,152 +0,0 @@
-/*
- * LFObjCGNURuntime.m vi:ts=4:sw=4:expandtab:
- * GNU Objective-C Runtime Abstraction and Support Code
- *
- * Copyright (C) 2005 - 2006 Landon Fuller <la...@op...>
- * All rights reserved.
- *
- * Author: Landon Fuller <la...@op...>
- *
- * This file is part of libFoundation.
- *
- * Permission to use, copy, modify, and distribute this software and its
- * documentation for any purpose and without fee is hereby granted, provided
- * that the above copyright notice appear in all copies and that both that
- * copyright notice and this permission notice appear in supporting
- * documentation.
- *
- * We disclaim all warranties with regard to this software, including all
- * implied warranties of merchantability and fitness, in no event shall
- * we be liable for any special, indirect or consequential damages or any
- * damages whatsoever resulting from loss of use, data or profits, whether in
- * an action of contract, negligence or other tortious action, arising out of
- * or in connection with the use or performance of this software.
- */
-
-/*!
- * @file
- * @internal
- * @brief LFObjCRuntime
- */
-
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
-
-#ifdef GNU_RUNTIME
-
-/* This is unfortunately required to use RTLD_NEXT on Linux systems */
-#define _GNU_SOURCE
-
-#include <Foundation/NSZone.h>
-#include <Foundation/NSException.h>
-#include <Foundation/LFObjCRuntime.h>
-#include <Foundation/spin.h>
-
-#include <sys/types.h>
-#include <unistd.h>
-#include <signal.h>
-
-# include <dlfcn.h>
-/* GCC's exception handling and stack unwinding routines */
-# include <unwind.h>
-
-/* Uncaught exception handler */
-static LFUncaughtExceptionHandler *ueh_handler;
-static slock_t ueh_lock;
-
-/*! libgcc's _Unwind_RaiseException()
- * @internal */
-static _Unwind_Reason_Code (*_real_Unwind_RaiseException)(struct _Unwind_Exception *e);
-
-/*!
- * Set Objective-C Uncaught Exception Handler.
- * @internal
- */
-LF_PRIVATE void LFObjCSetUncaughtExceptionHandler (LFUncaughtExceptionHandler *handler) {
- SpinLockAcquire(&ueh_lock);
- ueh_handler = handler;
- SpinLockRelease(&ueh_lock);
-}
-
-/*!
- * Get Objective-C Uncaught Exception Handler.
- * @internal
- */
-LF_PRIVATE LFUncaughtExceptionHandler *LFObjCGetUncaughtExceptionHandler (void) {
- LFUncaughtExceptionHandler *handler;
- SpinLockAcquire(&ueh_lock);
- handler = ueh_handler;
- SpinLockRelease(&ueh_lock);
-
- return handler;
-}
-
-/*!
- * Initialize the Objective-C Exception Handler.
- * @internal
- */
-LF_PRIVATE void LFObjCInitExceptionHandler (LFUncaughtExceptionHandler *handler) {
- /* Initialize the lock */
- SpinLockInit(&ueh_lock);
- ueh_handler = handler;
-
-#ifdef RTLD_NEXT
- /* Locate the _Unwind_RaiseException symbol */
- _real_Unwind_RaiseException = dlsym(RTLD_NEXT, "_Unwind_RaiseException");
-#endif /* RTLD_NEXT */
-
-}
-
-/******************************************************************************
- * XXX: Temporary Hack.
- *
- * When using the GNU Objective-C runtime, support for a default
- * Objective-C exception handler is implemented by overriding gcc's
- * _Unwind_RaiseException, calling the true _Unwind_RaiseException,
- * and checking for _URC_END_OF_STACK, which signals that no exception
- * handler was found.
- *
- * This is wrong, wrong, wrong, (really wrong!), but there is currently
- * no other way to implement this functionality.
- *
- * See http://gcc.gnu.org/bugzilla/show_bug.cgi?id=27466 for my libobjc
- * enhancement request.
- ******************************************************************************/
-
-/*! Our _Unwind_RaiseException()
- * @internal */
-_Unwind_Reason_Code _Unwind_RaiseException (struct _Unwind_Exception *uwe) {
- _Unwind_Reason_Code err;
-
- err = _real_Unwind_RaiseException(uwe);
- if (err == _URC_END_OF_STACK) {
- LFUncaughtExceptionHandler *handler;
-
- /* Acquire a lock and get the current ueh_handler */
- SpinLockAcquire(&ueh_lock);
- handler = ueh_handler;
- SpinLockRelease(&ueh_lock);
-
- /* If a handler is available, call it.
- * We manually re-raise the _Unwind_Exception so that we can get
- * access to the thrown Objective-C object without digging
- * into the private libobjc structures */
- @try {
- _real_Unwind_RaiseException(uwe);
- }
- @catch (id exc) {
- ueh_handler(exc);
- }
- }
-
- /* Fire SIGTRAP */
- kill(getpid(), SIGTRAP);
-
- /* We're going to return objc_exception_throw(), where abort() will be
- * called immediately. Unless someone caught SIGTRAP, this should
- * be unreachable */
- return err;
-}
-
-#endif /* GNU_RUNTIME */
Modified: trunk/Foundation/LFObjCRuntime.h.in
===================================================================
--- trunk/Foundation/LFObjCRuntime.h.in 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/LFObjCRuntime.h.in 2006-08-31 22:26:13 UTC (rev 281)
@@ -39,10 +39,14 @@
@class NSException;
+/* Apple or GNU Runtime */
#ifndef @OBJC_RUNTIME@
#define @OBJC_RUNTIME@ 1
#endif
+/* Exception Handling Implementation */
+@OBJC_EXCEPTIONS_DEFINE@
+
/* Include stdint.h if available */
@LF_STDINT_INC@
@@ -83,10 +87,6 @@
#define LFObjectGetSuperclass(obj) LFClassGetSuperclass(LFObjectGetClass(obj))
#define LFMethodGetIMP(method) (method != NULL ? method->method_imp : NULL)
-/*
- * Exception handling
- */
-
#ifdef LF_SPI
/*!
@@ -100,20 +100,26 @@
* Initialize the Apple or GNU Objective-C exception handler.
* @internal
*/
-void LFObjCInitExceptionHandler (LFUncaughtExceptionHandler *handler);
+LF_PRIVATE void LFObjCInitExceptionHandler (LFUncaughtExceptionHandler *handler);
/*!
* Set the uncaught exception handler.
* @internal
*/
-void LFObjCSetUncaughtExceptionHandler (LFUncaughtExceptionHandler *handler);
+LF_PRIVATE void LFObjCSetUncaughtExceptionHandler (LFUncaughtExceptionHandler *handler);
/*!
* Get the uncaught exception handler.
* @internal
*/
-LFUncaughtExceptionHandler *LFObjCGetUncaughtExceptionHandler (void);
+LF_PRIVATE LFUncaughtExceptionHandler *LFObjCGetUncaughtExceptionHandler (void);
+/*!
+ * Throw an exception.
+ * @internal
+ */
+LF_PRIVATE void LFObjC_ExceptionThrow (id exception);
+
#endif /* LF_SPI */
#if defined(GNU_RUNTIME)
Modified: trunk/Foundation/Makefile.in
===================================================================
--- trunk/Foundation/Makefile.in 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/Makefile.in 2006-08-31 22:26:13 UTC (rev 281)
@@ -45,8 +45,8 @@
NSUnicodeString.m \
NSSimpleCString.m \
NSZone.m \
- LFObjCAppleRuntime.m \
- LFObjCGNURuntime.m \
+ LFObjCExceptionStack.m \
+ LFObjCGNUException.m \
LFHash.c \
s_lock.c \
$(TAS_SRC)
@@ -64,8 +64,8 @@
NSUnicodeString.o \
NSSimpleCString.o \
NSZone.o \
- LFObjCAppleRuntime.o \
- LFObjCGNURuntime.o \
+ LFObjCExceptionStack.o \
+ LFObjCGNUException.o \
LFHash.o \
s_lock.o \
$(TAS_OBJS)
@@ -96,7 +96,8 @@
# File Substitutions
EDIT= sed \
-e 's,@OBJC_RUNTIME\@,$(OBJC_RUNTIME),g' \
- -e 's,@LF_STDINT_INC\@,$(LF_STDINT_INC),g'
+ -e 's,@LF_STDINT_INC\@,$(LF_STDINT_INC),g' \
+ -e 's,@OBJC_EXCEPTIONS_DEFINE\@,$(OBJC_EXCEPTIONS_DEFINE),g'
# Generated File(s)
LFObjCRuntime.h: LFObjCRuntime.h.in
Deleted: trunk/Foundation/NSClassicException.h
===================================================================
--- trunk/Foundation/NSClassicException.h 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/NSClassicException.h 2006-08-31 22:26:13 UTC (rev 281)
@@ -1,315 +0,0 @@
-/*
- NSClassicException.h
-
- Copyright (C) 1995, 1996 Ovidiu Predescu and Mircea Oancea.
- All rights reserved.
-
- Author: Ovidiu Predescu <ov...@bx...>
-
- This file is part of libFoundation.
-
- Permission to use, copy, modify, and distribute this software and its
- documentation for any purpose and without fee is hereby granted, provided
- that the above copyright notice appear in all copies and that both that
- copyright notice and this permission notice appear in supporting
- documentation.
-
- We disclaim all warranties with regard to this software, including all
- implied warranties of merchantability and fitness, in no event shall
- we be liable for any special, indirect or consequential damages or any
- damages whatsoever resulting from loss of use, data or profits, whether in
- an action of contract, negligence or other tortious action, arising out of
- or in connection with the use or performance of this software.
-*/
-
-#ifndef __NSException_h__
-#define __NSException_h__
-
-#include <setjmp.h>
-#include <stdarg.h>
-#include <Foundation/NSString.h>
-#include <Foundation/NSArray.h>
-
-@interface NSException : NSObject
-{
- NSString* name;
- NSString* reason;
- NSDictionary* userInfo;
-}
-
-/* Class initalization */
-+ (void)taskNowMultiThreaded:notification;
-
-/* Creating and Raising Exceptions */
-+ (NSException*)exceptionWithName:(NSString*)name
- reason:(NSString*)reason
- userInfo:(NSDictionary*)userInfo;
-+ (void)raise:(NSString *)name
- format:(NSString *)format,...;
-+ (void)raise:(NSString*)name
- format:(NSString*)format
- arguments:(va_list)argList;
-
-- (id)initWithName:(NSString*)name
- reason:(NSString*)reason
- userInfo:(NSDictionary*)userInfo;
-- (void)raise;
-
-/* Querying Exceptions */
-- (NSString*)name;
-- (NSString*)reason;
-- (NSDictionary*)userInfo;
-
-@end /* NSException */
-
-
-@interface NSException (Extensions)
-- (BOOL)exceptionIsKindOfClass:(Class)class;
- /* return [self isKindOfClass:class] */
-- (BOOL)exceptionIsIn:(NSArray*)exceptions;
-- (NSString*)errorString;
-- initWithFormat:(NSString*)format, ...;
-- setName:(NSString*)name;
-- setReason:(NSString*)reason;
-- setUserInfo:(NSDictionary*)userInfo;
-@end /* NSException (Extension) */
-
-
-typedef void NSUncaughtExceptionHandler(NSException *exception);
-
-NSUncaughtExceptionHandler *NSGetUncaughtExceptionHandler(void);
-void NSSetUncaughtExceptionHandler(NSUncaughtExceptionHandler *handler);
-
-/* Exception names */
-LF_EXPORT NSString *NSInconsistentArchiveException;
-LF_EXPORT NSString *NSGenericException;
-LF_EXPORT NSString *NSInternalInconsistencyException;
-LF_EXPORT NSString *NSInvalidArgumentException;
-LF_EXPORT NSString *NSMallocException;
-LF_EXPORT NSString *NSObjectInaccessibleException;
-LF_EXPORT NSString *NSObjectNotAvailableException;
-LF_EXPORT NSString *NSDestinationInvalidException;
-LF_EXPORT NSString *NSPortTimeoutException;
-LF_EXPORT NSString *NSInvalidSendPortException;
-LF_EXPORT NSString *NSInvalidReceivePortException;
-LF_EXPORT NSString *NSPortSendException;
-LF_EXPORT NSString *NSPortReceiveException;
-LF_EXPORT NSString *NSOldStyleException;
-LF_EXPORT NSString *NSRangeException;
-
-
-typedef struct _NSHandler
-{
- struct _NSHandler* previousHandler;
- jmp_buf jmpState;
- NSException* exception;
-} NSHandler;
-
-LF_EXPORT void _NSAddHandler(NSHandler *handler);
-LF_EXPORT void _NSRemoveHandler(NSHandler *handler);
-
-/* OpenStep macros for exception handling. */
-
-#define NS_DURING \
-({ \
- __label__ _quit; \
- NSHandler exceptionHandler; \
- if(!setjmp(exceptionHandler.jmpState)) { \
- _NSAddHandler(&exceptionHandler);
-
-#define NS_HANDLER \
- _NSRemoveHandler(&exceptionHandler); \
- goto _quit; /* to remove compiler warning about unused label*/ \
- } \
- else { \
- NSException* localException = exceptionHandler.exception; \
- _NSRemoveHandler(&exceptionHandler); \
-
-#define NS_ENDHANDLER \
- localException = nil; /* Avoid compiler warning */ \
- } \
-_quit: 0;\
-});
-
-#define NS_VALRETURN(value) \
- ({_NSRemoveHandler(&exceptionHandler); return (value);})
-
-#define NS_VOIDRETURN \
- ({_NSRemoveHandler(&exceptionHandler); return;})
-
-
-/*
- * The new macros for handling exceptions.
- */
-
-#define TRY \
-({ \
- __label__ _quit; \
- NSHandler exceptionHandler; \
- volatile int __setjmp_ret = setjmp(exceptionHandler.jmpState); \
- if(!__setjmp_ret) { \
- _NSAddHandler(&exceptionHandler);
-
-#define END_TRY \
- _NSRemoveHandler(&exceptionHandler); \
- goto _quit; /* to remove compiler warning about unused label */ \
- } \
-_quit: \
- { \
- void handler(NSException* localException) \
- { \
- BOOL _caught = NO; \
- if(localException) \
- _NSRemoveHandler(&exceptionHandler); \
- if(!localException) {
-
-#define CATCH(exception_class) \
- } else if([localException isKindOfClass:[exception_class class]]) { \
- _caught = YES;
-
-#ifndef PRECOMP
-# define MULTICATCH(exception_classes...) \
- } else if([localException exceptionIsIn: \
- [NSArray arrayWithObjects:##exception_classes, nil]]) { \
- _caught = YES;
-#endif /* PRECOMP */
-
-#define OTHERWISE \
- } else { \
- _caught = YES;
-
-#define CLEANUP \
- } \
- if(localException && !_caught) {
-
-#define FINALLY \
- } \
- if(1) {
-
-#define END_CATCH \
- } \
- if(!localException) return; \
- if(!_caught) \
- [localException raise]; \
- else RELEASE(localException); \
- } \
- handler(__setjmp_ret == 1 ? exceptionHandler.exception : nil); \
- } \
-});
-
- /* Use BREAK inside a TRY block to get out of it */
-#define BREAK ({_NSRemoveHandler(&exceptionHandler); goto _quit;})
-
-#ifndef PRECOMP
- /* If you want to generate an exception issue a THROW with the exception
- an object derived from the NSException class. */
-# define THROW(exception...) [##exception raise]
-#else
-# define THROW(exception) [exception raise]
-#endif /* PRECOMP */
-
- /* If you want to reraise an exception inside an exception handler
- just say RERAISE. */
-#define RERAISE THROW(localException)
-
-
-/*
- * Assertions.
- */
-
-#ifndef __FoundationException_definition__
-#define __FoundationException_definition__
-
-@interface FoundationException : NSException
-@end
-
-#endif /* __FoundationException_definition__ */
-
-@interface AssertException : FoundationException
-@end
-
-
-@interface NSAssertionHandler : NSObject
-
-/* Getting the Current Handler */
-+ (NSAssertionHandler*)currentHandler;
-
-/* Handling Failures */
-- (void)handleFailureInFunction:(NSString*)functionName
- file:(NSString*)fileName
- lineNumber:(int)line
- description:(NSString*)format,...;
-- (void)handleFailureInMethod:(SEL)selector
- object:(id)object
- file:(NSString*)fileName
- lineNumber:(int)line
- description:(NSString*)format,...;
-
-@end
-
-#ifndef PRECOMP
-
-#define NSAssert(condition, desc, arguments...) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInMethod:_cmd \
- object:self \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , ##arguments]; \
- 0;})
-
-#define NSCAssert(condition, desc, arguments...) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInFunction: \
- [NSString stringWithCString:__PRETTY_FUNCTION__] \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , ##arguments]; \
- 0;})
-
-#define Assert(condition) \
- ({if(!(condition)) {\
- NSLog([(@#condition) stringByPrependingString:@"Assertion failed: "]); \
- THROW([AssertException new]); \
- } \
- 0;})
-
-# define NSParameterAssert(condition) \
- ({if(!(condition)) {\
- NSLog([(@#condition) stringByPrependingString:@"Parameter Assertion failed: "]); \
- THROW([AssertException new]); \
- } \
- 0;})
-
-# define NSCParameterAssert(condition) \
- ({if(!(condition)) {\
- NSLog([(@#condition) stringByPrependingString:@"Parameter Assertion failed: "]); \
- THROW([AssertException new]); \
- } \
- 0;})
-
-#define NSAssert1(args...) NSAssert(##args)
-#define NSAssert2(args...) NSAssert(##args)
-#define NSAssert3(args...) NSAssert(##args)
-#define NSAssert4(args...) NSAssert(##args)
-#define NSAssert5(args...) NSAssert(##args)
-
-#define NSCAssert1(args...) NSCAssert(##args)
-#define NSCAssert2(args...) NSCAssert(##args)
-#define NSCAssert3(args...) NSCAssert(##args)
-#define NSCAssert4(args...) NSCAssert(##args)
-#define NSCAssert5(args...) NSCAssert(##args)
-
-#endif /* PRECOMP */
-
-
-#endif /* __NSException_h__ */
-
-/*
- Local Variables:
- c-basic-offset: 4
- tab-width: 8
- End:
-*/
Modified: trunk/Foundation/NSConcreteData.m
===================================================================
--- trunk/Foundation/NSConcreteData.m 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/NSConcreteData.m 2006-08-31 22:26:13 UTC (rev 281)
@@ -94,7 +94,7 @@
}
@catch (id e) {
NSZoneFree(NULL, buffer);
- @throw e;
+ LFObjC_ExceptionThrow(e);
}
/* Instantiated NSData instances will free buffer upon deallocation */
Modified: trunk/Foundation/NSException.h
===================================================================
--- trunk/Foundation/NSException.h 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/NSException.h 2006-08-31 22:26:13 UTC (rev 281)
@@ -36,6 +36,7 @@
#include <Foundation/NSString.h>
#include <stdarg.h>
+#include <setjmp.h>
@class NSString, NSDictionary;
@@ -77,7 +78,7 @@
@end
/*!
- * Function type used for NSSetUncaughtExceptionHandler() and NSGetUncaughtExceptionHandler()
+ * Function type used for NSSetUncaughtExceptionHandler() and NSGetUncaughtExceptionHandler().
* @ingroup NSException
*/
typedef void NSUncaughtExceptionHandler (NSException *exception);
@@ -85,11 +86,58 @@
void NSSetUncaughtExceptionHandler(NSUncaughtExceptionHandler *handler);
NSUncaughtExceptionHandler *NSGetUncaughtExceptionHandler(void);
-/* Legacy Exception Handling */
-#define NS_DURING @try {
-#define NS_HANDLER } @catch (NSException *localException) {
-#define NS_ENDHANDLER }
-#define NS_VALUERETURN(val, type) return (val);
-#define NS_VOIDRETURN return;
+/*
+ * Exception handling for the Apple runtime, and old-style exceptions
+ * in the GNU runtime.
+ *
+ * When language exceptions are enabled with Apple's runtime, the compiler
+ * will pass this structure to LFObjC_ExceptionThrow().
+ * Alternatively, old-style exception handling passes this structure manually.
+ *
+ * Do not touch these data structures, do not call these functions manually.
+ */
+typedef struct LFObjCLocalExceptionData {
+ jmp_buf buf;
+ void *pointers[4]; /* The exception is stored in the first pointer */
+} LFObjCLocalExceptionData;
+void _NSAddHandler (LFObjCLocalExceptionData *excData);
+void _NSRemoveHandler (LFObjCLocalExceptionData *excData);
+NSException *_NSExceptionFromHandler (LFObjCLocalExceptionData *excData);
+
+#ifdef LF_OBJC_LANGUAGE_EXCEPTIONS
+/* New-style Exception Handling */
+# define NS_DURING @try {
+# define NS_HANDLER } @catch (NSException *localException) {
+# define NS_ENDHANDLER }
+# define NS_VALUERETURN(val, type) return (val);
+# define NS_VOIDRETURN return;
+#else
+/* Old-style Exception Handling */
+# define NS_DURING { \
+ LFObjCLocalExceptionData _localHandler; \
+ if(!_setjmp(_localHandler.buf)) { \
+ _NSAddHandler(&_localHandler);
+
+#define NS_HANDLER \
+ _NSRemoveHandler(&_localHandler); \
+ } else { \
+ NSException *localException = _NSExceptionFromHandler(&_localHandler);
+
+#define NS_ENDHANDLER \
+ localException = nil; /* Avoid compiler warning */ \
+ } \
+}
+
+# define NS_VALUERETURN(value, type) { \
+ return (value); \
+}
+
+# define NS_VOIDRETURN { \
+ _NSRemoveHandler(&_localHandler); \
+ return; \
+}
+
+#endif /* !LF_OBJC_LANGUAGE_EXCEPTIONS */
+
#endif /* __NSException_h__ */
Modified: trunk/Foundation/NSException.m
===================================================================
--- trunk/Foundation/NSException.m 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/NSException.m 2006-08-31 22:26:13 UTC (rev 281)
@@ -245,7 +245,7 @@
* Raise the receiver.
*/
- (void) raise {
- @throw self;
+ LFObjC_ExceptionThrow(self);
}
Deleted: trunk/Foundation/NSFuncallException.h
===================================================================
--- trunk/Foundation/NSFuncallException.h 2006-08-31 07:30:41 UTC (rev 280)
+++ trunk/Foundation/NSFuncallException.h 2006-08-31 22:26:13 UTC (rev 281)
@@ -1,391 +0,0 @@
-/*
- NSFuncallException.h
-
- Copyright (C) 1995, 1996 Ovidiu Predescu and Mircea Oancea.
- All rights reserved.
-
- Author: Ovidiu Predescu <ov...@bx...>
-
- This file is part of libFoundation.
-
- Permission to use, copy, modify, and distribute this software and its
- documentation for any purpose and without fee is hereby granted, provided
- that the above copyright notice appear in all copies and that both that
- copyright notice and this permission notice appear in supporting
- documentation.
-
- We disclaim all warranties with regard to this software, including all
- implied warranties of merchantability and fitness, in no event shall
- we be liable for any special, indirect or consequential damages or any
- damages whatsoever resulting from loss of use, data or profits, whether in
- an action of contract, negligence or other tortious action, arising out of
- or in connection with the use or performance of this software.
-*/
-
-#ifndef __NSException_h__
-#define __NSException_h__
-
-#include <setjmp.h>
-#include <stdarg.h>
-#include <Foundation/NSString.h>
-#include <Foundation/NSArray.h>
-
-@class NSDictionary;
-
-@interface NSException : NSObject
-{
- NSString *name;
- NSString *reason;
- NSDictionary *userInfo;
-}
-
-/* Creating and Raising Exceptions */
-
-+ (NSException *)exceptionWithName:(NSString *)name
- reason:(NSString *)reason
- userInfo:(NSDictionary *)userInfo;
-+ (void)raise:(NSString *)name
- format:(NSString *)format,...;
-+ (void)raise:(NSString *)name
- format:(NSString *)format
- arguments:(va_list)argList;
-
-- (id)initWithName:(NSString *)name
- reason:(NSString *)reason
- userInfo:(NSDictionary *)userInfo;
-- (void)raise;
-
-/* Querying Exceptions */
-
-- (NSString *)name;
-- (NSString *)reason;
-- (NSDictionary *)userInfo;
-
-@end /* NSException */
-
-
-@interface NSException (Extensions)
-- (BOOL)exceptionIsKindOfClass:(Class)class;
- /* return [self isKindOfClass:class] */
-- (BOOL)exceptionIsIn:(NSArray *)exceptions;
-- (NSString *)errorString;
-- (id)initWithFormat:(NSString *)format, ...;
-- (id)initWithFormat:(NSString *)format arguments:(va_list)ap;
-- (id)setName:(NSString *)name;
-- (id)setReason:(NSString *)reason;
-- (id)setUserInfo:(NSDictionary *)userInfo;
-@end /* NSException (Extension) */
-
-@interface NSException (Backtrace)
-+ (NSString *)backtrace;
-+ (void)printBacktrace;
-@end /* NSException(Backtrace) */
-
-typedef void NSUncaughtExceptionHandler(NSException *exception);
-
-NSUncaughtExceptionHandler *NSGetUncaughtExceptionHandler(void);
-void NSSetUncaughtExceptionHandler(NSUncaughtExceptionHandler *handler);
-
-/* Exception names */
-LF_EXPORT NSString *NSInconsistentArchiveException;
-LF_EXPORT NSString *NSGenericException;
-LF_EXPORT NSString *NSInternalInconsistencyException;
-LF_EXPORT NSString *NSInvalidArgumentException;
-LF_EXPORT NSString *NSMallocException;
-LF_EXPORT NSString *NSObjectInaccessibleException;
-LF_EXPORT NSString *NSObjectNotAvailableException;
-LF_EXPORT NSString *NSDestinationInvalidException;
-LF_EXPORT NSString *NSPortTimeoutException;
-LF_EXPORT NSString *NSInvalidSendPortException;
-LF_EXPORT NSString *NSInvalidReceivePortException;
-LF_EXPORT NSString *NSPortSendException;
-LF_EXPORT NSString *NSPortReceiveException;
-LF_EXPORT NSString *NSOldStyleException;
-LF_EXPORT NSString *NSRangeException;
-
-/* OpenStep macros for exception handling.
- Use the ones defined below instead. */
-
-#define NS_DURING TRY {
-
-#define NS_HANDLER } END_TRY OTHERWISE {
-
-#define NS_ENDHANDLER } END_CATCH
-
-#define NS_VALRETURN(value) \
- ({_NSRemoveHandler(&exceptionHandler); handler(nil); return (value);})
-
-#define NS_VOIDRETURN \
- ({_NSRemoveHandler(&exceptionHandler); handler(nil); return;})
-
-typedef void (*THandlerFunction)(id);
-
-typedef struct _NSHandler
-{
- struct _NSHandler *previousHandler;
- jmp_buf jmpState;
- THandlerFunction handler;
-} NSHandler;
-
-LF_EXPORT void _NSAddHandler(NSHandler *handler);
-LF_EXPORT void _NSRemoveHandler(NSHandler *handler);
-
-
-/*
- * The new macros for handling exceptions.
- */
-
-#define TRY \
-{ \
- auto void handler(); \
- NSHandler exceptionHandler; \
-\
- int _dummy = \
- ({ \
- __label__ _quit; \
- if(!setjmp(exceptionHandler.jmpState)) { \
- exceptionHandler.handler = handler; \
- _NSAddHandler(&exceptionHandler);
-
-#define END_TRY \
- _NSRemoveHandler(&exceptionHandler); \
- handler(nil); \
- goto _quit; /* to remove compiler warning about unused label*/ \
- }; \
- _quit: 0; \
- }); \
- void handler(NSException *localException) \
- { \
- BOOL _caught = NO; \
- RETAIN(localException);\
- if (localException != nil) \
- _NSRemoveHandler(&exceptionHandler); \
- if (localException == nil) { _dummy++;
-
-#define CATCH(exception_class) \
- } else if([localException exceptionIsKindOfClass:[exception_class class]]) { \
- _caught = YES;
-
-#ifndef PRECOMP
-# define MULTICATCH(exception_classes...) \
- } else if ([localException exceptionIsIn: \
- [NSArray arrayWithObjects:##exception_classes, nil]]) { \
- _caught = YES;
-#endif /* PRECOMP */
-
-#define OTHERWISE \
- } else { \
- _caught = YES;
-
-#define CLEANUP \
- } \
- if(localException && !_caught) {
-
-#define FINALLY \
- } \
- if(1) {
-
-#define END_CATCH \
- } \
- if (localException==nil) return; \
- if (!_caught) \
- [localException raise]; \
- else {\
- RELEASE(localException); \
- longjmp(exceptionHandler.jmpState, 1); \
- }\
- } \
-}
-
-
-/* Use BREAK inside a TRY block to get out of it */
-#define BREAK ({_NSRemoveHandler(&exceptionHandler); goto _quit;})
-
-#ifndef PRECOMP
-/* If you want to generate an exception issue a THROW with the exception
- an object derived from the NSException class. */
-# define THROW(exception...) [##exception raise]
-#else
-# define THROW(exception) [exception raise]
-#endif /* PRECOMP */
-
-/* If you want to reraise an exception inside an exception handler
- just say RERAISE. */
-#define RERAISE [localException raise]
-
-
-
-/*
- * Assertions.
- */
-
-#ifndef __FoundationException_definition__
-#define __FoundationException_definition__
-
-@interface FoundationException : NSException
-@end
-
-#endif /* __FoundationException_definition__ */
-
-@interface AssertException : FoundationException
-@end
-
-
-@interface NSAssertionHandler : NSObject
-
-/* Getting the Current Handler */
-+ (NSAssertionHandler*)currentHandler;
-
-/* Handling Failures */
-- (void)handleFailureInFunction:(NSString*)functionName
- file:(NSString*)fileName
- lineNumber:(int)line
- description:(NSString*)format,...;
-- (void)handleFailureInMethod:(SEL)selector
- object:(id)object
- file:(NSString*)fileName
- lineNumber:(int)line
- description:(NSString*)format,...;
-
-@end
-
-
-#ifndef PRECOMP
-# define NSAssert(condition, desc, arguments...) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInMethod:_cmd \
- object:self \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , ##arguments]; \
- 0;})
-
-# define NSCAssert(condition, desc, arguments...) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInFunction: \
- [NSString stringWithCString:__PRETTY_FUNCTION__] \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , ##arguments]; \
- 0;})
-
-# define Assert(condition) \
- ({if(!(condition)) {\
- NSLog([(@#condition) stringByPrependingString:@"Assertion failed: "]); \
- [[AssertException new] raise]; \
- } \
- 0;})
-
-# define NSParameterAssert(condition) \
- ({if(!(condition)) {\
- NSLog([(@#condition) stringByPrependingString:@"Parameter Assertion failed: "]); \
- [[AssertException new] raise]; \
- } \
- 0;})
-
-# define NSCParameterAssert(condition) \
- ({if(!(condition)) {\
- NSLog([(@#condition) stringByPrependingString:@"Parameter Assertion failed: "]); \
- [[AssertException new] raise]; \
- } \
- 0;})
-
-# define NSAssert1(condition, desc, a1) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInMethod:_cmd object:self \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1]; \
- 0;})
-# define NSAssert2(condition, desc, a1, a2) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInMethod:_cmd object:self \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2]; \
- 0;})
-# define NSAssert3(condition, desc, a1, a2, a3) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInMethod:_cmd object:self \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2, a3]; \
- 0;})
-# define NSAssert4(condition, desc, a1, a2, a3, a4) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInMethod:_cmd object:self \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2, a3, a4]; \
- 0;})
-# define NSAssert5(condition, desc, a1, a2, a3, a4, a5) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInMethod:_cmd object:self \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2, a3, a4, a5]; \
- 0;})
-
-# define NSCAssert1(condition, desc, a1) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInFunction: \
- [NSString stringWithCString:__PRETTY_FUNCTION__] \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1]; \
- 0;})
-# define NSCAssert2(condition, desc, a1, a2) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInFunction: \
- [NSString stringWithCString:__PRETTY_FUNCTION__] \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2]; \
- 0;})
-# define NSCAssert3(condition, desc, a1, a2, a3) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInFunction: \
- [NSString stringWithCString:__PRETTY_FUNCTION__] \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2, a3]; \
- 0;})
-# define NSCAssert4(condition, desc, a1, a2, a3, a4) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInFunction: \
- [NSString stringWithCString:__PRETTY_FUNCTION__] \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2, a3, a4]; \
- 0;})
-# define NSCAssert5(condition, desc, a1, a2, a3, a4, a5) \
- ({ if(!(condition)) \
- [[NSAssertionHandler currentHandler] \
- handleFailureInFunction: \
- [NSString stringWithCString:__PRETTY_FUNCTION__] \
- file:[NSString stringWithCString:__FILE__] \
- lineNumber:__LINE__ \
- description:(desc) , a1, a2, a3, a4, a5]; \
- 0;})
-
-#endif /* PRECOMP */
-
-#endif /* __NSException_h__ */
-
-/*
- Local Variables:
- c-basic-offset: 4
- tab-width: 8
- End:
-*/
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|