summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorbd <bdunahu@operationnull.com>2025-05-11 19:40:47 -0400
committerbd <bdunahu@operationnull.com>2025-05-11 19:40:47 -0400
commitc9d4b54150b67e1701a920719ba2c7c03d897d27 (patch)
tree9c4c19ff4b0f7eb53bfae632437eff3a0a42d5e3 /src
parent79a68cabb033530871a1dab259149480584b2586 (diff)
Stride load, stride store
Diffstat (limited to 'src')
-rw-r--r--src/ex.cc33
-rw-r--r--src/id.cc8
-rw-r--r--src/mm.cc64
-rw-r--r--src/wb.cc13
4 files changed, 90 insertions, 28 deletions
diff --git a/src/ex.cc b/src/ex.cc
index cd00254..22cd092 100644
--- a/src/ex.cc
+++ b/src/ex.cc
@@ -240,13 +240,25 @@ void EX::handle_vector_operations(
this->set_condition(UF, underflow);
}
-void EX::handle_s_vector_operations(signed int &s1, signed int s2, Mnemonic m)
+void EX::handle_s_vector_operations(
+ std::array<signed int, V_R_LIMIT> &s1,
+ signed int s2,
+ Mnemonic m,
+ unsigned int v_len)
{
+ unsigned int i, inc1, inc2;
+
switch (m) {
- // case SRDL:
- // case SRDS:
- // s1 = s1 + s2;
- // break;
+ case SRDL:
+ case SRDS:
+ inc1 = s1[0];
+ s1[0] = s2;
+ for (i = 1; i < v_len; ++i) {
+ inc2 = s1[i];
+ s1[i] = s1[i - 1] + inc1;
+ inc1 = inc2;
+ }
+ break;
default:
throw std::invalid_argument("handle_s_vector_operations did not "
@@ -270,11 +282,12 @@ void EX::advance_helper()
handle_vector_operations(
this->curr_instr->operands.vector.slot_one,
this->curr_instr->operands.vector.slot_two, m, v_len_or_pc);
- }// else {
- // handle_s_vector_operations(
- // this->curr_instr->operands.s_vector.slot_one,
- // this->curr_instr->operands.s_vector.slot_two, m);
- // }
+ } else {
+ handle_s_vector_operations(
+ this->curr_instr->operands.s_vector.slot_one,
+ this->curr_instr->operands.s_vector.slot_two, m, v_len_or_pc);
+ printArray(this->curr_instr->operands.s_vector.slot_three);
+ }
this->status = OK;
}
diff --git a/src/id.cc b/src/id.cc
index 12f509f..9547486 100644
--- a/src/id.cc
+++ b/src/id.cc
@@ -135,10 +135,16 @@ void ID::decode_R_type(signed int &s1)
this->write_guard<std::array<signed int, V_R_LIMIT>>(s3);
break;
case SRDL:
- case SRDS:
this->curr_instr->operands.s_vector.slot_three =
this->write_guard<std::array<signed int, V_R_LIMIT>>(s3);
break;
+ case SRDS:
+ r1 = this->read_guard<std::array<signed int, V_R_LIMIT>>(
+ s3, this->curr_instr->operands.s_vector.slot_three);
+ if (r1 != OK) {
+ this->status = STALLED;
+ }
+ break;
default:
this->curr_instr->operands.integer.slot_three =
this->write_guard<signed int>(s3);
diff --git a/src/mm.cc b/src/mm.cc
index ac77433..63ee16a 100644
--- a/src/mm.cc
+++ b/src/mm.cc
@@ -25,15 +25,30 @@ void MM::advance_helper()
signed int data;
int i;
+ this->try_start();
+ if (this->status == OK) {
+ return;
+ }
+
switch (this->curr_instr->mnemonic) {
case LOAD:
i = this->storage->read_word(
this, this->curr_instr->operands.integer.slot_one, data);
- this->status = i ? OK : STALLED;
- if (this->status == OK) {
+ if (i) {
this->curr_instr->operands.integer.slot_one = data;
- } else
- this->status = STALLED;
+ }
+ this->try_finish(i);
+ break;
+ case SRDL:
+ i = this->storage->read_word(
+ this,
+ this->curr_instr->operands.s_vector.slot_one[this->curr_element],
+ data);
+ if (i) {
+ this->curr_instr->operands.s_vector.slot_one[this->curr_element] =
+ data;
+ }
+ this->try_finish(i);
break;
case PUSH:
@@ -41,22 +56,47 @@ void MM::advance_helper()
i = this->storage->write_word(
this, this->curr_instr->operands.integer.slot_two,
this->curr_instr->operands.integer.slot_one);
- this->status = i ? OK : STALLED;
- if (this->status != OK) {
- this->status = STALLED;
- }
+ this->try_finish(i);
+ break;
+ case SRDS:
+ i = this->storage->write_word(
+ this,
+ this->curr_instr->operands.s_vector.slot_three[this->curr_element],
+ this->curr_instr->operands.s_vector.slot_one[this->curr_element]);
+ this->try_finish(i);
break;
case POP:
- i = this->storage->read_word(this, this->curr_instr->operands.integer.slot_three, data);
+ i = this->storage->read_word(
+ this, this->curr_instr->operands.integer.slot_three, data);
this->status = i ? OK : STALLED;
- if (this->status == OK) {
+ if (i) {
this->curr_instr->operands.integer.slot_three = data;
- } else
- this->status = STALLED;
+ }
break;
default:
this->status = OK;
}
}
+
+void MM::try_start()
+{
+ if (this->curr_instr->type != SI_INT) {
+ this->status =
+ (this->curr_element >= this->curr_instr->slot_B) ? OK : STALLED;
+ }
+ if (this->status == OK)
+ this->curr_element = 0;
+}
+
+void MM::try_finish(int response)
+{
+ if (this->curr_instr->type == SI_INT) {
+ this->status = response ? OK : STALLED;
+ } else {
+ if (response) {
+ ++this->curr_element;
+ }
+ }
+}
diff --git a/src/wb.cc b/src/wb.cc
index fc714ad..89ee298 100644
--- a/src/wb.cc
+++ b/src/wb.cc
@@ -58,15 +58,11 @@ void WB::write_handler()
this->store_register<signed int>(
reg, this->curr_instr->operands.integer.slot_one);
break;
+ case S_VECT:
case R_VECT:
this->store_register<std::array<signed int, V_R_LIMIT>>(
reg, this->copy_extra_vector_elements());
break;
- // case S_VECT:
- // this->store_register<std::array<signed int, V_R_LIMIT>>(
- // reg, this->curr_instr->operands.s_vector.slot_three);
- // // todo, use copy_extra_vector_elements
- // break;
}
}
@@ -97,6 +93,13 @@ std::array<signed int, V_R_LIMIT> WB::copy_extra_vector_elements()
int i;
std::array<signed int, V_R_LIMIT> v;
+ if (this->curr_instr->type == S_VECT) {
+ if (this->curr_instr->slot_B == 0) {
+ v = {0};
+ return v;
+ }
+ }
+
v = this->curr_instr->operands.vector.slot_one;
for (i = V_R_LIMIT - 1; i >= this->curr_instr->slot_B; --i) {
v[i] = this->curr_instr->operands.vector.slot_three[i];