ARM指令集 - 更改CPSR(S位)

时间:2015-02-03 15:22:55

标签: arm

我想知道为什么ARM指令默认设置CPSR(如x86),但在这些情况下必须使用S位?当说明书没有改变CPSR提供更好的性能?例如,ADD指令提供比ADDS更好的性能?或者真正的交易是什么?

2 个答案:

答案 0 :(得分:1)

  

我想知道为什么ARM指令默认设置CPSR(如x86),但在这些情况下必须使用S位?

这是一个选择,它取决于背景。额外的灵活性仅受程序员想象力的限制。

  

当说明书没有改变CPSR提供更好的性能时?例如,ADD指令提供的性能优于ADDS

很可能永远不会 Note1 。即,没有设置CPSR的指令对大多数ARM CPU和指令执行速度更快(时钟更少)。

  

或者什么是真正的交易?

考虑一些'C'代码,

int i, sum;
char *p = array; /* passed in */

for(i = 0, sum = 0; i < 10 ; i++)
    sum += arrary[i];

return sum;

这可以转化为,

 mov r2, r0          ; get "array" to R2
 mov r1, #10         ; counter (reverse direction)
 mov r0, #0          ; sum = 0
1:
 subs r1, #1         ; set conditions
 add  r0, [r2], #1   ; does not affect conditions.
 bne  1b
 bx   lr

在这种情况下,循环体很简单。但是,如果循环中没有带条件的条件,那么编译器(或汇编程序员)可以在任何他们喜欢的地方调度循环递减,并且仍然设置要稍后测试的条件。对于更复杂的逻辑以及由于数据依赖性而导致CPU停顿的情况,这可能更为重要。对条件执行也很重要。

可选的“S”是许多指令的一个特征,而不是单个指令。

注1:有人可以随时制作ARM CPU并执行此操作。您必须查看数据表。我不知道任何需要更多时间设置条件的CPU。

答案 1 :(得分:1)

这是为了表演还是为了表演。如果你总是更改标志,那么你很难在多个指令上使用一个标志而没有一个与你的管道混淆的分支。

if(a==0)
{
  b=b+1;
  c=0;
}
else
{
  b=0;
  c=c+1;
}

传统上你必须用分支(伪代码不是真正的asm)来实现它

cmp a,0
bne  notzero
  add b,b,1
  mov c,0
  b waszero
notzero:
  mov b,0
  add c,c,1
waszero:

所以无论什么

你都会受到影响

但有条件执行

cmp a,0
addeq b,b,1
moveq c,0
addne c,c,1
movne b,0

没有分支你只是简单地翻阅代码,现在唯一的方法是1)你有一个选项,每条指令有条件地执行基于标志和2)修改标志的指令有一个选项不修改标志

根据处理器系列/体系结构的不同,添加甚至mov都会修改标志,因此您必须同时具有条件执行和不设置标志的选项。这就是为什么arm有一个添加和添加。

我认为他们已经摆脱了64位架构的所有这些,所以也许它很有趣和很酷,可能它没有被充分使用或者值得,或者他们只需要这四个位来将所有/一些指令保持为32位。