[英]How to read a condition flag in ARMv7 Thumb-2 assembly?
我正在使用帶有Thumb-2指令的ARMv7處理器。
我已經執行了ADD
, SUB
或CMP
。 現在我想將條件標志LE
移動到r2
。 在此之后, r2
應該包含0
或1
。
我一直在查看Thumb-2手冊,但我沒有找到條件MOV指令或讀取標志的特殊指令。
最有效的方法是什么? 提前致謝!
您需要使用ite
(if-then-else)指令啟動條件塊,然后使用條件賦值:
ite le @ if-then-else (le)
movle r2, #1 @ if (le) then r2 = #1
movgt r2, #0 @ else r2 = #0
通常,如果在前面添加適當的IT指令,則可以在Thumb-2中使用任意條件指令。 閱讀手冊了解詳情。
在ARM中,(幾乎)可以預測任何指令。 在拇指模式下,這需要一個it
指令來編碼下一個指令的否定或否定的謂詞和模式。
但是在統一語法中,匯編程序可以為你做到這it
,我認為沒有明確表示。
例如movle r0, #1
如果LE條件在flags中為真,則設置r0 = 1
,否則保持不變。 所以你首先需要一個mov r0, #0
。
ARM32沒有像x86的setcc
那樣的set-from-condition指令。
AArch64:將標志條件轉換為整數只需要一個cset
指令。
這個C源:
int booleanize(int x, int y) { return x<y; }
int booleanize_u(unsigned a, unsigned b) { return a<b; }
使用clang -O3( 在Godbolt編譯器瀏覽器上 )編譯ARM32 thumb,揭示了一些愚蠢的錯過優化。 gcc類似,制作沒有-mcpu
分支代碼,甚至比使用-mcpu=cortex-a53
更糟糕。 在簡單的微控制器上,Branchy可能並非完全不合理。
@@ BAD EXAMPLE, compiler missed optimizations
@ clang7.0 -target arm -mthumb -mcpu=cortex-a53
booleanize(int, int):
movs r2, #0 @ movs is 16-bit, mov is a 32-bit instruction, I think.
cmp r0, r1
it lt
movlt r2, #1
mov r0, r2 @ wasted instruction because the compiler wanted to mov #0 before cmp
bx lr
booleanize_u(unsigned int, unsigned int):
movs r2, #0
cmp r0, r1
it lo
movlo r2, #1
mov r0, r2
bx lr
這肯定比來自@ fuz的回答的ite le
/ movle / movgt更糟糕,有2個謂詞指令。
ARM模式代碼或多或少都很好,其中每個32位指令字在編碼中具有4位用於謂詞條件。 (asm源中沒有后綴的默認值是al
= always。)
@ gcc8.2 -O3 -mcpu=cortex-a53
booleanize(int, int):
cmp r0, r1
movge r0, #0 @ a simple mov without predication or flag-setting would work
movlt r0, #1
bx lr
booleanize_u(unsigned int, unsigned int):
cmp r0, r1
movcs r0, #0
movcc r0, #1
bx lr
cset
,booleanization。 @ clang and gcc make the same efficient code
booleanize(int, int):
cmp w0, w1
cset w0, lt @ signed less-than
ret
booleanize_u(unsigned int, unsigned int):
cmp w0, w1
cset w0, lo @ unsigned lower
ret
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.