Skip to main content

ab_riscv_interpreter/rv64/b/
zbc.rs

1//! RV64 Zbc extension
2
3pub mod rv64_zbc_helpers;
4#[cfg(test)]
5mod tests;
6
7use crate::{
8    ExecutableInstruction, ExecutableInstructionCsr, ExecutableInstructionOperands, ExecutionError,
9    RegisterFile, Rs1Rs2OperandValues, Rs1Rs2Operands,
10};
11use ab_riscv_macros::instruction_execution;
12use ab_riscv_primitives::prelude::*;
13use core::ops::ControlFlow;
14
15#[instruction_execution]
16impl<Reg> ExecutableInstructionOperands for Rv64ZbcInstruction<Reg> where Reg: Register<Type = u64> {}
17
18#[instruction_execution]
19impl<Reg, ExtState, CustomError> ExecutableInstructionCsr<ExtState, CustomError>
20    for Rv64ZbcInstruction<Reg>
21where
22    Reg: Register<Type = u64>,
23{
24}
25
26#[instruction_execution]
27impl<Reg, Regs, ExtState, Memory, PC, InstructionHandler, CustomError>
28    ExecutableInstruction<Regs, ExtState, Memory, PC, InstructionHandler, CustomError>
29    for Rv64ZbcInstruction<Reg>
30where
31    Reg: Register<Type = u64>,
32    Regs: RegisterFile<Reg>,
33{
34    #[inline(always)]
35    fn execute(
36        self,
37        Rs1Rs2OperandValues {
38            rs1_value,
39            rs2_value,
40        }: Rs1Rs2OperandValues<<Self::Reg as Register>::Type>,
41        _regs: &mut Regs,
42        _ext_state: &mut ExtState,
43        _memory: &mut Memory,
44        _program_counter: &mut PC,
45        _system_instruction_handler: &mut InstructionHandler,
46    ) -> Result<
47        ControlFlow<(), (Self::Reg, <Self::Reg as Register>::Type)>,
48        ExecutionError<Reg::Type, CustomError>,
49    > {
50        match self {
51            Self::Clmul { rd, rs1: _, rs2: _ } => {
52                let a = rs1_value;
53                let b = rs2_value;
54
55                Ok(ControlFlow::Continue((rd, rv64_zbc_helpers::clmul(a, b))))
56            }
57            Self::Clmulh { rd, rs1: _, rs2: _ } => {
58                let a = rs1_value;
59                let b = rs2_value;
60
61                Ok(ControlFlow::Continue((rd, rv64_zbc_helpers::clmulh(a, b))))
62            }
63            Self::Clmulr { rd, rs1: _, rs2: _ } => {
64                let a = rs1_value;
65                let b = rs2_value;
66
67                Ok(ControlFlow::Continue((rd, rv64_zbc_helpers::clmulr(a, b))))
68            }
69        }
70    }
71}