Skip to content
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20822,6 +20822,9 @@ static bool isNegatedInteger(SDValue Op) {
}

static SDValue getNegatedInteger(SDValue Op, SelectionDAG &DAG) {
if (isNegatedInteger(Op))
return Op.getOperand(1);

SDLoc DL(Op);
EVT VT = Op.getValueType();
SDValue Zero = DAG.getConstant(0, DL, VT);
Expand Down Expand Up @@ -25464,6 +25467,24 @@ static SDValue performCSELCombine(SDNode *N,
}
}

// CSEL a, b, cc, SUBS(SUB(x,y), 0) -> CSEL a, b, cc, SUBS(x,y) if cc doesn't
// use overflow flags to avoid the comparison with zero.
if (Cond.getOpcode() == AArch64ISD::SUBS &&
isNullConstant(Cond.getOperand(1))) {
SDValue Sub = Cond.getOperand(0);
AArch64CC::CondCode CC =
static_cast<AArch64CC::CondCode>(N->getConstantOperandVal(2));
if (Sub.getOpcode() == ISD::SUB &&
(CC == AArch64CC::EQ || CC == AArch64CC::NE || CC == AArch64CC::MI ||
CC == AArch64CC::PL)) {
SDLoc DL(N);
SDValue Subs = DAG.getNode(AArch64ISD::SUBS, DL, Cond->getVTList(),
Sub.getOperand(0), Sub.getOperand(1));
return DAG.getNode(AArch64ISD::CSEL, DL, N->getVTList(), N->getOperand(0),
N->getOperand(1), N->getOperand(2), Subs.getValue(1));
}
}

// CSEL (LASTB P, Z), X, NE(ANY P) -> CLASTB P, X, Z
if (SDValue CondLast = foldCSELofLASTB(N, DAG))
return CondLast;
Expand Down
54 changes: 27 additions & 27 deletions llvm/test/CodeGen/AArch64/abds-neg.ll
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,9 @@
define i8 @abd_ext_i8(i8 %a, i8 %b) nounwind {
; CHECK-LABEL: abd_ext_i8:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxtb
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxtb w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, pl
; CHECK-NEXT: ret
%aext = sext i8 %a to i64
Expand All @@ -25,9 +25,9 @@ define i8 @abd_ext_i8(i8 %a, i8 %b) nounwind {
define i8 @abd_ext_i8_i16(i8 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_ext_i8_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, pl
; CHECK-NEXT: ret
%aext = sext i8 %a to i64
Expand All @@ -42,9 +42,9 @@ define i8 @abd_ext_i8_i16(i8 %a, i16 %b) nounwind {
define i8 @abd_ext_i8_undef(i8 %a, i8 %b) nounwind {
; CHECK-LABEL: abd_ext_i8_undef:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxtb
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxtb w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, pl
; CHECK-NEXT: ret
%aext = sext i8 %a to i64
Expand All @@ -59,9 +59,9 @@ define i8 @abd_ext_i8_undef(i8 %a, i8 %b) nounwind {
define i16 @abd_ext_i16(i16 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_ext_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, pl
; CHECK-NEXT: ret
%aext = sext i16 %a to i64
Expand All @@ -77,8 +77,8 @@ define i16 @abd_ext_i16_i32(i16 %a, i32 %b) nounwind {
; CHECK-LABEL: abd_ext_i16_i32:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: subs w8, w1, w8
; CHECK-NEXT: cneg w0, w8, ge
; CHECK-NEXT: subs w8, w8, w1
; CHECK-NEXT: cneg w0, w8, gt
; CHECK-NEXT: ret
%aext = sext i16 %a to i64
%bext = sext i32 %b to i64
Expand All @@ -92,9 +92,9 @@ define i16 @abd_ext_i16_i32(i16 %a, i32 %b) nounwind {
define i16 @abd_ext_i16_undef(i16 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_ext_i16_undef:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, pl
; CHECK-NEXT: ret
%aext = sext i16 %a to i64
Expand All @@ -109,8 +109,8 @@ define i16 @abd_ext_i16_undef(i16 %a, i16 %b) nounwind {
define i32 @abd_ext_i32(i32 %a, i32 %b) nounwind {
; CHECK-LABEL: abd_ext_i32:
; CHECK: // %bb.0:
; CHECK-NEXT: subs w8, w1, w0
; CHECK-NEXT: cneg w0, w8, ge
; CHECK-NEXT: subs w8, w0, w1
; CHECK-NEXT: cneg w0, w8, gt
; CHECK-NEXT: ret
%aext = sext i32 %a to i64
%bext = sext i32 %b to i64
Expand All @@ -125,8 +125,8 @@ define i32 @abd_ext_i32_i16(i32 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_ext_i32_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: subs w8, w8, w0
; CHECK-NEXT: cneg w0, w8, ge
; CHECK-NEXT: subs w8, w0, w8
; CHECK-NEXT: cneg w0, w8, gt
; CHECK-NEXT: ret
%aext = sext i32 %a to i64
%bext = sext i16 %b to i64
Expand All @@ -140,8 +140,8 @@ define i32 @abd_ext_i32_i16(i32 %a, i16 %b) nounwind {
define i32 @abd_ext_i32_undef(i32 %a, i32 %b) nounwind {
; CHECK-LABEL: abd_ext_i32_undef:
; CHECK: // %bb.0:
; CHECK-NEXT: subs w8, w1, w0
; CHECK-NEXT: cneg w0, w8, ge
; CHECK-NEXT: subs w8, w0, w1
; CHECK-NEXT: cneg w0, w8, gt
; CHECK-NEXT: ret
%aext = sext i32 %a to i64
%bext = sext i32 %b to i64
Expand All @@ -155,8 +155,8 @@ define i32 @abd_ext_i32_undef(i32 %a, i32 %b) nounwind {
define i64 @abd_ext_i64(i64 %a, i64 %b) nounwind {
; CHECK-LABEL: abd_ext_i64:
; CHECK: // %bb.0:
; CHECK-NEXT: subs x8, x1, x0
; CHECK-NEXT: cneg x0, x8, ge
; CHECK-NEXT: subs x8, x0, x1
; CHECK-NEXT: cneg x0, x8, gt
; CHECK-NEXT: ret
%aext = sext i64 %a to i128
%bext = sext i64 %b to i128
Expand All @@ -170,8 +170,8 @@ define i64 @abd_ext_i64(i64 %a, i64 %b) nounwind {
define i64 @abd_ext_i64_undef(i64 %a, i64 %b) nounwind {
; CHECK-LABEL: abd_ext_i64_undef:
; CHECK: // %bb.0:
; CHECK-NEXT: subs x8, x1, x0
; CHECK-NEXT: cneg x0, x8, ge
; CHECK-NEXT: subs x8, x0, x1
; CHECK-NEXT: cneg x0, x8, gt
; CHECK-NEXT: ret
%aext = sext i64 %a to i128
%bext = sext i64 %b to i128
Expand Down
74 changes: 37 additions & 37 deletions llvm/test/CodeGen/AArch64/abds.ll
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,9 @@
define i8 @abd_ext_i8(i8 %a, i8 %b) nounwind {
; CHECK-LABEL: abd_ext_i8:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxtb
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxtb w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%aext = sext i8 %a to i64
Expand All @@ -24,9 +24,9 @@ define i8 @abd_ext_i8(i8 %a, i8 %b) nounwind {
define i8 @abd_ext_i8_i16(i8 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_ext_i8_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%aext = sext i8 %a to i64
Expand All @@ -40,9 +40,9 @@ define i8 @abd_ext_i8_i16(i8 %a, i16 %b) nounwind {
define i8 @abd_ext_i8_undef(i8 %a, i8 %b) nounwind {
; CHECK-LABEL: abd_ext_i8_undef:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxtb
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxtb w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%aext = sext i8 %a to i64
Expand All @@ -56,9 +56,9 @@ define i8 @abd_ext_i8_undef(i8 %a, i8 %b) nounwind {
define i16 @abd_ext_i16(i16 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_ext_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%aext = sext i16 %a to i64
Expand Down Expand Up @@ -87,9 +87,9 @@ define i16 @abd_ext_i16_i32(i16 %a, i32 %b) nounwind {
define i16 @abd_ext_i16_undef(i16 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_ext_i16_undef:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%aext = sext i16 %a to i64
Expand Down Expand Up @@ -214,9 +214,9 @@ define i128 @abd_ext_i128_undef(i128 %a, i128 %b) nounwind {
define i8 @abd_minmax_i8(i8 %a, i8 %b) nounwind {
; CHECK-LABEL: abd_minmax_i8:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxtb
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxtb w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%min = call i8 @llvm.smin.i8(i8 %a, i8 %b)
Expand All @@ -228,9 +228,9 @@ define i8 @abd_minmax_i8(i8 %a, i8 %b) nounwind {
define i16 @abd_minmax_i16(i16 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_minmax_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%min = call i16 @llvm.smin.i16(i16 %a, i16 %b)
Expand Down Expand Up @@ -286,9 +286,9 @@ define i128 @abd_minmax_i128(i128 %a, i128 %b) nounwind {
define i8 @abd_cmp_i8(i8 %a, i8 %b) nounwind {
; CHECK-LABEL: abd_cmp_i8:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxtb
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxtb w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%cmp = icmp sgt i8 %a, %b
Expand All @@ -301,9 +301,9 @@ define i8 @abd_cmp_i8(i8 %a, i8 %b) nounwind {
define i16 @abd_cmp_i16(i16 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_cmp_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%cmp = icmp sge i16 %a, %b
Expand Down Expand Up @@ -507,11 +507,11 @@ define i64 @vector_legalized(i16 %a, i16 %b) {
; CHECK-LABEL: vector_legalized:
; CHECK: // %bb.0:
; CHECK-NEXT: movi v0.2d, #0000000000000000
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: addp d0, v0.2d
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w8, w8, mi
; CHECK-NEXT: addp d0, v0.2d
; CHECK-NEXT: fmov x9, d0
; CHECK-NEXT: add x0, x9, x8
; CHECK-NEXT: ret
Expand All @@ -532,9 +532,9 @@ define i64 @vector_legalized(i16 %a, i16 %b) {
define i8 @abd_select_i8(i8 %a, i8 %b) nounwind {
; CHECK-LABEL: abd_select_i8:
; CHECK: // %bb.0:
; CHECK-NEXT: sxtb w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxtb
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxtb w8, w1
; CHECK-NEXT: sxtb w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%cmp = icmp slt i8 %a, %b
Expand All @@ -547,9 +547,9 @@ define i8 @abd_select_i8(i8 %a, i8 %b) nounwind {
define i16 @abd_select_i16(i16 %a, i16 %b) nounwind {
; CHECK-LABEL: abd_select_i16:
; CHECK: // %bb.0:
; CHECK-NEXT: sxth w8, w0
; CHECK-NEXT: sub w8, w8, w1, sxth
; CHECK-NEXT: cmp w8, #0
; CHECK-NEXT: sxth w8, w1
; CHECK-NEXT: sxth w9, w0
; CHECK-NEXT: subs w8, w9, w8
; CHECK-NEXT: cneg w0, w8, mi
; CHECK-NEXT: ret
%cmp = icmp sle i16 %a, %b
Expand Down
Loading