override and redirect mmu store functions to sv_proc_t
authorLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Mon, 29 Oct 2018 06:31:25 +0000 (06:31 +0000)
committerLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Mon, 29 Oct 2018 06:31:25 +0000 (06:31 +0000)
riscv/sv_insn_redirect.cc
riscv/sv_insn_redirect.h
riscv/sv_mmu.cc
riscv/sv_mmu.h

index 85ee6d642c8168db68c85578496f5512fd619ca4..3eb7a393c79e29125c5f76b80c8a9c778a2a9e56 100644 (file)
@@ -41,23 +41,6 @@ void (sv_proc_t::WRITE_RVC_FRS2S)(sv_float64_t const& value)
     WRITE_FREG(_insn->rvc_rs2s(), freg(value));
 }
 
-//void (sv_proc_t::WRITE_RD)(bool value)
-//{
-//    WRITE_REG( _insn->rd(), value ? 1 : 0);
-//}
-
-//
-//void (sv_proc_t::WRITE_RD)(sv_reg_t value)
-//{
-//    WRITE_REG( _insn->rd(), value );
-//}
-
-
-//void (sv_proc_t::WRITE_RVC_RS1S)(sv_sreg_t value)
-//{
-//    WRITE_REG(_insn->rvc_rs1s(), value );
-//}
-
 void (sv_proc_t::WRITE_RVC_RS1S)(sv_reg_t const& value)
 {
     WRITE_REG(_insn->rvc_rs1s(), value );
@@ -68,32 +51,13 @@ void (sv_proc_t::WRITE_RVC_RS2S)(sv_reg_t const& value)
     WRITE_REG(_insn->rvc_rs2s(), value );
 }
 
-//void (sv_proc_t::WRITE_RVC_RS2S)(sv_sreg_t value)
-//{
-//    WRITE_REG(_insn->rvc_rs2s(), value );
-//}
-
 void (sv_proc_t::WRITE_RD)(sv_reg_t const& value)
 {
     WRITE_REG( _insn->rd(), value ); // XXX TODO: replace properly
 }
 
-//void (sv_proc_t::WRITE_RD)(sv_sreg_t value)
-//{
-//    WRITE_REG( _insn->rd(), value ); // XXX TODO: replace properly
-//}
-
-//void (sv_proc_t::WRITE_REG)(reg_t reg, sv_sreg_t value)
-//{
-//    //WRITE_REG( reg, value ); // XXX TODO: replace properly
-//    STATE.XPR.write(reg, value);
-//}
-
-//#define OFFSDIV
-
 void (sv_proc_t::DO_WRITE_FREG)(reg_spec_t const& spec, sv_freg_t const& value)
 {
-    //WRITE_REG( reg, value ); // XXX TODO: replace properly
     reg_t reg = spec.reg;
     if (spec.offset) {
         reg += *spec.offset;
@@ -105,7 +69,6 @@ void (sv_proc_t::DO_WRITE_FREG)(reg_spec_t const& spec, sv_freg_t const& value)
 void (sv_proc_t::WRITE_REG)(reg_spec_t const& spec, sv_reg_t const& value)
 {
     uint64_t wval = (uint64_t)value;
-    //WRITE_REG( reg, value ); // XXX TODO: replace properly
     reg_t reg = spec.reg;
     int bitwidth = get_bitwidth(_insn->reg_elwidth(reg, true), xlen);
     unsigned int shift = 0;
@@ -244,13 +207,6 @@ sv_reg_t sv_proc_t::uint64_max()
     return ((UINT64_C(18446744073709551615)));
 }
 
-/*
-sv_reg_t (sv_proc_t::sext_xlen)(uint64_t x)
-{
-    x = (((sreg_t)(x) << (64-xlen)) >> (64-xlen));
-    return sv_uint64_t(x);
-}
-*/
 sv_sreg_t (sv_proc_t::sext_xlen)(sv_sreg_t const& v)
 {
     int64_t x = v;
@@ -272,12 +228,6 @@ sv_reg_t (sv_proc_t::zext_xlen)(sv_reg_t const& v)
     return sv_reg_t(x);
 }
 
-/*
-sv_reg_t (sv_proc_t::sext32)(uint_fast32_t v)
-{
-    return sext32((uint64_t)v); // XXX TODO do properly
-}
-*/
 sv_sreg_t (sv_proc_t::sext32)(sv_reg_t const& v)
 {
     uint64_t x = v;
@@ -285,13 +235,6 @@ sv_sreg_t (sv_proc_t::sext32)(sv_reg_t const& v)
     return sv_sreg_t((int64_t)x, v.get_xlen(), v.get_elwidth());
 }
 
-//sv_sreg_t (sv_proc_t::sext32)(sv_sreg_t const& v)
-//{
-//    int64_t x = v;
-//    x = ((sreg_t)(int32_t)(x));
-//    return sv_sreg_t(x);
-//}
-
 sv_reg_t (sv_proc_t::zext32)(sv_reg_t const& v)
 {
     uint64_t x = v;
@@ -299,70 +242,6 @@ sv_reg_t (sv_proc_t::zext32)(sv_reg_t const& v)
     return sv_reg_t(x);
 }
 
-/*
-sv_reg_t sv_reg_t::make_sv_int64_t (int64_t v) const
-{
-    return sv_sreg_t(v);
-}
-
-sv_reg_t sv_reg_t::make_sv_uint64_t (uint64_t v) const
-{
-    return sv_uint64_t(v);
-}
-
-
-sv_reg_t::operator sv_sreg_t ()
-{
-    return sv_sreg_t ( as_uint64() );
-}
-
-sv_reg_t::operator int32_t ()
-{
-    uint64_t x = get_data();
-    sv_sreg_t _x = (sv_sreg_t) x;
-    sv_sreg_t y = sv_sreg_t ( _x );
-    return y;
-}
-
-
-sv_reg_t::operator uint16_t ()
-{
-    uint64_t x = get_data();
-    uint16_t _x = (uint16_t) x;
-    sv_uint16_t y = sv_uint16_t ( _x );
-    return y;
-}
-
-
-sv_reg_t::operator uint8_t () // XXX TODO, make_sv_char_t
-{
-    uint64_t x = get_data();
-    uint8_t _x = (uint8_t) x;
-    sv_uint64_t y = sv_uint64_t ( _x );
-    return y;
-}
-
-sv_reg_t::operator char () // XXX TODO, make_sv_char_t
-{
-    uint64_t x = get_data();
-    char _x = (char) x;
-    sv_sreg_t y = sv_sreg_t ( _x );
-    return y;
-}
-
-sv_reg_t::operator uint32_t () // TODO, make_sv_uint32_t
-        { return make_sv_uint64_t( (sv_sreg_t) (as_uint64()) ); }
-sv_reg_t::operator sv_sreg_t ()
-        { return make_sv_int64_t( (sv_sreg_t) (as_uint64()) ); }
-
-sv_reg_t::operator sv_reg_t ()
-{
-    uint64_t x = get_data();
-    sv_uint64_t y = sv_uint64_t ( x );
-    return y;
-}
-*/
-
 sv_reg_t sv_proc_t::rv_add(sv_reg_t const & lhs, sv_reg_t const & rhs)
 {
     uint8_t bitwidth = _insn->src_bitwidth;
@@ -455,11 +334,6 @@ sv_reg_t sv_proc_t::rv_sl(sv_reg_t const & lhs, sv_reg_t const & rhs)
     return lhs << rhs;
 }
 
-//sv_sreg_t sv_proc_t::rv_sr(sv_sreg_t const & lhs, sv_reg_t const & rhs)
-//{
-//    return lhs >> rhs;
-//}
-
 sv_reg_t sv_proc_t::rv_sr(sv_reg_t const & lhs, sv_reg_t const & rhs)
 {
     return lhs >> rhs;
@@ -982,3 +856,32 @@ sv_reg_t sv_proc_t::mmu_load(reg_spec_t const& spec, sv_reg_t const& offs,
     return v;
 }
 
+void sv_proc_t::mmu_store(reg_spec_t const& spec, sv_reg_t const& offs,
+                                size_t width, reg_t val)
+{
+    // different "mode" applies, here: addr_mode.
+    reg_t reg = READ_REG(spec, true, width);
+    sv_reg_t addr = sv_reg_t((uint64_t)reg + (int64_t)offs);
+
+    // now that the address has been moved on by the modulo-offset,
+    // get only an elwidth-sized element (if not "default")
+    width = get_bitwidth(_insn->reg_elwidth(spec.reg, true), width);
+    fprintf(stderr, "mmu_store wid %ld addr %lx offs %lx stored %lx\n",
+                    width, (uint64_t)reg, (int64_t)offs, (uint64_t)val);
+    switch (width)
+    {
+        case 8:
+            p->get_mmu()->store_uint8(addr, val);
+            break;
+        case 16:
+            p->get_mmu()->store_uint16(addr, val);
+            break;
+        case 32:
+            p->get_mmu()->store_uint32(addr, val);
+            break;
+        case 64:
+            p->get_mmu()->store_uint64(addr, val);
+            break;
+    }
+}
+
index a04a82847dfd60253daef3c16eeebf70023301b6..6314c4c6c96a14670b7daa0efec9ad81660030e8 100644 (file)
@@ -246,7 +246,10 @@ public:
     sv_freg_t fsgnj128(sv_freg_t a, sv_freg_t b, bool n, bool x);
 
     sv_reg_t mmu_load(reg_spec_t const& spec, sv_reg_t const& offs,
-                                size_t width, bool ext);
+                      size_t width, bool ext);
+
+    void mmu_store(reg_spec_t const& spec, sv_reg_t const& offs,
+                   size_t width, reg_t val);
 
 
 #include "sv_insn_decl.h"
index 399fa1ddd1762b52e510ee0d81b21eac11de1bb4..8bded65841d31df6ad56c86995f5afe99040abb2 100644 (file)
@@ -21,16 +21,20 @@ sv_load_func(int16, 16, false )
 sv_load_func(int32, 32, false )
 sv_load_func(int64, 64, false )
 
-#define sv_store_func(type) \
+#define sv_store_func(type, width) \
+void sv_mmu_t::store_##type(reg_spec_t const& spec, sv_reg_t const& offs, \
+                            type##_t val) { \
+  proc->s.mmu_store(spec, offs, width, val); \
+} \
 void sv_mmu_t::store_##type(sv_reg_t const& addr, type##_t val) { \
   mmu_t::store_##type(addr, val); \
 }
 
 // store value to memory at aligned address
-sv_store_func(uint8)
-sv_store_func(uint16)
-sv_store_func(uint32)
-sv_store_func(uint64)
+sv_store_func(uint8, 8)
+sv_store_func(uint16, 16)
+sv_store_func(uint32, 32)
+sv_store_func(uint64, 64)
 
 #if 0
 #define sv_amo_func(type) \
index 824d166976b472dd34fafc9996d7c0ca68933e16..8c8ce9dad964f766959d02f5df32942288b2568e 100644 (file)
@@ -29,6 +29,8 @@ public:
   sv_load_func_decl(int64)
 
   #define sv_store_func_decl(type) \
+    void store_##type(reg_spec_t const& reg, sv_reg_t const& offs, \
+                      type##_t val); \
     void store_##type(sv_reg_t const& addr, type##_t val);
 
   // store value to memory at aligned address