[LLVMdev] RFC: New Exception Handling Proposal

Bill Wendling wendling at apple.com
Mon Nov 23 11:05:06 PST 2009


On Nov 20, 2009, at 2:15 AM, Jay Foad wrote:

>> Please read and let me know your opinions!
>
> This definitely seems like an improvement on the current situation.
>
>>            .---------.
>>            | convoke |
>>            `---------'
>>                 |
>>                 v
>>     .-----------------------.
>>     |                       |
>>     v                       |
>>  %normal   .----------------+---------------.
>>            |                |      ...      |
>>            v                v               v
>>       select.1 = 1   select.2 = 2    select.n = n
>>            |                |               |
>>            `----------------+---------------'
>>                             |
>>                             v
>>          .----------------------------------------.
>>          | %sel = phi [%select.1, ..., %select.n] |
>>          |     %eh_ptr = llvm.eh.exception()      |
>>          |           [cleanup code]               |
>>          |           switch on %sel               |
>>          `----------------------------------------'
>>                             |
>>                             v
>>                  .--------------------.
>>                  |          |   ...   |
>>                  v          v         v
>>               %catch.1   %catch.2  %catch.n
>
> One thing I don't like about this (not that it's any worse than the
> current situation) is that the llvm.eh.exception() call is now quite a
> long way away from the landing pads.
>
> As I understand it, when you generate native code, at each landing pad
> the exception pointer appears magically in a well-known native
> register. Do you think there's a way to model this more closely in the
> LLVM IR? (You could just specify that the llvm.eh.exception call has
> to be at the start of a landing pad, but I think that is too prone to
> being broken by optimisation passes.)
>
Well, it's not entirely magical. :-) It gets the exception object by  
calling __cxa_get_exception_ptr and __cxa_begin_catch (though both  
calls can be combined into __cxa_begin_catch, which is what we do).  
It's feasible to simply generate the llvm.eh.exception at the start of  
the catch block code and have that convert into the call to  
__cxa_begin_catch. My only concern is that we need to make sure that  
all EH conventions work in a similar way.

> To illustrate why I don't like having the llvm.eh.exception() call
> dissociated from the landing pads, what is the *exact* definition of
> llvm.eh.exception:
>
> - Does there have to be a one-to-one correspondence between convokes
> and llvm.eh.exception calls?
> - Does llvm.eh.exception have to be dominated by landing pads?
> - Does it just return the exception pointer from the *most recent*
> landing pad that execution flowed through?
>
> etc.
>
> Maybe (this has just occurred to me) the llvm.eh.exception call could
> explicitly refer to a convoke, which must dominate it?
>
Well, be warned that there can be multiple convokes which jump to the  
same landing pads. So there cannot be a one-to-one correspondence  
between them. However, an llvm.eh.exception should be dominated by at  
least one convoke. The only other problem I can see is if code  
branches into a catch block. It's gross, but could happen. In that  
case, the llvm.eh.exception should *not* be executed, because it's  
metadata constructed by the compiler, not user code. It would have to  
be peeled out into its own basic block in such instances.

-bw




More information about the llvm-dev mailing list