use reg_spec_t which passes reg + offset into sv_proc_t
authorLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Thu, 25 Oct 2018 05:36:06 +0000 (06:36 +0100)
committerLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Thu, 25 Oct 2018 05:36:06 +0000 (06:36 +0100)
17 files changed:
riscv/insn_template_sv.cc
riscv/insns/c_add.h
riscv/insns/c_jal.h
riscv/insns/c_jalr.h
riscv/insns/c_jr.h
riscv/insns/c_lui.h
riscv/insns/c_lwsp.h
riscv/insns/c_mv.h
riscv/insns/csrrc.h
riscv/insns/csrrci.h
riscv/insns/csrrs.h
riscv/insns/csrrsi.h
riscv/insns/csrrwi.h
riscv/sv.cc
riscv/sv_decode.h
riscv/sv_insn_redirect.cc
riscv/sv_insn_redirect.h

index 5bf0a0fed565c49f9187717aa1255c43bfe0efe9..f8b5522fb7f7a5a87e2d31cdcc961da451953f01 100644 (file)
@@ -77,7 +77,7 @@ reg_t sv_proc_t::FN(processor_t* p, insn_t s_insn, reg_t pc)
   reg_t _target_reg = 0;
   reg_t *target_reg = NULL;
 #endif
-  reg_t sp = 0;
+  reg_spec_t sp = {0,0};
   if (vlen > 0)
   {
     fprintf(stderr, "pre-ex reg %s %x %ld rd %ld rs1 %ld rs2 %ld vlen %d\n",
@@ -107,14 +107,14 @@ reg_t sv_proc_t::FN(processor_t* p, insn_t s_insn, reg_t pc)
 #endif
 #ifdef INSN_CATEGORY_TWINPREDICATION
 #ifdef INSN_TYPE_C_STACK_LD
-    src_pred = insn.predicate(sp, SRC_PREDINT, zeroingsrc);
+    src_pred = insn.predicate(sp.reg, SRC_PREDINT, zeroingsrc);
 #else
     src_pred = insn.predicate(s_insn.SRC_REG(), SRC_PREDINT, zeroingsrc);
 #endif
 #endif
 #ifdef DEST_PREDINT
 #ifdef INSN_TYPE_C_STACK_ST
-    dest_pred = insn.predicate(sp, DEST_PREDINT, zeroing);
+    dest_pred = insn.predicate(sp.reg, DEST_PREDINT, zeroing);
 #else
     // use the ORIGINAL, i.e. NON-REDIRECTED, register here
     dest_pred = insn.predicate(s_insn.DEST_REG(), DEST_PREDINT, zeroing);
@@ -186,24 +186,24 @@ reg_t sv_proc_t::FN(processor_t* p, insn_t s_insn, reg_t pc)
                       "vlen %d stop %d pred %lx rdv %lx v %ld rvc2 %ld sp %lx\n",
                 xstr(INSN), INSNCODE, voffs, *src_offs, *dest_offs,
                 vlen, insn.stop_vloop(),
-                dest_pred & (1<<voffs), READ_REG(insn._rvc_rs2()),
-                insn._rvc_rs2(), insn.rvc_lwsp_imm(), READ_REG(sp));
+                dest_pred & (1<<voffs), READ_REG(insn._rvc_rs2().reg),
+                insn._rvc_rs2().reg, insn.rvc_lwsp_imm(), READ_REG(sp.reg));
 #endif
 #ifdef INSN_C_LWSP
     fprintf(stderr, "pre %s %x vloop %d %d %d" \
-                      "vlen %d stop %d pred %lx rdv %lx rd %d rvc2 %ld sp %lx\n",
+                      "vlen %d stop %d pred %lx rdv %lx rd %ld rvc2 %ld sp %lx\n",
                 xstr(INSN), INSNCODE, voffs, *src_offs, *dest_offs,
                 vlen, insn.stop_vloop(),
-                dest_pred & (1<<voffs), READ_REG(insn._rd()),
-                insn._rd(), insn.rvc_lwsp_imm(), READ_REG(sp));
+                dest_pred & (1<<voffs), READ_REG(insn._rd().reg),
+                insn._rd().reg, insn.rvc_lwsp_imm(), READ_REG(sp.reg));
 #endif
 #ifdef INSN_C_BEQZ
     fprintf(stderr, "pre %s %x vloop %d %ld %d" \
                       "vlen %d stop %d pred %lx rdv %lx rvc_rs1 %ld\n",
                 xstr(INSN), INSNCODE, voffs, _target_reg, *dest_offs,
                 vlen, insn.stop_vloop(),
-                dest_pred & (1<<voffs), READ_REG(insn._rvc_rs1s()),
-                insn._rvc_rs1s());
+                dest_pred & (1<<voffs), READ_REG(insn._rvc_rs1s().reg),
+                insn._rvc_rs1s().reg);
 #endif
       #include INCLUDEFILE
 #ifdef DEST_PREDINT
@@ -221,13 +221,13 @@ reg_t sv_proc_t::FN(processor_t* p, insn_t s_insn, reg_t pc)
 #if defined(USING_REG_RD)
         fprintf(stderr, "reg %s %x vloop %d vlen %d stop %d pred %lx rd%lx\n",
                 xstr(INSN), INSNCODE, voffs, vlen, insn.stop_vloop(),
-                dest_pred & (1<<voffs), READ_REG(insn._rd()));
+                dest_pred & (1<<voffs), READ_REG(insn._rd().reg));
 #endif
 #if defined(USING_REG_FRD)
         fprintf(stderr, "reg %s %x vloop %d vlen %d stop %d pred %lx rd%g\n",
                 xstr(INSN), INSNCODE, voffs, vlen, insn.stop_vloop(),
                 dest_pred & (1<<voffs),
-                (double)(READ_FREG(insn._rd())).v[0]);
+                (double)(READ_FREG(insn._rd().reg)).v[0]);
 #endif
       }
       if (insn.stop_vloop())
index d9ecc32400422642935cc0678c9e8593aa4d1b32..955d50b55277958da89748cc9f1acfddb10e63e6 100644 (file)
@@ -1,3 +1,3 @@
 require_extension('C');
-require(insn.rvc_rs2() != 0);
+require(insn.insn_t::rvc_rs2() != 0);
 WRITE_RD(sext_xlen(rv_add(RVC_RS1, RVC_RS2)));
index ded03db048d71932a102a90fd5d02979ba4915d4..c31037bc85d4f490aa49a8dac2614bca362cae42 100644 (file)
@@ -1,8 +1,9 @@
 require_extension('C');
 if (xlen == 32) {
+  reg_spec_t xra = {X_RA, 0};
   reg_t tmp = npc;
   set_pc(pc + insn.rvc_j_imm());
-  WRITE_REG(X_RA, tmp);
+  WRITE_REG(xra, tmp);
 } else { // c.addiw
   require(insn.rvc_rd() != 0);
   WRITE_RD(sext32(rv_add(RVC_RS1, insn.rvc_imm())));
index 5ee9e10fa2f5d2cd44f61c9ef6a16e34e006f17c..7e5940771f80b7c94522bb3393d613e852dce8c8 100644 (file)
@@ -1,5 +1,6 @@
 require_extension('C');
-require(insn.rvc_rs1() != 0);
+require(insn.insn_t::rvc_rs1() != 0);
 reg_t tmp = npc;
 set_pc(rv_and(RVC_RS1, sv_reg_t(~reg_t(1))));
-WRITE_REG(X_RA, tmp);
+reg_spec_t xra = {X_RA, 0};
+WRITE_REG(xra, tmp);
index 1cb20d1e28f1796478971c5def0f78bf9acdcc72..c8149863a1d3b0bff78bf8181fbe421ba826fb5e 100644 (file)
@@ -1,3 +1,3 @@
 require_extension('C');
-require(insn.rvc_rs1() != 0);
+require(insn.insn_t::rvc_rs1() != 0);
 set_pc(rv_and(RVC_RS1, sv_reg_t(~reg_t(1))));
index 9b53a44042565eaa37ebd3600a57d9e921c7aa68..dcbc91dbc2107a478249e39072784e19f3c85bc4 100644 (file)
@@ -1,7 +1,7 @@
 require_extension('C');
 if (insn.insn_t::rvc_rd() == 2) { // c.addi16sp
   require(insn.rvc_addi16sp_imm() != 0);
-  WRITE_REG(X_SP, sext_xlen(rv_add(RVC_SP, insn.rvc_addi16sp_imm())));
+  WRITE_REG({X_SP,0}, sext_xlen(rv_add(RVC_SP, insn.rvc_addi16sp_imm())));
 } else {
   require(rv_ne(insn.rvc_imm(), sv_reg_t(0L)));
   WRITE_RD(rv_sl(insn.rvc_imm(), sv_reg_t(12UL)));
index b0f2549a9799711e1fadf05f4a0cc35f01d38774..6fd192c7244a2b95e722d3a360380d6bd4986efd 100644 (file)
@@ -1,3 +1,3 @@
 require_extension('C');
-require(insn.rvc_rd() != 0);
+require(insn.insn_t::rvc_rd() != 0);
 WRITE_RD(MMU.load_int32(rv_add(RVC_SP, insn.rvc_lwsp_imm())));
index a03d0d0763f26a62f3503c4552af308d1671598b..5e8f673cd7dce52998c4b3b85dc77f8af018e6ad 100644 (file)
@@ -1,3 +1,3 @@
 require_extension('C');
-require(insn.rvc_rs2() != 0);
+require(insn.insn_t::rvc_rs2() != 0);
 WRITE_RD(RVC_RS2);
index b82fcc52b371bdff14a516a8aa048a6c52b9877a..b0c597dbc23d2b921410cd8e1a467aff823039b6 100644 (file)
@@ -1,4 +1,4 @@
-bool write = insn.rs1() != 0;
+bool write = insn.insn_t::rs1() != 0;
 int csr = validate_csr(insn.csr(), write);
 reg_t old = p->get_csr(csr);
 if (write) {
index 35ac85fad1f5007c65437838722dcd40fd3795f8..9bf2c6213d6691a337dc0546329874c70895d80b 100644 (file)
@@ -1,8 +1,8 @@
-bool write = insn.rs1() != 0;
+bool write = insn.insn_t::rs1() != 0;
 int csr = validate_csr(insn.csr(), write);
 reg_t old = p->get_csr(csr);
 if (write) {
-  p->set_csr(csr, old & ~(reg_t)insn.rs1());
+  p->set_csr(csr, old & ~(reg_t)insn.insn_t::rs1());
 }
 WRITE_RD(sext_xlen(sv_reg_t(old)));
 serialize();
index f3f1166049d4a5c2f11833817414b3e3c586dca3..3680f4e5ddcf31f0a4cee6e3dc38a400b1089512 100644 (file)
@@ -1,4 +1,4 @@
-bool write = insn.rs1() != 0;
+bool write = insn.insn_t::rs1() != 0;
 int csr = validate_csr(insn.csr(), write);
 sv_reg_t old = sv_reg_t(p->get_csr(csr));
 if (write) {
index a06526141abedb162fed6de96f2f8f06f8fbf181..adda6be7420a1a9b858246d7ef62836ce0215702 100644 (file)
@@ -1,8 +1,8 @@
-bool write = insn.rs1() != 0;
+bool write = insn.insn_t::rs1() != 0;
 int csr = validate_csr(insn.csr(), write);
 reg_t old = p->get_csr(csr);
 if (write) {
-  p->set_csr(csr, old | insn.rs1());
+  p->set_csr(csr, old | insn.insn_t::rs1());
 }
 WRITE_RD(sext_xlen(sv_reg_t(old)));
 serialize();
index eaeecd5290cb2b4d3d22e6119c952d5289c2015c..7e1c4f7bac937387fd7581d7b8d4e41fd1c49bcc 100644 (file)
@@ -6,17 +6,17 @@ reg_t old = 0; // stop compiler bitchin
 if (csr != CSR_USVVL && csr != CSR_USVMVL)
 {
     old = p->get_csr(csr);
-    p->set_csr(csr, insn.rs1());
+    p->set_csr(csr, insn.insn_t::rs1());
 }
 else
 if (csr == CSR_USVVL || csr == CSR_USVMVL)
 {
-    p->set_csr(csr, insn.rs1()+1); // must add one here
+    p->set_csr(csr, insn.insn_t::rs1()+1); // must add one here
     old = p->get_csr(csr);
 }
 #else
 reg_t old = p->get_csr(csr);
-p->set_csr(csr, insn.rs1());
+p->set_csr(csr, insn.insn_t::rs1());
 #endif
 WRITE_RD(sext_xlen(sv_reg_t(old)));
 serialize();
index 53abaf46f71a3b8c4762fd9503ad861bfb34e581..7c2f0a174aa0d0ef5a614afe619ce7556930989e 100644 (file)
@@ -5,20 +5,20 @@
 int get_bitwidth(uint8_t elwidth, int xlen)
 {
   switch (elwidth) {
-      case 0: return (xlen == 32)? 64 : 32;
-      case 1: return (xlen == 32)? 32 : 64;
+      case 0: return xlen;
+      case 1: return 8;
       case 2: return 16;
-      default: return 8;
+      default: return 32;
   }
 }
 
 sv_insn_t::sv_insn_t(processor_t *pr, bool _sv_enabled,
-            insn_bits_t bits, unsigned int f, int xlen,
+            insn_bits_t bits, unsigned int f, int _xlen,
             uint64_t &p_rd, uint64_t &p_rs1, uint64_t &p_rs2, uint64_t &p_rs3,
             uint64_t &p_sp, uint64_t *p_im,
             int *o_rd, int *o_rs1, int *o_rs2, int *o_rs3, int *o_sp,
             int *o_imm) :
-            insn_t(bits), p(pr), src_bitwidth(0),
+            insn_t(bits), p(pr), src_bitwidth(0), xlen(_xlen),
             sv_enabled(_sv_enabled), vloop_continue(false),
             at_least_one_reg_vectorised(false), fimap(f),
             offs_rd(o_rd), offs_rs1(o_rs1), offs_rs2(o_rs2), offs_rs3(o_rs3),
@@ -35,31 +35,31 @@ sv_insn_t::sv_insn_t(processor_t *pr, bool _sv_enabled,
     {
         sv_reg_entry* r = NULL;
         if (bm == (REG_RS1 & fimap)) {
-             r = get_regentry(rs1(), true);
+             r = get_regentry(insn_t::rs1(), true);
         } else if (bm == (REG_RS2 & fimap)) {
-             r = get_regentry(rs2(), true);
+             r = get_regentry(insn_t::rs2(), true);
         } else if (bm == (REG_RS3 & fimap)) {
-             r = get_regentry(rs3(), true);
+             r = get_regentry(insn_t::rs3(), true);
         } else if (bm == (REG_RVC_RS1 & fimap)) {
-             r = get_regentry(rvc_rs1(), true);
+             r = get_regentry(insn_t::rvc_rs1(), true);
         } else if (bm == (REG_RVC_RS2 & fimap)) {
-             r = get_regentry(rvc_rs2(), true);
+             r = get_regentry(insn_t::rvc_rs2(), true);
         } else if (bm == (REG_RVC_RS1S & fimap)) {
-             r = get_regentry(rvc_rs1s(), true);
+             r = get_regentry(insn_t::rvc_rs1s(), true);
         } else if (bm == (REG_RVC_RS2S & fimap)) {
-             r = get_regentry(rvc_rs2s(), true);
+             r = get_regentry(insn_t::rvc_rs2s(), true);
         } else if (bm == (REG_FRS1 & fimap)) {
-             r = get_regentry(rs1(), false);
+             r = get_regentry(insn_t::rs1(), false);
         } else if (bm == (REG_FRS2 & fimap)) {
-             r = get_regentry(rs2(), false);
+             r = get_regentry(insn_t::rs2(), false);
         } else if (bm == (REG_FRS3 & fimap)) {
-             r = get_regentry(rs3(), false);
+             r = get_regentry(insn_t::rs3(), false);
         }
         if (r ==  NULL || !r->active) {
             continue;
         }
         uint8_t elwidth = r->elwidth;
-        uint8_t bitwidth = get_bitwidth(elwidth, xlen);
+        uint8_t bitwidth = get_bitwidth(elwidth, _xlen);
         src_bitwidth = std::max(src_bitwidth, bitwidth);
     }
 }
@@ -130,8 +130,11 @@ bool sv_insn_t::sv_check_reg(bool intreg, uint64_t reg)
  * of SV.  it's "supposed" to "just" be a vectorisation API. it isn't:
  * it's quite a bit more.
  */
-uint64_t sv_insn_t::remap(uint64_t reg, bool intreg, int voffs)
+reg_spec_t sv_insn_t::remap(uint64_t reg, bool intreg, int voffs)
 {
+  reg_spec_t spec;
+  spec.reg = reg;
+  spec.offset = voffs;
   // okaay so first determine which map to use.  intreg is passed
   // in (ultimately) from id_regs.py's examination of the use of
   // FRS1/RS1, WRITE_FRD/WRITE_RD, which in turn gets passed
@@ -142,7 +145,7 @@ uint64_t sv_insn_t::remap(uint64_t reg, bool intreg, int voffs)
   // is not being "redirected", so just return the actual reg.
   if (!r->active)
   {
-    return reg; // not active: return as-is
+    return spec; // not active: return as-is
   }
   vloop_continue = true;
 
@@ -156,7 +159,7 @@ uint64_t sv_insn_t::remap(uint64_t reg, bool intreg, int voffs)
   // we return the re-mapped register...
   if (!r->isvec) // scalar
   {
-    return reg;
+    return spec;
   }
   vloop_continue = true;
 
@@ -165,7 +168,8 @@ uint64_t sv_insn_t::remap(uint64_t reg, bool intreg, int voffs)
   // and, at last, we have "parallelism" a la contiguous registers.
   reg += voffs; // wheww :)
 
-  return reg;
+  spec.reg = reg;
+  return spec;
 }
 
 /* gets the predication value (if active).  returns all-1s if not active
@@ -215,14 +219,18 @@ reg_t sv_insn_t::predicate(uint64_t reg, bool intreg, bool &zeroing)
   return predicate;
 }
 
-uint64_t sv_insn_t::predicated(uint64_t reg, int offs, uint64_t pred)
+reg_spec_t sv_insn_t::predicated(reg_spec_t const& spec, int offs, uint64_t pred)
 {
+    reg_spec_t res = spec;
+    res.offset = offs;
     if (pred & (1<<offs))
     {
-        return reg;
+        return res;
     }
-    fprintf(stderr, "predication %ld %d %lx\n", reg, offs, pred);
-    return 0;
+    fprintf(stderr, "predication %ld %d %lx\n", spec.reg, offs, pred);
+    res.reg = 0;
+    res.offset = 0;
+    return res;
 }
 
 bool sv_insn_t::stop_vloop(void)
@@ -289,7 +297,7 @@ void sv_insn_t::setpc(int xlen, int vlen, reg_t &npc, reg_t addr, uint64_t offs,
     }
     fprintf(stderr, "setpc %lx offs %ld predicate %lx rs1 %ld rs2 %ld\n",
             save_branch_rd, offs, prs1,
-            READ_REG(rs1()), READ_REG(rs2()));
+            READ_REG(rs1().reg), READ_REG(rs2().reg));
 }
 
 uint8_t sv_insn_t::reg_elwidth(reg_t reg, bool intreg)
index f8701af92e0a2ffa5266ac9aa5081382f22853e2..e22b6aa094d6bf24277f4b98fc0c91c3d0af65c3 100644 (file)
 
 class processor_t;
 
+struct reg_spec_t
+{
+    reg_t reg;
+    int offset;
+};
+
 class sv_insn_t: public insn_t
 {
 public:
@@ -51,29 +57,29 @@ public:
         { return sv_reg_t(_rvc_spoffs_imm(4, insn_t::rvc_swsp_imm())); }
   uint64_t rvc_sdsp_imm() { return _rvc_spoffs_imm(8, insn_t::rvc_sdsp_imm()); }
 
-  uint64_t rd () { return predicated(_rd (), *offs_rd, prd); }
-  uint64_t rs1() { return predicated(_rs1(), *offs_rs1, prs1); }
-  uint64_t rs2() { return predicated(_rs2(), *offs_rs2, prs2); }
-  uint64_t rs3() { return predicated(_rs3(), *offs_rs3, prs3); }
-  uint64_t rvc_rs1 () { return predicated(_rvc_rs1 (), *offs_rs1, prs1); }
-  uint64_t rvc_rs1s() { return predicated(_rvc_rs1s(), *offs_rs1, prs1); }
-  uint64_t rvc_rs2 () { return predicated(_rvc_rs2 (), *offs_rs2, prs2); }
-  uint64_t rvc_rs2s() { return predicated(_rvc_rs2s(), *offs_rs2, prs2); }
-  uint64_t rvc_sp  () { return predicated(_rvc_sp  (), *offs_sp , psp ); }
-
-  uint64_t _rd () { return _remap(insn_t::rd (), fimap & REG_RD , offs_rd); }
-  uint64_t _rs1() { return _remap(insn_t::rs1(), fimap & REG_RS1, offs_rs1); }
-  uint64_t _rs2() { return _remap(insn_t::rs2(), fimap & REG_RS2, offs_rs2); }
-  uint64_t _rs3() { return _remap(insn_t::rs3(), fimap & REG_RS3, offs_rs3); }
-  uint64_t _rvc_rs1 () { return _remap(insn_t::rvc_rs1(), fimap & REG_RVC_RS1,
+  reg_spec_t rd () { return predicated(_rd (), *offs_rd, prd); }
+  reg_spec_t rs1() { return predicated(_rs1(), *offs_rs1, prs1); }
+  reg_spec_t rs2() { return predicated(_rs2(), *offs_rs2, prs2); }
+  reg_spec_t rs3() { return predicated(_rs3(), *offs_rs3, prs3); }
+  reg_spec_t rvc_rs1 () { return predicated(_rvc_rs1 (), *offs_rs1, prs1); }
+  reg_spec_t rvc_rs1s() { return predicated(_rvc_rs1s(), *offs_rs1, prs1); }
+  reg_spec_t rvc_rs2 () { return predicated(_rvc_rs2 (), *offs_rs2, prs2); }
+  reg_spec_t rvc_rs2s() { return predicated(_rvc_rs2s(), *offs_rs2, prs2); }
+  reg_spec_t rvc_sp  () { return predicated(_rvc_sp  (), *offs_sp , psp ); }
+
+  reg_spec_t _rd () { return _remap(insn_t::rd (), fimap & REG_RD , offs_rd); }
+  reg_spec_t _rs1() { return _remap(insn_t::rs1(), fimap & REG_RS1, offs_rs1); }
+  reg_spec_t _rs2() { return _remap(insn_t::rs2(), fimap & REG_RS2, offs_rs2); }
+  reg_spec_t _rs3() { return _remap(insn_t::rs3(), fimap & REG_RS3, offs_rs3); }
+  reg_spec_t _rvc_rs1 () { return _remap(insn_t::rvc_rs1(), fimap & REG_RVC_RS1,
                                        offs_rs1); }
-  uint64_t _rvc_rs1s() { return _remap(insn_t::rvc_rs1s(), fimap & REG_RVC_RS1S,
+  reg_spec_t _rvc_rs1s() { return _remap(insn_t::rvc_rs1s(), fimap & REG_RVC_RS1S,
                                        offs_rs1); }
-  uint64_t _rvc_rs2 () { return _remap(insn_t::rvc_rs2(), fimap & REG_RVC_RS2,
+  reg_spec_t _rvc_rs2 () { return _remap(insn_t::rvc_rs2(), fimap & REG_RVC_RS2,
                                        offs_rs2); }
-  uint64_t _rvc_rs2s() { return _remap(insn_t::rvc_rs2s(), fimap & REG_RVC_RS2S,
+  reg_spec_t _rvc_rs2s() { return _remap(insn_t::rvc_rs2s(), fimap & REG_RVC_RS2S,
                                        offs_rs2); }
-  uint64_t _rvc_sp  () { return _remap(2, true, // sp always 2, always int
+  reg_spec_t _rvc_sp  () { return _remap(2, true, // sp always 2, always int
                                        offs_sp); }
 
   void setpc(int xlen, int vlen, reg_t &npc, reg_t addr, uint64_t offs,
@@ -92,12 +98,13 @@ public:
 
   processor_t *p;
   uint8_t src_bitwidth;
+  int xlen;
   bool sv_enabled;
 
   // cached version of remap: if remap is called multiple times
   // by an emulated instruction it would increment the loop offset
   // before it's supposed to.
-  uint64_t _remap(uint64_t reg, bool isint, int *offs)
+  reg_spec_t _remap(uint64_t reg, bool isint, int *offs)
   {
     if (sv_check_reg(isint, reg))
     {
@@ -131,9 +138,9 @@ private:
 
   // remaps the register through the lookup table.
   // will need to take the current loop index/offset somehow
-  uint64_t remap(uint64_t reg, bool isint, int offs);
+  reg_spec_t remap(uint64_t reg, bool isint, int offs);
 
-  uint64_t predicated(uint64_t reg, int offs, uint64_t pred);
+  reg_spec_t predicated(reg_spec_t const& reg, int offs, uint64_t pred);
 };
 
 #endif
index ac2f58179bc76bf121e39351ecce71ed9ab6221f..46b4d7b7179280b608422a9eeaa73552aff6b4aa 100644 (file)
@@ -6,19 +6,29 @@
 void (sv_proc_t::WRITE_FRD)(float32_t value)
 {
     fprintf(stderr, "WRITE_FRD float32_t %f\n", (float)value.v);
-    DO_WRITE_FREG( _insn->rd(), freg(value) );
+    DO_WRITE_FREG( _insn->rd().reg, freg(value) );
 }
 
 void (sv_proc_t::WRITE_FRD)(float64_t value)
 {
     fprintf(stderr, "WRITE_FRD float64_t %g\n", (double)value.v);
-    DO_WRITE_FREG( _insn->rd(), freg(value) );
+    DO_WRITE_FREG( _insn->rd().reg, freg(value) );
 }
 
 void (sv_proc_t::WRITE_FRD)(freg_t value)
 {
     fprintf(stderr, "WRITE_FRD fsv_reg_t %lx\n", value.v[0]);
-    DO_WRITE_FREG( _insn->rd(), freg(value) );
+    DO_WRITE_FREG( _insn->rd().reg, freg(value) );
+}
+
+void (sv_proc_t::WRITE_RVC_FRS2S)(float32_t value)
+{
+    WRITE_FREG(_insn->rvc_rs2s().reg, freg(value));
+}
+
+void (sv_proc_t::WRITE_RVC_FRS2S)(float64_t const& value)
+{
+    WRITE_FREG(_insn->rvc_rs2s().reg, freg(value));
 }
 
 //void (sv_proc_t::WRITE_RD)(bool value)
@@ -69,10 +79,10 @@ void (sv_proc_t::WRITE_RD)(sv_reg_t const& value)
 //    STATE.XPR.write(reg, value);
 //}
 
-void (sv_proc_t::WRITE_REG)(reg_t reg, sv_reg_t const& value)
+void (sv_proc_t::WRITE_REG)(reg_spec_t const& spec, sv_reg_t const& value)
 {
     //WRITE_REG( reg, value ); // XXX TODO: replace properly
-    STATE.XPR.write(reg, value);
+    STATE.XPR.write(spec.reg, value);
 }
 
 //void (sv_proc_t::WRITE_REG)(reg_t reg, uint64_t value)
@@ -100,17 +110,18 @@ sv_reg_t (sv_proc_t::READ_REG)(uint64_t i)
 }
 */
 
-sv_reg_t sv_proc_t::get_intreg(reg_t reg)
+sv_reg_t sv_proc_t::get_intreg(reg_spec_t const&spec)
 {
-    //uint8_t elwidth = _insn->reg_elwidth(reg, true);
-    uint64_t data = _insn->p->get_state()->XPR[reg];
-    return sv_reg_t(data, xlen, _insn->src_bitwidth);
+    uint8_t elwidth = _insn->reg_elwidth(spec.reg, true);
+    uint64_t data = _insn->p->get_state()->XPR[spec.reg]; // XXX TODO: offset
+    uint8_t bitwidth = _insn->src_bitwidth;
+    return sv_reg_t(data, xlen, bitwidth);
 }
 
 #define GET_REG(name) \
     sv_reg_t sv_proc_t::get_##name() \
     { \
-        reg_t reg = _insn->name (); \
+        reg_spec_t reg = _insn->name (); \
         return get_intreg(reg); \
     }
 
@@ -122,24 +133,40 @@ GET_REG(rvc_rs2s)
 GET_REG(rvc_rs1)
 GET_REG(rvc_rs2)
 
+sv_reg_t sv_proc_t::get_rvc_sp()
+{
+    return get_intreg({X_SP, 0}); //_insn->rvc_sp()); // XXX TODO: work out redirection
+}
+
 freg_t sv_proc_t::get_frs1()
 {
-    return READ_FREG(_insn->rs1());
+    reg_spec_t spec = _insn->rs1();
+    return READ_FREG(spec.reg);
+}
+
+freg_t sv_proc_t::get_frs3()
+{
+    return READ_FREG(_insn->rs3().reg);
 }
 
 freg_t sv_proc_t::get_frs2()
 {
-    return READ_FREG(_insn->rs2());
+    return READ_FREG(_insn->rs2().reg);
 }
 
-sv_reg_t sv_proc_t::get_shamt()
+freg_t sv_proc_t::get_rvc_frs2s()
 {
-    return sv_reg_t(_insn->i_imm() & 0x3F); // XXX TODO: has to be elwidth'd
+    return READ_FREG(_insn->rvc_rs2s().reg);
 }
 
-sv_reg_t sv_proc_t::get_rvc_sp()
+freg_t sv_proc_t::get_rvc_frs2()
 {
-    return get_intreg(X_SP); // XXX TODO: work out redirection
+    return READ_FREG(_insn->rvc_rs2().reg);
+}
+
+sv_reg_t sv_proc_t::get_shamt()
+{
+    return sv_reg_t(_insn->i_imm() & 0x3F); // XXX TODO: has to be elwidth'd
 }
 
 sv_reg_t sv_proc_t::uint64_max()
index 4988ad54c3c860bdef1bef3374b6a55617166e3a..af2b67fa7042d7bd0488139133eabd8bf5eb32f2 100644 (file)
 #undef RS3
 #undef FRS1
 #undef FRS2
+#undef FRS3
 #undef RVC_RS1
 #undef RVC_RS2
+#undef RVC_FRS2
+#undef RVC_FRS2S
 #undef RVC_RS1S
 #undef RVC_RS2S
 #undef WRITE_REG
 #undef WRITE_FRD
 #undef WRITE_RVC_RS1S
 #undef WRITE_RVC_RS2S
+#undef WRITE_RVC_FRS2S
 #undef WRITE_RD
 #undef RVC_SP
 #undef SHAMT
@@ -33,11 +37,14 @@ class insn_t;
 
 #define FRS1 get_frs1()
 #define FRS2 get_frs2()
+#define FRS3 get_frs3()
 #define RS1 get_rs1()
 #define RS2 get_rs2()
 #define RS3 get_rs3()
 #define RVC_RS1 get_rvc_rs1()
 #define RVC_RS2 get_rvc_rs2()
+#define RVC_FRS2 get_rvc_frs2()
+#define RVC_FRS2S get_rvc_frs2s()
 #define RVC_RS1S get_rvc_rs1s()
 #define RVC_RS2S get_rvc_rs2s()
 #define RVC_SP get_rvc_sp()
@@ -58,11 +65,13 @@ public:
     void (WRITE_RD)(sv_reg_t const& value); // XXX TODO investigate
     //void (WRITE_RD)(sv_sreg_t value); // XXX TODO investigate
     void (WRITE_RVC_RS2S)(sv_reg_t const& value); // XXX TODO investigate
+    void (WRITE_RVC_FRS2S)(float64_t const& value); // XXX TODO investigate
+    void (WRITE_RVC_FRS2S)(float32_t value); // XXX TODO investigate
     //void (WRITE_RVC_RS2S)(sv_sreg_t value); // XXX TODO investigate
     void (WRITE_RVC_RS1S)(sv_reg_t const& value); // XXX TODO investigate
     //void (WRITE_RVC_RS1S)(sv_sreg_t value); // XXX TODO investigate
     //void (WRITE_REG)(reg_t reg, uint64_t value);
-    void (WRITE_REG)(reg_reg, sv_reg_t const& value);
+    void (WRITE_REG)(reg_spec_t const&reg, sv_reg_t const& value);
     //void (WRITE_REG)(reg_t reg, sv_sreg_t value);
     void (WRITE_FRD)(freg_t value);
     void (WRITE_FRD)(float64_t value);
@@ -88,7 +97,7 @@ public:
     }
 
 private:
-    sv_reg_t get_intreg(reg_reg);
+    sv_reg_t get_intreg(reg_spec_t const&reg);
 
 public:
     sv_reg_t get_rs1();
@@ -107,6 +116,9 @@ public:
 
     freg_t get_frs1();
     freg_t get_frs2();
+    freg_t get_frs3();
+    freg_t get_rvc_frs2();
+    freg_t get_rvc_frs2s();
 
     sv_sreg_t (sext_xlen)(sv_sreg_t const& v); // WARNING...
     sv_sreg_t (sext_xlen)(sv_reg_t const& v); // WARNING...