Fix bugs in all base instructions and make RISCOF tests pass

This commit is contained in:
Konstantin Nazarov 2024-12-16 22:16:31 +00:00
parent 40179ed237
commit 3888a0d65a
Signed by: knazarov
GPG key ID: 4CFE0A42FA409C22
3 changed files with 21 additions and 14 deletions

View file

@ -58,7 +58,7 @@ int main(int argc, char *argv[]) {
}
if (signature_filename.size() > 0) {
uint32_t signature_begin = std::get<0>(signature) + 4;
uint32_t signature_begin = std::get<0>(signature);
uint32_t signature_end = std::get<1>(signature);
std::vector<uint8_t> mem =

View file

@ -199,8 +199,8 @@ void VM::step() {
} else if (funct3 == 0x02) { // SLT
setreg(rd, (static_cast<int32_t>(registers[rs1]) <
static_cast<int32_t>(registers[rs2]))
? 0
: 1);
? 1
: 0);
} else if (funct3 == 0x03) { // SLTU
setreg(rd, (registers[rs1] < registers[rs2]) ? 1 : 0);
} else {
@ -294,7 +294,7 @@ void VM::step() {
}
} else if (funct3 == 0x05) {
if (((imm >> 5) & 0x7f) == 0x20) { // SRAI
int32_t value = static_cast<int32_t>(imm & 0x1f);
int32_t value = registers[rs1];
int32_t shift_amount = imm & 0x1F;
setreg(rd, value >> shift_amount);
} else if (((imm >> 5) & 0x7f) == 0x0) { // SRLI
@ -307,8 +307,8 @@ void VM::step() {
} else if (funct3 == 0x02) { // SLTI
setreg(rd, (static_cast<int32_t>(registers[rs1]) <
static_cast<int32_t>(imm))
? 0
: 1);
? 1
: 0);
} else if (funct3 == 0x03) { // SLTIU
setreg(rd, (registers[rs1] < static_cast<uint32_t>(imm)) ? 1 : 0);
} else {
@ -353,10 +353,10 @@ void VM::step() {
imm = sign_extend(instr >> 20, 12); // Extract 12-bit immediate
if (funct3 == 0x00) { // LB
uint32_t addr = registers[rs1] + imm;
setreg(rd, read_memory_byte(addr));
setreg(rd, sign_extend(read_memory_byte(addr), 8));
} else if (funct3 == 0x01) { // LH
uint32_t addr = registers[rs1] + imm;
setreg(rd, read_memory_half_word(addr));
setreg(rd, sign_extend(read_memory_half_word(addr), 16));
} else if (funct3 == 0x2) { // LW
uint32_t addr = registers[rs1] + imm;
setreg(rd, read_memory_word(addr));
@ -401,7 +401,8 @@ void VM::step() {
break;
}
case 0x67: { // JALR
int32_t offset = (instr >> 20); // Sign-extended 12-bit immediate
int32_t offset =
sign_extend(instr >> 20, 12); // Sign-extended 12-bit immediate
uint32_t target =
(registers[rs1] + offset) & ~1; // Target address (LSB cleared)
@ -423,10 +424,15 @@ void VM::step() {
// the current PC
break;
}
case 0x73: { // EBREAK
case 0x73: {
imm = sign_extend(instr >> 20, 12); // Extract 12-bit immediate
if (funct3 == 0x0 && imm == 0x1) { // EBREAK
pc -= 4;
throw EbreakException();
break;
} else {
throw std::runtime_error("Unknown opcode");
}
}
default:
throw std::runtime_error("Unknown opcode");

View file

@ -4,6 +4,7 @@ hart0:
physical_addr_sz: 32
User_Spec_Version: '2.3'
supported_xlen: [32]
hw_data_misaligned_support: false
misa:
# reset-val encodes the CPU capabilities in a special register,
# as specified in https://five-embeddev.com/riscv-priv-isa-manual/Priv-v1.12/machine.html