[cfe-dev] [LLVMdev] Clang devirtualization proposal

Sanjoy Das sanjoy at playingwithpointers.com
Fri Jul 31 23:22:50 PDT 2015


On Fri, Jul 31, 2015 at 6:18 PM, Reid Kleckner <rnk at google.com> wrote:
> Consider this pseudo-IR and some possible transforms that I would expect to
> be semantics preserving:
>
> void f(i32* readonly %a, i32* %b) {
>   llvm.assume(%a == %b)
>   store i32 42, i32* %b
> }
>   ...
>   %p = alloca i32
>   store i32 13, i32* %p
>   call f(i32* readonly %p, i32* %p)
>   %r = load i32, i32* %p
>
> ; Propagate llvm.assume info
> void f(i32* readonly %a, i32* %b) {
>   store i32 42, i32* %a
> }
>   ...
>   %p = alloca i32
>   store i32 13, i32* %p
>   call f(i32* readonly %p, i32* %p)
>   %r = load i32, i32* %p

I'd say this first transformation is incorrect.  `readonly` is
effectively part of `%a`'s "type" as it constrains and affects the
operations you can do on `%a`. Even if `%b` is bitwise equivalent to
`%a` at runtime, it is "type incompatible" to replace `%a` with `%b`.

This is similar to how you cannot replace `store i32 42, i32
addrspace(1)* %a` with `store i32 42, i32 addrspace(2)* %b`, even if
you can prove `ptrtoint %a` == `ptrtoint %b` -- the nature of `store`
is dependent on the type of the pointer you store through.

The glitch in LLVM IR right now is that the `readonly`ness of `%a` is
not modeled in the type system, when I think it should be. An `i32
readonly*` should be a different type from `i32*`.  In practice this
may be non-trivial to get right (for instance `phi`s and `selects`
will either have to do a type merge, or we'd have to have explicit
type operators at the IR level).

-- Sanjoy



More information about the cfe-dev mailing list