Just to note, I've read the questions and read the blog posts and I've also referenced the ABI.
What I completely don't understand is how that interacts with LLVM's EH intrinsics. The LLVM EH page gives a very vague overview- not exactly a checklist of "Implement X, Y, Z".
The LLVM EH page references the Itanium ABI directly. This would imply to me that LLVM only supports Itanium ABI exceptions. But I already know that Clang supports ARM and is developing support for Microsoft ABIs. So exactly how specific is LLVM's implementation of EH to the Itanium ABI?
When referencing the _Unwind stuff defined by Itanium ABI, is that obliged to be provided by a backend, or would I have to implement it for myself?
I also noticed that the LLVM IR generated by Clang does not reveal any language-specific tables, any exception frames, exception tables, or anything like that. In that case, how does LLVM know how to generate the language-specific data?
In short, how exactly do you go from LSDAs, EH contexts, and _Unwind_RaiseException
to landingpad
and resume
?
Edit: Just for reference, I'm going to be JITting the resulting code on Windows.
Nowadays Itanium C++ ABI is de facto standard C++ ABI used on many other platforms. Itanium C++ ABI supports zero cost exception handling technique, which is the most widespread technique for today.
To support exception handling one must change the semantics of a function
call. Now the calls fork the execution flow. One branch is taken when
everything is fine and the second branch is taken in case of an exception.
In LLVM IR there is the invoke
instruction to call functions that may throw.
When the second branch is taken several kinds of actions may be performed:
It's clear that some additional code must be generated to perform these actions.
That's why we've got the landingpad
instruction as well. It is the first
instruction to be executed after invoke
ends up with an exception.
But the main magic is performed at run-time. After an exception is thrown, the language agnostic runtime unwinds the stack, for every frame it finds language specific data area (LSDA) and calls language specific personality routine. The personality routine inspects program counter, LSDA and the current exception. It determines if any cleanup is necessary, if any throw specification is violated or if the exception can be caught by this frame.
As you probably know, all these data (personality routine, catched types, throw specification, cleanup actions) are already specified in landingpad
instruction, so no additional data should be passed to the backend to generate
exception-related sections in object file.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With