[LLVMdev] One way to support unwind on x86
Bjarke Walling
bwp at bwp.dk
Tue Mar 3 05:27:36 PST 2009
Hi Nicolas,
On Tue, Mar 3, 2009 at 11:38 AM, Nicolas Geoffray
<nicolas.geoffray at lip6.fr> wrote:
>
> Duncan Sands wrote:
>>
>> Another possibility, very close you yours and currently used by the vmkit
>> project, is to modify all functions so they return two values, the usual
>> return value and an additional boolean value indicating whether an
>> exception
>> was thrown during the call or not. Callers then branch to an appropriate
>> place based on this value. Thus there is no special stack unwinding, it
>> is just functions returning. This adds some distributed overhead, but
>> unwinding is fast. You can always return something more complicated than
>> a boolean of course.
>
>
> That's correct. Although, to make things clear, I'm not using the multiple
> return value features of LLVM. The signature of functions only return one
> value. If an exception happens, the boolean value is stored in a thread
> local specific variable. But conceptually, this pretty much is the same than
> returning two values.
I see. So you check this value stored in a thread-local variable after
each call? And you lower invoke to a call and branch with regard to
this value?
> It's *hardly* noticeable. If your language/runtime throws a lot of
> exceptions, that's the way to go currently (there are other sophisticated
> techniques, but much more complex). Dwarf is great if your language/runtime
> basically never throws exceptions. I can't give you an accurate measure of
> the real cost of Dwarf on Java applications because, unfortunately, libgcc
> did not optimize its dwarf info lookup on dynamically registered frames.
> It's doing a linear search of the info, and that takes *a lot* of time.
In my view I would use exceptions a lot more if they were very
efficient. Exceptions are nice, because they break the current code
flow and send a signal/message in the dynamic call stack.
What are these sophisticated techniques you are talking about? My time
frame for implementing this is, not unlimited, but fairly long. Less
than a year (of spare time) would be ok. I still need to feel
progress.
Another option I'm thinking about is creating a runtime that, when
initialized, compiles the DWARF information to native code. It could
create an Instruction Pointer lookup hash table associated with unwind
actions. Maybe libgcc/libunwind does this already? Starting your
executable would have a small overhead, but unwinding would be
efficient. I didn't start implementing this, mainly because I'm not
sure it's already implemented and also because I think exceptions,
like many other programming concepts, should be placed as a
responsibility of the compiler, not the executable. If I could place
as much overhead for the unwinding proces as possible in the compiler
instead of the runtime it would be great. I thought that instead of
the runtime created lookup table you could encode it as jmp
instructions after each call. It is like the optimisation of
malloc/free where you write a size value just before the allocated
memory block. The memory is in itself a hash table if the hashes are
memory locations.
Bjarke Walling
More information about the llvm-dev
mailing list