Skip to content

Commit

Permalink
[RISC-V][ISel] Remove redundant czero.eqz like 'czero.eqz a0, a0, a0' (
Browse files Browse the repository at this point in the history
…#90208)

In RISC-V ISel, the instruction `czero.eqz a0, a0, a0` is meaningless.
This patch does the following folds in ISel:
```
czero_eqz x, (setcc x, 0, ne) -> x
czero_nez x, (setcc x, 0, eq) -> x
```

---------

Signed-off-by: Zhijin Zeng <zhijin.zeng@spacemit.com>
  • Loading branch information
zengdage committed Apr 28, 2024
1 parent 2c1c887 commit 37eb9c9
Show file tree
Hide file tree
Showing 2 changed files with 125 additions and 7 deletions.
22 changes: 15 additions & 7 deletions llvm/lib/Target/RISCV/RISCVISelLowering.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16164,23 +16164,31 @@ SDValue RISCVTargetLowering::PerformDAGCombine(SDNode *N,
case ISD::SELECT:
return performSELECTCombine(N, DAG, Subtarget);
case RISCVISD::CZERO_EQZ:
case RISCVISD::CZERO_NEZ:
case RISCVISD::CZERO_NEZ: {
SDValue LHS = N->getOperand(0);
SDValue RHS = N->getOperand(1);
// czero_eq X, (xor Y, 1) -> czero_ne X, Y if Y is 0 or 1.
// czero_ne X, (xor Y, 1) -> czero_eq X, Y if Y is 0 or 1.
if (N->getOperand(1).getOpcode() == ISD::XOR &&
isOneConstant(N->getOperand(1).getOperand(1))) {
SDValue Cond = N->getOperand(1).getOperand(0);
if (RHS.getOpcode() == ISD::XOR && isOneConstant(RHS.getOperand(1))) {
SDValue Cond = RHS.getOperand(0);
APInt Mask = APInt::getBitsSetFrom(Cond.getValueSizeInBits(), 1);
if (DAG.MaskedValueIsZero(Cond, Mask)) {
unsigned NewOpc = N->getOpcode() == RISCVISD::CZERO_EQZ
? RISCVISD::CZERO_NEZ
: RISCVISD::CZERO_EQZ;
return DAG.getNode(NewOpc, SDLoc(N), N->getValueType(0),
N->getOperand(0), Cond);
return DAG.getNode(NewOpc, SDLoc(N), N->getValueType(0), LHS, Cond);
}
}
// czero_eqz x, (setcc x, 0, ne) -> x
// czero_nez x, (setcc x, 0, eq) -> x
if (RHS.getOpcode() == ISD::SETCC && isNullConstant(RHS.getOperand(1)) &&
cast<CondCodeSDNode>(RHS.getOperand(2))->get() ==
(N->getOpcode() == RISCVISD::CZERO_EQZ ? ISD::CondCode::SETNE
: ISD::CondCode::SETEQ) &&
LHS == RHS.getOperand(0))
return LHS;
return SDValue();

}
case RISCVISD::SELECT_CC: {
// Transform
SDValue LHS = N->getOperand(0);
Expand Down
110 changes: 110 additions & 0 deletions llvm/test/CodeGen/RISCV/select.ll
Original file line number Diff line number Diff line change
Expand Up @@ -1858,3 +1858,113 @@ define i32 @select_cst6(i1 zeroext %cond) {
%ret = select i1 %cond, i32 2049, i32 2047
ret i32 %ret
}

@select_redundant_czero_eqz_data = global i32 0, align 4

define void @select_redundant_czero_eqz1(ptr %0, ptr %1) {
; RV32IM-LABEL: select_redundant_czero_eqz1:
; RV32IM: # %bb.0: # %entry
; RV32IM-NEXT: bnez a0, .LBB49_2
; RV32IM-NEXT: # %bb.1:
; RV32IM-NEXT: lui a0, %hi(select_redundant_czero_eqz_data)
; RV32IM-NEXT: addi a0, a0, %lo(select_redundant_czero_eqz_data)
; RV32IM-NEXT: .LBB49_2: # %entry
; RV32IM-NEXT: sw a0, 0(a1)
; RV32IM-NEXT: ret
;
; RV64IM-LABEL: select_redundant_czero_eqz1:
; RV64IM: # %bb.0: # %entry
; RV64IM-NEXT: bnez a0, .LBB49_2
; RV64IM-NEXT: # %bb.1:
; RV64IM-NEXT: lui a0, %hi(select_redundant_czero_eqz_data)
; RV64IM-NEXT: addi a0, a0, %lo(select_redundant_czero_eqz_data)
; RV64IM-NEXT: .LBB49_2: # %entry
; RV64IM-NEXT: sd a0, 0(a1)
; RV64IM-NEXT: ret
;
; RV64IMXVTCONDOPS-LABEL: select_redundant_czero_eqz1:
; RV64IMXVTCONDOPS: # %bb.0: # %entry
; RV64IMXVTCONDOPS-NEXT: lui a2, %hi(select_redundant_czero_eqz_data)
; RV64IMXVTCONDOPS-NEXT: addi a2, a2, %lo(select_redundant_czero_eqz_data)
; RV64IMXVTCONDOPS-NEXT: vt.maskcn a2, a2, a0
; RV64IMXVTCONDOPS-NEXT: or a0, a2, a0
; RV64IMXVTCONDOPS-NEXT: sd a0, 0(a1)
; RV64IMXVTCONDOPS-NEXT: ret
;
; RV32IMZICOND-LABEL: select_redundant_czero_eqz1:
; RV32IMZICOND: # %bb.0: # %entry
; RV32IMZICOND-NEXT: lui a2, %hi(select_redundant_czero_eqz_data)
; RV32IMZICOND-NEXT: addi a2, a2, %lo(select_redundant_czero_eqz_data)
; RV32IMZICOND-NEXT: czero.nez a2, a2, a0
; RV32IMZICOND-NEXT: or a0, a2, a0
; RV32IMZICOND-NEXT: sw a0, 0(a1)
; RV32IMZICOND-NEXT: ret
;
; RV64IMZICOND-LABEL: select_redundant_czero_eqz1:
; RV64IMZICOND: # %bb.0: # %entry
; RV64IMZICOND-NEXT: lui a2, %hi(select_redundant_czero_eqz_data)
; RV64IMZICOND-NEXT: addi a2, a2, %lo(select_redundant_czero_eqz_data)
; RV64IMZICOND-NEXT: czero.nez a2, a2, a0
; RV64IMZICOND-NEXT: or a0, a2, a0
; RV64IMZICOND-NEXT: sd a0, 0(a1)
; RV64IMZICOND-NEXT: ret
entry:
%3 = icmp eq ptr %0, null
%4 = select i1 %3, ptr @select_redundant_czero_eqz_data, ptr %0
store ptr %4, ptr %1, align 8
ret void
}

define void @select_redundant_czero_eqz2(ptr %0, ptr %1) {
; RV32IM-LABEL: select_redundant_czero_eqz2:
; RV32IM: # %bb.0: # %entry
; RV32IM-NEXT: bnez a0, .LBB50_2
; RV32IM-NEXT: # %bb.1: # %entry
; RV32IM-NEXT: lui a0, %hi(select_redundant_czero_eqz_data)
; RV32IM-NEXT: addi a0, a0, %lo(select_redundant_czero_eqz_data)
; RV32IM-NEXT: .LBB50_2: # %entry
; RV32IM-NEXT: sw a0, 0(a1)
; RV32IM-NEXT: ret
;
; RV64IM-LABEL: select_redundant_czero_eqz2:
; RV64IM: # %bb.0: # %entry
; RV64IM-NEXT: bnez a0, .LBB50_2
; RV64IM-NEXT: # %bb.1: # %entry
; RV64IM-NEXT: lui a0, %hi(select_redundant_czero_eqz_data)
; RV64IM-NEXT: addi a0, a0, %lo(select_redundant_czero_eqz_data)
; RV64IM-NEXT: .LBB50_2: # %entry
; RV64IM-NEXT: sd a0, 0(a1)
; RV64IM-NEXT: ret
;
; RV64IMXVTCONDOPS-LABEL: select_redundant_czero_eqz2:
; RV64IMXVTCONDOPS: # %bb.0: # %entry
; RV64IMXVTCONDOPS-NEXT: lui a2, %hi(select_redundant_czero_eqz_data)
; RV64IMXVTCONDOPS-NEXT: addi a2, a2, %lo(select_redundant_czero_eqz_data)
; RV64IMXVTCONDOPS-NEXT: vt.maskcn a2, a2, a0
; RV64IMXVTCONDOPS-NEXT: or a0, a0, a2
; RV64IMXVTCONDOPS-NEXT: sd a0, 0(a1)
; RV64IMXVTCONDOPS-NEXT: ret
;
; RV32IMZICOND-LABEL: select_redundant_czero_eqz2:
; RV32IMZICOND: # %bb.0: # %entry
; RV32IMZICOND-NEXT: lui a2, %hi(select_redundant_czero_eqz_data)
; RV32IMZICOND-NEXT: addi a2, a2, %lo(select_redundant_czero_eqz_data)
; RV32IMZICOND-NEXT: czero.nez a2, a2, a0
; RV32IMZICOND-NEXT: or a0, a0, a2
; RV32IMZICOND-NEXT: sw a0, 0(a1)
; RV32IMZICOND-NEXT: ret
;
; RV64IMZICOND-LABEL: select_redundant_czero_eqz2:
; RV64IMZICOND: # %bb.0: # %entry
; RV64IMZICOND-NEXT: lui a2, %hi(select_redundant_czero_eqz_data)
; RV64IMZICOND-NEXT: addi a2, a2, %lo(select_redundant_czero_eqz_data)
; RV64IMZICOND-NEXT: czero.nez a2, a2, a0
; RV64IMZICOND-NEXT: or a0, a0, a2
; RV64IMZICOND-NEXT: sd a0, 0(a1)
; RV64IMZICOND-NEXT: ret
entry:
%3 = icmp ne ptr %0, null
%4 = select i1 %3, ptr %0, ptr @select_redundant_czero_eqz_data
store ptr %4, ptr %1, align 8
ret void
}

0 comments on commit 37eb9c9

Please sign in to comment.