Prajwal Rathnakar Hegde has uploaded this change for review. ( https://gem5-review.googlesource.com/c/public/gem5/+/70137?usp=email )

Change subject: arch-arm,cpu: Add four Arm SVE2 int instructions
......................................................................

arch-arm,cpu: Add four Arm SVE2 int instructions

This changeset adds ARM SVE2 integer instructions
- ADCLB, ADCLT, SBCLB, SBCLT
- Decoding logic as per sve encoding of Version: 2023-03

Change-Id: I1bd3fe24b33677baa0b6da3c1dd7423f2b13b2c6
---
M src/arch/arm/insts/sve.cc
M src/arch/arm/insts/sve.hh
M src/arch/arm/isa/formats/sve_2nd_level.isa
M src/arch/arm/isa/formats/sve_top_level.isa
M src/arch/arm/isa/insts/sve.isa
M src/arch/arm/isa/templates/sve.isa
M src/cpu/FuncUnit.py
M src/cpu/op_class.hh
8 files changed, 179 insertions(+), 4 deletions(-)



diff --git a/src/arch/arm/insts/sve.cc b/src/arch/arm/insts/sve.cc
index 546074c..01e0eb4 100644
--- a/src/arch/arm/insts/sve.cc
+++ b/src/arch/arm/insts/sve.cc
@@ -436,6 +436,20 @@
 }

 std::string
+Sve2TerArithOp::generateDisassembly(
+        Addr pc, const loader::SymbolTable *symtab) const
+{
+    std::stringstream ss;
+    printMnemonic(ss, "", false);
+    printVecReg(ss, dest, true);
+    ccprintf(ss, ", ");
+    printVecReg(ss, op1, true);
+    ccprintf(ss, ", ");
+    printVecReg(ss, op2, true);
+    return ss.str();
+}
+
+std::string
 SveTerImmUnpredOp::generateDisassembly(
         Addr pc, const loader::SymbolTable *symtab) const
 {
diff --git a/src/arch/arm/insts/sve.hh b/src/arch/arm/insts/sve.hh
index 66d82f0..3e509e2 100644
--- a/src/arch/arm/insts/sve.hh
+++ b/src/arch/arm/insts/sve.hh
@@ -498,6 +498,23 @@
             Addr pc, const loader::SymbolTable *symtab) const override;
 };

+///SVE2 Accumulate instructions
+class Sve2TerArithOp : public ArmStaticInst
+{
+  protected:
+    RegIndex dest, op1, op2;
+
+    Sve2TerArithOp(const char* mnem, ExtMachInst _machInst,
+                    OpClass __opClass, RegIndex _dest,
+                    RegIndex _op1, RegIndex _op2) :
+        ArmStaticInst(mnem, _machInst, __opClass),
+        dest(_dest), op1(_op1), op2(_op2)
+    {}
+
+    std::string generateDisassembly(
+            Addr pc, const loader::SymbolTable *symtab) const override;
+};
+
 /// Ternary with immediate, destructive, unpredicated SVE instruction.
 class SveTerImmUnpredOp : public ArmStaticInst
 {
diff --git a/src/arch/arm/isa/formats/sve_2nd_level.isa b/src/arch/arm/isa/formats/sve_2nd_level.isa
index 2ee3817..6a4c790 100644
--- a/src/arch/arm/isa/formats/sve_2nd_level.isa
+++ b/src/arch/arm/isa/formats/sve_2nd_level.isa
@@ -2284,6 +2284,50 @@
     } // decodeSveMultiplyIndexed

     StaticInstPtr
+    decodeSve2ArithCarry(ExtMachInst machInst)
+    {
+        RegIndex zn = (RegIndex) (uint8_t) bits(machInst, 9, 5);
+        RegIndex zm = (RegIndex) (uint8_t) bits(machInst, 20, 16);
+        RegIndex zda = (RegIndex) (uint8_t) bits(machInst, 4, 0);
+
+        uint8_t size = bits(machInst, 23, 22);
+        if (size & 0x2) {
+            if(bits(machInst, 10)){
+                return decodeSve2TerUnpred<Sve2Sbclt>(
+                        size, machInst, zda, zn, zm);
+            } else {
+                return decodeSve2TerUnpred<Sve2Sbclb>(
+                        size, machInst, zda, zn, zm);
+            }
+        } else {
+            if(bits(machInst, 10)){
+                return decodeSve2TerUnpred<Sve2Adclt>(
+                        size, machInst, zda, zn, zm);
+            } else {
+                return decodeSve2TerUnpred<Sve2Adclb>(
+                    size, machInst, zda, zn, zm);
+            }
+        }
+        return new Unknown64(machInst);
+    } //decodeSve2ArithCarry
+
+    StaticInstPtr
+    decodeSve2Accum(ExtMachInst machInst)
+    {
+        uint8_t op0 = bits(machInst, 19, 17);
+        uint8_t op1 = bits(machInst, 13, 11);
+        if (op0 != 0) {
+            switch (op1) {
+                case 2:
+                    return decodeSve2ArithCarry(machInst);
+                default:
+                    break;
+            }
+        }
+        return new Unknown64(machInst);
+    } //decodeSve2Accum
+
+    StaticInstPtr
     decodeSveFpFastReduc(ExtMachInst machInst)
     {
         RegIndex vd = (RegIndex) (uint8_t) bits(machInst, 4, 0);
diff --git a/src/arch/arm/isa/formats/sve_top_level.isa b/src/arch/arm/isa/formats/sve_top_level.isa
index 155ec1c..99ff73d 100644
--- a/src/arch/arm/isa/formats/sve_top_level.isa
+++ b/src/arch/arm/isa/formats/sve_top_level.isa
@@ -69,6 +69,7 @@
     StaticInstPtr decodeSvePsel(ExtMachInst machInst);
     StaticInstPtr decodeSveIntWideImmUnpred(ExtMachInst machInst);
     StaticInstPtr decodeSveClamp(ExtMachInst machInst);
+    StaticInstPtr decodeSve2Accum(ExtMachInst machInst);

     StaticInstPtr decodeSveMultiplyAddUnpred(ExtMachInst machInst);
     StaticInstPtr decodeSveMultiplyIndexed(ExtMachInst machInst);
@@ -173,10 +174,23 @@
                 break;
             }
           case 0x2:
-            if (bits(machInst, 20)) {
-                return decodeSveIntWideImmPred(machInst);
-            } else {
-                return decodeSveLogMaskImm(machInst);
+            {
+              if (bits(machInst, 30) == 0) {
+                if (bits(machInst, 20)) {
+                  return decodeSveIntWideImmPred(machInst);
+                } else {
+                  return decodeSveLogMaskImm(machInst);
+                }
+              } else {
+                uint8_t b_15_14 = bits(machInst, 15, 14);
+                switch (b_15_14) {
+                  case 3:
+                    return decodeSve2Accum(machInst);
+                  default :
+                    break;
+                }
+              }
+              break;
             }
           case 0x3:
             {
diff --git a/src/arch/arm/isa/insts/sve.isa b/src/arch/arm/isa/insts/sve.isa
index 97d4ec7..4515d9e 100644
--- a/src/arch/arm/isa/insts/sve.isa
+++ b/src/arch/arm/isa/insts/sve.isa
@@ -926,6 +926,19 @@
         }
     }

+    // Decodes ternary, unpredicated SVE2 instructions
+    template <template <typename T> class Base>
+    StaticInstPtr
+    decodeSve2TerUnpred(unsigned size, ExtMachInst machInst,
+                      RegIndex dest, RegIndex op1, RegIndex op2)
+    {
+        if (bits(size, 0) == 0) {
+            return new Base<uint32_t>(machInst, dest, op1, op2);
+        } else {
+            return new Base<uint64_t>(machInst, dest, op1, op2);
+        }
+    }
+
// Decodes ternary with immediate operand, destructive, unpredicated SVE
     // instructions handling floating-point variants only.
     template <template <typename T> class Base>
@@ -2085,6 +2098,35 @@
                          'class_name' : 'Sve' + Name}
             exec_output += SveOpExecDeclare.subst(substDict)

+    # Generates definitions for ternary SVE2 intructions (unpredicated)
+    def sve2TerInstUnpred(name, Name, opClass, types, op,
+                         isTop=False, isAdd=True, decoder='Generic'):
+        global header_output, exec_output, decoders
+        code = sveEnabledCheckCode + '''
+        unsigned const pairs = ArmStaticInst::getCurSveVecLen<Element>(
+                xc->tcBase()) / 2;
+        for (unsigned p = 0; p < pairs; p++) {
+            const Element& srcElem1 = AA64FpDestMerge_x[2 * p + 0];
+            const Element& srcElem2 = AA64FpOp1_x[%(src_top_elem)s];
+            int carryIn = bits(AA64FpOp2_x[2 * p + 1], 0);
+            Element %(op)s
+            int carryOut = findCarry(
+                                    sizeof(Element) * 8, res, srcElem1,
+                                    %(src_elem2)s) & 1;
+            AA64FpDest_x[2 * p + 0] = res;
+            AA64FpDest_x[2 * p + 1] = (Element)0x0 + carryOut;
+        }''' % {'op': op,
+                'src_top_elem' : '2 * p + 1' if isTop else '2 * p + 0',
+                'src_elem2' : 'srcElem2' if isAdd else '~(srcElem2)'}
+        iop = ArmInstObjParams(name, 'Sve2' + Name, 'Sve2TerArithOp',
+                               {'code': code, 'op_class': opClass}, [])
+        header_output += sve2TerInstUnpredOpDeclare.subst(iop)
+        exec_output += SveOpExecute.subst(iop)
+        for type in types:
+            substDict = {'targs' : type,
+                         'class_name' : 'Sve2' + Name}
+            exec_output += SveOpExecDeclare.subst(substDict)
+
# Generates definitions for ternary SVE instructions with indexed operand
     def sveTerIdxInst(name, Name, opClass, types, op, decoder='Generic'):
         global header_output, exec_output, decoders
@@ -4052,6 +4094,22 @@
     # MLS
     mlsCode = 'destElem -= srcElem1 * srcElem2;'
     sveTerInst('mls', 'Mls', 'SimdMultAccOp', signedTypes, mlsCode)
+    # ADCLT
+    adcltCode = 'res = srcElem1 + srcElem2 + carryIn;'
+    sve2TerInstUnpred('adclt', 'Adclt', 'SimdLargeArithOp', unsignedTypes,
+                       adcltCode, isTop=True, isAdd=True)
+    # ADCLB
+    adclbCode = 'res = srcElem1 + srcElem2 + carryIn;'
+    sve2TerInstUnpred('adclb', 'Adclb', 'SimdLargeArithOp', unsignedTypes,
+                      adclbCode, isTop=False, isAdd=True)
+    # SBCLT
+    sbcltCode = 'res = srcElem1 + ~(srcElem2) + carryIn;'
+    sve2TerInstUnpred('sbclt', 'Sbclt', 'SimdLargeArithOp', unsignedTypes,
+                      sbcltCode, isTop=True, isAdd=False)
+    # SBCLB
+    sbclbCode = 'res = srcElem1 + ~(srcElem2) + carryIn;'
+    sve2TerInstUnpred('sbclb', 'Sbclb', 'SimdLargeArithOp', unsignedTypes,
+                      sbclbCode, isTop=False, isAdd=False)
     # MOVPRFX (predicated)
     movCode = 'destElem = srcElem1;'
     sveUnaryInst('movprfx', 'MovprfxPredM', 'SimdMiscOp', unsignedTypes,
diff --git a/src/arch/arm/isa/templates/sve.isa b/src/arch/arm/isa/templates/sve.isa
index 9260441..1548d72 100644
--- a/src/arch/arm/isa/templates/sve.isa
+++ b/src/arch/arm/isa/templates/sve.isa
@@ -489,6 +489,32 @@
 };
 }};

+def template sve2TerInstUnpredOpDeclare {{
+template <class _Element>
+class %(class_name)s : public %(base_class)s
+{
+  private:
+    %(reg_idx_arr_decl)s;
+
+  protected:
+    typedef _Element Element;
+    typedef _Element TPElem;
+
+  public:
+    // Constructor
+    %(class_name)s(ExtMachInst machInst, RegIndex _dest,
+                   RegIndex _op1, RegIndex _op2) :
+        %(base_class)s("%(mnemonic)s", machInst, %(op_class)s,
+                       _dest, _op1, _op2)
+    {
+        %(set_reg_idx_arr)s;
+        %(constructor)s;
+    }
+
+    Fault execute(ExecContext *, trace::InstRecord *) const override;
+};
+}};
+
 def template SveTerImmUnpredOpDeclare {{
 template <class _Element>
 class %(class_name)s : public %(base_class)s
diff --git a/src/cpu/FuncUnit.py b/src/cpu/FuncUnit.py
index 4a2733a..48e2c9b 100644
--- a/src/cpu/FuncUnit.py
+++ b/src/cpu/FuncUnit.py
@@ -98,6 +98,7 @@
         "FloatMemWrite",
         "IprAccess",
         "InstPrefetch",
+        "SimdLargeArith"
     ]


diff --git a/src/cpu/op_class.hh b/src/cpu/op_class.hh
index 4de018f..3db249d 100644
--- a/src/cpu/op_class.hh
+++ b/src/cpu/op_class.hh
@@ -99,6 +99,7 @@
 static const OpClass SimdShaSigma2Op = enums::SimdShaSigma2;
 static const OpClass SimdShaSigma3Op = enums::SimdShaSigma3;
 static const OpClass SimdPredAluOp = enums::SimdPredAlu;
+static const OpClass SimdLargeArithOp = enums::SimdLargeArith;
 static const OpClass MatrixOp = enums::Matrix;
 static const OpClass MatrixMovOp = enums::MatrixMov;
 static const OpClass MatrixOPOp = enums::MatrixOP;

--
To view, visit https://gem5-review.googlesource.com/c/public/gem5/+/70137?usp=email To unsubscribe, or for help writing mail filters, visit https://gem5-review.googlesource.com/settings

Gerrit-MessageType: newchange
Gerrit-Project: public/gem5
Gerrit-Branch: develop
Gerrit-Change-Id: I1bd3fe24b33677baa0b6da3c1dd7423f2b13b2c6
Gerrit-Change-Number: 70137
Gerrit-PatchSet: 1
Gerrit-Owner: Prajwal Rathnakar Hegde <prhe...@wisc.edu>
_______________________________________________
gem5-dev mailing list -- gem5-dev@gem5.org
To unsubscribe send an email to gem5-dev-le...@gem5.org
  • [gem5-dev] [M] Change in gem... Prajwal Rathnakar Hegde (Gerrit) via gem5-dev

Reply via email to