C++ Exception Handling Problem

Hello,

I'm in the process of creating a JIT and I've run into a problem with
exception handling. The situation I'm in is that my program will JIT
functions, which will call native C++ functions (part of the run-time
support). These native functions can throw exceptions. However, I don't
actually want to handle these exceptions in the JITted functions. There are
already try/catch blocks in place in the C++ function that calls the JITted
functions.

The problem I run into is that when exceptions are thrown, they aren't
caught anywhere. My program crashes with an error message: "terminate called
after throwing an instance of 'RunError'". Where RunError is the exception
type. Hence, the exceptions aren't getting caught where they should be.

What I'd like to know is how I can fix this situation, so that if my C++
runtime support functions throw an exception, it can unwind the JITted
functions properly, and these functions can ensure that the proper native
C++ catch block receives the exception. I looked at the LLVM docs, but I'm
still puzzled.

Hi Nyx,

I'm in the process of creating a JIT and I've run into a problem with
exception handling. The situation I'm in is that my program will JIT
functions, which will call native C++ functions (part of the run-time
support). These native functions can throw exceptions. However, I don't
actually want to handle these exceptions in the JITted functions. There are
already try/catch blocks in place in the C++ function that calls the JITted
functions.

The problem I run into is that when exceptions are thrown, they aren't
caught anywhere. My program crashes with an error message: "terminate called
after throwing an instance of 'RunError'". Where RunError is the exception
type. Hence, the exceptions aren't getting caught where they should be.

does this happen in the non-jit context. For example, suppose rather than
JITing your bitcode you compile it down to object code, and arrange for it
to be called from C++ and call C++. Do exceptions then propagate and get
caught correctly?

Ciao,

Duncan.

Duncan Sands wrote:

Hi Nyx,

I'm in the process of creating a JIT and I've run into a problem with
exception handling. The situation I'm in is that my program will JIT
functions, which will call native C++ functions (part of the run-time
support). These native functions can throw exceptions. However, I don't
actually want to handle these exceptions in the JITted functions. There
are
already try/catch blocks in place in the C++ function that calls the
JITted
functions.

The problem I run into is that when exceptions are thrown, they aren't
caught anywhere. My program crashes with an error message: "terminate
called
after throwing an instance of 'RunError'". Where RunError is the
exception
type. Hence, the exceptions aren't getting caught where they should be.

does this happen in the non-jit context. For example, suppose rather than
JITing your bitcode you compile it down to object code, and arrange for it
to be called from C++ and call C++. Do exceptions then propagate and get
caught correctly?

Ciao,

Duncan.
_______________________________________________
LLVM Developers mailing list
LLVMdev@cs.uiuc.edu http://llvm.cs.uiuc.edu
http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev

By that I assume you mean compiling into a .o object file? I presume that
would work, but I can't really do that right now because the code I produce
contains pointers to dynamically allocated structures. What I'm doing right
now is getting a function pointer from the execution engine and calling the
JITted functions directly.

Hi Nyx,

By that I assume you mean compiling into a .o object file? I presume that
would work,

why not try it with a simple model example. Because if it doesn't work
then that tells you a lot already!

but I can't really do that right now because the code I produce
contains pointers to dynamically allocated structures. What I'm doing right
now is getting a function pointer from the execution engine and calling the
JITted functions directly.

Ciao,

Duncan.

Hi,

Nyx wrote:

Hello,

I'm in the process of creating a JIT and I've run into a problem with
exception handling. The situation I'm in is that my program will JIT
functions, which will call native C++ functions (part of the run-time
support). These native functions can throw exceptions. However, I don't
actually want to handle these exceptions in the JITted functions. There are
already try/catch blocks in place in the C++ function that calls the JITted
functions.

The problem I run into is that when exceptions are thrown, they aren't
caught anywhere. My program crashes with an error message: "terminate called
after throwing an instance of 'RunError'". Where RunError is the exception
type. Hence, the exceptions aren't getting caught where they should be.

What I'd like to know is how I can fix this situation, so that if my C++
runtime support functions throw an exception, it can unwind the JITted
functions properly, and these functions can ensure that the proper native
C++ catch block receives the exception. I looked at the LLVM docs, but I'm
still puzzled.
  
I'm under the impression that the JIT doesn't handle exceptions by default.
Try including,

#include "llvm/Target/TargetOptions.h"

and before creating the JIT do,

llvm::ExceptionHandling = true;

I hope this helps.

-Argiris

Hi Nyx,

Nyx wrote:

Duncan Sands wrote:
  

Hi Nyx,

I'm in the process of creating a JIT and I've run into a problem with
exception handling. The situation I'm in is that my program will JIT
functions, which will call native C++ functions (part of the run-time
support). These native functions can throw exceptions. However, I don't
actually want to handle these exceptions in the JITted functions. There
are
already try/catch blocks in place in the C++ function that calls the
JITted
functions.

The problem I run into is that when exceptions are thrown, they aren't
caught anywhere. My program crashes with an error message: "terminate
called
after throwing an instance of 'RunError'". Where RunError is the
exception
type. Hence, the exceptions aren't getting caught where they should be.
      
My guess here is that there are JITted functions in your stack. If that's the case, you need to set the ExceptionHandling flag of LLVM on. This will make the JIT generate dwarf tables for JITted code, and libgcc will be able to unwind these functions.

Nicolas

Well that seems to fix the problem. Exceptions are now properly caught by the
C++ code.

Thank you for your help everyone!

Argiris Kirtzidis wrote: