条件付きでゼロをレジスタに移動しますか?
Dec 01 2020
アセンブリ内のレジスタにゼロを条件付きで移動する方法はありますか?私がやろうとしている
cmpb %r9b, %r8b #compare r9 and r8
cmovgq $0, %rcx #If r8>r9, move zero to rcx
しかし、コンパイラは、最初のオペランドが即値定数であるという事実のために、「cmovgのオペランドタイプの不一致」について不平を言っています。movへの条件付きジャンプについて考えましたが、他にもっと良いオペコードがあるかどうかはわかりません。別のレジスタを使い果たすことなく、このレジスタを条件付きでゼロにするにはどうすればよいですか?
回答
dannyadam Dec 01 2020 at 03:36
cmovgq
命令は即値オペランドを受け入れないため、別のレジスタを使用しないアプローチでは、スタックにゼロ値を追加し、即値を使用する代わりに対応するアドレスを使用してから、スタックポインタを復元することができます。
pushq $0 # push 0 onto the stack cmpb %r9b, %r8b # compare r9b and r8b cmovgq (%rsp), %rcx # if r8b > r9b, move zero to rcx addq $8, %rsp # restore stack pointer
あるいは、ゼロをスタックにプッシュしてからスタックポインタを復元するのではなく、ゼロ値をメモリの他の場所に格納することもできます。
cmpb %r9b, %r8b # compare r9b and r8b
cmovgq zero, %rcx # if r8b > r9b, move zero to rcx
...
.section .rodata
zero:
.quad 0
を使用するのcmovgq
ではなく、条件付きジャンプは別のレジスタを使用しない代替アプローチであり、同じ動作になります(つまり、rcx
条件付きで0に設定されますr8b > r9b
)。
cmpb %r9b, %r8b # compare r9 and r8
jle destination # if r8b <= r9b, skip the next line
movq $0, %rcx # if r8b > r9b, move zero to rcx
destination:
...