我对以下目的感到困惑:
....
BL some_func
MOV R3, R0,LSL#16
MOVS R3, R3,LSR#16
....
为什么转回来?和movs?
答案 0 :(得分:3)
执行r0& = 0xFFFF
需要三条指令mov r3,#0x00FF orr r3,r3,#0xFF00 and r0,r0,r3
因此来回转换效率更高。
您可能一直在做的是与16位变量相关的事情,因此为了准确,编译器必须截断高位以使程序正常运行。如果你使用了int或者其他可能没有这样做的东西,不确定这是不是你如何煽动这些指示。
有时你会看到这个做一个符号扩展,但这不是一个算术移位,它是一个逻辑移位(零进入而不是进位)。
也许你的代码就像if(hello& 0xFFFF)那样。
ARM不会正常更新标志,除非你告诉它,出于性能原因,如果没有其他类似的代码
if(a&0xFF) b=0x12; else b=0x34; would be something like: ands r0,r0,#0xFF movne r1,#0x12 moveq r1,#0x34
使用其他处理器并且将始终设置标志,下一条指令将是一个导致管道刷新的分支。
ands r0,r0,#0xFF bne notequal mov r1,#0x12 b wasequal notequal: mov r1,#0x34 wasequal:
执行时更加残酷。许多处理器也会在移动时立即覆盖标志,而手臂也不会这样做。 (拇指模式是另一个故事)。
而不是只有具有条件字段的分支,臂上的每条指令都有一个条件字段,如果相等则分支,如果相等,则加上if等于,sub如果相等,则分支如果进位设置,如果是携带设置等。同样,可以修改标志的指令有一个操作码位,用于启用或禁用标志的更新。您将s添加到指令中。并且r0,r1,r2没有,但是r0,r1,r2确实更新了标志。
所以你的两条指令做了两件事,它将寄存器的高16位清零,然后为随后的条件设置标志。对于一个如果相等可能是分支的mov或者如果不相等则分支。您最初的源代码看起来是什么产生了这个?
答案 1 :(得分:2)