[llvm-dev] IR canonicalization: select or bool math? (original) (raw)
Sanjoy Das via llvm-dev llvm-dev at lists.llvm.org
Wed Sep 28 22:12:43 PDT 2016
- Previous message: [llvm-dev] IR canonicalization: select or bool math?
- Next message: [llvm-dev] IR canonicalization: select or bool math?
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]
My gut tells me that Hal is right, and we should prefer zexts as long as the select boils down to one instruction, but let me go against my intuition and try to list two reasons why we should prefer selects:
Folding operations into selects: it is trivial to transform f(select X, Const0, Const1) to select X, f(Const0), f(Const1), while doing that can be difficult for zexts.
define i32 @sel_1_or_0(i1 %a) { %b = select i1 %a, i32 1, i32 0 %k = add i32 %b, 50 ret i32 %k }
==>
define i32 @sel_1_or_0(i1 %a) { %b = select i1 %a, i32 51, i32 50 ret i32 %b }
but
define i32 @sel_1_or_0(i1 %a) { %b = zext i1 %a to i32 %k = add i32 %b, 50 ret i32 %k }
is not as natural to transform.
zexts (resp. sexts) lose information when combined with nuw (resp. nsw) operations.
That is, if we inline
define i32 @sel_1_or_0(i1 %a) { %b = zext i1 %a to i32 ret i32 %b }
into f and get
define i32 @f(i32 %x, i32 %y) { %x.zext = ... %y.zext = ... ;; There are some existing use of %x.zext and %y.zext %a = add nuw i1 %x, %y %b = zext i1 %a to i32 ret i32 %b }
then we'll get (following your instructions, I've not verified that this actually happens :) )
define i32 @f(i1 %x, i1 %y) { %x.zext = ... %y.zext = ... %a = add nuw i32 %x.zext, %y.zext ret i32 %a }
but we've now lost information -- we no longer know that %a is 0 or 1 -- it can also be 2. This would not happen if we always canonicalized zext i1 C to iN to select C, iN 1, iN 0
-- Sanjoy
- Previous message: [llvm-dev] IR canonicalization: select or bool math?
- Next message: [llvm-dev] IR canonicalization: select or bool math?
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]