From 71e2e98d07499c6d0f31596fec52cd8cef5813a9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Karel=20Ko=C4=8D=C3=AD?= Date: Fri, 5 Jan 2018 18:14:53 +0100 Subject: Implement machine restart --- qtmips_machine/core.cpp | 25 +++++++++++++++++-------- qtmips_machine/core.h | 6 ++++++ qtmips_machine/memory.cpp | 10 ++++++++++ qtmips_machine/memory.h | 3 +++ qtmips_machine/qtmipsmachine.cpp | 7 ++++++- qtmips_machine/registers.cpp | 13 +++++++++---- qtmips_machine/registers.h | 2 ++ 7 files changed, 53 insertions(+), 13 deletions(-) diff --git a/qtmips_machine/core.cpp b/qtmips_machine/core.cpp index 53b7cad..faebd87 100644 --- a/qtmips_machine/core.cpp +++ b/qtmips_machine/core.cpp @@ -259,11 +259,11 @@ void Core::dtMemoryInit(struct dtMemory &dt) { CoreSingle::CoreSingle(Registers *regs, MemoryAccess *mem, bool jmp_delay_slot) : \ Core(regs, mem) { - if (jmp_delay_slot) { + if (jmp_delay_slot) jmp_delay_decode = new struct Core::dtDecode(); - dtDecodeInit(*jmp_delay_decode); - } else + else jmp_delay_decode = nullptr; + reset(); } CoreSingle::~CoreSingle() { @@ -284,16 +284,18 @@ void CoreSingle::step() { handle_pc(d); } +void CoreSingle::reset() { + if (jmp_delay_decode != nullptr) + Core::dtDecodeInit(*jmp_delay_decode); +} + CorePipelined::CorePipelined(Registers *regs, MemoryAccess *mem) : \ Core(regs, mem) { - dtFetchInit(dt_f); - dtDecodeInit(dt_d); - dtExecuteInit(dt_e); - dtMemoryInit(dt_m); + reset(); } void CorePipelined::step() { - // TODO implement pipelined + // TODO implement forward unit writeback(dt_m); dt_m =memory(dt_e); dt_e = execute(dt_d); @@ -301,3 +303,10 @@ void CorePipelined::step() { dt_f = fetch(); handle_pc(dt_d); } + +void CorePipelined::reset() { + dtFetchInit(dt_f); + dtDecodeInit(dt_d); + dtExecuteInit(dt_e); + dtMemoryInit(dt_m); +} diff --git a/qtmips_machine/core.h b/qtmips_machine/core.h index 7d38d79..1878bfc 100644 --- a/qtmips_machine/core.h +++ b/qtmips_machine/core.h @@ -17,6 +17,8 @@ public: virtual void step() = 0; // Do single step + virtual void reset() = 0; // Reset core (only core, memory and registers has to be reseted separately) + signals: void instruction_fetched(machine::Instruction &inst); @@ -75,6 +77,8 @@ public: void step(); + void reset(); + private: struct Core::dtDecode *jmp_delay_decode; }; @@ -85,6 +89,8 @@ public: void step(); + void reset(); + private: struct Core::dtFetch dt_f; struct Core::dtDecode dt_d; diff --git a/qtmips_machine/memory.cpp b/qtmips_machine/memory.cpp index 142c750..69f7d54 100644 --- a/qtmips_machine/memory.cpp +++ b/qtmips_machine/memory.cpp @@ -178,6 +178,16 @@ Memory::~Memory() { free_section_tree(this->mt_root, 0); } +void Memory::reset() { + free_section_tree(this->mt_root, 0); + this->mt_root = allocate_section_tree(); +} + +void Memory::reset(const Memory &m) { + free_section_tree(this->mt_root, 0); + this->mt_root = copy_section_tree(m.get_memorytree_root(), 0); +} + // Create address mask with section length #define ADDRESS_MASK(LEN) ((1 << (LEN)) - 1) diff --git a/qtmips_machine/memory.h b/qtmips_machine/memory.h index ab33e4a..3bd1060 100644 --- a/qtmips_machine/memory.h +++ b/qtmips_machine/memory.h @@ -43,6 +43,7 @@ public: void write_byte(std::uint32_t offset, std::uint8_t value); std::uint8_t read_byte(std::uint32_t offset) const; + void merge(MemorySection&); std::uint32_t length() const; const std::uint8_t* data() const; @@ -71,6 +72,8 @@ public: Memory(); Memory(const Memory&); ~Memory(); + void reset(); // Reset whole content of memory (removes old tree and creates new one) + void reset(const Memory&); MemorySection *get_section(std::uint32_t address, bool create) const; // returns section containing given address void write_byte(std::uint32_t address, std::uint8_t value); diff --git a/qtmips_machine/qtmipsmachine.cpp b/qtmips_machine/qtmipsmachine.cpp index 744c5e2..1d7523c 100644 --- a/qtmips_machine/qtmipsmachine.cpp +++ b/qtmips_machine/qtmipsmachine.cpp @@ -110,7 +110,12 @@ void QtMipsMachine::step() { } void QtMipsMachine::restart() { - // TODO + pause(); + regs->reset(); + mem->reset(*mem_program_only); + // TODO cache + cr->reset(); + set_status(ST_READY); } void QtMipsMachine::set_status(enum Status st) { diff --git a/qtmips_machine/registers.cpp b/qtmips_machine/registers.cpp index 447fdfc..5a720f7 100644 --- a/qtmips_machine/registers.cpp +++ b/qtmips_machine/registers.cpp @@ -10,10 +10,7 @@ using namespace machine; ////////////////////////////////////////////////////////////////////////////// Registers::Registers() : QObject() { - this->pc = PC_INIT; // Initialize to beginning program section - for (int i = 0; i < 31; i++) - this->gp[i] = 0; - this->hi = this->lo = 0; + reset(); } Registers::Registers(const Registers &orig) : QObject() { @@ -99,3 +96,11 @@ bool Registers::operator==(const Registers &c) const { bool Registers::operator!=(const Registers &c) const { return ! this->operator==(c); } + +void Registers::reset() { + pc_abs_jmp(PC_INIT); // Initialize to beginning program section + for (int i = 1; i < 32; i++) + write_gp(i, 0); + write_hi_lo(false, 0); + write_hi_lo(true, 0); +} diff --git a/qtmips_machine/registers.h b/qtmips_machine/registers.h index fa3e304..9bb8426 100644 --- a/qtmips_machine/registers.h +++ b/qtmips_machine/registers.h @@ -26,6 +26,8 @@ public: bool operator ==(const Registers &c) const; bool operator !=(const Registers &c) const; + void reset(); // Reset all values to zero (except pc) + signals: void pc_update(std::uint32_t val); void gp_update(std::uint8_t i, std::uint32_t val); -- cgit v1.2.3