Skip to content

Commit e302dd6

Browse files
committed
[AArch64] Eliminate Common SUBS by Reassociating Non-Constants
Commit 1eed469 added logic to reassociate a (add (add x y) -c) operand to a CSEL instruction with a comparison involving x and c (or a similar constant) in order to obtain a common (SUBS x c) instruction. This commit extends this logic to non-constants. In this way, we also reassociate a (sub (add x y) z) operand of a CSEL instruction to (add (sub x z) y) if the CSEL compares x and z, for example. Alive proof: https://alive2.llvm.org/ce/z/SEVpRm
1 parent 3e9df16 commit e302dd6

File tree

2 files changed

+92
-87
lines changed

2 files changed

+92
-87
lines changed

llvm/lib/Target/AArch64/AArch64ISelLowering.cpp

Lines changed: 42 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -24898,16 +24898,31 @@ static SDValue reassociateCSELOperandsForCSE(SDNode *N, SelectionDAG &DAG) {
2489824898
SDValue SubsNode = N->getOperand(3);
2489924899
if (SubsNode.getOpcode() != AArch64ISD::SUBS || !SubsNode.hasOneUse())
2490024900
return SDValue();
24901-
auto *CmpOpConst = dyn_cast<ConstantSDNode>(SubsNode.getOperand(1));
24902-
if (!CmpOpConst)
24903-
return SDValue();
2490424901

24902+
SDValue CmpOpToMatch = SubsNode.getOperand(1);
2490524903
SDValue CmpOpOther = SubsNode.getOperand(0);
2490624904
EVT VT = N->getValueType(0);
2490724905

24906+
unsigned ExpectedOpcode;
24907+
SDValue ExpectedOp;
24908+
SDValue SubsOp;
24909+
auto *CmpOpConst = dyn_cast<ConstantSDNode>(CmpOpToMatch);
24910+
if (CmpOpConst) {
24911+
ExpectedOpcode = ISD::ADD;
24912+
ExpectedOp =
24913+
DAG.getConstant(-CmpOpConst->getAPIntValue(), SDLoc(CmpOpConst),
24914+
CmpOpConst->getValueType(0));
24915+
SubsOp = DAG.getConstant(CmpOpConst->getAPIntValue(), SDLoc(CmpOpConst),
24916+
CmpOpConst->getValueType(0));
24917+
} else {
24918+
ExpectedOpcode = ISD::SUB;
24919+
ExpectedOp = CmpOpToMatch;
24920+
SubsOp = CmpOpToMatch;
24921+
}
24922+
2490824923
// Get the operand that can be reassociated with the SUBS instruction.
24909-
auto GetReassociationOp = [&](SDValue Op, APInt ExpectedConst) {
24910-
if (Op.getOpcode() != ISD::ADD)
24924+
auto GetReassociationOp = [&](SDValue Op, SDValue ExpectedOp) {
24925+
if (Op.getOpcode() != ExpectedOpcode)
2491124926
return SDValue();
2491224927
if (Op.getOperand(0).getOpcode() != ISD::ADD ||
2491324928
!Op.getOperand(0).hasOneUse())
@@ -24918,24 +24933,21 @@ static SDValue reassociateCSELOperandsForCSE(SDNode *N, SelectionDAG &DAG) {
2491824933
std::swap(X, Y);
2491924934
if (X != CmpOpOther)
2492024935
return SDValue();
24921-
auto *AddOpConst = dyn_cast<ConstantSDNode>(Op.getOperand(1));
24922-
if (!AddOpConst || AddOpConst->getAPIntValue() != ExpectedConst)
24936+
if (ExpectedOp != Op.getOperand(1))
2492324937
return SDValue();
2492424938
return Y;
2492524939
};
2492624940

2492724941
// Try the reassociation using the given constant and condition code.
24928-
auto Fold = [&](APInt NewCmpConst, AArch64CC::CondCode NewCC) {
24929-
APInt ExpectedConst = -NewCmpConst;
24930-
SDValue TReassocOp = GetReassociationOp(N->getOperand(0), ExpectedConst);
24931-
SDValue FReassocOp = GetReassociationOp(N->getOperand(1), ExpectedConst);
24942+
auto Fold = [&](AArch64CC::CondCode NewCC, SDValue ExpectedOp,
24943+
SDValue SubsOp) {
24944+
SDValue TReassocOp = GetReassociationOp(N->getOperand(0), ExpectedOp);
24945+
SDValue FReassocOp = GetReassociationOp(N->getOperand(1), ExpectedOp);
2493224946
if (!TReassocOp && !FReassocOp)
2493324947
return SDValue();
2493424948

2493524949
SDValue NewCmp = DAG.getNode(AArch64ISD::SUBS, SDLoc(SubsNode),
24936-
DAG.getVTList(VT, MVT_CC), CmpOpOther,
24937-
DAG.getConstant(NewCmpConst, SDLoc(CmpOpConst),
24938-
CmpOpConst->getValueType(0)));
24950+
DAG.getVTList(VT, MVT_CC), CmpOpOther, SubsOp);
2493924951

2494024952
auto Reassociate = [&](SDValue ReassocOp, unsigned OpNum) {
2494124953
if (!ReassocOp)
@@ -24957,9 +24969,19 @@ static SDValue reassociateCSELOperandsForCSE(SDNode *N, SelectionDAG &DAG) {
2495724969

2495824970
// First, try to eliminate the compare instruction by searching for a
2495924971
// subtraction with the same constant.
24960-
if (SDValue R = Fold(CmpOpConst->getAPIntValue(), CC))
24972+
if (SDValue R = Fold(CC, ExpectedOp, SubsOp))
2496124973
return R;
2496224974

24975+
if (!CmpOpConst) {
24976+
// Try again with the operands of the SUBS instruction and the condition
24977+
// swapped. Due to canonicalization, this only helps for non-constant
24978+
// operands of the SUBS instruction.
24979+
std::swap(CmpOpToMatch, CmpOpOther);
24980+
if (SDValue R = Fold(getSwappedCondition(CC), CmpOpToMatch, CmpOpToMatch))
24981+
return R;
24982+
return SDValue();
24983+
}
24984+
2496324985
if ((CC == AArch64CC::EQ || CC == AArch64CC::NE) && !CmpOpConst->isZero())
2496424986
return SDValue();
2496524987

@@ -24971,7 +24993,11 @@ static SDValue reassociateCSELOperandsForCSE(SDNode *N, SelectionDAG &DAG) {
2497124993
// them here but check for them nevertheless to be on the safe side.
2497224994
auto CheckedFold = [&](bool Check, APInt NewCmpConst,
2497324995
AArch64CC::CondCode NewCC) {
24974-
return Check ? Fold(NewCmpConst, NewCC) : SDValue();
24996+
auto ExpectedOp = DAG.getConstant(-NewCmpConst, SDLoc(CmpOpConst),
24997+
CmpOpConst->getValueType(0));
24998+
auto SubsOp = DAG.getConstant(NewCmpConst, SDLoc(CmpOpConst),
24999+
CmpOpConst->getValueType(0));
25000+
return Check ? Fold(NewCC, ExpectedOp, SubsOp) : SDValue();
2497525001
};
2497625002
switch (CC) {
2497725003
case AArch64CC::EQ:

llvm/test/CodeGen/AArch64/csel-cmp-cse.ll

Lines changed: 50 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -338,9 +338,8 @@ define i32 @test_eq0_multi_use_sub_i32(i32 %x0, i32 %x1) {
338338
define i32 @test_eq_nonconst_sub_add_i32(i32 %x0, i32 %x1, i32 %x2) {
339339
; CHECK-LABEL: test_eq_nonconst_sub_add_i32:
340340
; CHECK: // %bb.0:
341-
; CHECK-NEXT: add w8, w0, w1
342-
; CHECK-NEXT: cmp w1, w2
343-
; CHECK-NEXT: sub w8, w8, w2
341+
; CHECK-NEXT: subs w8, w1, w2
342+
; CHECK-NEXT: add w8, w8, w0
344343
; CHECK-NEXT: csel w0, wzr, w8, eq
345344
; CHECK-NEXT: ret
346345
%cmp = icmp eq i32 %x1, %x2
@@ -353,9 +352,8 @@ define i32 @test_eq_nonconst_sub_add_i32(i32 %x0, i32 %x1, i32 %x2) {
353352
define i32 @test_ne_nonconst_sub_add_i32(i32 %x0, i32 %x1, i32 %x2) {
354353
; CHECK-LABEL: test_ne_nonconst_sub_add_i32:
355354
; CHECK: // %bb.0:
356-
; CHECK-NEXT: add w8, w0, w1
357-
; CHECK-NEXT: cmp w1, w2
358-
; CHECK-NEXT: sub w8, w8, w2
355+
; CHECK-NEXT: subs w8, w1, w2
356+
; CHECK-NEXT: add w8, w8, w0
359357
; CHECK-NEXT: csel w0, wzr, w8, ne
360358
; CHECK-NEXT: ret
361359
%cmp = icmp ne i32 %x1, %x2
@@ -368,9 +366,8 @@ define i32 @test_ne_nonconst_sub_add_i32(i32 %x0, i32 %x1, i32 %x2) {
368366
define i32 @test_ult_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
369367
; CHECK-LABEL: test_ult_nonconst_i32:
370368
; CHECK: // %bb.0:
371-
; CHECK-NEXT: add w8, w0, w1
372-
; CHECK-NEXT: cmp w1, w2
373-
; CHECK-NEXT: sub w8, w8, w2
369+
; CHECK-NEXT: subs w8, w1, w2
370+
; CHECK-NEXT: add w8, w8, w0
374371
; CHECK-NEXT: csel w0, wzr, w8, lo
375372
; CHECK-NEXT: ret
376373
%cmp = icmp ult i32 %x1, %x2
@@ -383,9 +380,8 @@ define i32 @test_ult_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
383380
define i32 @test_ule_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
384381
; CHECK-LABEL: test_ule_nonconst_i32:
385382
; CHECK: // %bb.0:
386-
; CHECK-NEXT: add w8, w0, w1
387-
; CHECK-NEXT: cmp w1, w2
388-
; CHECK-NEXT: sub w8, w8, w2
383+
; CHECK-NEXT: subs w8, w1, w2
384+
; CHECK-NEXT: add w8, w8, w0
389385
; CHECK-NEXT: csel w0, wzr, w8, ls
390386
; CHECK-NEXT: ret
391387
%cmp = icmp ule i32 %x1, %x2
@@ -398,9 +394,8 @@ define i32 @test_ule_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
398394
define i32 @test_ugt_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
399395
; CHECK-LABEL: test_ugt_nonconst_i32:
400396
; CHECK: // %bb.0:
401-
; CHECK-NEXT: add w8, w0, w1
402-
; CHECK-NEXT: cmp w1, w2
403-
; CHECK-NEXT: sub w8, w8, w2
397+
; CHECK-NEXT: subs w8, w1, w2
398+
; CHECK-NEXT: add w8, w8, w0
404399
; CHECK-NEXT: csel w0, wzr, w8, hi
405400
; CHECK-NEXT: ret
406401
%cmp = icmp ugt i32 %x1, %x2
@@ -413,9 +408,8 @@ define i32 @test_ugt_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
413408
define i32 @test_uge_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
414409
; CHECK-LABEL: test_uge_nonconst_i32:
415410
; CHECK: // %bb.0:
416-
; CHECK-NEXT: add w8, w0, w1
417-
; CHECK-NEXT: cmp w1, w2
418-
; CHECK-NEXT: sub w8, w8, w2
411+
; CHECK-NEXT: subs w8, w1, w2
412+
; CHECK-NEXT: add w8, w8, w0
419413
; CHECK-NEXT: csel w0, wzr, w8, hs
420414
; CHECK-NEXT: ret
421415
%cmp = icmp uge i32 %x1, %x2
@@ -428,9 +422,8 @@ define i32 @test_uge_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
428422
define i32 @test_slt_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
429423
; CHECK-LABEL: test_slt_nonconst_i32:
430424
; CHECK: // %bb.0:
431-
; CHECK-NEXT: add w8, w0, w1
432-
; CHECK-NEXT: cmp w1, w2
433-
; CHECK-NEXT: sub w8, w8, w2
425+
; CHECK-NEXT: subs w8, w1, w2
426+
; CHECK-NEXT: add w8, w8, w0
434427
; CHECK-NEXT: csel w0, wzr, w8, lt
435428
; CHECK-NEXT: ret
436429
%cmp = icmp slt i32 %x1, %x2
@@ -443,9 +436,8 @@ define i32 @test_slt_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
443436
define i32 @test_sle_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
444437
; CHECK-LABEL: test_sle_nonconst_i32:
445438
; CHECK: // %bb.0:
446-
; CHECK-NEXT: add w8, w0, w1
447-
; CHECK-NEXT: cmp w1, w2
448-
; CHECK-NEXT: sub w8, w8, w2
439+
; CHECK-NEXT: subs w8, w1, w2
440+
; CHECK-NEXT: add w8, w8, w0
449441
; CHECK-NEXT: csel w0, wzr, w8, le
450442
; CHECK-NEXT: ret
451443
%cmp = icmp sle i32 %x1, %x2
@@ -458,9 +450,8 @@ define i32 @test_sle_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
458450
define i32 @test_sgt_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
459451
; CHECK-LABEL: test_sgt_nonconst_i32:
460452
; CHECK: // %bb.0:
461-
; CHECK-NEXT: add w8, w0, w1
462-
; CHECK-NEXT: cmp w1, w2
463-
; CHECK-NEXT: sub w8, w8, w2
453+
; CHECK-NEXT: subs w8, w1, w2
454+
; CHECK-NEXT: add w8, w8, w0
464455
; CHECK-NEXT: csel w0, wzr, w8, gt
465456
; CHECK-NEXT: ret
466457
%cmp = icmp sgt i32 %x1, %x2
@@ -473,9 +464,8 @@ define i32 @test_sgt_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
473464
define i32 @test_sge_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
474465
; CHECK-LABEL: test_sge_nonconst_i32:
475466
; CHECK: // %bb.0:
476-
; CHECK-NEXT: add w8, w0, w1
477-
; CHECK-NEXT: cmp w1, w2
478-
; CHECK-NEXT: sub w8, w8, w2
467+
; CHECK-NEXT: subs w8, w1, w2
468+
; CHECK-NEXT: add w8, w8, w0
479469
; CHECK-NEXT: csel w0, wzr, w8, ge
480470
; CHECK-NEXT: ret
481471
%cmp = icmp sge i32 %x1, %x2
@@ -488,9 +478,8 @@ define i32 @test_sge_nonconst_i32(i32 %x0, i32 %x1, i32 %x2) {
488478
define i64 @test_ult_nonconst_i64(i64 %x0, i64 %x1, i64 %x2) {
489479
; CHECK-LABEL: test_ult_nonconst_i64:
490480
; CHECK: // %bb.0:
491-
; CHECK-NEXT: add x8, x0, x1
492-
; CHECK-NEXT: cmp x1, x2
493-
; CHECK-NEXT: sub x8, x8, x2
481+
; CHECK-NEXT: subs x8, x1, x2
482+
; CHECK-NEXT: add x8, x8, x0
494483
; CHECK-NEXT: csel x0, xzr, x8, lo
495484
; CHECK-NEXT: ret
496485
%cmp = icmp ult i64 %x1, %x2
@@ -503,9 +492,8 @@ define i64 @test_ult_nonconst_i64(i64 %x0, i64 %x1, i64 %x2) {
503492
define i32 @test_eq_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
504493
; CHECK-LABEL: test_eq_nonconst_sub_add_comm_i32:
505494
; CHECK: // %bb.0:
506-
; CHECK-NEXT: add w8, w0, w1
507-
; CHECK-NEXT: cmp w2, w1
508-
; CHECK-NEXT: sub w8, w8, w2
495+
; CHECK-NEXT: subs w8, w1, w2
496+
; CHECK-NEXT: add w8, w8, w0
509497
; CHECK-NEXT: csel w0, wzr, w8, eq
510498
; CHECK-NEXT: ret
511499
%cmp = icmp eq i32 %x2, %x1
@@ -518,9 +506,8 @@ define i32 @test_eq_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
518506
define i32 @test_ne_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
519507
; CHECK-LABEL: test_ne_nonconst_sub_add_comm_i32:
520508
; CHECK: // %bb.0:
521-
; CHECK-NEXT: add w8, w0, w1
522-
; CHECK-NEXT: cmp w2, w1
523-
; CHECK-NEXT: sub w8, w8, w2
509+
; CHECK-NEXT: subs w8, w1, w2
510+
; CHECK-NEXT: add w8, w8, w0
524511
; CHECK-NEXT: csel w0, wzr, w8, ne
525512
; CHECK-NEXT: ret
526513
%cmp = icmp ne i32 %x2, %x1
@@ -533,10 +520,9 @@ define i32 @test_ne_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
533520
define i32 @test_ult_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
534521
; CHECK-LABEL: test_ult_nonconst_sub_add_comm_i32:
535522
; CHECK: // %bb.0:
536-
; CHECK-NEXT: add w8, w0, w1
537-
; CHECK-NEXT: cmp w2, w1
538-
; CHECK-NEXT: sub w8, w8, w2
539-
; CHECK-NEXT: csel w0, wzr, w8, lo
523+
; CHECK-NEXT: subs w8, w1, w2
524+
; CHECK-NEXT: add w8, w8, w0
525+
; CHECK-NEXT: csel w0, wzr, w8, hi
540526
; CHECK-NEXT: ret
541527
%cmp = icmp ult i32 %x2, %x1
542528
%add = add nuw i32 %x0, %x1
@@ -548,10 +534,9 @@ define i32 @test_ult_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
548534
define i32 @test_ule_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
549535
; CHECK-LABEL: test_ule_nonconst_sub_add_comm_i32:
550536
; CHECK: // %bb.0:
551-
; CHECK-NEXT: add w8, w0, w1
552-
; CHECK-NEXT: cmp w2, w1
553-
; CHECK-NEXT: sub w8, w8, w2
554-
; CHECK-NEXT: csel w0, wzr, w8, ls
537+
; CHECK-NEXT: subs w8, w1, w2
538+
; CHECK-NEXT: add w8, w8, w0
539+
; CHECK-NEXT: csel w0, wzr, w8, hs
555540
; CHECK-NEXT: ret
556541
%cmp = icmp ule i32 %x2, %x1
557542
%add = add nuw i32 %x0, %x1
@@ -563,10 +548,9 @@ define i32 @test_ule_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
563548
define i32 @test_ugt_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
564549
; CHECK-LABEL: test_ugt_nonconst_sub_add_comm_i32:
565550
; CHECK: // %bb.0:
566-
; CHECK-NEXT: add w8, w0, w1
567-
; CHECK-NEXT: cmp w2, w1
568-
; CHECK-NEXT: sub w8, w8, w2
569-
; CHECK-NEXT: csel w0, wzr, w8, hi
551+
; CHECK-NEXT: subs w8, w1, w2
552+
; CHECK-NEXT: add w8, w8, w0
553+
; CHECK-NEXT: csel w0, wzr, w8, lo
570554
; CHECK-NEXT: ret
571555
%cmp = icmp ugt i32 %x2, %x1
572556
%add = add nuw i32 %x0, %x1
@@ -578,10 +562,9 @@ define i32 @test_ugt_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
578562
define i32 @test_uge_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
579563
; CHECK-LABEL: test_uge_nonconst_sub_add_comm_i32:
580564
; CHECK: // %bb.0:
581-
; CHECK-NEXT: add w8, w0, w1
582-
; CHECK-NEXT: cmp w2, w1
583-
; CHECK-NEXT: sub w8, w8, w2
584-
; CHECK-NEXT: csel w0, wzr, w8, hs
565+
; CHECK-NEXT: subs w8, w1, w2
566+
; CHECK-NEXT: add w8, w8, w0
567+
; CHECK-NEXT: csel w0, wzr, w8, ls
585568
; CHECK-NEXT: ret
586569
%cmp = icmp uge i32 %x2, %x1
587570
%add = add nuw i32 %x0, %x1
@@ -593,10 +576,9 @@ define i32 @test_uge_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
593576
define i32 @test_slt_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
594577
; CHECK-LABEL: test_slt_nonconst_sub_add_comm_i32:
595578
; CHECK: // %bb.0:
596-
; CHECK-NEXT: add w8, w0, w1
597-
; CHECK-NEXT: cmp w2, w1
598-
; CHECK-NEXT: sub w8, w8, w2
599-
; CHECK-NEXT: csel w0, wzr, w8, lt
579+
; CHECK-NEXT: subs w8, w1, w2
580+
; CHECK-NEXT: add w8, w8, w0
581+
; CHECK-NEXT: csel w0, wzr, w8, gt
600582
; CHECK-NEXT: ret
601583
%cmp = icmp slt i32 %x2, %x1
602584
%add = add nuw i32 %x0, %x1
@@ -608,10 +590,9 @@ define i32 @test_slt_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
608590
define i32 @test_sle_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
609591
; CHECK-LABEL: test_sle_nonconst_sub_add_comm_i32:
610592
; CHECK: // %bb.0:
611-
; CHECK-NEXT: add w8, w0, w1
612-
; CHECK-NEXT: cmp w2, w1
613-
; CHECK-NEXT: sub w8, w8, w2
614-
; CHECK-NEXT: csel w0, wzr, w8, le
593+
; CHECK-NEXT: subs w8, w1, w2
594+
; CHECK-NEXT: add w8, w8, w0
595+
; CHECK-NEXT: csel w0, wzr, w8, ge
615596
; CHECK-NEXT: ret
616597
%cmp = icmp sle i32 %x2, %x1
617598
%add = add nuw i32 %x0, %x1
@@ -623,10 +604,9 @@ define i32 @test_sle_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
623604
define i32 @test_sgt_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
624605
; CHECK-LABEL: test_sgt_nonconst_sub_add_comm_i32:
625606
; CHECK: // %bb.0:
626-
; CHECK-NEXT: add w8, w0, w1
627-
; CHECK-NEXT: cmp w2, w1
628-
; CHECK-NEXT: sub w8, w8, w2
629-
; CHECK-NEXT: csel w0, wzr, w8, gt
607+
; CHECK-NEXT: subs w8, w1, w2
608+
; CHECK-NEXT: add w8, w8, w0
609+
; CHECK-NEXT: csel w0, wzr, w8, lt
630610
; CHECK-NEXT: ret
631611
%cmp = icmp sgt i32 %x2, %x1
632612
%add = add nuw i32 %x0, %x1
@@ -638,10 +618,9 @@ define i32 @test_sgt_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
638618
define i32 @test_sge_nonconst_sub_add_comm_i32(i32 %x0, i32 %x1, i32 %x2) {
639619
; CHECK-LABEL: test_sge_nonconst_sub_add_comm_i32:
640620
; CHECK: // %bb.0:
641-
; CHECK-NEXT: add w8, w0, w1
642-
; CHECK-NEXT: cmp w2, w1
643-
; CHECK-NEXT: sub w8, w8, w2
644-
; CHECK-NEXT: csel w0, wzr, w8, ge
621+
; CHECK-NEXT: subs w8, w1, w2
622+
; CHECK-NEXT: add w8, w8, w0
623+
; CHECK-NEXT: csel w0, wzr, w8, le
645624
; CHECK-NEXT: ret
646625
%cmp = icmp sge i32 %x2, %x1
647626
%add = add nuw i32 %x0, %x1

0 commit comments

Comments
 (0)