Add --disable-dtb option to suppress writing the DTB to memory
[riscv-isa-sim.git] / riscv / processor.cc
index 90266b99aef5ba60fbe36de1dfaa89693afc4b11..4a7d0ec6147a8c58be756faf914b4b4ab6732fbe 100644 (file)
@@ -28,7 +28,11 @@ processor_t::processor_t(const char* isa, simif_t* sim, uint32_t id,
   register_base_instructions();
 
   mmu = new mmu_t(sim, this);
+
   disassembler = new disassembler_t(max_xlen);
+  if (ext)
+    for (auto disasm_insn : ext->get_disasms())
+      disassembler->add_insn(disasm_insn);
 
   reset();
 }
@@ -121,7 +125,6 @@ void state_t::reset(reg_t max_isa)
   misa = max_isa;
   prv = PRV_M;
   pc = DEFAULT_RSTVEC;
-  load_reservation = -1;
   tselect = 0;
   for (unsigned int i = 0; i < num_triggers; i++)
     mcontrol[i].type = 2;
@@ -298,8 +301,6 @@ void processor_t::take_trap(trap_t& t, reg_t epc)
     set_csr(CSR_MSTATUS, s);
     set_privilege(PRV_M);
   }
-
-  yield_load_reservation();
 }
 
 void processor_t::disasm(insn_t insn)
@@ -329,7 +330,8 @@ int processor_t::paddr_bits()
 void processor_t::set_csr(int which, reg_t val)
 {
   val = zext_xlen(val);
-  reg_t delegable_ints = MIP_SSIP | MIP_STIP | MIP_SEIP | (1 << IRQ_COP);
+  reg_t delegable_ints = MIP_SSIP | MIP_STIP | MIP_SEIP
+                       | ((ext != NULL) << IRQ_COP);
   reg_t all_ints = delegable_ints | MIP_MSIP | MIP_MTIP;
   switch (which)
   {
@@ -406,10 +408,16 @@ void processor_t::set_csr(int which, reg_t val)
         state.minstret = (state.minstret >> 32 << 32) | (val & 0xffffffffU);
       else
         state.minstret = val;
+      // The ISA mandates that if an instruction writes instret, the write
+      // takes precedence over the increment to instret.  However, Spike
+      // unconditionally increments instret after executing an instruction.
+      // Correct for this artifact by decrementing instret here.
+      state.minstret--;
       break;
     case CSR_MINSTRETH:
     case CSR_MCYCLEH:
       state.minstret = (val << 32) | (state.minstret << 32 >> 32);
+      state.minstret--; // See comment above.
       break;
     case CSR_SCOUNTEREN:
       state.scounteren = val;
@@ -587,7 +595,7 @@ reg_t processor_t::get_csr(int which)
     case CSR_MCOUNTEREN: return state.mcounteren;
     case CSR_SSTATUS: {
       reg_t mask = SSTATUS_SIE | SSTATUS_SPIE | SSTATUS_SPP | SSTATUS_FS
-                 | SSTATUS_XS | SSTATUS_SUM | SSTATUS_UXL;
+                 | SSTATUS_XS | SSTATUS_SUM | SSTATUS_MXR | SSTATUS_UXL;
       reg_t sstatus = state.mstatus & mask;
       if ((sstatus & SSTATUS_FS) == SSTATUS_FS ||
           (sstatus & SSTATUS_XS) == SSTATUS_XS)