xref: /qemu/disas/riscv.c (revision ea10325917c8a8f92611025c85950c00f826cb73)
1*ea103259SMichael Clark /*
2*ea103259SMichael Clark  * QEMU RISC-V Disassembler
3*ea103259SMichael Clark  *
4*ea103259SMichael Clark  * Copyright (c) 2016-2017 Michael Clark <michaeljclark@mac.com>
5*ea103259SMichael Clark  * Copyright (c) 2017-2018 SiFive, Inc.
6*ea103259SMichael Clark  *
7*ea103259SMichael Clark  * This program is free software; you can redistribute it and/or modify it
8*ea103259SMichael Clark  * under the terms and conditions of the GNU General Public License,
9*ea103259SMichael Clark  * version 2 or later, as published by the Free Software Foundation.
10*ea103259SMichael Clark  *
11*ea103259SMichael Clark  * This program is distributed in the hope it will be useful, but WITHOUT
12*ea103259SMichael Clark  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13*ea103259SMichael Clark  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14*ea103259SMichael Clark  * more details.
15*ea103259SMichael Clark  *
16*ea103259SMichael Clark  * You should have received a copy of the GNU General Public License along with
17*ea103259SMichael Clark  * this program.  If not, see <http://www.gnu.org/licenses/>.
18*ea103259SMichael Clark  */
19*ea103259SMichael Clark 
20*ea103259SMichael Clark #include "qemu/osdep.h"
21*ea103259SMichael Clark #include "disas/bfd.h"
22*ea103259SMichael Clark 
23*ea103259SMichael Clark 
24*ea103259SMichael Clark /* types */
25*ea103259SMichael Clark 
26*ea103259SMichael Clark typedef uint64_t rv_inst;
27*ea103259SMichael Clark typedef uint16_t rv_opcode;
28*ea103259SMichael Clark 
29*ea103259SMichael Clark /* enums */
30*ea103259SMichael Clark 
31*ea103259SMichael Clark typedef enum {
32*ea103259SMichael Clark     rv32,
33*ea103259SMichael Clark     rv64,
34*ea103259SMichael Clark     rv128
35*ea103259SMichael Clark } rv_isa;
36*ea103259SMichael Clark 
37*ea103259SMichael Clark typedef enum {
38*ea103259SMichael Clark     rv_rm_rne = 0,
39*ea103259SMichael Clark     rv_rm_rtz = 1,
40*ea103259SMichael Clark     rv_rm_rdn = 2,
41*ea103259SMichael Clark     rv_rm_rup = 3,
42*ea103259SMichael Clark     rv_rm_rmm = 4,
43*ea103259SMichael Clark     rv_rm_dyn = 7,
44*ea103259SMichael Clark } rv_rm;
45*ea103259SMichael Clark 
46*ea103259SMichael Clark typedef enum {
47*ea103259SMichael Clark     rv_fence_i = 8,
48*ea103259SMichael Clark     rv_fence_o = 4,
49*ea103259SMichael Clark     rv_fence_r = 2,
50*ea103259SMichael Clark     rv_fence_w = 1,
51*ea103259SMichael Clark } rv_fence;
52*ea103259SMichael Clark 
53*ea103259SMichael Clark typedef enum {
54*ea103259SMichael Clark     rv_ireg_zero,
55*ea103259SMichael Clark     rv_ireg_ra,
56*ea103259SMichael Clark     rv_ireg_sp,
57*ea103259SMichael Clark     rv_ireg_gp,
58*ea103259SMichael Clark     rv_ireg_tp,
59*ea103259SMichael Clark     rv_ireg_t0,
60*ea103259SMichael Clark     rv_ireg_t1,
61*ea103259SMichael Clark     rv_ireg_t2,
62*ea103259SMichael Clark     rv_ireg_s0,
63*ea103259SMichael Clark     rv_ireg_s1,
64*ea103259SMichael Clark     rv_ireg_a0,
65*ea103259SMichael Clark     rv_ireg_a1,
66*ea103259SMichael Clark     rv_ireg_a2,
67*ea103259SMichael Clark     rv_ireg_a3,
68*ea103259SMichael Clark     rv_ireg_a4,
69*ea103259SMichael Clark     rv_ireg_a5,
70*ea103259SMichael Clark     rv_ireg_a6,
71*ea103259SMichael Clark     rv_ireg_a7,
72*ea103259SMichael Clark     rv_ireg_s2,
73*ea103259SMichael Clark     rv_ireg_s3,
74*ea103259SMichael Clark     rv_ireg_s4,
75*ea103259SMichael Clark     rv_ireg_s5,
76*ea103259SMichael Clark     rv_ireg_s6,
77*ea103259SMichael Clark     rv_ireg_s7,
78*ea103259SMichael Clark     rv_ireg_s8,
79*ea103259SMichael Clark     rv_ireg_s9,
80*ea103259SMichael Clark     rv_ireg_s10,
81*ea103259SMichael Clark     rv_ireg_s11,
82*ea103259SMichael Clark     rv_ireg_t3,
83*ea103259SMichael Clark     rv_ireg_t4,
84*ea103259SMichael Clark     rv_ireg_t5,
85*ea103259SMichael Clark     rv_ireg_t6,
86*ea103259SMichael Clark } rv_ireg;
87*ea103259SMichael Clark 
88*ea103259SMichael Clark typedef enum {
89*ea103259SMichael Clark     rvc_end,
90*ea103259SMichael Clark     rvc_simm_6,
91*ea103259SMichael Clark     rvc_imm_6,
92*ea103259SMichael Clark     rvc_imm_7,
93*ea103259SMichael Clark     rvc_imm_8,
94*ea103259SMichael Clark     rvc_imm_9,
95*ea103259SMichael Clark     rvc_imm_10,
96*ea103259SMichael Clark     rvc_imm_12,
97*ea103259SMichael Clark     rvc_imm_18,
98*ea103259SMichael Clark     rvc_imm_nz,
99*ea103259SMichael Clark     rvc_imm_x2,
100*ea103259SMichael Clark     rvc_imm_x4,
101*ea103259SMichael Clark     rvc_imm_x8,
102*ea103259SMichael Clark     rvc_imm_x16,
103*ea103259SMichael Clark     rvc_rd_b3,
104*ea103259SMichael Clark     rvc_rs1_b3,
105*ea103259SMichael Clark     rvc_rs2_b3,
106*ea103259SMichael Clark     rvc_rd_eq_rs1,
107*ea103259SMichael Clark     rvc_rd_eq_ra,
108*ea103259SMichael Clark     rvc_rd_eq_sp,
109*ea103259SMichael Clark     rvc_rd_eq_x0,
110*ea103259SMichael Clark     rvc_rs1_eq_sp,
111*ea103259SMichael Clark     rvc_rs1_eq_x0,
112*ea103259SMichael Clark     rvc_rs2_eq_x0,
113*ea103259SMichael Clark     rvc_rd_ne_x0_x2,
114*ea103259SMichael Clark     rvc_rd_ne_x0,
115*ea103259SMichael Clark     rvc_rs1_ne_x0,
116*ea103259SMichael Clark     rvc_rs2_ne_x0,
117*ea103259SMichael Clark     rvc_rs2_eq_rs1,
118*ea103259SMichael Clark     rvc_rs1_eq_ra,
119*ea103259SMichael Clark     rvc_imm_eq_zero,
120*ea103259SMichael Clark     rvc_imm_eq_n1,
121*ea103259SMichael Clark     rvc_imm_eq_p1,
122*ea103259SMichael Clark     rvc_csr_eq_0x001,
123*ea103259SMichael Clark     rvc_csr_eq_0x002,
124*ea103259SMichael Clark     rvc_csr_eq_0x003,
125*ea103259SMichael Clark     rvc_csr_eq_0xc00,
126*ea103259SMichael Clark     rvc_csr_eq_0xc01,
127*ea103259SMichael Clark     rvc_csr_eq_0xc02,
128*ea103259SMichael Clark     rvc_csr_eq_0xc80,
129*ea103259SMichael Clark     rvc_csr_eq_0xc81,
130*ea103259SMichael Clark     rvc_csr_eq_0xc82,
131*ea103259SMichael Clark } rvc_constraint;
132*ea103259SMichael Clark 
133*ea103259SMichael Clark typedef enum {
134*ea103259SMichael Clark     rv_codec_illegal,
135*ea103259SMichael Clark     rv_codec_none,
136*ea103259SMichael Clark     rv_codec_u,
137*ea103259SMichael Clark     rv_codec_uj,
138*ea103259SMichael Clark     rv_codec_i,
139*ea103259SMichael Clark     rv_codec_i_sh5,
140*ea103259SMichael Clark     rv_codec_i_sh6,
141*ea103259SMichael Clark     rv_codec_i_sh7,
142*ea103259SMichael Clark     rv_codec_i_csr,
143*ea103259SMichael Clark     rv_codec_s,
144*ea103259SMichael Clark     rv_codec_sb,
145*ea103259SMichael Clark     rv_codec_r,
146*ea103259SMichael Clark     rv_codec_r_m,
147*ea103259SMichael Clark     rv_codec_r4_m,
148*ea103259SMichael Clark     rv_codec_r_a,
149*ea103259SMichael Clark     rv_codec_r_l,
150*ea103259SMichael Clark     rv_codec_r_f,
151*ea103259SMichael Clark     rv_codec_cb,
152*ea103259SMichael Clark     rv_codec_cb_imm,
153*ea103259SMichael Clark     rv_codec_cb_sh5,
154*ea103259SMichael Clark     rv_codec_cb_sh6,
155*ea103259SMichael Clark     rv_codec_ci,
156*ea103259SMichael Clark     rv_codec_ci_sh5,
157*ea103259SMichael Clark     rv_codec_ci_sh6,
158*ea103259SMichael Clark     rv_codec_ci_16sp,
159*ea103259SMichael Clark     rv_codec_ci_lwsp,
160*ea103259SMichael Clark     rv_codec_ci_ldsp,
161*ea103259SMichael Clark     rv_codec_ci_lqsp,
162*ea103259SMichael Clark     rv_codec_ci_li,
163*ea103259SMichael Clark     rv_codec_ci_lui,
164*ea103259SMichael Clark     rv_codec_ci_none,
165*ea103259SMichael Clark     rv_codec_ciw_4spn,
166*ea103259SMichael Clark     rv_codec_cj,
167*ea103259SMichael Clark     rv_codec_cj_jal,
168*ea103259SMichael Clark     rv_codec_cl_lw,
169*ea103259SMichael Clark     rv_codec_cl_ld,
170*ea103259SMichael Clark     rv_codec_cl_lq,
171*ea103259SMichael Clark     rv_codec_cr,
172*ea103259SMichael Clark     rv_codec_cr_mv,
173*ea103259SMichael Clark     rv_codec_cr_jalr,
174*ea103259SMichael Clark     rv_codec_cr_jr,
175*ea103259SMichael Clark     rv_codec_cs,
176*ea103259SMichael Clark     rv_codec_cs_sw,
177*ea103259SMichael Clark     rv_codec_cs_sd,
178*ea103259SMichael Clark     rv_codec_cs_sq,
179*ea103259SMichael Clark     rv_codec_css_swsp,
180*ea103259SMichael Clark     rv_codec_css_sdsp,
181*ea103259SMichael Clark     rv_codec_css_sqsp,
182*ea103259SMichael Clark } rv_codec;
183*ea103259SMichael Clark 
184*ea103259SMichael Clark typedef enum {
185*ea103259SMichael Clark     rv_op_illegal = 0,
186*ea103259SMichael Clark     rv_op_lui = 1,
187*ea103259SMichael Clark     rv_op_auipc = 2,
188*ea103259SMichael Clark     rv_op_jal = 3,
189*ea103259SMichael Clark     rv_op_jalr = 4,
190*ea103259SMichael Clark     rv_op_beq = 5,
191*ea103259SMichael Clark     rv_op_bne = 6,
192*ea103259SMichael Clark     rv_op_blt = 7,
193*ea103259SMichael Clark     rv_op_bge = 8,
194*ea103259SMichael Clark     rv_op_bltu = 9,
195*ea103259SMichael Clark     rv_op_bgeu = 10,
196*ea103259SMichael Clark     rv_op_lb = 11,
197*ea103259SMichael Clark     rv_op_lh = 12,
198*ea103259SMichael Clark     rv_op_lw = 13,
199*ea103259SMichael Clark     rv_op_lbu = 14,
200*ea103259SMichael Clark     rv_op_lhu = 15,
201*ea103259SMichael Clark     rv_op_sb = 16,
202*ea103259SMichael Clark     rv_op_sh = 17,
203*ea103259SMichael Clark     rv_op_sw = 18,
204*ea103259SMichael Clark     rv_op_addi = 19,
205*ea103259SMichael Clark     rv_op_slti = 20,
206*ea103259SMichael Clark     rv_op_sltiu = 21,
207*ea103259SMichael Clark     rv_op_xori = 22,
208*ea103259SMichael Clark     rv_op_ori = 23,
209*ea103259SMichael Clark     rv_op_andi = 24,
210*ea103259SMichael Clark     rv_op_slli = 25,
211*ea103259SMichael Clark     rv_op_srli = 26,
212*ea103259SMichael Clark     rv_op_srai = 27,
213*ea103259SMichael Clark     rv_op_add = 28,
214*ea103259SMichael Clark     rv_op_sub = 29,
215*ea103259SMichael Clark     rv_op_sll = 30,
216*ea103259SMichael Clark     rv_op_slt = 31,
217*ea103259SMichael Clark     rv_op_sltu = 32,
218*ea103259SMichael Clark     rv_op_xor = 33,
219*ea103259SMichael Clark     rv_op_srl = 34,
220*ea103259SMichael Clark     rv_op_sra = 35,
221*ea103259SMichael Clark     rv_op_or = 36,
222*ea103259SMichael Clark     rv_op_and = 37,
223*ea103259SMichael Clark     rv_op_fence = 38,
224*ea103259SMichael Clark     rv_op_fence_i = 39,
225*ea103259SMichael Clark     rv_op_lwu = 40,
226*ea103259SMichael Clark     rv_op_ld = 41,
227*ea103259SMichael Clark     rv_op_sd = 42,
228*ea103259SMichael Clark     rv_op_addiw = 43,
229*ea103259SMichael Clark     rv_op_slliw = 44,
230*ea103259SMichael Clark     rv_op_srliw = 45,
231*ea103259SMichael Clark     rv_op_sraiw = 46,
232*ea103259SMichael Clark     rv_op_addw = 47,
233*ea103259SMichael Clark     rv_op_subw = 48,
234*ea103259SMichael Clark     rv_op_sllw = 49,
235*ea103259SMichael Clark     rv_op_srlw = 50,
236*ea103259SMichael Clark     rv_op_sraw = 51,
237*ea103259SMichael Clark     rv_op_ldu = 52,
238*ea103259SMichael Clark     rv_op_lq = 53,
239*ea103259SMichael Clark     rv_op_sq = 54,
240*ea103259SMichael Clark     rv_op_addid = 55,
241*ea103259SMichael Clark     rv_op_sllid = 56,
242*ea103259SMichael Clark     rv_op_srlid = 57,
243*ea103259SMichael Clark     rv_op_sraid = 58,
244*ea103259SMichael Clark     rv_op_addd = 59,
245*ea103259SMichael Clark     rv_op_subd = 60,
246*ea103259SMichael Clark     rv_op_slld = 61,
247*ea103259SMichael Clark     rv_op_srld = 62,
248*ea103259SMichael Clark     rv_op_srad = 63,
249*ea103259SMichael Clark     rv_op_mul = 64,
250*ea103259SMichael Clark     rv_op_mulh = 65,
251*ea103259SMichael Clark     rv_op_mulhsu = 66,
252*ea103259SMichael Clark     rv_op_mulhu = 67,
253*ea103259SMichael Clark     rv_op_div = 68,
254*ea103259SMichael Clark     rv_op_divu = 69,
255*ea103259SMichael Clark     rv_op_rem = 70,
256*ea103259SMichael Clark     rv_op_remu = 71,
257*ea103259SMichael Clark     rv_op_mulw = 72,
258*ea103259SMichael Clark     rv_op_divw = 73,
259*ea103259SMichael Clark     rv_op_divuw = 74,
260*ea103259SMichael Clark     rv_op_remw = 75,
261*ea103259SMichael Clark     rv_op_remuw = 76,
262*ea103259SMichael Clark     rv_op_muld = 77,
263*ea103259SMichael Clark     rv_op_divd = 78,
264*ea103259SMichael Clark     rv_op_divud = 79,
265*ea103259SMichael Clark     rv_op_remd = 80,
266*ea103259SMichael Clark     rv_op_remud = 81,
267*ea103259SMichael Clark     rv_op_lr_w = 82,
268*ea103259SMichael Clark     rv_op_sc_w = 83,
269*ea103259SMichael Clark     rv_op_amoswap_w = 84,
270*ea103259SMichael Clark     rv_op_amoadd_w = 85,
271*ea103259SMichael Clark     rv_op_amoxor_w = 86,
272*ea103259SMichael Clark     rv_op_amoor_w = 87,
273*ea103259SMichael Clark     rv_op_amoand_w = 88,
274*ea103259SMichael Clark     rv_op_amomin_w = 89,
275*ea103259SMichael Clark     rv_op_amomax_w = 90,
276*ea103259SMichael Clark     rv_op_amominu_w = 91,
277*ea103259SMichael Clark     rv_op_amomaxu_w = 92,
278*ea103259SMichael Clark     rv_op_lr_d = 93,
279*ea103259SMichael Clark     rv_op_sc_d = 94,
280*ea103259SMichael Clark     rv_op_amoswap_d = 95,
281*ea103259SMichael Clark     rv_op_amoadd_d = 96,
282*ea103259SMichael Clark     rv_op_amoxor_d = 97,
283*ea103259SMichael Clark     rv_op_amoor_d = 98,
284*ea103259SMichael Clark     rv_op_amoand_d = 99,
285*ea103259SMichael Clark     rv_op_amomin_d = 100,
286*ea103259SMichael Clark     rv_op_amomax_d = 101,
287*ea103259SMichael Clark     rv_op_amominu_d = 102,
288*ea103259SMichael Clark     rv_op_amomaxu_d = 103,
289*ea103259SMichael Clark     rv_op_lr_q = 104,
290*ea103259SMichael Clark     rv_op_sc_q = 105,
291*ea103259SMichael Clark     rv_op_amoswap_q = 106,
292*ea103259SMichael Clark     rv_op_amoadd_q = 107,
293*ea103259SMichael Clark     rv_op_amoxor_q = 108,
294*ea103259SMichael Clark     rv_op_amoor_q = 109,
295*ea103259SMichael Clark     rv_op_amoand_q = 110,
296*ea103259SMichael Clark     rv_op_amomin_q = 111,
297*ea103259SMichael Clark     rv_op_amomax_q = 112,
298*ea103259SMichael Clark     rv_op_amominu_q = 113,
299*ea103259SMichael Clark     rv_op_amomaxu_q = 114,
300*ea103259SMichael Clark     rv_op_ecall = 115,
301*ea103259SMichael Clark     rv_op_ebreak = 116,
302*ea103259SMichael Clark     rv_op_uret = 117,
303*ea103259SMichael Clark     rv_op_sret = 118,
304*ea103259SMichael Clark     rv_op_hret = 119,
305*ea103259SMichael Clark     rv_op_mret = 120,
306*ea103259SMichael Clark     rv_op_dret = 121,
307*ea103259SMichael Clark     rv_op_sfence_vm = 122,
308*ea103259SMichael Clark     rv_op_sfence_vma = 123,
309*ea103259SMichael Clark     rv_op_wfi = 124,
310*ea103259SMichael Clark     rv_op_csrrw = 125,
311*ea103259SMichael Clark     rv_op_csrrs = 126,
312*ea103259SMichael Clark     rv_op_csrrc = 127,
313*ea103259SMichael Clark     rv_op_csrrwi = 128,
314*ea103259SMichael Clark     rv_op_csrrsi = 129,
315*ea103259SMichael Clark     rv_op_csrrci = 130,
316*ea103259SMichael Clark     rv_op_flw = 131,
317*ea103259SMichael Clark     rv_op_fsw = 132,
318*ea103259SMichael Clark     rv_op_fmadd_s = 133,
319*ea103259SMichael Clark     rv_op_fmsub_s = 134,
320*ea103259SMichael Clark     rv_op_fnmsub_s = 135,
321*ea103259SMichael Clark     rv_op_fnmadd_s = 136,
322*ea103259SMichael Clark     rv_op_fadd_s = 137,
323*ea103259SMichael Clark     rv_op_fsub_s = 138,
324*ea103259SMichael Clark     rv_op_fmul_s = 139,
325*ea103259SMichael Clark     rv_op_fdiv_s = 140,
326*ea103259SMichael Clark     rv_op_fsgnj_s = 141,
327*ea103259SMichael Clark     rv_op_fsgnjn_s = 142,
328*ea103259SMichael Clark     rv_op_fsgnjx_s = 143,
329*ea103259SMichael Clark     rv_op_fmin_s = 144,
330*ea103259SMichael Clark     rv_op_fmax_s = 145,
331*ea103259SMichael Clark     rv_op_fsqrt_s = 146,
332*ea103259SMichael Clark     rv_op_fle_s = 147,
333*ea103259SMichael Clark     rv_op_flt_s = 148,
334*ea103259SMichael Clark     rv_op_feq_s = 149,
335*ea103259SMichael Clark     rv_op_fcvt_w_s = 150,
336*ea103259SMichael Clark     rv_op_fcvt_wu_s = 151,
337*ea103259SMichael Clark     rv_op_fcvt_s_w = 152,
338*ea103259SMichael Clark     rv_op_fcvt_s_wu = 153,
339*ea103259SMichael Clark     rv_op_fmv_x_s = 154,
340*ea103259SMichael Clark     rv_op_fclass_s = 155,
341*ea103259SMichael Clark     rv_op_fmv_s_x = 156,
342*ea103259SMichael Clark     rv_op_fcvt_l_s = 157,
343*ea103259SMichael Clark     rv_op_fcvt_lu_s = 158,
344*ea103259SMichael Clark     rv_op_fcvt_s_l = 159,
345*ea103259SMichael Clark     rv_op_fcvt_s_lu = 160,
346*ea103259SMichael Clark     rv_op_fld = 161,
347*ea103259SMichael Clark     rv_op_fsd = 162,
348*ea103259SMichael Clark     rv_op_fmadd_d = 163,
349*ea103259SMichael Clark     rv_op_fmsub_d = 164,
350*ea103259SMichael Clark     rv_op_fnmsub_d = 165,
351*ea103259SMichael Clark     rv_op_fnmadd_d = 166,
352*ea103259SMichael Clark     rv_op_fadd_d = 167,
353*ea103259SMichael Clark     rv_op_fsub_d = 168,
354*ea103259SMichael Clark     rv_op_fmul_d = 169,
355*ea103259SMichael Clark     rv_op_fdiv_d = 170,
356*ea103259SMichael Clark     rv_op_fsgnj_d = 171,
357*ea103259SMichael Clark     rv_op_fsgnjn_d = 172,
358*ea103259SMichael Clark     rv_op_fsgnjx_d = 173,
359*ea103259SMichael Clark     rv_op_fmin_d = 174,
360*ea103259SMichael Clark     rv_op_fmax_d = 175,
361*ea103259SMichael Clark     rv_op_fcvt_s_d = 176,
362*ea103259SMichael Clark     rv_op_fcvt_d_s = 177,
363*ea103259SMichael Clark     rv_op_fsqrt_d = 178,
364*ea103259SMichael Clark     rv_op_fle_d = 179,
365*ea103259SMichael Clark     rv_op_flt_d = 180,
366*ea103259SMichael Clark     rv_op_feq_d = 181,
367*ea103259SMichael Clark     rv_op_fcvt_w_d = 182,
368*ea103259SMichael Clark     rv_op_fcvt_wu_d = 183,
369*ea103259SMichael Clark     rv_op_fcvt_d_w = 184,
370*ea103259SMichael Clark     rv_op_fcvt_d_wu = 185,
371*ea103259SMichael Clark     rv_op_fclass_d = 186,
372*ea103259SMichael Clark     rv_op_fcvt_l_d = 187,
373*ea103259SMichael Clark     rv_op_fcvt_lu_d = 188,
374*ea103259SMichael Clark     rv_op_fmv_x_d = 189,
375*ea103259SMichael Clark     rv_op_fcvt_d_l = 190,
376*ea103259SMichael Clark     rv_op_fcvt_d_lu = 191,
377*ea103259SMichael Clark     rv_op_fmv_d_x = 192,
378*ea103259SMichael Clark     rv_op_flq = 193,
379*ea103259SMichael Clark     rv_op_fsq = 194,
380*ea103259SMichael Clark     rv_op_fmadd_q = 195,
381*ea103259SMichael Clark     rv_op_fmsub_q = 196,
382*ea103259SMichael Clark     rv_op_fnmsub_q = 197,
383*ea103259SMichael Clark     rv_op_fnmadd_q = 198,
384*ea103259SMichael Clark     rv_op_fadd_q = 199,
385*ea103259SMichael Clark     rv_op_fsub_q = 200,
386*ea103259SMichael Clark     rv_op_fmul_q = 201,
387*ea103259SMichael Clark     rv_op_fdiv_q = 202,
388*ea103259SMichael Clark     rv_op_fsgnj_q = 203,
389*ea103259SMichael Clark     rv_op_fsgnjn_q = 204,
390*ea103259SMichael Clark     rv_op_fsgnjx_q = 205,
391*ea103259SMichael Clark     rv_op_fmin_q = 206,
392*ea103259SMichael Clark     rv_op_fmax_q = 207,
393*ea103259SMichael Clark     rv_op_fcvt_s_q = 208,
394*ea103259SMichael Clark     rv_op_fcvt_q_s = 209,
395*ea103259SMichael Clark     rv_op_fcvt_d_q = 210,
396*ea103259SMichael Clark     rv_op_fcvt_q_d = 211,
397*ea103259SMichael Clark     rv_op_fsqrt_q = 212,
398*ea103259SMichael Clark     rv_op_fle_q = 213,
399*ea103259SMichael Clark     rv_op_flt_q = 214,
400*ea103259SMichael Clark     rv_op_feq_q = 215,
401*ea103259SMichael Clark     rv_op_fcvt_w_q = 216,
402*ea103259SMichael Clark     rv_op_fcvt_wu_q = 217,
403*ea103259SMichael Clark     rv_op_fcvt_q_w = 218,
404*ea103259SMichael Clark     rv_op_fcvt_q_wu = 219,
405*ea103259SMichael Clark     rv_op_fclass_q = 220,
406*ea103259SMichael Clark     rv_op_fcvt_l_q = 221,
407*ea103259SMichael Clark     rv_op_fcvt_lu_q = 222,
408*ea103259SMichael Clark     rv_op_fcvt_q_l = 223,
409*ea103259SMichael Clark     rv_op_fcvt_q_lu = 224,
410*ea103259SMichael Clark     rv_op_fmv_x_q = 225,
411*ea103259SMichael Clark     rv_op_fmv_q_x = 226,
412*ea103259SMichael Clark     rv_op_c_addi4spn = 227,
413*ea103259SMichael Clark     rv_op_c_fld = 228,
414*ea103259SMichael Clark     rv_op_c_lw = 229,
415*ea103259SMichael Clark     rv_op_c_flw = 230,
416*ea103259SMichael Clark     rv_op_c_fsd = 231,
417*ea103259SMichael Clark     rv_op_c_sw = 232,
418*ea103259SMichael Clark     rv_op_c_fsw = 233,
419*ea103259SMichael Clark     rv_op_c_nop = 234,
420*ea103259SMichael Clark     rv_op_c_addi = 235,
421*ea103259SMichael Clark     rv_op_c_jal = 236,
422*ea103259SMichael Clark     rv_op_c_li = 237,
423*ea103259SMichael Clark     rv_op_c_addi16sp = 238,
424*ea103259SMichael Clark     rv_op_c_lui = 239,
425*ea103259SMichael Clark     rv_op_c_srli = 240,
426*ea103259SMichael Clark     rv_op_c_srai = 241,
427*ea103259SMichael Clark     rv_op_c_andi = 242,
428*ea103259SMichael Clark     rv_op_c_sub = 243,
429*ea103259SMichael Clark     rv_op_c_xor = 244,
430*ea103259SMichael Clark     rv_op_c_or = 245,
431*ea103259SMichael Clark     rv_op_c_and = 246,
432*ea103259SMichael Clark     rv_op_c_subw = 247,
433*ea103259SMichael Clark     rv_op_c_addw = 248,
434*ea103259SMichael Clark     rv_op_c_j = 249,
435*ea103259SMichael Clark     rv_op_c_beqz = 250,
436*ea103259SMichael Clark     rv_op_c_bnez = 251,
437*ea103259SMichael Clark     rv_op_c_slli = 252,
438*ea103259SMichael Clark     rv_op_c_fldsp = 253,
439*ea103259SMichael Clark     rv_op_c_lwsp = 254,
440*ea103259SMichael Clark     rv_op_c_flwsp = 255,
441*ea103259SMichael Clark     rv_op_c_jr = 256,
442*ea103259SMichael Clark     rv_op_c_mv = 257,
443*ea103259SMichael Clark     rv_op_c_ebreak = 258,
444*ea103259SMichael Clark     rv_op_c_jalr = 259,
445*ea103259SMichael Clark     rv_op_c_add = 260,
446*ea103259SMichael Clark     rv_op_c_fsdsp = 261,
447*ea103259SMichael Clark     rv_op_c_swsp = 262,
448*ea103259SMichael Clark     rv_op_c_fswsp = 263,
449*ea103259SMichael Clark     rv_op_c_ld = 264,
450*ea103259SMichael Clark     rv_op_c_sd = 265,
451*ea103259SMichael Clark     rv_op_c_addiw = 266,
452*ea103259SMichael Clark     rv_op_c_ldsp = 267,
453*ea103259SMichael Clark     rv_op_c_sdsp = 268,
454*ea103259SMichael Clark     rv_op_c_lq = 269,
455*ea103259SMichael Clark     rv_op_c_sq = 270,
456*ea103259SMichael Clark     rv_op_c_lqsp = 271,
457*ea103259SMichael Clark     rv_op_c_sqsp = 272,
458*ea103259SMichael Clark     rv_op_nop = 273,
459*ea103259SMichael Clark     rv_op_mv = 274,
460*ea103259SMichael Clark     rv_op_not = 275,
461*ea103259SMichael Clark     rv_op_neg = 276,
462*ea103259SMichael Clark     rv_op_negw = 277,
463*ea103259SMichael Clark     rv_op_sext_w = 278,
464*ea103259SMichael Clark     rv_op_seqz = 279,
465*ea103259SMichael Clark     rv_op_snez = 280,
466*ea103259SMichael Clark     rv_op_sltz = 281,
467*ea103259SMichael Clark     rv_op_sgtz = 282,
468*ea103259SMichael Clark     rv_op_fmv_s = 283,
469*ea103259SMichael Clark     rv_op_fabs_s = 284,
470*ea103259SMichael Clark     rv_op_fneg_s = 285,
471*ea103259SMichael Clark     rv_op_fmv_d = 286,
472*ea103259SMichael Clark     rv_op_fabs_d = 287,
473*ea103259SMichael Clark     rv_op_fneg_d = 288,
474*ea103259SMichael Clark     rv_op_fmv_q = 289,
475*ea103259SMichael Clark     rv_op_fabs_q = 290,
476*ea103259SMichael Clark     rv_op_fneg_q = 291,
477*ea103259SMichael Clark     rv_op_beqz = 292,
478*ea103259SMichael Clark     rv_op_bnez = 293,
479*ea103259SMichael Clark     rv_op_blez = 294,
480*ea103259SMichael Clark     rv_op_bgez = 295,
481*ea103259SMichael Clark     rv_op_bltz = 296,
482*ea103259SMichael Clark     rv_op_bgtz = 297,
483*ea103259SMichael Clark     rv_op_ble = 298,
484*ea103259SMichael Clark     rv_op_bleu = 299,
485*ea103259SMichael Clark     rv_op_bgt = 300,
486*ea103259SMichael Clark     rv_op_bgtu = 301,
487*ea103259SMichael Clark     rv_op_j = 302,
488*ea103259SMichael Clark     rv_op_ret = 303,
489*ea103259SMichael Clark     rv_op_jr = 304,
490*ea103259SMichael Clark     rv_op_rdcycle = 305,
491*ea103259SMichael Clark     rv_op_rdtime = 306,
492*ea103259SMichael Clark     rv_op_rdinstret = 307,
493*ea103259SMichael Clark     rv_op_rdcycleh = 308,
494*ea103259SMichael Clark     rv_op_rdtimeh = 309,
495*ea103259SMichael Clark     rv_op_rdinstreth = 310,
496*ea103259SMichael Clark     rv_op_frcsr = 311,
497*ea103259SMichael Clark     rv_op_frrm = 312,
498*ea103259SMichael Clark     rv_op_frflags = 313,
499*ea103259SMichael Clark     rv_op_fscsr = 314,
500*ea103259SMichael Clark     rv_op_fsrm = 315,
501*ea103259SMichael Clark     rv_op_fsflags = 316,
502*ea103259SMichael Clark     rv_op_fsrmi = 317,
503*ea103259SMichael Clark     rv_op_fsflagsi = 318,
504*ea103259SMichael Clark } rv_op;
505*ea103259SMichael Clark 
506*ea103259SMichael Clark /* structures */
507*ea103259SMichael Clark 
508*ea103259SMichael Clark typedef struct {
509*ea103259SMichael Clark     uint64_t  pc;
510*ea103259SMichael Clark     uint64_t  inst;
511*ea103259SMichael Clark     int32_t   imm;
512*ea103259SMichael Clark     uint16_t  op;
513*ea103259SMichael Clark     uint8_t   codec;
514*ea103259SMichael Clark     uint8_t   rd;
515*ea103259SMichael Clark     uint8_t   rs1;
516*ea103259SMichael Clark     uint8_t   rs2;
517*ea103259SMichael Clark     uint8_t   rs3;
518*ea103259SMichael Clark     uint8_t   rm;
519*ea103259SMichael Clark     uint8_t   pred;
520*ea103259SMichael Clark     uint8_t   succ;
521*ea103259SMichael Clark     uint8_t   aq;
522*ea103259SMichael Clark     uint8_t   rl;
523*ea103259SMichael Clark } rv_decode;
524*ea103259SMichael Clark 
525*ea103259SMichael Clark typedef struct {
526*ea103259SMichael Clark     const int op;
527*ea103259SMichael Clark     const rvc_constraint *constraints;
528*ea103259SMichael Clark } rv_comp_data;
529*ea103259SMichael Clark 
530*ea103259SMichael Clark typedef struct {
531*ea103259SMichael Clark     const char * const name;
532*ea103259SMichael Clark     const rv_codec codec;
533*ea103259SMichael Clark     const char * const format;
534*ea103259SMichael Clark     const rv_comp_data *pseudo;
535*ea103259SMichael Clark     const int decomp_rv32;
536*ea103259SMichael Clark     const int decomp_rv64;
537*ea103259SMichael Clark     const int decomp_rv128;
538*ea103259SMichael Clark } rv_opcode_data;
539*ea103259SMichael Clark 
540*ea103259SMichael Clark /* register names */
541*ea103259SMichael Clark 
542*ea103259SMichael Clark static const char rv_ireg_name_sym[32][5] = {
543*ea103259SMichael Clark     "zero", "ra",   "sp",   "gp",   "tp",   "t0",   "t1",   "t2",
544*ea103259SMichael Clark     "s0",   "s1",   "a0",   "a1",   "a2",   "a3",   "a4",   "a5",
545*ea103259SMichael Clark     "a6",   "a7",   "s2",   "s3",   "s4",   "s5",   "s6",   "s7",
546*ea103259SMichael Clark     "s8",   "s9",   "s10",  "s11",  "t3",   "t4",   "t5",   "t6",
547*ea103259SMichael Clark };
548*ea103259SMichael Clark 
549*ea103259SMichael Clark static const char rv_freg_name_sym[32][5] = {
550*ea103259SMichael Clark     "ft0",  "ft1",  "ft2",  "ft3",  "ft4",  "ft5",  "ft6",  "ft7",
551*ea103259SMichael Clark     "fs0",  "fs1",  "fa0",  "fa1",  "fa2",  "fa3",  "fa4",  "fa5",
552*ea103259SMichael Clark     "fa6",  "fa7",  "fs2",  "fs3",  "fs4",  "fs5",  "fs6",  "fs7",
553*ea103259SMichael Clark     "fs8",  "fs9",  "fs10", "fs11", "ft8",  "ft9",  "ft10", "ft11",
554*ea103259SMichael Clark };
555*ea103259SMichael Clark 
556*ea103259SMichael Clark /* instruction formats */
557*ea103259SMichael Clark 
558*ea103259SMichael Clark #define rv_fmt_none                   "O\t"
559*ea103259SMichael Clark #define rv_fmt_rs1                    "O\t1"
560*ea103259SMichael Clark #define rv_fmt_offset                 "O\to"
561*ea103259SMichael Clark #define rv_fmt_pred_succ              "O\tp,s"
562*ea103259SMichael Clark #define rv_fmt_rs1_rs2                "O\t1,2"
563*ea103259SMichael Clark #define rv_fmt_rd_imm                 "O\t0,i"
564*ea103259SMichael Clark #define rv_fmt_rd_offset              "O\t0,o"
565*ea103259SMichael Clark #define rv_fmt_rd_rs1_rs2             "O\t0,1,2"
566*ea103259SMichael Clark #define rv_fmt_frd_rs1                "O\t3,1"
567*ea103259SMichael Clark #define rv_fmt_rd_frs1                "O\t0,4"
568*ea103259SMichael Clark #define rv_fmt_rd_frs1_frs2           "O\t0,4,5"
569*ea103259SMichael Clark #define rv_fmt_frd_frs1_frs2          "O\t3,4,5"
570*ea103259SMichael Clark #define rv_fmt_rm_frd_frs1            "O\tr,3,4"
571*ea103259SMichael Clark #define rv_fmt_rm_frd_rs1             "O\tr,3,1"
572*ea103259SMichael Clark #define rv_fmt_rm_rd_frs1             "O\tr,0,4"
573*ea103259SMichael Clark #define rv_fmt_rm_frd_frs1_frs2       "O\tr,3,4,5"
574*ea103259SMichael Clark #define rv_fmt_rm_frd_frs1_frs2_frs3  "O\tr,3,4,5,6"
575*ea103259SMichael Clark #define rv_fmt_rd_rs1_imm             "O\t0,1,i"
576*ea103259SMichael Clark #define rv_fmt_rd_rs1_offset          "O\t0,1,i"
577*ea103259SMichael Clark #define rv_fmt_rd_offset_rs1          "O\t0,i(1)"
578*ea103259SMichael Clark #define rv_fmt_frd_offset_rs1         "O\t3,i(1)"
579*ea103259SMichael Clark #define rv_fmt_rd_csr_rs1             "O\t0,c,1"
580*ea103259SMichael Clark #define rv_fmt_rd_csr_zimm            "O\t0,c,7"
581*ea103259SMichael Clark #define rv_fmt_rs2_offset_rs1         "O\t2,i(1)"
582*ea103259SMichael Clark #define rv_fmt_frs2_offset_rs1        "O\t5,i(1)"
583*ea103259SMichael Clark #define rv_fmt_rs1_rs2_offset         "O\t1,2,o"
584*ea103259SMichael Clark #define rv_fmt_rs2_rs1_offset         "O\t2,1,o"
585*ea103259SMichael Clark #define rv_fmt_aqrl_rd_rs2_rs1        "OAR\t0,2,(1)"
586*ea103259SMichael Clark #define rv_fmt_aqrl_rd_rs1            "OAR\t0,(1)"
587*ea103259SMichael Clark #define rv_fmt_rd                     "O\t0"
588*ea103259SMichael Clark #define rv_fmt_rd_zimm                "O\t0,7"
589*ea103259SMichael Clark #define rv_fmt_rd_rs1                 "O\t0,1"
590*ea103259SMichael Clark #define rv_fmt_rd_rs2                 "O\t0,2"
591*ea103259SMichael Clark #define rv_fmt_rs1_offset             "O\t1,o"
592*ea103259SMichael Clark #define rv_fmt_rs2_offset             "O\t2,o"
593*ea103259SMichael Clark 
594*ea103259SMichael Clark /* pseudo-instruction constraints */
595*ea103259SMichael Clark 
596*ea103259SMichael Clark static const rvc_constraint rvcc_jal[] = { rvc_rd_eq_ra, rvc_end };
597*ea103259SMichael Clark static const rvc_constraint rvcc_jalr[] = { rvc_rd_eq_ra, rvc_imm_eq_zero, rvc_end };
598*ea103259SMichael Clark static const rvc_constraint rvcc_nop[] = { rvc_rd_eq_x0, rvc_rs1_eq_x0, rvc_imm_eq_zero, rvc_end };
599*ea103259SMichael Clark static const rvc_constraint rvcc_mv[] = { rvc_imm_eq_zero, rvc_end };
600*ea103259SMichael Clark static const rvc_constraint rvcc_not[] = { rvc_imm_eq_n1, rvc_end };
601*ea103259SMichael Clark static const rvc_constraint rvcc_neg[] = { rvc_rs1_eq_x0, rvc_end };
602*ea103259SMichael Clark static const rvc_constraint rvcc_negw[] = { rvc_rs1_eq_x0, rvc_end };
603*ea103259SMichael Clark static const rvc_constraint rvcc_sext_w[] = { rvc_rs2_eq_x0, rvc_end };
604*ea103259SMichael Clark static const rvc_constraint rvcc_seqz[] = { rvc_imm_eq_p1, rvc_end };
605*ea103259SMichael Clark static const rvc_constraint rvcc_snez[] = { rvc_rs1_eq_x0, rvc_end };
606*ea103259SMichael Clark static const rvc_constraint rvcc_sltz[] = { rvc_rs2_eq_x0, rvc_end };
607*ea103259SMichael Clark static const rvc_constraint rvcc_sgtz[] = { rvc_rs1_eq_x0, rvc_end };
608*ea103259SMichael Clark static const rvc_constraint rvcc_fmv_s[] = { rvc_rs2_eq_rs1, rvc_end };
609*ea103259SMichael Clark static const rvc_constraint rvcc_fabs_s[] = { rvc_rs2_eq_rs1, rvc_end };
610*ea103259SMichael Clark static const rvc_constraint rvcc_fneg_s[] = { rvc_rs2_eq_rs1, rvc_end };
611*ea103259SMichael Clark static const rvc_constraint rvcc_fmv_d[] = { rvc_rs2_eq_rs1, rvc_end };
612*ea103259SMichael Clark static const rvc_constraint rvcc_fabs_d[] = { rvc_rs2_eq_rs1, rvc_end };
613*ea103259SMichael Clark static const rvc_constraint rvcc_fneg_d[] = { rvc_rs2_eq_rs1, rvc_end };
614*ea103259SMichael Clark static const rvc_constraint rvcc_fmv_q[] = { rvc_rs2_eq_rs1, rvc_end };
615*ea103259SMichael Clark static const rvc_constraint rvcc_fabs_q[] = { rvc_rs2_eq_rs1, rvc_end };
616*ea103259SMichael Clark static const rvc_constraint rvcc_fneg_q[] = { rvc_rs2_eq_rs1, rvc_end };
617*ea103259SMichael Clark static const rvc_constraint rvcc_beqz[] = { rvc_rs2_eq_x0, rvc_end };
618*ea103259SMichael Clark static const rvc_constraint rvcc_bnez[] = { rvc_rs2_eq_x0, rvc_end };
619*ea103259SMichael Clark static const rvc_constraint rvcc_blez[] = { rvc_rs1_eq_x0, rvc_end };
620*ea103259SMichael Clark static const rvc_constraint rvcc_bgez[] = { rvc_rs2_eq_x0, rvc_end };
621*ea103259SMichael Clark static const rvc_constraint rvcc_bltz[] = { rvc_rs2_eq_x0, rvc_end };
622*ea103259SMichael Clark static const rvc_constraint rvcc_bgtz[] = { rvc_rs1_eq_x0, rvc_end };
623*ea103259SMichael Clark static const rvc_constraint rvcc_ble[] = { rvc_end };
624*ea103259SMichael Clark static const rvc_constraint rvcc_bleu[] = { rvc_end };
625*ea103259SMichael Clark static const rvc_constraint rvcc_bgt[] = { rvc_end };
626*ea103259SMichael Clark static const rvc_constraint rvcc_bgtu[] = { rvc_end };
627*ea103259SMichael Clark static const rvc_constraint rvcc_j[] = { rvc_rd_eq_x0, rvc_end };
628*ea103259SMichael Clark static const rvc_constraint rvcc_ret[] = { rvc_rd_eq_x0, rvc_rs1_eq_ra, rvc_end };
629*ea103259SMichael Clark static const rvc_constraint rvcc_jr[] = { rvc_rd_eq_x0, rvc_imm_eq_zero, rvc_end };
630*ea103259SMichael Clark static const rvc_constraint rvcc_rdcycle[] = { rvc_rs1_eq_x0, rvc_csr_eq_0xc00, rvc_end };
631*ea103259SMichael Clark static const rvc_constraint rvcc_rdtime[] = { rvc_rs1_eq_x0, rvc_csr_eq_0xc01, rvc_end };
632*ea103259SMichael Clark static const rvc_constraint rvcc_rdinstret[] = { rvc_rs1_eq_x0, rvc_csr_eq_0xc02, rvc_end };
633*ea103259SMichael Clark static const rvc_constraint rvcc_rdcycleh[] = { rvc_rs1_eq_x0, rvc_csr_eq_0xc80, rvc_end };
634*ea103259SMichael Clark static const rvc_constraint rvcc_rdtimeh[] = { rvc_rs1_eq_x0, rvc_csr_eq_0xc81, rvc_end };
635*ea103259SMichael Clark static const rvc_constraint rvcc_rdinstreth[] = { rvc_rs1_eq_x0, rvc_csr_eq_0xc80, rvc_end };
636*ea103259SMichael Clark static const rvc_constraint rvcc_frcsr[] = { rvc_rs1_eq_x0, rvc_csr_eq_0x003, rvc_end };
637*ea103259SMichael Clark static const rvc_constraint rvcc_frrm[] = { rvc_rs1_eq_x0, rvc_csr_eq_0x002, rvc_end };
638*ea103259SMichael Clark static const rvc_constraint rvcc_frflags[] = { rvc_rs1_eq_x0, rvc_csr_eq_0x001, rvc_end };
639*ea103259SMichael Clark static const rvc_constraint rvcc_fscsr[] = { rvc_csr_eq_0x003, rvc_end };
640*ea103259SMichael Clark static const rvc_constraint rvcc_fsrm[] = { rvc_csr_eq_0x002, rvc_end };
641*ea103259SMichael Clark static const rvc_constraint rvcc_fsflags[] = { rvc_csr_eq_0x001, rvc_end };
642*ea103259SMichael Clark static const rvc_constraint rvcc_fsrmi[] = { rvc_csr_eq_0x002, rvc_end };
643*ea103259SMichael Clark static const rvc_constraint rvcc_fsflagsi[] = { rvc_csr_eq_0x001, rvc_end };
644*ea103259SMichael Clark 
645*ea103259SMichael Clark /* pseudo-instruction metadata */
646*ea103259SMichael Clark 
647*ea103259SMichael Clark static const rv_comp_data rvcp_jal[] = {
648*ea103259SMichael Clark     { rv_op_j, rvcc_j },
649*ea103259SMichael Clark     { rv_op_jal, rvcc_jal },
650*ea103259SMichael Clark     { rv_op_illegal, NULL }
651*ea103259SMichael Clark };
652*ea103259SMichael Clark 
653*ea103259SMichael Clark static const rv_comp_data rvcp_jalr[] = {
654*ea103259SMichael Clark     { rv_op_ret, rvcc_ret },
655*ea103259SMichael Clark     { rv_op_jr, rvcc_jr },
656*ea103259SMichael Clark     { rv_op_jalr, rvcc_jalr },
657*ea103259SMichael Clark     { rv_op_illegal, NULL }
658*ea103259SMichael Clark };
659*ea103259SMichael Clark 
660*ea103259SMichael Clark static const rv_comp_data rvcp_beq[] = {
661*ea103259SMichael Clark     { rv_op_beqz, rvcc_beqz },
662*ea103259SMichael Clark     { rv_op_illegal, NULL }
663*ea103259SMichael Clark };
664*ea103259SMichael Clark 
665*ea103259SMichael Clark static const rv_comp_data rvcp_bne[] = {
666*ea103259SMichael Clark     { rv_op_bnez, rvcc_bnez },
667*ea103259SMichael Clark     { rv_op_illegal, NULL }
668*ea103259SMichael Clark };
669*ea103259SMichael Clark 
670*ea103259SMichael Clark static const rv_comp_data rvcp_blt[] = {
671*ea103259SMichael Clark     { rv_op_bltz, rvcc_bltz },
672*ea103259SMichael Clark     { rv_op_bgtz, rvcc_bgtz },
673*ea103259SMichael Clark     { rv_op_bgt, rvcc_bgt },
674*ea103259SMichael Clark     { rv_op_illegal, NULL }
675*ea103259SMichael Clark };
676*ea103259SMichael Clark 
677*ea103259SMichael Clark static const rv_comp_data rvcp_bge[] = {
678*ea103259SMichael Clark     { rv_op_blez, rvcc_blez },
679*ea103259SMichael Clark     { rv_op_bgez, rvcc_bgez },
680*ea103259SMichael Clark     { rv_op_ble, rvcc_ble },
681*ea103259SMichael Clark     { rv_op_illegal, NULL }
682*ea103259SMichael Clark };
683*ea103259SMichael Clark 
684*ea103259SMichael Clark static const rv_comp_data rvcp_bltu[] = {
685*ea103259SMichael Clark     { rv_op_bgtu, rvcc_bgtu },
686*ea103259SMichael Clark     { rv_op_illegal, NULL }
687*ea103259SMichael Clark };
688*ea103259SMichael Clark 
689*ea103259SMichael Clark static const rv_comp_data rvcp_bgeu[] = {
690*ea103259SMichael Clark     { rv_op_bleu, rvcc_bleu },
691*ea103259SMichael Clark     { rv_op_illegal, NULL }
692*ea103259SMichael Clark };
693*ea103259SMichael Clark 
694*ea103259SMichael Clark static const rv_comp_data rvcp_addi[] = {
695*ea103259SMichael Clark     { rv_op_nop, rvcc_nop },
696*ea103259SMichael Clark     { rv_op_mv, rvcc_mv },
697*ea103259SMichael Clark     { rv_op_illegal, NULL }
698*ea103259SMichael Clark };
699*ea103259SMichael Clark 
700*ea103259SMichael Clark static const rv_comp_data rvcp_sltiu[] = {
701*ea103259SMichael Clark     { rv_op_seqz, rvcc_seqz },
702*ea103259SMichael Clark     { rv_op_illegal, NULL }
703*ea103259SMichael Clark };
704*ea103259SMichael Clark 
705*ea103259SMichael Clark static const rv_comp_data rvcp_xori[] = {
706*ea103259SMichael Clark     { rv_op_not, rvcc_not },
707*ea103259SMichael Clark     { rv_op_illegal, NULL }
708*ea103259SMichael Clark };
709*ea103259SMichael Clark 
710*ea103259SMichael Clark static const rv_comp_data rvcp_sub[] = {
711*ea103259SMichael Clark     { rv_op_neg, rvcc_neg },
712*ea103259SMichael Clark     { rv_op_illegal, NULL }
713*ea103259SMichael Clark };
714*ea103259SMichael Clark 
715*ea103259SMichael Clark static const rv_comp_data rvcp_slt[] = {
716*ea103259SMichael Clark     { rv_op_sltz, rvcc_sltz },
717*ea103259SMichael Clark     { rv_op_sgtz, rvcc_sgtz },
718*ea103259SMichael Clark     { rv_op_illegal, NULL }
719*ea103259SMichael Clark };
720*ea103259SMichael Clark 
721*ea103259SMichael Clark static const rv_comp_data rvcp_sltu[] = {
722*ea103259SMichael Clark     { rv_op_snez, rvcc_snez },
723*ea103259SMichael Clark     { rv_op_illegal, NULL }
724*ea103259SMichael Clark };
725*ea103259SMichael Clark 
726*ea103259SMichael Clark static const rv_comp_data rvcp_addiw[] = {
727*ea103259SMichael Clark     { rv_op_sext_w, rvcc_sext_w },
728*ea103259SMichael Clark     { rv_op_illegal, NULL }
729*ea103259SMichael Clark };
730*ea103259SMichael Clark 
731*ea103259SMichael Clark static const rv_comp_data rvcp_subw[] = {
732*ea103259SMichael Clark     { rv_op_negw, rvcc_negw },
733*ea103259SMichael Clark     { rv_op_illegal, NULL }
734*ea103259SMichael Clark };
735*ea103259SMichael Clark 
736*ea103259SMichael Clark static const rv_comp_data rvcp_csrrw[] = {
737*ea103259SMichael Clark     { rv_op_fscsr, rvcc_fscsr },
738*ea103259SMichael Clark     { rv_op_fsrm, rvcc_fsrm },
739*ea103259SMichael Clark     { rv_op_fsflags, rvcc_fsflags },
740*ea103259SMichael Clark     { rv_op_illegal, NULL }
741*ea103259SMichael Clark };
742*ea103259SMichael Clark 
743*ea103259SMichael Clark static const rv_comp_data rvcp_csrrs[] = {
744*ea103259SMichael Clark     { rv_op_rdcycle, rvcc_rdcycle },
745*ea103259SMichael Clark     { rv_op_rdtime, rvcc_rdtime },
746*ea103259SMichael Clark     { rv_op_rdinstret, rvcc_rdinstret },
747*ea103259SMichael Clark     { rv_op_rdcycleh, rvcc_rdcycleh },
748*ea103259SMichael Clark     { rv_op_rdtimeh, rvcc_rdtimeh },
749*ea103259SMichael Clark     { rv_op_rdinstreth, rvcc_rdinstreth },
750*ea103259SMichael Clark     { rv_op_frcsr, rvcc_frcsr },
751*ea103259SMichael Clark     { rv_op_frrm, rvcc_frrm },
752*ea103259SMichael Clark     { rv_op_frflags, rvcc_frflags },
753*ea103259SMichael Clark     { rv_op_illegal, NULL }
754*ea103259SMichael Clark };
755*ea103259SMichael Clark 
756*ea103259SMichael Clark static const rv_comp_data rvcp_csrrwi[] = {
757*ea103259SMichael Clark     { rv_op_fsrmi, rvcc_fsrmi },
758*ea103259SMichael Clark     { rv_op_fsflagsi, rvcc_fsflagsi },
759*ea103259SMichael Clark     { rv_op_illegal, NULL }
760*ea103259SMichael Clark };
761*ea103259SMichael Clark 
762*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnj_s[] = {
763*ea103259SMichael Clark     { rv_op_fmv_s, rvcc_fmv_s },
764*ea103259SMichael Clark     { rv_op_illegal, NULL }
765*ea103259SMichael Clark };
766*ea103259SMichael Clark 
767*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnjn_s[] = {
768*ea103259SMichael Clark     { rv_op_fneg_s, rvcc_fneg_s },
769*ea103259SMichael Clark     { rv_op_illegal, NULL }
770*ea103259SMichael Clark };
771*ea103259SMichael Clark 
772*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnjx_s[] = {
773*ea103259SMichael Clark     { rv_op_fabs_s, rvcc_fabs_s },
774*ea103259SMichael Clark     { rv_op_illegal, NULL }
775*ea103259SMichael Clark };
776*ea103259SMichael Clark 
777*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnj_d[] = {
778*ea103259SMichael Clark     { rv_op_fmv_d, rvcc_fmv_d },
779*ea103259SMichael Clark     { rv_op_illegal, NULL }
780*ea103259SMichael Clark };
781*ea103259SMichael Clark 
782*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnjn_d[] = {
783*ea103259SMichael Clark     { rv_op_fneg_d, rvcc_fneg_d },
784*ea103259SMichael Clark     { rv_op_illegal, NULL }
785*ea103259SMichael Clark };
786*ea103259SMichael Clark 
787*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnjx_d[] = {
788*ea103259SMichael Clark     { rv_op_fabs_d, rvcc_fabs_d },
789*ea103259SMichael Clark     { rv_op_illegal, NULL }
790*ea103259SMichael Clark };
791*ea103259SMichael Clark 
792*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnj_q[] = {
793*ea103259SMichael Clark     { rv_op_fmv_q, rvcc_fmv_q },
794*ea103259SMichael Clark     { rv_op_illegal, NULL }
795*ea103259SMichael Clark };
796*ea103259SMichael Clark 
797*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnjn_q[] = {
798*ea103259SMichael Clark     { rv_op_fneg_q, rvcc_fneg_q },
799*ea103259SMichael Clark     { rv_op_illegal, NULL }
800*ea103259SMichael Clark };
801*ea103259SMichael Clark 
802*ea103259SMichael Clark static const rv_comp_data rvcp_fsgnjx_q[] = {
803*ea103259SMichael Clark     { rv_op_fabs_q, rvcc_fabs_q },
804*ea103259SMichael Clark     { rv_op_illegal, NULL }
805*ea103259SMichael Clark };
806*ea103259SMichael Clark 
807*ea103259SMichael Clark /* instruction metadata */
808*ea103259SMichael Clark 
809*ea103259SMichael Clark const rv_opcode_data opcode_data[] = {
810*ea103259SMichael Clark     { "illegal", rv_codec_illegal, rv_fmt_none, NULL, 0, 0, 0 },
811*ea103259SMichael Clark     { "lui", rv_codec_u, rv_fmt_rd_imm, NULL, 0, 0, 0 },
812*ea103259SMichael Clark     { "auipc", rv_codec_u, rv_fmt_rd_offset, NULL, 0, 0, 0 },
813*ea103259SMichael Clark     { "jal", rv_codec_uj, rv_fmt_rd_offset, rvcp_jal, 0, 0, 0 },
814*ea103259SMichael Clark     { "jalr", rv_codec_i, rv_fmt_rd_rs1_offset, rvcp_jalr, 0, 0, 0 },
815*ea103259SMichael Clark     { "beq", rv_codec_sb, rv_fmt_rs1_rs2_offset, rvcp_beq, 0, 0, 0 },
816*ea103259SMichael Clark     { "bne", rv_codec_sb, rv_fmt_rs1_rs2_offset, rvcp_bne, 0, 0, 0 },
817*ea103259SMichael Clark     { "blt", rv_codec_sb, rv_fmt_rs1_rs2_offset, rvcp_blt, 0, 0, 0 },
818*ea103259SMichael Clark     { "bge", rv_codec_sb, rv_fmt_rs1_rs2_offset, rvcp_bge, 0, 0, 0 },
819*ea103259SMichael Clark     { "bltu", rv_codec_sb, rv_fmt_rs1_rs2_offset, rvcp_bltu, 0, 0, 0 },
820*ea103259SMichael Clark     { "bgeu", rv_codec_sb, rv_fmt_rs1_rs2_offset, rvcp_bgeu, 0, 0, 0 },
821*ea103259SMichael Clark     { "lb", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
822*ea103259SMichael Clark     { "lh", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
823*ea103259SMichael Clark     { "lw", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
824*ea103259SMichael Clark     { "lbu", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
825*ea103259SMichael Clark     { "lhu", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
826*ea103259SMichael Clark     { "sb", rv_codec_s, rv_fmt_rs2_offset_rs1, NULL, 0, 0, 0 },
827*ea103259SMichael Clark     { "sh", rv_codec_s, rv_fmt_rs2_offset_rs1, NULL, 0, 0, 0 },
828*ea103259SMichael Clark     { "sw", rv_codec_s, rv_fmt_rs2_offset_rs1, NULL, 0, 0, 0 },
829*ea103259SMichael Clark     { "addi", rv_codec_i, rv_fmt_rd_rs1_imm, rvcp_addi, 0, 0, 0 },
830*ea103259SMichael Clark     { "slti", rv_codec_i, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
831*ea103259SMichael Clark     { "sltiu", rv_codec_i, rv_fmt_rd_rs1_imm, rvcp_sltiu, 0, 0, 0 },
832*ea103259SMichael Clark     { "xori", rv_codec_i, rv_fmt_rd_rs1_imm, rvcp_xori, 0, 0, 0 },
833*ea103259SMichael Clark     { "ori", rv_codec_i, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
834*ea103259SMichael Clark     { "andi", rv_codec_i, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
835*ea103259SMichael Clark     { "slli", rv_codec_i_sh7, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
836*ea103259SMichael Clark     { "srli", rv_codec_i_sh7, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
837*ea103259SMichael Clark     { "srai", rv_codec_i_sh7, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
838*ea103259SMichael Clark     { "add", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
839*ea103259SMichael Clark     { "sub", rv_codec_r, rv_fmt_rd_rs1_rs2, rvcp_sub, 0, 0, 0 },
840*ea103259SMichael Clark     { "sll", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
841*ea103259SMichael Clark     { "slt", rv_codec_r, rv_fmt_rd_rs1_rs2, rvcp_slt, 0, 0, 0 },
842*ea103259SMichael Clark     { "sltu", rv_codec_r, rv_fmt_rd_rs1_rs2, rvcp_sltu, 0, 0, 0 },
843*ea103259SMichael Clark     { "xor", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
844*ea103259SMichael Clark     { "srl", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
845*ea103259SMichael Clark     { "sra", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
846*ea103259SMichael Clark     { "or", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
847*ea103259SMichael Clark     { "and", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
848*ea103259SMichael Clark     { "fence", rv_codec_r_f, rv_fmt_pred_succ, NULL, 0, 0, 0 },
849*ea103259SMichael Clark     { "fence.i", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
850*ea103259SMichael Clark     { "lwu", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
851*ea103259SMichael Clark     { "ld", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
852*ea103259SMichael Clark     { "sd", rv_codec_s, rv_fmt_rs2_offset_rs1, NULL, 0, 0, 0 },
853*ea103259SMichael Clark     { "addiw", rv_codec_i, rv_fmt_rd_rs1_imm, rvcp_addiw, 0, 0, 0 },
854*ea103259SMichael Clark     { "slliw", rv_codec_i_sh5, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
855*ea103259SMichael Clark     { "srliw", rv_codec_i_sh5, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
856*ea103259SMichael Clark     { "sraiw", rv_codec_i_sh5, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
857*ea103259SMichael Clark     { "addw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
858*ea103259SMichael Clark     { "subw", rv_codec_r, rv_fmt_rd_rs1_rs2, rvcp_subw, 0, 0, 0 },
859*ea103259SMichael Clark     { "sllw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
860*ea103259SMichael Clark     { "srlw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
861*ea103259SMichael Clark     { "sraw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
862*ea103259SMichael Clark     { "ldu", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
863*ea103259SMichael Clark     { "lq", rv_codec_i, rv_fmt_rd_offset_rs1, NULL, 0, 0, 0 },
864*ea103259SMichael Clark     { "sq", rv_codec_s, rv_fmt_rs2_offset_rs1, NULL, 0, 0, 0 },
865*ea103259SMichael Clark     { "addid", rv_codec_i, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
866*ea103259SMichael Clark     { "sllid", rv_codec_i_sh6, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
867*ea103259SMichael Clark     { "srlid", rv_codec_i_sh6, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
868*ea103259SMichael Clark     { "sraid", rv_codec_i_sh6, rv_fmt_rd_rs1_imm, NULL, 0, 0, 0 },
869*ea103259SMichael Clark     { "addd", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
870*ea103259SMichael Clark     { "subd", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
871*ea103259SMichael Clark     { "slld", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
872*ea103259SMichael Clark     { "srld", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
873*ea103259SMichael Clark     { "srad", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
874*ea103259SMichael Clark     { "mul", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
875*ea103259SMichael Clark     { "mulh", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
876*ea103259SMichael Clark     { "mulhsu", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
877*ea103259SMichael Clark     { "mulhu", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
878*ea103259SMichael Clark     { "div", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
879*ea103259SMichael Clark     { "divu", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
880*ea103259SMichael Clark     { "rem", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
881*ea103259SMichael Clark     { "remu", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
882*ea103259SMichael Clark     { "mulw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
883*ea103259SMichael Clark     { "divw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
884*ea103259SMichael Clark     { "divuw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
885*ea103259SMichael Clark     { "remw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
886*ea103259SMichael Clark     { "remuw", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
887*ea103259SMichael Clark     { "muld", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
888*ea103259SMichael Clark     { "divd", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
889*ea103259SMichael Clark     { "divud", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
890*ea103259SMichael Clark     { "remd", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
891*ea103259SMichael Clark     { "remud", rv_codec_r, rv_fmt_rd_rs1_rs2, NULL, 0, 0, 0 },
892*ea103259SMichael Clark     { "lr.w", rv_codec_r_l, rv_fmt_aqrl_rd_rs1, NULL, 0, 0, 0 },
893*ea103259SMichael Clark     { "sc.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
894*ea103259SMichael Clark     { "amoswap.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
895*ea103259SMichael Clark     { "amoadd.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
896*ea103259SMichael Clark     { "amoxor.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
897*ea103259SMichael Clark     { "amoor.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
898*ea103259SMichael Clark     { "amoand.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
899*ea103259SMichael Clark     { "amomin.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
900*ea103259SMichael Clark     { "amomax.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
901*ea103259SMichael Clark     { "amominu.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
902*ea103259SMichael Clark     { "amomaxu.w", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
903*ea103259SMichael Clark     { "lr.d", rv_codec_r_l, rv_fmt_aqrl_rd_rs1, NULL, 0, 0, 0 },
904*ea103259SMichael Clark     { "sc.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
905*ea103259SMichael Clark     { "amoswap.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
906*ea103259SMichael Clark     { "amoadd.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
907*ea103259SMichael Clark     { "amoxor.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
908*ea103259SMichael Clark     { "amoor.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
909*ea103259SMichael Clark     { "amoand.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
910*ea103259SMichael Clark     { "amomin.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
911*ea103259SMichael Clark     { "amomax.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
912*ea103259SMichael Clark     { "amominu.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
913*ea103259SMichael Clark     { "amomaxu.d", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
914*ea103259SMichael Clark     { "lr.q", rv_codec_r_l, rv_fmt_aqrl_rd_rs1, NULL, 0, 0, 0 },
915*ea103259SMichael Clark     { "sc.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
916*ea103259SMichael Clark     { "amoswap.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
917*ea103259SMichael Clark     { "amoadd.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
918*ea103259SMichael Clark     { "amoxor.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
919*ea103259SMichael Clark     { "amoor.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
920*ea103259SMichael Clark     { "amoand.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
921*ea103259SMichael Clark     { "amomin.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
922*ea103259SMichael Clark     { "amomax.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
923*ea103259SMichael Clark     { "amominu.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
924*ea103259SMichael Clark     { "amomaxu.q", rv_codec_r_a, rv_fmt_aqrl_rd_rs2_rs1, NULL, 0, 0, 0 },
925*ea103259SMichael Clark     { "ecall", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
926*ea103259SMichael Clark     { "ebreak", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
927*ea103259SMichael Clark     { "uret", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
928*ea103259SMichael Clark     { "sret", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
929*ea103259SMichael Clark     { "hret", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
930*ea103259SMichael Clark     { "mret", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
931*ea103259SMichael Clark     { "dret", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
932*ea103259SMichael Clark     { "sfence.vm", rv_codec_r, rv_fmt_rs1, NULL, 0, 0, 0 },
933*ea103259SMichael Clark     { "sfence.vma", rv_codec_r, rv_fmt_rs1_rs2, NULL, 0, 0, 0 },
934*ea103259SMichael Clark     { "wfi", rv_codec_none, rv_fmt_none, NULL, 0, 0, 0 },
935*ea103259SMichael Clark     { "csrrw", rv_codec_i_csr, rv_fmt_rd_csr_rs1, rvcp_csrrw, 0, 0, 0 },
936*ea103259SMichael Clark     { "csrrs", rv_codec_i_csr, rv_fmt_rd_csr_rs1, rvcp_csrrs, 0, 0, 0 },
937*ea103259SMichael Clark     { "csrrc", rv_codec_i_csr, rv_fmt_rd_csr_rs1, NULL, 0, 0, 0 },
938*ea103259SMichael Clark     { "csrrwi", rv_codec_i_csr, rv_fmt_rd_csr_zimm, rvcp_csrrwi, 0, 0, 0 },
939*ea103259SMichael Clark     { "csrrsi", rv_codec_i_csr, rv_fmt_rd_csr_zimm, NULL, 0, 0, 0 },
940*ea103259SMichael Clark     { "csrrci", rv_codec_i_csr, rv_fmt_rd_csr_zimm, NULL, 0, 0, 0 },
941*ea103259SMichael Clark     { "flw", rv_codec_i, rv_fmt_frd_offset_rs1, NULL, 0, 0, 0 },
942*ea103259SMichael Clark     { "fsw", rv_codec_s, rv_fmt_frs2_offset_rs1, NULL, 0, 0, 0 },
943*ea103259SMichael Clark     { "fmadd.s", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
944*ea103259SMichael Clark     { "fmsub.s", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
945*ea103259SMichael Clark     { "fnmsub.s", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
946*ea103259SMichael Clark     { "fnmadd.s", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
947*ea103259SMichael Clark     { "fadd.s", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
948*ea103259SMichael Clark     { "fsub.s", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
949*ea103259SMichael Clark     { "fmul.s", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
950*ea103259SMichael Clark     { "fdiv.s", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
951*ea103259SMichael Clark     { "fsgnj.s", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnj_s, 0, 0, 0 },
952*ea103259SMichael Clark     { "fsgnjn.s", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnjn_s, 0, 0, 0 },
953*ea103259SMichael Clark     { "fsgnjx.s", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnjx_s, 0, 0, 0 },
954*ea103259SMichael Clark     { "fmin.s", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
955*ea103259SMichael Clark     { "fmax.s", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
956*ea103259SMichael Clark     { "fsqrt.s", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
957*ea103259SMichael Clark     { "fle.s", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
958*ea103259SMichael Clark     { "flt.s", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
959*ea103259SMichael Clark     { "feq.s", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
960*ea103259SMichael Clark     { "fcvt.w.s", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
961*ea103259SMichael Clark     { "fcvt.wu.s", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
962*ea103259SMichael Clark     { "fcvt.s.w", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
963*ea103259SMichael Clark     { "fcvt.s.wu", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
964*ea103259SMichael Clark     { "fmv.x.s", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
965*ea103259SMichael Clark     { "fclass.s", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
966*ea103259SMichael Clark     { "fmv.s.x", rv_codec_r, rv_fmt_frd_rs1, NULL, 0, 0, 0 },
967*ea103259SMichael Clark     { "fcvt.l.s", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
968*ea103259SMichael Clark     { "fcvt.lu.s", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
969*ea103259SMichael Clark     { "fcvt.s.l", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
970*ea103259SMichael Clark     { "fcvt.s.lu", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
971*ea103259SMichael Clark     { "fld", rv_codec_i, rv_fmt_frd_offset_rs1, NULL, 0, 0, 0 },
972*ea103259SMichael Clark     { "fsd", rv_codec_s, rv_fmt_frs2_offset_rs1, NULL, 0, 0, 0 },
973*ea103259SMichael Clark     { "fmadd.d", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
974*ea103259SMichael Clark     { "fmsub.d", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
975*ea103259SMichael Clark     { "fnmsub.d", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
976*ea103259SMichael Clark     { "fnmadd.d", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
977*ea103259SMichael Clark     { "fadd.d", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
978*ea103259SMichael Clark     { "fsub.d", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
979*ea103259SMichael Clark     { "fmul.d", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
980*ea103259SMichael Clark     { "fdiv.d", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
981*ea103259SMichael Clark     { "fsgnj.d", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnj_d, 0, 0, 0 },
982*ea103259SMichael Clark     { "fsgnjn.d", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnjn_d, 0, 0, 0 },
983*ea103259SMichael Clark     { "fsgnjx.d", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnjx_d, 0, 0, 0 },
984*ea103259SMichael Clark     { "fmin.d", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
985*ea103259SMichael Clark     { "fmax.d", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
986*ea103259SMichael Clark     { "fcvt.s.d", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
987*ea103259SMichael Clark     { "fcvt.d.s", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
988*ea103259SMichael Clark     { "fsqrt.d", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
989*ea103259SMichael Clark     { "fle.d", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
990*ea103259SMichael Clark     { "flt.d", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
991*ea103259SMichael Clark     { "feq.d", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
992*ea103259SMichael Clark     { "fcvt.w.d", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
993*ea103259SMichael Clark     { "fcvt.wu.d", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
994*ea103259SMichael Clark     { "fcvt.d.w", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
995*ea103259SMichael Clark     { "fcvt.d.wu", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
996*ea103259SMichael Clark     { "fclass.d", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
997*ea103259SMichael Clark     { "fcvt.l.d", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
998*ea103259SMichael Clark     { "fcvt.lu.d", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
999*ea103259SMichael Clark     { "fmv.x.d", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
1000*ea103259SMichael Clark     { "fcvt.d.l", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
1001*ea103259SMichael Clark     { "fcvt.d.lu", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
1002*ea103259SMichael Clark     { "fmv.d.x", rv_codec_r, rv_fmt_frd_rs1, NULL, 0, 0, 0 },
1003*ea103259SMichael Clark     { "flq", rv_codec_i, rv_fmt_frd_offset_rs1, NULL, 0, 0, 0 },
1004*ea103259SMichael Clark     { "fsq", rv_codec_s, rv_fmt_frs2_offset_rs1, NULL, 0, 0, 0 },
1005*ea103259SMichael Clark     { "fmadd.q", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
1006*ea103259SMichael Clark     { "fmsub.q", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
1007*ea103259SMichael Clark     { "fnmsub.q", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
1008*ea103259SMichael Clark     { "fnmadd.q", rv_codec_r4_m, rv_fmt_rm_frd_frs1_frs2_frs3, NULL, 0, 0, 0 },
1009*ea103259SMichael Clark     { "fadd.q", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
1010*ea103259SMichael Clark     { "fsub.q", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
1011*ea103259SMichael Clark     { "fmul.q", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
1012*ea103259SMichael Clark     { "fdiv.q", rv_codec_r_m, rv_fmt_rm_frd_frs1_frs2, NULL, 0, 0, 0 },
1013*ea103259SMichael Clark     { "fsgnj.q", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnj_q, 0, 0, 0 },
1014*ea103259SMichael Clark     { "fsgnjn.q", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnjn_q, 0, 0, 0 },
1015*ea103259SMichael Clark     { "fsgnjx.q", rv_codec_r, rv_fmt_frd_frs1_frs2, rvcp_fsgnjx_q, 0, 0, 0 },
1016*ea103259SMichael Clark     { "fmin.q", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
1017*ea103259SMichael Clark     { "fmax.q", rv_codec_r, rv_fmt_frd_frs1_frs2, NULL, 0, 0, 0 },
1018*ea103259SMichael Clark     { "fcvt.s.q", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
1019*ea103259SMichael Clark     { "fcvt.q.s", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
1020*ea103259SMichael Clark     { "fcvt.d.q", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
1021*ea103259SMichael Clark     { "fcvt.q.d", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
1022*ea103259SMichael Clark     { "fsqrt.q", rv_codec_r_m, rv_fmt_rm_frd_frs1, NULL, 0, 0, 0 },
1023*ea103259SMichael Clark     { "fle.q", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
1024*ea103259SMichael Clark     { "flt.q", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
1025*ea103259SMichael Clark     { "feq.q", rv_codec_r, rv_fmt_rd_frs1_frs2, NULL, 0, 0, 0 },
1026*ea103259SMichael Clark     { "fcvt.w.q", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
1027*ea103259SMichael Clark     { "fcvt.wu.q", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
1028*ea103259SMichael Clark     { "fcvt.q.w", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
1029*ea103259SMichael Clark     { "fcvt.q.wu", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
1030*ea103259SMichael Clark     { "fclass.q", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
1031*ea103259SMichael Clark     { "fcvt.l.q", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
1032*ea103259SMichael Clark     { "fcvt.lu.q", rv_codec_r_m, rv_fmt_rm_rd_frs1, NULL, 0, 0, 0 },
1033*ea103259SMichael Clark     { "fcvt.q.l", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
1034*ea103259SMichael Clark     { "fcvt.q.lu", rv_codec_r_m, rv_fmt_rm_frd_rs1, NULL, 0, 0, 0 },
1035*ea103259SMichael Clark     { "fmv.x.q", rv_codec_r, rv_fmt_rd_frs1, NULL, 0, 0, 0 },
1036*ea103259SMichael Clark     { "fmv.q.x", rv_codec_r, rv_fmt_frd_rs1, NULL, 0, 0, 0 },
1037*ea103259SMichael Clark     { "c.addi4spn", rv_codec_ciw_4spn, rv_fmt_rd_rs1_imm, NULL, rv_op_addi, rv_op_addi, rv_op_addi },
1038*ea103259SMichael Clark     { "c.fld", rv_codec_cl_ld, rv_fmt_frd_offset_rs1, NULL, rv_op_fld, rv_op_fld, 0 },
1039*ea103259SMichael Clark     { "c.lw", rv_codec_cl_lw, rv_fmt_rd_offset_rs1, NULL, rv_op_lw, rv_op_lw, rv_op_lw },
1040*ea103259SMichael Clark     { "c.flw", rv_codec_cl_lw, rv_fmt_frd_offset_rs1, NULL, rv_op_flw, 0, 0 },
1041*ea103259SMichael Clark     { "c.fsd", rv_codec_cs_sd, rv_fmt_frs2_offset_rs1, NULL, rv_op_fsd, rv_op_fsd, 0 },
1042*ea103259SMichael Clark     { "c.sw", rv_codec_cs_sw, rv_fmt_rs2_offset_rs1, NULL, rv_op_sw, rv_op_sw, rv_op_sw },
1043*ea103259SMichael Clark     { "c.fsw", rv_codec_cs_sw, rv_fmt_frs2_offset_rs1, NULL, rv_op_fsw, 0, 0 },
1044*ea103259SMichael Clark     { "c.nop", rv_codec_ci_none, rv_fmt_none, NULL, rv_op_addi, rv_op_addi, rv_op_addi },
1045*ea103259SMichael Clark     { "c.addi", rv_codec_ci, rv_fmt_rd_rs1_imm, NULL, rv_op_addi, rv_op_addi, rv_op_addi },
1046*ea103259SMichael Clark     { "c.jal", rv_codec_cj_jal, rv_fmt_rd_offset, NULL, rv_op_jal, 0, 0 },
1047*ea103259SMichael Clark     { "c.li", rv_codec_ci_li, rv_fmt_rd_rs1_imm, NULL, rv_op_addi, rv_op_addi, rv_op_addi },
1048*ea103259SMichael Clark     { "c.addi16sp", rv_codec_ci_16sp, rv_fmt_rd_rs1_imm, NULL, rv_op_addi, rv_op_addi, rv_op_addi },
1049*ea103259SMichael Clark     { "c.lui", rv_codec_ci_lui, rv_fmt_rd_imm, NULL, rv_op_lui, rv_op_lui, rv_op_lui },
1050*ea103259SMichael Clark     { "c.srli", rv_codec_cb_sh6, rv_fmt_rd_rs1_imm, NULL, rv_op_srli, rv_op_srli, rv_op_srli },
1051*ea103259SMichael Clark     { "c.srai", rv_codec_cb_sh6, rv_fmt_rd_rs1_imm, NULL, rv_op_srai, rv_op_srai, rv_op_srai },
1052*ea103259SMichael Clark     { "c.andi", rv_codec_cb_imm, rv_fmt_rd_rs1_imm, NULL, rv_op_andi, rv_op_andi, rv_op_andi },
1053*ea103259SMichael Clark     { "c.sub", rv_codec_cs, rv_fmt_rd_rs1_rs2, NULL, rv_op_sub, rv_op_sub, rv_op_sub },
1054*ea103259SMichael Clark     { "c.xor", rv_codec_cs, rv_fmt_rd_rs1_rs2, NULL, rv_op_xor, rv_op_xor, rv_op_xor },
1055*ea103259SMichael Clark     { "c.or", rv_codec_cs, rv_fmt_rd_rs1_rs2, NULL, rv_op_or, rv_op_or, rv_op_or },
1056*ea103259SMichael Clark     { "c.and", rv_codec_cs, rv_fmt_rd_rs1_rs2, NULL, rv_op_and, rv_op_and, rv_op_and },
1057*ea103259SMichael Clark     { "c.subw", rv_codec_cs, rv_fmt_rd_rs1_rs2, NULL, rv_op_subw, rv_op_subw, rv_op_subw },
1058*ea103259SMichael Clark     { "c.addw", rv_codec_cs, rv_fmt_rd_rs1_rs2, NULL, rv_op_addw, rv_op_addw, rv_op_addw },
1059*ea103259SMichael Clark     { "c.j", rv_codec_cj, rv_fmt_rd_offset, NULL, rv_op_jal, rv_op_jal, rv_op_jal },
1060*ea103259SMichael Clark     { "c.beqz", rv_codec_cb, rv_fmt_rs1_rs2_offset, NULL, rv_op_beq, rv_op_beq, rv_op_beq },
1061*ea103259SMichael Clark     { "c.bnez", rv_codec_cb, rv_fmt_rs1_rs2_offset, NULL, rv_op_bne, rv_op_bne, rv_op_bne },
1062*ea103259SMichael Clark     { "c.slli", rv_codec_ci_sh6, rv_fmt_rd_rs1_imm, NULL, rv_op_slli, rv_op_slli, rv_op_slli },
1063*ea103259SMichael Clark     { "c.fldsp", rv_codec_ci_ldsp, rv_fmt_frd_offset_rs1, NULL, rv_op_fld, rv_op_fld, rv_op_fld },
1064*ea103259SMichael Clark     { "c.lwsp", rv_codec_ci_lwsp, rv_fmt_rd_offset_rs1, NULL, rv_op_lw, rv_op_lw, rv_op_lw },
1065*ea103259SMichael Clark     { "c.flwsp", rv_codec_ci_lwsp, rv_fmt_frd_offset_rs1, NULL, rv_op_flw, 0, 0 },
1066*ea103259SMichael Clark     { "c.jr", rv_codec_cr_jr, rv_fmt_rd_rs1_offset, NULL, rv_op_jalr, rv_op_jalr, rv_op_jalr },
1067*ea103259SMichael Clark     { "c.mv", rv_codec_cr_mv, rv_fmt_rd_rs1_rs2, NULL, rv_op_addi, rv_op_addi, rv_op_addi },
1068*ea103259SMichael Clark     { "c.ebreak", rv_codec_ci_none, rv_fmt_none, NULL, rv_op_ebreak, rv_op_ebreak, rv_op_ebreak },
1069*ea103259SMichael Clark     { "c.jalr", rv_codec_cr_jalr, rv_fmt_rd_rs1_offset, NULL, rv_op_jalr, rv_op_jalr, rv_op_jalr },
1070*ea103259SMichael Clark     { "c.add", rv_codec_cr, rv_fmt_rd_rs1_rs2, NULL, rv_op_add, rv_op_add, rv_op_add },
1071*ea103259SMichael Clark     { "c.fsdsp", rv_codec_css_sdsp, rv_fmt_frs2_offset_rs1, NULL, rv_op_fsd, rv_op_fsd, rv_op_fsd },
1072*ea103259SMichael Clark     { "c.swsp", rv_codec_css_swsp, rv_fmt_rs2_offset_rs1, NULL, rv_op_sw, rv_op_sw, rv_op_sw },
1073*ea103259SMichael Clark     { "c.fswsp", rv_codec_css_swsp, rv_fmt_frs2_offset_rs1, NULL, rv_op_fsw, 0, 0 },
1074*ea103259SMichael Clark     { "c.ld", rv_codec_cl_ld, rv_fmt_rd_offset_rs1, NULL, 0, rv_op_ld, rv_op_ld },
1075*ea103259SMichael Clark     { "c.sd", rv_codec_cs_sd, rv_fmt_rs2_offset_rs1, NULL, 0, rv_op_sd, rv_op_sd },
1076*ea103259SMichael Clark     { "c.addiw", rv_codec_ci, rv_fmt_rd_rs1_imm, NULL, 0, rv_op_addiw, rv_op_addiw },
1077*ea103259SMichael Clark     { "c.ldsp", rv_codec_ci_ldsp, rv_fmt_rd_offset_rs1, NULL, 0, rv_op_ld, rv_op_ld },
1078*ea103259SMichael Clark     { "c.sdsp", rv_codec_css_sdsp, rv_fmt_rs2_offset_rs1, NULL, 0, rv_op_sd, rv_op_sd },
1079*ea103259SMichael Clark     { "c.lq", rv_codec_cl_lq, rv_fmt_rd_offset_rs1, NULL, 0, 0, rv_op_lq },
1080*ea103259SMichael Clark     { "c.sq", rv_codec_cs_sq, rv_fmt_rs2_offset_rs1, NULL, 0, 0, rv_op_sq },
1081*ea103259SMichael Clark     { "c.lqsp", rv_codec_ci_lqsp, rv_fmt_rd_offset_rs1, NULL, 0, 0, rv_op_lq },
1082*ea103259SMichael Clark     { "c.sqsp", rv_codec_css_sqsp, rv_fmt_rs2_offset_rs1, NULL, 0, 0, rv_op_sq },
1083*ea103259SMichael Clark     { "nop", rv_codec_i, rv_fmt_none, NULL, 0, 0, 0 },
1084*ea103259SMichael Clark     { "mv", rv_codec_i, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1085*ea103259SMichael Clark     { "not", rv_codec_i, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1086*ea103259SMichael Clark     { "neg", rv_codec_r, rv_fmt_rd_rs2, NULL, 0, 0, 0 },
1087*ea103259SMichael Clark     { "negw", rv_codec_r, rv_fmt_rd_rs2, NULL, 0, 0, 0 },
1088*ea103259SMichael Clark     { "sext.w", rv_codec_i, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1089*ea103259SMichael Clark     { "seqz", rv_codec_i, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1090*ea103259SMichael Clark     { "snez", rv_codec_r, rv_fmt_rd_rs2, NULL, 0, 0, 0 },
1091*ea103259SMichael Clark     { "sltz", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1092*ea103259SMichael Clark     { "sgtz", rv_codec_r, rv_fmt_rd_rs2, NULL, 0, 0, 0 },
1093*ea103259SMichael Clark     { "fmv.s", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1094*ea103259SMichael Clark     { "fabs.s", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1095*ea103259SMichael Clark     { "fneg.s", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1096*ea103259SMichael Clark     { "fmv.d", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1097*ea103259SMichael Clark     { "fabs.d", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1098*ea103259SMichael Clark     { "fneg.d", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1099*ea103259SMichael Clark     { "fmv.q", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1100*ea103259SMichael Clark     { "fabs.q", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1101*ea103259SMichael Clark     { "fneg.q", rv_codec_r, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1102*ea103259SMichael Clark     { "beqz", rv_codec_sb, rv_fmt_rs1_offset, NULL, 0, 0, 0 },
1103*ea103259SMichael Clark     { "bnez", rv_codec_sb, rv_fmt_rs1_offset, NULL, 0, 0, 0 },
1104*ea103259SMichael Clark     { "blez", rv_codec_sb, rv_fmt_rs2_offset, NULL, 0, 0, 0 },
1105*ea103259SMichael Clark     { "bgez", rv_codec_sb, rv_fmt_rs1_offset, NULL, 0, 0, 0 },
1106*ea103259SMichael Clark     { "bltz", rv_codec_sb, rv_fmt_rs1_offset, NULL, 0, 0, 0 },
1107*ea103259SMichael Clark     { "bgtz", rv_codec_sb, rv_fmt_rs2_offset, NULL, 0, 0, 0 },
1108*ea103259SMichael Clark     { "ble", rv_codec_sb, rv_fmt_rs2_rs1_offset, NULL, 0, 0, 0 },
1109*ea103259SMichael Clark     { "bleu", rv_codec_sb, rv_fmt_rs2_rs1_offset, NULL, 0, 0, 0 },
1110*ea103259SMichael Clark     { "bgt", rv_codec_sb, rv_fmt_rs2_rs1_offset, NULL, 0, 0, 0 },
1111*ea103259SMichael Clark     { "bgtu", rv_codec_sb, rv_fmt_rs2_rs1_offset, NULL, 0, 0, 0 },
1112*ea103259SMichael Clark     { "j", rv_codec_uj, rv_fmt_offset, NULL, 0, 0, 0 },
1113*ea103259SMichael Clark     { "ret", rv_codec_i, rv_fmt_none, NULL, 0, 0, 0 },
1114*ea103259SMichael Clark     { "jr", rv_codec_i, rv_fmt_rs1, NULL, 0, 0, 0 },
1115*ea103259SMichael Clark     { "rdcycle", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1116*ea103259SMichael Clark     { "rdtime", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1117*ea103259SMichael Clark     { "rdinstret", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1118*ea103259SMichael Clark     { "rdcycleh", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1119*ea103259SMichael Clark     { "rdtimeh", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1120*ea103259SMichael Clark     { "rdinstreth", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1121*ea103259SMichael Clark     { "frcsr", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1122*ea103259SMichael Clark     { "frrm", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1123*ea103259SMichael Clark     { "frflags", rv_codec_i_csr, rv_fmt_rd, NULL, 0, 0, 0 },
1124*ea103259SMichael Clark     { "fscsr", rv_codec_i_csr, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1125*ea103259SMichael Clark     { "fsrm", rv_codec_i_csr, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1126*ea103259SMichael Clark     { "fsflags", rv_codec_i_csr, rv_fmt_rd_rs1, NULL, 0, 0, 0 },
1127*ea103259SMichael Clark     { "fsrmi", rv_codec_i_csr, rv_fmt_rd_zimm, NULL, 0, 0, 0 },
1128*ea103259SMichael Clark     { "fsflagsi", rv_codec_i_csr, rv_fmt_rd_zimm, NULL, 0, 0, 0 },
1129*ea103259SMichael Clark };
1130*ea103259SMichael Clark 
1131*ea103259SMichael Clark /* CSR names */
1132*ea103259SMichael Clark 
1133*ea103259SMichael Clark static const char *csr_name(int csrno)
1134*ea103259SMichael Clark {
1135*ea103259SMichael Clark     switch (csrno) {
1136*ea103259SMichael Clark     case 0x0000: return "ustatus";
1137*ea103259SMichael Clark     case 0x0001: return "fflags";
1138*ea103259SMichael Clark     case 0x0002: return "frm";
1139*ea103259SMichael Clark     case 0x0003: return "fcsr";
1140*ea103259SMichael Clark     case 0x0004: return "uie";
1141*ea103259SMichael Clark     case 0x0005: return "utvec";
1142*ea103259SMichael Clark     case 0x0040: return "uscratch";
1143*ea103259SMichael Clark     case 0x0041: return "uepc";
1144*ea103259SMichael Clark     case 0x0042: return "ucause";
1145*ea103259SMichael Clark     case 0x0043: return "utval";
1146*ea103259SMichael Clark     case 0x0044: return "uip";
1147*ea103259SMichael Clark     case 0x0100: return "sstatus";
1148*ea103259SMichael Clark     case 0x0102: return "sedeleg";
1149*ea103259SMichael Clark     case 0x0103: return "sideleg";
1150*ea103259SMichael Clark     case 0x0104: return "sie";
1151*ea103259SMichael Clark     case 0x0105: return "stvec";
1152*ea103259SMichael Clark     case 0x0106: return "scounteren";
1153*ea103259SMichael Clark     case 0x0140: return "sscratch";
1154*ea103259SMichael Clark     case 0x0141: return "sepc";
1155*ea103259SMichael Clark     case 0x0142: return "scause";
1156*ea103259SMichael Clark     case 0x0143: return "stval";
1157*ea103259SMichael Clark     case 0x0144: return "sip";
1158*ea103259SMichael Clark     case 0x0180: return "satp";
1159*ea103259SMichael Clark     case 0x0200: return "hstatus";
1160*ea103259SMichael Clark     case 0x0202: return "hedeleg";
1161*ea103259SMichael Clark     case 0x0203: return "hideleg";
1162*ea103259SMichael Clark     case 0x0204: return "hie";
1163*ea103259SMichael Clark     case 0x0205: return "htvec";
1164*ea103259SMichael Clark     case 0x0240: return "hscratch";
1165*ea103259SMichael Clark     case 0x0241: return "hepc";
1166*ea103259SMichael Clark     case 0x0242: return "hcause";
1167*ea103259SMichael Clark     case 0x0243: return "hbadaddr";
1168*ea103259SMichael Clark     case 0x0244: return "hip";
1169*ea103259SMichael Clark     case 0x0300: return "mstatus";
1170*ea103259SMichael Clark     case 0x0301: return "misa";
1171*ea103259SMichael Clark     case 0x0302: return "medeleg";
1172*ea103259SMichael Clark     case 0x0303: return "mideleg";
1173*ea103259SMichael Clark     case 0x0304: return "mie";
1174*ea103259SMichael Clark     case 0x0305: return "mtvec";
1175*ea103259SMichael Clark     case 0x0306: return "mcounteren";
1176*ea103259SMichael Clark     case 0x0320: return "mucounteren";
1177*ea103259SMichael Clark     case 0x0321: return "mscounteren";
1178*ea103259SMichael Clark     case 0x0322: return "mhcounteren";
1179*ea103259SMichael Clark     case 0x0323: return "mhpmevent3";
1180*ea103259SMichael Clark     case 0x0324: return "mhpmevent4";
1181*ea103259SMichael Clark     case 0x0325: return "mhpmevent5";
1182*ea103259SMichael Clark     case 0x0326: return "mhpmevent6";
1183*ea103259SMichael Clark     case 0x0327: return "mhpmevent7";
1184*ea103259SMichael Clark     case 0x0328: return "mhpmevent8";
1185*ea103259SMichael Clark     case 0x0329: return "mhpmevent9";
1186*ea103259SMichael Clark     case 0x032a: return "mhpmevent10";
1187*ea103259SMichael Clark     case 0x032b: return "mhpmevent11";
1188*ea103259SMichael Clark     case 0x032c: return "mhpmevent12";
1189*ea103259SMichael Clark     case 0x032d: return "mhpmevent13";
1190*ea103259SMichael Clark     case 0x032e: return "mhpmevent14";
1191*ea103259SMichael Clark     case 0x032f: return "mhpmevent15";
1192*ea103259SMichael Clark     case 0x0330: return "mhpmevent16";
1193*ea103259SMichael Clark     case 0x0331: return "mhpmevent17";
1194*ea103259SMichael Clark     case 0x0332: return "mhpmevent18";
1195*ea103259SMichael Clark     case 0x0333: return "mhpmevent19";
1196*ea103259SMichael Clark     case 0x0334: return "mhpmevent20";
1197*ea103259SMichael Clark     case 0x0335: return "mhpmevent21";
1198*ea103259SMichael Clark     case 0x0336: return "mhpmevent22";
1199*ea103259SMichael Clark     case 0x0337: return "mhpmevent23";
1200*ea103259SMichael Clark     case 0x0338: return "mhpmevent24";
1201*ea103259SMichael Clark     case 0x0339: return "mhpmevent25";
1202*ea103259SMichael Clark     case 0x033a: return "mhpmevent26";
1203*ea103259SMichael Clark     case 0x033b: return "mhpmevent27";
1204*ea103259SMichael Clark     case 0x033c: return "mhpmevent28";
1205*ea103259SMichael Clark     case 0x033d: return "mhpmevent29";
1206*ea103259SMichael Clark     case 0x033e: return "mhpmevent30";
1207*ea103259SMichael Clark     case 0x033f: return "mhpmevent31";
1208*ea103259SMichael Clark     case 0x0340: return "mscratch";
1209*ea103259SMichael Clark     case 0x0341: return "mepc";
1210*ea103259SMichael Clark     case 0x0342: return "mcause";
1211*ea103259SMichael Clark     case 0x0343: return "mtval";
1212*ea103259SMichael Clark     case 0x0344: return "mip";
1213*ea103259SMichael Clark     case 0x0380: return "mbase";
1214*ea103259SMichael Clark     case 0x0381: return "mbound";
1215*ea103259SMichael Clark     case 0x0382: return "mibase";
1216*ea103259SMichael Clark     case 0x0383: return "mibound";
1217*ea103259SMichael Clark     case 0x0384: return "mdbase";
1218*ea103259SMichael Clark     case 0x0385: return "mdbound";
1219*ea103259SMichael Clark     case 0x03a0: return "pmpcfg3";
1220*ea103259SMichael Clark     case 0x03b0: return "pmpaddr0";
1221*ea103259SMichael Clark     case 0x03b1: return "pmpaddr1";
1222*ea103259SMichael Clark     case 0x03b2: return "pmpaddr2";
1223*ea103259SMichael Clark     case 0x03b3: return "pmpaddr3";
1224*ea103259SMichael Clark     case 0x03b4: return "pmpaddr4";
1225*ea103259SMichael Clark     case 0x03b5: return "pmpaddr5";
1226*ea103259SMichael Clark     case 0x03b6: return "pmpaddr6";
1227*ea103259SMichael Clark     case 0x03b7: return "pmpaddr7";
1228*ea103259SMichael Clark     case 0x03b8: return "pmpaddr8";
1229*ea103259SMichael Clark     case 0x03b9: return "pmpaddr9";
1230*ea103259SMichael Clark     case 0x03ba: return "pmpaddr10";
1231*ea103259SMichael Clark     case 0x03bb: return "pmpaddr11";
1232*ea103259SMichael Clark     case 0x03bc: return "pmpaddr12";
1233*ea103259SMichael Clark     case 0x03bd: return "pmpaddr14";
1234*ea103259SMichael Clark     case 0x03be: return "pmpaddr13";
1235*ea103259SMichael Clark     case 0x03bf: return "pmpaddr15";
1236*ea103259SMichael Clark     case 0x0780: return "mtohost";
1237*ea103259SMichael Clark     case 0x0781: return "mfromhost";
1238*ea103259SMichael Clark     case 0x0782: return "mreset";
1239*ea103259SMichael Clark     case 0x0783: return "mipi";
1240*ea103259SMichael Clark     case 0x0784: return "miobase";
1241*ea103259SMichael Clark     case 0x07a0: return "tselect";
1242*ea103259SMichael Clark     case 0x07a1: return "tdata1";
1243*ea103259SMichael Clark     case 0x07a2: return "tdata2";
1244*ea103259SMichael Clark     case 0x07a3: return "tdata3";
1245*ea103259SMichael Clark     case 0x07b0: return "dcsr";
1246*ea103259SMichael Clark     case 0x07b1: return "dpc";
1247*ea103259SMichael Clark     case 0x07b2: return "dscratch";
1248*ea103259SMichael Clark     case 0x0b00: return "mcycle";
1249*ea103259SMichael Clark     case 0x0b01: return "mtime";
1250*ea103259SMichael Clark     case 0x0b02: return "minstret";
1251*ea103259SMichael Clark     case 0x0b03: return "mhpmcounter3";
1252*ea103259SMichael Clark     case 0x0b04: return "mhpmcounter4";
1253*ea103259SMichael Clark     case 0x0b05: return "mhpmcounter5";
1254*ea103259SMichael Clark     case 0x0b06: return "mhpmcounter6";
1255*ea103259SMichael Clark     case 0x0b07: return "mhpmcounter7";
1256*ea103259SMichael Clark     case 0x0b08: return "mhpmcounter8";
1257*ea103259SMichael Clark     case 0x0b09: return "mhpmcounter9";
1258*ea103259SMichael Clark     case 0x0b0a: return "mhpmcounter10";
1259*ea103259SMichael Clark     case 0x0b0b: return "mhpmcounter11";
1260*ea103259SMichael Clark     case 0x0b0c: return "mhpmcounter12";
1261*ea103259SMichael Clark     case 0x0b0d: return "mhpmcounter13";
1262*ea103259SMichael Clark     case 0x0b0e: return "mhpmcounter14";
1263*ea103259SMichael Clark     case 0x0b0f: return "mhpmcounter15";
1264*ea103259SMichael Clark     case 0x0b10: return "mhpmcounter16";
1265*ea103259SMichael Clark     case 0x0b11: return "mhpmcounter17";
1266*ea103259SMichael Clark     case 0x0b12: return "mhpmcounter18";
1267*ea103259SMichael Clark     case 0x0b13: return "mhpmcounter19";
1268*ea103259SMichael Clark     case 0x0b14: return "mhpmcounter20";
1269*ea103259SMichael Clark     case 0x0b15: return "mhpmcounter21";
1270*ea103259SMichael Clark     case 0x0b16: return "mhpmcounter22";
1271*ea103259SMichael Clark     case 0x0b17: return "mhpmcounter23";
1272*ea103259SMichael Clark     case 0x0b18: return "mhpmcounter24";
1273*ea103259SMichael Clark     case 0x0b19: return "mhpmcounter25";
1274*ea103259SMichael Clark     case 0x0b1a: return "mhpmcounter26";
1275*ea103259SMichael Clark     case 0x0b1b: return "mhpmcounter27";
1276*ea103259SMichael Clark     case 0x0b1c: return "mhpmcounter28";
1277*ea103259SMichael Clark     case 0x0b1d: return "mhpmcounter29";
1278*ea103259SMichael Clark     case 0x0b1e: return "mhpmcounter30";
1279*ea103259SMichael Clark     case 0x0b1f: return "mhpmcounter31";
1280*ea103259SMichael Clark     case 0x0b80: return "mcycleh";
1281*ea103259SMichael Clark     case 0x0b81: return "mtimeh";
1282*ea103259SMichael Clark     case 0x0b82: return "minstreth";
1283*ea103259SMichael Clark     case 0x0b83: return "mhpmcounter3h";
1284*ea103259SMichael Clark     case 0x0b84: return "mhpmcounter4h";
1285*ea103259SMichael Clark     case 0x0b85: return "mhpmcounter5h";
1286*ea103259SMichael Clark     case 0x0b86: return "mhpmcounter6h";
1287*ea103259SMichael Clark     case 0x0b87: return "mhpmcounter7h";
1288*ea103259SMichael Clark     case 0x0b88: return "mhpmcounter8h";
1289*ea103259SMichael Clark     case 0x0b89: return "mhpmcounter9h";
1290*ea103259SMichael Clark     case 0x0b8a: return "mhpmcounter10h";
1291*ea103259SMichael Clark     case 0x0b8b: return "mhpmcounter11h";
1292*ea103259SMichael Clark     case 0x0b8c: return "mhpmcounter12h";
1293*ea103259SMichael Clark     case 0x0b8d: return "mhpmcounter13h";
1294*ea103259SMichael Clark     case 0x0b8e: return "mhpmcounter14h";
1295*ea103259SMichael Clark     case 0x0b8f: return "mhpmcounter15h";
1296*ea103259SMichael Clark     case 0x0b90: return "mhpmcounter16h";
1297*ea103259SMichael Clark     case 0x0b91: return "mhpmcounter17h";
1298*ea103259SMichael Clark     case 0x0b92: return "mhpmcounter18h";
1299*ea103259SMichael Clark     case 0x0b93: return "mhpmcounter19h";
1300*ea103259SMichael Clark     case 0x0b94: return "mhpmcounter20h";
1301*ea103259SMichael Clark     case 0x0b95: return "mhpmcounter21h";
1302*ea103259SMichael Clark     case 0x0b96: return "mhpmcounter22h";
1303*ea103259SMichael Clark     case 0x0b97: return "mhpmcounter23h";
1304*ea103259SMichael Clark     case 0x0b98: return "mhpmcounter24h";
1305*ea103259SMichael Clark     case 0x0b99: return "mhpmcounter25h";
1306*ea103259SMichael Clark     case 0x0b9a: return "mhpmcounter26h";
1307*ea103259SMichael Clark     case 0x0b9b: return "mhpmcounter27h";
1308*ea103259SMichael Clark     case 0x0b9c: return "mhpmcounter28h";
1309*ea103259SMichael Clark     case 0x0b9d: return "mhpmcounter29h";
1310*ea103259SMichael Clark     case 0x0b9e: return "mhpmcounter30h";
1311*ea103259SMichael Clark     case 0x0b9f: return "mhpmcounter31h";
1312*ea103259SMichael Clark     case 0x0c00: return "cycle";
1313*ea103259SMichael Clark     case 0x0c01: return "time";
1314*ea103259SMichael Clark     case 0x0c02: return "instret";
1315*ea103259SMichael Clark     case 0x0c80: return "cycleh";
1316*ea103259SMichael Clark     case 0x0c81: return "timeh";
1317*ea103259SMichael Clark     case 0x0c82: return "instreth";
1318*ea103259SMichael Clark     case 0x0d00: return "scycle";
1319*ea103259SMichael Clark     case 0x0d01: return "stime";
1320*ea103259SMichael Clark     case 0x0d02: return "sinstret";
1321*ea103259SMichael Clark     case 0x0d80: return "scycleh";
1322*ea103259SMichael Clark     case 0x0d81: return "stimeh";
1323*ea103259SMichael Clark     case 0x0d82: return "sinstreth";
1324*ea103259SMichael Clark     case 0x0e00: return "hcycle";
1325*ea103259SMichael Clark     case 0x0e01: return "htime";
1326*ea103259SMichael Clark     case 0x0e02: return "hinstret";
1327*ea103259SMichael Clark     case 0x0e80: return "hcycleh";
1328*ea103259SMichael Clark     case 0x0e81: return "htimeh";
1329*ea103259SMichael Clark     case 0x0e82: return "hinstreth";
1330*ea103259SMichael Clark     case 0x0f11: return "mvendorid";
1331*ea103259SMichael Clark     case 0x0f12: return "marchid";
1332*ea103259SMichael Clark     case 0x0f13: return "mimpid";
1333*ea103259SMichael Clark     case 0x0f14: return "mhartid";
1334*ea103259SMichael Clark     default: return NULL;
1335*ea103259SMichael Clark     }
1336*ea103259SMichael Clark }
1337*ea103259SMichael Clark 
1338*ea103259SMichael Clark /* decode opcode */
1339*ea103259SMichael Clark 
1340*ea103259SMichael Clark static void decode_inst_opcode(rv_decode *dec, rv_isa isa)
1341*ea103259SMichael Clark {
1342*ea103259SMichael Clark     rv_inst inst = dec->inst;
1343*ea103259SMichael Clark     rv_opcode op = rv_op_illegal;
1344*ea103259SMichael Clark     switch (((inst >> 0) & 0b11)) {
1345*ea103259SMichael Clark     case 0:
1346*ea103259SMichael Clark         switch (((inst >> 13) & 0b111)) {
1347*ea103259SMichael Clark         case 0: op = rv_op_c_addi4spn; break;
1348*ea103259SMichael Clark         case 1:
1349*ea103259SMichael Clark             if (isa == rv128) {
1350*ea103259SMichael Clark                 op = rv_op_c_lq;
1351*ea103259SMichael Clark             } else {
1352*ea103259SMichael Clark                 op = rv_op_c_fld;
1353*ea103259SMichael Clark             }
1354*ea103259SMichael Clark             break;
1355*ea103259SMichael Clark         case 2: op = rv_op_c_lw; break;
1356*ea103259SMichael Clark         case 3:
1357*ea103259SMichael Clark             if (isa == rv32) {
1358*ea103259SMichael Clark                 op = rv_op_c_flw;
1359*ea103259SMichael Clark             } else {
1360*ea103259SMichael Clark                 op = rv_op_c_ld;
1361*ea103259SMichael Clark             }
1362*ea103259SMichael Clark             break;
1363*ea103259SMichael Clark         case 5:
1364*ea103259SMichael Clark             if (isa == rv128) {
1365*ea103259SMichael Clark                 op = rv_op_c_sq;
1366*ea103259SMichael Clark             } else {
1367*ea103259SMichael Clark                 op = rv_op_c_fsd;
1368*ea103259SMichael Clark             }
1369*ea103259SMichael Clark             break;
1370*ea103259SMichael Clark         case 6: op = rv_op_c_sw; break;
1371*ea103259SMichael Clark         case 7:
1372*ea103259SMichael Clark             if (isa == rv32) {
1373*ea103259SMichael Clark                 op = rv_op_c_fsw;
1374*ea103259SMichael Clark             } else {
1375*ea103259SMichael Clark                 op = rv_op_c_sd;
1376*ea103259SMichael Clark             }
1377*ea103259SMichael Clark             break;
1378*ea103259SMichael Clark         }
1379*ea103259SMichael Clark         break;
1380*ea103259SMichael Clark     case 1:
1381*ea103259SMichael Clark         switch (((inst >> 13) & 0b111)) {
1382*ea103259SMichael Clark         case 0:
1383*ea103259SMichael Clark             switch (((inst >> 2) & 0b11111111111)) {
1384*ea103259SMichael Clark             case 0: op = rv_op_c_nop; break;
1385*ea103259SMichael Clark             default: op = rv_op_c_addi; break;
1386*ea103259SMichael Clark             }
1387*ea103259SMichael Clark             break;
1388*ea103259SMichael Clark         case 1:
1389*ea103259SMichael Clark             if (isa == rv32) {
1390*ea103259SMichael Clark                 op = rv_op_c_jal;
1391*ea103259SMichael Clark             } else {
1392*ea103259SMichael Clark                 op = rv_op_c_addiw;
1393*ea103259SMichael Clark             }
1394*ea103259SMichael Clark             break;
1395*ea103259SMichael Clark         case 2: op = rv_op_c_li; break;
1396*ea103259SMichael Clark         case 3:
1397*ea103259SMichael Clark             switch (((inst >> 7) & 0b11111)) {
1398*ea103259SMichael Clark             case 2: op = rv_op_c_addi16sp; break;
1399*ea103259SMichael Clark             default: op = rv_op_c_lui; break;
1400*ea103259SMichael Clark             }
1401*ea103259SMichael Clark             break;
1402*ea103259SMichael Clark         case 4:
1403*ea103259SMichael Clark             switch (((inst >> 10) & 0b11)) {
1404*ea103259SMichael Clark             case 0:
1405*ea103259SMichael Clark                 op = rv_op_c_srli;
1406*ea103259SMichael Clark                 break;
1407*ea103259SMichael Clark             case 1:
1408*ea103259SMichael Clark                 op = rv_op_c_srai;
1409*ea103259SMichael Clark                 break;
1410*ea103259SMichael Clark             case 2: op = rv_op_c_andi; break;
1411*ea103259SMichael Clark             case 3:
1412*ea103259SMichael Clark                 switch (((inst >> 10) & 0b100) | ((inst >> 5) & 0b011)) {
1413*ea103259SMichael Clark                 case 0: op = rv_op_c_sub; break;
1414*ea103259SMichael Clark                 case 1: op = rv_op_c_xor; break;
1415*ea103259SMichael Clark                 case 2: op = rv_op_c_or; break;
1416*ea103259SMichael Clark                 case 3: op = rv_op_c_and; break;
1417*ea103259SMichael Clark                 case 4: op = rv_op_c_subw; break;
1418*ea103259SMichael Clark                 case 5: op = rv_op_c_addw; break;
1419*ea103259SMichael Clark                 }
1420*ea103259SMichael Clark                 break;
1421*ea103259SMichael Clark             }
1422*ea103259SMichael Clark             break;
1423*ea103259SMichael Clark         case 5: op = rv_op_c_j; break;
1424*ea103259SMichael Clark         case 6: op = rv_op_c_beqz; break;
1425*ea103259SMichael Clark         case 7: op = rv_op_c_bnez; break;
1426*ea103259SMichael Clark         }
1427*ea103259SMichael Clark         break;
1428*ea103259SMichael Clark     case 2:
1429*ea103259SMichael Clark         switch (((inst >> 13) & 0b111)) {
1430*ea103259SMichael Clark         case 0:
1431*ea103259SMichael Clark             op = rv_op_c_slli;
1432*ea103259SMichael Clark             break;
1433*ea103259SMichael Clark         case 1:
1434*ea103259SMichael Clark             if (isa == rv128) {
1435*ea103259SMichael Clark                 op = rv_op_c_lqsp;
1436*ea103259SMichael Clark             } else {
1437*ea103259SMichael Clark                 op = rv_op_c_fldsp;
1438*ea103259SMichael Clark             }
1439*ea103259SMichael Clark             break;
1440*ea103259SMichael Clark         case 2: op = rv_op_c_lwsp; break;
1441*ea103259SMichael Clark         case 3:
1442*ea103259SMichael Clark             if (isa == rv32) {
1443*ea103259SMichael Clark                 op = rv_op_c_flwsp;
1444*ea103259SMichael Clark             } else {
1445*ea103259SMichael Clark                 op = rv_op_c_ldsp;
1446*ea103259SMichael Clark             }
1447*ea103259SMichael Clark             break;
1448*ea103259SMichael Clark         case 4:
1449*ea103259SMichael Clark             switch (((inst >> 12) & 0b1)) {
1450*ea103259SMichael Clark             case 0:
1451*ea103259SMichael Clark                 switch (((inst >> 2) & 0b11111)) {
1452*ea103259SMichael Clark                 case 0: op = rv_op_c_jr; break;
1453*ea103259SMichael Clark                 default: op = rv_op_c_mv; break;
1454*ea103259SMichael Clark                 }
1455*ea103259SMichael Clark                 break;
1456*ea103259SMichael Clark             case 1:
1457*ea103259SMichael Clark                 switch (((inst >> 2) & 0b11111)) {
1458*ea103259SMichael Clark                 case 0:
1459*ea103259SMichael Clark                     switch (((inst >> 7) & 0b11111)) {
1460*ea103259SMichael Clark                     case 0: op = rv_op_c_ebreak; break;
1461*ea103259SMichael Clark                     default: op = rv_op_c_jalr; break;
1462*ea103259SMichael Clark                     }
1463*ea103259SMichael Clark                     break;
1464*ea103259SMichael Clark                 default: op = rv_op_c_add; break;
1465*ea103259SMichael Clark                 }
1466*ea103259SMichael Clark                 break;
1467*ea103259SMichael Clark             }
1468*ea103259SMichael Clark             break;
1469*ea103259SMichael Clark         case 5:
1470*ea103259SMichael Clark             if (isa == rv128) {
1471*ea103259SMichael Clark                 op = rv_op_c_sqsp;
1472*ea103259SMichael Clark             } else {
1473*ea103259SMichael Clark                 op = rv_op_c_fsdsp; break;
1474*ea103259SMichael Clark             }
1475*ea103259SMichael Clark         case 6: op = rv_op_c_swsp; break;
1476*ea103259SMichael Clark         case 7:
1477*ea103259SMichael Clark             if (isa == rv32) {
1478*ea103259SMichael Clark                 op = rv_op_c_fswsp;
1479*ea103259SMichael Clark             } else {
1480*ea103259SMichael Clark                 op = rv_op_c_sdsp;
1481*ea103259SMichael Clark             }
1482*ea103259SMichael Clark             break;
1483*ea103259SMichael Clark         }
1484*ea103259SMichael Clark         break;
1485*ea103259SMichael Clark     case 3:
1486*ea103259SMichael Clark         switch (((inst >> 2) & 0b11111)) {
1487*ea103259SMichael Clark         case 0:
1488*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1489*ea103259SMichael Clark             case 0: op = rv_op_lb; break;
1490*ea103259SMichael Clark             case 1: op = rv_op_lh; break;
1491*ea103259SMichael Clark             case 2: op = rv_op_lw; break;
1492*ea103259SMichael Clark             case 3: op = rv_op_ld; break;
1493*ea103259SMichael Clark             case 4: op = rv_op_lbu; break;
1494*ea103259SMichael Clark             case 5: op = rv_op_lhu; break;
1495*ea103259SMichael Clark             case 6: op = rv_op_lwu; break;
1496*ea103259SMichael Clark             case 7: op = rv_op_ldu; break;
1497*ea103259SMichael Clark             }
1498*ea103259SMichael Clark             break;
1499*ea103259SMichael Clark         case 1:
1500*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1501*ea103259SMichael Clark             case 2: op = rv_op_flw; break;
1502*ea103259SMichael Clark             case 3: op = rv_op_fld; break;
1503*ea103259SMichael Clark             case 4: op = rv_op_flq; break;
1504*ea103259SMichael Clark             }
1505*ea103259SMichael Clark             break;
1506*ea103259SMichael Clark         case 3:
1507*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1508*ea103259SMichael Clark             case 0: op = rv_op_fence; break;
1509*ea103259SMichael Clark             case 1: op = rv_op_fence_i; break;
1510*ea103259SMichael Clark             case 2: op = rv_op_lq; break;
1511*ea103259SMichael Clark             }
1512*ea103259SMichael Clark             break;
1513*ea103259SMichael Clark         case 4:
1514*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1515*ea103259SMichael Clark             case 0: op = rv_op_addi; break;
1516*ea103259SMichael Clark             case 1:
1517*ea103259SMichael Clark                 switch (((inst >> 27) & 0b11111)) {
1518*ea103259SMichael Clark                 case 0: op = rv_op_slli; break;
1519*ea103259SMichael Clark                 }
1520*ea103259SMichael Clark                 break;
1521*ea103259SMichael Clark             case 2: op = rv_op_slti; break;
1522*ea103259SMichael Clark             case 3: op = rv_op_sltiu; break;
1523*ea103259SMichael Clark             case 4: op = rv_op_xori; break;
1524*ea103259SMichael Clark             case 5:
1525*ea103259SMichael Clark                 switch (((inst >> 27) & 0b11111)) {
1526*ea103259SMichael Clark                 case 0: op = rv_op_srli; break;
1527*ea103259SMichael Clark                 case 8: op = rv_op_srai; break;
1528*ea103259SMichael Clark                 }
1529*ea103259SMichael Clark                 break;
1530*ea103259SMichael Clark             case 6: op = rv_op_ori; break;
1531*ea103259SMichael Clark             case 7: op = rv_op_andi; break;
1532*ea103259SMichael Clark             }
1533*ea103259SMichael Clark             break;
1534*ea103259SMichael Clark         case 5: op = rv_op_auipc; break;
1535*ea103259SMichael Clark         case 6:
1536*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1537*ea103259SMichael Clark             case 0: op = rv_op_addiw; break;
1538*ea103259SMichael Clark             case 1:
1539*ea103259SMichael Clark                 switch (((inst >> 25) & 0b1111111)) {
1540*ea103259SMichael Clark                 case 0: op = rv_op_slliw; break;
1541*ea103259SMichael Clark                 }
1542*ea103259SMichael Clark                 break;
1543*ea103259SMichael Clark             case 5:
1544*ea103259SMichael Clark                 switch (((inst >> 25) & 0b1111111)) {
1545*ea103259SMichael Clark                 case 0: op = rv_op_srliw; break;
1546*ea103259SMichael Clark                 case 32: op = rv_op_sraiw; break;
1547*ea103259SMichael Clark                 }
1548*ea103259SMichael Clark                 break;
1549*ea103259SMichael Clark             }
1550*ea103259SMichael Clark             break;
1551*ea103259SMichael Clark         case 8:
1552*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1553*ea103259SMichael Clark             case 0: op = rv_op_sb; break;
1554*ea103259SMichael Clark             case 1: op = rv_op_sh; break;
1555*ea103259SMichael Clark             case 2: op = rv_op_sw; break;
1556*ea103259SMichael Clark             case 3: op = rv_op_sd; break;
1557*ea103259SMichael Clark             case 4: op = rv_op_sq; break;
1558*ea103259SMichael Clark             }
1559*ea103259SMichael Clark             break;
1560*ea103259SMichael Clark         case 9:
1561*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1562*ea103259SMichael Clark             case 2: op = rv_op_fsw; break;
1563*ea103259SMichael Clark             case 3: op = rv_op_fsd; break;
1564*ea103259SMichael Clark             case 4: op = rv_op_fsq; break;
1565*ea103259SMichael Clark             }
1566*ea103259SMichael Clark             break;
1567*ea103259SMichael Clark         case 11:
1568*ea103259SMichael Clark             switch (((inst >> 24) & 0b11111000) | ((inst >> 12) & 0b00000111)) {
1569*ea103259SMichael Clark             case 2: op = rv_op_amoadd_w; break;
1570*ea103259SMichael Clark             case 3: op = rv_op_amoadd_d; break;
1571*ea103259SMichael Clark             case 4: op = rv_op_amoadd_q; break;
1572*ea103259SMichael Clark             case 10: op = rv_op_amoswap_w; break;
1573*ea103259SMichael Clark             case 11: op = rv_op_amoswap_d; break;
1574*ea103259SMichael Clark             case 12: op = rv_op_amoswap_q; break;
1575*ea103259SMichael Clark             case 18:
1576*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1577*ea103259SMichael Clark                 case 0: op = rv_op_lr_w; break;
1578*ea103259SMichael Clark                 }
1579*ea103259SMichael Clark                 break;
1580*ea103259SMichael Clark             case 19:
1581*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1582*ea103259SMichael Clark                 case 0: op = rv_op_lr_d; break;
1583*ea103259SMichael Clark                 }
1584*ea103259SMichael Clark                 break;
1585*ea103259SMichael Clark             case 20:
1586*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1587*ea103259SMichael Clark                 case 0: op = rv_op_lr_q; break;
1588*ea103259SMichael Clark                 }
1589*ea103259SMichael Clark                 break;
1590*ea103259SMichael Clark             case 26: op = rv_op_sc_w; break;
1591*ea103259SMichael Clark             case 27: op = rv_op_sc_d; break;
1592*ea103259SMichael Clark             case 28: op = rv_op_sc_q; break;
1593*ea103259SMichael Clark             case 34: op = rv_op_amoxor_w; break;
1594*ea103259SMichael Clark             case 35: op = rv_op_amoxor_d; break;
1595*ea103259SMichael Clark             case 36: op = rv_op_amoxor_q; break;
1596*ea103259SMichael Clark             case 66: op = rv_op_amoor_w; break;
1597*ea103259SMichael Clark             case 67: op = rv_op_amoor_d; break;
1598*ea103259SMichael Clark             case 68: op = rv_op_amoor_q; break;
1599*ea103259SMichael Clark             case 98: op = rv_op_amoand_w; break;
1600*ea103259SMichael Clark             case 99: op = rv_op_amoand_d; break;
1601*ea103259SMichael Clark             case 100: op = rv_op_amoand_q; break;
1602*ea103259SMichael Clark             case 130: op = rv_op_amomin_w; break;
1603*ea103259SMichael Clark             case 131: op = rv_op_amomin_d; break;
1604*ea103259SMichael Clark             case 132: op = rv_op_amomin_q; break;
1605*ea103259SMichael Clark             case 162: op = rv_op_amomax_w; break;
1606*ea103259SMichael Clark             case 163: op = rv_op_amomax_d; break;
1607*ea103259SMichael Clark             case 164: op = rv_op_amomax_q; break;
1608*ea103259SMichael Clark             case 194: op = rv_op_amominu_w; break;
1609*ea103259SMichael Clark             case 195: op = rv_op_amominu_d; break;
1610*ea103259SMichael Clark             case 196: op = rv_op_amominu_q; break;
1611*ea103259SMichael Clark             case 226: op = rv_op_amomaxu_w; break;
1612*ea103259SMichael Clark             case 227: op = rv_op_amomaxu_d; break;
1613*ea103259SMichael Clark             case 228: op = rv_op_amomaxu_q; break;
1614*ea103259SMichael Clark             }
1615*ea103259SMichael Clark             break;
1616*ea103259SMichael Clark         case 12:
1617*ea103259SMichael Clark             switch (((inst >> 22) & 0b1111111000) | ((inst >> 12) & 0b0000000111)) {
1618*ea103259SMichael Clark             case 0: op = rv_op_add; break;
1619*ea103259SMichael Clark             case 1: op = rv_op_sll; break;
1620*ea103259SMichael Clark             case 2: op = rv_op_slt; break;
1621*ea103259SMichael Clark             case 3: op = rv_op_sltu; break;
1622*ea103259SMichael Clark             case 4: op = rv_op_xor; break;
1623*ea103259SMichael Clark             case 5: op = rv_op_srl; break;
1624*ea103259SMichael Clark             case 6: op = rv_op_or; break;
1625*ea103259SMichael Clark             case 7: op = rv_op_and; break;
1626*ea103259SMichael Clark             case 8: op = rv_op_mul; break;
1627*ea103259SMichael Clark             case 9: op = rv_op_mulh; break;
1628*ea103259SMichael Clark             case 10: op = rv_op_mulhsu; break;
1629*ea103259SMichael Clark             case 11: op = rv_op_mulhu; break;
1630*ea103259SMichael Clark             case 12: op = rv_op_div; break;
1631*ea103259SMichael Clark             case 13: op = rv_op_divu; break;
1632*ea103259SMichael Clark             case 14: op = rv_op_rem; break;
1633*ea103259SMichael Clark             case 15: op = rv_op_remu; break;
1634*ea103259SMichael Clark             case 256: op = rv_op_sub; break;
1635*ea103259SMichael Clark             case 261: op = rv_op_sra; break;
1636*ea103259SMichael Clark             }
1637*ea103259SMichael Clark             break;
1638*ea103259SMichael Clark         case 13: op = rv_op_lui; break;
1639*ea103259SMichael Clark         case 14:
1640*ea103259SMichael Clark             switch (((inst >> 22) & 0b1111111000) | ((inst >> 12) & 0b0000000111)) {
1641*ea103259SMichael Clark             case 0: op = rv_op_addw; break;
1642*ea103259SMichael Clark             case 1: op = rv_op_sllw; break;
1643*ea103259SMichael Clark             case 5: op = rv_op_srlw; break;
1644*ea103259SMichael Clark             case 8: op = rv_op_mulw; break;
1645*ea103259SMichael Clark             case 12: op = rv_op_divw; break;
1646*ea103259SMichael Clark             case 13: op = rv_op_divuw; break;
1647*ea103259SMichael Clark             case 14: op = rv_op_remw; break;
1648*ea103259SMichael Clark             case 15: op = rv_op_remuw; break;
1649*ea103259SMichael Clark             case 256: op = rv_op_subw; break;
1650*ea103259SMichael Clark             case 261: op = rv_op_sraw; break;
1651*ea103259SMichael Clark             }
1652*ea103259SMichael Clark             break;
1653*ea103259SMichael Clark         case 16:
1654*ea103259SMichael Clark             switch (((inst >> 25) & 0b11)) {
1655*ea103259SMichael Clark             case 0: op = rv_op_fmadd_s; break;
1656*ea103259SMichael Clark             case 1: op = rv_op_fmadd_d; break;
1657*ea103259SMichael Clark             case 3: op = rv_op_fmadd_q; break;
1658*ea103259SMichael Clark             }
1659*ea103259SMichael Clark             break;
1660*ea103259SMichael Clark         case 17:
1661*ea103259SMichael Clark             switch (((inst >> 25) & 0b11)) {
1662*ea103259SMichael Clark             case 0: op = rv_op_fmsub_s; break;
1663*ea103259SMichael Clark             case 1: op = rv_op_fmsub_d; break;
1664*ea103259SMichael Clark             case 3: op = rv_op_fmsub_q; break;
1665*ea103259SMichael Clark             }
1666*ea103259SMichael Clark             break;
1667*ea103259SMichael Clark         case 18:
1668*ea103259SMichael Clark             switch (((inst >> 25) & 0b11)) {
1669*ea103259SMichael Clark             case 0: op = rv_op_fnmsub_s; break;
1670*ea103259SMichael Clark             case 1: op = rv_op_fnmsub_d; break;
1671*ea103259SMichael Clark             case 3: op = rv_op_fnmsub_q; break;
1672*ea103259SMichael Clark             }
1673*ea103259SMichael Clark             break;
1674*ea103259SMichael Clark         case 19:
1675*ea103259SMichael Clark             switch (((inst >> 25) & 0b11)) {
1676*ea103259SMichael Clark             case 0: op = rv_op_fnmadd_s; break;
1677*ea103259SMichael Clark             case 1: op = rv_op_fnmadd_d; break;
1678*ea103259SMichael Clark             case 3: op = rv_op_fnmadd_q; break;
1679*ea103259SMichael Clark             }
1680*ea103259SMichael Clark             break;
1681*ea103259SMichael Clark         case 20:
1682*ea103259SMichael Clark             switch (((inst >> 25) & 0b1111111)) {
1683*ea103259SMichael Clark             case 0: op = rv_op_fadd_s; break;
1684*ea103259SMichael Clark             case 1: op = rv_op_fadd_d; break;
1685*ea103259SMichael Clark             case 3: op = rv_op_fadd_q; break;
1686*ea103259SMichael Clark             case 4: op = rv_op_fsub_s; break;
1687*ea103259SMichael Clark             case 5: op = rv_op_fsub_d; break;
1688*ea103259SMichael Clark             case 7: op = rv_op_fsub_q; break;
1689*ea103259SMichael Clark             case 8: op = rv_op_fmul_s; break;
1690*ea103259SMichael Clark             case 9: op = rv_op_fmul_d; break;
1691*ea103259SMichael Clark             case 11: op = rv_op_fmul_q; break;
1692*ea103259SMichael Clark             case 12: op = rv_op_fdiv_s; break;
1693*ea103259SMichael Clark             case 13: op = rv_op_fdiv_d; break;
1694*ea103259SMichael Clark             case 15: op = rv_op_fdiv_q; break;
1695*ea103259SMichael Clark             case 16:
1696*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1697*ea103259SMichael Clark                 case 0: op = rv_op_fsgnj_s; break;
1698*ea103259SMichael Clark                 case 1: op = rv_op_fsgnjn_s; break;
1699*ea103259SMichael Clark                 case 2: op = rv_op_fsgnjx_s; break;
1700*ea103259SMichael Clark                 }
1701*ea103259SMichael Clark                 break;
1702*ea103259SMichael Clark             case 17:
1703*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1704*ea103259SMichael Clark                 case 0: op = rv_op_fsgnj_d; break;
1705*ea103259SMichael Clark                 case 1: op = rv_op_fsgnjn_d; break;
1706*ea103259SMichael Clark                 case 2: op = rv_op_fsgnjx_d; break;
1707*ea103259SMichael Clark                 }
1708*ea103259SMichael Clark                 break;
1709*ea103259SMichael Clark             case 19:
1710*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1711*ea103259SMichael Clark                 case 0: op = rv_op_fsgnj_q; break;
1712*ea103259SMichael Clark                 case 1: op = rv_op_fsgnjn_q; break;
1713*ea103259SMichael Clark                 case 2: op = rv_op_fsgnjx_q; break;
1714*ea103259SMichael Clark                 }
1715*ea103259SMichael Clark                 break;
1716*ea103259SMichael Clark             case 20:
1717*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1718*ea103259SMichael Clark                 case 0: op = rv_op_fmin_s; break;
1719*ea103259SMichael Clark                 case 1: op = rv_op_fmax_s; break;
1720*ea103259SMichael Clark                 }
1721*ea103259SMichael Clark                 break;
1722*ea103259SMichael Clark             case 21:
1723*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1724*ea103259SMichael Clark                 case 0: op = rv_op_fmin_d; break;
1725*ea103259SMichael Clark                 case 1: op = rv_op_fmax_d; break;
1726*ea103259SMichael Clark                 }
1727*ea103259SMichael Clark                 break;
1728*ea103259SMichael Clark             case 23:
1729*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1730*ea103259SMichael Clark                 case 0: op = rv_op_fmin_q; break;
1731*ea103259SMichael Clark                 case 1: op = rv_op_fmax_q; break;
1732*ea103259SMichael Clark                 }
1733*ea103259SMichael Clark                 break;
1734*ea103259SMichael Clark             case 32:
1735*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1736*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_s_d; break;
1737*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_s_q; break;
1738*ea103259SMichael Clark                 }
1739*ea103259SMichael Clark                 break;
1740*ea103259SMichael Clark             case 33:
1741*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1742*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_d_s; break;
1743*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_d_q; break;
1744*ea103259SMichael Clark                 }
1745*ea103259SMichael Clark                 break;
1746*ea103259SMichael Clark             case 35:
1747*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1748*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_q_s; break;
1749*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_q_d; break;
1750*ea103259SMichael Clark                 }
1751*ea103259SMichael Clark                 break;
1752*ea103259SMichael Clark             case 44:
1753*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1754*ea103259SMichael Clark                 case 0: op = rv_op_fsqrt_s; break;
1755*ea103259SMichael Clark                 }
1756*ea103259SMichael Clark                 break;
1757*ea103259SMichael Clark             case 45:
1758*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1759*ea103259SMichael Clark                 case 0: op = rv_op_fsqrt_d; break;
1760*ea103259SMichael Clark                 }
1761*ea103259SMichael Clark                 break;
1762*ea103259SMichael Clark             case 47:
1763*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1764*ea103259SMichael Clark                 case 0: op = rv_op_fsqrt_q; break;
1765*ea103259SMichael Clark                 }
1766*ea103259SMichael Clark                 break;
1767*ea103259SMichael Clark             case 80:
1768*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1769*ea103259SMichael Clark                 case 0: op = rv_op_fle_s; break;
1770*ea103259SMichael Clark                 case 1: op = rv_op_flt_s; break;
1771*ea103259SMichael Clark                 case 2: op = rv_op_feq_s; break;
1772*ea103259SMichael Clark                 }
1773*ea103259SMichael Clark                 break;
1774*ea103259SMichael Clark             case 81:
1775*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1776*ea103259SMichael Clark                 case 0: op = rv_op_fle_d; break;
1777*ea103259SMichael Clark                 case 1: op = rv_op_flt_d; break;
1778*ea103259SMichael Clark                 case 2: op = rv_op_feq_d; break;
1779*ea103259SMichael Clark                 }
1780*ea103259SMichael Clark                 break;
1781*ea103259SMichael Clark             case 83:
1782*ea103259SMichael Clark                 switch (((inst >> 12) & 0b111)) {
1783*ea103259SMichael Clark                 case 0: op = rv_op_fle_q; break;
1784*ea103259SMichael Clark                 case 1: op = rv_op_flt_q; break;
1785*ea103259SMichael Clark                 case 2: op = rv_op_feq_q; break;
1786*ea103259SMichael Clark                 }
1787*ea103259SMichael Clark                 break;
1788*ea103259SMichael Clark             case 96:
1789*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1790*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_w_s; break;
1791*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_wu_s; break;
1792*ea103259SMichael Clark                 case 2: op = rv_op_fcvt_l_s; break;
1793*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_lu_s; break;
1794*ea103259SMichael Clark                 }
1795*ea103259SMichael Clark                 break;
1796*ea103259SMichael Clark             case 97:
1797*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1798*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_w_d; break;
1799*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_wu_d; break;
1800*ea103259SMichael Clark                 case 2: op = rv_op_fcvt_l_d; break;
1801*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_lu_d; break;
1802*ea103259SMichael Clark                 }
1803*ea103259SMichael Clark                 break;
1804*ea103259SMichael Clark             case 99:
1805*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1806*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_w_q; break;
1807*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_wu_q; break;
1808*ea103259SMichael Clark                 case 2: op = rv_op_fcvt_l_q; break;
1809*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_lu_q; break;
1810*ea103259SMichael Clark                 }
1811*ea103259SMichael Clark                 break;
1812*ea103259SMichael Clark             case 104:
1813*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1814*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_s_w; break;
1815*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_s_wu; break;
1816*ea103259SMichael Clark                 case 2: op = rv_op_fcvt_s_l; break;
1817*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_s_lu; break;
1818*ea103259SMichael Clark                 }
1819*ea103259SMichael Clark                 break;
1820*ea103259SMichael Clark             case 105:
1821*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1822*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_d_w; break;
1823*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_d_wu; break;
1824*ea103259SMichael Clark                 case 2: op = rv_op_fcvt_d_l; break;
1825*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_d_lu; break;
1826*ea103259SMichael Clark                 }
1827*ea103259SMichael Clark                 break;
1828*ea103259SMichael Clark             case 107:
1829*ea103259SMichael Clark                 switch (((inst >> 20) & 0b11111)) {
1830*ea103259SMichael Clark                 case 0: op = rv_op_fcvt_q_w; break;
1831*ea103259SMichael Clark                 case 1: op = rv_op_fcvt_q_wu; break;
1832*ea103259SMichael Clark                 case 2: op = rv_op_fcvt_q_l; break;
1833*ea103259SMichael Clark                 case 3: op = rv_op_fcvt_q_lu; break;
1834*ea103259SMichael Clark                 }
1835*ea103259SMichael Clark                 break;
1836*ea103259SMichael Clark             case 112:
1837*ea103259SMichael Clark                 switch (((inst >> 17) & 0b11111000) | ((inst >> 12) & 0b00000111)) {
1838*ea103259SMichael Clark                 case 0: op = rv_op_fmv_x_s; break;
1839*ea103259SMichael Clark                 case 1: op = rv_op_fclass_s; break;
1840*ea103259SMichael Clark                 }
1841*ea103259SMichael Clark                 break;
1842*ea103259SMichael Clark             case 113:
1843*ea103259SMichael Clark                 switch (((inst >> 17) & 0b11111000) | ((inst >> 12) & 0b00000111)) {
1844*ea103259SMichael Clark                 case 0: op = rv_op_fmv_x_d; break;
1845*ea103259SMichael Clark                 case 1: op = rv_op_fclass_d; break;
1846*ea103259SMichael Clark                 }
1847*ea103259SMichael Clark                 break;
1848*ea103259SMichael Clark             case 115:
1849*ea103259SMichael Clark                 switch (((inst >> 17) & 0b11111000) | ((inst >> 12) & 0b00000111)) {
1850*ea103259SMichael Clark                 case 0: op = rv_op_fmv_x_q; break;
1851*ea103259SMichael Clark                 case 1: op = rv_op_fclass_q; break;
1852*ea103259SMichael Clark                 }
1853*ea103259SMichael Clark                 break;
1854*ea103259SMichael Clark             case 120:
1855*ea103259SMichael Clark                 switch (((inst >> 17) & 0b11111000) | ((inst >> 12) & 0b00000111)) {
1856*ea103259SMichael Clark                 case 0: op = rv_op_fmv_s_x; break;
1857*ea103259SMichael Clark                 }
1858*ea103259SMichael Clark                 break;
1859*ea103259SMichael Clark             case 121:
1860*ea103259SMichael Clark                 switch (((inst >> 17) & 0b11111000) | ((inst >> 12) & 0b00000111)) {
1861*ea103259SMichael Clark                 case 0: op = rv_op_fmv_d_x; break;
1862*ea103259SMichael Clark                 }
1863*ea103259SMichael Clark                 break;
1864*ea103259SMichael Clark             case 123:
1865*ea103259SMichael Clark                 switch (((inst >> 17) & 0b11111000) | ((inst >> 12) & 0b00000111)) {
1866*ea103259SMichael Clark                 case 0: op = rv_op_fmv_q_x; break;
1867*ea103259SMichael Clark                 }
1868*ea103259SMichael Clark                 break;
1869*ea103259SMichael Clark             }
1870*ea103259SMichael Clark             break;
1871*ea103259SMichael Clark         case 22:
1872*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1873*ea103259SMichael Clark             case 0: op = rv_op_addid; break;
1874*ea103259SMichael Clark             case 1:
1875*ea103259SMichael Clark                 switch (((inst >> 26) & 0b111111)) {
1876*ea103259SMichael Clark                 case 0: op = rv_op_sllid; break;
1877*ea103259SMichael Clark                 }
1878*ea103259SMichael Clark                 break;
1879*ea103259SMichael Clark             case 5:
1880*ea103259SMichael Clark                 switch (((inst >> 26) & 0b111111)) {
1881*ea103259SMichael Clark                 case 0: op = rv_op_srlid; break;
1882*ea103259SMichael Clark                 case 16: op = rv_op_sraid; break;
1883*ea103259SMichael Clark                 }
1884*ea103259SMichael Clark                 break;
1885*ea103259SMichael Clark             }
1886*ea103259SMichael Clark             break;
1887*ea103259SMichael Clark         case 24:
1888*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1889*ea103259SMichael Clark             case 0: op = rv_op_beq; break;
1890*ea103259SMichael Clark             case 1: op = rv_op_bne; break;
1891*ea103259SMichael Clark             case 4: op = rv_op_blt; break;
1892*ea103259SMichael Clark             case 5: op = rv_op_bge; break;
1893*ea103259SMichael Clark             case 6: op = rv_op_bltu; break;
1894*ea103259SMichael Clark             case 7: op = rv_op_bgeu; break;
1895*ea103259SMichael Clark             }
1896*ea103259SMichael Clark             break;
1897*ea103259SMichael Clark         case 25:
1898*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1899*ea103259SMichael Clark             case 0: op = rv_op_jalr; break;
1900*ea103259SMichael Clark             }
1901*ea103259SMichael Clark             break;
1902*ea103259SMichael Clark         case 27: op = rv_op_jal; break;
1903*ea103259SMichael Clark         case 28:
1904*ea103259SMichael Clark             switch (((inst >> 12) & 0b111)) {
1905*ea103259SMichael Clark             case 0:
1906*ea103259SMichael Clark                 switch (((inst >> 20) & 0b111111100000) | ((inst >> 7) & 0b000000011111)) {
1907*ea103259SMichael Clark                 case 0:
1908*ea103259SMichael Clark                     switch (((inst >> 15) & 0b1111111111)) {
1909*ea103259SMichael Clark                     case 0: op = rv_op_ecall; break;
1910*ea103259SMichael Clark                     case 32: op = rv_op_ebreak; break;
1911*ea103259SMichael Clark                     case 64: op = rv_op_uret; break;
1912*ea103259SMichael Clark                     }
1913*ea103259SMichael Clark                     break;
1914*ea103259SMichael Clark                 case 256:
1915*ea103259SMichael Clark                     switch (((inst >> 20) & 0b11111)) {
1916*ea103259SMichael Clark                     case 2:
1917*ea103259SMichael Clark                         switch (((inst >> 15) & 0b11111)) {
1918*ea103259SMichael Clark                         case 0: op = rv_op_sret; break;
1919*ea103259SMichael Clark                         }
1920*ea103259SMichael Clark                         break;
1921*ea103259SMichael Clark                     case 4: op = rv_op_sfence_vm; break;
1922*ea103259SMichael Clark                     case 5:
1923*ea103259SMichael Clark                         switch (((inst >> 15) & 0b11111)) {
1924*ea103259SMichael Clark                         case 0: op = rv_op_wfi; break;
1925*ea103259SMichael Clark                         }
1926*ea103259SMichael Clark                         break;
1927*ea103259SMichael Clark                     }
1928*ea103259SMichael Clark                     break;
1929*ea103259SMichael Clark                 case 288: op = rv_op_sfence_vma; break;
1930*ea103259SMichael Clark                 case 512:
1931*ea103259SMichael Clark                     switch (((inst >> 15) & 0b1111111111)) {
1932*ea103259SMichael Clark                     case 64: op = rv_op_hret; break;
1933*ea103259SMichael Clark                     }
1934*ea103259SMichael Clark                     break;
1935*ea103259SMichael Clark                 case 768:
1936*ea103259SMichael Clark                     switch (((inst >> 15) & 0b1111111111)) {
1937*ea103259SMichael Clark                     case 64: op = rv_op_mret; break;
1938*ea103259SMichael Clark                     }
1939*ea103259SMichael Clark                     break;
1940*ea103259SMichael Clark                 case 1952:
1941*ea103259SMichael Clark                     switch (((inst >> 15) & 0b1111111111)) {
1942*ea103259SMichael Clark                     case 576: op = rv_op_dret; break;
1943*ea103259SMichael Clark                     }
1944*ea103259SMichael Clark                     break;
1945*ea103259SMichael Clark                 }
1946*ea103259SMichael Clark                 break;
1947*ea103259SMichael Clark             case 1: op = rv_op_csrrw; break;
1948*ea103259SMichael Clark             case 2: op = rv_op_csrrs; break;
1949*ea103259SMichael Clark             case 3: op = rv_op_csrrc; break;
1950*ea103259SMichael Clark             case 5: op = rv_op_csrrwi; break;
1951*ea103259SMichael Clark             case 6: op = rv_op_csrrsi; break;
1952*ea103259SMichael Clark             case 7: op = rv_op_csrrci; break;
1953*ea103259SMichael Clark             }
1954*ea103259SMichael Clark             break;
1955*ea103259SMichael Clark         case 30:
1956*ea103259SMichael Clark             switch (((inst >> 22) & 0b1111111000) | ((inst >> 12) & 0b0000000111)) {
1957*ea103259SMichael Clark             case 0: op = rv_op_addd; break;
1958*ea103259SMichael Clark             case 1: op = rv_op_slld; break;
1959*ea103259SMichael Clark             case 5: op = rv_op_srld; break;
1960*ea103259SMichael Clark             case 8: op = rv_op_muld; break;
1961*ea103259SMichael Clark             case 12: op = rv_op_divd; break;
1962*ea103259SMichael Clark             case 13: op = rv_op_divud; break;
1963*ea103259SMichael Clark             case 14: op = rv_op_remd; break;
1964*ea103259SMichael Clark             case 15: op = rv_op_remud; break;
1965*ea103259SMichael Clark             case 256: op = rv_op_subd; break;
1966*ea103259SMichael Clark             case 261: op = rv_op_srad; break;
1967*ea103259SMichael Clark             }
1968*ea103259SMichael Clark             break;
1969*ea103259SMichael Clark         }
1970*ea103259SMichael Clark         break;
1971*ea103259SMichael Clark     }
1972*ea103259SMichael Clark     dec->op = op;
1973*ea103259SMichael Clark }
1974*ea103259SMichael Clark 
1975*ea103259SMichael Clark /* operand extractors */
1976*ea103259SMichael Clark 
1977*ea103259SMichael Clark static uint32_t operand_rd(rv_inst inst)
1978*ea103259SMichael Clark {
1979*ea103259SMichael Clark     return (inst << 52) >> 59;
1980*ea103259SMichael Clark }
1981*ea103259SMichael Clark 
1982*ea103259SMichael Clark static uint32_t operand_rs1(rv_inst inst)
1983*ea103259SMichael Clark {
1984*ea103259SMichael Clark     return (inst << 44) >> 59;
1985*ea103259SMichael Clark }
1986*ea103259SMichael Clark 
1987*ea103259SMichael Clark static uint32_t operand_rs2(rv_inst inst)
1988*ea103259SMichael Clark {
1989*ea103259SMichael Clark     return (inst << 39) >> 59;
1990*ea103259SMichael Clark }
1991*ea103259SMichael Clark 
1992*ea103259SMichael Clark static uint32_t operand_rs3(rv_inst inst)
1993*ea103259SMichael Clark {
1994*ea103259SMichael Clark     return (inst << 32) >> 59;
1995*ea103259SMichael Clark }
1996*ea103259SMichael Clark 
1997*ea103259SMichael Clark static uint32_t operand_aq(rv_inst inst)
1998*ea103259SMichael Clark {
1999*ea103259SMichael Clark     return (inst << 37) >> 63;
2000*ea103259SMichael Clark }
2001*ea103259SMichael Clark 
2002*ea103259SMichael Clark static uint32_t operand_rl(rv_inst inst)
2003*ea103259SMichael Clark {
2004*ea103259SMichael Clark     return (inst << 38) >> 63;
2005*ea103259SMichael Clark }
2006*ea103259SMichael Clark 
2007*ea103259SMichael Clark static uint32_t operand_pred(rv_inst inst)
2008*ea103259SMichael Clark {
2009*ea103259SMichael Clark     return (inst << 36) >> 60;
2010*ea103259SMichael Clark }
2011*ea103259SMichael Clark 
2012*ea103259SMichael Clark static uint32_t operand_succ(rv_inst inst)
2013*ea103259SMichael Clark {
2014*ea103259SMichael Clark     return (inst << 40) >> 60;
2015*ea103259SMichael Clark }
2016*ea103259SMichael Clark 
2017*ea103259SMichael Clark static uint32_t operand_rm(rv_inst inst)
2018*ea103259SMichael Clark {
2019*ea103259SMichael Clark     return (inst << 49) >> 61;
2020*ea103259SMichael Clark }
2021*ea103259SMichael Clark 
2022*ea103259SMichael Clark static uint32_t operand_shamt5(rv_inst inst)
2023*ea103259SMichael Clark {
2024*ea103259SMichael Clark     return (inst << 39) >> 59;
2025*ea103259SMichael Clark }
2026*ea103259SMichael Clark 
2027*ea103259SMichael Clark static uint32_t operand_shamt6(rv_inst inst)
2028*ea103259SMichael Clark {
2029*ea103259SMichael Clark     return (inst << 38) >> 58;
2030*ea103259SMichael Clark }
2031*ea103259SMichael Clark 
2032*ea103259SMichael Clark static uint32_t operand_shamt7(rv_inst inst)
2033*ea103259SMichael Clark {
2034*ea103259SMichael Clark     return (inst << 37) >> 57;
2035*ea103259SMichael Clark }
2036*ea103259SMichael Clark 
2037*ea103259SMichael Clark static uint32_t operand_crdq(rv_inst inst)
2038*ea103259SMichael Clark {
2039*ea103259SMichael Clark     return (inst << 59) >> 61;
2040*ea103259SMichael Clark }
2041*ea103259SMichael Clark 
2042*ea103259SMichael Clark static uint32_t operand_crs1q(rv_inst inst)
2043*ea103259SMichael Clark {
2044*ea103259SMichael Clark     return (inst << 54) >> 61;
2045*ea103259SMichael Clark }
2046*ea103259SMichael Clark 
2047*ea103259SMichael Clark static uint32_t operand_crs1rdq(rv_inst inst)
2048*ea103259SMichael Clark {
2049*ea103259SMichael Clark     return (inst << 54) >> 61;
2050*ea103259SMichael Clark }
2051*ea103259SMichael Clark 
2052*ea103259SMichael Clark static uint32_t operand_crs2q(rv_inst inst)
2053*ea103259SMichael Clark {
2054*ea103259SMichael Clark     return (inst << 59) >> 61;
2055*ea103259SMichael Clark }
2056*ea103259SMichael Clark 
2057*ea103259SMichael Clark static uint32_t operand_crd(rv_inst inst)
2058*ea103259SMichael Clark {
2059*ea103259SMichael Clark     return (inst << 52) >> 59;
2060*ea103259SMichael Clark }
2061*ea103259SMichael Clark 
2062*ea103259SMichael Clark static uint32_t operand_crs1(rv_inst inst)
2063*ea103259SMichael Clark {
2064*ea103259SMichael Clark     return (inst << 52) >> 59;
2065*ea103259SMichael Clark }
2066*ea103259SMichael Clark 
2067*ea103259SMichael Clark static uint32_t operand_crs1rd(rv_inst inst)
2068*ea103259SMichael Clark {
2069*ea103259SMichael Clark     return (inst << 52) >> 59;
2070*ea103259SMichael Clark }
2071*ea103259SMichael Clark 
2072*ea103259SMichael Clark static uint32_t operand_crs2(rv_inst inst)
2073*ea103259SMichael Clark {
2074*ea103259SMichael Clark     return (inst << 57) >> 59;
2075*ea103259SMichael Clark }
2076*ea103259SMichael Clark 
2077*ea103259SMichael Clark static uint32_t operand_cimmsh5(rv_inst inst)
2078*ea103259SMichael Clark {
2079*ea103259SMichael Clark     return (inst << 57) >> 59;
2080*ea103259SMichael Clark }
2081*ea103259SMichael Clark 
2082*ea103259SMichael Clark static uint32_t operand_csr12(rv_inst inst)
2083*ea103259SMichael Clark {
2084*ea103259SMichael Clark     return (inst << 32) >> 52;
2085*ea103259SMichael Clark }
2086*ea103259SMichael Clark 
2087*ea103259SMichael Clark static int32_t operand_imm12(rv_inst inst)
2088*ea103259SMichael Clark {
2089*ea103259SMichael Clark     return ((int64_t)inst << 32) >> 52;
2090*ea103259SMichael Clark }
2091*ea103259SMichael Clark 
2092*ea103259SMichael Clark static int32_t operand_imm20(rv_inst inst)
2093*ea103259SMichael Clark {
2094*ea103259SMichael Clark     return (((int64_t)inst << 32) >> 44) << 12;
2095*ea103259SMichael Clark }
2096*ea103259SMichael Clark 
2097*ea103259SMichael Clark static int32_t operand_jimm20(rv_inst inst)
2098*ea103259SMichael Clark {
2099*ea103259SMichael Clark     return (((int64_t)inst << 32) >> 63) << 20 |
2100*ea103259SMichael Clark         ((inst << 33) >> 54) << 1 |
2101*ea103259SMichael Clark         ((inst << 43) >> 63) << 11 |
2102*ea103259SMichael Clark         ((inst << 44) >> 56) << 12;
2103*ea103259SMichael Clark }
2104*ea103259SMichael Clark 
2105*ea103259SMichael Clark static int32_t operand_simm12(rv_inst inst)
2106*ea103259SMichael Clark {
2107*ea103259SMichael Clark     return (((int64_t)inst << 32) >> 57) << 5 |
2108*ea103259SMichael Clark         (inst << 52) >> 59;
2109*ea103259SMichael Clark }
2110*ea103259SMichael Clark 
2111*ea103259SMichael Clark static int32_t operand_sbimm12(rv_inst inst)
2112*ea103259SMichael Clark {
2113*ea103259SMichael Clark     return (((int64_t)inst << 32) >> 63) << 12 |
2114*ea103259SMichael Clark         ((inst << 33) >> 58) << 5 |
2115*ea103259SMichael Clark         ((inst << 52) >> 60) << 1 |
2116*ea103259SMichael Clark         ((inst << 56) >> 63) << 11;
2117*ea103259SMichael Clark }
2118*ea103259SMichael Clark 
2119*ea103259SMichael Clark static uint32_t operand_cimmsh6(rv_inst inst)
2120*ea103259SMichael Clark {
2121*ea103259SMichael Clark     return ((inst << 51) >> 63) << 5 |
2122*ea103259SMichael Clark         (inst << 57) >> 59;
2123*ea103259SMichael Clark }
2124*ea103259SMichael Clark 
2125*ea103259SMichael Clark static int32_t operand_cimmi(rv_inst inst)
2126*ea103259SMichael Clark {
2127*ea103259SMichael Clark     return (((int64_t)inst << 51) >> 63) << 5 |
2128*ea103259SMichael Clark         (inst << 57) >> 59;
2129*ea103259SMichael Clark }
2130*ea103259SMichael Clark 
2131*ea103259SMichael Clark static int32_t operand_cimmui(rv_inst inst)
2132*ea103259SMichael Clark {
2133*ea103259SMichael Clark     return (((int64_t)inst << 51) >> 63) << 17 |
2134*ea103259SMichael Clark         ((inst << 57) >> 59) << 12;
2135*ea103259SMichael Clark }
2136*ea103259SMichael Clark 
2137*ea103259SMichael Clark static uint32_t operand_cimmlwsp(rv_inst inst)
2138*ea103259SMichael Clark {
2139*ea103259SMichael Clark     return ((inst << 51) >> 63) << 5 |
2140*ea103259SMichael Clark         ((inst << 57) >> 61) << 2 |
2141*ea103259SMichael Clark         ((inst << 60) >> 62) << 6;
2142*ea103259SMichael Clark }
2143*ea103259SMichael Clark 
2144*ea103259SMichael Clark static uint32_t operand_cimmldsp(rv_inst inst)
2145*ea103259SMichael Clark {
2146*ea103259SMichael Clark     return ((inst << 51) >> 63) << 5 |
2147*ea103259SMichael Clark         ((inst << 57) >> 62) << 3 |
2148*ea103259SMichael Clark         ((inst << 59) >> 61) << 6;
2149*ea103259SMichael Clark }
2150*ea103259SMichael Clark 
2151*ea103259SMichael Clark static uint32_t operand_cimmlqsp(rv_inst inst)
2152*ea103259SMichael Clark {
2153*ea103259SMichael Clark     return ((inst << 51) >> 63) << 5 |
2154*ea103259SMichael Clark         ((inst << 57) >> 63) << 4 |
2155*ea103259SMichael Clark         ((inst << 58) >> 60) << 6;
2156*ea103259SMichael Clark }
2157*ea103259SMichael Clark 
2158*ea103259SMichael Clark static int32_t operand_cimm16sp(rv_inst inst)
2159*ea103259SMichael Clark {
2160*ea103259SMichael Clark     return (((int64_t)inst << 51) >> 63) << 9 |
2161*ea103259SMichael Clark         ((inst << 57) >> 63) << 4 |
2162*ea103259SMichael Clark         ((inst << 58) >> 63) << 6 |
2163*ea103259SMichael Clark         ((inst << 59) >> 62) << 7 |
2164*ea103259SMichael Clark         ((inst << 61) >> 63) << 5;
2165*ea103259SMichael Clark }
2166*ea103259SMichael Clark 
2167*ea103259SMichael Clark static int32_t operand_cimmj(rv_inst inst)
2168*ea103259SMichael Clark {
2169*ea103259SMichael Clark     return (((int64_t)inst << 51) >> 63) << 11 |
2170*ea103259SMichael Clark         ((inst << 52) >> 63) << 4 |
2171*ea103259SMichael Clark         ((inst << 53) >> 62) << 8 |
2172*ea103259SMichael Clark         ((inst << 55) >> 63) << 10 |
2173*ea103259SMichael Clark         ((inst << 56) >> 63) << 6 |
2174*ea103259SMichael Clark         ((inst << 57) >> 63) << 7 |
2175*ea103259SMichael Clark         ((inst << 58) >> 61) << 1 |
2176*ea103259SMichael Clark         ((inst << 61) >> 63) << 5;
2177*ea103259SMichael Clark }
2178*ea103259SMichael Clark 
2179*ea103259SMichael Clark static int32_t operand_cimmb(rv_inst inst)
2180*ea103259SMichael Clark {
2181*ea103259SMichael Clark     return (((int64_t)inst << 51) >> 63) << 8 |
2182*ea103259SMichael Clark         ((inst << 52) >> 62) << 3 |
2183*ea103259SMichael Clark         ((inst << 57) >> 62) << 6 |
2184*ea103259SMichael Clark         ((inst << 59) >> 62) << 1 |
2185*ea103259SMichael Clark         ((inst << 61) >> 63) << 5;
2186*ea103259SMichael Clark }
2187*ea103259SMichael Clark 
2188*ea103259SMichael Clark static uint32_t operand_cimmswsp(rv_inst inst)
2189*ea103259SMichael Clark {
2190*ea103259SMichael Clark     return ((inst << 51) >> 60) << 2 |
2191*ea103259SMichael Clark         ((inst << 55) >> 62) << 6;
2192*ea103259SMichael Clark }
2193*ea103259SMichael Clark 
2194*ea103259SMichael Clark static uint32_t operand_cimmsdsp(rv_inst inst)
2195*ea103259SMichael Clark {
2196*ea103259SMichael Clark     return ((inst << 51) >> 61) << 3 |
2197*ea103259SMichael Clark         ((inst << 54) >> 61) << 6;
2198*ea103259SMichael Clark }
2199*ea103259SMichael Clark 
2200*ea103259SMichael Clark static uint32_t operand_cimmsqsp(rv_inst inst)
2201*ea103259SMichael Clark {
2202*ea103259SMichael Clark     return ((inst << 51) >> 62) << 4 |
2203*ea103259SMichael Clark         ((inst << 53) >> 60) << 6;
2204*ea103259SMichael Clark }
2205*ea103259SMichael Clark 
2206*ea103259SMichael Clark static uint32_t operand_cimm4spn(rv_inst inst)
2207*ea103259SMichael Clark {
2208*ea103259SMichael Clark     return ((inst << 51) >> 62) << 4 |
2209*ea103259SMichael Clark         ((inst << 53) >> 60) << 6 |
2210*ea103259SMichael Clark         ((inst << 57) >> 63) << 2 |
2211*ea103259SMichael Clark         ((inst << 58) >> 63) << 3;
2212*ea103259SMichael Clark }
2213*ea103259SMichael Clark 
2214*ea103259SMichael Clark static uint32_t operand_cimmw(rv_inst inst)
2215*ea103259SMichael Clark {
2216*ea103259SMichael Clark     return ((inst << 51) >> 61) << 3 |
2217*ea103259SMichael Clark         ((inst << 57) >> 63) << 2 |
2218*ea103259SMichael Clark         ((inst << 58) >> 63) << 6;
2219*ea103259SMichael Clark }
2220*ea103259SMichael Clark 
2221*ea103259SMichael Clark static uint32_t operand_cimmd(rv_inst inst)
2222*ea103259SMichael Clark {
2223*ea103259SMichael Clark     return ((inst << 51) >> 61) << 3 |
2224*ea103259SMichael Clark         ((inst << 57) >> 62) << 6;
2225*ea103259SMichael Clark }
2226*ea103259SMichael Clark 
2227*ea103259SMichael Clark static uint32_t operand_cimmq(rv_inst inst)
2228*ea103259SMichael Clark {
2229*ea103259SMichael Clark     return ((inst << 51) >> 62) << 4 |
2230*ea103259SMichael Clark         ((inst << 53) >> 63) << 8 |
2231*ea103259SMichael Clark         ((inst << 57) >> 62) << 6;
2232*ea103259SMichael Clark }
2233*ea103259SMichael Clark 
2234*ea103259SMichael Clark /* decode operands */
2235*ea103259SMichael Clark 
2236*ea103259SMichael Clark static void decode_inst_operands(rv_decode *dec)
2237*ea103259SMichael Clark {
2238*ea103259SMichael Clark     rv_inst inst = dec->inst;
2239*ea103259SMichael Clark     dec->codec = opcode_data[dec->op].codec;
2240*ea103259SMichael Clark     switch (dec->codec) {
2241*ea103259SMichael Clark     case rv_codec_none:
2242*ea103259SMichael Clark         dec->rd = dec->rs1 = dec->rs2 = rv_ireg_zero;
2243*ea103259SMichael Clark         dec->imm = 0;
2244*ea103259SMichael Clark         break;
2245*ea103259SMichael Clark     case rv_codec_u:
2246*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2247*ea103259SMichael Clark         dec->rs1 = dec->rs2 = rv_ireg_zero;
2248*ea103259SMichael Clark         dec->imm = operand_imm20(inst);
2249*ea103259SMichael Clark         break;
2250*ea103259SMichael Clark     case rv_codec_uj:
2251*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2252*ea103259SMichael Clark         dec->rs1 = dec->rs2 = rv_ireg_zero;
2253*ea103259SMichael Clark         dec->imm = operand_jimm20(inst);
2254*ea103259SMichael Clark         break;
2255*ea103259SMichael Clark     case rv_codec_i:
2256*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2257*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2258*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2259*ea103259SMichael Clark         dec->imm = operand_imm12(inst);
2260*ea103259SMichael Clark         break;
2261*ea103259SMichael Clark     case rv_codec_i_sh5:
2262*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2263*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2264*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2265*ea103259SMichael Clark         dec->imm = operand_shamt5(inst);
2266*ea103259SMichael Clark         break;
2267*ea103259SMichael Clark     case rv_codec_i_sh6:
2268*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2269*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2270*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2271*ea103259SMichael Clark         dec->imm = operand_shamt6(inst);
2272*ea103259SMichael Clark         break;
2273*ea103259SMichael Clark     case rv_codec_i_sh7:
2274*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2275*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2276*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2277*ea103259SMichael Clark         dec->imm = operand_shamt7(inst);
2278*ea103259SMichael Clark         break;
2279*ea103259SMichael Clark     case rv_codec_i_csr:
2280*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2281*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2282*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2283*ea103259SMichael Clark         dec->imm = operand_csr12(inst);
2284*ea103259SMichael Clark         break;
2285*ea103259SMichael Clark     case rv_codec_s:
2286*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2287*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2288*ea103259SMichael Clark         dec->rs2 = operand_rs2(inst);
2289*ea103259SMichael Clark         dec->imm = operand_simm12(inst);
2290*ea103259SMichael Clark         break;
2291*ea103259SMichael Clark     case rv_codec_sb:
2292*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2293*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2294*ea103259SMichael Clark         dec->rs2 = operand_rs2(inst);
2295*ea103259SMichael Clark         dec->imm = operand_sbimm12(inst);
2296*ea103259SMichael Clark         break;
2297*ea103259SMichael Clark     case rv_codec_r:
2298*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2299*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2300*ea103259SMichael Clark         dec->rs2 = operand_rs2(inst);
2301*ea103259SMichael Clark         dec->imm = 0;
2302*ea103259SMichael Clark         break;
2303*ea103259SMichael Clark     case rv_codec_r_m:
2304*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2305*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2306*ea103259SMichael Clark         dec->rs2 = operand_rs2(inst);
2307*ea103259SMichael Clark         dec->imm = 0;
2308*ea103259SMichael Clark         dec->rm = operand_rm(inst);
2309*ea103259SMichael Clark         break;
2310*ea103259SMichael Clark     case rv_codec_r4_m:
2311*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2312*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2313*ea103259SMichael Clark         dec->rs2 = operand_rs2(inst);
2314*ea103259SMichael Clark         dec->rs3 = operand_rs3(inst);
2315*ea103259SMichael Clark         dec->imm = 0;
2316*ea103259SMichael Clark         dec->rm = operand_rm(inst);
2317*ea103259SMichael Clark         break;
2318*ea103259SMichael Clark     case rv_codec_r_a:
2319*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2320*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2321*ea103259SMichael Clark         dec->rs2 = operand_rs2(inst);
2322*ea103259SMichael Clark         dec->imm = 0;
2323*ea103259SMichael Clark         dec->aq = operand_aq(inst);
2324*ea103259SMichael Clark         dec->rl = operand_rl(inst);
2325*ea103259SMichael Clark         break;
2326*ea103259SMichael Clark     case rv_codec_r_l:
2327*ea103259SMichael Clark         dec->rd = operand_rd(inst);
2328*ea103259SMichael Clark         dec->rs1 = operand_rs1(inst);
2329*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2330*ea103259SMichael Clark         dec->imm = 0;
2331*ea103259SMichael Clark         dec->aq = operand_aq(inst);
2332*ea103259SMichael Clark         dec->rl = operand_rl(inst);
2333*ea103259SMichael Clark         break;
2334*ea103259SMichael Clark     case rv_codec_r_f:
2335*ea103259SMichael Clark         dec->rd = dec->rs1 = dec->rs2 = rv_ireg_zero;
2336*ea103259SMichael Clark         dec->pred = operand_pred(inst);
2337*ea103259SMichael Clark         dec->succ = operand_succ(inst);
2338*ea103259SMichael Clark         dec->imm = 0;
2339*ea103259SMichael Clark         break;
2340*ea103259SMichael Clark     case rv_codec_cb:
2341*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2342*ea103259SMichael Clark         dec->rs1 = operand_crs1q(inst) + 8;
2343*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2344*ea103259SMichael Clark         dec->imm = operand_cimmb(inst);
2345*ea103259SMichael Clark         break;
2346*ea103259SMichael Clark     case rv_codec_cb_imm:
2347*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rdq(inst) + 8;
2348*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2349*ea103259SMichael Clark         dec->imm = operand_cimmi(inst);
2350*ea103259SMichael Clark         break;
2351*ea103259SMichael Clark     case rv_codec_cb_sh5:
2352*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rdq(inst) + 8;
2353*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2354*ea103259SMichael Clark         dec->imm = operand_cimmsh5(inst);
2355*ea103259SMichael Clark         break;
2356*ea103259SMichael Clark     case rv_codec_cb_sh6:
2357*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rdq(inst) + 8;
2358*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2359*ea103259SMichael Clark         dec->imm = operand_cimmsh6(inst);
2360*ea103259SMichael Clark         break;
2361*ea103259SMichael Clark     case rv_codec_ci:
2362*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rd(inst);
2363*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2364*ea103259SMichael Clark         dec->imm = operand_cimmi(inst);
2365*ea103259SMichael Clark         break;
2366*ea103259SMichael Clark     case rv_codec_ci_sh5:
2367*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rd(inst);
2368*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2369*ea103259SMichael Clark         dec->imm = operand_cimmsh5(inst);
2370*ea103259SMichael Clark         break;
2371*ea103259SMichael Clark     case rv_codec_ci_sh6:
2372*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rd(inst);
2373*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2374*ea103259SMichael Clark         dec->imm = operand_cimmsh6(inst);
2375*ea103259SMichael Clark         break;
2376*ea103259SMichael Clark     case rv_codec_ci_16sp:
2377*ea103259SMichael Clark         dec->rd = rv_ireg_sp;
2378*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2379*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2380*ea103259SMichael Clark         dec->imm = operand_cimm16sp(inst);
2381*ea103259SMichael Clark         break;
2382*ea103259SMichael Clark     case rv_codec_ci_lwsp:
2383*ea103259SMichael Clark         dec->rd = operand_crd(inst);
2384*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2385*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2386*ea103259SMichael Clark         dec->imm = operand_cimmlwsp(inst);
2387*ea103259SMichael Clark         break;
2388*ea103259SMichael Clark     case rv_codec_ci_ldsp:
2389*ea103259SMichael Clark         dec->rd = operand_crd(inst);
2390*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2391*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2392*ea103259SMichael Clark         dec->imm = operand_cimmldsp(inst);
2393*ea103259SMichael Clark         break;
2394*ea103259SMichael Clark     case rv_codec_ci_lqsp:
2395*ea103259SMichael Clark         dec->rd = operand_crd(inst);
2396*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2397*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2398*ea103259SMichael Clark         dec->imm = operand_cimmlqsp(inst);
2399*ea103259SMichael Clark         break;
2400*ea103259SMichael Clark     case rv_codec_ci_li:
2401*ea103259SMichael Clark         dec->rd = operand_crd(inst);
2402*ea103259SMichael Clark         dec->rs1 = rv_ireg_zero;
2403*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2404*ea103259SMichael Clark         dec->imm = operand_cimmi(inst);
2405*ea103259SMichael Clark         break;
2406*ea103259SMichael Clark     case rv_codec_ci_lui:
2407*ea103259SMichael Clark         dec->rd = operand_crd(inst);
2408*ea103259SMichael Clark         dec->rs1 = rv_ireg_zero;
2409*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2410*ea103259SMichael Clark         dec->imm = operand_cimmui(inst);
2411*ea103259SMichael Clark         break;
2412*ea103259SMichael Clark     case rv_codec_ci_none:
2413*ea103259SMichael Clark         dec->rd = dec->rs1 = dec->rs2 = rv_ireg_zero;
2414*ea103259SMichael Clark         dec->imm = 0;
2415*ea103259SMichael Clark         break;
2416*ea103259SMichael Clark     case rv_codec_ciw_4spn:
2417*ea103259SMichael Clark         dec->rd = operand_crdq(inst) + 8;
2418*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2419*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2420*ea103259SMichael Clark         dec->imm = operand_cimm4spn(inst);
2421*ea103259SMichael Clark         break;
2422*ea103259SMichael Clark     case rv_codec_cj:
2423*ea103259SMichael Clark         dec->rd = dec->rs1 = dec->rs2 = rv_ireg_zero;
2424*ea103259SMichael Clark         dec->imm = operand_cimmj(inst);
2425*ea103259SMichael Clark         break;
2426*ea103259SMichael Clark     case rv_codec_cj_jal:
2427*ea103259SMichael Clark         dec->rd = rv_ireg_ra;
2428*ea103259SMichael Clark         dec->rs1 = dec->rs2 = rv_ireg_zero;
2429*ea103259SMichael Clark         dec->imm = operand_cimmj(inst);
2430*ea103259SMichael Clark         break;
2431*ea103259SMichael Clark     case rv_codec_cl_lw:
2432*ea103259SMichael Clark         dec->rd = operand_crdq(inst) + 8;
2433*ea103259SMichael Clark         dec->rs1 = operand_crs1q(inst) + 8;
2434*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2435*ea103259SMichael Clark         dec->imm = operand_cimmw(inst);
2436*ea103259SMichael Clark         break;
2437*ea103259SMichael Clark     case rv_codec_cl_ld:
2438*ea103259SMichael Clark         dec->rd = operand_crdq(inst) + 8;
2439*ea103259SMichael Clark         dec->rs1 = operand_crs1q(inst) + 8;
2440*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2441*ea103259SMichael Clark         dec->imm = operand_cimmd(inst);
2442*ea103259SMichael Clark         break;
2443*ea103259SMichael Clark     case rv_codec_cl_lq:
2444*ea103259SMichael Clark         dec->rd = operand_crdq(inst) + 8;
2445*ea103259SMichael Clark         dec->rs1 = operand_crs1q(inst) + 8;
2446*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2447*ea103259SMichael Clark         dec->imm = operand_cimmq(inst);
2448*ea103259SMichael Clark         break;
2449*ea103259SMichael Clark     case rv_codec_cr:
2450*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rd(inst);
2451*ea103259SMichael Clark         dec->rs2 = operand_crs2(inst);
2452*ea103259SMichael Clark         dec->imm = 0;
2453*ea103259SMichael Clark         break;
2454*ea103259SMichael Clark     case rv_codec_cr_mv:
2455*ea103259SMichael Clark         dec->rd = operand_crd(inst);
2456*ea103259SMichael Clark         dec->rs1 = operand_crs2(inst);
2457*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2458*ea103259SMichael Clark         dec->imm = 0;
2459*ea103259SMichael Clark         break;
2460*ea103259SMichael Clark     case rv_codec_cr_jalr:
2461*ea103259SMichael Clark         dec->rd = rv_ireg_ra;
2462*ea103259SMichael Clark         dec->rs1 = operand_crs1(inst);
2463*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2464*ea103259SMichael Clark         dec->imm = 0;
2465*ea103259SMichael Clark         break;
2466*ea103259SMichael Clark     case rv_codec_cr_jr:
2467*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2468*ea103259SMichael Clark         dec->rs1 = operand_crs1(inst);
2469*ea103259SMichael Clark         dec->rs2 = rv_ireg_zero;
2470*ea103259SMichael Clark         dec->imm = 0;
2471*ea103259SMichael Clark         break;
2472*ea103259SMichael Clark     case rv_codec_cs:
2473*ea103259SMichael Clark         dec->rd = dec->rs1 = operand_crs1rdq(inst) + 8;
2474*ea103259SMichael Clark         dec->rs2 = operand_crs2q(inst) + 8;
2475*ea103259SMichael Clark         dec->imm = 0;
2476*ea103259SMichael Clark         break;
2477*ea103259SMichael Clark     case rv_codec_cs_sw:
2478*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2479*ea103259SMichael Clark         dec->rs1 = operand_crs1q(inst) + 8;
2480*ea103259SMichael Clark         dec->rs2 = operand_crs2q(inst) + 8;
2481*ea103259SMichael Clark         dec->imm = operand_cimmw(inst);
2482*ea103259SMichael Clark         break;
2483*ea103259SMichael Clark     case rv_codec_cs_sd:
2484*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2485*ea103259SMichael Clark         dec->rs1 = operand_crs1q(inst) + 8;
2486*ea103259SMichael Clark         dec->rs2 = operand_crs2q(inst) + 8;
2487*ea103259SMichael Clark         dec->imm = operand_cimmd(inst);
2488*ea103259SMichael Clark         break;
2489*ea103259SMichael Clark     case rv_codec_cs_sq:
2490*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2491*ea103259SMichael Clark         dec->rs1 = operand_crs1q(inst) + 8;
2492*ea103259SMichael Clark         dec->rs2 = operand_crs2q(inst) + 8;
2493*ea103259SMichael Clark         dec->imm = operand_cimmq(inst);
2494*ea103259SMichael Clark         break;
2495*ea103259SMichael Clark     case rv_codec_css_swsp:
2496*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2497*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2498*ea103259SMichael Clark         dec->rs2 = operand_crs2(inst);
2499*ea103259SMichael Clark         dec->imm = operand_cimmswsp(inst);
2500*ea103259SMichael Clark         break;
2501*ea103259SMichael Clark     case rv_codec_css_sdsp:
2502*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2503*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2504*ea103259SMichael Clark         dec->rs2 = operand_crs2(inst);
2505*ea103259SMichael Clark         dec->imm = operand_cimmsdsp(inst);
2506*ea103259SMichael Clark         break;
2507*ea103259SMichael Clark     case rv_codec_css_sqsp:
2508*ea103259SMichael Clark         dec->rd = rv_ireg_zero;
2509*ea103259SMichael Clark         dec->rs1 = rv_ireg_sp;
2510*ea103259SMichael Clark         dec->rs2 = operand_crs2(inst);
2511*ea103259SMichael Clark         dec->imm = operand_cimmsqsp(inst);
2512*ea103259SMichael Clark         break;
2513*ea103259SMichael Clark     };
2514*ea103259SMichael Clark }
2515*ea103259SMichael Clark 
2516*ea103259SMichael Clark /* check constraint */
2517*ea103259SMichael Clark 
2518*ea103259SMichael Clark static bool check_constraints(rv_decode *dec, const rvc_constraint *c)
2519*ea103259SMichael Clark {
2520*ea103259SMichael Clark     int32_t imm = dec->imm;
2521*ea103259SMichael Clark     uint8_t rd = dec->rd, rs1 = dec->rs1, rs2 = dec->rs2;
2522*ea103259SMichael Clark     while (*c != rvc_end) {
2523*ea103259SMichael Clark         switch (*c) {
2524*ea103259SMichael Clark         case rvc_simm_6:
2525*ea103259SMichael Clark             if (!(imm >= -32 && imm < 32)) {
2526*ea103259SMichael Clark                 return false;
2527*ea103259SMichael Clark             }
2528*ea103259SMichael Clark             break;
2529*ea103259SMichael Clark         case rvc_imm_6:
2530*ea103259SMichael Clark             if (!(imm <= 63)) {
2531*ea103259SMichael Clark                 return false;
2532*ea103259SMichael Clark             }
2533*ea103259SMichael Clark             break;
2534*ea103259SMichael Clark         case rvc_imm_7:
2535*ea103259SMichael Clark             if (!(imm <= 127)) {
2536*ea103259SMichael Clark                 return false;
2537*ea103259SMichael Clark             }
2538*ea103259SMichael Clark             break;
2539*ea103259SMichael Clark         case rvc_imm_8:
2540*ea103259SMichael Clark             if (!(imm <= 255)) {
2541*ea103259SMichael Clark                 return false;
2542*ea103259SMichael Clark             }
2543*ea103259SMichael Clark             break;
2544*ea103259SMichael Clark         case rvc_imm_9:
2545*ea103259SMichael Clark             if (!(imm <= 511)) {
2546*ea103259SMichael Clark                 return false;
2547*ea103259SMichael Clark             }
2548*ea103259SMichael Clark             break;
2549*ea103259SMichael Clark         case rvc_imm_10:
2550*ea103259SMichael Clark             if (!(imm <= 1023)) {
2551*ea103259SMichael Clark                 return false;
2552*ea103259SMichael Clark             }
2553*ea103259SMichael Clark             break;
2554*ea103259SMichael Clark         case rvc_imm_12:
2555*ea103259SMichael Clark             if (!(imm <= 4095)) {
2556*ea103259SMichael Clark                 return false;
2557*ea103259SMichael Clark             }
2558*ea103259SMichael Clark             break;
2559*ea103259SMichael Clark         case rvc_imm_18:
2560*ea103259SMichael Clark             if (!(imm <= 262143)) {
2561*ea103259SMichael Clark                 return false;
2562*ea103259SMichael Clark             }
2563*ea103259SMichael Clark             break;
2564*ea103259SMichael Clark         case rvc_imm_nz:
2565*ea103259SMichael Clark             if (!(imm != 0)) {
2566*ea103259SMichael Clark                 return false;
2567*ea103259SMichael Clark             }
2568*ea103259SMichael Clark             break;
2569*ea103259SMichael Clark         case rvc_imm_x2:
2570*ea103259SMichael Clark             if (!((imm & 0b1) == 0)) {
2571*ea103259SMichael Clark                 return false;
2572*ea103259SMichael Clark             }
2573*ea103259SMichael Clark             break;
2574*ea103259SMichael Clark         case rvc_imm_x4:
2575*ea103259SMichael Clark             if (!((imm & 0b11) == 0)) {
2576*ea103259SMichael Clark                 return false;
2577*ea103259SMichael Clark             }
2578*ea103259SMichael Clark             break;
2579*ea103259SMichael Clark         case rvc_imm_x8:
2580*ea103259SMichael Clark             if (!((imm & 0b111) == 0)) {
2581*ea103259SMichael Clark                 return false;
2582*ea103259SMichael Clark             }
2583*ea103259SMichael Clark             break;
2584*ea103259SMichael Clark         case rvc_imm_x16:
2585*ea103259SMichael Clark             if (!((imm & 0b1111) == 0)) {
2586*ea103259SMichael Clark                 return false;
2587*ea103259SMichael Clark             }
2588*ea103259SMichael Clark             break;
2589*ea103259SMichael Clark         case rvc_rd_b3:
2590*ea103259SMichael Clark             if (!(rd  >= 8 && rd  <= 15)) {
2591*ea103259SMichael Clark                 return false;
2592*ea103259SMichael Clark             }
2593*ea103259SMichael Clark             break;
2594*ea103259SMichael Clark         case rvc_rs1_b3:
2595*ea103259SMichael Clark             if (!(rs1 >= 8 && rs1 <= 15)) {
2596*ea103259SMichael Clark                 return false;
2597*ea103259SMichael Clark             }
2598*ea103259SMichael Clark             break;
2599*ea103259SMichael Clark         case rvc_rs2_b3:
2600*ea103259SMichael Clark             if (!(rs2 >= 8 && rs2 <= 15)) {
2601*ea103259SMichael Clark                 return false;
2602*ea103259SMichael Clark             }
2603*ea103259SMichael Clark             break;
2604*ea103259SMichael Clark         case rvc_rd_eq_rs1:
2605*ea103259SMichael Clark             if (!(rd == rs1)) {
2606*ea103259SMichael Clark                 return false;
2607*ea103259SMichael Clark             }
2608*ea103259SMichael Clark             break;
2609*ea103259SMichael Clark         case rvc_rd_eq_ra:
2610*ea103259SMichael Clark             if (!(rd == 1)) {
2611*ea103259SMichael Clark                 return false;
2612*ea103259SMichael Clark             }
2613*ea103259SMichael Clark             break;
2614*ea103259SMichael Clark         case rvc_rd_eq_sp:
2615*ea103259SMichael Clark             if (!(rd == 2)) {
2616*ea103259SMichael Clark                 return false;
2617*ea103259SMichael Clark             }
2618*ea103259SMichael Clark             break;
2619*ea103259SMichael Clark         case rvc_rd_eq_x0:
2620*ea103259SMichael Clark             if (!(rd == 0)) {
2621*ea103259SMichael Clark                 return false;
2622*ea103259SMichael Clark             }
2623*ea103259SMichael Clark             break;
2624*ea103259SMichael Clark         case rvc_rs1_eq_sp:
2625*ea103259SMichael Clark             if (!(rs1 == 2)) {
2626*ea103259SMichael Clark                 return false;
2627*ea103259SMichael Clark             }
2628*ea103259SMichael Clark             break;
2629*ea103259SMichael Clark         case rvc_rs1_eq_x0:
2630*ea103259SMichael Clark             if (!(rs1 == 0)) {
2631*ea103259SMichael Clark                 return false;
2632*ea103259SMichael Clark             }
2633*ea103259SMichael Clark             break;
2634*ea103259SMichael Clark         case rvc_rs2_eq_x0:
2635*ea103259SMichael Clark             if (!(rs2 == 0)) {
2636*ea103259SMichael Clark                 return false;
2637*ea103259SMichael Clark             }
2638*ea103259SMichael Clark             break;
2639*ea103259SMichael Clark         case rvc_rd_ne_x0_x2:
2640*ea103259SMichael Clark             if (!(rd != 0 && rd != 2)) {
2641*ea103259SMichael Clark                 return false;
2642*ea103259SMichael Clark             }
2643*ea103259SMichael Clark             break;
2644*ea103259SMichael Clark         case rvc_rd_ne_x0:
2645*ea103259SMichael Clark             if (!(rd != 0)) {
2646*ea103259SMichael Clark                 return false;
2647*ea103259SMichael Clark             }
2648*ea103259SMichael Clark             break;
2649*ea103259SMichael Clark         case rvc_rs1_ne_x0:
2650*ea103259SMichael Clark             if (!(rs1 != 0)) {
2651*ea103259SMichael Clark                 return false;
2652*ea103259SMichael Clark             }
2653*ea103259SMichael Clark             break;
2654*ea103259SMichael Clark         case rvc_rs2_ne_x0:
2655*ea103259SMichael Clark             if (!(rs2 != 0)) {
2656*ea103259SMichael Clark                 return false;
2657*ea103259SMichael Clark             }
2658*ea103259SMichael Clark             break;
2659*ea103259SMichael Clark         case rvc_rs2_eq_rs1:
2660*ea103259SMichael Clark             if (!(rs2 == rs1)) {
2661*ea103259SMichael Clark                 return false;
2662*ea103259SMichael Clark             }
2663*ea103259SMichael Clark             break;
2664*ea103259SMichael Clark         case rvc_rs1_eq_ra:
2665*ea103259SMichael Clark             if (!(rs1 == 1)) {
2666*ea103259SMichael Clark                 return false;
2667*ea103259SMichael Clark             }
2668*ea103259SMichael Clark             break;
2669*ea103259SMichael Clark         case rvc_imm_eq_zero:
2670*ea103259SMichael Clark             if (!(imm == 0)) {
2671*ea103259SMichael Clark                 return false;
2672*ea103259SMichael Clark             }
2673*ea103259SMichael Clark             break;
2674*ea103259SMichael Clark         case rvc_imm_eq_n1:
2675*ea103259SMichael Clark             if (!(imm == -1)) {
2676*ea103259SMichael Clark                 return false;
2677*ea103259SMichael Clark             }
2678*ea103259SMichael Clark             break;
2679*ea103259SMichael Clark         case rvc_imm_eq_p1:
2680*ea103259SMichael Clark             if (!(imm == 1)) {
2681*ea103259SMichael Clark                 return false;
2682*ea103259SMichael Clark             }
2683*ea103259SMichael Clark             break;
2684*ea103259SMichael Clark         case rvc_csr_eq_0x001:
2685*ea103259SMichael Clark             if (!(imm == 0x001)) {
2686*ea103259SMichael Clark                 return false;
2687*ea103259SMichael Clark             }
2688*ea103259SMichael Clark             break;
2689*ea103259SMichael Clark         case rvc_csr_eq_0x002:
2690*ea103259SMichael Clark             if (!(imm == 0x002)) {
2691*ea103259SMichael Clark                 return false;
2692*ea103259SMichael Clark             }
2693*ea103259SMichael Clark             break;
2694*ea103259SMichael Clark         case rvc_csr_eq_0x003:
2695*ea103259SMichael Clark             if (!(imm == 0x003)) {
2696*ea103259SMichael Clark                 return false;
2697*ea103259SMichael Clark             }
2698*ea103259SMichael Clark             break;
2699*ea103259SMichael Clark         case rvc_csr_eq_0xc00:
2700*ea103259SMichael Clark             if (!(imm == 0xc00)) {
2701*ea103259SMichael Clark                 return false;
2702*ea103259SMichael Clark             }
2703*ea103259SMichael Clark             break;
2704*ea103259SMichael Clark         case rvc_csr_eq_0xc01:
2705*ea103259SMichael Clark             if (!(imm == 0xc01)) {
2706*ea103259SMichael Clark                 return false;
2707*ea103259SMichael Clark             }
2708*ea103259SMichael Clark             break;
2709*ea103259SMichael Clark         case rvc_csr_eq_0xc02:
2710*ea103259SMichael Clark             if (!(imm == 0xc02)) {
2711*ea103259SMichael Clark                 return false;
2712*ea103259SMichael Clark             }
2713*ea103259SMichael Clark             break;
2714*ea103259SMichael Clark         case rvc_csr_eq_0xc80:
2715*ea103259SMichael Clark             if (!(imm == 0xc80)) {
2716*ea103259SMichael Clark                 return false;
2717*ea103259SMichael Clark             }
2718*ea103259SMichael Clark             break;
2719*ea103259SMichael Clark         case rvc_csr_eq_0xc81:
2720*ea103259SMichael Clark             if (!(imm == 0xc81)) {
2721*ea103259SMichael Clark                 return false;
2722*ea103259SMichael Clark             }
2723*ea103259SMichael Clark             break;
2724*ea103259SMichael Clark         case rvc_csr_eq_0xc82:
2725*ea103259SMichael Clark             if (!(imm == 0xc82)) {
2726*ea103259SMichael Clark                 return false;
2727*ea103259SMichael Clark             }
2728*ea103259SMichael Clark             break;
2729*ea103259SMichael Clark         default: break;
2730*ea103259SMichael Clark         }
2731*ea103259SMichael Clark         c++;
2732*ea103259SMichael Clark     }
2733*ea103259SMichael Clark     return true;
2734*ea103259SMichael Clark }
2735*ea103259SMichael Clark 
2736*ea103259SMichael Clark /* instruction length */
2737*ea103259SMichael Clark 
2738*ea103259SMichael Clark static size_t inst_length(rv_inst inst)
2739*ea103259SMichael Clark {
2740*ea103259SMichael Clark     /* NOTE: supports maximum instruction size of 64-bits */
2741*ea103259SMichael Clark 
2742*ea103259SMichael Clark     /* instruction length coding
2743*ea103259SMichael Clark      *
2744*ea103259SMichael Clark      *      aa - 16 bit aa != 11
2745*ea103259SMichael Clark      *   bbb11 - 32 bit bbb != 111
2746*ea103259SMichael Clark      *  011111 - 48 bit
2747*ea103259SMichael Clark      * 0111111 - 64 bit
2748*ea103259SMichael Clark      */
2749*ea103259SMichael Clark 
2750*ea103259SMichael Clark     return (inst &      0b11) != 0b11      ? 2
2751*ea103259SMichael Clark          : (inst &   0b11100) != 0b11100   ? 4
2752*ea103259SMichael Clark          : (inst &  0b111111) == 0b011111  ? 6
2753*ea103259SMichael Clark          : (inst & 0b1111111) == 0b0111111 ? 8
2754*ea103259SMichael Clark          : 0;
2755*ea103259SMichael Clark }
2756*ea103259SMichael Clark 
2757*ea103259SMichael Clark /* format instruction */
2758*ea103259SMichael Clark 
2759*ea103259SMichael Clark static void append(char *s1, const char *s2, size_t n)
2760*ea103259SMichael Clark {
2761*ea103259SMichael Clark     size_t l1 = strlen(s1);
2762*ea103259SMichael Clark     if (n - l1 - 1 > 0) {
2763*ea103259SMichael Clark         strncat(s1, s2, n - l1);
2764*ea103259SMichael Clark     }
2765*ea103259SMichael Clark }
2766*ea103259SMichael Clark 
2767*ea103259SMichael Clark static void format_inst(char *buf, size_t buflen, size_t tab, rv_decode *dec)
2768*ea103259SMichael Clark {
2769*ea103259SMichael Clark     char tmp[64];
2770*ea103259SMichael Clark     const char *fmt;
2771*ea103259SMichael Clark 
2772*ea103259SMichael Clark     if (dec->op == rv_op_illegal) {
2773*ea103259SMichael Clark         size_t len = inst_length(dec->inst);
2774*ea103259SMichael Clark         switch (len) {
2775*ea103259SMichael Clark         case 2:
2776*ea103259SMichael Clark             snprintf(buf, buflen, "(0x%04" PRIx64 ")", dec->inst);
2777*ea103259SMichael Clark             break;
2778*ea103259SMichael Clark         case 4:
2779*ea103259SMichael Clark             snprintf(buf, buflen, "(0x%08" PRIx64 ")", dec->inst);
2780*ea103259SMichael Clark             break;
2781*ea103259SMichael Clark         case 6:
2782*ea103259SMichael Clark             snprintf(buf, buflen, "(0x%012" PRIx64 ")", dec->inst);
2783*ea103259SMichael Clark             break;
2784*ea103259SMichael Clark         default:
2785*ea103259SMichael Clark             snprintf(buf, buflen, "(0x%016" PRIx64 ")", dec->inst);
2786*ea103259SMichael Clark             break;
2787*ea103259SMichael Clark         }
2788*ea103259SMichael Clark         return;
2789*ea103259SMichael Clark     }
2790*ea103259SMichael Clark 
2791*ea103259SMichael Clark     fmt = opcode_data[dec->op].format;
2792*ea103259SMichael Clark     while (*fmt) {
2793*ea103259SMichael Clark         switch (*fmt) {
2794*ea103259SMichael Clark         case 'O':
2795*ea103259SMichael Clark             append(buf, opcode_data[dec->op].name, buflen);
2796*ea103259SMichael Clark             break;
2797*ea103259SMichael Clark         case '(':
2798*ea103259SMichael Clark             append(buf, "(", buflen);
2799*ea103259SMichael Clark             break;
2800*ea103259SMichael Clark         case ',':
2801*ea103259SMichael Clark             append(buf, ",", buflen);
2802*ea103259SMichael Clark             break;
2803*ea103259SMichael Clark         case ')':
2804*ea103259SMichael Clark             append(buf, ")", buflen);
2805*ea103259SMichael Clark             break;
2806*ea103259SMichael Clark         case '0':
2807*ea103259SMichael Clark             append(buf, rv_ireg_name_sym[dec->rd], buflen);
2808*ea103259SMichael Clark             break;
2809*ea103259SMichael Clark         case '1':
2810*ea103259SMichael Clark             append(buf, rv_ireg_name_sym[dec->rs1], buflen);
2811*ea103259SMichael Clark             break;
2812*ea103259SMichael Clark         case '2':
2813*ea103259SMichael Clark             append(buf, rv_ireg_name_sym[dec->rs2], buflen);
2814*ea103259SMichael Clark             break;
2815*ea103259SMichael Clark         case '3':
2816*ea103259SMichael Clark             append(buf, rv_freg_name_sym[dec->rd], buflen);
2817*ea103259SMichael Clark             break;
2818*ea103259SMichael Clark         case '4':
2819*ea103259SMichael Clark             append(buf, rv_freg_name_sym[dec->rs1], buflen);
2820*ea103259SMichael Clark             break;
2821*ea103259SMichael Clark         case '5':
2822*ea103259SMichael Clark             append(buf, rv_freg_name_sym[dec->rs2], buflen);
2823*ea103259SMichael Clark             break;
2824*ea103259SMichael Clark         case '6':
2825*ea103259SMichael Clark             append(buf, rv_freg_name_sym[dec->rs3], buflen);
2826*ea103259SMichael Clark             break;
2827*ea103259SMichael Clark         case '7':
2828*ea103259SMichael Clark             snprintf(tmp, sizeof(tmp), "%d", dec->rs1);
2829*ea103259SMichael Clark             append(buf, tmp, buflen);
2830*ea103259SMichael Clark             break;
2831*ea103259SMichael Clark         case 'i':
2832*ea103259SMichael Clark             snprintf(tmp, sizeof(tmp), "%d", dec->imm);
2833*ea103259SMichael Clark             append(buf, tmp, buflen);
2834*ea103259SMichael Clark             break;
2835*ea103259SMichael Clark         case 'o':
2836*ea103259SMichael Clark             snprintf(tmp, sizeof(tmp), "%d", dec->imm);
2837*ea103259SMichael Clark             append(buf, tmp, buflen);
2838*ea103259SMichael Clark             while (strlen(buf) < tab * 2) {
2839*ea103259SMichael Clark                 append(buf, " ", buflen);
2840*ea103259SMichael Clark             }
2841*ea103259SMichael Clark             snprintf(tmp, sizeof(tmp), "# 0x%" PRIx64,
2842*ea103259SMichael Clark                 dec->pc + dec->imm);
2843*ea103259SMichael Clark             append(buf, tmp, buflen);
2844*ea103259SMichael Clark             break;
2845*ea103259SMichael Clark         case 'c': {
2846*ea103259SMichael Clark             const char *name = csr_name(dec->imm & 0xfff);
2847*ea103259SMichael Clark             if (name) {
2848*ea103259SMichael Clark                 append(buf, name, buflen);
2849*ea103259SMichael Clark             } else {
2850*ea103259SMichael Clark                 snprintf(tmp, sizeof(tmp), "0x%03x", dec->imm & 0xfff);
2851*ea103259SMichael Clark                 append(buf, tmp, buflen);
2852*ea103259SMichael Clark             }
2853*ea103259SMichael Clark             break;
2854*ea103259SMichael Clark         }
2855*ea103259SMichael Clark         case 'r':
2856*ea103259SMichael Clark             switch (dec->rm) {
2857*ea103259SMichael Clark             case rv_rm_rne:
2858*ea103259SMichael Clark                 append(buf, "rne", buflen);
2859*ea103259SMichael Clark                 break;
2860*ea103259SMichael Clark             case rv_rm_rtz:
2861*ea103259SMichael Clark                 append(buf, "rtz", buflen);
2862*ea103259SMichael Clark                 break;
2863*ea103259SMichael Clark             case rv_rm_rdn:
2864*ea103259SMichael Clark                 append(buf, "rdn", buflen);
2865*ea103259SMichael Clark                 break;
2866*ea103259SMichael Clark             case rv_rm_rup:
2867*ea103259SMichael Clark                 append(buf, "rup", buflen);
2868*ea103259SMichael Clark                 break;
2869*ea103259SMichael Clark             case rv_rm_rmm:
2870*ea103259SMichael Clark                 append(buf, "rmm", buflen);
2871*ea103259SMichael Clark                 break;
2872*ea103259SMichael Clark             case rv_rm_dyn:
2873*ea103259SMichael Clark                 append(buf, "dyn", buflen);
2874*ea103259SMichael Clark                 break;
2875*ea103259SMichael Clark             default:
2876*ea103259SMichael Clark                 append(buf, "inv", buflen);
2877*ea103259SMichael Clark                 break;
2878*ea103259SMichael Clark             }
2879*ea103259SMichael Clark             break;
2880*ea103259SMichael Clark         case 'p':
2881*ea103259SMichael Clark             if (dec->pred & rv_fence_i) {
2882*ea103259SMichael Clark                 append(buf, "i", buflen);
2883*ea103259SMichael Clark             }
2884*ea103259SMichael Clark             if (dec->pred & rv_fence_o) {
2885*ea103259SMichael Clark                 append(buf, "o", buflen);
2886*ea103259SMichael Clark             }
2887*ea103259SMichael Clark             if (dec->pred & rv_fence_r) {
2888*ea103259SMichael Clark                 append(buf, "r", buflen);
2889*ea103259SMichael Clark             }
2890*ea103259SMichael Clark             if (dec->pred & rv_fence_w) {
2891*ea103259SMichael Clark                 append(buf, "w", buflen);
2892*ea103259SMichael Clark             }
2893*ea103259SMichael Clark             break;
2894*ea103259SMichael Clark         case 's':
2895*ea103259SMichael Clark             if (dec->succ & rv_fence_i) {
2896*ea103259SMichael Clark                 append(buf, "i", buflen);
2897*ea103259SMichael Clark             }
2898*ea103259SMichael Clark             if (dec->succ & rv_fence_o) {
2899*ea103259SMichael Clark                 append(buf, "o", buflen);
2900*ea103259SMichael Clark             }
2901*ea103259SMichael Clark             if (dec->succ & rv_fence_r) {
2902*ea103259SMichael Clark                 append(buf, "r", buflen);
2903*ea103259SMichael Clark             }
2904*ea103259SMichael Clark             if (dec->succ & rv_fence_w) {
2905*ea103259SMichael Clark                 append(buf, "w", buflen);
2906*ea103259SMichael Clark             }
2907*ea103259SMichael Clark             break;
2908*ea103259SMichael Clark         case '\t':
2909*ea103259SMichael Clark             while (strlen(buf) < tab) {
2910*ea103259SMichael Clark                 append(buf, " ", buflen);
2911*ea103259SMichael Clark             }
2912*ea103259SMichael Clark             break;
2913*ea103259SMichael Clark         case 'A':
2914*ea103259SMichael Clark             if (dec->aq) {
2915*ea103259SMichael Clark                 append(buf, ".aq", buflen);
2916*ea103259SMichael Clark             }
2917*ea103259SMichael Clark             break;
2918*ea103259SMichael Clark         case 'R':
2919*ea103259SMichael Clark             if (dec->rl) {
2920*ea103259SMichael Clark                 append(buf, ".rl", buflen);
2921*ea103259SMichael Clark             }
2922*ea103259SMichael Clark             break;
2923*ea103259SMichael Clark         default:
2924*ea103259SMichael Clark             break;
2925*ea103259SMichael Clark         }
2926*ea103259SMichael Clark         fmt++;
2927*ea103259SMichael Clark     }
2928*ea103259SMichael Clark }
2929*ea103259SMichael Clark 
2930*ea103259SMichael Clark /* lift instruction to pseudo-instruction */
2931*ea103259SMichael Clark 
2932*ea103259SMichael Clark static void decode_inst_lift_pseudo(rv_decode *dec)
2933*ea103259SMichael Clark {
2934*ea103259SMichael Clark     const rv_comp_data *comp_data = opcode_data[dec->op].pseudo;
2935*ea103259SMichael Clark     if (!comp_data) {
2936*ea103259SMichael Clark         return;
2937*ea103259SMichael Clark     }
2938*ea103259SMichael Clark     while (comp_data->constraints) {
2939*ea103259SMichael Clark         if (check_constraints(dec, comp_data->constraints)) {
2940*ea103259SMichael Clark             dec->op = comp_data->op;
2941*ea103259SMichael Clark             dec->codec = opcode_data[dec->op].codec;
2942*ea103259SMichael Clark             return;
2943*ea103259SMichael Clark         }
2944*ea103259SMichael Clark         comp_data++;
2945*ea103259SMichael Clark     }
2946*ea103259SMichael Clark }
2947*ea103259SMichael Clark 
2948*ea103259SMichael Clark /* decompress instruction */
2949*ea103259SMichael Clark 
2950*ea103259SMichael Clark static void decode_inst_decompress_rv32(rv_decode *dec)
2951*ea103259SMichael Clark {
2952*ea103259SMichael Clark     int decomp_op = opcode_data[dec->op].decomp_rv32;
2953*ea103259SMichael Clark     if (decomp_op != rv_op_illegal) {
2954*ea103259SMichael Clark         dec->op = decomp_op;
2955*ea103259SMichael Clark         dec->codec = opcode_data[decomp_op].codec;
2956*ea103259SMichael Clark     }
2957*ea103259SMichael Clark }
2958*ea103259SMichael Clark 
2959*ea103259SMichael Clark static void decode_inst_decompress_rv64(rv_decode *dec)
2960*ea103259SMichael Clark {
2961*ea103259SMichael Clark     int decomp_op = opcode_data[dec->op].decomp_rv64;
2962*ea103259SMichael Clark     if (decomp_op != rv_op_illegal) {
2963*ea103259SMichael Clark         dec->op = decomp_op;
2964*ea103259SMichael Clark         dec->codec = opcode_data[decomp_op].codec;
2965*ea103259SMichael Clark     }
2966*ea103259SMichael Clark }
2967*ea103259SMichael Clark 
2968*ea103259SMichael Clark static void decode_inst_decompress_rv128(rv_decode *dec)
2969*ea103259SMichael Clark {
2970*ea103259SMichael Clark     int decomp_op = opcode_data[dec->op].decomp_rv128;
2971*ea103259SMichael Clark     if (decomp_op != rv_op_illegal) {
2972*ea103259SMichael Clark         dec->op = decomp_op;
2973*ea103259SMichael Clark         dec->codec = opcode_data[decomp_op].codec;
2974*ea103259SMichael Clark     }
2975*ea103259SMichael Clark }
2976*ea103259SMichael Clark 
2977*ea103259SMichael Clark static void decode_inst_decompress(rv_decode *dec, rv_isa isa)
2978*ea103259SMichael Clark {
2979*ea103259SMichael Clark     switch (isa) {
2980*ea103259SMichael Clark     case rv32:
2981*ea103259SMichael Clark         decode_inst_decompress_rv32(dec);
2982*ea103259SMichael Clark         break;
2983*ea103259SMichael Clark     case rv64:
2984*ea103259SMichael Clark         decode_inst_decompress_rv64(dec);
2985*ea103259SMichael Clark         break;
2986*ea103259SMichael Clark     case rv128:
2987*ea103259SMichael Clark         decode_inst_decompress_rv128(dec);
2988*ea103259SMichael Clark         break;
2989*ea103259SMichael Clark     }
2990*ea103259SMichael Clark }
2991*ea103259SMichael Clark 
2992*ea103259SMichael Clark /* disassemble instruction */
2993*ea103259SMichael Clark 
2994*ea103259SMichael Clark static void
2995*ea103259SMichael Clark disasm_inst(char *buf, size_t buflen, rv_isa isa, uint64_t pc, rv_inst inst)
2996*ea103259SMichael Clark {
2997*ea103259SMichael Clark     rv_decode dec = { 0 };
2998*ea103259SMichael Clark     dec.pc = pc;
2999*ea103259SMichael Clark     dec.inst = inst;
3000*ea103259SMichael Clark     decode_inst_opcode(&dec, isa);
3001*ea103259SMichael Clark     decode_inst_operands(&dec);
3002*ea103259SMichael Clark     decode_inst_decompress(&dec, isa);
3003*ea103259SMichael Clark     decode_inst_lift_pseudo(&dec);
3004*ea103259SMichael Clark     format_inst(buf, buflen, 16, &dec);
3005*ea103259SMichael Clark }
3006*ea103259SMichael Clark 
3007*ea103259SMichael Clark static int
3008*ea103259SMichael Clark print_insn_riscv(bfd_vma memaddr, struct disassemble_info *info, rv_isa isa)
3009*ea103259SMichael Clark {
3010*ea103259SMichael Clark     char buf[128] = { 0 };
3011*ea103259SMichael Clark     bfd_byte packet[2];
3012*ea103259SMichael Clark     rv_inst inst = 0;
3013*ea103259SMichael Clark     size_t len = 2;
3014*ea103259SMichael Clark     bfd_vma n;
3015*ea103259SMichael Clark     int status;
3016*ea103259SMichael Clark 
3017*ea103259SMichael Clark     /* Instructions are made of 2-byte packets in little-endian order */
3018*ea103259SMichael Clark     for (n = 0; n < len; n += 2) {
3019*ea103259SMichael Clark         status = (*info->read_memory_func)(memaddr + n, packet, 2, info);
3020*ea103259SMichael Clark         if (status != 0) {
3021*ea103259SMichael Clark             /* Don't fail just because we fell off the end.  */
3022*ea103259SMichael Clark             if (n > 0) {
3023*ea103259SMichael Clark                 break;
3024*ea103259SMichael Clark             }
3025*ea103259SMichael Clark             (*info->memory_error_func)(status, memaddr, info);
3026*ea103259SMichael Clark             return status;
3027*ea103259SMichael Clark         }
3028*ea103259SMichael Clark         inst |= ((rv_inst) bfd_getl16(packet)) << (8 * n);
3029*ea103259SMichael Clark         if (n == 0) {
3030*ea103259SMichael Clark             len = inst_length(inst);
3031*ea103259SMichael Clark         }
3032*ea103259SMichael Clark     }
3033*ea103259SMichael Clark 
3034*ea103259SMichael Clark     disasm_inst(buf, sizeof(buf), isa, memaddr, inst);
3035*ea103259SMichael Clark     (*info->fprintf_func)(info->stream, "%s", buf);
3036*ea103259SMichael Clark 
3037*ea103259SMichael Clark     return len;
3038*ea103259SMichael Clark }
3039*ea103259SMichael Clark 
3040*ea103259SMichael Clark int print_insn_riscv32(bfd_vma memaddr, struct disassemble_info *info)
3041*ea103259SMichael Clark {
3042*ea103259SMichael Clark     return print_insn_riscv(memaddr, info, rv32);
3043*ea103259SMichael Clark }
3044*ea103259SMichael Clark 
3045*ea103259SMichael Clark int print_insn_riscv64(bfd_vma memaddr, struct disassemble_info *info)
3046*ea103259SMichael Clark {
3047*ea103259SMichael Clark     return print_insn_riscv(memaddr, info, rv64);
3048*ea103259SMichael Clark }
3049