Use new NaN discipline
[riscv-isa-sim.git] / hwacha / decode_hwacha.h
1 #ifndef _DECODE_HWACHA_H
2 #define _DECODE_HWACHA_H
3
4 #include "hwacha.h"
5 #include "hwacha_xcpt.h"
6 #include "mmu.h"
7
8 #define XS1 (xs1)
9 #define XS2 (xs2)
10 #define WRITE_XRD(value) (xd = value)
11
12 #define NXPR (h->get_ct_state()->nxpr)
13 #define NFPR (h->get_ct_state()->nfpr)
14 #define MAXVL (h->get_ct_state()->maxvl)
15 #define VL (h->get_ct_state()->vl)
16 #define UTIDX (h->get_ct_state()->count)
17 #define PREC (h->get_ct_state()->prec)
18 #define VF_PC (h->get_ct_state()->vf_pc)
19 #define WRITE_NXPR(nxprnext) (h->get_ct_state()->nxpr = (nxprnext))
20 #define WRITE_NFPR(nfprnext) (h->get_ct_state()->nfpr = (nfprnext))
21 #define WRITE_MAXVL(maxvlnext) (h->get_ct_state()->maxvl = (maxvlnext))
22 #define WRITE_VL(vlnext) (h->get_ct_state()->vl = (vlnext))
23 #define WRITE_UTIDX(value) (h->get_ct_state()->count = (value))
24 #define WRITE_VF_PC(pcnext) (h->get_ct_state()->vf_pc = (pcnext))
25 #define WRITE_PREC(precision) (h->get_ct_state()->prec = (precision))
26
27 #define INSN_RS1 (insn.rs1())
28 #define INSN_RS2 (insn.rs2())
29 #define INSN_RS3 (insn.rs3())
30 #define INSN_RD (insn.rd())
31 #define INSN_SEG (((reg_t)insn.i_imm() >> 9)+1)
32
33 static inline reg_t read_xpr(hwacha_t* h, insn_t insn, uint32_t idx, size_t src)
34 {
35 if (src >= h->get_ct_state()->nxpr)
36 h->take_exception(HWACHA_CAUSE_TVEC_ILLEGAL_REGID, uint32_t(insn.bits()));
37 return (h->get_ut_state(idx)->XPR[src]);
38 }
39
40 static inline void write_xpr(hwacha_t* h, insn_t insn, uint32_t idx, size_t dst, reg_t value)
41 {
42 if (dst >= h->get_ct_state()->nxpr)
43 h->take_exception(HWACHA_CAUSE_TVEC_ILLEGAL_REGID, uint32_t(insn.bits()));
44 h->get_ut_state(idx)->XPR.write(dst, value);
45 }
46
47 #define UT_READ_XPR(idx, src) read_xpr(h, insn, idx, src)
48 #define UT_WRITE_XPR(idx, dst, value) write_xpr(h, insn, idx, dst, value)
49 #define UT_RS1(idx) (UT_READ_XPR(idx, INSN_RS1))
50 #define UT_RS2(idx) (UT_READ_XPR(idx, INSN_RS2))
51 #define UT_WRITE_RD(idx, value) (UT_WRITE_XPR(idx, INSN_RD, value))
52
53 static inline reg_t read_fpr(hwacha_t* h, insn_t insn, uint32_t idx, size_t src)
54 {
55 if (src >= h->get_ct_state()->nfpr)
56 h->take_exception(HWACHA_CAUSE_TVEC_ILLEGAL_REGID, uint32_t(insn.bits()));
57 return (h->get_ut_state(idx)->FPR[src]);
58 }
59
60 static inline void write_fpr(hwacha_t* h, insn_t insn, uint32_t idx, size_t dst, reg_t value)
61 {
62 if (dst >= h->get_ct_state()->nfpr)
63 h->take_exception(HWACHA_CAUSE_TVEC_ILLEGAL_REGID, uint32_t(insn.bits()));
64 h->get_ut_state(idx)->FPR.write(dst, value);
65 }
66
67 #define UT_READ_FPR(idx, src) read_fpr(h, insn, idx, src)
68 #define UT_WRITE_FPR(idx, dst, value) write_fpr(h, insn, idx, dst, value)
69 #define UT_FRS1(idx) (UT_READ_FPR(idx, INSN_RS1))
70 #define UT_FRS2(idx) (UT_READ_FPR(idx, INSN_RS2))
71 #define UT_FRS3(idx) (UT_READ_FPR(idx, INSN_RS3))
72 #define UT_WRITE_FRD(idx, value) (UT_WRITE_FPR(idx, INSN_RD, value))
73
74 #define VEC_SEG_LOAD(dst, func, inc) \
75 VEC_SEG_ST_LOAD(dst, func, INSN_SEG*inc, inc)
76
77 #define VEC_SEG_ST_LOAD(dst, func, stride, inc) \
78 reg_t seg_addr = XS1; \
79 for (uint32_t i=0; i<VL; i++) { \
80 reg_t addr = seg_addr; \
81 seg_addr += stride; \
82 for (uint32_t j=0; j<INSN_SEG; j++) { \
83 UT_WRITE_##dst(i, INSN_RD+j, p->get_mmu()->func(addr)); \
84 addr += inc; \
85 } \
86 }
87
88 #define VEC_SEG_STORE(src, func, inc) \
89 VEC_SEG_ST_STORE(src, func, INSN_SEG*inc, inc)
90
91 #define VEC_SEG_ST_STORE(src, func, stride, inc) \
92 reg_t seg_addr = XS1; \
93 for (uint32_t i=0; i<VL; i++) { \
94 reg_t addr = seg_addr; \
95 seg_addr += stride; \
96 for (uint32_t j=0; j<INSN_SEG; j++) { \
97 p->get_mmu()->func(addr, UT_READ_##src(i, INSN_RD+j)); \
98 addr += inc; \
99 } \
100 }
101
102 #define require_supervisor_hwacha \
103 if (get_field(p->get_state()->mstatus, MSTATUS_PRV) < PRV_S) \
104 h->take_exception(HWACHA_CAUSE_PRIVILEGED_INSTRUCTION, uint32_t(insn.bits()));
105
106 #endif