[LLVMdev] About trapvalues

Dan Gohman gohman at apple.com
Tue Apr 12 18:57:26 PDT 2011

On Apr 12, 2011, at 9:59 AM, Jianzhou Zhao wrote:

> Hi,
> I am trying to understand trapvalues
>   http://llvm.org/docs/LangRef.html#trapvalues
> My question is that how LLVM expects to use trapvalues. Should we track if a value is trapped or not at runtime or statically? One rule (for terminator instruction) that defines a trap value is
>   # An instruction control-depends on a terminator instruction if the terminator instruction has multiple successors and the instruction is always executed when control transfers to one of the successors, and may not be executed when control is transfered to another.
> But, at runtime, it seems difficult to know if an instruction "may not be executed when control is transfered to another." For example of the code given on the webpage.
> entry:
>   ...
>   %br i1 %cmp, %true, %end ; Branch to either destination.
> true:
>    ...
>    br label %end
> end:
>    ...
>    volatile store i32 0, i32* @g ; %end is control-equivalent to %entry
>                                             ; so this is defined (ignoring earlier
>                                             ; undefined behavior in this example).
> Statically, we can see the store in the end block is not trapped since it always runs no matter what value %cmp is. But at runtime, we may have to keep track of the code's CFG. 

Yes. I believe fully precise trap tracking would require a
highly elaborate combination of static and dynamic analysis, 
and at the whole-program level.

> On other hand, the rules for Phi nodes/Arguments/Calls are defined in terms of dynamic states for preciseness.
> #Phi nodes depend on the operand corresponding to their dynamic predecessor basic block.
> #Function arguments depend on the corresponding actual argument values in the dynamic callers of their functions.
> #Call instructions depend on the ret instructions that dynamically transfer control back to them.
> I think Function arguments and calls are fine to keep track at runtime. But Phi nodes have the same problem as the terminator instruction rule. My confusion is the operational meaning of trapvalues.

The main intuition for trap values is that they can occur on
speculative code paths, and if a speculative path is discarded,
its trap values are harmlessly discarded as well. But if a trap
value reaches a non-speculative path, it triggers actual
undefined behavior.

It's unfortunate that this simple concept ended up being so
hard to verify dynamically. But, for example, dependencies have
to be fully precise even across things like call boundaries,
because neither inlining nor outlining should be able to change
program semantics. Perhaps it would be practical to develop a
conservative tracker which could catch common problems though.


More information about the llvm-dev mailing list