riscv_etrace/instruction/
decode.rs1use crate::config::Parameters;
6
7use super::bits::Bits;
8use super::info::Info;
9
10pub trait Decode<I: Info> {
12 fn decode_16(&self, insn: u16) -> I;
14
15 fn decode_32(&self, insn: u32) -> I;
17
18 fn decode_48(&self, insn: u64) -> I;
20
21 fn decode_64(&self, insn: u64) -> I;
23
24 fn decode_bits(&self, bits: Bits) -> I {
26 match bits {
27 Bits::Bit16(bits) => self.decode_16(bits),
28 Bits::Bit32(bits) => self.decode_32(bits),
29 Bits::Bit48(bits) => self.decode_48(bits),
30 Bits::Bit64(bits) => self.decode_64(bits),
31 }
32 }
33}
34
35impl<D, I> Decode<(I, Bits)> for D
36where
37 D: Decode<I>,
38 I: Info,
39 (I, Bits): Info,
40{
41 fn decode_16(&self, insn: u16) -> (I, Bits) {
42 (self.decode_16(insn), Bits::Bit16(insn))
43 }
44
45 fn decode_32(&self, insn: u32) -> (I, Bits) {
46 (self.decode_32(insn), Bits::Bit32(insn))
47 }
48
49 fn decode_48(&self, insn: u64) -> (I, Bits) {
50 (self.decode_48(insn), Bits::Bit48(insn))
51 }
52
53 fn decode_64(&self, insn: u64) -> (I, Bits) {
54 (self.decode_64(insn), Bits::Bit64(insn))
55 }
56}
57
58#[cfg(feature = "riscv-isa")]
59impl Decode<riscv_isa::Instruction> for riscv_isa::Target {
60 fn decode_16(&self, insn: u16) -> riscv_isa::Instruction {
61 use riscv_isa::Compressed;
62
63 match riscv_isa::decode_compressed(insn, self) {
66 Compressed::C_LUI { rd: 0, .. } => Compressed::UNIMP,
67 Compressed::C_JR { rs1: 0, .. } => Compressed::UNIMP,
68 Compressed::C_JALR { rs1: 0, .. } => Compressed::UNIMP,
69 insn => insn,
70 }
71 .into()
72 }
73
74 fn decode_32(&self, insn: u32) -> riscv_isa::Instruction {
75 riscv_isa::decode_full(insn, self)
76 }
77
78 fn decode_48(&self, _insn: u64) -> riscv_isa::Instruction {
79 riscv_isa::Instruction::UNIMP
80 }
81
82 fn decode_64(&self, _insn: u64) -> riscv_isa::Instruction {
83 riscv_isa::Instruction::UNIMP
84 }
85}
86
87#[cfg(feature = "riscv-isa")]
88impl Decode<riscv_isa::Compressed> for riscv_isa::Target {
89 fn decode_16(&self, insn: u16) -> riscv_isa::Compressed {
90 use riscv_isa::Compressed;
91
92 match riscv_isa::decode_compressed(insn, self) {
95 Compressed::C_LUI { rd: 0, .. } => Compressed::UNIMP,
96 Compressed::C_JR { rs1: 0, .. } => Compressed::UNIMP,
97 Compressed::C_JALR { rs1: 0, .. } => Compressed::UNIMP,
98 insn => insn,
99 }
100 }
101
102 fn decode_32(&self, _insn: u32) -> riscv_isa::Compressed {
103 riscv_isa::Compressed::UNIMP
104 }
105
106 fn decode_48(&self, _insn: u64) -> riscv_isa::Compressed {
107 riscv_isa::Compressed::UNIMP
108 }
109
110 fn decode_64(&self, _insn: u64) -> riscv_isa::Compressed {
111 riscv_isa::Compressed::UNIMP
112 }
113}
114
115#[cfg(all(feature = "either", feature = "riscv-isa"))]
116impl Decode<either::Either<riscv_isa::Compressed, riscv_isa::Instruction>> for riscv_isa::Target {
117 fn decode_16(
118 &self,
119 insn: u16,
120 ) -> either::Either<riscv_isa::Compressed, riscv_isa::Instruction> {
121 either::Left(self.decode_16(insn))
122 }
123
124 fn decode_32(
125 &self,
126 insn: u32,
127 ) -> either::Either<riscv_isa::Compressed, riscv_isa::Instruction> {
128 either::Right(self.decode_32(insn))
129 }
130
131 fn decode_48(
132 &self,
133 insn: u64,
134 ) -> either::Either<riscv_isa::Compressed, riscv_isa::Instruction> {
135 either::Right(self.decode_48(insn))
136 }
137
138 fn decode_64(
139 &self,
140 insn: u64,
141 ) -> either::Either<riscv_isa::Compressed, riscv_isa::Instruction> {
142 either::Right(self.decode_64(insn))
143 }
144}
145
146pub trait MakeDecode {
151 fn rv32i_full() -> Self;
157
158 fn rv64i_full() -> Self;
164
165 fn infer_from_params(params: &Parameters) -> Option<Self>
171 where
172 Self: Sized,
173 {
174 match params.iaddress_width_p.get() {
175 0..=32 => Some(Self::rv32i_full()),
176 33..=64 => Some(Self::rv64i_full()),
177 _ => None,
178 }
179 }
180}
181
182#[cfg(feature = "riscv-isa")]
183impl MakeDecode for riscv_isa::Target {
184 fn rv32i_full() -> Self {
185 Self {
186 xlen: riscv_isa::Xlen::Rv32,
187 privileged: true,
188 supervisor_mode: true,
189 m: true,
190 a: true,
191 f: true,
192 d: true,
193 q: true,
194 c: true,
195 zicsr: true,
196 zifencei: true,
197 zawrs: true,
198 zfh: true,
199 zba: true,
200 zbb: true,
201 zbc: true,
202 zbkb: true,
203 zbs: true,
204 }
205 }
206
207 fn rv64i_full() -> Self {
208 Self {
209 xlen: riscv_isa::Xlen::Rv64,
210 privileged: true,
211 supervisor_mode: true,
212 m: true,
213 a: true,
214 f: true,
215 d: true,
216 q: true,
217 c: true,
218 zicsr: true,
219 zifencei: true,
220 zawrs: true,
221 zfh: true,
222 zba: true,
223 zbb: true,
224 zbc: true,
225 zbkb: true,
226 zbs: true,
227 }
228 }
229}