forked from OSchip/llvm-project
[RISCV] Add another isel optimization for (and (shl x, c2), c1)
Turn (and (shl x, c2), c1) -> (slli (srli x, c3-c2), c3) if c1 is a shifted mask with no leading zeros and c3 trailing zeros where c3 is greater than c2.
This commit is contained in:
parent
8811227a0c
commit
70f50114f3
|
@ -674,6 +674,23 @@ void RISCVDAGToDAGISel::Select(SDNode *Node) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Turn (and (shl x, c2), c1) -> (slli (srli x, c3-c2), c3) if c1 is a
|
||||||
|
// shifted mask with no leading zeros and c3 trailing zeros.
|
||||||
|
if (LeftShift && isShiftedMask_64(C1)) {
|
||||||
|
uint64_t Leading = XLen - (64 - countLeadingZeros(C1));
|
||||||
|
uint64_t C3 = countTrailingZeros(C1);
|
||||||
|
if (Leading == 0 && C2 < C3 && OneUseOrZExtW && !ZExtOrANDI) {
|
||||||
|
SDNode *SRLI = CurDAG->getMachineNode(
|
||||||
|
RISCV::SRLI, DL, XLenVT, X,
|
||||||
|
CurDAG->getTargetConstant(C3 - C2, DL, XLenVT));
|
||||||
|
SDNode *SLLI =
|
||||||
|
CurDAG->getMachineNode(RISCV::SLLI, DL, XLenVT, SDValue(SRLI, 0),
|
||||||
|
CurDAG->getTargetConstant(C3, DL, XLenVT));
|
||||||
|
ReplaceNode(Node, SLLI);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ISD::INTRINSIC_WO_CHAIN: {
|
case ISD::INTRINSIC_WO_CHAIN: {
|
||||||
|
|
|
@ -86,9 +86,8 @@ define i64 @test4(i64 %x) {
|
||||||
define i32 @test5(i32 %x) {
|
define i32 @test5(i32 %x) {
|
||||||
; RV32I-LABEL: test5:
|
; RV32I-LABEL: test5:
|
||||||
; RV32I: # %bb.0:
|
; RV32I: # %bb.0:
|
||||||
; RV32I-NEXT: slli a0, a0, 6
|
; RV32I-NEXT: srli a0, a0, 10
|
||||||
; RV32I-NEXT: lui a1, 1048560
|
; RV32I-NEXT: slli a0, a0, 16
|
||||||
; RV32I-NEXT: and a0, a0, a1
|
|
||||||
; RV32I-NEXT: ret
|
; RV32I-NEXT: ret
|
||||||
;
|
;
|
||||||
; RV64I-LABEL: test5:
|
; RV64I-LABEL: test5:
|
||||||
|
@ -108,16 +107,14 @@ define i64 @test6(i64 %x) {
|
||||||
; RV32I-NEXT: srli a2, a0, 26
|
; RV32I-NEXT: srli a2, a0, 26
|
||||||
; RV32I-NEXT: slli a1, a1, 6
|
; RV32I-NEXT: slli a1, a1, 6
|
||||||
; RV32I-NEXT: or a1, a1, a2
|
; RV32I-NEXT: or a1, a1, a2
|
||||||
; RV32I-NEXT: slli a0, a0, 6
|
; RV32I-NEXT: srli a0, a0, 10
|
||||||
; RV32I-NEXT: lui a2, 1048560
|
; RV32I-NEXT: slli a0, a0, 16
|
||||||
; RV32I-NEXT: and a0, a0, a2
|
|
||||||
; RV32I-NEXT: ret
|
; RV32I-NEXT: ret
|
||||||
;
|
;
|
||||||
; RV64I-LABEL: test6:
|
; RV64I-LABEL: test6:
|
||||||
; RV64I: # %bb.0:
|
; RV64I: # %bb.0:
|
||||||
; RV64I-NEXT: slli a0, a0, 6
|
; RV64I-NEXT: srli a0, a0, 10
|
||||||
; RV64I-NEXT: lui a1, 1048560
|
; RV64I-NEXT: slli a0, a0, 16
|
||||||
; RV64I-NEXT: and a0, a0, a1
|
|
||||||
; RV64I-NEXT: ret
|
; RV64I-NEXT: ret
|
||||||
%a = shl i64 %x, 6
|
%a = shl i64 %x, 6
|
||||||
%b = and i64 %a, -65536
|
%b = and i64 %a, -65536
|
||||||
|
|
Loading…
Reference in New Issue