[llvm] db83e3e - [Hexagon] Generate HVX/FP arithmetic instructions

Krzysztof Parzyszek via llvm-commits llvm-commits at lists.llvm.org
Thu Dec 30 12:48:00 PST 2021


Author: Krzysztof Parzyszek
Date: 2021-12-30T12:47:30-08:00
New Revision: db83e3e5071afeb161ce3cdc246668ace9e1bb8e

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

LOG: [Hexagon] Generate HVX/FP arithmetic instructions

Co-authored-by: Anirudh Sundar Subramaniam <quic_sanirudh at quicinc.com>
Co-authored-by: Sumanth Gundapaneni <sgundapa at quicinc.com>
Co-authored-by: Joshua Herrera <joshherr at quicinc.com>

Added: 
    llvm/test/CodeGen/Hexagon/autohvx/arith-float.ll

Modified: 
    llvm/lib/Target/Hexagon/HexagonISelLoweringHVX.cpp
    llvm/lib/Target/Hexagon/HexagonPatternsHVX.td

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Target/Hexagon/HexagonISelLoweringHVX.cpp b/llvm/lib/Target/Hexagon/HexagonISelLoweringHVX.cpp
index 80287518fa56..a65ceccb60a1 100755
--- a/llvm/lib/Target/Hexagon/HexagonISelLoweringHVX.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonISelLoweringHVX.cpp
@@ -93,6 +93,12 @@ HexagonTargetLowering::initializeHVXLowering() {
       Subtarget.useHVXFloatingPoint()) {
     setOperationAction(ISD::FMINNUM, MVT::v64f16, Legal);
     setOperationAction(ISD::FMAXNUM, MVT::v64f16, Legal);
+    setOperationAction(ISD::FADD,    MVT::v64f16, Legal);
+    setOperationAction(ISD::FSUB,    MVT::v64f16, Legal);
+    setOperationAction(ISD::FMUL,    MVT::v64f16, Legal);
+    setOperationAction(ISD::FADD,    MVT::v32f32, Legal);
+    setOperationAction(ISD::FSUB,    MVT::v32f32, Legal);
+    setOperationAction(ISD::FMUL,    MVT::v32f32, Legal);
     setOperationAction(ISD::FMINNUM, MVT::v32f32, Legal);
     setOperationAction(ISD::FMAXNUM, MVT::v32f32, Legal);
     setOperationAction(ISD::INSERT_SUBVECTOR,  MVT::v64f16, Custom);
@@ -126,6 +132,9 @@ HexagonTargetLowering::initializeHVXLowering() {
 
     setOperationAction(ISD::LOAD,    MVT::v64f32, Custom);
     setOperationAction(ISD::STORE,   MVT::v64f32, Custom);
+    setOperationAction(ISD::FADD,    MVT::v64f32, Custom);
+    setOperationAction(ISD::FSUB,    MVT::v64f32, Custom);
+    setOperationAction(ISD::FMUL,    MVT::v64f32, Custom);
     setOperationAction(ISD::FMINNUM, MVT::v64f32, Custom);
     setOperationAction(ISD::FMAXNUM, MVT::v64f32, Custom);
     setOperationAction(ISD::VSELECT, MVT::v64f32, Custom);
@@ -2291,6 +2300,9 @@ HexagonTargetLowering::LowerHvxOperation(SDValue Op, SelectionDAG &DAG) const {
       case ISD::CTLZ:
       case ISD::CTTZ:
       case ISD::MUL:
+      case ISD::FADD:
+      case ISD::FSUB:
+      case ISD::FMUL:
       case ISD::FMINNUM:
       case ISD::FMAXNUM:
       case ISD::MULHS:

diff  --git a/llvm/lib/Target/Hexagon/HexagonPatternsHVX.td b/llvm/lib/Target/Hexagon/HexagonPatternsHVX.td
index f72f02eb9cba..33bf8ed71a9c 100644
--- a/llvm/lib/Target/Hexagon/HexagonPatternsHVX.td
+++ b/llvm/lib/Target/Hexagon/HexagonPatternsHVX.td
@@ -453,6 +453,52 @@ let Predicates = [UseHVX] in {
            (V6_vmux HvxQR:$Qu, HvxVR:$Vt, HvxVR:$Vs)>;
 }
 
+// For now, we always deal with vector floating point in SF mode.
+class OpR_RR_pat_conv<InstHexagon MI, PatFrag Op, ValueType ResType,
+                      PatFrag RsPred, PatFrag RtPred = RsPred>
+  : Pat<(ResType (Op RsPred:$Rs, RtPred:$Rt)),
+        (V6_vconv_sf_qf32 (VecF32 (MI RsPred:$Rs, RtPred:$Rt)))>;
+
+class OpR_RR_pat_conv_hf<InstHexagon MI, PatFrag Op, ValueType ResType,
+                      PatFrag RsPred, PatFrag RtPred = RsPred>
+  : Pat<(ResType (Op RsPred:$Rs, RtPred:$Rt)),
+        (V6_vconv_hf_qf16 (VecF16 (MI RsPred:$Rs, RtPred:$Rt)))>;
+
+let Predicates = [UseHVXV68, UseHVXQFloat] in {
+  def: OpR_RR_pat_conv_hf<V6_vsub_hf,        pf2<fsub>,  VecF16, HVF16>;
+  def: OpR_RR_pat_conv_hf<V6_vadd_hf,        pf2<fadd>,  VecF16, HVF16>;
+  def: OpR_RR_pat_conv_hf<V6_vmpy_qf16_hf,   pf2<fmul>,  VecF16, HVF16>;
+  def: OpR_RR_pat_conv<V6_vsub_sf,        pf2<fsub>,  VecF32, HVF32>;
+  def: OpR_RR_pat_conv<V6_vadd_sf,        pf2<fadd>,  VecF32, HVF32>;
+  def: OpR_RR_pat_conv<V6_vmpy_qf32_sf,   pf2<fmul>,  VecF32, HVF32>;
+
+  // For now we assume that the fp32 register is always coming in as IEEE float
+  // since the qfloat arithmetic instructions above always generate the
+  // accompanying conversions as part of their pattern
+  def: Pat<(VecF16 (pf1<fpround> HWF32:$Vuu)),
+          (V6_vdealh (V6_vconv_hf_qf32
+              (VecPF32 (Combinev (V6_vadd_sf (HiVec HvxWR:$Vuu), (V6_vd0)),
+                                 (V6_vadd_sf (LoVec HvxWR:$Vuu), (V6_vd0))
+              ))))>;
+
+}
+
+// HVX IEEE arithmetic Instructions
+let Predicates = [UseHVXV68, UseHVXIEEEFP] in {
+  def: Pat<(fadd HVF16:$Rs, HVF16:$Rt),
+           (V6_vadd_hf_hf HVF16:$Rs, HVF16:$Rt)>;
+  def: Pat<(fadd HVF32:$Rs, HVF32:$Rt),
+           (V6_vadd_sf_sf HVF32:$Rs, HVF32:$Rt)>;
+  def: Pat<(fsub HVF16:$Rs, HVF16:$Rt),
+           (V6_vsub_hf_hf HVF16:$Rs, HVF16:$Rt)>;
+  def: Pat<(fsub HVF32:$Rs, HVF32:$Rt),
+           (V6_vsub_sf_sf HVF32:$Rs, HVF32:$Rt)>;
+  def: Pat<(fmul HVF16:$Rs, HVF16:$Rt),
+           (V6_vmpy_hf_hf HVF16:$Rs, HVF16:$Rt)>;
+  def: Pat<(fmul HVF32:$Rs, HVF32:$Rt),
+           (V6_vmpy_sf_sf HVF32:$Rs, HVF32:$Rt)>;
+}
+
 let Predicates = [UseHVXV68, UseHVXFloatingPoint] in {
   def: Pat<(vselect HQ16:$Qu, HVF16:$Vs, HVF16:$Vt),
            (V6_vmux HvxQR:$Qu, HvxVR:$Vs, HvxVR:$Vt)>;

diff  --git a/llvm/test/CodeGen/Hexagon/autohvx/arith-float.ll b/llvm/test/CodeGen/Hexagon/autohvx/arith-float.ll
new file mode 100644
index 000000000000..0ba7f2c04601
--- /dev/null
+++ b/llvm/test/CodeGen/Hexagon/autohvx/arith-float.ll
@@ -0,0 +1,167 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
+; RUN: llc -march=hexagon < %s | FileCheck %s
+
+define <64 x half> @f0(<64 x half> %a0, <64 x half> %a1) #0 {
+; CHECK-LABEL: f0:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.qf16 = vadd(v0.hf,v1.hf)
+; CHECK-NEXT:    }
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.hf = v0.qf16
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fadd <64 x half> %a0, %a1
+  ret <64 x half> %v0
+}
+
+define <32 x float> @f1(<32 x float> %a0, <32 x float> %a1) #0 {
+; CHECK-LABEL: f1:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.qf32 = vadd(v0.sf,v1.sf)
+; CHECK-NEXT:    }
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.sf = v0.qf32
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fadd <32 x float> %a0, %a1
+  ret <32 x float> %v0
+}
+
+define <64 x half> @f2(<64 x half> %a0, <64 x half> %a1) #0 {
+; CHECK-LABEL: f2:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.qf16 = vsub(v0.hf,v1.hf)
+; CHECK-NEXT:    }
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.hf = v0.qf16
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fsub <64 x half> %a0, %a1
+  ret <64 x half> %v0
+}
+
+define <32 x float> @f3(<32 x float> %a0, <32 x float> %a1) #0 {
+; CHECK-LABEL: f3:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.qf32 = vsub(v0.sf,v1.sf)
+; CHECK-NEXT:    }
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.sf = v0.qf32
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fsub <32 x float> %a0, %a1
+  ret <32 x float> %v0
+}
+
+define <64 x half> @f4(<64 x half> %a0, <64 x half> %a1) #0 {
+; CHECK-LABEL: f4:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.qf16 = vmpy(v0.hf,v1.hf)
+; CHECK-NEXT:    }
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.hf = v0.qf16
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fmul <64 x half> %a0, %a1
+  ret <64 x half> %v0
+}
+
+define <32 x float> @f5(<32 x float> %a0, <32 x float> %a1) #0 {
+; CHECK-LABEL: f5:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.qf32 = vmpy(v0.sf,v1.sf)
+; CHECK-NEXT:    }
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.sf = v0.qf32
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fmul <32 x float> %a0, %a1
+  ret <32 x float> %v0
+}
+
+define <64 x half> @f6(<64 x half> %a0, <64 x half> %a1) #1 {
+; CHECK-LABEL: f6:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.hf = vadd(v0.hf,v1.hf)
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fadd <64 x half> %a0, %a1
+  ret <64 x half> %v0
+}
+
+define <32 x float> @f7(<32 x float> %a0, <32 x float> %a1) #1 {
+; CHECK-LABEL: f7:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.sf = vadd(v0.sf,v1.sf)
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fadd <32 x float> %a0, %a1
+  ret <32 x float> %v0
+}
+
+define <64 x half> @f8(<64 x half> %a0, <64 x half> %a1) #1 {
+; CHECK-LABEL: f8:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.hf = vsub(v0.hf,v1.hf)
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fsub <64 x half> %a0, %a1
+  ret <64 x half> %v0
+}
+
+define <32 x float> @f9(<32 x float> %a0, <32 x float> %a1) #1 {
+; CHECK-LABEL: f9:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.sf = vsub(v0.sf,v1.sf)
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fsub <32 x float> %a0, %a1
+  ret <32 x float> %v0
+}
+
+define <64 x half> @f10(<64 x half> %a0, <64 x half> %a1) #1 {
+; CHECK-LABEL: f10:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.hf = vmpy(v0.hf,v1.hf)
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fmul <64 x half> %a0, %a1
+  ret <64 x half> %v0
+}
+
+define <32 x float> @f11(<32 x float> %a0, <32 x float> %a1) #1 {
+; CHECK-LABEL: f11:
+; CHECK:       // %bb.0: // %b0
+; CHECK-NEXT:    {
+; CHECK-NEXT:     v0.sf = vmpy(v0.sf,v1.sf)
+; CHECK-NEXT:     jumpr r31
+; CHECK-NEXT:    }
+b0:
+  %v0 = fmul <32 x float> %a0, %a1
+  ret <32 x float> %v0
+}
+
+attributes #0 = { nounwind "target-cpu"="hexagonv69" "target-features"="+hvxv69,+hvx-length128b,+hvx-qfloat" }
+attributes #1 = { nounwind "target-cpu"="hexagonv69" "target-features"="+hvxv69,+hvx-length128b,+hvx-ieee-fp" }


        


More information about the llvm-commits mailing list