From e26d895762e7a802c4b6c6a970a63309f7d0fdb7 Mon Sep 17 00:00:00 2001 From: Pavel Pisa Date: Sun, 17 Mar 2019 20:49:22 +0100 Subject: Registers and cop0 state updates and reads are visualized by highlights. Signed-off-by: Pavel Pisa --- qtmips_gui/cop0dock.cpp | 46 +++++++++++++++++++++++++++-- qtmips_gui/cop0dock.h | 9 ++++++ qtmips_gui/registersdock.cpp | 69 ++++++++++++++++++++++++++++++++++++++++---- qtmips_gui/registersdock.h | 12 ++++++++ qtmips_machine/cop0state.cpp | 5 +++- qtmips_machine/cop0state.h | 1 + qtmips_machine/registers.cpp | 14 ++++++--- qtmips_machine/registers.h | 2 ++ 8 files changed, 145 insertions(+), 13 deletions(-) diff --git a/qtmips_gui/cop0dock.cpp b/qtmips_gui/cop0dock.cpp index 1070444..9e35d6b 100644 --- a/qtmips_gui/cop0dock.cpp +++ b/qtmips_gui/cop0dock.cpp @@ -50,14 +50,24 @@ Cop0Dock::Cop0Dock(QWidget *parent) : QDockWidget(parent) { } while(false) cop0reg[0] = nullptr; - for (int i = 1; i < machine::Cop0State::COP0REGS_CNT; i++) + for (int i = 1; i < machine::Cop0State::COP0REGS_CNT; i++) { INIT(cop0reg[i], machine::Cop0State::cop0reg_name((machine::Cop0State::Cop0Registers)i)); + cop0reg_highlighted[i] = false; + } #undef INIT scrollarea->setWidget(widg); setWidget(scrollarea); setObjectName("Coprocessor0"); setWindowTitle("Coprocessor0"); + + pal_normal = QPalette(cop0reg[1]->palette()); + pal_updated = QPalette(cop0reg[1]->palette()); + pal_read = QPalette(cop0reg[1]->palette()); + pal_normal.setColor(QPalette::WindowText, QColor(0, 0, 0)); + pal_updated.setColor(QPalette::WindowText, QColor(240, 0, 0)); + pal_read.setColor(QPalette::WindowText, QColor(0, 0, 240)); + cop0reg_highlighted_any = false; } Cop0Dock::~Cop0Dock() { @@ -76,11 +86,15 @@ void Cop0Dock::setup(machine::QtMipsMachine *machine) { } const machine::Cop0State *cop0state = machine->cop0state(); - connect(cop0state, &machine::Cop0State::cop0reg_update, - this, &Cop0Dock::cop0reg_changed); for (int i = 1; i < machine::Cop0State::COP0REGS_CNT; i++) labelVal(cop0reg[i], cop0state->read_cop0reg((machine::Cop0State::Cop0Registers)i)); + + connect(cop0state, &machine::Cop0State::cop0reg_update, + this, &Cop0Dock::cop0reg_changed); + connect(cop0state, &machine::Cop0State::cop0reg_read, + this, &Cop0Dock::cop0reg_read); + connect(machine, SIGNAL(tick()), this, SLOT(clear_highlights())); } void Cop0Dock::cop0reg_changed(enum machine::Cop0State::Cop0Registers reg, std::uint32_t val) { @@ -88,6 +102,32 @@ void Cop0Dock::cop0reg_changed(enum machine::Cop0State::Cop0Registers reg, std:: QString("Cop0Dock received signal with invalid cop0 register: ") + QString::number((uint)reg)); labelVal(cop0reg[(uint)reg], val); + cop0reg[reg]->setPalette(pal_updated); + cop0reg_highlighted[reg] = true; + cop0reg_highlighted_any = true; +} + +void Cop0Dock::cop0reg_read(enum machine::Cop0State::Cop0Registers reg, std::uint32_t val) { + (void)val; + SANITY_ASSERT((uint)reg < machine::Cop0State::COP0REGS_CNT && (uint)reg, + QString("Cop0Dock received signal with invalid cop0 register: ") + + QString::number((uint)reg)); + if (!cop0reg_highlighted[reg]) + cop0reg[reg]->setPalette(pal_read); + cop0reg_highlighted[reg] = true; + cop0reg_highlighted_any = true; +} + +void Cop0Dock::clear_highlights() { + if (!cop0reg_highlighted_any) + return; + for (int i = 1; i < machine::Cop0State::COP0REGS_CNT; i++) { + if (cop0reg_highlighted[i]) { + cop0reg[i]->setPalette(pal_normal); + cop0reg_highlighted[i] = false; + } + } + cop0reg_highlighted_any = false; } void Cop0Dock::labelVal(QLabel *label, std::uint32_t value) { diff --git a/qtmips_gui/cop0dock.h b/qtmips_gui/cop0dock.h index 5dfa058..79f8a3e 100644 --- a/qtmips_gui/cop0dock.h +++ b/qtmips_gui/cop0dock.h @@ -41,6 +41,7 @@ #include #include #include +#include #include "qtmipsmachine.h" #include "statictable.h" @@ -54,12 +55,20 @@ public: private slots: void cop0reg_changed(enum machine::Cop0State::Cop0Registers reg, std::uint32_t val); + void cop0reg_read(enum machine::Cop0State::Cop0Registers reg, std::uint32_t val); + void clear_highlights(); private: StaticTable *widg; QScrollArea *scrollarea; QLabel *cop0reg[machine::Cop0State::COP0REGS_CNT]; + bool cop0reg_highlighted[machine::Cop0State::COP0REGS_CNT]; + bool cop0reg_highlighted_any; + + QPalette pal_normal; + QPalette pal_updated; + QPalette pal_read; void labelVal(QLabel *label, std::uint32_t val); }; diff --git a/qtmips_gui/registersdock.cpp b/qtmips_gui/registersdock.cpp index 2823abc..b72696d 100644 --- a/qtmips_gui/registersdock.cpp +++ b/qtmips_gui/registersdock.cpp @@ -74,6 +74,9 @@ RegistersDock::RegistersDock(QWidget *parent) : QDockWidget(parent) { scrollarea = new QScrollArea(this); scrollarea->setWidgetResizable(true); widg = new StaticTable(scrollarea); + gp_highlighted = 0; + hi_highlighted = false; + lo_highlighted = false; #define INIT(X, LABEL) do{ \ X = new QLabel("0x00000000", widg); \ @@ -94,6 +97,13 @@ RegistersDock::RegistersDock(QWidget *parent) : QDockWidget(parent) { setWidget(scrollarea); setObjectName("Registers"); setWindowTitle("Registers"); + + pal_normal = QPalette(gp[0]->palette()); + pal_updated = QPalette(gp[0]->palette()); + pal_read = QPalette(gp[0]->palette()); + pal_normal.setColor(QPalette::WindowText, QColor(0, 0, 0)); + pal_updated.setColor(QPalette::WindowText, QColor(240, 0, 0)); + pal_read.setColor(QPalette::WindowText, QColor(0, 0, 240)); } RegistersDock::~RegistersDock() { @@ -118,9 +128,6 @@ void RegistersDock::setup(machine::QtMipsMachine *machine) { } const machine::Registers *regs = machine->registers(); - connect(regs, SIGNAL(pc_update(std::uint32_t)), this, SLOT(pc_changed(std::uint32_t))); - connect(regs, SIGNAL(gp_update(std::uint8_t,std::uint32_t)), this, SLOT(gp_changed(std::uint8_t,std::uint32_t))); - connect(regs, SIGNAL(hi_lo_update(bool,std::uint32_t)), this, SLOT(hi_lo_changed(bool,std::uint32_t))); // Load values labelVal(pc, regs->read_pc()); @@ -128,6 +135,13 @@ void RegistersDock::setup(machine::QtMipsMachine *machine) { labelVal(lo, regs->read_hi_lo(false)); for (int i = 0; i < 32; i++) labelVal(gp[i], regs->read_gp(i)); + + connect(regs, SIGNAL(pc_update(std::uint32_t)), this, SLOT(pc_changed(std::uint32_t))); + connect(regs, SIGNAL(gp_update(std::uint8_t,std::uint32_t)), this, SLOT(gp_changed(std::uint8_t,std::uint32_t))); + connect(regs, SIGNAL(hi_lo_update(bool,std::uint32_t)), this, SLOT(hi_lo_changed(bool,std::uint32_t))); + connect(regs, SIGNAL(gp_read(std::uint8_t,std::uint32_t)), this, SLOT(gp_read(std::uint8_t,std::uint32_t))); + connect(regs, SIGNAL(hi_lo_read(bool,std::uint32_t)), this, SLOT(hi_lo_read(bool,std::uint32_t))); + connect(machine, SIGNAL(tick()), this, SLOT(clear_highlights())); } void RegistersDock::pc_changed(std::uint32_t val) { @@ -137,13 +151,58 @@ void RegistersDock::pc_changed(std::uint32_t val) { void RegistersDock::gp_changed(std::uint8_t i, std::uint32_t val) { SANITY_ASSERT(i < 32, QString("RegistersDock received signal with invalid gp register: ") + QString::number(i)); labelVal(gp[i], val); + gp[i]->setPalette(pal_updated); + gp_highlighted |= 1 << i; +} + +void RegistersDock::gp_read(std::uint8_t i, std::uint32_t val) { + (void)val; + SANITY_ASSERT(i < 32, QString("RegistersDock received signal with invalid gp register: ") + QString::number(i)); + if (!(gp_highlighted & (1 << i))) { + gp[i]->setPalette(pal_read); + gp_highlighted |= 1 << i; + } } void RegistersDock::hi_lo_changed(bool hi, std::uint32_t val) { - if (hi) + if (hi) { labelVal(this->hi, val); - else + this->hi->setPalette(pal_updated); + hi_highlighted = true; + } else { labelVal(lo, val); + this->lo->setPalette(pal_updated); + lo_highlighted = true; + } +} + +void RegistersDock::hi_lo_read(bool hi, std::uint32_t val) { + (void)val; + if (hi) { + if (!hi_highlighted) + this->hi->setPalette(pal_read); + hi_highlighted = true; + } else { + if (!lo_highlighted) + this->lo->setPalette(pal_read); + lo_highlighted = true; + } +} + +void RegistersDock::clear_highlights() { + if (hi_highlighted) + this->hi->setPalette(pal_normal); + if (lo_highlighted) + this->lo->setPalette(pal_normal); + if (gp_highlighted != 0) { + for (int i = 0; i < 32; i++) { + if (gp_highlighted & (1 << i)) + gp[i]->setPalette(pal_normal); + } + } + gp_highlighted = 0; + hi_highlighted = false; + lo_highlighted = false; } void RegistersDock::labelVal(QLabel *label, std::uint32_t value) { diff --git a/qtmips_gui/registersdock.h b/qtmips_gui/registersdock.h index c56f375..dcc5e9b 100644 --- a/qtmips_gui/registersdock.h +++ b/qtmips_gui/registersdock.h @@ -41,6 +41,7 @@ #include #include #include +#include #include "qtmipsmachine.h" #include "statictable.h" @@ -56,6 +57,9 @@ private slots: void pc_changed(std::uint32_t val); void gp_changed(std::uint8_t i, std::uint32_t val); void hi_lo_changed(bool hi, std::uint32_t val); + void gp_read(std::uint8_t i, std::uint32_t val); + void hi_lo_read(bool hi, std::uint32_t val); + void clear_highlights(); private: StaticTable *widg; @@ -66,6 +70,14 @@ private: QLabel *lo; QLabel *gp[32]; + std::uint32_t gp_highlighted; + bool hi_highlighted; + bool lo_highlighted; + + QPalette pal_normal; + QPalette pal_updated; + QPalette pal_read; + void labelVal(QLabel *label, std::uint32_t val); }; diff --git a/qtmips_machine/cop0state.cpp b/qtmips_machine/cop0state.cpp index 35f78d1..1caada1 100644 --- a/qtmips_machine/cop0state.cpp +++ b/qtmips_machine/cop0state.cpp @@ -150,7 +150,10 @@ QString Cop0State::cop0reg_name(enum Cop0Registers reg) { } std::uint32_t Cop0State::read_cop0reg_default(enum Cop0Registers reg) const { - return cop0reg[(int)reg]; + std::uint32_t val; + val = cop0reg[(int)reg]; + emit cop0reg_read(reg, val); + return val; } void Cop0State::write_cop0reg_default(enum Cop0Registers reg, std::uint32_t value) { diff --git a/qtmips_machine/cop0state.h b/qtmips_machine/cop0state.h index 0fd3d3f..a6af9a4 100644 --- a/qtmips_machine/cop0state.h +++ b/qtmips_machine/cop0state.h @@ -89,6 +89,7 @@ public: signals: void cop0reg_update(enum Cop0Registers reg, std::uint32_t val); + void cop0reg_read(enum Cop0Registers reg, std::uint32_t val) const; public slots: void set_interrupt_signal(uint irq_num, bool active); diff --git a/qtmips_machine/registers.cpp b/qtmips_machine/registers.cpp index fa9731a..ed27ec6 100644 --- a/qtmips_machine/registers.cpp +++ b/qtmips_machine/registers.cpp @@ -87,25 +87,31 @@ void Registers::pc_abs_jmp_28(std::uint32_t address) { } std::uint32_t Registers::read_gp(std::uint8_t i) const { + std::uint32_t value; SANITY_ASSERT(i < 32, QString("Trying to read from register ") + QString(i)); if (!i) // $0 always reads as 0 return 0; - return this->gp[i - 1]; + value = this->gp[i - 1]; + emit gp_read(i, value); + return value; } void Registers::write_gp(std::uint8_t i, std::uint32_t value) { SANITY_ASSERT(i < 32, QString("Trying to write to register ") + QString(i)); if (i == 0) // Skip write to $0 return; - emit gp_update(i, value); this->gp[i - 1] = value; + emit gp_update(i, value); } std::uint32_t Registers::read_hi_lo(bool is_hi) const { + std::uint32_t value; if (is_hi) - return hi; + value = hi; else - return lo; + value = lo; + emit hi_lo_read(is_hi, value); + return value; } void Registers::write_hi_lo(bool is_hi, std::uint32_t value) { diff --git a/qtmips_machine/registers.h b/qtmips_machine/registers.h index a4f7aa8..63aa266 100644 --- a/qtmips_machine/registers.h +++ b/qtmips_machine/registers.h @@ -67,6 +67,8 @@ signals: void pc_update(std::uint32_t val); void gp_update(std::uint8_t i, std::uint32_t val); void hi_lo_update(bool hi, std::uint32_t val); + void gp_read(std::uint8_t i, std::uint32_t val) const; + void hi_lo_read(bool hi, std::uint32_t val) const; private: std::uint32_t gp[31]; // general-purpose registers ($0 is intentionally skipped) -- cgit v1.2.3