[v3,04/13] bfd/RISC-V: Zv{b,k}* imply Zve32x

Message ID 0450f2b8-fa5b-4921-b330-d9fe2e2c54b2@suse.com
State New
Headers
Series RISC-V: assorted fixes and (hopefully) improvements |

Commit Message

Jan Beulich June 19, 2026, 11:48 a.m. UTC
  The specification is quite explicit about this.
---
Is the placement of "zve32x" after "zvbb" / "zvbc" actually correct? While
riscv_compare_subsets() indeed does a mere strcasecmp() past "zv", it
seems unlikely to be mere chance that Zve* come ahead of all other Zv* in
riscv_supported_std_z_ext[].
---
v3: New.
  

Comments

Jiawei June 22, 2026, 8:47 a.m. UTC | #1
Hi Jan,

I checked this locally with current binutils using as-new/readelf.

For the ordering question, the canonical order does not seem to come 
from the
order in riscv_supported_std_z_ext[]. riscv_compare_subsets() compares Z
extensions by the character after 'z' and then by a case-insensitive suffix
comparison. For Zv* extensions, this means the current canonical order is
roughly:

zvbb, zvbc, zve32x, zvkb, zvkg, zvkn*, zvks*

The assembler/readelf tests confirm this. For example, both

-march=rv32i_zvbc_zve32x
-march=rv32i_zve32x_zvbc

are canonicalized with zvbc before zve32x, while zvkb/zvkg/zvkn*/zvks* are
placed after zve32x. So the ordering in the updated imply.d output looks
consistent with the current canonicalization rule.

However, while testing the implied-dependency change, I noticed another
possible issue. With the new implicit rows, an input such as

-march=rv32i_zvbc

is canonicalized as:

rv32i2p1_zvbc1p0_zve32x1p0

whereas explicitly specifying zve32x, for example

-march=rv32i_zvbc_zve32x

produces:

rv32i2p1_zicsr2p0_zvbc1p0_zve32x1p0_zvl32b1p0

So adding zve32x through the new Zv{b,k}* implication does not seem to 
trigger
the further dependencies normally implied by zve32x. This looks like it may
come from the implicit-subset processing order / single forward scan.

Therefore, I think the canonical placement of zve32x in the test is correct
for the current ordering rule, but we may need to clarify whether the 
implied
dependency should also pull in the full zve32x dependency closure.

BR,
Jiawei

On 2026/6/19 19:48, Jan Beulich wrote:
> The specification is quite explicit about this.
> ---
> Is the placement of "zve32x" after "zvbb" / "zvbc" actually correct? While
> riscv_compare_subsets() indeed does a mere strcasecmp() past "zv", it
> seems unlikely to be mere chance that Zve* come ahead of all other Zv* in
> riscv_supported_std_z_ext[].
> ---
> v3: New.
>
> --- a/bfd/elfxx-riscv.c
> +++ b/bfd/elfxx-riscv.c
> @@ -1306,6 +1306,15 @@ static const struct riscv_implicit_subse
>     {"zvksc", "+zvks,+zvbc", check_implicit_always},
>     {"zvks", "+zvksed,+zvksh,+zvkb,+zvkt", check_implicit_always},
>   
> +  {"zvbc", "+zve32x", check_implicit_always},
> +  {"zvkb", "+zve32x", check_implicit_always},
> +  {"zvkg", "+zve32x", check_implicit_always},
> +  {"zvkned", "+zve32x", check_implicit_always},
> +  {"zvknha", "+zve32x", check_implicit_always},
> +  {"zvknhb", "+zve32x", check_implicit_always},
> +  {"zvksed", "+zve32x", check_implicit_always},
> +  {"zvksh", "+zve32x", check_implicit_always},
> +
>     {"sdtrig", "+zicsr", check_implicit_always},
>   
>     {"smaia", "+ssaia", check_implicit_always},
> --- a/gas/testsuite/gas/riscv/imply.d
> +++ b/gas/testsuite/gas/riscv/imply.d
> @@ -87,13 +87,13 @@ SYMBOL TABLE:
>   [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zk1p0_zkn1p0_zknd1p0_zkne1p0_zknh1p0_zkr1p0_zkt1p0
>   [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zkn1p0_zknd1p0_zkne1p0_zknh1p0
>   [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zks1p0_zksed1p0_zksh1p0
> -[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbb1p0_zvkb1p0
> -[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvkg1p0_zvkn1p0_zvkned1p0_zvkng1p0_zvknhb1p0_zvkt1p0
> -[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zvkb1p0_zvkn1p0_zvknc1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> -[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvkn1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> -[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvkg1p0_zvks1p0_zvksed1p0_zvksg1p0_zvksh1p0_zvkt1p0
> -[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zvkb1p0_zvks1p0_zvksc1p0_zvksed1p0_zvksh1p0_zvkt1p0
> -[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvks1p0_zvksed1p0_zvksh1p0_zvkt1p0
> +[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbb1p0_zve32x1p0_zvkb1p0
> +[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkg1p0_zvkn1p0_zvkned1p0_zvkng1p0_zvknhb1p0_zvkt1p0
> +[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zve32x1p0_zvkb1p0_zvkn1p0_zvknc1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> +[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkn1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> +[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkg1p0_zvks1p0_zvksed1p0_zvksg1p0_zvksh1p0_zvkt1p0
> +[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zve32x1p0_zvkb1p0_zvks1p0_zvksc1p0_zvksed1p0_zvksh1p0_zvkt1p0
> +[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvks1p0_zvksed1p0_zvksh1p0_zvkt1p0
>   [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zicsr2p0_sdtrig1p0
>   [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zicsr2p0_smaia1p0_ssaia1p0
>   [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zicsr2p0_smcdeleg1p0_ssccfg1p0_sscsrind1p0
  
Jan Beulich June 22, 2026, 9:31 a.m. UTC | #2
On 22.06.2026 10:47, Jiawei wrote:
> I checked this locally with current binutils using as-new/readelf.
> 
> For the ordering question, the canonical order does not seem to come 
> from the
> order in riscv_supported_std_z_ext[]. riscv_compare_subsets() compares Z
> extensions by the character after 'z' and then by a case-insensitive suffix
> comparison. For Zv* extensions, this means the current canonical order is
> roughly:
> 
> zvbb, zvbc, zve32x, zvkb, zvkg, zvkn*, zvks*
> 
> The assembler/readelf tests confirm this. For example, both
> 
> -march=rv32i_zvbc_zve32x
> -march=rv32i_zve32x_zvbc
> 
> are canonicalized with zvbc before zve32x, while zvkb/zvkg/zvkn*/zvks* are
> placed after zve32x. So the ordering in the updated imply.d output looks
> consistent with the current canonicalization rule.
> 
> However, while testing the implied-dependency change, I noticed another
> possible issue. With the new implicit rows, an input such as
> 
> -march=rv32i_zvbc
> 
> is canonicalized as:
> 
> rv32i2p1_zvbc1p0_zve32x1p0
> 
> whereas explicitly specifying zve32x, for example
> 
> -march=rv32i_zvbc_zve32x
> 
> produces:
> 
> rv32i2p1_zicsr2p0_zvbc1p0_zve32x1p0_zvl32b1p0
> 
> So adding zve32x through the new Zv{b,k}* implication does not seem to 
> trigger
> the further dependencies normally implied by zve32x. This looks like it may
> come from the implicit-subset processing order / single forward scan.

So this comment

/* Please added in order since this table is only run once time.  */

really is misleading. "in order" doesn't quite get it, as apparently only
forward references are permitted within the table. That then means that
the patch needs to move up the whole Zv{b,k} group as well.

Jan
  
Nelson Chu July 21, 2026, 2:24 a.m. UTC | #3
On Fri, Jun 19, 2026 at 7:48 PM Jan Beulich <jbeulich@suse.com> wrote:
>
> The specification is quite explicit about this.

OK, thanks.  As for ...

> Is the placement of "zve32x" after "zvbb" / "zvbc" actually correct? While
> riscv_compare_subsets() indeed does a mere strcasecmp() past "zv", it
> seems unlikely to be mere chance that Zve* come ahead of all other Zv* in
> riscv_supported_std_z_ext[].

... I checked the ISA spec again from here,
https://github.com/riscv/riscv-isa-manual/blob/main/src/unpriv/naming.adoc#additional-standard-unprivileged-extension-names,

"If multiple ext:z[] extensions are named, they should be ordered
first by category, then alphabetically within a category — for
example, Zicsr_Zifencei_Ztso"
So I think since the alphabetical order, zve* should be placed after
zvb*.  The order of riscv_supported_* tables doesn't affect the final
output, but it would be good to be maintained in the right order.

Btw (not related to this patch), the spec also said "The name must end
with an alphabetical character. The second letter from the end cannot
be numeric if the last letter is p".  I recall that some of the
ratified extensions violate this rule by ending with a number, though
I forget exactly which ones. In any case, unless the spec has been
updated, I personally wouldn't want to see them forced into
binutils...

Thanks
Nelson

>
> --- a/bfd/elfxx-riscv.c
> +++ b/bfd/elfxx-riscv.c
> @@ -1306,6 +1306,15 @@ static const struct riscv_implicit_subse
>    {"zvksc", "+zvks,+zvbc", check_implicit_always},
>    {"zvks", "+zvksed,+zvksh,+zvkb,+zvkt", check_implicit_always},
>
> +  {"zvbc", "+zve32x", check_implicit_always},
> +  {"zvkb", "+zve32x", check_implicit_always},
> +  {"zvkg", "+zve32x", check_implicit_always},
> +  {"zvkned", "+zve32x", check_implicit_always},
> +  {"zvknha", "+zve32x", check_implicit_always},
> +  {"zvknhb", "+zve32x", check_implicit_always},
> +  {"zvksed", "+zve32x", check_implicit_always},
> +  {"zvksh", "+zve32x", check_implicit_always},
> +
>    {"sdtrig", "+zicsr", check_implicit_always},
>
>    {"smaia", "+ssaia", check_implicit_always},
> --- a/gas/testsuite/gas/riscv/imply.d
> +++ b/gas/testsuite/gas/riscv/imply.d
> @@ -87,13 +87,13 @@ SYMBOL TABLE:
>  [0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zk1p0_zkn1p0_zknd1p0_zkne1p0_zknh1p0_zkr1p0_zkt1p0
>  [0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zkn1p0_zknd1p0_zkne1p0_zknh1p0
>  [0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zks1p0_zksed1p0_zksh1p0
> -[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvbb1p0_zvkb1p0
> -[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvkb1p0_zvkg1p0_zvkn1p0_zvkned1p0_zvkng1p0_zvknhb1p0_zvkt1p0
> -[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvbc1p0_zvkb1p0_zvkn1p0_zvknc1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> -[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvkb1p0_zvkn1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> -[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvkb1p0_zvkg1p0_zvks1p0_zvksed1p0_zvksg1p0_zvksh1p0_zvkt1p0
> -[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvbc1p0_zvkb1p0_zvks1p0_zvksc1p0_zvksed1p0_zvksh1p0_zvkt1p0
> -[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvkb1p0_zvks1p0_zvksed1p0_zvksh1p0_zvkt1p0
> +[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvbb1p0_zve32x1p0_zvkb1p0
> +[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkg1p0_zvkn1p0_zvkned1p0_zvkng1p0_zvknhb1p0_zvkt1p0
> +[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvbc1p0_zve32x1p0_zvkb1p0_zvkn1p0_zvknc1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> +[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkn1p0_zvkned1p0_zvknhb1p0_zvkt1p0
> +[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkg1p0_zvks1p0_zvksed1p0_zvksg1p0_zvksh1p0_zvkt1p0
> +[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zvbc1p0_zve32x1p0_zvkb1p0_zvks1p0_zvksc1p0_zvksed1p0_zvksh1p0_zvkt1p0
> +[0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvks1p0_zvksed1p0_zvksh1p0_zvkt1p0
>  [0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zicsr2p0_sdtrig1p0
>  [0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zicsr2p0_smaia1p0_ssaia1p0
>  [0-9a-f]+ l       .text        0+000 \$xrv32i2p1_zicsr2p0_smcdeleg1p0_ssccfg1p0_sscsrind1p0
>
  
Jan Beulich July 21, 2026, 6:35 a.m. UTC | #4
On 21.07.2026 04:24, Nelson Chu wrote:
> On Fri, Jun 19, 2026 at 7:48 PM Jan Beulich <jbeulich@suse.com> wrote:
>>
>> The specification is quite explicit about this.
> 
> OK, thanks.

Hmm, thanks, but you giving an okay here contradicts what you say / quote
below. (Plus, see below, the v3 arrangement is wrong anyway.)

>  As for ...
> 
>> Is the placement of "zve32x" after "zvbb" / "zvbc" actually correct? While
>> riscv_compare_subsets() indeed does a mere strcasecmp() past "zv", it
>> seems unlikely to be mere chance that Zve* come ahead of all other Zv* in
>> riscv_supported_std_z_ext[].
> 
> ... I checked the ISA spec again from here,
> https://github.com/riscv/riscv-isa-manual/blob/main/src/unpriv/naming.adoc#additional-standard-unprivileged-extension-names,
> 
> "If multiple ext:z[] extensions are named, they should be ordered
> first by category, then alphabetically within a category — for
> example, Zicsr_Zifencei_Ztso"
> So I think since the alphabetical order, zve* should be placed after
> zvb*.

Well, first of all we need to heed the comment ahead of the table, no
matter how cryptic / vague / ambiguous it is:

/* Please added in order since this table is only run once time.  */

zve* _must_ come after everything mentioning it as a dependency. Hence
in v4 it now is:

--- a/bfd/elfxx-riscv.c
+++ b/bfd/elfxx-riscv.c
@@ -1239,11 +1239,30 @@ static const struct riscv_implicit_subse
   {"zvfhmin", "+zve32f", check_implicit_always},
   {"zvfbfwma", "+zfbfmin,+zvfbfmin", check_implicit_always},
   {"zvfbfmin", "+zve32f", check_implicit_always},
+
+  {"zvbb", "+zvkb", check_implicit_always},
+  {"zvkng", "+zvkn,+zvkg", check_implicit_always},
+  {"zvknc", "+zvkn,+zvbc", check_implicit_always},
+  {"zvkn", "+zvkned,+zvknhb,+zvkb,+zvkt", check_implicit_always},
+  {"zvksg", "+zvks,+zvkg", check_implicit_always},
+  {"zvksc", "+zvks,+zvbc", check_implicit_always},
+  {"zvks", "+zvksed,+zvksh,+zvkb,+zvkt", check_implicit_always},
+
+  {"zvbc", "+zve32x", check_implicit_always},
+  {"zvkb", "+zve32x", check_implicit_always},
+  {"zvkg", "+zve32x", check_implicit_always},
+  {"zvkned", "+zve32x", check_implicit_always},
+  {"zvknha", "+zve32x", check_implicit_always},
+  {"zvknhb", "+zve32x", check_implicit_always},
+  {"zvksed", "+zve32x", check_implicit_always},
+  {"zvksh", "+zve32x", check_implicit_always},
+
   {"zve64d", "+d,+zve64f", check_implicit_always},
   {"zve64f", "+zve32f,+zve64x,+zvl64b", check_implicit_always},
   {"zve32f", "+f,+zve32x,+zvl32b", check_implicit_always},
   {"zve64x", "+zve32x,+zvl64b", check_implicit_always},
   {"zve32x", "+zvl32b,+zicsr", check_implicit_always},
+
   {"zvl65536b", "+zvl32768b", check_implicit_always},
   {"zvl32768b", "+zvl16384b", check_implicit_always},
   {"zvl16384b", "+zvl8192b", check_implicit_always},
@@ -1303,13 +1322,6 @@ static const struct riscv_implicit_subse
   {"zk", "+zkn,+zkr,+zkt", check_implicit_always},
   {"zkn", "+zbkb,+zbkc,+zbkx,+zkne,+zknd,+zknh", check_implicit_always},
   {"zks", "+zbkb,+zbkc,+zbkx,+zksed,+zksh", check_implicit_always},
-  {"zvbb", "+zvkb", check_implicit_always},
-  {"zvkng", "+zvkn,+zvkg", check_implicit_always},
-  {"zvknc", "+zvkn,+zvbc", check_implicit_always},
-  {"zvkn", "+zvkned,+zvknhb,+zvkb,+zvkt", check_implicit_always},
-  {"zvksg", "+zvks,+zvkg", check_implicit_always},
-  {"zvksc", "+zvks,+zvbc", check_implicit_always},
-  {"zvks", "+zvksed,+zvksh,+zvkb,+zvkt", check_implicit_always},
 
   {"sdtrig", "+zicsr", check_implicit_always},
 

This requirement also gets in the way of alphabetical sorting (e.g.
zvknc has to come ahead of zvbc). Yet of course the term "category"
is fuzzy as well. Given the v4 hunks above, what supposed order is
it that you read out of the text you quote? What exactly are the
"categories" specifically here?

And then, is e.g. zk* coming after zv* correct? That's hard to tell
already simply because there's V as an extension, but there's no K.
Or is e.g. zicntr and zihpm living very early in the table not
requiring not calling for zicfilp / zicfiss to move up as well? Or
wouldn't zclsd then belong together with zcd and zcf? C / Zc* in
particular mix pretty unhelpfully with other extensions, when it
comes to determining "categories".

>  The order of riscv_supported_* tables doesn't affect the final
> output, but it would be good to be maintained in the right order.

Right, but that of riscv_implicit_subsets[] does.

Jan
  

Patch

--- a/bfd/elfxx-riscv.c
+++ b/bfd/elfxx-riscv.c
@@ -1306,6 +1306,15 @@  static const struct riscv_implicit_subse
   {"zvksc", "+zvks,+zvbc", check_implicit_always},
   {"zvks", "+zvksed,+zvksh,+zvkb,+zvkt", check_implicit_always},
 
+  {"zvbc", "+zve32x", check_implicit_always},
+  {"zvkb", "+zve32x", check_implicit_always},
+  {"zvkg", "+zve32x", check_implicit_always},
+  {"zvkned", "+zve32x", check_implicit_always},
+  {"zvknha", "+zve32x", check_implicit_always},
+  {"zvknhb", "+zve32x", check_implicit_always},
+  {"zvksed", "+zve32x", check_implicit_always},
+  {"zvksh", "+zve32x", check_implicit_always},
+
   {"sdtrig", "+zicsr", check_implicit_always},
 
   {"smaia", "+ssaia", check_implicit_always},
--- a/gas/testsuite/gas/riscv/imply.d
+++ b/gas/testsuite/gas/riscv/imply.d
@@ -87,13 +87,13 @@  SYMBOL TABLE:
 [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zk1p0_zkn1p0_zknd1p0_zkne1p0_zknh1p0_zkr1p0_zkt1p0
 [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zkn1p0_zknd1p0_zkne1p0_zknh1p0
 [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zbkb1p0_zbkc1p0_zbkx1p0_zks1p0_zksed1p0_zksh1p0
-[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbb1p0_zvkb1p0
-[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvkg1p0_zvkn1p0_zvkned1p0_zvkng1p0_zvknhb1p0_zvkt1p0
-[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zvkb1p0_zvkn1p0_zvknc1p0_zvkned1p0_zvknhb1p0_zvkt1p0
-[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvkn1p0_zvkned1p0_zvknhb1p0_zvkt1p0
-[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvkg1p0_zvks1p0_zvksed1p0_zvksg1p0_zvksh1p0_zvkt1p0
-[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zvkb1p0_zvks1p0_zvksc1p0_zvksed1p0_zvksh1p0_zvkt1p0
-[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvkb1p0_zvks1p0_zvksed1p0_zvksh1p0_zvkt1p0
+[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbb1p0_zve32x1p0_zvkb1p0
+[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkg1p0_zvkn1p0_zvkned1p0_zvkng1p0_zvknhb1p0_zvkt1p0
+[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zve32x1p0_zvkb1p0_zvkn1p0_zvknc1p0_zvkned1p0_zvknhb1p0_zvkt1p0
+[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkn1p0_zvkned1p0_zvknhb1p0_zvkt1p0
+[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvkg1p0_zvks1p0_zvksed1p0_zvksg1p0_zvksh1p0_zvkt1p0
+[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zvbc1p0_zve32x1p0_zvkb1p0_zvks1p0_zvksc1p0_zvksed1p0_zvksh1p0_zvkt1p0
+[0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zve32x1p0_zvkb1p0_zvks1p0_zvksed1p0_zvksh1p0_zvkt1p0
 [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zicsr2p0_sdtrig1p0
 [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zicsr2p0_smaia1p0_ssaia1p0
 [0-9a-f]+ l       .text	0+000 \$xrv32i2p1_zicsr2p0_smcdeleg1p0_ssccfg1p0_sscsrind1p0