Browse Source

rvp: new instructions from 0.20

The complete set of instructions added for RV32 are:
  PSSHL.HS SSHL PSSHL.DHS PSSHL.DWS
  PSSHLR.HS SSHLR PSSHLR.DHS PSSHLR.DWS
And for RV64:
  PSSHL.HS PSSHL.WS SHL PNCLIPP.B PNCLIPP.H PNCLIPP.W
  PSSHLR.HS PSSHLR.WS SHLR PNCLIPUP.B PNCLIPUP.H PNCLIPUP.W

reference:
  https://www.jhauser.us/RISCV/ext-P/RVP-instrEncodings-020.pdf
https://www.jhauser.us/RISCV/ext-P/RVP-baseInstrs-Sail-020.txt

Signed-off-by: Chih-Min Chao <chihmin.chao@sifive.com>
pull/2246/head
Chih-Min Chao 2 months ago
parent
commit
7a42a63eca
  1. 2
      riscv/insns/pnclipiu_b.h
  2. 2
      riscv/insns/pnclipiu_h.h
  3. 13
      riscv/insns/pnclipp_b.h
  4. 13
      riscv/insns/pnclipp_h.h
  5. 13
      riscv/insns/pnclipp_w.h
  6. 13
      riscv/insns/pnclipup_b.h
  7. 13
      riscv/insns/pnclipup_h.h
  8. 13
      riscv/insns/pnclipup_w.h
  9. 19
      riscv/insns/psshl_dhs.h
  10. 19
      riscv/insns/psshl_dws.h
  11. 18
      riscv/insns/psshl_hs.h
  12. 19
      riscv/insns/psshl_ws.h
  13. 23
      riscv/insns/psshlr_dhs.h
  14. 23
      riscv/insns/psshlr_dws.h
  15. 22
      riscv/insns/psshlr_hs.h
  16. 23
      riscv/insns/psshlr_ws.h
  17. 15
      riscv/insns/shl.h
  18. 19
      riscv/insns/shlr.h
  19. 18
      riscv/insns/sshl.h
  20. 22
      riscv/insns/sshlr.h
  21. 2
      riscv/overlap_list.h
  22. 18
      riscv/riscv.mk.in

2
riscv/insns/pnclipiu_b.h

@ -1,4 +1,4 @@
require_rv32;
P_NARROW_RD_RS1_ULOOP(8, 16, {
p_rd = P_USAT(8, p_rs1 >> insn.shamth());
p_rd = P_USAT_FULL(8, (sreg_t)(p_rs1 >> insn.shamth()));
})

2
riscv/insns/pnclipiu_h.h

@ -1,4 +1,4 @@
require_rv32;
P_NARROW_RD_RS1_ULOOP(16, 32, {
p_rd = P_USAT(16, (p_rs1 >> insn.shamtw()));
p_rd = P_USAT_FULL(16, (sreg_t)(p_rs1 >> insn.shamtw()));
})

13
riscv/insns/pnclipp_b.h

@ -0,0 +1,13 @@
require_extension('P');
require_rv64;
reg_t rd_tmp = 0;
reg_t s_low = RS1;
reg_t s_high = RS2;
for (int i = 0; i < 8; i++) {
sreg_t s_h = (i < 4) ? P_FIELD(s_low, i, 16) : P_FIELD(s_high, i - 4, 16);
sreg_t sat_val = P_SAT(8, s_h);
if (sat_val != s_h) P.VU.vxsat->write(1);
rd_tmp = set_field(rd_tmp, make_mask64(i * 8, 8), (uint8_t)sat_val);
}
WRITE_RD(rd_tmp);

13
riscv/insns/pnclipp_h.h

@ -0,0 +1,13 @@
require_extension('P');
require_rv64;
reg_t rd_tmp = 0;
reg_t s_low = RS1;
reg_t s_high = RS2;
for (int i = 0; i < 4; i++) {
sreg_t s_w = (i < 2) ? P_FIELD(s_low, i, 32) : P_FIELD(s_high, i - 2, 32);
sreg_t sat_val = P_SAT(16, s_w);
if (sat_val != s_w) P.VU.vxsat->write(1);
rd_tmp = set_field(rd_tmp, make_mask64(i * 16, 16), (uint16_t)sat_val);
}
WRITE_RD(rd_tmp);

13
riscv/insns/pnclipp_w.h

@ -0,0 +1,13 @@
require_extension('P');
require_rv64;
int64_t s1 = (int64_t)RS1;
int64_t s2 = (int64_t)RS2;
sreg_t sat_w0 = P_SAT(32, s1);
if (sat_w0 != s1) P.VU.vxsat->write(1);
sreg_t sat_w1 = P_SAT(32, s2);
if (sat_w1 != s2) P.VU.vxsat->write(1);
WRITE_RD(((uint64_t)(uint32_t)sat_w1 << 32) | (uint32_t)sat_w0);

13
riscv/insns/pnclipup_b.h

@ -0,0 +1,13 @@
require_extension('P');
require_rv64;
reg_t rd_tmp = 0;
reg_t s_low = RS1;
reg_t s_high = RS2;
for (int i = 0; i < 8; i++) {
reg_t s_h = (i < 4) ? P_UFIELD(s_low, i, 16) : P_UFIELD(s_high, i - 4, 16);
reg_t sat_val = P_USAT_FULL(8, (sreg_t)s_h);
if (sat_val != s_h) P.VU.vxsat->write(1);
rd_tmp = set_field(rd_tmp, make_mask64(i * 8, 8), (uint8_t)sat_val);
}
WRITE_RD(rd_tmp);

13
riscv/insns/pnclipup_h.h

@ -0,0 +1,13 @@
require_extension('P');
require_rv64;
reg_t rd_tmp = 0;
reg_t s_low = RS1;
reg_t s_high = RS2;
for (int i = 0; i < 4; i++) {
reg_t s_w = (i < 2) ? P_UFIELD(s_low, i, 32) : P_UFIELD(s_high, i - 2, 32);
reg_t sat_val = P_USAT_FULL(16, (sreg_t)s_w);
if (sat_val != s_w) P.VU.vxsat->write(1);
rd_tmp = set_field(rd_tmp, make_mask64(i * 16, 16), (uint16_t)sat_val);
}
WRITE_RD(rd_tmp);

13
riscv/insns/pnclipup_w.h

@ -0,0 +1,13 @@
require_extension('P');
require_rv64;
uint64_t s1 = RS1;
uint64_t s2 = RS2;
reg_t sat_w0 = P_USAT_FULL(32, (sreg_t)s1);
if (sat_w0 != s1) P.VU.vxsat->write(1);
reg_t sat_w1 = P_USAT_FULL(32, (sreg_t)s2);
if (sat_w1 != s2) P.VU.vxsat->write(1);
WRITE_RD(((uint64_t)(uint32_t)sat_w1 << 32) | (uint32_t)sat_w0);

19
riscv/insns/psshl_dhs.h

@ -0,0 +1,19 @@
require_rv32;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_DW_LOOP(16, 16, {
if (sshamt < 0) {
if (sshamt <= -16)
p_rd = 0;
else
p_rd = (uint16_t)p_rs1 >> (-sshamt);
} else {
uint32_t shx = (sshamt >= 16) ? ((uint32_t)(uint16_t)p_rs1 << 16) : ((uint32_t)(uint16_t)p_rs1 << sshamt);
if (shx > 0xFFFF) {
P.VU.vxsat->write(1);
p_rd = 0xFFFF;
} else {
p_rd = (uint16_t)shx;
}
}
})

19
riscv/insns/psshl_dws.h

@ -0,0 +1,19 @@
require_rv32;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_DW_LOOP(32, 32, {
if (sshamt < 0) {
if (sshamt <= -32)
p_rd = 0;
else
p_rd = (uint32_t)p_rs1 >> (-sshamt);
} else {
uint64_t shx = (sshamt >= 32) ? ((uint64_t)(uint32_t)p_rs1 << 32) : ((uint64_t)(uint32_t)p_rs1 << sshamt);
if (shx > 0xFFFFFFFFULL) {
P.VU.vxsat->write(1);
p_rd = 0xFFFFFFFF;
} else {
p_rd = (uint32_t)shx;
}
}
})

18
riscv/insns/psshl_hs.h

@ -0,0 +1,18 @@
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_LOOP(16, 16, {
if (sshamt < 0) {
if (sshamt <= -16)
p_rd = 0;
else
p_rd = (uint16_t)p_rs1 >> (-sshamt);
} else {
uint32_t shx = (sshamt >= 16) ? ((uint32_t)(uint16_t)p_rs1 << 16) : ((uint32_t)(uint16_t)p_rs1 << sshamt);
if (shx > 0xFFFF) {
P.VU.vxsat->write(1);
p_rd = 0xFFFF;
} else {
p_rd = (uint16_t)shx;
}
}
})

19
riscv/insns/psshl_ws.h

@ -0,0 +1,19 @@
require_rv64;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_LOOP(32, 32, {
if (sshamt < 0) {
if (sshamt <= -32)
p_rd = 0;
else
p_rd = (uint32_t)p_rs1 >> (-sshamt);
} else {
uint64_t shx = (sshamt >= 32) ? ((uint64_t)(uint32_t)p_rs1 << 32) : ((uint64_t)(uint32_t)p_rs1 << sshamt);
if (shx > 0xFFFFFFFFULL) {
P.VU.vxsat->write(1);
p_rd = 0xFFFFFFFF;
} else {
p_rd = (uint32_t)shx;
}
}
})

23
riscv/insns/psshlr_dhs.h

@ -0,0 +1,23 @@
require_rv32;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_DW_LOOP(16, 16, {
if (sshamt < 0) {
uint32_t shx;
if (sshamt < -16)
shx = 0;
else if (sshamt == -16)
shx = ((uint16_t)p_rs1 >> 15) & 1;
else
shx = ((uint32_t)(uint16_t)p_rs1 << 1) >> (-sshamt);
p_rd = (uint16_t)((shx + 1) >> 1);
} else {
uint32_t shx = (sshamt >= 16) ? ((uint32_t)(uint16_t)p_rs1 << 16) : ((uint32_t)(uint16_t)p_rs1 << sshamt);
if (shx > 0xFFFF) {
P.VU.vxsat->write(1);
p_rd = 0xFFFF;
} else {
p_rd = (uint16_t)shx;
}
}
})

23
riscv/insns/psshlr_dws.h

@ -0,0 +1,23 @@
require_rv32;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_DW_LOOP(32, 32, {
if (sshamt < 0) {
uint64_t shx;
if (sshamt < -32)
shx = 0;
else if (sshamt == -32)
shx = ((uint32_t)p_rs1 >> 31) & 1;
else
shx = ((uint64_t)(uint32_t)p_rs1 << 1) >> (-sshamt);
p_rd = (uint32_t)((shx + 1) >> 1);
} else {
uint64_t shx = (sshamt >= 32) ? ((uint64_t)(uint32_t)p_rs1 << 32) : ((uint64_t)(uint32_t)p_rs1 << sshamt);
if (shx > 0xFFFFFFFFULL) {
P.VU.vxsat->write(1);
p_rd = 0xFFFFFFFF;
} else {
p_rd = (uint32_t)shx;
}
}
})

22
riscv/insns/psshlr_hs.h

@ -0,0 +1,22 @@
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_LOOP(16, 16, {
if (sshamt < 0) {
uint32_t shx;
if (sshamt < -16)
shx = 0;
else if (sshamt == -16)
shx = ((uint16_t)p_rs1 >> 15) & 1;
else
shx = ((uint32_t)(uint16_t)p_rs1 << 1) >> (-sshamt);
p_rd = (uint16_t)((shx + 1) >> 1);
} else {
uint32_t shx = (sshamt >= 16) ? ((uint32_t)(uint16_t)p_rs1 << 16) : ((uint32_t)(uint16_t)p_rs1 << sshamt);
if (shx > 0xFFFF) {
P.VU.vxsat->write(1);
p_rd = 0xFFFF;
} else {
p_rd = (uint16_t)shx;
}
}
})

23
riscv/insns/psshlr_ws.h

@ -0,0 +1,23 @@
require_rv64;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
P_RD_RS1_LOOP(32, 32, {
if (sshamt < 0) {
uint64_t shx;
if (sshamt < -32)
shx = 0;
else if (sshamt == -32)
shx = ((uint32_t)p_rs1 >> 31) & 1;
else
shx = ((uint64_t)(uint32_t)p_rs1 << 1) >> (-sshamt);
p_rd = (uint32_t)((shx + 1) >> 1);
} else {
uint64_t shx = (sshamt >= 32) ? ((uint64_t)(uint32_t)p_rs1 << 32) : ((uint64_t)(uint32_t)p_rs1 << sshamt);
if (shx > 0xFFFFFFFFULL) {
P.VU.vxsat->write(1);
p_rd = 0xFFFFFFFF;
} else {
p_rd = (uint32_t)shx;
}
}
})

15
riscv/insns/shl.h

@ -0,0 +1,15 @@
require_extension('P');
require_rv64;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
if (sshamt < 0) {
if (sshamt <= -64)
WRITE_RD(0);
else
WRITE_RD(RS1 >> (-sshamt));
} else {
if (sshamt >= 64)
WRITE_RD(0);
else
WRITE_RD(RS1 << sshamt);
}

19
riscv/insns/shlr.h

@ -0,0 +1,19 @@
require_extension('P');
require_rv64;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
if (sshamt < 0) {
__uint128_t shx;
if (sshamt < -64)
shx = 0;
else if (sshamt == -64)
shx = (RS1 >> 63) & 1;
else
shx = ((__uint128_t)RS1 << 1) >> (-sshamt);
WRITE_RD((uint64_t)((shx + 1) >> 1));
} else {
if (sshamt >= 64)
WRITE_RD(0);
else
WRITE_RD(RS1 << sshamt);
}

18
riscv/insns/sshl.h

@ -0,0 +1,18 @@
require_extension('P');
require_rv32;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
if (sshamt < 0) {
if (sshamt <= -32)
WRITE_RD(0);
else
WRITE_RD(RS1 >> (-sshamt));
} else {
uint64_t shx = (sshamt >= 32) ? ((uint64_t)RS1 << 32) : ((uint64_t)RS1 << sshamt);
if (shx > 0xFFFFFFFFULL) {
P.VU.vxsat->write(1);
WRITE_RD(0xFFFFFFFF);
} else {
WRITE_RD((uint32_t)shx);
}
}

22
riscv/insns/sshlr.h

@ -0,0 +1,22 @@
require_extension('P');
require_rv32;
sreg_t sshamt = P_FIELD(RS2, 0, 8);
if (sshamt < 0) {
uint64_t shx;
if (sshamt < -32)
shx = 0;
else if (sshamt == -32)
shx = (RS1 >> 31) & 1;
else
shx = ((uint64_t)RS1 << 1) >> (-sshamt);
WRITE_RD((uint32_t)((shx + 1) >> 1));
} else {
uint64_t shx = (sshamt >= 32) ? ((uint64_t)RS1 << 32) : ((uint64_t)RS1 << sshamt);
if (shx > 0xFFFFFFFFULL) {
P.VU.vxsat->write(1);
WRITE_RD(0xFFFFFFFF);
} else {
WRITE_RD((uint32_t)shx);
}
}

2
riscv/overlap_list.h

@ -93,3 +93,5 @@ DECLARE_OVERLAP_INSN(pmqacc_w_h11, 'P')
DECLARE_OVERLAP_INSN(pmqracc_w_h00, 'P')
DECLARE_OVERLAP_INSN(pmqracc_w_h01, 'P')
DECLARE_OVERLAP_INSN(pmqracc_w_h11, 'P')
DECLARE_OVERLAP_INSN(psshl_ws, 'P')
DECLARE_OVERLAP_INSN(psshlr_ws, 'P')

18
riscv/riscv.mk.in

@ -1741,6 +1741,24 @@ riscv_insn_ext_p = \
pmq2adda_w \
pmqr2add_w \
pmqr2adda_w \
sshl \
sshlr \
shl \
shlr \
psshl_hs \
psshlr_hs \
psshl_ws \
psshlr_ws \
psshl_dhs \
psshlr_dhs \
psshl_dws \
psshlr_dws \
pnclipp_b \
pnclipp_h \
pnclipp_w \
pnclipup_b \
pnclipup_h \
pnclipup_w \
riscv_insn_list = \
$(riscv_insn_ext_i) \

Loading…
Cancel
Save