切换实现;手臂;汇编器;aarch64;arm64 [英] switch implementation; arm; assembler; aarch64; arm64

查看:61
本文介绍了切换实现;手臂;汇编器;aarch64;arm64的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对在 aarch64 汇编器上实现switch"运算符的方法很感兴趣.在 arm32 平台上,我使用了类似

 ldr pc, [pc, ta, LSL#2]nop//对齐.int .L.case1.int .L.case2....int .L.caseN

但由于 64 位版本对 'pc' 寄存器的使用有很多限制,这样的实现不再起作用.

似乎最简单的方法是使用对比较和分支操作,如

cmp ta, #1b.eq .L.case1cmp ta, #2b.eq .L.case2...

但有时有多达十几个案例,这会导致在到达最后一个案例"之前出现明显延迟.

请您分享一下如何在 aarch64 上实现快速切换的想法.

谢谢:)

解决方案

我没有 64 位 ARM 汇编器来测试这个,但我相信你会做类似下面的事情来实现一个跳转表:

>

 adr x0, jmp_tableldr x0, [x0, x1, LSL#3]x0jmp_table:.quad .L.case1.quad .L.case2.quad .L.case3

第一条指令,ADR,将标签的地址加载到寄存器中.最后一条指令 BR 跳转到地址存储在寄存器中.

如果您要创建共享库或位置无关的可执行文件,您可以尝试以下操作:

 adr x0, jmp_table添加 x0, x0, x1, LSL#2x0jmp_table:b.L.case1b.L.case2b.L.case3

替代 PIC 示例

 adr x0, jmp_tableldr w1, [x0, x1, LSL#2]添加 x0, x0, x1x0jmp_table:.int .L.case1 - jmp_table.int .L.case2 - jmp_table.int .L.case3 - jmp_table

I'm interesting in the ways to implement 'switch' operator on aarch64 assembler. On arm32 platforms I used something like

    ldr         pc,         [pc, ta, LSL#2]
    nop                                         // alignment
    .int        .L.case1
    .int        .L.case2
    ...
    .int        .L.caseN

But since 64bit version has a lot of restriction on 'pc' register usage, such implementation doesn't work any more.

It seems that the easiest way is to use pair of compare and branch operations, like

cmp ta, #1
b.eq .L.case1
cmp ta, #2
b.eq .L.case2
...

But sometimes there are up to dozen cases and it would lead to a significant delay before reaching the last 'case'.

Could you share your ideas how to implement fast switch on aarch64, please.

Thanks :)

解决方案

I don't have an 64-bit ARM assembler to test this with but I believe you would do something like the following to implement a jump table:

    adr  x0, jmp_table
    ldr  x0, [x0, x1, LSL#3]
    br   x0

jmp_table:
    .quad .L.case1
    .quad .L.case2
    .quad .L.case3

The first instruction, ADR, loads the address of a label into a register. The last instruction, BR, jumps to the address stored in the register.

If you're creating a shared library or a position independent executable you can try something like following:

    adr  x0, jmp_table
    add  x0, x0, x1, LSL#2
    br   x0

jmp_table:
    b .L.case1
    b .L.case2
    b .L.case3

Alternate PIC example

    adr  x0, jmp_table
    ldr  w1, [x0, x1, LSL#2]
    add  x0, x0, x1
    br   x0

jmp_table:
    .int  .L.case1 - jmp_table
    .int  .L.case2 - jmp_table
    .int  .L.case3 - jmp_table

这篇关于切换实现;手臂;汇编器;aarch64;arm64的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆