[PATCH] D127871: [RISCV] Optimize 2x SELECT for floating-point types

Craig Topper via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Sat Jul 9 23:13:29 PDT 2022


craig.topper added inline comments.


================
Comment at: llvm/lib/Target/RISCV/RISCVISelLowering.cpp:9857
+      Next->getOpcode() == MI.getOpcode() &&
+      Next->getOperand(2).getReg() == MI.getOperand(2).getReg() &&
+      Next->getOperand(5).getReg() == MI.getOperand(0).getReg() &&
----------------
liaolucy wrote:
> craig.topper wrote:
> > I don't understand the new check. Why was it wrong to optimize 1.1 and 2.1 in the failed case?
> Yesterday, I saw that x86 has  this check.
> 
> ```
> 
>   // CMOV ((CMOV F, T, cc1), T, cc2) is checked here and handled by a separate
>   // function - EmitLoweredCascadedSelect
> 
>   // This checks for case 2, but only do this if we didn't already find
>   // case 1, as indicated by LastCMOV == MI.
>   if (LastCMOV == &MI && NextMIIt != ThisMBB->end() &&
>       NextMIIt->getOpcode() == MI.getOpcode() &&
>       NextMIIt->getOperand(2).getReg() == MI.getOperand(2).getReg() &&
>       NextMIIt->getOperand(1).getReg() == MI.getOperand(0).getReg() &&
>       NextMIIt->getOperand(1).isKill()) {
>     return EmitLoweredCascadedSelect(MI, *NextMIIt, ThisMBB);
>   }
> 
> ```
> 
> Try to understand:
>  1.1 %29:fpr32 = Select_FPR32_Using_CC_GPR killed %7:gpr, %27:gpr, 4, %3:fpr32, killed %25:fpr3
>  2.1 %30:fpr32 = Select_FPR32_Using_CC_GPR killed %18:gpr, %24:gpr, 1, %16:fpr32, killed %29:fpr32
>  
> %7 (a), %27 (b)
> %18 (c), %24 (d) 
> Eg: 
> ```
>    a=b , c=d,
>     a=b , c!=d
>     a!=b, c=d,
>     a!=b, c!=d
> ```
> 
> b=d:
> ```
> %7 (a), %27 (b), 
> %18 (c), %24 (b) 
> a=b,  c=b     a=b=c
> a=b,  c!=b 
>                 a!= c (optimize)   
> a!=b, c=b
> a!=b, c!=b   a!=b!=c
> ```
X86 has the CMP done has a separate instruction that writes EFLAGS. The getOperand(2) check for X86 is making sure that the EFLAGS come from the same CMP instruction. RISC-V has does the comparison has part of the branch so it's different.


For 
1.1 %29:fpr32 = Select_FPR32_Using_CC_GPR killed %7:gpr, %27:gpr, 4, %3:fpr32, killed %25:fpr3
2.1 %30:fpr32 = Select_FPR32_Using_CC_GPR killed %18:gpr, %24:gpr, 1, %16:fpr32, killed %29:fpr32

The original code is
(%18 != %24) ? %16 : ((%7 < %27) ? %3 : %25)

The transform this patch is trying to do needs to be

```
bb1:
  BNE %18, %24, bb4
bb2:
  BLTU %7, %27, bb4
bb3:
  // fallthrough
bb4
  phi %16, bb1, %3, bb2, %25 bb3
```

The condition of the second select needs to be checked first.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D127871/new/

https://reviews.llvm.org/D127871



More information about the llvm-commits mailing list