aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTsukasa OI <research_trasio@irq.a4lg.com>2023-08-12 16:14:04 +0000
committerTsukasa OI <research_trasio@irq.a4lg.com>2023-08-15 06:46:18 +0000
commit239af8cbd15cd9ef11e333f9889834665066e4b3 (patch)
tree3950380006ea35b0425fcb5e638f4d1a19445ff7
parent2266f8631806ec65a9a9ff8a7c68a56c83eae81d (diff)
downloadbinutils-239af8cbd15cd9ef11e333f9889834665066e4b3.zip
binutils-239af8cbd15cd9ef11e333f9889834665066e4b3.tar.gz
binutils-239af8cbd15cd9ef11e333f9889834665066e4b3.tar.bz2
RISC-V: Make "fli.h" available to 'Zvfh' + 'Zfa'
The documentation of the 'Zfa' extension states that "fli.h" is available "if the Zfh or Zvfh extension is implemented" (both the latest and the oldest editions are checked). This fact was not reflected in Binutils ('Zvfh' implies 'Zfhmin', not full 'Zfh' extension and "fli.h" required 'Zfh' and 'Zfa' extensions). This commit makes "fli.h" also available when both 'Zfa' and 'Zvfh' extensions are implemented. bfd/ChangeLog: * elfxx-riscv.c (riscv_multi_subset_supports): Add new instruction class handling. (riscv_multi_subset_supports_ext): Likewise. gas/ChangeLog: * testsuite/gas/riscv/zfa-zvfh.s: New test. * testsuite/gas/riscv/zfa-zvfh.d: Ditto. include/ChangeLog: * opcode/riscv.h (enum riscv_insn_class): Add new instruction class. opcodes/ChangeLog: * riscv-opc.c (riscv_opcodes): Change instruction class of "fli.h" from INSN_CLASS_ZFH_AND_ZFA to new INSN_CLASS_ZFH_OR_ZVFH_AND_ZFA.
-rw-r--r--bfd/elfxx-riscv.c15
-rw-r--r--gas/testsuite/gas/riscv/zfa-zvfh.d16
-rw-r--r--gas/testsuite/gas/riscv/zfa-zvfh.s10
-rw-r--r--include/opcode/riscv.h1
-rw-r--r--opcodes/riscv-opc.c2
5 files changed, 43 insertions, 1 deletions
diff --git a/bfd/elfxx-riscv.c b/bfd/elfxx-riscv.c
index 6b34c2f..e9852ef 100644
--- a/bfd/elfxx-riscv.c
+++ b/bfd/elfxx-riscv.c
@@ -2463,6 +2463,10 @@ riscv_multi_subset_supports (riscv_parse_subset_t *rps,
case INSN_CLASS_ZFH_AND_ZFA:
return riscv_subset_supports (rps, "zfh")
&& riscv_subset_supports (rps, "zfa");
+ case INSN_CLASS_ZFH_OR_ZVFH_AND_ZFA:
+ return (riscv_subset_supports (rps, "zfh")
+ || riscv_subset_supports (rps, "zvfh"))
+ && riscv_subset_supports (rps, "zfa");
case INSN_CLASS_ZBA:
return riscv_subset_supports (rps, "zba");
case INSN_CLASS_ZBB:
@@ -2704,6 +2708,17 @@ riscv_multi_subset_supports_ext (riscv_parse_subset_t *rps,
return "zfh";
else
return "zfa";
+ case INSN_CLASS_ZFH_OR_ZVFH_AND_ZFA:
+ if (!riscv_subset_supports (rps, "zfa"))
+ {
+ if (!riscv_subset_supports (rps, "zfh")
+ && !riscv_subset_supports (rps, "zvfh"))
+ return _("zfh' and `zfa', or `zvfh' and `zfa");
+ else
+ return "zfa";
+ }
+ else
+ return _("zfh' or `zvfh");
case INSN_CLASS_ZBA:
return "zba";
case INSN_CLASS_ZBB:
diff --git a/gas/testsuite/gas/riscv/zfa-zvfh.d b/gas/testsuite/gas/riscv/zfa-zvfh.d
new file mode 100644
index 0000000..8fbe06c
--- /dev/null
+++ b/gas/testsuite/gas/riscv/zfa-zvfh.d
@@ -0,0 +1,16 @@
+#as: -march=rv32iq_zfa_zvfh
+#objdump: -d
+
+.*:[ ]+file format .*
+
+Disassembly of section .text:
+
+0+000 <target>:
+[ ]+[0-9a-f]+:[ ]+f41c00d3[ ]+fli\.h[ ]+ft1,0x1p\+3
+[ ]+[0-9a-f]+:[ ]+f41c80d3[ ]+fli\.h[ ]+ft1,0x1p\+4
+[ ]+[0-9a-f]+:[ ]+f41d00d3[ ]+fli\.h[ ]+ft1,0x1p\+7
+[ ]+[0-9a-f]+:[ ]+f41d80d3[ ]+fli\.h[ ]+ft1,0x1p\+8
+[ ]+[0-9a-f]+:[ ]+f41e00d3[ ]+fli\.h[ ]+ft1,0x1p\+15
+[ ]+[0-9a-f]+:[ ]+f41e80d3[ ]+fli\.h[ ]+ft1,0x1p\+16
+[ ]+[0-9a-f]+:[ ]+f41f00d3[ ]+fli\.h[ ]+ft1,inf
+[ ]+[0-9a-f]+:[ ]+f41f80d3[ ]+fli\.h[ ]+ft1,nan
diff --git a/gas/testsuite/gas/riscv/zfa-zvfh.s b/gas/testsuite/gas/riscv/zfa-zvfh.s
new file mode 100644
index 0000000..61c26e6
--- /dev/null
+++ b/gas/testsuite/gas/riscv/zfa-zvfh.s
@@ -0,0 +1,10 @@
+target:
+ # fli.h is available on (('Zfh' || 'Zvfh') && 'Zfa')
+ fli.h ft1, 8.0
+ fli.h ft1, 0x1p4
+ fli.h ft1, 128.0
+ fli.h ft1, 0x1p8
+ fli.h ft1, 32768.0
+ fli.h ft1, 0x1p16
+ fli.h ft1, inf
+ fli.h ft1, nan
diff --git a/include/opcode/riscv.h b/include/opcode/riscv.h
index 0b8fde9..38927bd 100644
--- a/include/opcode/riscv.h
+++ b/include/opcode/riscv.h
@@ -409,6 +409,7 @@ enum riscv_insn_class
INSN_CLASS_D_AND_ZFA,
INSN_CLASS_Q_AND_ZFA,
INSN_CLASS_ZFH_AND_ZFA,
+ INSN_CLASS_ZFH_OR_ZVFH_AND_ZFA,
INSN_CLASS_ZBA,
INSN_CLASS_ZBB,
INSN_CLASS_ZBC,
diff --git a/opcodes/riscv-opc.c b/opcodes/riscv-opc.c
index 02f993d..067e9fd 100644
--- a/opcodes/riscv-opc.c
+++ b/opcodes/riscv-opc.c
@@ -990,7 +990,7 @@ const struct riscv_opcode riscv_opcodes[] =
{"fli.s", 0, INSN_CLASS_ZFA, "D,Wfv", MATCH_FLI_S, MASK_FLI_S, match_opcode, 0 },
{"fli.d", 0, INSN_CLASS_D_AND_ZFA, "D,Wfv", MATCH_FLI_D, MASK_FLI_D, match_opcode, 0 },
{"fli.q", 0, INSN_CLASS_Q_AND_ZFA, "D,Wfv", MATCH_FLI_Q, MASK_FLI_Q, match_opcode, 0 },
-{"fli.h", 0, INSN_CLASS_ZFH_AND_ZFA, "D,Wfv", MATCH_FLI_H, MASK_FLI_H, match_opcode, 0 },
+{"fli.h", 0, INSN_CLASS_ZFH_OR_ZVFH_AND_ZFA, "D,Wfv", MATCH_FLI_H, MASK_FLI_H, match_opcode, 0 },
{"fminm.s", 0, INSN_CLASS_ZFA, "D,S,T", MATCH_FMINM_S, MASK_FMINM_S, match_opcode, 0 },
{"fmaxm.s", 0, INSN_CLASS_ZFA, "D,S,T", MATCH_FMAXM_S, MASK_FMAXM_S, match_opcode, 0 },
{"fminm.d", 0, INSN_CLASS_D_AND_ZFA, "D,S,T", MATCH_FMINM_D, MASK_FMINM_D, match_opcode, 0 },