Skip to content

Commit e042ff7

Browse files
committed
[SDAG][RISCV] Avoid expanding is-power-of-2 pattern on riscv32/64 with zbb
This patch adjusts the legality check for riscv to use `cpop/cpopw` since `isOperationLegal(ISD::CTPOP, MVT::i32)` returns false on rv64gc_zbb. Clang vs gcc: https://godbolt.org/z/rc3s4hjPh Reviewed By: craig.topper Differential Revision: https://reviews.llvm.org/D156390
1 parent 695138c commit e042ff7

File tree

8 files changed

+2022
-58
lines changed

8 files changed

+2022
-58
lines changed

llvm/include/llvm/CodeGen/TargetLowering.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -651,6 +651,11 @@ class TargetLoweringBase {
651651
return false;
652652
}
653653

654+
/// Return true if ctpop instruction is fast.
655+
virtual bool isCtpopFast(EVT VT) const {
656+
return isOperationLegal(ISD::CTPOP, VT);
657+
}
658+
654659
/// Return the maximum number of "x & (x - 1)" operations that can be done
655660
/// instead of deferring to a custom CTPOP.
656661
virtual unsigned getCustomCtpopCost(EVT VT, ISD::CondCode Cond) const {

llvm/lib/CodeGen/SelectionDAG/TargetLowering.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4168,8 +4168,8 @@ static SDValue simplifySetCCWithCTPOP(const TargetLowering &TLI, EVT VT,
41684168
// (ctpop x) u< 2 -> (x & x-1) == 0
41694169
// (ctpop x) u> 1 -> (x & x-1) != 0
41704170
if (Cond == ISD::SETULT || Cond == ISD::SETUGT) {
4171-
// Keep the CTPOP if it is a legal vector op.
4172-
if (CTVT.isVector() && TLI.isOperationLegal(ISD::CTPOP, CTVT))
4171+
// Keep the CTPOP if it is a cheap vector op.
4172+
if (CTVT.isVector() && TLI.isCtpopFast(CTVT))
41734173
return SDValue();
41744174

41754175
unsigned CostLimit = TLI.getCustomCtpopCost(CTVT, Cond);
@@ -4194,8 +4194,8 @@ static SDValue simplifySetCCWithCTPOP(const TargetLowering &TLI, EVT VT,
41944194
// (ctpop x) == 1 --> (x != 0) && ((x & x-1) == 0)
41954195
// (ctpop x) != 1 --> (x == 0) || ((x & x-1) != 0)
41964196
if ((Cond == ISD::SETEQ || Cond == ISD::SETNE) && C1 == 1) {
4197-
// Keep the CTPOP if it is legal.
4198-
if (TLI.isOperationLegal(ISD::CTPOP, CTVT))
4197+
// Keep the CTPOP if it is cheap.
4198+
if (TLI.isCtpopFast(CTVT))
41994199
return SDValue();
42004200

42014201
SDValue Zero = DAG.getConstant(0, dl, CTVT);

llvm/lib/Target/RISCV/RISCVISelLowering.cpp

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18585,6 +18585,20 @@ bool RISCVTargetLowering::areTwoSDNodeTargetMMOFlagsMergeable(
1858518585
return getTargetMMOFlags(NodeX) == getTargetMMOFlags(NodeY);
1858618586
}
1858718587

18588+
bool RISCVTargetLowering::isCtpopFast(EVT VT) const {
18589+
if (VT.isScalableVector())
18590+
return isTypeLegal(VT) && Subtarget.hasStdExtZvbb();
18591+
if (VT.isFixedLengthVector() && Subtarget.hasStdExtZvbb())
18592+
return true;
18593+
return Subtarget.hasStdExtZbb() &&
18594+
(VT == MVT::i32 || VT == MVT::i64 || VT.isFixedLengthVector());
18595+
}
18596+
18597+
unsigned RISCVTargetLowering::getCustomCtpopCost(EVT VT,
18598+
ISD::CondCode Cond) const {
18599+
return isCtpopFast(VT) ? 0 : 1;
18600+
}
18601+
1858818602
namespace llvm::RISCVVIntrinsicsTable {
1858918603

1859018604
#define GET_RISCVVIntrinsicsTable_IMPL

llvm/lib/Target/RISCV/RISCVISelLowering.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -607,6 +607,10 @@ class RISCVTargetLowering : public TargetLowering {
607607
}
608608
bool convertSelectOfConstantsToMath(EVT VT) const override { return true; }
609609

610+
bool isCtpopFast(EVT VT) const override;
611+
612+
unsigned getCustomCtpopCost(EVT VT, ISD::CondCode Cond) const override;
613+
610614
bool preferZeroCompareBranch() const override { return true; }
611615

612616
bool shouldInsertFencesForAtomic(const Instruction *I) const override {

0 commit comments

Comments
 (0)