views:

399

answers:

1

Given the following situation:

@try {
    @try {
        // raises an exception :)
        [receiver raisingFirstException];
    } @finally {
        // raises another exception :)
        [otherReceiver raisingFinalException];
    }
} @catch (id e) {
    printf("exception: %s\n", [[e stringValue] cString]);
}

Is there any way to either get the first exception within the @finally block or to get both exceptions within the @catch block?

I have code where the @finally block does some checks which may raise an exception but I don't want to loose the original exception (the root cause).

If there was no original exception but the checks fail I want the exception they throw.

+1  A: 

The best way to do this is to assign the exception to a variable that is accessible from the rest of your block.

NSException *ex;
@try {
    @try {
        [someObject methodWhichCouldThrowException];
    } @catch (NSException *e) {
        ex = e;
    } @finally {
        [anotherObject methodWhichCouldThrowADifferentException];
    }
} @catch (NSException *e) {
    // From here you can access both the exception thrown by 'someObject'
    // as well as the exception thrown by 'anotherObject'.
}
Sebastian Celis
Seems I have simplified my example too much. The first exception is thrown by a method somewhere else in the program.I will edit my question accordingly.
Tilo Prütz
But can't you still do what you want by changing your 'finally' block to a 'catch' block and set the exception to a local variable there? I'll edit my response.
Sebastian Celis
Okay, that may be an option. But the code won't be as simple as it is now :(.
Tilo Prütz
Yeah, nested exception code is never pretty. But there's really no other way to do this. You have to put in lots of 'catch' blocks and maintain references to any exceptions you might need later.
Sebastian Celis
Before the objective-c exceptions exists I used my own setjmp/longjmp implementation with a set of macros. While the macros were nearly mysterious I had access to the eventually occurred exception in the finally block :).
Tilo Prütz