这可以用于返回RAX寄存器中9倍的内容吗?
Times9:
mov rbp, rax
add rax, rax ;(x2)
add rax, rax ;(x4)
add rax, rax ;(x8)
add rax, rbp ;(x9)
push rax
ret
答案 0 :(得分:5)
您可以使用LEA
:
lea rax,[rax + rax*8] ; rax *= 9
注意:我还没有做过任何基准测试,看看这是否比其他方法更快。无论如何,它的代码更少。
答案 1 :(得分:1)
这是一个有效的方法,但您的具体实施有一些问题。
首先,它会不必要地破坏寄存器。尽可能减少副作用是一个很好的经验法则,例如(在这种情况下)改变rbp
。当然,如果您特意陈述某些寄存器可能已损坏,您可以通过不保存它们来实现更快的速度。
其次,rbp
并不是真正正确的寄存器,因为它在堆栈帧管理的许多调用约定中使用。我使用其他通用寄存器之一,例如rbx
。
第三,你拥有的例程几乎肯定会崩溃,因为条目中的堆栈内容不与退出时相同。你最后按rax
然后尝试返回,这意味着返回地址几乎肯定是不 CPU所期望的。
为此,我会将其重写为:
Times9:
push rbx ; save
push rax ; rax -> rbx
pop rbx
add rax, rax ; double
add rax, rax ; quadruple
add rax, rax ; octuple
add rax, rbx ; now nine times
pop rbx ; restore and return
ret
现在,请记住,可以通过向左移动三位来完成乘八运算,例如:
shl rax, 3
但是,如果代码简洁是您的主要考虑因素,则可以使用MUL
或IMUL
完成整数乘以九,这样您可能需要考虑这一点。
答案 2 :(得分:-1)
是的。如果您正在考虑性能,可以这样做
Times9:
mov rbp, rax
shl rax, 3 // left shift by 3: 8x
add rax, rbp
push rax
ret