[llvm-commits] [llvm] r123621 - in /llvm/trunk: lib/CodeGen/SelectionDAG/TargetLowering.cpp test/CodeGen/X86/ctpop-combine.ll

Dirk Steinke steinke.dirk.ml at googlemail.com
Tue Jan 18 14:54:24 PST 2011


On 01/18/2011 06:51 PM, Chris Lattner wrote:
>
> On Jan 18, 2011, at 9:46 AM, Benjamin Kramer wrote:
>
>>
>> On 18.01.2011, at 18:29, Chris Lattner wrote:
>>
>>> On Jan 18, 2011, at 7:38 AM, Benjamin Kramer wrote:
>>>>> This seems like an important loop!  One simple thing that I see is that we have:
>>>>>
>>>>> ...
>>>>>      imulq   %r9, %r13
>>>>>      shrq    $56, %r13
>>>>> ...
>>>>>      imulq   %r9, %rbp
>>>>>      shrq    $56, %rbp
>>>>>      subl    %r13d, %ebp
>>>>> ...
>>>>>      cmpl    $2, %ebp
>>>>>      jne     LBB4_14
>>>>>
>>>>> Is there some cheaper way to do ((x*0x101010101010101)>>56)-((y*0x101010101010101)>>56) != 2?
>>>>
>>>> Applying distributive laws yields ((x-y)*0x101010101010101)>>56 != 2, however adding a
>>>> "machine distribution" pass just to catch this one feels like overkill.
>>>
>>> Interesting! If that was safe then this could recursively simplify even more.  Is distribution safe across shifts though?  Instcombine doesn't simplify this, and doesn't simplify the similar code with add instead of sub:
>>
>> No it's not, I was confused, shifts are not distributive even for unsigned integers :(
>
> The only cleverness I can come up with is something like:
>
>   ((x - (y&  (-1<<  56)))>>  56)&  255
>
> This is the same number of operations, but the&255 can be done implicitly with subreg tricks on X86.  I don't think that this is worth implementing though.
>
> -Chris

Normally you could turn (A >> S) - (B >> S) == N into
   (A ^ (B + (N << S))) & (-1 << S) == 0,
   or (A ^ (B + (N << S))) >> S == 0
Unfortunately, in this case, the immediates are too big to be folded 
into the add and test instructions.

But I just had another idea: perhaps we can fold the two multiplies 
together. If we know, that each byte of the source words can only be 
within [0..8], we should be able to transform
    ((x*0x101010101010101)>>56)-((y*0x101010101010101)>>56) != 2
into
    (((x - y + 0x0808080808080808) * 0x0101010101010101) >> 56) != 66
Am I missing something?

Dirk

> _______________________________________________
> llvm-commits mailing list
> llvm-commits at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits




More information about the llvm-commits mailing list