diff --git a/riscv/insn_template.h b/riscv/insn_template.h index bf9d9d74..7a9aadd8 100644 --- a/riscv/insn_template.h +++ b/riscv/insn_template.h @@ -7,6 +7,7 @@ #include "internals.h" #include "specialize.h" #include "tracer.h" +#include "p_ext_macros.h" #include "v_ext_macros.h" #include "debug_defines.h" #include diff --git a/riscv/insns/aadd.h b/riscv/insns/aadd.h new file mode 100644 index 00000000..5456cef6 --- /dev/null +++ b/riscv/insns/aadd.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD((RS1 + RS2)>>1); \ No newline at end of file diff --git a/riscv/insns/aaddu.h b/riscv/insns/aaddu.h new file mode 100644 index 00000000..bf011496 --- /dev/null +++ b/riscv/insns/aaddu.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD((0ULL + (uint32_t)RS1 + (uint32_t)RS2)>>1); \ No newline at end of file diff --git a/riscv/insns/abs.h b/riscv/insns/abs.h new file mode 100644 index 00000000..1b747ffe --- /dev/null +++ b/riscv/insns/abs.h @@ -0,0 +1,4 @@ +require_extension('P'); +reg_t s1 = RS1; +reg_t result = (int64_t(s1) < 0) ? -s1 : s1; +WRITE_RD(sext_xlen(result)); \ No newline at end of file diff --git a/riscv/insns/asub.h b/riscv/insns/asub.h new file mode 100644 index 00000000..b7a7ab53 --- /dev/null +++ b/riscv/insns/asub.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD((RS1 - RS2)>>1); \ No newline at end of file diff --git a/riscv/insns/asubu.h b/riscv/insns/asubu.h new file mode 100644 index 00000000..6139feb2 --- /dev/null +++ b/riscv/insns/asubu.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD((0ULL + (uint32_t)RS1 - (uint32_t)RS2)>>1); \ No newline at end of file diff --git a/riscv/insns/cls.h b/riscv/insns/cls.h new file mode 100644 index 00000000..3d80b618 --- /dev/null +++ b/riscv/insns/cls.h @@ -0,0 +1,10 @@ +require_extension('P'); +reg_t x = xlen - 1; +reg_t msb = (RS1 >> (xlen - 1)) & 1; +for (int i = 0; i < xlen - 1; i++) { + if (msb != ((RS1 >> (xlen - i - 2)) & 1)) { + x = i; + break; + } +} +WRITE_RD(sext_xlen(x)); \ No newline at end of file diff --git a/riscv/insns/macc_h00.h b/riscv/insns/macc_h00.h new file mode 100644 index 00000000..bddbc4cd --- /dev/null +++ b/riscv/insns/macc_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + sext(RS1, 16) * sext(RS2, 16)); \ No newline at end of file diff --git a/riscv/insns/macc_h01.h b/riscv/insns/macc_h01.h new file mode 100644 index 00000000..551e4568 --- /dev/null +++ b/riscv/insns/macc_h01.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + sext(RS1, 16) * sext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/macc_h11.h b/riscv/insns/macc_h11.h new file mode 100644 index 00000000..73104545 --- /dev/null +++ b/riscv/insns/macc_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + sext(RS1 >> 16, 16) * sext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/maccsu_h00.h b/riscv/insns/maccsu_h00.h new file mode 100644 index 00000000..4039c255 --- /dev/null +++ b/riscv/insns/maccsu_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + sext(RS1, 16) * zext(RS2, 16)); \ No newline at end of file diff --git a/riscv/insns/maccsu_h11.h b/riscv/insns/maccsu_h11.h new file mode 100644 index 00000000..1bbde234 --- /dev/null +++ b/riscv/insns/maccsu_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + sext(RS1 >> 16, 16) * zext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/maccu_h00.h b/riscv/insns/maccu_h00.h new file mode 100644 index 00000000..22002959 --- /dev/null +++ b/riscv/insns/maccu_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + zext(RS1, 16) * zext(RS2, 16)); \ No newline at end of file diff --git a/riscv/insns/maccu_h01.h b/riscv/insns/maccu_h01.h new file mode 100644 index 00000000..a35865bf --- /dev/null +++ b/riscv/insns/maccu_h01.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + zext(RS1, 16) * zext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/maccu_h11.h b/riscv/insns/maccu_h11.h new file mode 100644 index 00000000..a30a8760 --- /dev/null +++ b/riscv/insns/maccu_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + zext(RS1 >> 16, 16) * zext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/merge.h b/riscv/insns/merge.h new file mode 100644 index 00000000..d184c5c8 --- /dev/null +++ b/riscv/insns/merge.h @@ -0,0 +1,2 @@ +require_extension('P'); +WRITE_RD((RS2 & RD) | (RS1 & ~RD)); \ No newline at end of file diff --git a/riscv/insns/mhacc.h b/riscv/insns/mhacc.h new file mode 100644 index 00000000..77de911d --- /dev/null +++ b/riscv/insns/mhacc.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * sext32(RS2); +WRITE_RD(RD + (mres >> 32)); \ No newline at end of file diff --git a/riscv/insns/mhacc_h0.h b/riscv/insns/mhacc_h0.h new file mode 100644 index 00000000..699e9165 --- /dev/null +++ b/riscv/insns/mhacc_h0.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * sext32(P_FIELD(RS2, 0, 16)); +WRITE_RD(RD + (mres >> 32)); \ No newline at end of file diff --git a/riscv/insns/mhacc_h1.h b/riscv/insns/mhacc_h1.h new file mode 100644 index 00000000..ea228fe6 --- /dev/null +++ b/riscv/insns/mhacc_h1.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * sext32(P_FIELD(RS2, 1, 16)); +WRITE_RD(RD + (mres >> 32)); \ No newline at end of file diff --git a/riscv/insns/mhaccsu.h b/riscv/insns/mhaccsu.h new file mode 100644 index 00000000..328355c1 --- /dev/null +++ b/riscv/insns/mhaccsu.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * reg_t((uint32_t)RS2); +WRITE_RD(RD + (mres >> 32)); \ No newline at end of file diff --git a/riscv/insns/mhaccsu_h0.h b/riscv/insns/mhaccsu_h0.h new file mode 100644 index 00000000..e89f309b --- /dev/null +++ b/riscv/insns/mhaccsu_h0.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * (uint32_t)P_FIELD(RS2, 0, 16); +WRITE_RD(RD + (mres >> 32)); \ No newline at end of file diff --git a/riscv/insns/mhaccsu_h1.h b/riscv/insns/mhaccsu_h1.h new file mode 100644 index 00000000..e49a15f6 --- /dev/null +++ b/riscv/insns/mhaccsu_h1.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * (uint32_t)P_FIELD(RS2, 1, 16); +WRITE_RD(RD + (mres >> 32)); \ No newline at end of file diff --git a/riscv/insns/mhaccu.h b/riscv/insns/mhaccu.h new file mode 100644 index 00000000..e9fb8020 --- /dev/null +++ b/riscv/insns/mhaccu.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +uint64_t mres = reg_t((uint32_t)RS1) * reg_t((uint32_t)RS2); +WRITE_RD(RD + (mres >> 32)); \ No newline at end of file diff --git a/riscv/insns/mhracc.h b/riscv/insns/mhracc.h new file mode 100644 index 00000000..902b0e56 --- /dev/null +++ b/riscv/insns/mhracc.h @@ -0,0 +1,5 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * sext32(RS2); +int32_t round = ((mres >> 31) + 1) >> 1; +WRITE_RD(RD + round); \ No newline at end of file diff --git a/riscv/insns/mhraccsu.h b/riscv/insns/mhraccsu.h new file mode 100644 index 00000000..5d676ba6 --- /dev/null +++ b/riscv/insns/mhraccsu.h @@ -0,0 +1,5 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext(RS1,64) * reg_t((uint32_t)RS2); +int32_t round = ((mres >> 31) + 1) >> 1; +WRITE_RD(RD + round); \ No newline at end of file diff --git a/riscv/insns/mhraccu.h b/riscv/insns/mhraccu.h new file mode 100644 index 00000000..9cf5e5a4 --- /dev/null +++ b/riscv/insns/mhraccu.h @@ -0,0 +1,5 @@ +require_extension('P'); +require_rv32; +reg_t mres = reg_t((uint32_t)RS1) * reg_t((uint32_t)RS2); +uint32_t round = ((mres >> 31) + 1) >> 1; +WRITE_RD(RD + round); \ No newline at end of file diff --git a/riscv/insns/mqacc_h00.h b/riscv/insns/mqacc_h00.h new file mode 100644 index 00000000..7b4b8e7c --- /dev/null +++ b/riscv/insns/mqacc_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + (((int32_t)P_FIELD(RS1, 0, 16) * P_FIELD(RS2, 0, 16)) >> 15)); \ No newline at end of file diff --git a/riscv/insns/mqacc_h01.h b/riscv/insns/mqacc_h01.h new file mode 100644 index 00000000..ff618720 --- /dev/null +++ b/riscv/insns/mqacc_h01.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + (((int32_t)P_FIELD(RS1, 0, 16) * P_FIELD(RS2, 1, 16)) >> 15)); \ No newline at end of file diff --git a/riscv/insns/mqacc_h11.h b/riscv/insns/mqacc_h11.h new file mode 100644 index 00000000..ac9e18bc --- /dev/null +++ b/riscv/insns/mqacc_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + (((int32_t)P_FIELD(RS1, 1, 16) * P_FIELD(RS2, 1, 16)) >> 15)); \ No newline at end of file diff --git a/riscv/insns/mqracc_h00.h b/riscv/insns/mqracc_h00.h new file mode 100644 index 00000000..37d49bde --- /dev/null +++ b/riscv/insns/mqracc_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + (((int32_t)P_FIELD(RS1, 0, 16) * P_FIELD(RS2, 0, 16) + 0x4000) >> 15)); \ No newline at end of file diff --git a/riscv/insns/mqracc_h01.h b/riscv/insns/mqracc_h01.h new file mode 100644 index 00000000..3e7358e5 --- /dev/null +++ b/riscv/insns/mqracc_h01.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + (((int32_t)P_FIELD(RS1, 0, 16) * P_FIELD(RS2, 1, 16) + 0x4000) >> 15)); \ No newline at end of file diff --git a/riscv/insns/mqracc_h11.h b/riscv/insns/mqracc_h11.h new file mode 100644 index 00000000..c4eb4860 --- /dev/null +++ b/riscv/insns/mqracc_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RD + (((int32_t)P_FIELD(RS1, 1, 16) * P_FIELD(RS2, 1, 16) + 0x4000) >> 15)); \ No newline at end of file diff --git a/riscv/insns/mseq.h b/riscv/insns/mseq.h new file mode 100644 index 00000000..cf540b20 --- /dev/null +++ b/riscv/insns/mseq.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(RS1 == RS2 ? -1 : 0); \ No newline at end of file diff --git a/riscv/insns/mslt.h b/riscv/insns/mslt.h new file mode 100644 index 00000000..18aa387a --- /dev/null +++ b/riscv/insns/mslt.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD((int32_t)RS1 < (int32_t)RS2 ? -1 : 0); \ No newline at end of file diff --git a/riscv/insns/msltu.h b/riscv/insns/msltu.h new file mode 100644 index 00000000..062f12df --- /dev/null +++ b/riscv/insns/msltu.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD((uint32_t)RS1 < (uint32_t)RS2 ? -1 : 0); \ No newline at end of file diff --git a/riscv/insns/mul_h00.h b/riscv/insns/mul_h00.h new file mode 100644 index 00000000..69bfaae6 --- /dev/null +++ b/riscv/insns/mul_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(sext(RS1, 16) * sext(RS2, 16)); \ No newline at end of file diff --git a/riscv/insns/mul_h01.h b/riscv/insns/mul_h01.h new file mode 100644 index 00000000..ec95fe17 --- /dev/null +++ b/riscv/insns/mul_h01.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(sext(RS1, 16) * sext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/mul_h11.h b/riscv/insns/mul_h11.h new file mode 100644 index 00000000..4ea0d680 --- /dev/null +++ b/riscv/insns/mul_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(sext(RS1 >> 16, 16) * sext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/mulh_h0.h b/riscv/insns/mulh_h0.h new file mode 100644 index 00000000..2143d3d2 --- /dev/null +++ b/riscv/insns/mulh_h0.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +int64_t mres = sext(RS1,64) * sext(P_FIELD(RS2, 0, 16),64); +WRITE_RD(mres>>32); \ No newline at end of file diff --git a/riscv/insns/mulh_h1.h b/riscv/insns/mulh_h1.h new file mode 100644 index 00000000..5e5bf994 --- /dev/null +++ b/riscv/insns/mulh_h1.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +int64_t mres = sext(RS1,64) * sext(P_FIELD(RS2, 1, 16),64); +WRITE_RD(mres>>32); \ No newline at end of file diff --git a/riscv/insns/mulhr.h b/riscv/insns/mulhr.h new file mode 100644 index 00000000..527d2a2f --- /dev/null +++ b/riscv/insns/mulhr.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +int64_t mres = sext(RS1,64) * sext(RS2,64); +WRITE_RD(((mres >> 31) + 1) >> 1); \ No newline at end of file diff --git a/riscv/insns/mulhrsu.h b/riscv/insns/mulhrsu.h new file mode 100644 index 00000000..bbd7619b --- /dev/null +++ b/riscv/insns/mulhrsu.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext(RS1,64) * reg_t((uint32_t)RS2); +WRITE_RD(((mres >> 31) + 1) >> 1); \ No newline at end of file diff --git a/riscv/insns/mulhru.h b/riscv/insns/mulhru.h new file mode 100644 index 00000000..51cf38cb --- /dev/null +++ b/riscv/insns/mulhru.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = reg_t((uint32_t)RS1) * reg_t((uint32_t)RS2); +WRITE_RD(((mres >> 31) + 1) >> 1); \ No newline at end of file diff --git a/riscv/insns/mulhsu_h0.h b/riscv/insns/mulhsu_h0.h new file mode 100644 index 00000000..2cdb292c --- /dev/null +++ b/riscv/insns/mulhsu_h0.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * (uint32_t)P_FIELD(RS2, 0, 16); +WRITE_RD(mres >> 32); \ No newline at end of file diff --git a/riscv/insns/mulhsu_h1.h b/riscv/insns/mulhsu_h1.h new file mode 100644 index 00000000..4cc9fc32 --- /dev/null +++ b/riscv/insns/mulhsu_h1.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +sreg_t mres = sext32(RS1) * (uint32_t)P_FIELD(RS2, 1, 16); +WRITE_RD(mres >> 32); \ No newline at end of file diff --git a/riscv/insns/mulq.h b/riscv/insns/mulq.h new file mode 100644 index 00000000..cb362db9 --- /dev/null +++ b/riscv/insns/mulq.h @@ -0,0 +1,7 @@ +require_extension('P'); +require_rv32; +if ((RS1 != (reg_t)INT32_MIN) || (RS2 != (reg_t)INT32_MIN)) { + WRITE_RD((RS1 * RS2) >> 31); + } else { + WRITE_RD(INT32_MAX); +} diff --git a/riscv/insns/mulqr.h b/riscv/insns/mulqr.h new file mode 100644 index 00000000..070b8fc4 --- /dev/null +++ b/riscv/insns/mulqr.h @@ -0,0 +1,7 @@ +require_extension('P'); +require_rv32; +if ((RS1 != (reg_t)INT32_MIN) || (RS2 != (reg_t)INT32_MIN)) { + WRITE_RD((((RS1 * RS2) >> 30) + 1) >> 1); + } else { + WRITE_RD(INT32_MAX); +} diff --git a/riscv/insns/mulsu_h00.h b/riscv/insns/mulsu_h00.h new file mode 100644 index 00000000..f02de759 --- /dev/null +++ b/riscv/insns/mulsu_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(sext(RS1, 16) * zext(RS2, 16)); \ No newline at end of file diff --git a/riscv/insns/mulsu_h11.h b/riscv/insns/mulsu_h11.h new file mode 100644 index 00000000..d4954037 --- /dev/null +++ b/riscv/insns/mulsu_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(sext(RS1 >> 16, 16) * zext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/mulu_h00.h b/riscv/insns/mulu_h00.h new file mode 100644 index 00000000..d92c605b --- /dev/null +++ b/riscv/insns/mulu_h00.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(zext(RS1, 16) * zext(RS2, 16)); \ No newline at end of file diff --git a/riscv/insns/mulu_h01.h b/riscv/insns/mulu_h01.h new file mode 100644 index 00000000..75a8302b --- /dev/null +++ b/riscv/insns/mulu_h01.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(zext(RS1, 16) * zext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/mulu_h11.h b/riscv/insns/mulu_h11.h new file mode 100644 index 00000000..28db7c86 --- /dev/null +++ b/riscv/insns/mulu_h11.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(zext(RS1 >> 16, 16) * zext(RS2 >> 16, 16)); \ No newline at end of file diff --git a/riscv/insns/mvm.h b/riscv/insns/mvm.h new file mode 100644 index 00000000..bf2ddad1 --- /dev/null +++ b/riscv/insns/mvm.h @@ -0,0 +1,2 @@ +require_extension('P'); +WRITE_RD((RS1 & RS2) | (RD & ~RS2)); \ No newline at end of file diff --git a/riscv/insns/mvmn.h b/riscv/insns/mvmn.h new file mode 100644 index 00000000..8c863d91 --- /dev/null +++ b/riscv/insns/mvmn.h @@ -0,0 +1,2 @@ +require_extension('P'); +WRITE_RD((RD & RS2) | (RS1 & ~RS2)); \ No newline at end of file diff --git a/riscv/insns/paadd_b.h b/riscv/insns/paadd_b.h new file mode 100644 index 00000000..9f5f043c --- /dev/null +++ b/riscv/insns/paadd_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + p_rd = (p_rs1 + p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/paadd_h.h b/riscv/insns/paadd_h.h new file mode 100644 index 00000000..bc01ea16 --- /dev/null +++ b/riscv/insns/paadd_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + p_rd = (p_rs1 + p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/paaddu_b.h b/riscv/insns/paaddu_b.h new file mode 100644 index 00000000..0a413d55 --- /dev/null +++ b/riscv/insns/paaddu_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(8,8,8, { + p_rd = (p_rs1 + p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/paaddu_h.h b/riscv/insns/paaddu_h.h new file mode 100644 index 00000000..dbef824b --- /dev/null +++ b/riscv/insns/paaddu_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + p_rd = (p_rs1 + p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/paas_hx.h b/riscv/insns/paas_hx.h new file mode 100644 index 00000000..5c393a85 --- /dev/null +++ b/riscv/insns/paas_hx.h @@ -0,0 +1,5 @@ +P_CROSS_LOOP(16, { + p_rd = (p_rs1 + p_rs2) >> 1; +}, { + p_rd = (p_rs1 - p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pabd_b.h b/riscv/insns/pabd_b.h new file mode 100644 index 00000000..978adbac --- /dev/null +++ b/riscv/insns/pabd_b.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(8, 8, 8, { + p_rd = (p_rs1 < p_rs2) ? (int8_t)((uint8_t)p_rs2 - (uint8_t)p_rs1) + : (int8_t)((uint8_t)p_rs1 - (uint8_t)p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pabd_h.h b/riscv/insns/pabd_h.h new file mode 100644 index 00000000..cd18fac7 --- /dev/null +++ b/riscv/insns/pabd_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(16, 16, 16, { + p_rd = (p_rs1 < p_rs2) ? (int16_t)((uint16_t)p_rs2 - (uint16_t)p_rs1) + : (int16_t)((uint16_t)p_rs1 - (uint16_t)p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pabdsumau_b.h b/riscv/insns/pabdsumau_b.h new file mode 100644 index 00000000..6ffc6888 --- /dev/null +++ b/riscv/insns/pabdsumau_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_ULOOP(64, 8, true, false, { + p_res += (p_rs1 > p_rs2 ? p_rs1 - p_rs2 : p_rs2 - p_rs1); +}) \ No newline at end of file diff --git a/riscv/insns/pabdsumu_b.h b/riscv/insns/pabdsumu_b.h new file mode 100644 index 00000000..b7effa47 --- /dev/null +++ b/riscv/insns/pabdsumu_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_ULOOP(64, 8, false, false, { + p_res += (p_rs1 > p_rs2 ? p_rs1 - p_rs2 : p_rs2 - p_rs1); +}) \ No newline at end of file diff --git a/riscv/insns/pabdu_b.h b/riscv/insns/pabdu_b.h new file mode 100644 index 00000000..d0092550 --- /dev/null +++ b/riscv/insns/pabdu_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(8, 8, 8, { + p_rd = (p_rs1 < p_rs2) ? p_rs2 - p_rs1 : p_rs1 - p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pabdu_h.h b/riscv/insns/pabdu_h.h new file mode 100644 index 00000000..83b1445d --- /dev/null +++ b/riscv/insns/pabdu_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(16, 16, 16, { + p_rd = (p_rs1 < p_rs2) ? p_rs2 - p_rs1 : p_rs1 - p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pack.h b/riscv/insns/pack.h index acc49877..25f5145b 100644 --- a/riscv/insns/pack.h +++ b/riscv/insns/pack.h @@ -1,6 +1,7 @@ // RV32Zbb contains zext.h but not general pack require(((xlen == 32) && (insn.rs2() == 0) && p->extension_enabled(EXT_ZBB)) - || p->extension_enabled(EXT_ZBKB)); + || p->extension_enabled(EXT_ZBKB) + || p->extension_enabled('P')); reg_t lo = zext_xlen(RS1 << (xlen/2)) >> (xlen/2); reg_t hi = zext_xlen(RS2 << (xlen/2)); -WRITE_RD(sext_xlen(lo | hi)); +WRITE_RD(sext_xlen(lo | hi)); \ No newline at end of file diff --git a/riscv/insns/padd_b.h b/riscv/insns/padd_b.h new file mode 100644 index 00000000..05f890ca --- /dev/null +++ b/riscv/insns/padd_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + p_rd = p_rs1 + p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/padd_bs.h b/riscv/insns/padd_bs.h new file mode 100644 index 00000000..9070fc9b --- /dev/null +++ b/riscv/insns/padd_bs.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(8, 8, { + p_rd = p_rs1 + P_FIELD(RS2, 0, 8); +}) \ No newline at end of file diff --git a/riscv/insns/padd_h.h b/riscv/insns/padd_h.h new file mode 100644 index 00000000..5ff1d324 --- /dev/null +++ b/riscv/insns/padd_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16, 16, 16, { + p_rd = p_rs1 + p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/padd_hs.h b/riscv/insns/padd_hs.h new file mode 100644 index 00000000..e68d0044 --- /dev/null +++ b/riscv/insns/padd_hs.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = p_rs1 + P_FIELD(RS2, 0, 16); +}) \ No newline at end of file diff --git a/riscv/insns/pas_hx.h b/riscv/insns/pas_hx.h new file mode 100644 index 00000000..fbe4a244 --- /dev/null +++ b/riscv/insns/pas_hx.h @@ -0,0 +1,5 @@ +P_CROSS_LOOP(16, { + p_rd = p_rs1 + p_rs2; +}, { + p_rd = p_rs1 - p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pasa_hx.h b/riscv/insns/pasa_hx.h new file mode 100644 index 00000000..eea09357 --- /dev/null +++ b/riscv/insns/pasa_hx.h @@ -0,0 +1,5 @@ +P_CROSS_LOOP(16, { + p_rd = (p_rs1 - p_rs2) >> 1; +}, { + p_rd = (p_rs1 + p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pasub_b.h b/riscv/insns/pasub_b.h new file mode 100644 index 00000000..48173164 --- /dev/null +++ b/riscv/insns/pasub_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + p_rd = (p_rs1 - p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pasub_h.h b/riscv/insns/pasub_h.h new file mode 100644 index 00000000..57c271ae --- /dev/null +++ b/riscv/insns/pasub_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + p_rd = (p_rs1 - p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pasubu_b.h b/riscv/insns/pasubu_b.h new file mode 100644 index 00000000..7543305a --- /dev/null +++ b/riscv/insns/pasubu_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(8,8,8, { + p_rd = (p_rs1 - p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pasubu_h.h b/riscv/insns/pasubu_h.h new file mode 100644 index 00000000..453fe57b --- /dev/null +++ b/riscv/insns/pasubu_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + p_rd = (p_rs1 - p_rs2) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pli_b.h b/riscv/insns/pli_b.h new file mode 100644 index 00000000..b04452e3 --- /dev/null +++ b/riscv/insns/pli_b.h @@ -0,0 +1,3 @@ +P_RD_LOOP(8, { + p_rd = insn.p_imm8(); +}) \ No newline at end of file diff --git a/riscv/insns/pli_db.h b/riscv/insns/pli_db.h new file mode 100644 index 00000000..e411fe0f --- /dev/null +++ b/riscv/insns/pli_db.h @@ -0,0 +1,4 @@ +require_rv32; +P_RD_DW_LOOP(8, { + p_rd = insn.p_imm8(); +}) \ No newline at end of file diff --git a/riscv/insns/pli_dh.h b/riscv/insns/pli_dh.h new file mode 100644 index 00000000..215b03df --- /dev/null +++ b/riscv/insns/pli_dh.h @@ -0,0 +1,4 @@ +require_rv32; +P_RD_DW_LOOP(16, { + p_rd = (insn.p_imm10csl() & 0x200) ? (0xfc00 | insn.p_imm10csl()) : insn.p_imm10csl(); +}) \ No newline at end of file diff --git a/riscv/insns/pli_h.h b/riscv/insns/pli_h.h new file mode 100644 index 00000000..4a891624 --- /dev/null +++ b/riscv/insns/pli_h.h @@ -0,0 +1,3 @@ +P_RD_LOOP(16, { + p_rd = (insn.p_imm10csl() & 0x200) ? (0xfc00 | insn.p_imm10csl()) : insn.p_imm10csl(); +}) \ No newline at end of file diff --git a/riscv/insns/plui_dh.h b/riscv/insns/plui_dh.h new file mode 100644 index 00000000..61f3d6b6 --- /dev/null +++ b/riscv/insns/plui_dh.h @@ -0,0 +1,4 @@ +require_rv32; +P_RD_DW_LOOP(16, { + p_rd = insn.p_imm10csr(); +}) \ No newline at end of file diff --git a/riscv/insns/plui_h.h b/riscv/insns/plui_h.h new file mode 100644 index 00000000..c11af3e3 --- /dev/null +++ b/riscv/insns/plui_h.h @@ -0,0 +1,3 @@ +P_RD_LOOP(16, { + p_rd = insn.p_imm10csr(); +}) \ No newline at end of file diff --git a/riscv/insns/pm2add_h.h b/riscv/insns/pm2add_h.h new file mode 100644 index 00000000..c0218159 --- /dev/null +++ b/riscv/insns/pm2add_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 16, false, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2add_hx.h b/riscv/insns/pm2add_hx.h new file mode 100644 index 00000000..a84dbcc7 --- /dev/null +++ b/riscv/insns/pm2add_hx.h @@ -0,0 +1,3 @@ +P_REDUCTION_CROSS_LOOP(32, 16, false, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2adda_h.h b/riscv/insns/pm2adda_h.h new file mode 100644 index 00000000..ed2e0eb5 --- /dev/null +++ b/riscv/insns/pm2adda_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 16, true, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2adda_hx.h b/riscv/insns/pm2adda_hx.h new file mode 100644 index 00000000..2a5d96cb --- /dev/null +++ b/riscv/insns/pm2adda_hx.h @@ -0,0 +1,3 @@ +P_REDUCTION_CROSS_LOOP(32, 16, true, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2addasu_h.h b/riscv/insns/pm2addasu_h.h new file mode 100644 index 00000000..8ddbcf21 --- /dev/null +++ b/riscv/insns/pm2addasu_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_SULOOP(32, 16, true, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2addau_h.h b/riscv/insns/pm2addau_h.h new file mode 100644 index 00000000..bc8dba63 --- /dev/null +++ b/riscv/insns/pm2addau_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_ULOOP(32, 16, true, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2addsu_h.h b/riscv/insns/pm2addsu_h.h new file mode 100644 index 00000000..dfbc5274 --- /dev/null +++ b/riscv/insns/pm2addsu_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_SULOOP(32, 16, false, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2addu_h.h b/riscv/insns/pm2addu_h.h new file mode 100644 index 00000000..97944410 --- /dev/null +++ b/riscv/insns/pm2addu_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_ULOOP(32, 16, false, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2sadd_h.h b/riscv/insns/pm2sadd_h.h new file mode 100644 index 00000000..01ba8c66 --- /dev/null +++ b/riscv/insns/pm2sadd_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 16, false, true, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2sadd_hx.h b/riscv/insns/pm2sadd_hx.h new file mode 100644 index 00000000..d7dca373 --- /dev/null +++ b/riscv/insns/pm2sadd_hx.h @@ -0,0 +1,3 @@ +P_REDUCTION_CROSS_LOOP(32, 16, false, true, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2sub_h.h b/riscv/insns/pm2sub_h.h new file mode 100644 index 00000000..48f6ce06 --- /dev/null +++ b/riscv/insns/pm2sub_h.h @@ -0,0 +1,6 @@ +P_REDUCTION_LOOP(32, 16, false, false, { + if (j & 1) + p_res -= p_rs1 * p_rs2; + else + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2sub_hx.h b/riscv/insns/pm2sub_hx.h new file mode 100644 index 00000000..1ff687c0 --- /dev/null +++ b/riscv/insns/pm2sub_hx.h @@ -0,0 +1,6 @@ +P_REDUCTION_CROSS_LOOP(32, 16, false, false, { + if (j & 1) + p_res -= p_rs1 * p_rs2; + else + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2suba_h.h b/riscv/insns/pm2suba_h.h new file mode 100644 index 00000000..d8c923e2 --- /dev/null +++ b/riscv/insns/pm2suba_h.h @@ -0,0 +1,6 @@ +P_REDUCTION_LOOP(32, 16, true, false, { + if (j & 1) + p_res -= p_rs1 * p_rs2; + else + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm2suba_hx.h b/riscv/insns/pm2suba_hx.h new file mode 100644 index 00000000..13971e26 --- /dev/null +++ b/riscv/insns/pm2suba_hx.h @@ -0,0 +1,6 @@ +P_REDUCTION_CROSS_LOOP(32, 16, true, false, { + if (j & 1) + p_res -= p_rs1 * p_rs2; + else + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm4add_b.h b/riscv/insns/pm4add_b.h new file mode 100644 index 00000000..ac1c49ce --- /dev/null +++ b/riscv/insns/pm4add_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 8, false, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm4adda_b.h b/riscv/insns/pm4adda_b.h new file mode 100644 index 00000000..d3e00eee --- /dev/null +++ b/riscv/insns/pm4adda_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 8, true, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm4addasu_b.h b/riscv/insns/pm4addasu_b.h new file mode 100644 index 00000000..cac07f07 --- /dev/null +++ b/riscv/insns/pm4addasu_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_SULOOP(32, 8, true, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm4addau_b.h b/riscv/insns/pm4addau_b.h new file mode 100644 index 00000000..37b29c33 --- /dev/null +++ b/riscv/insns/pm4addau_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_ULOOP(32, 8, true, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm4addsu_b.h b/riscv/insns/pm4addsu_b.h new file mode 100644 index 00000000..02fb9b74 --- /dev/null +++ b/riscv/insns/pm4addsu_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_SULOOP(32, 8, false, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pm4addu_b.h b/riscv/insns/pm4addu_b.h new file mode 100644 index 00000000..a6880e57 --- /dev/null +++ b/riscv/insns/pm4addu_b.h @@ -0,0 +1,3 @@ +P_REDUCTION_ULOOP(32, 8, false, false, { + p_res += p_rs1 * p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pmax_b.h b/riscv/insns/pmax_b.h new file mode 100644 index 00000000..9ab92eb3 --- /dev/null +++ b/riscv/insns/pmax_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + p_rd = (p_rs1 > p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pmax_h.h b/riscv/insns/pmax_h.h new file mode 100644 index 00000000..b1e9c0ad --- /dev/null +++ b/riscv/insns/pmax_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + p_rd = (p_rs1 > p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pmaxu_b.h b/riscv/insns/pmaxu_b.h new file mode 100644 index 00000000..82b60f67 --- /dev/null +++ b/riscv/insns/pmaxu_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(8,8,8, { + p_rd = (p_rs1 > p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pmaxu_h.h b/riscv/insns/pmaxu_h.h new file mode 100644 index 00000000..ac6f6028 --- /dev/null +++ b/riscv/insns/pmaxu_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + p_rd = (p_rs1 > p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pmhacc_h.h b/riscv/insns/pmhacc_h.h new file mode 100644 index 00000000..053c2858 --- /dev/null +++ b/riscv/insns/pmhacc_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + int32_t mres = sext32(p_rs1) * sext32(p_rs2); + p_rd += mres>>16; +}) \ No newline at end of file diff --git a/riscv/insns/pmhacc_h_b0.h b/riscv/insns/pmhacc_h_b0.h new file mode 100644 index 00000000..60a1d5c2 --- /dev/null +++ b/riscv/insns/pmhacc_h_b0.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_E_LOOP(16,16,8, { + int32_t mres = sext32(p_rs1) * sext32(p_rs2); + p_rd += mres>>16; +}) \ No newline at end of file diff --git a/riscv/insns/pmhacc_h_b1.h b/riscv/insns/pmhacc_h_b1.h new file mode 100644 index 00000000..c7aa4d7a --- /dev/null +++ b/riscv/insns/pmhacc_h_b1.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_O_LOOP(16,16,8, { + int32_t mres = sext32(p_rs1) * sext32(p_rs2); + p_rd += mres>>16; +}) \ No newline at end of file diff --git a/riscv/insns/pmhaccsu_h.h b/riscv/insns/pmhaccsu_h.h new file mode 100644 index 00000000..10b0211c --- /dev/null +++ b/riscv/insns/pmhaccsu_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_SULOOP(16,16,16, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + p_rd += mres>>16; +}) \ No newline at end of file diff --git a/riscv/insns/pmhaccsu_h_b0.h b/riscv/insns/pmhaccsu_h_b0.h new file mode 100644 index 00000000..3d14229b --- /dev/null +++ b/riscv/insns/pmhaccsu_h_b0.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_E_SULOOP(16,16,8, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + p_rd += mres>>16; +}) \ No newline at end of file diff --git a/riscv/insns/pmhaccsu_h_b1.h b/riscv/insns/pmhaccsu_h_b1.h new file mode 100644 index 00000000..6a5a478f --- /dev/null +++ b/riscv/insns/pmhaccsu_h_b1.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_O_SULOOP(16,16,8, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + p_rd += mres>>16; +}) \ No newline at end of file diff --git a/riscv/insns/pmhaccu_h.h b/riscv/insns/pmhaccu_h.h new file mode 100644 index 00000000..de1c6eb1 --- /dev/null +++ b/riscv/insns/pmhaccu_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + uint32_t mres = zext(p_rs1,32) * zext(p_rs2,32); + p_rd += mres>>16; +}) \ No newline at end of file diff --git a/riscv/insns/pmhracc_h.h b/riscv/insns/pmhracc_h.h new file mode 100644 index 00000000..1c79a71a --- /dev/null +++ b/riscv/insns/pmhracc_h.h @@ -0,0 +1,5 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + int32_t mres = sext(p_rs1,32) * sext(p_rs2,32); + int16_t round = ((mres >> 15) + 1) >> 1; + p_rd += round; +}) \ No newline at end of file diff --git a/riscv/insns/pmhraccsu_h.h b/riscv/insns/pmhraccsu_h.h new file mode 100644 index 00000000..c4302837 --- /dev/null +++ b/riscv/insns/pmhraccsu_h.h @@ -0,0 +1,5 @@ +P_RD_RS1_RS2_SULOOP(16,16,16, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + int16_t round = ((mres >> 15) + 1) >> 1; + p_rd += round; +}) \ No newline at end of file diff --git a/riscv/insns/pmhraccu_h.h b/riscv/insns/pmhraccu_h.h new file mode 100644 index 00000000..41efaad8 --- /dev/null +++ b/riscv/insns/pmhraccu_h.h @@ -0,0 +1,5 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + uint32_t mres = zext(p_rs1,32) * zext(p_rs2,32); + uint16_t round = ((mres >> 15) + 1) >> 1; + p_rd += round; +}) \ No newline at end of file diff --git a/riscv/insns/pmin_b.h b/riscv/insns/pmin_b.h new file mode 100644 index 00000000..402301c0 --- /dev/null +++ b/riscv/insns/pmin_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + p_rd = (p_rs1 < p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pmin_h.h b/riscv/insns/pmin_h.h new file mode 100644 index 00000000..2634f3cd --- /dev/null +++ b/riscv/insns/pmin_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + p_rd = (p_rs1 < p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pminu_b.h b/riscv/insns/pminu_b.h new file mode 100644 index 00000000..1156ff22 --- /dev/null +++ b/riscv/insns/pminu_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(8,8,8, { + p_rd = (p_rs1 < p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pminu_h.h b/riscv/insns/pminu_h.h new file mode 100644 index 00000000..734339c8 --- /dev/null +++ b/riscv/insns/pminu_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + p_rd = (p_rs1 < p_rs2) ? p_rs1 : p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pmq2add_h.h b/riscv/insns/pmq2add_h.h new file mode 100644 index 00000000..efa6e8ff --- /dev/null +++ b/riscv/insns/pmq2add_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 16, false, false, { + p_res += (p_rs1 * p_rs2) >> 15; +}) \ No newline at end of file diff --git a/riscv/insns/pmq2adda_h.h b/riscv/insns/pmq2adda_h.h new file mode 100644 index 00000000..70e4a5c2 --- /dev/null +++ b/riscv/insns/pmq2adda_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 16, true, false, { + p_res += (p_rs1 * p_rs2) >> 15; +}) \ No newline at end of file diff --git a/riscv/insns/pmqr2add_h.h b/riscv/insns/pmqr2add_h.h new file mode 100644 index 00000000..ee8ac64a --- /dev/null +++ b/riscv/insns/pmqr2add_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 16, false, false, { + p_res += ((p_rs1 * p_rs2) + 0x4000) >> 15; +}) \ No newline at end of file diff --git a/riscv/insns/pmqr2adda_h.h b/riscv/insns/pmqr2adda_h.h new file mode 100644 index 00000000..7352e174 --- /dev/null +++ b/riscv/insns/pmqr2adda_h.h @@ -0,0 +1,3 @@ +P_REDUCTION_LOOP(32, 16, true, false, { + p_res += ((p_rs1 * p_rs2) + 0x4000) >> 15; +}) \ No newline at end of file diff --git a/riscv/insns/pmseq_b.h b/riscv/insns/pmseq_b.h new file mode 100644 index 00000000..bd66522d --- /dev/null +++ b/riscv/insns/pmseq_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + p_rd = (p_rs1 == p_rs2) ? -1 : 0; +}) \ No newline at end of file diff --git a/riscv/insns/pmseq_h.h b/riscv/insns/pmseq_h.h new file mode 100644 index 00000000..3a9b42f8 --- /dev/null +++ b/riscv/insns/pmseq_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + p_rd = (p_rs1 == p_rs2) ? -1 : 0; +}) \ No newline at end of file diff --git a/riscv/insns/pmslt_b.h b/riscv/insns/pmslt_b.h new file mode 100644 index 00000000..d0c1d1a6 --- /dev/null +++ b/riscv/insns/pmslt_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + p_rd = (p_rs1 < p_rs2) ? -1 : 0; +}) \ No newline at end of file diff --git a/riscv/insns/pmslt_h.h b/riscv/insns/pmslt_h.h new file mode 100644 index 00000000..73f71531 --- /dev/null +++ b/riscv/insns/pmslt_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + p_rd = (p_rs1 < p_rs2) ? -1 : 0; +}) \ No newline at end of file diff --git a/riscv/insns/pmsltu_b.h b/riscv/insns/pmsltu_b.h new file mode 100644 index 00000000..8e39925b --- /dev/null +++ b/riscv/insns/pmsltu_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(8,8,8, { + p_rd = (p_rs1 < p_rs2) ? -1 : 0; +}) \ No newline at end of file diff --git a/riscv/insns/pmsltu_h.h b/riscv/insns/pmsltu_h.h new file mode 100644 index 00000000..90d21792 --- /dev/null +++ b/riscv/insns/pmsltu_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + p_rd = (p_rs1 < p_rs2) ? -1 : 0; +}) \ No newline at end of file diff --git a/riscv/insns/pmul_h_b00.h b/riscv/insns/pmul_h_b00.h new file mode 100644 index 00000000..41af6b34 --- /dev/null +++ b/riscv/insns/pmul_h_b00.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_EE_LOOP(16, 8, 8, { + p_rd = sext32(p_rs1) * sext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pmul_h_b01.h b/riscv/insns/pmul_h_b01.h new file mode 100644 index 00000000..1cb85a1b --- /dev/null +++ b/riscv/insns/pmul_h_b01.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_EO_LOOP(16, 8, 8, { + p_rd = sext32(p_rs1) * sext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pmul_h_b11.h b/riscv/insns/pmul_h_b11.h new file mode 100644 index 00000000..8a1765d2 --- /dev/null +++ b/riscv/insns/pmul_h_b11.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_OO_LOOP(16, 8, 8, { + p_rd = sext32(p_rs1) * sext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pmulh_h.h b/riscv/insns/pmulh_h.h new file mode 100644 index 00000000..0e199f7b --- /dev/null +++ b/riscv/insns/pmulh_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + int32_t mres = sext(p_rs1,32) * sext(p_rs2,32); + p_rd = mres >> 16; +}) \ No newline at end of file diff --git a/riscv/insns/pmulh_h_b0.h b/riscv/insns/pmulh_h_b0.h new file mode 100644 index 00000000..5c69a9c6 --- /dev/null +++ b/riscv/insns/pmulh_h_b0.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_E_LOOP(16,16,8, { + int32_t mres = sext(p_rs1,32) * sext(p_rs2,32); + p_rd = mres >> 16; +}) \ No newline at end of file diff --git a/riscv/insns/pmulh_h_b1.h b/riscv/insns/pmulh_h_b1.h new file mode 100644 index 00000000..1cd5d680 --- /dev/null +++ b/riscv/insns/pmulh_h_b1.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_O_LOOP(16,16,8, { + int32_t mres = sext(p_rs1,32) * sext(p_rs2,32); + p_rd = mres >> 16; +}) \ No newline at end of file diff --git a/riscv/insns/pmulhr_h.h b/riscv/insns/pmulhr_h.h new file mode 100644 index 00000000..fbccf0fe --- /dev/null +++ b/riscv/insns/pmulhr_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + int32_t mres = sext(p_rs1,32) * sext(p_rs2,32); + p_rd = ((mres >> 15) + 1) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pmulhrsu_h.h b/riscv/insns/pmulhrsu_h.h new file mode 100644 index 00000000..ab681ef0 --- /dev/null +++ b/riscv/insns/pmulhrsu_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_SULOOP(16,16,16, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + p_rd = ((mres >> 15) + 1) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pmulhru_h.h b/riscv/insns/pmulhru_h.h new file mode 100644 index 00000000..82f1bfe5 --- /dev/null +++ b/riscv/insns/pmulhru_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + uint32_t mres = zext(p_rs1,32) * zext(p_rs2,32); + p_rd = ((mres >> 15) + 1) >> 1; +}) \ No newline at end of file diff --git a/riscv/insns/pmulhsu_h.h b/riscv/insns/pmulhsu_h.h new file mode 100644 index 00000000..d4f07462 --- /dev/null +++ b/riscv/insns/pmulhsu_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_SULOOP(16,16,16, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + p_rd = mres >> 16; +}) \ No newline at end of file diff --git a/riscv/insns/pmulhsu_h_b0.h b/riscv/insns/pmulhsu_h_b0.h new file mode 100644 index 00000000..3cfdd4b4 --- /dev/null +++ b/riscv/insns/pmulhsu_h_b0.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_E_SULOOP(16,16,8, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + p_rd = mres >> 16; +}) \ No newline at end of file diff --git a/riscv/insns/pmulhsu_h_b1.h b/riscv/insns/pmulhsu_h_b1.h new file mode 100644 index 00000000..4e6b5bf3 --- /dev/null +++ b/riscv/insns/pmulhsu_h_b1.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_O_SULOOP(16,16,8, { + int32_t mres = sext(p_rs1,32) * zext(p_rs2,32); + p_rd = mres >> 16; +}) \ No newline at end of file diff --git a/riscv/insns/pmulhu_h.h b/riscv/insns/pmulhu_h.h new file mode 100644 index 00000000..32a1b280 --- /dev/null +++ b/riscv/insns/pmulhu_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + uint32_t mres = zext(p_rs1,32) * zext(p_rs2,32); + p_rd = mres >> 16; +}) \ No newline at end of file diff --git a/riscv/insns/pmulq_h.h b/riscv/insns/pmulq_h.h new file mode 100644 index 00000000..ad5f5f9e --- /dev/null +++ b/riscv/insns/pmulq_h.h @@ -0,0 +1,7 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + if ((p_rs1 != INT16_MIN) | (p_rs2 != INT16_MIN)) { + p_rd = (p_rs1 * p_rs2) >> 15; + } else { + p_rd = INT16_MAX; + } +}) \ No newline at end of file diff --git a/riscv/insns/pmulqr_h.h b/riscv/insns/pmulqr_h.h new file mode 100644 index 00000000..8dc8b472 --- /dev/null +++ b/riscv/insns/pmulqr_h.h @@ -0,0 +1,7 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + if ((p_rs1 != INT16_MIN) | (p_rs2 != INT16_MIN)) { + p_rd = (((p_rs1 * p_rs2) >> 14) + 1) >> 1; + } else { + p_rd = INT16_MAX; + } +}) \ No newline at end of file diff --git a/riscv/insns/pmulsu_h_b00.h b/riscv/insns/pmulsu_h_b00.h new file mode 100644 index 00000000..4682257e --- /dev/null +++ b/riscv/insns/pmulsu_h_b00.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_EE_SULOOP(16, 8, 8, { + p_rd = sext32(p_rs1) * zext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pmulsu_h_b11.h b/riscv/insns/pmulsu_h_b11.h new file mode 100644 index 00000000..57436181 --- /dev/null +++ b/riscv/insns/pmulsu_h_b11.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_OO_SULOOP(16, 8, 8, { + p_rd = sext32(p_rs1) * zext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pmulu_h_b00.h b/riscv/insns/pmulu_h_b00.h new file mode 100644 index 00000000..8ff863f0 --- /dev/null +++ b/riscv/insns/pmulu_h_b00.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_EE_ULOOP(16, 8, 8, { + p_rd = zext32(p_rs1) * zext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pmulu_h_b01.h b/riscv/insns/pmulu_h_b01.h new file mode 100644 index 00000000..24d782cf --- /dev/null +++ b/riscv/insns/pmulu_h_b01.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_EO_ULOOP(16, 8, 8, { + p_rd = zext32(p_rs1) * zext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pmulu_h_b11.h b/riscv/insns/pmulu_h_b11.h new file mode 100644 index 00000000..31316a1d --- /dev/null +++ b/riscv/insns/pmulu_h_b11.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_OO_ULOOP(16, 8, 8, { + p_rd = zext32(p_rs1) * zext32(p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/ppaire_b.h b/riscv/insns/ppaire_b.h new file mode 100644 index 00000000..a1b9665a --- /dev/null +++ b/riscv/insns/ppaire_b.h @@ -0,0 +1 @@ +P_PACK(8, 0, 0); \ No newline at end of file diff --git a/riscv/insns/ppaireo_b.h b/riscv/insns/ppaireo_b.h new file mode 100644 index 00000000..1e02dc4c --- /dev/null +++ b/riscv/insns/ppaireo_b.h @@ -0,0 +1 @@ +P_PACK(8, 0, 1); \ No newline at end of file diff --git a/riscv/insns/ppaireo_h.h b/riscv/insns/ppaireo_h.h new file mode 100644 index 00000000..c5f043f5 --- /dev/null +++ b/riscv/insns/ppaireo_h.h @@ -0,0 +1 @@ +P_PACK(16, 0, 1); \ No newline at end of file diff --git a/riscv/insns/ppairo_b.h b/riscv/insns/ppairo_b.h new file mode 100644 index 00000000..c691850b --- /dev/null +++ b/riscv/insns/ppairo_b.h @@ -0,0 +1 @@ +P_PACK(8, 1, 1); \ No newline at end of file diff --git a/riscv/insns/ppairo_h.h b/riscv/insns/ppairo_h.h new file mode 100644 index 00000000..600ee873 --- /dev/null +++ b/riscv/insns/ppairo_h.h @@ -0,0 +1 @@ +P_PACK(16, 1, 1); \ No newline at end of file diff --git a/riscv/insns/ppairoe_b.h b/riscv/insns/ppairoe_b.h new file mode 100644 index 00000000..37df7381 --- /dev/null +++ b/riscv/insns/ppairoe_b.h @@ -0,0 +1 @@ +P_PACK(8, 1, 0); \ No newline at end of file diff --git a/riscv/insns/ppairoe_h.h b/riscv/insns/ppairoe_h.h new file mode 100644 index 00000000..ecca5386 --- /dev/null +++ b/riscv/insns/ppairoe_h.h @@ -0,0 +1 @@ +P_PACK(16, 1, 0); \ No newline at end of file diff --git a/riscv/insns/predsum_bs.h b/riscv/insns/predsum_bs.h new file mode 100644 index 00000000..9f110b6d --- /dev/null +++ b/riscv/insns/predsum_bs.h @@ -0,0 +1,5 @@ +reg_t rd_tmp = RS2; \ +P_RS1_LOOP_BASE(8) + P_RS1_PARAMS(8) + rd_tmp += sext_xlen(p_rs1); +P_RD_LOOP_END() \ No newline at end of file diff --git a/riscv/insns/predsum_hs.h b/riscv/insns/predsum_hs.h new file mode 100644 index 00000000..dd2c8242 --- /dev/null +++ b/riscv/insns/predsum_hs.h @@ -0,0 +1,5 @@ +reg_t rd_tmp = RS2; \ +P_RS1_LOOP_BASE(16) + P_RS1_PARAMS(16) + rd_tmp += sext_xlen(p_rs1); +P_RD_LOOP_END() \ No newline at end of file diff --git a/riscv/insns/predsumu_bs.h b/riscv/insns/predsumu_bs.h new file mode 100644 index 00000000..e5c2f53a --- /dev/null +++ b/riscv/insns/predsumu_bs.h @@ -0,0 +1,5 @@ +reg_t rd_tmp = RS2; \ +P_RS1_LOOP_BASE(8) + P_RS1_UPARAMS(8) + rd_tmp += zext_xlen(p_rs1); +P_RD_LOOP_END() \ No newline at end of file diff --git a/riscv/insns/predsumu_hs.h b/riscv/insns/predsumu_hs.h new file mode 100644 index 00000000..bf2dc457 --- /dev/null +++ b/riscv/insns/predsumu_hs.h @@ -0,0 +1,5 @@ +reg_t rd_tmp = RS2; \ +P_RS1_LOOP_BASE(16) + P_RS1_UPARAMS(16) + rd_tmp += zext_xlen(p_rs1); +P_RD_LOOP_END() \ No newline at end of file diff --git a/riscv/insns/psa_hx.h b/riscv/insns/psa_hx.h new file mode 100644 index 00000000..864671e4 --- /dev/null +++ b/riscv/insns/psa_hx.h @@ -0,0 +1,5 @@ +P_CROSS_LOOP(16, { + p_rd = p_rs1 - p_rs2; +}, { + p_rd = p_rs1 + p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/psabs_b.h b/riscv/insns/psabs_b.h new file mode 100644 index 00000000..8ca5085b --- /dev/null +++ b/riscv/insns/psabs_b.h @@ -0,0 +1,5 @@ +P_RD_RS1_LOOP(8, 8, { + sreg_t abs_val = p_rs1 > 0 ? p_rs1 : -sext32(p_rs1); + p_rd = P_SAT(8, abs_val); + if (p_rd != abs_val) P.VU.vxsat->write(1); +}) \ No newline at end of file diff --git a/riscv/insns/psabs_h.h b/riscv/insns/psabs_h.h new file mode 100644 index 00000000..54564afe --- /dev/null +++ b/riscv/insns/psabs_h.h @@ -0,0 +1,5 @@ +P_RD_RS1_LOOP(16, 16, { + sreg_t abs_val = p_rs1 > 0 ? p_rs1 : -sext32(p_rs1); + p_rd = P_SAT(16, abs_val); + if (p_rd != abs_val) P.VU.vxsat->write(1); +}) \ No newline at end of file diff --git a/riscv/insns/psadd_b.h b/riscv/insns/psadd_b.h new file mode 100644 index 00000000..a024d4d0 --- /dev/null +++ b/riscv/insns/psadd_b.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + bool sat = false; + p_rd = (sat_add(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/psadd_h.h b/riscv/insns/psadd_h.h new file mode 100644 index 00000000..47af97ad --- /dev/null +++ b/riscv/insns/psadd_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + bool sat = false; + p_rd = (sat_add(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/psaddu_b.h b/riscv/insns/psaddu_b.h new file mode 100644 index 00000000..491fc2d3 --- /dev/null +++ b/riscv/insns/psaddu_b.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_ULOOP(8,8,8, { + bool sat = false; + p_rd = (sat_addu(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/psaddu_h.h b/riscv/insns/psaddu_h.h new file mode 100644 index 00000000..f28d0f32 --- /dev/null +++ b/riscv/insns/psaddu_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + bool sat = false; + p_rd = (sat_addu(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/psas_hx.h b/riscv/insns/psas_hx.h new file mode 100644 index 00000000..3be87430 --- /dev/null +++ b/riscv/insns/psas_hx.h @@ -0,0 +1,7 @@ +P_CROSS_ULOOP(16, { + bool sat = false; + p_rd = (sat_add(p_rs1, p_rs2, sat)); +}, { + bool sat = false; + p_rd = (sat_sub(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/psati_h.h b/riscv/insns/psati_h.h new file mode 100644 index 00000000..b63f2233 --- /dev/null +++ b/riscv/insns/psati_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = P_SAT(insn.shamth() + 1, p_rs1); +}) \ No newline at end of file diff --git a/riscv/insns/psext_h_b.h b/riscv/insns/psext_h_b.h new file mode 100644 index 00000000..1bc3dd0b --- /dev/null +++ b/riscv/insns/psext_h_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = (int16_t)(int8_t)p_rs1; +}) \ No newline at end of file diff --git a/riscv/insns/psh1add_h.h b/riscv/insns/psh1add_h.h new file mode 100644 index 00000000..db41f6e4 --- /dev/null +++ b/riscv/insns/psh1add_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16, 16, 16, { + p_rd = (p_rs1 << 1) + p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/psll_bs.h b/riscv/insns/psll_bs.h new file mode 100644 index 00000000..de0fa0df --- /dev/null +++ b/riscv/insns/psll_bs.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(8, 8, { + p_rd = p_rs1 << (RS2 & (8 - 1)); +}) \ No newline at end of file diff --git a/riscv/insns/psll_hs.h b/riscv/insns/psll_hs.h new file mode 100644 index 00000000..5470506f --- /dev/null +++ b/riscv/insns/psll_hs.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = p_rs1 << (RS2 & (16 - 1)); +}) \ No newline at end of file diff --git a/riscv/insns/pslli_b.h b/riscv/insns/pslli_b.h new file mode 100644 index 00000000..79f8ebc5 --- /dev/null +++ b/riscv/insns/pslli_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(8, 8, { + p_rd = p_rs1 << insn.shamtb(); +}) \ No newline at end of file diff --git a/riscv/insns/pslli_h.h b/riscv/insns/pslli_h.h new file mode 100644 index 00000000..65127f7e --- /dev/null +++ b/riscv/insns/pslli_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = p_rs1 << insn.shamth(); +}) \ No newline at end of file diff --git a/riscv/insns/psra_bs.h b/riscv/insns/psra_bs.h new file mode 100644 index 00000000..bdc00144 --- /dev/null +++ b/riscv/insns/psra_bs.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(8, 8, { + p_rd = p_rs1 >> (RS2 & (8 - 1)); +}) \ No newline at end of file diff --git a/riscv/insns/psra_hs.h b/riscv/insns/psra_hs.h new file mode 100644 index 00000000..3a719ac2 --- /dev/null +++ b/riscv/insns/psra_hs.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = p_rs1 >> (RS2 & (16 - 1)); +}) \ No newline at end of file diff --git a/riscv/insns/psrai_b.h b/riscv/insns/psrai_b.h new file mode 100644 index 00000000..dd109927 --- /dev/null +++ b/riscv/insns/psrai_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(8, 8, { + p_rd = p_rs1 >> insn.shamtb(); +}) \ No newline at end of file diff --git a/riscv/insns/psrai_h.h b/riscv/insns/psrai_h.h new file mode 100644 index 00000000..89a1a686 --- /dev/null +++ b/riscv/insns/psrai_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = p_rs1 >> insn.shamth(); +}) \ No newline at end of file diff --git a/riscv/insns/psrari_h.h b/riscv/insns/psrari_h.h new file mode 100644 index 00000000..ace18a9a --- /dev/null +++ b/riscv/insns/psrari_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = insn.shamth() ? ((p_rs1 >> insn.shamth()) + ((p_rs1 >> (insn.shamth() - 1)) & 1)) : p_rs1; +}) \ No newline at end of file diff --git a/riscv/insns/psrl_bs.h b/riscv/insns/psrl_bs.h new file mode 100644 index 00000000..5e3c5953 --- /dev/null +++ b/riscv/insns/psrl_bs.h @@ -0,0 +1,3 @@ +P_RD_RS1_ULOOP(8, 8, { + p_rd = p_rs1 >> (RS2 & (8 - 1)); +}) \ No newline at end of file diff --git a/riscv/insns/psrl_hs.h b/riscv/insns/psrl_hs.h new file mode 100644 index 00000000..d3389c05 --- /dev/null +++ b/riscv/insns/psrl_hs.h @@ -0,0 +1,3 @@ +P_RD_RS1_ULOOP(16, 16, { + p_rd = p_rs1 >> (RS2 & (16 - 1)); +}) \ No newline at end of file diff --git a/riscv/insns/psrli_b.h b/riscv/insns/psrli_b.h new file mode 100644 index 00000000..68b79e06 --- /dev/null +++ b/riscv/insns/psrli_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_ULOOP(8, 8, { + p_rd = p_rs1 >> insn.shamtb(); +}) \ No newline at end of file diff --git a/riscv/insns/psrli_h.h b/riscv/insns/psrli_h.h new file mode 100644 index 00000000..b7b2a763 --- /dev/null +++ b/riscv/insns/psrli_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_ULOOP(16, 16, { + p_rd = p_rs1 >> insn.shamth(); +}) \ No newline at end of file diff --git a/riscv/insns/pssa_hx.h b/riscv/insns/pssa_hx.h new file mode 100644 index 00000000..0a8b7c7b --- /dev/null +++ b/riscv/insns/pssa_hx.h @@ -0,0 +1,7 @@ +P_CROSS_ULOOP(16, { + bool sat = false; + p_rd = (sat_sub(p_rs1, p_rs2, sat)); +}, { + bool sat = false; + p_rd = (sat_add(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/pssh1sadd_h.h b/riscv/insns/pssh1sadd_h.h new file mode 100644 index 00000000..dead4c71 --- /dev/null +++ b/riscv/insns/pssh1sadd_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16, 16, 16, { + p_rd = P_SAT(16, P_SAT(16, p_rs1 << 1) + p_rs2); +}) \ No newline at end of file diff --git a/riscv/insns/pssha_hs.h b/riscv/insns/pssha_hs.h new file mode 100644 index 00000000..34d9852e --- /dev/null +++ b/riscv/insns/pssha_hs.h @@ -0,0 +1,11 @@ +sreg_t sshamt = P_FIELD(RS2, 0, 8); +P_RD_RS1_LOOP(16, 16, { + if (p_rs1 == 0) + p_rd = 0; + else if (sshamt >= 16) + p_rd = (p_rs1 & 0x8000) ? 0x8000 : 0x7fff; + else if (sshamt <= -16) + p_rd = (p_rs1 & 0x8000) ? 0xffff : 0; + else + p_rd = sshamt >= 0 ? P_SAT(16, sext32(p_rs1) << sshamt) : (p_rs1 >> -sshamt); +}) \ No newline at end of file diff --git a/riscv/insns/psshar_hs.h b/riscv/insns/psshar_hs.h new file mode 100644 index 00000000..73d220aa --- /dev/null +++ b/riscv/insns/psshar_hs.h @@ -0,0 +1,11 @@ +sreg_t sshamt = P_FIELD(RS2, 0, 8); +P_RD_RS1_LOOP(16, 16, { + if (p_rs1 == 0) + p_rd = 0; + else if (sshamt >= 16) + p_rd = (p_rs1 & 0x8000) ? 0x8000 : 0x7fff; + else if (sshamt <= -16) + p_rd = 0; + else + p_rd = sshamt >= 0 ? P_SAT(16, sext32(p_rs1) << sshamt) : ((p_rs1 >> -sshamt) + ((p_rs1 >> (-sshamt - 1)) & 1)); +}) \ No newline at end of file diff --git a/riscv/insns/psslai_h.h b/riscv/insns/psslai_h.h new file mode 100644 index 00000000..b5ae37e1 --- /dev/null +++ b/riscv/insns/psslai_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = P_SAT(16, sext32(p_rs1) << insn.shamth()); +}) \ No newline at end of file diff --git a/riscv/insns/pssub_b.h b/riscv/insns/pssub_b.h new file mode 100644 index 00000000..91a89aa1 --- /dev/null +++ b/riscv/insns/pssub_b.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(8,8,8, { + bool sat = false; + p_rd = (sat_sub(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/pssub_h.h b/riscv/insns/pssub_h.h new file mode 100644 index 00000000..db88d680 --- /dev/null +++ b/riscv/insns/pssub_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_LOOP(16,16,16, { + bool sat = false; + p_rd = (sat_sub(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/pssubu_b.h b/riscv/insns/pssubu_b.h new file mode 100644 index 00000000..3fd44bee --- /dev/null +++ b/riscv/insns/pssubu_b.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_ULOOP(8,8,8, { + bool sat = false; + p_rd = (sat_subu(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/pssubu_h.h b/riscv/insns/pssubu_h.h new file mode 100644 index 00000000..de3ff72a --- /dev/null +++ b/riscv/insns/pssubu_h.h @@ -0,0 +1,4 @@ +P_RD_RS1_RS2_ULOOP(16,16,16, { + bool sat = false; + p_rd = (sat_subu(p_rs1, p_rs2, sat)); +}) \ No newline at end of file diff --git a/riscv/insns/psub_b.h b/riscv/insns/psub_b.h new file mode 100644 index 00000000..1dce95cf --- /dev/null +++ b/riscv/insns/psub_b.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(8, 8, 8, { + p_rd = p_rs1 - p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/psub_h.h b/riscv/insns/psub_h.h new file mode 100644 index 00000000..a2d7c3b1 --- /dev/null +++ b/riscv/insns/psub_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_RS2_LOOP(16, 16, 16, { + p_rd = p_rs1 - p_rs2; +}) \ No newline at end of file diff --git a/riscv/insns/pusati_h.h b/riscv/insns/pusati_h.h new file mode 100644 index 00000000..d5857448 --- /dev/null +++ b/riscv/insns/pusati_h.h @@ -0,0 +1,3 @@ +P_RD_RS1_LOOP(16, 16, { + p_rd = P_USAT(insn.shamth() + 1, p_rs1); +}) \ No newline at end of file diff --git a/riscv/insns/sadd.h b/riscv/insns/sadd.h new file mode 100644 index 00000000..94cc264c --- /dev/null +++ b/riscv/insns/sadd.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(P_SAT(xlen, sext_xlen((RS1 << 1) + RS2))); \ No newline at end of file diff --git a/riscv/insns/saddu.h b/riscv/insns/saddu.h new file mode 100644 index 00000000..dec16b84 --- /dev/null +++ b/riscv/insns/saddu.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +bool sat = false; +WRITE_RD(sat_addu(RS1, RS2, sat)); \ No newline at end of file diff --git a/riscv/insns/sati_rv32.h b/riscv/insns/sati_rv32.h new file mode 100644 index 00000000..a950d95c --- /dev/null +++ b/riscv/insns/sati_rv32.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(P_SAT(insn.shamtw() + 1, (sreg_t)RS1)); \ No newline at end of file diff --git a/riscv/insns/slx.h b/riscv/insns/slx.h new file mode 100644 index 00000000..a6eb3e9c --- /dev/null +++ b/riscv/insns/slx.h @@ -0,0 +1,16 @@ +require_extension('P'); +if(xlen == 64){ + int shamt = RS2 & 63; + if(shamt == 0){ + WRITE_RD((uint64_t)RD); + }else{ + WRITE_RD(((uint64_t)RS1 >> (64 - shamt)) | ((uint64_t)RD << shamt)); + } +}else{ + int shamt = (uint32_t)RS2 & 31; + if (shamt == 0) { + WRITE_RD(sext_xlen((uint32_t)RD)); + } else { + WRITE_RD(sext_xlen(((uint32_t)RS1 >> (32 - shamt)) | ((uint32_t)RD << shamt))); + } +} diff --git a/riscv/insns/srari_rv32.h b/riscv/insns/srari_rv32.h new file mode 100644 index 00000000..25d4bee4 --- /dev/null +++ b/riscv/insns/srari_rv32.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(insn.shamtw() ? ((sext_xlen(RS1) >> insn.shamtw()) + ((sext_xlen(RS1) >> (insn.shamtw() - 1)) & 1)) : RS1); \ No newline at end of file diff --git a/riscv/insns/srx.h b/riscv/insns/srx.h new file mode 100644 index 00000000..19460c74 --- /dev/null +++ b/riscv/insns/srx.h @@ -0,0 +1,16 @@ +require_extension('P'); +if(xlen == 64){ + int shamt = RS2 & 63; + if(shamt == 0){ + WRITE_RD((uint64_t)RD); + }else{ + WRITE_RD(((uint64_t)RS1 << (64 - shamt)) | ((uint64_t)RD >> shamt)); + } +}else{ + int shamt = (uint32_t)RS2 & 31; + if (shamt == 0) { + WRITE_RD(sext_xlen((uint32_t)RD)); + } else { + WRITE_RD(sext_xlen(((uint32_t)RS1 << (32 - shamt)) | ((uint32_t)RD >> shamt))); + } +} diff --git a/riscv/insns/ssh1sadd.h b/riscv/insns/ssh1sadd.h new file mode 100644 index 00000000..94cc264c --- /dev/null +++ b/riscv/insns/ssh1sadd.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(P_SAT(xlen, sext_xlen((RS1 << 1) + RS2))); \ No newline at end of file diff --git a/riscv/insns/ssha.h b/riscv/insns/ssha.h new file mode 100644 index 00000000..ed1247f6 --- /dev/null +++ b/riscv/insns/ssha.h @@ -0,0 +1,11 @@ +require_extension('P'); +require_rv32; +sreg_t sshamt = P_FIELD(RS2, 0, 8); +if (RS1 == 0) + WRITE_RD(0); +else if (sshamt >= 32) + WRITE_RD((RS1 & 0x80000000) ? 0x80000000 : 0x7fffffff); +else if (sshamt <= -32) + WRITE_RD((RS1 & 0x80000000) ? 0xffffffff : 0); +else + WRITE_RD(sshamt >= 0 ? P_SAT(32, static_cast (RS1) << sshamt) : (RS1 >> -sshamt)); \ No newline at end of file diff --git a/riscv/insns/sshar.h b/riscv/insns/sshar.h new file mode 100644 index 00000000..d602edb7 --- /dev/null +++ b/riscv/insns/sshar.h @@ -0,0 +1,11 @@ +require_extension('P'); +require_rv32; +sreg_t sshamt = P_FIELD(RS2, 0, 8); +if (RS1 == 0) + WRITE_RD(0); +else if (sshamt >= 32) + WRITE_RD((RS1 & 0x80000000) ? 0x80000000 : 0x7fffffff); +else if (sshamt <= -32) + WRITE_RD(0); +else + WRITE_RD(sshamt >= 0 ? P_SAT(32, static_cast (RS1) << sshamt) : ((RS1 >> -sshamt) + ((RS1 >> (-sshamt - 1)) & 1))); \ No newline at end of file diff --git a/riscv/insns/sslai.h b/riscv/insns/sslai.h new file mode 100644 index 00000000..5db6ab1a --- /dev/null +++ b/riscv/insns/sslai.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(P_SAT(32, static_cast (RS1) << insn.shamtw())); \ No newline at end of file diff --git a/riscv/insns/ssub.h b/riscv/insns/ssub.h new file mode 100644 index 00000000..f3db9b4b --- /dev/null +++ b/riscv/insns/ssub.h @@ -0,0 +1,5 @@ +require_extension('P'); +require_rv32; +bool sat = false; +int32_t p_rd = sat_sub(RS1, RS2, sat); +WRITE_RD(p_rd); \ No newline at end of file diff --git a/riscv/insns/ssubu.h b/riscv/insns/ssubu.h new file mode 100644 index 00000000..c4aac5d3 --- /dev/null +++ b/riscv/insns/ssubu.h @@ -0,0 +1,4 @@ +require_extension('P'); +require_rv32; +bool sat = false; +WRITE_RD(sat_subu(RS1, RS2, sat)); \ No newline at end of file diff --git a/riscv/insns/usati_rv32.h b/riscv/insns/usati_rv32.h new file mode 100644 index 00000000..84ba83a1 --- /dev/null +++ b/riscv/insns/usati_rv32.h @@ -0,0 +1,3 @@ +require_extension('P'); +require_rv32; +WRITE_RD(P_USAT(insn.shamtw() + 1, (sreg_t)RS1)); \ No newline at end of file diff --git a/riscv/p_ext_macros.h b/riscv/p_ext_macros.h new file mode 100644 index 00000000..40bf1f6f --- /dev/null +++ b/riscv/p_ext_macros.h @@ -0,0 +1,512 @@ +#ifndef _RISCV_P_EXT_MACROS_H_ +#define _RISCV_P_EXT_MACROS_H_ + +// rd temp +#define WRITE_P_RD() \ + rd_tmp = set_field(rd_tmp, make_mask64((i * sizeof(p_rd) * 8), sizeof(p_rd) * 8), p_rd); + +// Field +#define P_FIELD(R, INDEX, SIZE) \ + (type_sew_t::type)get_field(R, make_mask64(((INDEX) * SIZE), SIZE)) + +#define P_UFIELD(R, INDEX, SIZE) \ + (type_usew_t::type)get_field(R, make_mask64(((INDEX) * SIZE), SIZE)) + +// Params +#define P_RD_PARAMS(BIT) \ + auto p_rd = P_FIELD(rd_tmp, i, BIT); + +#define P_RD_UPARAMS(BIT) \ + auto p_rd = P_UFIELD(rd_tmp, i, BIT); + +#define P_RS1_PARAMS(BIT) \ + auto p_rs1 = P_FIELD(rs1, i, BIT); + +#define P_RS1_UPARAMS(BIT) \ + auto p_rs1 = P_UFIELD(rs1, i, BIT); + +#define P_RS1_INNER_PARAMS(BIT_INNER) \ + auto p_rs1 = P_FIELD(rs1, j, BIT_INNER); + +#define P_RS1_INNER_UPARAMS(BIT_INNER) \ + auto p_rs1 = P_UFIELD(rs1, j, BIT_INNER); + +#define P_RS1_EVEN_PARAMS(BIT) \ + auto p_rs1 = P_FIELD(rs1, i * 2, BIT); + +#define P_RS1_ODD_PARAMS(BIT) \ + auto p_rs1 = P_FIELD(rs1, i * 2 + 1, BIT); + +#define P_RS1_EVEN_UPARAMS(BIT) \ + auto p_rs1 = P_UFIELD(rs1, i * 2, BIT); + +#define P_RS1_ODD_UPARAMS(BIT) \ + auto p_rs1 = P_UFIELD(rs1, i * 2 + 1, BIT); + +#define P_RS2_PARAMS(BIT) \ + auto p_rs2 = P_FIELD(rs2, i, BIT); + +#define P_RS2_UPARAMS(BIT) \ + auto p_rs2 = P_UFIELD(rs2, i, BIT); + +#define P_RS2_CROSS_PARAMS(BIT) \ + auto p_rs2 = P_FIELD(rs2, (i ^ 1), BIT); + +#define P_RS2_CROSS_UPARAMS(BIT) \ + auto p_rs2 = P_UFIELD(rs2, (i ^ 1), BIT); + +#define P_RS2_INNER_PARAMS(BIT_INNER) \ + auto p_rs2 = P_FIELD(rs2, j, BIT_INNER); + +#define P_RS2_INNER_UPARAMS(BIT_INNER) \ + auto p_rs2 = P_UFIELD(rs2, j, BIT_INNER); + +#define P_RS2_INNER_CROSS_PARAMS(BIT_INNER) \ + auto p_rs2 = P_FIELD(rs2, (j ^ 1), BIT_INNER); + +#define P_RS2_EVEN_PARAMS(BIT) \ + auto p_rs2 = P_FIELD(rs2, i * 2, BIT); + +#define P_RS2_ODD_PARAMS(BIT) \ + auto p_rs2 = P_FIELD(rs2, i * 2 + 1, BIT); + +#define P_RS2_EVEN_UPARAMS(BIT) \ + auto p_rs2 = P_UFIELD(rs2, i * 2, BIT); + +#define P_RS2_ODD_UPARAMS(BIT) \ + auto p_rs2 = P_UFIELD(rs2, i * 2 + 1, BIT); + +// Loop base +#define P_RD_LOOP_BASE(BIT) \ + require_extension('P'); \ + require((BIT) == e8 || (BIT) == e16 || (BIT) == e32); \ + reg_t rd_tmp = RD; \ + sreg_t len = xlen / (BIT); \ + for (sreg_t i = len - 1; i >= 0; --i) { + +#define P_RD_RS1_LOOP_BASE(BIT) \ + require_extension('P'); \ + require((BIT) == e8 || (BIT) == e16 || (BIT) == e32); \ + reg_t rd_tmp = RD; \ + reg_t rs1 = RS1; \ + sreg_t len = xlen / (BIT); \ + for (sreg_t i = len - 1; i >= 0; --i) { + +#define P_RD_RS1_RS2_LOOP_BASE(BIT) \ + require_extension('P'); \ + require((BIT) == e8 || (BIT) == e16 || (BIT) == e32); \ + reg_t rd_tmp = RD; \ + reg_t rs1 = RS1; \ + reg_t rs2 = RS2; \ + sreg_t len = xlen / (BIT); \ + for (sreg_t i = len - 1; i >= 0; --i) { + +#define P_RS1_LOOP_BASE(BIT) \ + require_extension('P'); \ + require((BIT) == e8 || (BIT) == e16 || (BIT) == e32); \ + reg_t rs1 = RS1; \ + sreg_t len = xlen / (BIT); \ + for (sreg_t i = len - 1; i >= 0; --i) { + +#define P_REDUCTION_LOOP_BASE(BIT, BIT_INNER, USE_RD) \ + require_extension('P'); \ + require(BIT == e16 || BIT == e32 || BIT == e64); \ + reg_t rd_tmp = USE_RD ? zext_xlen(RD) : 0; \ + reg_t rs1 = zext_xlen(RS1); \ + reg_t rs2 = zext_xlen(RS2); \ + sreg_t len = 64 / BIT; \ + sreg_t len_inner = BIT / BIT_INNER; \ + for (sreg_t i = len - 1; i >= 0; --i) { \ + sreg_t p_res = P_FIELD(rd_tmp, i, BIT); \ + for (sreg_t j = i * len_inner; j < (i + 1) * len_inner; ++j) { + +#define P_REDUCTION_ULOOP_BASE(BIT, BIT_INNER, USE_RD) \ + require_extension('P'); \ + require(BIT == e16 || BIT == e32 || BIT == e64); \ + reg_t rd_tmp = USE_RD ? zext_xlen(RD) : 0; \ + reg_t rs1 = zext_xlen(RS1); \ + reg_t rs2 = zext_xlen(RS2); \ + sreg_t len = 64 / BIT; \ + sreg_t len_inner = BIT / BIT_INNER; \ + for (sreg_t i = len - 1; i >= 0; --i) { \ + sreg_t p_res = P_UFIELD(rd_tmp, i, BIT); \ + for (sreg_t j = i * len_inner; j < (i + 1) * len_inner; ++j) { + +#define P_REDUCTION_ULOOP_BASE(BIT, BIT_INNER, USE_RD) \ + require_extension('P'); \ + require(BIT == e16 || BIT == e32 || BIT == e64); \ + reg_t rd_tmp = USE_RD ? zext_xlen(RD) : 0; \ + reg_t rs1 = zext_xlen(RS1); \ + reg_t rs2 = zext_xlen(RS2); \ + sreg_t len = 64 / BIT; \ + sreg_t len_inner = BIT / BIT_INNER; \ + for (sreg_t i = len - 1; i >= 0; --i) { \ + sreg_t p_res = P_UFIELD(rd_tmp, i, BIT); \ + for (sreg_t j = i * len_inner; j < (i + 1) * len_inner; ++j) { + +#define P_RD_DW_LOOP_BASE(BIT) \ + require_extension('P'); \ + require((BIT) == e8 || (BIT) == e16 || (BIT) == e32); \ + reg_t rd_tmp = P_RD_PAIR; \ + sreg_t len = xlen / (BIT) * 2; \ + for (sreg_t i = len - 1; i >= 0; --i) { + +// Loop body +#define P_RD_LOOP_BODY(BIT, BODY) { \ + P_RD_PARAMS(BIT) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_LOOP_BODY(BIT_RD, BIT_RS1, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_PARAMS(BIT_RS1) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_ULOOP_BODY(BIT_RD, BIT_RS1, BODY) { \ + P_RD_UPARAMS(BIT_RD) \ + P_RS1_UPARAMS(BIT_RS1) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_PARAMS(BIT_RS1) \ + P_RS2_PARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_UPARAMS(BIT_RD) \ + P_RS1_UPARAMS(BIT_RS1) \ + P_RS2_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_PARAMS(BIT_RS1) \ + P_RS2_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_CROSS_LOOP_BODY(BIT, BODY) { \ + P_RD_PARAMS(BIT) \ + P_RS1_PARAMS(BIT) \ + P_RS2_CROSS_PARAMS(BIT) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_CROSS_ULOOP_BODY(BIT, BODY) { \ + P_RD_UPARAMS(BIT) \ + P_RS1_UPARAMS(BIT) \ + P_RS2_CROSS_UPARAMS(BIT) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_EE_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_EVEN_PARAMS(BIT_RS1) \ + P_RS2_EVEN_PARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_EO_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_EVEN_PARAMS(BIT_RS1) \ + P_RS2_ODD_PARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_OO_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_ODD_PARAMS(BIT_RS1) \ + P_RS2_ODD_PARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_EE_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_UPARAMS(BIT_RD) \ + P_RS1_EVEN_UPARAMS(BIT_RS1) \ + P_RS2_EVEN_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_EO_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_UPARAMS(BIT_RD) \ + P_RS1_EVEN_UPARAMS(BIT_RS1) \ + P_RS2_ODD_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_OO_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_UPARAMS(BIT_RD) \ + P_RS1_ODD_UPARAMS(BIT_RS1) \ + P_RS2_ODD_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_EE_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_EVEN_PARAMS(BIT_RS1) \ + P_RS2_EVEN_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_OO_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_ODD_PARAMS(BIT_RS1) \ + P_RS2_ODD_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_E_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_PARAMS(BIT_RS1) \ + P_RS2_EVEN_PARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_O_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_PARAMS(BIT_RS1) \ + P_RS2_ODD_PARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_E_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_PARAMS(BIT_RS1) \ + P_RS2_EVEN_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +#define P_RD_RS1_RS2_O_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) { \ + P_RD_PARAMS(BIT_RD) \ + P_RS1_PARAMS(BIT_RS1) \ + P_RS2_ODD_UPARAMS(BIT_RS2) \ + BODY \ + WRITE_P_RD(); \ +} + +// Loop end +#define P_RD_LOOP_END() \ + } \ + WRITE_RD(sext_xlen(rd_tmp)); + +#define P_REDUCTION_LOOP_END(BIT, IS_SAT) \ + } \ + if (IS_SAT) { \ + p_res = P_SAT(BIT, p_res); \ + } \ + type_usew_t::type p_rd = p_res; \ + WRITE_P_RD(); \ + } \ + WRITE_RD(sext_xlen(rd_tmp)); + +#define P_REDUCTION_ULOOP_END(BIT, IS_SAT) \ + } \ + type_usew_t::type p_rd = p_res; \ + WRITE_P_RD(); \ + } \ + WRITE_RD(sext_xlen(rd_tmp)); + +#define P_RD_DW_LOOP_END() \ + } \ + WRITE_P_RD_PAIR(rd_tmp); + +// Loop +#define P_RD_LOOP(BIT_RD, BODY) \ + P_RD_LOOP_BASE(BIT_RD) \ + P_RD_LOOP_BODY(BIT_RD, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_LOOP(BIT_RD, BIT_RS1, BODY) \ + P_RD_RS1_LOOP_BASE(BIT_RD) \ + P_RD_RS1_LOOP_BODY(BIT_RD, BIT_RS1, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_ULOOP(BIT_RD, BIT_RS1, BODY) \ + P_RD_RS1_LOOP_BASE(BIT_RD) \ + P_RD_RS1_ULOOP_BODY(BIT_RD, BIT_RS1, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_LOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_ULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_SULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_CROSS_LOOP(BIT, BODY1, BODY2) \ + P_RD_RS1_RS2_LOOP_BASE(BIT) \ + P_CROSS_LOOP_BODY(BIT, BODY1) \ + --i; \ + if (sizeof(#BODY2) == 1) { \ + P_CROSS_LOOP_BODY(BIT, BODY1) \ + } \ + else { \ + P_CROSS_LOOP_BODY(BIT, BODY2) \ + } \ + P_RD_LOOP_END() + +#define P_CROSS_ULOOP(BIT, BODY1, BODY2) \ + P_RD_RS1_RS2_LOOP_BASE(BIT) \ + P_CROSS_ULOOP_BODY(BIT, BODY1) \ + --i; \ + if (sizeof(#BODY2) == 1) { \ + P_CROSS_ULOOP_BODY(BIT, BODY1) \ + } \ + else { \ + P_CROSS_ULOOP_BODY(BIT, BODY2) \ + } \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_EE_LOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_EE_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_EO_LOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_EO_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_OO_LOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_OO_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_EE_ULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_EE_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_EO_ULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_EO_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_OO_ULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_OO_ULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_EE_SULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_EE_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_OO_SULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_OO_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_E_LOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_E_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_O_LOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_O_LOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_E_SULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_E_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_RD_RS1_RS2_O_SULOOP(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_RS1_RS2_LOOP_BASE(BIT_RD) \ + P_RD_RS1_RS2_O_SULOOP_BODY(BIT_RD, BIT_RS1, BIT_RS2, BODY) \ + P_RD_LOOP_END() + +#define P_REDUCTION_LOOP(BIT, BIT_INNER, USE_RD, IS_SAT, BODY) \ + P_REDUCTION_LOOP_BASE(BIT, BIT_INNER, USE_RD) \ + P_RS1_INNER_PARAMS(BIT_INNER) \ + P_RS2_INNER_PARAMS(BIT_INNER) \ + BODY \ + P_REDUCTION_LOOP_END(BIT, IS_SAT) + +#define P_REDUCTION_SULOOP(BIT, BIT_INNER, USE_RD, IS_SAT, BODY) \ + P_REDUCTION_LOOP_BASE(BIT, BIT_INNER, USE_RD) \ + P_RS1_INNER_PARAMS(BIT_INNER) \ + P_RS2_INNER_UPARAMS(BIT_INNER) \ + BODY \ + P_REDUCTION_LOOP_END(BIT, IS_SAT) + +#define P_REDUCTION_ULOOP(BIT, BIT_INNER, USE_RD, IS_SAT, BODY) \ + P_REDUCTION_ULOOP_BASE(BIT, BIT_INNER, USE_RD) \ + P_RS1_INNER_UPARAMS(BIT_INNER) \ + P_RS2_INNER_UPARAMS(BIT_INNER) \ + BODY \ + P_REDUCTION_ULOOP_END(BIT, IS_SAT) + +#define P_REDUCTION_CROSS_LOOP(BIT, BIT_INNER, USE_RD, IS_SAT, BODY) \ + P_REDUCTION_LOOP_BASE(BIT, BIT_INNER, USE_RD) \ + P_RS1_INNER_PARAMS(BIT_INNER) \ + P_RS2_INNER_CROSS_PARAMS(BIT_INNER) \ + BODY \ + P_REDUCTION_LOOP_END(BIT, IS_SAT) + +#define P_RD_DW_LOOP(BIT_RD, BODY) \ + P_RD_DW_LOOP_BASE(BIT_RD) \ + P_RD_LOOP_BODY(BIT_RD, BODY) \ + P_RD_DW_LOOP_END() + +// Misc +#define P_SAT(BIT, R) ( \ + ((BIT) == 64) ? (R) : \ + ((R) > ((1LL << ((BIT) - 1)) - 1)) ? ((1LL << ((BIT) - 1)) - 1) : \ + ((R) < -(1LL << ((BIT) - 1))) ? -(1LL << ((BIT) - 1)) : \ + (R) \ +) + +#define P_USAT(BIT, R) ( \ + ((R) < 0) ? 0 : \ + ((BIT) == 64) ? (R) : \ + ((R) > ((1LL << ((BIT) - 1)) - 1)) ? ((1LL << ((BIT) - 1)) - 1) : \ + (R) \ +) + +#define P_PACK(BIT, X, Y) \ + require_extension('P'); \ + require(BIT == e8 || BIT == e16 || BIT == e32); \ + reg_t rd_tmp = 0; \ + for (sreg_t i = 0; i < xlen / BIT / 2; i++) { \ + rd_tmp = set_field(rd_tmp, make_mask64((i * 2 + 1) * BIT, BIT), \ + P_UFIELD(RS2, i * 2 + Y, BIT)); \ + rd_tmp = set_field(rd_tmp, make_mask64(i * 2 * BIT, BIT), \ + P_UFIELD(RS1, i * 2 + X, BIT)); \ + } \ + WRITE_RD(sext_xlen(rd_tmp)); + +#endif \ No newline at end of file diff --git a/riscv/riscv.mk.in b/riscv/riscv.mk.in index a996b889..e1f1add8 100644 --- a/riscv/riscv.mk.in +++ b/riscv/riscv.mk.in @@ -1150,6 +1150,216 @@ riscv_insn_ext_zvzip = \ vpaire_vv \ vpairo_vv \ +riscv_insn_ext_p = \ + pli_b \ + pli_h \ + plui_h \ + padd_bs \ + padd_hs \ + padd_b \ + padd_h \ + psub_b \ + psub_h \ + psadd_b \ + psadd_h \ + sadd \ + psaddu_b \ + psaddu_h \ + saddu \ + pssub_b \ + pssub_h \ + ssub \ + pssubu_b \ + pssubu_h \ + ssubu \ + paadd_b \ + paadd_h \ + aadd \ + paaddu_b \ + paaddu_h \ + aaddu \ + pasub_b \ + pasub_h \ + asub \ + pasubu_b \ + pasubu_h \ + asubu \ + psh1add_h \ + pssh1sadd_h \ + ssh1sadd \ + pas_hx \ + psa_hx \ + psas_hx \ + pssa_hx \ + paas_hx \ + pasa_hx \ + pabd_b \ + pabd_h \ + pabdu_b \ + pabdu_h \ + psabs_b \ + psabs_h \ + predsum_bs \ + predsum_hs \ + predsumu_bs \ + predsumu_hs \ + pabdsumu_b \ + pabdsumau_b \ + psext_h_b \ + psati_h \ + sati_rv32 \ + pusati_h \ + usati_rv32 \ + pslli_b \ + pslli_h \ + psll_bs \ + psll_hs \ + psrli_b \ + psrli_h \ + psrl_bs \ + psrl_hs \ + psrai_b \ + psrai_h \ + psra_bs \ + psra_hs \ + psslai_h \ + psrari_h \ + pssha_hs \ + psshar_hs \ + sslai \ + srari_rv32 \ + ssha \ + sshar \ + pmin_b \ + pmin_h \ + pminu_b \ + pminu_h \ + pmax_b \ + pmax_h \ + pmaxu_b \ + pmaxu_h \ + pmseq_b \ + pmseq_h \ + mseq \ + pmslt_b \ + pmslt_h \ + mslt \ + pmsltu_b \ + pmsltu_h \ + msltu \ + ppaire_b \ + ppaireo_b \ + ppaireo_h \ + ppairoe_b \ + ppairoe_h \ + ppairo_b \ + ppairo_h \ + abs \ + cls \ + slx \ + srx \ + mvm \ + mvmn \ + merge \ + pmulh_h \ + pmulhr_h \ + pmulhsu_h \ + pmulhrsu_h \ + pmulhu_h \ + pmulhru_h \ + pmulq_h \ + pmulqr_h \ + mulhr \ + mulhrsu \ + mulhru \ + mulq \ + mulqr \ + pmul_h_b00 \ + pmul_h_b01 \ + pmul_h_b11 \ + pmulsu_h_b00 \ + pmulsu_h_b11 \ + pmulu_h_b00 \ + pmulu_h_b01 \ + pmulu_h_b11 \ + mul_h00 \ + mul_h01 \ + mul_h11 \ + mulsu_h00 \ + mulsu_h11 \ + mulu_h00 \ + mulu_h01 \ + mulu_h11 \ + pmulh_h_b0 \ + pmulh_h_b1 \ + pmulhsu_h_b0 \ + pmulhsu_h_b1 \ + mulh_h0 \ + mulh_h1 \ + mulhsu_h0 \ + mulhsu_h1 \ + pmhacc_h \ + pmhracc_h \ + pmhaccsu_h \ + pmhraccsu_h \ + pmhaccu_h \ + pmhraccu_h \ + mhacc \ + mhracc \ + mhaccsu \ + mhraccsu \ + mhaccu \ + mhraccu \ + mqacc_h00 \ + mqacc_h01 \ + mqacc_h11 \ + mqracc_h00 \ + mqracc_h01 \ + mqracc_h11 \ + macc_h00 \ + macc_h01 \ + macc_h11 \ + maccsu_h00 \ + maccsu_h11 \ + maccu_h00 \ + maccu_h01 \ + maccu_h11 \ + pmhacc_h_b0 \ + pmhacc_h_b1 \ + pmhaccsu_h_b0 \ + pmhaccsu_h_b1 \ + mhacc_h0 \ + mhacc_h1 \ + mhaccsu_h0 \ + mhaccsu_h1 \ + pmq2add_h \ + pmq2adda_h \ + pmqr2add_h \ + pmqr2adda_h \ + pm2add_h \ + pm2adda_h \ + pm2addsu_h \ + pm2addasu_h \ + pm2addu_h \ + pm2addau_h \ + pm2add_hx \ + pm2adda_hx \ + pm2sadd_h \ + pm2sadd_hx \ + pm2sub_h \ + pm2suba_h \ + pm2sub_hx \ + pm2suba_hx \ + pm4add_b \ + pm4adda_b \ + pm4addsu_b \ + pm4addasu_b \ + pm4addu_b \ + pm4addau_b \ + pli_db \ + pli_dh \ + plui_dh \ + riscv_insn_list = \ $(riscv_insn_ext_i) \ $(riscv_insn_ext_c) \ @@ -1165,6 +1375,7 @@ riscv_insn_list = \ $(riscv_insn_ext_cmo) \ $(riscv_insn_ext_d_zfa) \ $(riscv_insn_ext_f_zfa) \ + $(riscv_insn_ext_p) \ $(riscv_insn_ext_h) \ $(riscv_insn_ext_k) \ $(if $(HAVE_INT128),$(riscv_insn_ext_q),) \