mirror of
https://sourceware.org/git/binutils-gdb.git
synced 2024-11-23 10:03:47 +08:00
RISC-V: Add Zcmt instructions and csr.
This patch supports Zcmt[1] instruction 'cm.jt' and 'cm.jalt'. Add new CSR jvt for tablejump using. Since 'cm.jt' and 'cm.jalt' have the same instructiong encoding, use 'match_cm_jt' and 'match_cm_jalt' check the 'zcmt_index' field to distinguish them. [1] https://github.com/riscvarchive/riscv-code-size-reduction/releases Co-Authored by: Charlie Keaney <charlie.keaney@embecosm.com> Co-Authored by: Mary Bennett <mary.bennett@embecosm.com> Co-Authored by: Nandni Jamnadas <nandni.jamnadas@embecosm.com> Co-Authored by: Sinan Lin <sinan.lin@linux.alibaba.com> Co-Authored by: Simon Cook <simon.cook@embecosm.com> Co-Authored by: Shihua Liao <shihua@iscas.ac.cn> Co-Authored by: Yulong Shi <yulong@iscas.ac.cn> bfd/ChangeLog: * elfxx-riscv.c (riscv_multi_subset_supports): New extension. (riscv_multi_subset_supports_ext): Ditto. gas/ChangeLog: * config/tc-riscv.c (enum riscv_csr_class): New CSR. (riscv_csr_address): Ditto. (validate_riscv_insn): New operand. (riscv_ip): Ditto. * testsuite/gas/riscv/csr-version-1p10.d: New CSR. * testsuite/gas/riscv/csr-version-1p10.l: Ditto. * testsuite/gas/riscv/csr-version-1p11.d: Ditto. * testsuite/gas/riscv/csr-version-1p11.l: Ditto. * testsuite/gas/riscv/csr-version-1p12.d: Ditto. * testsuite/gas/riscv/csr-version-1p12.l: Ditto. * testsuite/gas/riscv/csr.s: Ditto. * testsuite/gas/riscv/march-help.l: New extension. * testsuite/gas/riscv/zcmt-fail.d: New test. * testsuite/gas/riscv/zcmt-fail.l: New test. * testsuite/gas/riscv/zcmt-fail.s: New test. * testsuite/gas/riscv/zcmt.d: New test. * testsuite/gas/riscv/zcmt.s: New test. include/ChangeLog: * opcode/riscv-opc.h (MATCH_CM_JT): New opcode. (MASK_CM_JT): New mask. (MATCH_CM_JALT): New opcode. (MASK_CM_JALT): New mask. (CSR_JVT): New CSR. (DECLARE_INSN): New declaration. (DECLARE_CSR): Ditto. * opcode/riscv.h (EXTRACT_ZCMT_INDEX): New marco. (ENCODE_ZCMT_INDEX): Ditto. (enum riscv_insn_class): New class. opcodes/ChangeLog: * riscv-dis.c (print_insn_args): New operand. * riscv-opc.c (match_cm_jt): New function. (match_cm_jalt): Ditto.
This commit is contained in:
parent
46e64f7387
commit
00ef37e860
@ -1214,6 +1214,7 @@ static struct riscv_implicit_subset riscv_implicit_subsets[] =
|
||||
{"zcf", "+f,+zca", check_implicit_always},
|
||||
{"zcmp", "+zca", check_implicit_always},
|
||||
{"zcmop", "+zca", check_implicit_always},
|
||||
{"zcmt", "+zca,+zicsr", check_implicit_always},
|
||||
|
||||
{"shcounterenw", "+h", check_implicit_always},
|
||||
{"shgatpa", "+h", check_implicit_always},
|
||||
@ -1424,6 +1425,7 @@ static struct riscv_supported_ext riscv_supported_std_z_ext[] =
|
||||
{"zcd", ISA_SPEC_CLASS_DRAFT, 1, 0, 0 },
|
||||
{"zcmop", ISA_SPEC_CLASS_DRAFT, 1, 0, 0 },
|
||||
{"zcmp", ISA_SPEC_CLASS_DRAFT, 1, 0, 0 },
|
||||
{"zcmt", ISA_SPEC_CLASS_DRAFT, 1, 0, 0 },
|
||||
{NULL, 0, 0, 0, 0}
|
||||
};
|
||||
|
||||
@ -2720,6 +2722,8 @@ riscv_multi_subset_supports (riscv_parse_subset_t *rps,
|
||||
return riscv_subset_supports (rps, "zcmop");
|
||||
case INSN_CLASS_ZCMP:
|
||||
return riscv_subset_supports (rps, "zcmp");
|
||||
case INSN_CLASS_ZCMT:
|
||||
return riscv_subset_supports (rps, "zcmt");
|
||||
case INSN_CLASS_SVINVAL:
|
||||
return riscv_subset_supports (rps, "svinval");
|
||||
case INSN_CLASS_H:
|
||||
@ -3002,6 +3006,8 @@ riscv_multi_subset_supports_ext (riscv_parse_subset_t *rps,
|
||||
return "zcmop";
|
||||
case INSN_CLASS_ZCMP:
|
||||
return "zcmp";
|
||||
case INSN_CLASS_ZCMT:
|
||||
return "zcmt";
|
||||
case INSN_CLASS_SVINVAL:
|
||||
return "svinval";
|
||||
case INSN_CLASS_H:
|
||||
|
@ -71,6 +71,7 @@ enum riscv_csr_class
|
||||
CSR_CLASS_I_32, /* rv32 only */
|
||||
CSR_CLASS_F, /* f-ext only */
|
||||
CSR_CLASS_ZKR, /* zkr only */
|
||||
CSR_CLASS_ZCMT, /* zcmt only */
|
||||
CSR_CLASS_V, /* rvv only */
|
||||
CSR_CLASS_DEBUG, /* debug CSR */
|
||||
CSR_CLASS_H, /* hypervisor */
|
||||
@ -1070,6 +1071,9 @@ riscv_csr_address (const char *csr_name,
|
||||
case CSR_CLASS_ZKR:
|
||||
extension = "zkr";
|
||||
break;
|
||||
case CSR_CLASS_ZCMT:
|
||||
extension = "zcmt";
|
||||
break;
|
||||
case CSR_CLASS_V:
|
||||
extension = "zve32x";
|
||||
break;
|
||||
@ -1650,6 +1654,9 @@ validate_riscv_insn (const struct riscv_opcode *opc, int length)
|
||||
case 'p': used_bits |= ENCODE_ZCMP_SPIMM (-1U); break;
|
||||
/* Register list operand for cm.push and cm.pop. */
|
||||
case 'r': USE_BITS (OP_MASK_REG_LIST, OP_SH_REG_LIST); break;
|
||||
/* Table jump used by cm.jt or cm.jalt. */
|
||||
case 'i':
|
||||
case 'I': used_bits |= ENCODE_ZCMT_INDEX (-1U); break;
|
||||
case 'f': break;
|
||||
default:
|
||||
goto unknown_validate_operand;
|
||||
@ -3922,6 +3929,28 @@ riscv_ip (char *str, struct riscv_cl_insn *ip, expressionS *imm_expr,
|
||||
break;
|
||||
INSERT_OPERAND (SREG2, *ip, regno % 8);
|
||||
continue;
|
||||
case 'I': /* index operand of cm.jt. The range is from 0 to 31. */
|
||||
my_getSmallExpression (imm_expr, imm_reloc, asarg, p);
|
||||
if (imm_expr->X_op != O_constant
|
||||
|| imm_expr->X_add_number < 0
|
||||
|| imm_expr->X_add_number > 31)
|
||||
{
|
||||
as_bad ("bad index value for cm.jt, range: [0, 31]");
|
||||
break;
|
||||
}
|
||||
ip->insn_opcode |= ENCODE_ZCMT_INDEX (imm_expr->X_add_number);
|
||||
goto rvc_imm_done;
|
||||
case 'i': /* index operand of cm.jalt. The range is from 32 to 255. */
|
||||
my_getSmallExpression (imm_expr, imm_reloc, asarg, p);
|
||||
if (imm_expr->X_op != O_constant
|
||||
|| imm_expr->X_add_number < 32
|
||||
|| imm_expr->X_add_number > 255)
|
||||
{
|
||||
as_bad ("bad index value for cm.jalt, range: [32, 255]");
|
||||
break;
|
||||
}
|
||||
ip->insn_opcode |= ENCODE_ZCMT_INDEX (imm_expr->X_add_number);
|
||||
goto rvc_imm_done;
|
||||
default:
|
||||
goto unknown_riscv_ip_operand;
|
||||
}
|
||||
|
@ -919,3 +919,5 @@ Disassembly of section .text:
|
||||
[ ]+[0-9a-f]+:[ ]+c2159073[ ]+csrw[ ]+vtype,a1
|
||||
[ ]+[0-9a-f]+:[ ]+c2202573[ ]+csrr[ ]+a0,vlenb
|
||||
[ ]+[0-9a-f]+:[ ]+c2259073[ ]+csrw[ ]+vlenb,a1
|
||||
[ ]+[0-9a-f]+:[ ]+01702573[ ]+csrr[ ]+a0,jvt
|
||||
[ ]+[0-9a-f]+:[ ]+01759073[ ]+csrw[ ]+jvt,a1
|
||||
|
@ -1689,3 +1689,7 @@
|
||||
.*Info: macro .*
|
||||
.*Warning: read-only CSR is written `csrw vlenb,a1'
|
||||
.*Info: macro .*
|
||||
.*Warning: invalid CSR `jvt', needs `zcmt' extension
|
||||
.*Info: macro .*
|
||||
.*Warning: invalid CSR `jvt', needs `zcmt' extension
|
||||
.*Info: macro .*
|
||||
|
@ -919,3 +919,5 @@ Disassembly of section .text:
|
||||
[ ]+[0-9a-f]+:[ ]+c2159073[ ]+csrw[ ]+vtype,a1
|
||||
[ ]+[0-9a-f]+:[ ]+c2202573[ ]+csrr[ ]+a0,vlenb
|
||||
[ ]+[0-9a-f]+:[ ]+c2259073[ ]+csrw[ ]+vlenb,a1
|
||||
[ ]+[0-9a-f]+:[ ]+01702573[ ]+csrr[ ]+a0,jvt
|
||||
[ ]+[0-9a-f]+:[ ]+01759073[ ]+csrw[ ]+jvt,a1
|
||||
|
@ -1685,3 +1685,7 @@
|
||||
.*Info: macro .*
|
||||
.*Warning: read-only CSR is written `csrw vlenb,a1'
|
||||
.*Info: macro .*
|
||||
.*Warning: invalid CSR `jvt', needs `zcmt' extension
|
||||
.*Info: macro .*
|
||||
.*Warning: invalid CSR `jvt', needs `zcmt' extension
|
||||
.*Info: macro .*
|
||||
|
@ -919,3 +919,5 @@ Disassembly of section .text:
|
||||
[ ]+[0-9a-f]+:[ ]+c2159073[ ]+csrw[ ]+vtype,a1
|
||||
[ ]+[0-9a-f]+:[ ]+c2202573[ ]+csrr[ ]+a0,vlenb
|
||||
[ ]+[0-9a-f]+:[ ]+c2259073[ ]+csrw[ ]+vlenb,a1
|
||||
[ ]+[0-9a-f]+:[ ]+01702573[ ]+csrr[ ]+a0,jvt
|
||||
[ ]+[0-9a-f]+:[ ]+01759073[ ]+csrw[ ]+jvt,a1
|
||||
|
@ -1449,3 +1449,7 @@
|
||||
.*Info: macro .*
|
||||
.*Warning: read-only CSR is written `csrw vlenb,a1'
|
||||
.*Info: macro .*
|
||||
.*Warning: invalid CSR `jvt', needs `zcmt' extension
|
||||
.*Info: macro .*
|
||||
.*Warning: invalid CSR `jvt', needs `zcmt' extension
|
||||
.*Info: macro .*
|
||||
|
@ -528,3 +528,6 @@
|
||||
csr vl
|
||||
csr vtype
|
||||
csr vlenb
|
||||
|
||||
# Zcmt
|
||||
csr jvt
|
||||
|
@ -104,6 +104,7 @@ All available -march extensions for RISC-V:
|
||||
zcd 1.0
|
||||
zcmop 1.0
|
||||
zcmp 1.0
|
||||
zcmt 1.0
|
||||
shcounterenw 1.0
|
||||
shgatpa 1.0
|
||||
shtvala 1.0
|
||||
|
3
gas/testsuite/gas/riscv/zcmt-fail.d
Normal file
3
gas/testsuite/gas/riscv/zcmt-fail.d
Normal file
@ -0,0 +1,3 @@
|
||||
#as: -march=rv64i_zcmt
|
||||
#source: zcmt-fail.s
|
||||
#error_output: zcmt-fail.l
|
13
gas/testsuite/gas/riscv/zcmt-fail.l
Normal file
13
gas/testsuite/gas/riscv/zcmt-fail.l
Normal file
@ -0,0 +1,13 @@
|
||||
.*: Assembler messages:
|
||||
.*: Error: bad index value for cm.jt, range: \[0, 31\]
|
||||
.*: Error: illegal operands `cm.jt -1'
|
||||
.*: Error: bad index value for cm.jt, range: \[0, 31\]
|
||||
.*: Error: illegal operands `cm.jt 256'
|
||||
.*: Error: bad index value for cm.jt, range: \[0, 31\]
|
||||
.*: Error: illegal operands `cm.jt x0'
|
||||
.*: Error: bad index value for cm.jalt, range: \[32, 255\]
|
||||
.*: Error: illegal operands `cm.jalt -1'
|
||||
.*: Error: bad index value for cm.jalt, range: \[32, 255\]
|
||||
.*: Error: illegal operands `cm.jalt 256'
|
||||
.*: Error: bad index value for cm.jalt, range: \[32, 255\]
|
||||
.*: Error: illegal operands `cm.jalt x0'
|
7
gas/testsuite/gas/riscv/zcmt-fail.s
Normal file
7
gas/testsuite/gas/riscv/zcmt-fail.s
Normal file
@ -0,0 +1,7 @@
|
||||
target:
|
||||
cm.jt -1
|
||||
cm.jt 256
|
||||
cm.jt x0
|
||||
cm.jalt -1
|
||||
cm.jalt 256
|
||||
cm.jalt x0
|
14
gas/testsuite/gas/riscv/zcmt.d
Normal file
14
gas/testsuite/gas/riscv/zcmt.d
Normal file
@ -0,0 +1,14 @@
|
||||
#as: -march=rv32i_zcmt
|
||||
#source: zcmt.s
|
||||
#objdump: -dr -Mno-aliases
|
||||
|
||||
.*:[ ]+file format .*
|
||||
|
||||
|
||||
Disassembly of section .text:
|
||||
|
||||
0+000 <target>:
|
||||
[ ]*[0-9a-f]+:[ ]+a002[ ]+cm.jt[ ]+0
|
||||
[ ]*[0-9a-f]+:[ ]+a07e[ ]+cm.jt[ ]+31
|
||||
[ ]*[0-9a-f]+:[ ]+a102[ ]+cm.jalt[ ]+64
|
||||
[ ]*[0-9a-f]+:[ ]+a3fe[ ]+cm.jalt[ ]+255
|
5
gas/testsuite/gas/riscv/zcmt.s
Normal file
5
gas/testsuite/gas/riscv/zcmt.s
Normal file
@ -0,0 +1,5 @@
|
||||
target:
|
||||
cm.jt 0
|
||||
cm.jt 31
|
||||
cm.jalt 64
|
||||
cm.jalt 255
|
@ -2305,6 +2305,11 @@
|
||||
#define MASK_CM_MVA01S 0xfc63
|
||||
#define MATCH_CM_MVSA01 0xac22
|
||||
#define MASK_CM_MVSA01 0xfc63
|
||||
/* Zcmt instructions. */
|
||||
#define MATCH_CM_JT 0xa002
|
||||
#define MASK_CM_JT 0xfc03
|
||||
#define MATCH_CM_JALT 0xa002
|
||||
#define MASK_CM_JALT 0xfc03
|
||||
/* Svinval instruction. */
|
||||
#define MATCH_SINVAL_VMA 0x16000073
|
||||
#define MASK_SINVAL_VMA 0xfe007fff
|
||||
@ -4190,6 +4195,8 @@
|
||||
#define CSR_MSCONTEXT 0x7aa
|
||||
/* Unprivileged Scalar Crypto CSR addresses. */
|
||||
#define CSR_SEED 0x015
|
||||
/* Unprivileged Zcmt CSR addresses. */
|
||||
#define CSR_JVT 0x017
|
||||
/* Unprivileged Vector CSR addresses. */
|
||||
#define CSR_VSTART 0x008
|
||||
#define CSR_VXSAT 0x009
|
||||
@ -4731,6 +4738,9 @@ DECLARE_INSN(cm_popret, MATCH_CM_POPRET, MASK_CM_POPRET)
|
||||
DECLARE_INSN(cm_popretz, MATCH_CM_POPRETZ, MASK_CM_POPRETZ)
|
||||
DECLARE_INSN(cm_mvsa01, MATCH_CM_MVSA01, MASK_CM_MVSA01)
|
||||
DECLARE_INSN(cm_mva01s, MATCH_CM_MVA01S, MASK_CM_MVA01S)
|
||||
/* Zcmt instructions. */
|
||||
DECLARE_INSN(cm_jt, MATCH_CM_JT, MASK_CM_JT)
|
||||
DECLARE_INSN(cm_jalt, MATCH_CM_JALT, MASK_CM_JALT)
|
||||
/* Vendor-specific (T-Head) XTheadBa instructions. */
|
||||
DECLARE_INSN(th_addsl, MATCH_TH_ADDSL, MASK_TH_ADDSL)
|
||||
/* Vendor-specific (T-Head) XTheadBb instructions. */
|
||||
@ -5304,6 +5314,8 @@ DECLARE_CSR(mcontext, CSR_MCONTEXT, CSR_CLASS_DEBUG, PRIV_SPEC_CLASS_NONE, PRIV_
|
||||
DECLARE_CSR(mscontext, CSR_MSCONTEXT, CSR_CLASS_DEBUG, PRIV_SPEC_CLASS_NONE, PRIV_SPEC_CLASS_NONE)
|
||||
/* Unprivileged Scalar Crypto CSRs. */
|
||||
DECLARE_CSR(seed, CSR_SEED, CSR_CLASS_ZKR, PRIV_SPEC_CLASS_NONE, PRIV_SPEC_CLASS_NONE)
|
||||
/* Unprivileged Zcmt CSRs. */
|
||||
DECLARE_CSR(jvt, CSR_JVT, CSR_CLASS_ZCMT, PRIV_SPEC_CLASS_NONE, PRIV_SPEC_CLASS_NONE)
|
||||
/* Unprivileged Vector CSRs. */
|
||||
DECLARE_CSR(vstart, CSR_VSTART, CSR_CLASS_V, PRIV_SPEC_CLASS_NONE, PRIV_SPEC_CLASS_NONE)
|
||||
DECLARE_CSR(vxsat, CSR_VXSAT, CSR_CLASS_V, PRIV_SPEC_CLASS_NONE, PRIV_SPEC_CLASS_NONE)
|
||||
|
@ -115,6 +115,8 @@ static inline unsigned int riscv_insn_length (insn_t insn)
|
||||
(RV_X(x, 5, 1) << 1)
|
||||
#define EXTRACT_ZCMP_SPIMM(x) \
|
||||
(RV_X(x, 2, 2) << 4)
|
||||
#define EXTRACT_ZCMT_INDEX(x) \
|
||||
(RV_X(x, 2, 8))
|
||||
/* Vendor-specific (CORE-V) extract macros. */
|
||||
#define EXTRACT_CV_IS2_UIMM5(x) \
|
||||
(RV_X(x, 20, 5))
|
||||
@ -183,6 +185,8 @@ static inline unsigned int riscv_insn_length (insn_t insn)
|
||||
(RV_X(x, 1, 1) << 5)
|
||||
#define ENCODE_ZCMP_SPIMM(x) \
|
||||
(RV_X(x, 4, 2) << 2)
|
||||
#define ENCODE_ZCMT_INDEX(x) \
|
||||
(RV_X(x, 0, 8) << 2)
|
||||
/* Vendor-specific (CORE-V) encode macros. */
|
||||
#define ENCODE_CV_IS2_UIMM5(x) \
|
||||
(RV_X(x, 0, 5) << 20)
|
||||
@ -517,6 +521,7 @@ enum riscv_insn_class
|
||||
INSN_CLASS_ZCB_AND_ZMMUL,
|
||||
INSN_CLASS_ZCMOP,
|
||||
INSN_CLASS_ZCMP,
|
||||
INSN_CLASS_ZCMT,
|
||||
INSN_CLASS_SVINVAL,
|
||||
INSN_CLASS_ZICBOM,
|
||||
INSN_CLASS_ZICBOP,
|
||||
|
@ -737,6 +737,11 @@ print_insn_args (const char *oparg, insn_t l, bfd_vma pc, disassemble_info *info
|
||||
print (info->stream, dis_style_immediate, "%d",
|
||||
riscv_get_spimm (l));
|
||||
break;
|
||||
case 'i':
|
||||
case 'I':
|
||||
print (info->stream, dis_style_address_offset,
|
||||
"%lu", EXTRACT_ZCMT_INDEX (l));
|
||||
break;
|
||||
default:
|
||||
goto undefined_modifier;
|
||||
}
|
||||
|
@ -362,6 +362,25 @@ match_sreg1_not_eq_sreg2 (const struct riscv_opcode *op, insn_t insn)
|
||||
&& (EXTRACT_OPERAND (SREG1, insn) != EXTRACT_OPERAND (SREG2, insn));
|
||||
}
|
||||
|
||||
/* This is used for cm.jt. This requires index operand to be less than 32. */
|
||||
|
||||
static int
|
||||
match_cm_jt (const struct riscv_opcode *op, insn_t insn)
|
||||
{
|
||||
return match_opcode (op, insn)
|
||||
&& EXTRACT_ZCMT_INDEX (insn) < 32;
|
||||
}
|
||||
|
||||
/* This is used for cm.jalt. This requires index operand to be in 32 to 255. */
|
||||
|
||||
static int
|
||||
match_cm_jalt (const struct riscv_opcode *op, insn_t insn)
|
||||
{
|
||||
return match_opcode (op, insn)
|
||||
&& EXTRACT_ZCMT_INDEX (insn) >= 32
|
||||
&& EXTRACT_ZCMT_INDEX (insn) < 256;
|
||||
}
|
||||
|
||||
/* The order of overloaded instructions matters. Label arguments and
|
||||
register arguments look the same. Instructions that can have either
|
||||
for arguments must apear in the correct order in this table for the
|
||||
@ -2196,6 +2215,10 @@ const struct riscv_opcode riscv_opcodes[] =
|
||||
{"cm.mva01s", 0, INSN_CLASS_ZCMP, "Wc1,Wc2", MATCH_CM_MVA01S, MASK_CM_MVA01S, match_opcode, 0 },
|
||||
{"cm.mvsa01", 0, INSN_CLASS_ZCMP, "Wc1,Wc2", MATCH_CM_MVSA01, MASK_CM_MVSA01, match_sreg1_not_eq_sreg2, 0 },
|
||||
|
||||
/* Zcmt instructions */
|
||||
{"cm.jt", 0, INSN_CLASS_ZCMT, "WcI", MATCH_CM_JT, MASK_CM_JT, match_cm_jt, 0 },
|
||||
{"cm.jalt", 0, INSN_CLASS_ZCMT, "Wci", MATCH_CM_JALT, MASK_CM_JALT, match_cm_jalt, 0 },
|
||||
|
||||
/* Supervisor instructions. */
|
||||
{"csrr", 0, INSN_CLASS_ZICSR, "d,E", MATCH_CSRRS, MASK_CSRRS|MASK_RS1, match_opcode, INSN_ALIAS },
|
||||
{"csrwi", 0, INSN_CLASS_ZICSR, "E,Z", MATCH_CSRRWI, MASK_CSRRWI|MASK_RD, match_opcode, INSN_ALIAS },
|
||||
|
Loading…
Reference in New Issue
Block a user