diff options
author | Chih-Min Chao <chihmin.chao@sifive.com> | 2020-05-27 00:55:58 -0700 |
---|---|---|
committer | Chih-Min Chao <chihmin.chao@sifive.com> | 2020-05-28 22:36:15 -0700 |
commit | 3035256f1a451da1dabff677e6e14b13fef7edc1 (patch) | |
tree | 0d82dd524add0706e5113c0fd9d55daf0f044d51 | |
parent | f5983b39c583971b8443b9f16705cbfb1588dbf5 (diff) | |
download | riscv-isa-sim-3035256f1a451da1dabff677e6e14b13fef7edc1.zip riscv-isa-sim-3035256f1a451da1dabff677e6e14b13fef7edc1.tar.gz riscv-isa-sim-3035256f1a451da1dabff677e6e14b13fef7edc1.tar.bz2 |
rvv: add amo instructions
use --isa=rv64gcv_zvamo to enable it
Signed-off-by: Chih-Min Chao <chihmin.chao@sifive.com>
41 files changed, 318 insertions, 54 deletions
diff --git a/riscv/decode.h b/riscv/decode.h index c37d409..6188e52 100644 --- a/riscv/decode.h +++ b/riscv/decode.h @@ -1684,6 +1684,49 @@ for (reg_t i = 0; i < vlmax && P.VU.vl != 0; ++i) { \ p->VU.vstart = 0; // +// vector: amo +// +#define VI_AMO(op, type, idx_type) \ + require_vector; \ + require_extension(EXT_ZVAMO); \ + if (insn.v_wd()) \ + require_vm; \ + require_align(insn.rd(), P.VU.vflmul); \ + require(P.VU.vsew <= P.get_xlen() && P.VU.vsew >= 32); \ + require_align(insn.rd(), P.VU.vflmul); \ + P.VU.veew = idx_type; \ + P.VU.vemul = ((float)P.VU.veew / P.VU.vsew * P.VU.vflmul); \ + require(P.VU.vemul >= 0.125 && P.VU.vemul <= 8); \ + require_align(insn.rs2(), P.VU.vemul); \ + VI_DUPLICATE_VREG(insn.rs2(), idx_type); \ + const reg_t vl = P.VU.vl; \ + const reg_t baseAddr = RS1; \ + const reg_t vd = insn.rd(); \ + for (reg_t i = P.VU.vstart; i < vl; ++i) { \ + VI_ELEMENT_SKIP(i); \ + VI_STRIP(i); \ + switch (P.VU.vsew) { \ + case e32: {\ + auto vs3 = P.VU.elt< type ## 32_t>(vd, vreg_inx); \ + auto val = MMU.amo_uint32(baseAddr + index[i], [&]( type ## 32_t lhs) { op }); \ + if (insn.v_wd()) \ + P.VU.elt< type ## 32_t>(vd, vreg_inx, true) = val; \ + } \ + break; \ + case e64: {\ + auto vs3 = P.VU.elt< type ## 64_t>(vd, vreg_inx); \ + auto val = MMU.amo_uint64(baseAddr + index[i], [&]( type ## 64_t lhs) { op }); \ + if (insn.v_wd()) \ + P.VU.elt< type ## 64_t>(vd, vreg_inx, true) = val; \ + } \ + break; \ + default: \ + require(0); \ + break; \ + } \ + } \ + P.VU.vstart = 0; + // vector: sign/unsiged extension #define VI_VV_EXT(div, type) \ require(insn.rd() != insn.rs2()); \ diff --git a/riscv/encoding.h b/riscv/encoding.h index ecacefe..0726b3f 100644 --- a/riscv/encoding.h +++ b/riscv/encoding.h @@ -1551,42 +1551,78 @@ #define MASK_VWMACCUS_VX 0xfc00707f #define MATCH_VWMACCSU_VX 0xfc006057 #define MASK_VWMACCSU_VX 0xfc00707f -#define MATCH_VAMOSWAPW_V 0x800602f -#define MASK_VAMOSWAPW_V 0xf800707f -#define MATCH_VAMOADDW_V 0x602f -#define MASK_VAMOADDW_V 0xf800707f -#define MATCH_VAMOXORW_V 0x2000602f -#define MASK_VAMOXORW_V 0xf800707f -#define MATCH_VAMOANDW_V 0x6000602f -#define MASK_VAMOANDW_V 0xf800707f -#define MATCH_VAMOORW_V 0x4000602f -#define MASK_VAMOORW_V 0xf800707f -#define MATCH_VAMOMINW_V 0x8000602f -#define MASK_VAMOMINW_V 0xf800707f -#define MATCH_VAMOMAXW_V 0xa000602f -#define MASK_VAMOMAXW_V 0xf800707f -#define MATCH_VAMOMINUW_V 0xc000602f -#define MASK_VAMOMINUW_V 0xf800707f -#define MATCH_VAMOMAXUW_V 0xe000602f -#define MASK_VAMOMAXUW_V 0xf800707f -#define MATCH_VAMOSWAPE_V 0x800702f -#define MASK_VAMOSWAPE_V 0xf800707f -#define MATCH_VAMOADDE_V 0x702f -#define MASK_VAMOADDE_V 0xf800707f -#define MATCH_VAMOXORE_V 0x2000702f -#define MASK_VAMOXORE_V 0xf800707f -#define MATCH_VAMOANDE_V 0x6000702f -#define MASK_VAMOANDE_V 0xf800707f -#define MATCH_VAMOORE_V 0x4000702f -#define MASK_VAMOORE_V 0xf800707f -#define MATCH_VAMOMINE_V 0x8000702f -#define MASK_VAMOMINE_V 0xf800707f -#define MATCH_VAMOMAXE_V 0xa000702f -#define MASK_VAMOMAXE_V 0xf800707f -#define MATCH_VAMOMINUE_V 0xc000702f -#define MASK_VAMOMINUE_V 0xf800707f -#define MATCH_VAMOMAXUE_V 0xe000702f -#define MASK_VAMOMAXUE_V 0xf800707f +#define MATCH_VAMOSWAPE8_V 0x800002f +#define MASK_VAMOSWAPE8_V 0xf800707f +#define MATCH_VAMOADDE8_V 0x2f +#define MASK_VAMOADDE8_V 0xf800707f +#define MATCH_VAMOXORE8_V 0x2000002f +#define MASK_VAMOXORE8_V 0xf800707f +#define MATCH_VAMOANDE8_V 0x6000002f +#define MASK_VAMOANDE8_V 0xf800707f +#define MATCH_VAMOORE8_V 0x4000002f +#define MASK_VAMOORE8_V 0xf800707f +#define MATCH_VAMOMINE8_V 0x8000002f +#define MASK_VAMOMINE8_V 0xf800707f +#define MATCH_VAMOMAXE8_V 0xa000002f +#define MASK_VAMOMAXE8_V 0xf800707f +#define MATCH_VAMOMINUE8_V 0xc000002f +#define MASK_VAMOMINUE8_V 0xf800707f +#define MATCH_VAMOMAXUE8_V 0xe000002f +#define MASK_VAMOMAXUE8_V 0xf800707f +#define MATCH_VAMOSWAPE16_V 0x800502f +#define MASK_VAMOSWAPE16_V 0xf800707f +#define MATCH_VAMOADDE16_V 0x502f +#define MASK_VAMOADDE16_V 0xf800707f +#define MATCH_VAMOXORE16_V 0x2000502f +#define MASK_VAMOXORE16_V 0xf800707f +#define MATCH_VAMOANDE16_V 0x6000502f +#define MASK_VAMOANDE16_V 0xf800707f +#define MATCH_VAMOORE16_V 0x4000502f +#define MASK_VAMOORE16_V 0xf800707f +#define MATCH_VAMOMINE16_V 0x8000502f +#define MASK_VAMOMINE16_V 0xf800707f +#define MATCH_VAMOMAXE16_V 0xa000502f +#define MASK_VAMOMAXE16_V 0xf800707f +#define MATCH_VAMOMINUE16_V 0xc000502f +#define MASK_VAMOMINUE16_V 0xf800707f +#define MATCH_VAMOMAXUE16_V 0xe000502f +#define MASK_VAMOMAXUE16_V 0xf800707f +#define MATCH_VAMOSWAPE32_V 0x800602f +#define MASK_VAMOSWAPE32_V 0xf800707f +#define MATCH_VAMOADDE32_V 0x602f +#define MASK_VAMOADDE32_V 0xf800707f +#define MATCH_VAMOXORE32_V 0x2000602f +#define MASK_VAMOXORE32_V 0xf800707f +#define MATCH_VAMOANDE32_V 0x6000602f +#define MASK_VAMOANDE32_V 0xf800707f +#define MATCH_VAMOORE32_V 0x4000602f +#define MASK_VAMOORE32_V 0xf800707f +#define MATCH_VAMOMINE32_V 0x8000602f +#define MASK_VAMOMINE32_V 0xf800707f +#define MATCH_VAMOMAXE32_V 0xa000602f +#define MASK_VAMOMAXE32_V 0xf800707f +#define MATCH_VAMOMINUE32_V 0xc000602f +#define MASK_VAMOMINUE32_V 0xf800707f +#define MATCH_VAMOMAXUE32_V 0xe000602f +#define MASK_VAMOMAXUE32_V 0xf800707f +#define MATCH_VAMOSWAPE64_V 0x800702f +#define MASK_VAMOSWAPE64_V 0xf800707f +#define MATCH_VAMOADDE64_V 0x702f +#define MASK_VAMOADDE64_V 0xf800707f +#define MATCH_VAMOXORE64_V 0x2000702f +#define MASK_VAMOXORE64_V 0xf800707f +#define MATCH_VAMOANDE64_V 0x6000702f +#define MASK_VAMOANDE64_V 0xf800707f +#define MATCH_VAMOORE64_V 0x4000702f +#define MASK_VAMOORE64_V 0xf800707f +#define MATCH_VAMOMINE64_V 0x8000702f +#define MASK_VAMOMINE64_V 0xf800707f +#define MATCH_VAMOMAXE64_V 0xa000702f +#define MASK_VAMOMAXE64_V 0xf800707f +#define MATCH_VAMOMINUE64_V 0xc000702f +#define MASK_VAMOMINUE64_V 0xf800707f +#define MATCH_VAMOMAXUE64_V 0xe000702f +#define MASK_VAMOMAXUE64_V 0xf800707f #define MATCH_VMVNFR_V 0x9e003057 #define MASK_VMVNFR_V 0xfe00707f #define CSR_FFLAGS 0x1 @@ -2535,24 +2571,42 @@ DECLARE_INSN(vwmaccu_vx, MATCH_VWMACCU_VX, MASK_VWMACCU_VX) DECLARE_INSN(vwmacc_vx, MATCH_VWMACC_VX, MASK_VWMACC_VX) DECLARE_INSN(vwmaccus_vx, MATCH_VWMACCUS_VX, MASK_VWMACCUS_VX) DECLARE_INSN(vwmaccsu_vx, MATCH_VWMACCSU_VX, MASK_VWMACCSU_VX) -DECLARE_INSN(vamoswapw_v, MATCH_VAMOSWAPW_V, MASK_VAMOSWAPW_V) -DECLARE_INSN(vamoaddw_v, MATCH_VAMOADDW_V, MASK_VAMOADDW_V) -DECLARE_INSN(vamoxorw_v, MATCH_VAMOXORW_V, MASK_VAMOXORW_V) -DECLARE_INSN(vamoandw_v, MATCH_VAMOANDW_V, MASK_VAMOANDW_V) -DECLARE_INSN(vamoorw_v, MATCH_VAMOORW_V, MASK_VAMOORW_V) -DECLARE_INSN(vamominw_v, MATCH_VAMOMINW_V, MASK_VAMOMINW_V) -DECLARE_INSN(vamomaxw_v, MATCH_VAMOMAXW_V, MASK_VAMOMAXW_V) -DECLARE_INSN(vamominuw_v, MATCH_VAMOMINUW_V, MASK_VAMOMINUW_V) -DECLARE_INSN(vamomaxuw_v, MATCH_VAMOMAXUW_V, MASK_VAMOMAXUW_V) -DECLARE_INSN(vamoswape_v, MATCH_VAMOSWAPE_V, MASK_VAMOSWAPE_V) -DECLARE_INSN(vamoadde_v, MATCH_VAMOADDE_V, MASK_VAMOADDE_V) -DECLARE_INSN(vamoxore_v, MATCH_VAMOXORE_V, MASK_VAMOXORE_V) -DECLARE_INSN(vamoande_v, MATCH_VAMOANDE_V, MASK_VAMOANDE_V) -DECLARE_INSN(vamoore_v, MATCH_VAMOORE_V, MASK_VAMOORE_V) -DECLARE_INSN(vamomine_v, MATCH_VAMOMINE_V, MASK_VAMOMINE_V) -DECLARE_INSN(vamomaxe_v, MATCH_VAMOMAXE_V, MASK_VAMOMAXE_V) -DECLARE_INSN(vamominue_v, MATCH_VAMOMINUE_V, MASK_VAMOMINUE_V) -DECLARE_INSN(vamomaxue_v, MATCH_VAMOMAXUE_V, MASK_VAMOMAXUE_V) +DECLARE_INSN(vamoswape8_v, MATCH_VAMOSWAPE8_V, MASK_VAMOSWAPE8_V) +DECLARE_INSN(vamoadde8_v, MATCH_VAMOADDE8_V, MASK_VAMOADDE8_V) +DECLARE_INSN(vamoxore8_v, MATCH_VAMOXORE8_V, MASK_VAMOXORE8_V) +DECLARE_INSN(vamoande8_v, MATCH_VAMOANDE8_V, MASK_VAMOANDE8_V) +DECLARE_INSN(vamoore8_v, MATCH_VAMOORE8_V, MASK_VAMOORE8_V) +DECLARE_INSN(vamomine8_v, MATCH_VAMOMINE8_V, MASK_VAMOMINE8_V) +DECLARE_INSN(vamomaxe8_v, MATCH_VAMOMAXE8_V, MASK_VAMOMAXE8_V) +DECLARE_INSN(vamominue8_v, MATCH_VAMOMINUE8_V, MASK_VAMOMINUE8_V) +DECLARE_INSN(vamomaxue8_v, MATCH_VAMOMAXUE8_V, MASK_VAMOMAXUE8_V) +DECLARE_INSN(vamoswape16_v, MATCH_VAMOSWAPE16_V, MASK_VAMOSWAPE16_V) +DECLARE_INSN(vamoadde16_v, MATCH_VAMOADDE16_V, MASK_VAMOADDE16_V) +DECLARE_INSN(vamoxore16_v, MATCH_VAMOXORE16_V, MASK_VAMOXORE16_V) +DECLARE_INSN(vamoande16_v, MATCH_VAMOANDE16_V, MASK_VAMOANDE16_V) +DECLARE_INSN(vamoore16_v, MATCH_VAMOORE16_V, MASK_VAMOORE16_V) +DECLARE_INSN(vamomine16_v, MATCH_VAMOMINE16_V, MASK_VAMOMINE16_V) +DECLARE_INSN(vamomaxe16_v, MATCH_VAMOMAXE16_V, MASK_VAMOMAXE16_V) +DECLARE_INSN(vamominue16_v, MATCH_VAMOMINUE16_V, MASK_VAMOMINUE16_V) +DECLARE_INSN(vamomaxue16_v, MATCH_VAMOMAXUE16_V, MASK_VAMOMAXUE16_V) +DECLARE_INSN(vamoswape32_v, MATCH_VAMOSWAPE32_V, MASK_VAMOSWAPE32_V) +DECLARE_INSN(vamoadde32_v, MATCH_VAMOADDE32_V, MASK_VAMOADDE32_V) +DECLARE_INSN(vamoxore32_v, MATCH_VAMOXORE32_V, MASK_VAMOXORE32_V) +DECLARE_INSN(vamoande32_v, MATCH_VAMOANDE32_V, MASK_VAMOANDE32_V) +DECLARE_INSN(vamoore32_v, MATCH_VAMOORE32_V, MASK_VAMOORE32_V) +DECLARE_INSN(vamomine32_v, MATCH_VAMOMINE32_V, MASK_VAMOMINE32_V) +DECLARE_INSN(vamomaxe32_v, MATCH_VAMOMAXE32_V, MASK_VAMOMAXE32_V) +DECLARE_INSN(vamominue32_v, MATCH_VAMOMINUE32_V, MASK_VAMOMINUE32_V) +DECLARE_INSN(vamomaxue32_v, MATCH_VAMOMAXUE32_V, MASK_VAMOMAXUE32_V) +DECLARE_INSN(vamoswape64_v, MATCH_VAMOSWAPE64_V, MASK_VAMOSWAPE64_V) +DECLARE_INSN(vamoadde64_v, MATCH_VAMOADDE64_V, MASK_VAMOADDE64_V) +DECLARE_INSN(vamoxore64_v, MATCH_VAMOXORE64_V, MASK_VAMOXORE64_V) +DECLARE_INSN(vamoande64_v, MATCH_VAMOANDE64_V, MASK_VAMOANDE64_V) +DECLARE_INSN(vamoore64_v, MATCH_VAMOORE64_V, MASK_VAMOORE64_V) +DECLARE_INSN(vamomine64_v, MATCH_VAMOMINE64_V, MASK_VAMOMINE64_V) +DECLARE_INSN(vamomaxe64_v, MATCH_VAMOMAXE64_V, MASK_VAMOMAXE64_V) +DECLARE_INSN(vamominue64_v, MATCH_VAMOMINUE64_V, MASK_VAMOMINUE64_V) +DECLARE_INSN(vamomaxue64_v, MATCH_VAMOMAXUE64_V, MASK_VAMOMAXUE64_V) DECLARE_INSN(vmvnfr_v, MATCH_VMVNFR_V, MASK_VMVNFR_V) #endif #ifdef DECLARE_CSR diff --git a/riscv/insns/vamoadde16_v.h b/riscv/insns/vamoadde16_v.h new file mode 100644 index 0000000..3cb3db7 --- /dev/null +++ b/riscv/insns/vamoadde16_v.h @@ -0,0 +1,2 @@ +//vamoadde.v vd, (rs1), vs2, vd +VI_AMO({ return lhs + vs3; }, uint, e16); diff --git a/riscv/insns/vamoadde32_v.h b/riscv/insns/vamoadde32_v.h new file mode 100644 index 0000000..2bd77fc --- /dev/null +++ b/riscv/insns/vamoadde32_v.h @@ -0,0 +1,2 @@ +//vamoadde.v vd, (rs1), vs2, vd +VI_AMO({ return lhs + vs3; }, uint, e32); diff --git a/riscv/insns/vamoadde64_v.h b/riscv/insns/vamoadde64_v.h new file mode 100644 index 0000000..79ca748 --- /dev/null +++ b/riscv/insns/vamoadde64_v.h @@ -0,0 +1,2 @@ +//vamoadde.v vd, (rs1), vs2, vd +VI_AMO({ return lhs + vs3; }, uint, e64); diff --git a/riscv/insns/vamoadde8_v.h b/riscv/insns/vamoadde8_v.h new file mode 100644 index 0000000..06b8c79 --- /dev/null +++ b/riscv/insns/vamoadde8_v.h @@ -0,0 +1,2 @@ +//vamoadde.v vd, (rs1), vs2, vd +VI_AMO({ return lhs + vs3; }, uint, e8); diff --git a/riscv/insns/vamoande16_v.h b/riscv/insns/vamoande16_v.h new file mode 100644 index 0000000..be11949 --- /dev/null +++ b/riscv/insns/vamoande16_v.h @@ -0,0 +1,2 @@ +//vamoande.v vd, (rs1), vs2, vd +VI_AMO({ return lhs & vs3; }, uint, e16); diff --git a/riscv/insns/vamoande32_v.h b/riscv/insns/vamoande32_v.h new file mode 100644 index 0000000..7150670 --- /dev/null +++ b/riscv/insns/vamoande32_v.h @@ -0,0 +1,2 @@ +//vamoande.v vd, (rs1), vs2, vd +VI_AMO({ return lhs & vs3; }, uint, e32); diff --git a/riscv/insns/vamoande64_v.h b/riscv/insns/vamoande64_v.h new file mode 100644 index 0000000..3efae3b --- /dev/null +++ b/riscv/insns/vamoande64_v.h @@ -0,0 +1,2 @@ +//vamoande.v vd, (rs1), vs2, vd +VI_AMO({ return lhs & vs3; }, uint, e64); diff --git a/riscv/insns/vamoande8_v.h b/riscv/insns/vamoande8_v.h new file mode 100644 index 0000000..c47645d --- /dev/null +++ b/riscv/insns/vamoande8_v.h @@ -0,0 +1,2 @@ +//vamoande.v vd, (rs1), vs2, vd +VI_AMO({ return lhs & vs3; }, uint, e8); diff --git a/riscv/insns/vamomaxe16_v.h b/riscv/insns/vamomaxe16_v.h new file mode 100644 index 0000000..ca67893 --- /dev/null +++ b/riscv/insns/vamomaxe16_v.h @@ -0,0 +1,2 @@ +//vamomaxe.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3; }, int, e16); diff --git a/riscv/insns/vamomaxe32_v.h b/riscv/insns/vamomaxe32_v.h new file mode 100644 index 0000000..b6823cd --- /dev/null +++ b/riscv/insns/vamomaxe32_v.h @@ -0,0 +1,2 @@ +//vamomaxe.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3; }, int, e32); diff --git a/riscv/insns/vamomaxe64_v.h b/riscv/insns/vamomaxe64_v.h new file mode 100644 index 0000000..46e8a3b --- /dev/null +++ b/riscv/insns/vamomaxe64_v.h @@ -0,0 +1,2 @@ +//vamomaxe.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3; }, int, e64); diff --git a/riscv/insns/vamomaxe8_v.h b/riscv/insns/vamomaxe8_v.h new file mode 100644 index 0000000..9697b3a --- /dev/null +++ b/riscv/insns/vamomaxe8_v.h @@ -0,0 +1,2 @@ +//vamomaxe.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3; }, int, e8); diff --git a/riscv/insns/vamomaxue16_v.h b/riscv/insns/vamomaxue16_v.h new file mode 100644 index 0000000..e05971d --- /dev/null +++ b/riscv/insns/vamomaxue16_v.h @@ -0,0 +1,2 @@ +//vamomaxue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3;; }, uint, e16); diff --git a/riscv/insns/vamomaxue32_v.h b/riscv/insns/vamomaxue32_v.h new file mode 100644 index 0000000..9b87354 --- /dev/null +++ b/riscv/insns/vamomaxue32_v.h @@ -0,0 +1,2 @@ +//vamomaxue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3;; }, uint, e32); diff --git a/riscv/insns/vamomaxue64_v.h b/riscv/insns/vamomaxue64_v.h new file mode 100644 index 0000000..bbfbc9f --- /dev/null +++ b/riscv/insns/vamomaxue64_v.h @@ -0,0 +1,2 @@ +//vamomaxue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3;; }, uint, e64); diff --git a/riscv/insns/vamomaxue8_v.h b/riscv/insns/vamomaxue8_v.h new file mode 100644 index 0000000..357ba24 --- /dev/null +++ b/riscv/insns/vamomaxue8_v.h @@ -0,0 +1,2 @@ +//vamomaxue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs >= vs3 ? lhs : vs3;; }, uint, e8); diff --git a/riscv/insns/vamomine16_v.h b/riscv/insns/vamomine16_v.h new file mode 100644 index 0000000..9d1ecac --- /dev/null +++ b/riscv/insns/vamomine16_v.h @@ -0,0 +1,2 @@ +//vamomine.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3; }, int, e16); diff --git a/riscv/insns/vamomine32_v.h b/riscv/insns/vamomine32_v.h new file mode 100644 index 0000000..6cb8475 --- /dev/null +++ b/riscv/insns/vamomine32_v.h @@ -0,0 +1,2 @@ +//vamomine.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3; }, int, e32); diff --git a/riscv/insns/vamomine64_v.h b/riscv/insns/vamomine64_v.h new file mode 100644 index 0000000..9ef3d4e --- /dev/null +++ b/riscv/insns/vamomine64_v.h @@ -0,0 +1,2 @@ +//vamomine.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3; }, int, e64); diff --git a/riscv/insns/vamomine8_v.h b/riscv/insns/vamomine8_v.h new file mode 100644 index 0000000..5c035ea --- /dev/null +++ b/riscv/insns/vamomine8_v.h @@ -0,0 +1,2 @@ +//vamomine.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3; }, int, e8); diff --git a/riscv/insns/vamominue16_v.h b/riscv/insns/vamominue16_v.h new file mode 100644 index 0000000..d4a8f89 --- /dev/null +++ b/riscv/insns/vamominue16_v.h @@ -0,0 +1,2 @@ +//vamominue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3;; }, uint, e16); diff --git a/riscv/insns/vamominue32_v.h b/riscv/insns/vamominue32_v.h new file mode 100644 index 0000000..16296c5 --- /dev/null +++ b/riscv/insns/vamominue32_v.h @@ -0,0 +1,2 @@ +//vamominue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3;; }, uint, e32); diff --git a/riscv/insns/vamominue64_v.h b/riscv/insns/vamominue64_v.h new file mode 100644 index 0000000..fd850fd --- /dev/null +++ b/riscv/insns/vamominue64_v.h @@ -0,0 +1,2 @@ +//vamominue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3;; }, uint, e64); diff --git a/riscv/insns/vamominue8_v.h b/riscv/insns/vamominue8_v.h new file mode 100644 index 0000000..3749d05 --- /dev/null +++ b/riscv/insns/vamominue8_v.h @@ -0,0 +1,2 @@ +//vamominue.v vd, (rs1), vs2, vd +VI_AMO({ return lhs < vs3 ? lhs : vs3;; }, uint, e8); diff --git a/riscv/insns/vamoore16_v.h b/riscv/insns/vamoore16_v.h new file mode 100644 index 0000000..a5ba1ca --- /dev/null +++ b/riscv/insns/vamoore16_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs | vs3; }, uint, e16); diff --git a/riscv/insns/vamoore32_v.h b/riscv/insns/vamoore32_v.h new file mode 100644 index 0000000..94e4458 --- /dev/null +++ b/riscv/insns/vamoore32_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs | vs3; }, uint, e32); diff --git a/riscv/insns/vamoore64_v.h b/riscv/insns/vamoore64_v.h new file mode 100644 index 0000000..84e0394 --- /dev/null +++ b/riscv/insns/vamoore64_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs | vs3; }, uint, e64); diff --git a/riscv/insns/vamoore8_v.h b/riscv/insns/vamoore8_v.h new file mode 100644 index 0000000..364035d --- /dev/null +++ b/riscv/insns/vamoore8_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs | vs3; }, uint, e8); diff --git a/riscv/insns/vamoswape16_v.h b/riscv/insns/vamoswape16_v.h new file mode 100644 index 0000000..31ff021 --- /dev/null +++ b/riscv/insns/vamoswape16_v.h @@ -0,0 +1,2 @@ +//vamoswape.v vd, (rs1), vs2, vd +VI_AMO({ return vs3; }, uint, e16); diff --git a/riscv/insns/vamoswape32_v.h b/riscv/insns/vamoswape32_v.h new file mode 100644 index 0000000..a574192 --- /dev/null +++ b/riscv/insns/vamoswape32_v.h @@ -0,0 +1,2 @@ +//vamoswape.v vd, (rs1), vs2, vd +VI_AMO({ return vs3; }, uint, e32); diff --git a/riscv/insns/vamoswape64_v.h b/riscv/insns/vamoswape64_v.h new file mode 100644 index 0000000..58bd035 --- /dev/null +++ b/riscv/insns/vamoswape64_v.h @@ -0,0 +1,2 @@ +//vamoswape.v vd, (rs1), vs2, vd +VI_AMO({ return vs3; }, uint, e64); diff --git a/riscv/insns/vamoswape8_v.h b/riscv/insns/vamoswape8_v.h new file mode 100644 index 0000000..af37c8c --- /dev/null +++ b/riscv/insns/vamoswape8_v.h @@ -0,0 +1,2 @@ +//vamoswape.v vd, (rs1), vs2, vd +VI_AMO({ return vs3; }, uint, e8); diff --git a/riscv/insns/vamoxore16_v.h b/riscv/insns/vamoxore16_v.h new file mode 100644 index 0000000..61e8c32 --- /dev/null +++ b/riscv/insns/vamoxore16_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs ^ vs3; }, uint, e16); diff --git a/riscv/insns/vamoxore32_v.h b/riscv/insns/vamoxore32_v.h new file mode 100644 index 0000000..d48d951 --- /dev/null +++ b/riscv/insns/vamoxore32_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs ^ vs3; }, uint, e32); diff --git a/riscv/insns/vamoxore64_v.h b/riscv/insns/vamoxore64_v.h new file mode 100644 index 0000000..f7a3ca4 --- /dev/null +++ b/riscv/insns/vamoxore64_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs ^ vs3; }, uint, e64); diff --git a/riscv/insns/vamoxore8_v.h b/riscv/insns/vamoxore8_v.h new file mode 100644 index 0000000..4b6c798 --- /dev/null +++ b/riscv/insns/vamoxore8_v.h @@ -0,0 +1,2 @@ +//vamoore.v vd, (rs1), vs2, vd +VI_AMO({ return lhs ^ vs3; }, uint, e8); diff --git a/riscv/processor.cc b/riscv/processor.cc index 123a8cc..2a0a561 100644 --- a/riscv/processor.cc +++ b/riscv/processor.cc @@ -257,6 +257,8 @@ void processor_t::parse_isa_string(const char* str) auto ext_str = std::string(ext, end - ext); if (ext_str == "zfh") { extension_table[EXT_ZFH] = true; + } else if (ext_str == "zvamo") { + extension_table[EXT_ZVAMO] = true; } else { sprintf(error_msg, "unsupported extension '%s'", ext_str.c_str()); bad_isa_string(str, error_msg); @@ -282,6 +284,10 @@ void processor_t::parse_isa_string(const char* str) if (supports_extension('Q') && !supports_extension('D')) bad_isa_string(str, "'Q' extension requires 'D'"); + + if (supports_extension(EXT_ZVAMO) && + !(supports_extension('A') && supports_extension('V'))) + bad_isa_string(str, "'Zvamo' extension requires 'A' and 'V'"); } void state_t::reset(reg_t max_isa) diff --git a/riscv/riscv.mk.in b/riscv/riscv.mk.in index cbb6088..f63368d 100644 --- a/riscv/riscv.mk.in +++ b/riscv/riscv.mk.in @@ -614,6 +614,44 @@ riscv_insn_ext_v_alu_fp = \ vmfne_vf \ vmfne_vv \ +riscv_insn_ext_v_amo = \ + vamoswape8_v \ + vamoadde8_v \ + vamoande8_v \ + vamomaxe8_v \ + vamomaxue8_v \ + vamomine8_v \ + vamominue8_v \ + vamoore8_v \ + vamoxore8_v \ + vamoswape16_v \ + vamoadde16_v \ + vamoande16_v \ + vamomaxe16_v \ + vamomaxue16_v \ + vamomine16_v \ + vamominue16_v \ + vamoore16_v \ + vamoxore16_v \ + vamoswape32_v \ + vamoadde32_v \ + vamoande32_v \ + vamomaxe32_v \ + vamomaxue32_v \ + vamomine32_v \ + vamominue32_v \ + vamoore32_v \ + vamoxore32_v \ + vamoswape64_v \ + vamoadde64_v \ + vamoande64_v \ + vamomaxe64_v \ + vamomaxue64_v \ + vamomine64_v \ + vamominue64_v \ + vamoore64_v \ + vamoxore64_v \ + riscv_insn_ext_v_ldst = \ vl1r_v \ vlb_v \ @@ -669,6 +707,7 @@ riscv_insn_ext_v_ctrl = \ riscv_insn_ext_v = \ $(riscv_insn_ext_v_alu_fp) \ $(riscv_insn_ext_v_alu_int) \ + $(riscv_insn_ext_v_amo) \ $(riscv_insn_ext_v_ctrl) \ $(riscv_insn_ext_v_ldst) \ diff --git a/spike_main/disasm.cc b/spike_main/disasm.cc index 975b5f7..eeeaff2 100644 --- a/spike_main/disasm.cc +++ b/spike_main/disasm.cc @@ -347,6 +347,18 @@ struct : public arg_t { } } v_vtype; +struct : public arg_t { + std::string to_string(insn_t insn) const { + return "x0"; + } +} x0; + +typedef struct { + reg_t match; + reg_t mask; + const char *fmt; + std::vector<const arg_t*>& arg; +} custom_fmt_t; std::string disassembler_t::disassemble(insn_t insn) const { @@ -366,6 +378,9 @@ disassembler_t::disassembler_t(int xlen) const uint32_t mask_rvc_rs2 = 0x1fUL << 2; const uint32_t mask_rvc_imm = mask_rvc_rs2 | 0x1000UL; const uint32_t mask_nf = 0x7Ul << 29; + const uint32_t mask_wd = 0x1Ul << 26; + const uint32_t mask_amoop = 0x1fUl << 27; + const uint32_t mask_width = 0x7Ul << 12; #define DECLARE_INSN(code, match, mask) \ const uint32_t match_##code = match; \ @@ -1111,6 +1126,41 @@ disassembler_t::disassembler_t(int xlen) #undef DISASM_OPIV_W__INSN #undef DISASM_VFUNARY0_INSN + // vector amo + std::vector<const arg_t *> v_fmt_amo_wd = {&vd, &v_address, &vs2, &vd, &opt, &vm}; + std::vector<const arg_t *> v_fmt_amo = {&x0, &v_address, &vs2, &vd, &opt, &vm}; + for (size_t elt = 0; elt <= 3; ++elt) { + const custom_fmt_t template_insn[] = { + {match_vamoswape8_v | mask_wd, mask_vamoswape8_v | mask_wd, + "%se%d.v", v_fmt_amo_wd}, + {match_vamoswape8_v, mask_vamoswape8_v | mask_wd, + "%se%d.v", v_fmt_amo}, + }; + std::pair<const char*, reg_t> amo_map[] = { + {"vamoswap", 0x01ul << 27}, + {"vamoadd", 0x00ul << 27}, + {"vamoxor", 0x04ul << 27}, + {"vamoor", 0x0cul << 27}, + {"vamomin", 0x10ul << 27}, + {"vamomax", 0x14ul << 27}, + {"vamominu", 0x18ul << 27}, + {"vamomaxu", 0x1cul << 27}}; + const reg_t elt_map[] = {0x0ul << 12, 0x4ul << 12, + 0x6ul <<12, 0x7ul << 12}; + + for (size_t idx = 0; idx < sizeof(amo_map) / sizeof(amo_map[0]); ++idx) { + for (auto item : template_insn) { + char buf[128]; + sprintf(buf, item.fmt, amo_map[idx].first, 8 << elt); + add_insn(new disasm_insn_t(buf, + (item.match & ~mask_width & ~mask_amoop) | + (amo_map[idx].second | elt_map[elt]), + item.mask, + item.arg)); + } + } + } + if (xlen == 32) { DISASM_INSN("c.flw", c_flw, 0, {&rvc_fp_rs2s, &rvc_lw_address}); DISASM_INSN("c.flwsp", c_flwsp, 0, {&frd, &rvc_lwsp_address}); |