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) { 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); uint32_t signature_end = std::get<1>(signature);
std::vector<uint8_t> mem = std::vector<uint8_t> mem =

View file

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

View file

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