[llvm] f37d7c9 - [AVR] Optimize 16-bit comparison with a constant

Ben Shi via llvm-commits llvm-commits at lists.llvm.org
Wed Feb 8 23:13:24 PST 2023


Author: Ben Shi
Date: 2023-02-09T15:13:01+08:00
New Revision: f37d7c9381ffc720a00ab61945f96e083eb58f55

URL: https://github.com/llvm/llvm-project/commit/f37d7c9381ffc720a00ab61945f96e083eb58f55
DIFF: https://github.com/llvm/llvm-project/commit/f37d7c9381ffc720a00ab61945f96e083eb58f55.diff

LOG: [AVR] Optimize 16-bit comparison with a constant

Fixes https://github.com/llvm/llvm-project/issues/30923

Reviewed By: jacquesguan, aykevl

Differential Revision: https://reviews.llvm.org/D142281

Added: 
    

Modified: 
    llvm/lib/Target/AVR/AVRISelLowering.cpp
    llvm/test/CodeGen/AVR/cmp.ll

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Target/AVR/AVRISelLowering.cpp b/llvm/lib/Target/AVR/AVRISelLowering.cpp
index ee2c48917971..6c60d87c4704 100644
--- a/llvm/lib/Target/AVR/AVRISelLowering.cpp
+++ b/llvm/lib/Target/AVR/AVRISelLowering.cpp
@@ -634,11 +634,35 @@ SDValue AVRTargetLowering::getAVRCmp(SDValue LHS, SDValue RHS,
   SDValue Cmp;
 
   if (LHS.getSimpleValueType() == MVT::i16 && isa<ConstantSDNode>(RHS)) {
-    // Generate a CPI/CPC pair if RHS is a 16-bit constant.
+    uint64_t Imm = cast<ConstantSDNode>(RHS)->getZExtValue();
+    // Generate a CPI/CPC pair if RHS is a 16-bit constant. Use the zero
+    // register for the constant RHS if its lower or higher byte is zero.
     SDValue LHSlo = DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, LHS,
                                 DAG.getIntPtrConstant(0, DL));
     SDValue LHShi = DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, LHS,
                                 DAG.getIntPtrConstant(1, DL));
+    SDValue RHSlo = (Imm & 0xff) == 0
+                        ? DAG.getRegister(Subtarget.getZeroRegister(), MVT::i8)
+                        : DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, RHS,
+                                      DAG.getIntPtrConstant(0, DL));
+    SDValue RHShi = (Imm & 0xff00) == 0
+                        ? DAG.getRegister(Subtarget.getZeroRegister(), MVT::i8)
+                        : DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, RHS,
+                                      DAG.getIntPtrConstant(1, DL));
+    Cmp = DAG.getNode(AVRISD::CMP, DL, MVT::Glue, LHSlo, RHSlo);
+    Cmp = DAG.getNode(AVRISD::CMPC, DL, MVT::Glue, LHShi, RHShi, Cmp);
+  } else if (RHS.getSimpleValueType() == MVT::i16 && isa<ConstantSDNode>(LHS)) {
+    // Generate a CPI/CPC pair if LHS is a 16-bit constant. Use the zero
+    // register for the constant LHS if its lower or higher byte is zero.
+    uint64_t Imm = cast<ConstantSDNode>(LHS)->getZExtValue();
+    SDValue LHSlo = (Imm & 0xff) == 0
+                        ? DAG.getRegister(Subtarget.getZeroRegister(), MVT::i8)
+                        : DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, LHS,
+                                      DAG.getIntPtrConstant(0, DL));
+    SDValue LHShi = (Imm & 0xff00) == 0
+                        ? DAG.getRegister(Subtarget.getZeroRegister(), MVT::i8)
+                        : DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, LHS,
+                                      DAG.getIntPtrConstant(1, DL));
     SDValue RHSlo = DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, RHS,
                                 DAG.getIntPtrConstant(0, DL));
     SDValue RHShi = DAG.getNode(ISD::EXTRACT_ELEMENT, DL, MVT::i8, RHS,

diff  --git a/llvm/test/CodeGen/AVR/cmp.ll b/llvm/test/CodeGen/AVR/cmp.ll
index e9769068f911..715a3f1c9c18 100644
--- a/llvm/test/CodeGen/AVR/cmp.ll
+++ b/llvm/test/CodeGen/AVR/cmp.ll
@@ -1,4 +1,5 @@
 ; RUN: llc < %s -march=avr | FileCheck %s
+; RUN: llc < %s -mtriple=avr -mcpu=attiny10 | FileCheck --check-prefix=TINY %s
 
 declare void @f1(i8)
 declare void @f2(i8)
@@ -202,3 +203,98 @@ if.else:
 if.end:
   ret void
 }
+
+define i16 @cmp_i16_gt_0(i16 %0) {
+; CHECK-LABEL: cmp_i16_gt_0:
+; CHECK:       ; %bb.0:
+; CHECK-NEXT:    ldi r18, 1
+; CHECK-NEXT:    cp r1, r24
+; CHECK-NEXT:    cpc r1, r25
+; CHECK-NEXT:    brlt .LBB11_2
+; CHECK-NEXT:  ; %bb.1:
+; CHECK-NEXT:    mov r18, r1
+; CHECK-NEXT:  .LBB11_2:
+; CHECK-NEXT:    mov r24, r18
+; CHECK-NEXT:    clr r25
+; CHECK-NEXT:    ret
+;
+; TINY-LABEL: cmp_i16_gt_0:
+; TINY:       ; %bb.0:
+; TINY-NEXT:    ldi r20, 1
+; TINY-NEXT:    cp r17, r24
+; TINY-NEXT:    cpc r17, r25
+; TINY-NEXT:    brlt .LBB11_2
+; TINY-NEXT:  ; %bb.1:
+; TINY-NEXT:    mov r20, r17
+; TINY-NEXT:  .LBB11_2:
+; TINY-NEXT:    mov r24, r20
+; TINY-NEXT:    clr r25
+; TINY-NEXT:    ret
+  %2 = icmp sgt i16 %0, 0
+  %3 = zext i1 %2 to i16
+  ret i16 %3
+}
+
+define i16 @cmp_i16_gt_126(i16 %0) {
+; CHECK-LABEL: cmp_i16_gt_126:
+; CHECK:       ; %bb.0:
+; CHECK-NEXT:    ldi r18, 1
+; CHECK-NEXT:    cpi r24, 127
+; CHECK-NEXT:    cpc r25, r1
+; CHECK-NEXT:    brge .LBB12_2
+; CHECK-NEXT:  ; %bb.1:
+; CHECK-NEXT:    mov r18, r1
+; CHECK-NEXT:  .LBB12_2:
+; CHECK-NEXT:    mov r24, r18
+; CHECK-NEXT:    clr r25
+; CHECK-NEXT:    ret
+;
+; TINY-LABEL: cmp_i16_gt_126:
+; TINY:       ; %bb.0:
+; TINY-NEXT:    ldi r20, 1
+; TINY-NEXT:    cpi r24, 127
+; TINY-NEXT:    cpc r25, r17
+; TINY-NEXT:    brge .LBB12_2
+; TINY-NEXT:  ; %bb.1:
+; TINY-NEXT:    mov r20, r17
+; TINY-NEXT:  .LBB12_2:
+; TINY-NEXT:    mov r24, r20
+; TINY-NEXT:    clr r25
+; TINY-NEXT:    ret
+  %2 = icmp sgt i16 %0, 126
+  %3 = zext i1 %2 to i16
+  ret i16 %3
+}
+
+define i16 @cmp_i16_gt_1023(i16 %0) {
+; CHECK-LABEL: cmp_i16_gt_1023:
+; CHECK:       ; %bb.0:
+; CHECK-NEXT:    ldi r19, 4
+; CHECK-NEXT:    ldi r18, 1
+; CHECK-NEXT:    cp r24, r1
+; CHECK-NEXT:    cpc r25, r19
+; CHECK-NEXT:    brge .LBB13_2
+; CHECK-NEXT:  ; %bb.1:
+; CHECK-NEXT:    mov r18, r1
+; CHECK-NEXT:  .LBB13_2:
+; CHECK-NEXT:    mov r24, r18
+; CHECK-NEXT:    clr r25
+; CHECK-NEXT:    ret
+;
+; TINY-LABEL: cmp_i16_gt_1023:
+; TINY:       ; %bb.0:
+; TINY-NEXT:    ldi r21, 4
+; TINY-NEXT:    ldi r20, 1
+; TINY-NEXT:    cp r24, r17
+; TINY-NEXT:    cpc r25, r21
+; TINY-NEXT:    brge .LBB13_2
+; TINY-NEXT:  ; %bb.1:
+; TINY-NEXT:    mov r20, r17
+; TINY-NEXT:  .LBB13_2:
+; TINY-NEXT:    mov r24, r20
+; TINY-NEXT:    clr r25
+; TINY-NEXT:    ret
+  %2 = icmp sgt i16 %0, 1023
+  %3 = zext i1 %2 to i16
+  ret i16 %3
+}


        


More information about the llvm-commits mailing list