From 939e23883eea11c08b61375b7c70b8c70ba67451 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fran=C3=A7ois=20Autin?= Date: Mon, 27 Mar 2023 11:22:53 +0200 Subject: [PATCH] :recycle: Simplified OPI --- src/simulator/machine.rs | 36 +++++++++++++++++++++--------------- 1 file changed, 21 insertions(+), 15 deletions(-) diff --git a/src/simulator/machine.rs b/src/simulator/machine.rs index 56224ea..2048455 100644 --- a/src/simulator/machine.rs +++ b/src/simulator/machine.rs @@ -13,7 +13,7 @@ use std::{ io::Write, - fs::File + fs::File, ops::Add }; use crate::simulator::{ print, @@ -381,21 +381,27 @@ impl Machine { /// Executes RISC-V Integer Register-Immediate Instructions on the machine fn opi_instruction(&mut self, inst: Instruction) -> Result<(), MachineError> { + let mut compute = |operation: &dyn Fn (i64, i64) -> i64| { + self.int_reg.set_reg(inst.rd, operation(self.int_reg.get_reg(inst.rs1), inst.imm12_I_signed as i64)); + Ok(()) + }; match inst.funct3 { - RISCV_OPI_ADDI => self.int_reg.set_reg(inst.rd, self.int_reg.get_reg(inst.rs1) + inst.imm12_I_signed as i64), - RISCV_OPI_SLTI => self.int_reg.set_reg(inst.rd, (self.int_reg.get_reg(inst.rs1) < inst.imm12_I_signed as i64) as i64), - RISCV_OPI_XORI => self.int_reg.set_reg(inst.rd, self.int_reg.get_reg(inst.rs1) ^ inst.imm12_I_signed as i64), - RISCV_OPI_ORI => self.int_reg.set_reg(inst.rd, self.int_reg.get_reg(inst.rs1) | inst.imm12_I_signed as i64), - RISCV_OPI_ANDI => self.int_reg.set_reg(inst.rd, self.int_reg.get_reg(inst.rs1) & inst.imm12_I_signed as i64), - RISCV_OPI_SLLI => self.int_reg.set_reg(inst.rd, self.int_reg.get_reg(inst.rs1) << inst.shamt), - RISCV_OPI_SRI => if inst.funct7_smaller == RISCV_OPI_SRI_SRLI { - self.int_reg.set_reg(inst.rd, (self.int_reg.get_reg(inst.rs1) >> inst.shamt) & self.shiftmask[inst.shamt as usize] as i64); - } else { // SRAI - self.int_reg.set_reg(inst.rd, self.int_reg.get_reg(inst.rs1) >> inst.shamt); - }, - _ => panic!("In OPI switch case, this should never happen... Instr was %x\n {}", inst.value) + RISCV_OPI_ADDI => compute(&std::ops::Add::add), + RISCV_OPI_SLTI => compute(&|a, b| { (a < b) as i64 }), + RISCV_OPI_XORI => compute(&|a, b| { a ^ b }), + RISCV_OPI_ORI => compute(&|a, b| { a | b }), + RISCV_OPI_ANDI => compute(&|a, b| { a & b }), + RISCV_OPI_SLLI => compute(&|a, b| { a << b }), + RISCV_OPI_SRI => { + if inst.funct7_smaller == RISCV_OPI_SRI_SRLI { + self.int_reg.set_reg(inst.rd, (self.int_reg.get_reg(inst.rs1) >> inst.shamt) & self.shiftmask[inst.shamt as usize] as i64) + } else { // SRAI + self.int_reg.set_reg(inst.rd, self.int_reg.get_reg(inst.rs1) >> inst.shamt) + } + Ok(()) + } + _ => Err(MachineError::new(format!("In OPI switch case, this should never happen... Instr was %x\n {}", inst.value).as_str())) } - Ok(()) } /// Executes simple RISC-V mathematical operations on the machine @@ -517,7 +523,7 @@ impl Machine { } else { // SRAW self.int_reg.set_reg(inst.rd, local_dataa >> (local_datab & 0x1f)) }, - _ => panic!("this instruction ({}) doesn't exists", inst.value) + _ => panic!("this instruction ({}) doesn't exist", inst.value) } } Ok(())