misc: back to little endian because I am evil

This commit is contained in:
2025-06-17 19:51:16 +01:00
parent 0b16246dd2
commit 3a40719e54
4 changed files with 63 additions and 35 deletions
+1 -1
View File
@@ -17,6 +17,6 @@ fn main() {
.iter() .iter()
.map(|i| i.encode()) .map(|i| i.encode())
.for_each(|i| { .for_each(|i| {
output_file.write_all(&i.to_be_bytes()).unwrap(); output_file.write_all(&i.to_le_bytes()).unwrap();
}); });
} }
+1 -1
View File
@@ -78,7 +78,7 @@ impl MemoryUnit for MainStore {
bytes[1] = block.data[(offset + 1) as usize]; bytes[1] = block.data[(offset + 1) as usize];
bytes[2] = block.data[(offset + 2) as usize]; bytes[2] = block.data[(offset + 2) as usize];
bytes[3] = block.data[(offset + 3) as usize]; bytes[3] = block.data[(offset + 3) as usize];
u32::from_be_bytes(bytes) u32::from_le_bytes(bytes)
} }
fn read_range(&mut self, addr: u32, size: u32) -> Vec<u8> { fn read_range(&mut self, addr: u32, size: u32) -> Vec<u8> {
+60 -32
View File
@@ -8,7 +8,9 @@ use crate::emulator::system::{
model::{IODevice, RegFile}, model::{IODevice, RegFile},
}; };
use common::instructions::{Instruction, Interrupt, Register, errors::InstructionDecodeError}; use common::instructions::{
Instruction, Interrupt, Register, errors::InstructionDecodeError,
};
pub struct Processor { pub struct Processor {
pub memory: Box<dyn MemoryUnit>, pub memory: Box<dyn MemoryUnit>,
@@ -168,71 +170,90 @@ impl Executable for Instruction {
*cpu.reg(a.dr) = cpu.get(a.sr1); *cpu.reg(a.dr) = cpu.get(a.sr1);
} }
// Copies from SrcReg to a.drReg, sign extending the value to take up a full word. // Copies from SrcReg to a.drReg, sign extending the value to take up a full
// word.
Self::MovSigned(a) => { Self::MovSigned(a) => {
*cpu.reg(a.dr) = sign_extend(cpu.get(a.sr1)); *cpu.reg(a.dr) = sign_extend(cpu.get(a.sr1));
} }
// Loads a byte from memory address (base + offset) into a.drReg. The effective address must be byte-aligned. // Loads a byte from memory address (base + offset) into a.drReg. The
// effective address must be byte-aligned.
Self::LoadByte(a) => { Self::LoadByte(a) => {
*cpu.reg(a.r2) = *cpu.reg(a.r2) = u32::from(
u32::from(cpu.memory.read_byte(cpu.get(a.r1) + u32::from(a.immediate))); cpu.memory.read_byte(cpu.get(a.r1) + u32::from(a.immediate)),
);
} }
// Loads a sign-extended byte from memory address (base + offset) into a.drReg. The effective address must be byte-aligned. // Loads a sign-extended byte from memory address (base + offset) into
// a.drReg. The effective address must be byte-aligned.
Self::LoadByteSigned(a) => { Self::LoadByteSigned(a) => {
*cpu.reg(a.r2) = sign_extend(u32::from( *cpu.reg(a.r2) = sign_extend(u32::from(
cpu.memory.read_byte(cpu.get(a.r1) + u32::from(a.immediate)), cpu.memory.read_byte(cpu.get(a.r1) + u32::from(a.immediate)),
)); ));
} }
// Loads a half-word from memory address (base + offset) into a.drReg. The effective address must be 2-byte-aligned. // Loads a half-word from memory address (base + offset) into a.drReg. The
// effective address must be 2-byte-aligned.
Self::LoadHalfword(a) => { Self::LoadHalfword(a) => {
// we read an entire word, then right shift so we only get the first half of the word // we read an entire word, then right shift so we only get the first half
*cpu.reg(a.r2) = cpu.memory.read_word(cpu.get(a.r1) + u32::from(a.immediate)) >> 16; // of the word
}
// Loads a sign-extended half-word from memory address (base + offset) into a.drReg. The effective address must be 2-byte-aligned.
Self::LoadHalfwordSigned(a) => {
*cpu.reg(a.r2) = *cpu.reg(a.r2) =
sign_extend(cpu.memory.read_word(cpu.get(a.r1) + u32::from(a.immediate)) >> 16); cpu.memory.read_word(cpu.get(a.r1) + u32::from(a.immediate)) >> 16;
} }
// Loads a word from memory address (base + offset) into a.drReg. The effective address must be 4-byte-aligned. // Loads a sign-extended half-word from memory address (base + offset) into
// a.drReg. The effective address must be 2-byte-aligned.
Self::LoadHalfwordSigned(a) => {
*cpu.reg(a.r2) = sign_extend(
cpu.memory.read_word(cpu.get(a.r1) + u32::from(a.immediate)) >> 16,
);
}
// Loads a word from memory address (base + offset) into a.drReg. The
// effective address must be 4-byte-aligned.
Self::LoadWord(a) => { Self::LoadWord(a) => {
*cpu.reg(a.r2) = cpu.memory.read_word(cpu.get(a.r1) + u32::from(a.immediate)); *cpu.reg(a.r2) =
cpu.memory.read_word(cpu.get(a.r1) + u32::from(a.immediate));
} }
// Stores a byte from SrcReg in memory address (base + offset) The effective address must be byte-aligned. // Stores a byte from SrcReg in memory address (base + offset) The effective
// address must be byte-aligned.
Self::StoreByte(a) => { Self::StoreByte(a) => {
cpu.memory cpu.memory.write_byte(
.write_byte(cpu.get(a.r1) + u32::from(a.immediate), cpu.get(a.r2) as u8); cpu.get(a.r1) + u32::from(a.immediate),
cpu.get(a.r2) as u8,
);
} }
// Stores a half-word from SrcReg in memory address (base + offset) The effective address must be 2-byte-aligned. // Stores a half-word from SrcReg in memory address (base + offset) The
// effective address must be 2-byte-aligned.
Self::StoreHalfword(a) => { Self::StoreHalfword(a) => {
// split the value into bytes and then write two bytes // split the value into bytes and then write two bytes
let bytes = (cpu.get(a.r1) as u16).to_be_bytes(); let bytes = (cpu.get(a.r1) as u16).to_le_bytes();
cpu.memory cpu.memory
.write_byte(cpu.get(a.r1) + u32::from(a.immediate), bytes[0]); .write_byte(cpu.get(a.r1) + u32::from(a.immediate), bytes[0]);
cpu.memory cpu.memory
.write_byte(cpu.get(a.r1) + u32::from(a.immediate) + 1, bytes[1]); .write_byte(cpu.get(a.r1) + u32::from(a.immediate) + 1, bytes[1]);
} }
// Stores a word from SrcReg in memory address (base + offset) The effective address must be 4-byte-aligned. // Stores a word from SrcReg in memory address (base + offset) The effective
// address must be 4-byte-aligned.
Self::StoreWord(a) => { Self::StoreWord(a) => {
cpu.memory cpu.memory
.write_word(cpu.get(a.r1) + u32::from(a.immediate), cpu.get(a.r2)); .write_word(cpu.get(a.r1) + u32::from(a.immediate), cpu.get(a.r2));
} }
// Loads a 16-bit literal value into reg, setting the bottom 16 bits of the word. To populate the upper 16 bits, see LUI. // Loads a 16-bit literal value into reg, setting the bottom 16 bits of the
// word. To populate the upper 16 bits, see LUI.
Self::LoadLowerImmediate(a) => { Self::LoadLowerImmediate(a) => {
*cpu.reg(a.r1) = u32::from(a.immediate); *cpu.reg(a.r1) = u32::from(a.immediate);
} }
// Loads a 16-bit literal value into reg, setting the top 16 bits of the word. To populate the lower 16 bits, see LLI. // Loads a 16-bit literal value into reg, setting the top 16 bits of the word.
// To populate the lower 16 bits, see LLI.
Self::LoadUpperImmediate(a) => { Self::LoadUpperImmediate(a) => {
*cpu.reg(a.r1) = (cpu.get(a.r1) & 0x0000_FFFF) | u32::from(a.immediate) << 16; *cpu.reg(a.r1) =
(cpu.get(a.r1) & 0x0000_FFFF) | u32::from(a.immediate) << 16;
} }
// Unconditionally jumps to the calculated address or direct address // Unconditionally jumps to the calculated address or direct address
@@ -259,7 +280,8 @@ impl Executable for Instruction {
} }
} }
// Jumps to the calculated address or direct address if greater than flag or equal flag set. // Jumps to the calculated address or direct address if greater than flag or
// equal flag set.
Self::JumpGe(a) => { Self::JumpGe(a) => {
if cpu.get_flag(Flag::GreaterThan) || cpu.get_flag(Flag::Equal) { if cpu.get_flag(Flag::GreaterThan) || cpu.get_flag(Flag::Equal) {
cpu.jump(a.r1, a.immediate); cpu.jump(a.r1, a.immediate);
@@ -273,7 +295,8 @@ impl Executable for Instruction {
} }
} }
// Jumps to the calculated address or direct address if less than flag or equal flag set. // Jumps to the calculated address or direct address if less than flag or
// equal flag set.
Self::JumpLe(a) => { Self::JumpLe(a) => {
if cpu.get_flag(Flag::LessThan) || cpu.get_flag(Flag::Equal) { if cpu.get_flag(Flag::LessThan) || cpu.get_flag(Flag::Equal) {
cpu.jump(a.r1, a.immediate); cpu.jump(a.r1, a.immediate);
@@ -286,20 +309,24 @@ impl Executable for Instruction {
// Decrements the value in the given register // Decrements the value in the given register
Self::Decrement(a) => *cpu.reg(a.sr1) = dec(cpu.get(a.sr1)), Self::Decrement(a) => *cpu.reg(a.sr1) = dec(cpu.get(a.sr1)),
// Left shifts the value in Reg by the given amount (either a register, or a literal value) // Left shifts the value in Reg by the given amount (either a register, or a
// literal value)
Self::ShiftLeft(a) => { Self::ShiftLeft(a) => {
let regval = cpu.get(a.sr2); let regval = cpu.get(a.sr2);
let val = cpu.get(a.sr1); let val = cpu.get(a.sr1);
*cpu.reg(a.sr1) = shl(val, if regval != 0 { regval as u8 } else { a.shamt }); *cpu.reg(a.sr1) =
shl(val, if regval != 0 { regval as u8 } else { a.shamt });
} }
// Right shifts the value in Reg by the given amount (either a register, or a literal value). // Right shifts the value in Reg by the given amount (either a register, or a
// literal value).
Self::ShiftRight(a) => { Self::ShiftRight(a) => {
let regval = cpu.get(a.sr2); let regval = cpu.get(a.sr2);
let val = cpu.get(a.sr1); let val = cpu.get(a.sr1);
*cpu.reg(a.sr1) = shr(val, if regval != 0 { regval as u8 } else { a.shamt }); *cpu.reg(a.sr1) =
shr(val, if regval != 0 { regval as u8 } else { a.shamt });
} }
// Adds the value of Src2 to Src1 and writes the result to a.dr // Adds the value of Src2 to Src1 and writes the result to a.dr
@@ -333,7 +360,8 @@ impl Executable for Instruction {
// Performs bitwise XNOR on Src1 and Src2 storing the result in a.dr // Performs bitwise XNOR on Src1 and Src2 storing the result in a.dr
Self::Xnor(a) => *cpu.reg(a.dr) = xnor(cpu.get(a.sr1), cpu.get(a.sr2)), Self::Xnor(a) => *cpu.reg(a.dr) = xnor(cpu.get(a.sr1), cpu.get(a.sr2)),
// Compares the value of Reg1 to the value in Reg2. The results of the comparisons are set in the Status register. // Compares the value of Reg1 to the value in Reg2. The results of the
// comparisons are set in the Status register.
Self::Compare(a) => { Self::Compare(a) => {
cpu.cmp(cpu.get(a.sr1), cpu.get(a.sr2)); cpu.cmp(cpu.get(a.sr1), cpu.get(a.sr2));
} }
+1 -1
View File
@@ -178,7 +178,7 @@ impl Editor {
bytes[i] = byte; bytes[i] = byte;
} }
} }
let value = u32::from_be_bytes(bytes); let value = u32::from_le_bytes(bytes);
// Address column // Address column
ui.with_layout( ui.with_layout(