aboutsummaryrefslogtreecommitdiff
path: root/qtmips_gui
diff options
context:
space:
mode:
Diffstat (limited to 'qtmips_gui')
-rw-r--r--qtmips_gui/NewDialog.ui31
-rw-r--r--qtmips_gui/NewDialogCache.ui169
-rw-r--r--qtmips_gui/newdialog.cpp190
-rw-r--r--qtmips_gui/newdialog.h15
4 files changed, 293 insertions, 112 deletions
diff --git a/qtmips_gui/NewDialog.ui b/qtmips_gui/NewDialog.ui
index a39a014..0490ca3 100644
--- a/qtmips_gui/NewDialog.ui
+++ b/qtmips_gui/NewDialog.ui
@@ -37,7 +37,7 @@
</attribute>
<layout class="QVBoxLayout" name="verticalLayout_5">
<item>
- <widget class="QGroupBox" name="groupBox_2">
+ <widget class="QGroupBox" name="preset_box">
<property name="title">
<string>Preset</string>
</property>
@@ -198,6 +198,35 @@
</widget>
</item>
<item>
+ <widget class="QGroupBox" name="groupBox">
+ <property name="title">
+ <string>Access time (in cycles)</string>
+ </property>
+ <layout class="QFormLayout" name="formLayout">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label_2">
+ <property name="text">
+ <string>Read:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1">
+ <widget class="QSpinBox" name="mem_time_read"/>
+ </item>
+ <item row="1" column="0">
+ <widget class="QLabel" name="label_3">
+ <property name="text">
+ <string>Write:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1">
+ <widget class="QSpinBox" name="mem_time_write"/>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
<spacer name="verticalSpacer_2">
<property name="orientation">
<enum>Qt::Vertical</enum>
diff --git a/qtmips_gui/NewDialogCache.ui b/qtmips_gui/NewDialogCache.ui
index 3c91824..04f15f7 100644
--- a/qtmips_gui/NewDialogCache.ui
+++ b/qtmips_gui/NewDialogCache.ui
@@ -6,63 +6,140 @@
<rect>
<x>0</x>
<y>0</y>
- <width>339</width>
- <height>167</height>
+ <width>435</width>
+ <height>272</height>
</rect>
</property>
<property name="windowTitle">
<string>Form</string>
</property>
- <layout class="QFormLayout" name="formLayout_2">
- <item row="0" column="0">
- <widget class="QLabel" name="label">
- <property name="text">
- <string>Capacity:</string>
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <item>
+ <widget class="QGroupBox" name="enabled">
+ <property name="title">
+ <string/>
</property>
- </widget>
- </item>
- <item row="0" column="1">
- <widget class="QSpinBox" name="spinBox"/>
- </item>
- <item row="1" column="0">
- <widget class="QLabel" name="label_2">
- <property name="text">
- <string>Number of sets:</string>
+ <property name="checkable">
+ <bool>true</bool>
</property>
+ <layout class="QFormLayout" name="formLayout">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label">
+ <property name="text">
+ <string>Capacity:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1">
+ <widget class="QSpinBox" name="capcity"/>
+ </item>
+ <item row="1" column="0">
+ <widget class="QLabel" name="label_2">
+ <property name="text">
+ <string>Number of sets:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="1">
+ <widget class="QSpinBox" name="number_of_sets"/>
+ </item>
+ <item row="2" column="0">
+ <widget class="QLabel" name="label_3">
+ <property name="text">
+ <string>Block size:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="1">
+ <widget class="QSpinBox" name="block_size"/>
+ </item>
+ <item row="3" column="0">
+ <widget class="QLabel" name="label_4">
+ <property name="text">
+ <string>Number of blocks:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="3" column="1">
+ <widget class="QSpinBox" name="number_of_blocks"/>
+ </item>
+ <item row="4" column="0">
+ <widget class="QLabel" name="label_5">
+ <property name="text">
+ <string>Degree of associativity:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="4" column="1">
+ <widget class="QSpinBox" name="degree_if_associativity"/>
+ </item>
+ <item row="5" column="0">
+ <widget class="QLabel" name="label_6">
+ <property name="text">
+ <string>Replacement policy:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="6" column="0">
+ <widget class="QLabel" name="label_7">
+ <property name="text">
+ <string>Writeback policy:</string>
+ </property>
+ </widget>
+ </item>
+ <item row="5" column="1">
+ <widget class="QComboBox" name="comboBox">
+ <item>
+ <property name="text">
+ <string>Random</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Least Recently Used (LRU)</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Least Frequently Used (LFU)</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Adaptive Replacement Cache (ARC)</string>
+ </property>
+ </item>
+ </widget>
+ </item>
+ <item row="6" column="1">
+ <widget class="QComboBox" name="comboBox_2">
+ <item>
+ <property name="text">
+ <string>Write trough</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Write back</string>
+ </property>
+ </item>
+ </widget>
+ </item>
+ </layout>
</widget>
</item>
- <item row="2" column="0">
- <widget class="QLabel" name="label_3">
- <property name="text">
- <string>Block size:</string>
+ <item>
+ <spacer name="verticalSpacer">
+ <property name="orientation">
+ <enum>Qt::Vertical</enum>
</property>
- </widget>
- </item>
- <item row="3" column="0">
- <widget class="QLabel" name="label_4">
- <property name="text">
- <string>Number of blocks:</string>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>20</width>
+ <height>40</height>
+ </size>
</property>
- </widget>
- </item>
- <item row="4" column="0">
- <widget class="QLabel" name="label_5">
- <property name="text">
- <string>Degree of associativity:</string>
- </property>
- </widget>
- </item>
- <item row="1" column="1">
- <widget class="QSpinBox" name="spinBox_2"/>
- </item>
- <item row="2" column="1">
- <widget class="QSpinBox" name="spinBox_3"/>
- </item>
- <item row="3" column="1">
- <widget class="QSpinBox" name="spinBox_4"/>
- </item>
- <item row="4" column="1">
- <widget class="QSpinBox" name="spinBox_5"/>
+ </spacer>
</item>
</layout>
</widget>
diff --git a/qtmips_gui/newdialog.cpp b/qtmips_gui/newdialog.cpp
index 6aec98a..033d0ce 100644
--- a/qtmips_gui/newdialog.cpp
+++ b/qtmips_gui/newdialog.cpp
@@ -5,32 +5,35 @@
NewDialog::NewDialog(QWidget *parent, QSettings *settings) : QDialog(parent) {
setWindowTitle("New machine");
+ this->settings = settings;
+ config = nullptr;
+
ui = new Ui::NewDialog();
ui->setupUi(this);
ui_cache_p = new Ui::NewDialogCache();
ui_cache_p->setupUi(ui->tab_cache_program);
ui_cache_d = new Ui::NewDialogCache();
ui_cache_d->setupUi(ui->tab_cache_data);
- // TODO setup more? settings and configuration pull
-
- this->settings = settings;
-
- QObject::connect(ui->pushButton_load, SIGNAL(clicked(bool)), this, SLOT(create()));
- QObject::connect(ui->pushButton_cancel, SIGNAL(clicked(bool)), this, SLOT(cancel()));
- // Signals on Base tab
- QObject::connect(ui->preset_no_pipeline, SIGNAL(toggled(bool)), this, SLOT(preset(bool)));
- QObject::connect(ui->preset_pipelined, SIGNAL(toggled(bool)), this, SLOT(preset(bool)));
- QObject::connect(ui->pushButton_browse, SIGNAL(clicked(bool)), this, SLOT(browse_elf()));
-#define CUSTOM_PRESET(UI) QObject::connect(UI, SIGNAL(clicked(bool)), this, SLOT(set_custom_preset()))
- // Signals on Core tab
- CUSTOM_PRESET(ui->pipelined);
- // Signals on Memory tab
- CUSTOM_PRESET(ui->mem_protec_write);
- CUSTOM_PRESET(ui->mem_protec_exec);
-#undef CUSTOM_PRESET
- // Load setting after signals are configured so that we can have correct settings
- load_settings();
+ connect(ui->pushButton_load, SIGNAL(clicked(bool)), this, SLOT(create()));
+ connect(ui->pushButton_cancel, SIGNAL(clicked(bool)), this, SLOT(cancel()));
+ connect(ui->pushButton_browse, SIGNAL(clicked(bool)), this, SLOT(browse_elf()));
+ //connect(ui->preset_box, SIGNAL(clicked(bool)), this, SLOT(set_preset()));
+ connect(ui->preset_no_pipeline, SIGNAL(toggled(bool)), this, SLOT(set_preset()));
+ connect(ui->preset_pipelined, SIGNAL(toggled(bool)), this, SLOT(set_preset()));
+
+ connect(ui->pipelined, SIGNAL(clicked(bool)), this, SLOT(pipelined_change(bool)));
+ connect(ui->delay_slot, SIGNAL(clicked(bool)), this, SLOT(delay_slot_change(bool)));
+ connect(ui->hazard_unit, SIGNAL(clicked(bool)), this, SLOT(hazard_unit_change()));
+ connect(ui->hazard_stall, SIGNAL(clicked(bool)), this, SLOT(hazard_unit_change()));
+ connect(ui->hazard_stall_forward, SIGNAL(clicked(bool)), this, SLOT(hazard_unit_change()));
+ connect(ui->mem_protec_exec, SIGNAL(clicked(bool)), this, SIGNAL(mem_protec_exec_change(bool)));
+ connect(ui->mem_protec_write, SIGNAL(clicked(bool)), this, SLOT(mem_protec_write_change(bool)));
+
+ connect(ui_cache_p->enabled, SIGNAL(clicked(bool)), this, SLOT(cache_program_change(bool)));
+ connect(ui_cache_d->enabled, SIGNAL(clicked(bool)), this, SLOT(cache_data_change(bool)));
+
+ load_settings(); // Also configures gui
}
NewDialog::~NewDialog() {
@@ -38,6 +41,7 @@ NewDialog::~NewDialog() {
delete ui_cache_p;
delete ui;
// Settings is freed by parent
+ delete config;
}
void NewDialog::closeEvent(QCloseEvent *) {
@@ -55,13 +59,8 @@ void NewDialog::cancel() {
void NewDialog::create() {
MainWindow *prnt = (MainWindow*)parent();
- machine::MachineConfig mc;
- mc.set_elf(ui->elf_file->text());
- mc.set_pipelined(ui->pipelined->isChecked());
- // TODO other settings
-
try {
- prnt->create_core(mc);
+ prnt->create_core(*config);
} catch (const machine::QtMipsExceptionInput &e) {
QMessageBox msg(this);
msg.setText(e.msg(false));
@@ -80,54 +79,119 @@ void NewDialog::create() {
void NewDialog::browse_elf() {
QFileDialog elf_dialog(this);
elf_dialog.setFileMode(QFileDialog::ExistingFile);
- if (elf_dialog.exec())
- ui->elf_file->setText(elf_dialog.selectedFiles()[0]);
+ if (elf_dialog.exec()) {
+ QString path = elf_dialog.selectedFiles()[0];
+ ui->elf_file->setText(path);
+ config->set_elf(path);
+ }
+ // Elf shouldn't have any other effect so we skip config_gui here
+}
+
+void NewDialog::set_preset() {
+ if (ui->preset_no_pipeline->isChecked())
+ config->preset(machine::CP_SINGLE);
+ else if (ui->preset_pipelined->isChecked())
+ config->preset(machine::CP_PIPE_WITH_CACHE);
+ else
+ // Skip apply configuration as we changed nothing.
+ return;
+ config_gui();
+}
+
+// Common end section of *_change slots
+#define CHANGE_COMMON do { \
+ ui->preset_custom->setChecked(true); \
+ config_gui(); \
+ } while(false)
+
+void NewDialog::pipelined_change(bool val) {
+ config->set_pipelined(val);
+ CHANGE_COMMON;
+}
+
+void NewDialog::delay_slot_change(bool val) {
+ config->set_delay_slot(val);
+ CHANGE_COMMON;
}
-void NewDialog::preset(bool value) {
- if (value) {
- bool pip = ui->preset_pipelined->isChecked();
- // Core settings
- ui->pipelined->setChecked(pip);
- // Memory settings
- ui->mem_protec_write->setChecked(true);
- ui->mem_protec_exec->setChecked(true);
- } // Else custom so do no changes
+void NewDialog::hazard_unit_change() {
+ if (ui->hazard_unit->isChecked())
+ config->set_hazard_unit(ui->hazard_stall->isChecked() ? machine::MachineConfig::HU_STALL : machine::MachineConfig::HU_STALL_FORWARD);
+ else
+ config->set_hazard_unit(machine::MachineConfig::HU_NONE);
+ CHANGE_COMMON;
}
-void NewDialog::set_custom_preset() {
- ui->preset_custom->setChecked(true);
+void NewDialog::mem_protec_exec_change(bool v) {
+ config->set_memory_execute_protection(v);
+ CHANGE_COMMON;
}
-#define LOAD_BUTTON(NAME, DEF) ui->NAME->setChecked(settings->value(#NAME, DEF).toBool())
-#define LOAD_LINE(NAME, DEF) ui->NAME->setText(settings->value(#NAME, DEF).toString())
+void NewDialog::mem_protec_write_change(bool v) {
+ config->set_memory_write_protection(v);
+ CHANGE_COMMON;
+}
-#define STORE_BUTTON(NAME) settings->setValue(#NAME, ui->NAME->isChecked())
-#define STORE_LINE(NAME) settings->setValue(#NAME, ui->NAME->text())
+void NewDialog::cache_data_change(bool v) {
+ config->access_cache_data()->set_enabled(v);
+ CHANGE_COMMON;
+}
+
+void NewDialog::cache_program_change(bool v) {
+ config->access_cache_program()->set_enabled(v);
+ CHANGE_COMMON;
+}
+
+void NewDialog::config_gui() {
+ // Set values
+ ui->elf_file->setText(config->elf());
+ ui->pipelined->setChecked(config->pipelined());
+ ui->delay_slot->setChecked(config->delay_slot());
+ ui->hazard_unit->setChecked(config->hazard_unit() != machine::MachineConfig::HU_NONE);
+ ui->hazard_stall->setChecked(config->hazard_unit() == machine::MachineConfig::HU_STALL);
+ // ui->hazard_stall_forward is configured automatically according to box exclusivity
+ ui->mem_protec_exec->setChecked(config->memory_execute_protection());
+ ui->mem_protec_write->setChecked(config->memory_write_protection());
+ ui->mem_time_read->setValue(config->memory_access_time_read());
+ ui->mem_time_write->setValue(config->memory_access_time_write());
+ ui_cache_p->enabled->setChecked(config->cache_program().enabled());
+ ui_cache_d->enabled->setChecked(config->cache_data().enabled());
+ // Disable various sections according to configuration
+ ui->delay_slot->setEnabled(!config->pipelined());
+ ui->hazard_unit->setEnabled(config->pipelined());
+}
void NewDialog::load_settings() {
- // Core tab
- LOAD_BUTTON(pipelined, false);
- // Memory tab
- LOAD_BUTTON(mem_protec_write, true);
- LOAD_BUTTON(mem_protec_exec, true);
- // Base tab
- // We are doing this last so presets can reset previous configuration to somethin valid
- LOAD_BUTTON(preset_no_pipeline, true);
- LOAD_BUTTON(preset_pipelined, false);
- LOAD_BUTTON(preset_custom, false);
- LOAD_LINE(elf_file, "");
+ if (config != nullptr)
+ delete config;
+
+ // Load config
+ config = new machine::MachineConfig(settings);
+
+ // Load preset
+ unsigned preset = settings->value("Preset", 1).toUInt();
+ if (preset != 0) {
+ enum machine::ConfigPresets p = (enum machine::ConfigPresets)(preset - 1);
+ config->preset(p);
+ switch (p) {
+ case machine::CP_SINGLE:
+ ui->preset_no_pipeline->setChecked(true);
+ break;
+ case machine::CP_PIPE_WITH_CACHE:
+ ui->preset_pipelined->setChecked(true);
+ break;
+ }
+ } else
+ ui->preset_custom->setChecked(true);
+
+ config_gui();
}
void NewDialog::store_settings() {
- // Core tab
- STORE_BUTTON(pipelined);
- // Memory tab
- STORE_BUTTON(mem_protec_write);
- STORE_BUTTON(mem_protec_exec);
- // Base tab
- STORE_BUTTON(preset_no_pipeline);
- STORE_BUTTON(preset_pipelined);
- STORE_BUTTON(preset_custom);
- STORE_LINE(elf_file);
+ config->store(settings);
+
+ if (ui->preset_custom->isChecked())
+ settings->setValue("Preset", 0);
+ else
+ settings->setValue("Preset", ui->preset_no_pipeline->isChecked() ? machine::CP_SINGLE + 1 : machine::CP_PIPE_WITH_CACHE + 1);
}
diff --git a/qtmips_gui/newdialog.h b/qtmips_gui/newdialog.h
index a088777..5b50a41 100644
--- a/qtmips_gui/newdialog.h
+++ b/qtmips_gui/newdialog.h
@@ -7,6 +7,7 @@
#include <QMessageBox>
#include "ui_NewDialog.h"
#include "ui_NewDialogCache.h"
+#include "machineconfig.h"
class NewDialog : public QDialog {
Q_OBJECT
@@ -21,14 +22,24 @@ private slots:
void cancel();
void create();
void browse_elf();
- void preset(bool);
- void set_custom_preset();
+ void set_preset();
+ void pipelined_change(bool);
+ void delay_slot_change(bool);
+ void hazard_unit_change();
+ void mem_protec_exec_change(bool);
+ void mem_protec_write_change(bool);
+
+ void cache_data_change(bool);
+ void cache_program_change(bool);
private:
Ui::NewDialog *ui;
Ui::NewDialogCache *ui_cache_p, *ui_cache_d;
QSettings *settings;
+ machine::MachineConfig *config;
+ void config_gui(); // Apply configuration to gui
+
void load_settings();
void store_settings();
};