I have build a Ruby extension in Objective-C. Now I want to use @throw/@catch etc. instead of macro based exception handling and self build error handling.
I am using the GNU runtime shipped with the GCC.
When I run my Ruby app with my extension it core dumps as soon as an exception occurs. The abort() comes from the GNU Objective-C runtime (libobjc/exception.c:375):
void
objc_exception_throw (id value)
{
struct ObjcException *header = calloc (1, sizeof (*header));
header->base.exception_class = __objc_exception_class;
header->base.exception_cleanup = __objc_exception_cleanup;
header->value = value;
#ifdef SJLJ_EXCEPTIONS
_Unwind_SjLj_RaiseException (&header->base);
#else
_Unwind_RaiseException (&header->base);
#endif
/* Some sort of unwinding error. */
abort ();
}
Since I compiled with -fobjc-exceptions I think _Unwind_RaiseException is being called.
Is there any way to use the Objective-C exceptions in a Ruby extension?
Problem solved:
The GNU Objective-C runtime does not handle the result of
_Unwind_(SjLj_)RaiseException(see code above). In my case it returned5which stands for “end of stack” and means that I had forgotten a @try/@catch block.There really should be some logging or a hook to do it self.
Update:
Unless one compiles Ruby with
-fobjc-exceptionsthe Objective-C exception handling cannot trace the stack through Ruby code. Therefore you must be aware to catch and wrap or translate any Objective-C exception before giving control to Ruby.