首页澳门新葡亰官方网站 › 跳转指令

跳转指令

arm汇编指令总结(不断更新),arm不断更新

/**
******************************************************************************
* @author    Maoxiao Hu * @version   V1.0.0 * @date       Jan-2015
******************************************************************************
* < COPYRIGHT 2015 ISE of SHANDONG UNIVERSITY >
******************************************************************************
**/ 控制流指令     转移指令(branch)         说明:无条件转移B,BAL
        举例:    B LABEL        ; LABEL为某个位置     条件转移
        说明:    BEQ    相等             BNE    不等
            BPL    非负             BMI    负             BCC    无进位
            BCS    有进位             BLO    小于(无符号数)
            BHS    大于等于(无符号数)
            BHI    大于(无符号数)
            BLS    小于等于(无符号数)
            BVC    无溢出(有符号数)
            BVS    有溢出(有符号数)
            BGT    大于(有符号数)
            BGE    大于等于(有符号数)
            BLT    小于(有符号数)
            BLE    小于等于(有符号数)
            和其中BCC和BLO,BCS和BHS的二进制代码相同
-----------------------------------
BIC 是 逻辑”与非” 指令, 实现的 Bit Clear的功能 举例: BIC    
R0,   R0  , #0xF0000000 #将 R0  高4位清零 BIC    R1,  R1,   #0x0F
#将R1   低4位清0
-----------------------------------

控制流指令
    转移指令(branch)
        说明:无条件转移B,BAL
        举例:    B LABEL        ; LABEL为某个位置
    条件转移
        说明:    BEQ    相等
            BNE    不等
            BPL    非负
            BMI    负
            BCC    无进位
            BCS    有进位
            BLO    小于(无符号数)
            BHS    大于等于(无符号数)
            BHI    大于(无符号数)
            BLS    小于等于(无符号数)
            BVC    无溢出(有符号数)
            BVS    有溢出(有符号数)
            BGT    大于(有符号数)
            BGE    大于等于(有符号数)
            BLT    小于(有符号数)
            BLE    小于等于(有符号数)
            和其中BCC和BLO,BCS和BHS的二进制代码相同

/**
******************************************************************************
* @author    Maoxiao Hu * @version  ...

所有的体系结构都必须要有比较和条件跳转,虽然很多相似之处,但是各个体系结构都有自己的一套实现。

用有16条指令,分两类:

PowerPC也是用四种状态编码:小于,大于,等于,以及溢出,不过存在8份拷贝。这种冗余设计本质上来说,就是为PowerPC多添加了8个4位寄存器,让PowerPC的指令在使用状态的时候减少冲突。每个状态码都可以是一个比较指令的目的,也可以是一个条件跳转的源。整数指令有一个可选位,来标识这个整数操作后是否有一个与零比较来设置状态寄存器。浮点指令也可以选择设置第二个状态寄存器。PowerPC提供对这8个4位寄存器的逻辑操作(CRAND,CROR,CRXOR,CRNAND,CRNOR,CREQV),为单条的分支指令提高更复杂的条件比较。

0 0 0
0 1 0
1 0 1
1 1 0
译注:逻辑表达式为 Op_1 AND NOT Op_2
 
EOR : 逻辑异或
(logical Exclusive OR)
EOR{条件}{S} <dest>, <op 1>, <op 2>

⑴两个无符号整数大小关系的条件转移指令:

无符号数大小用高(Above)、低(Below)助记符

JB:无符号低于

JNAE:无符号不高于等于

 

 

JNB:无符号不低于

JAE:无符号高于等于

 

 

JBE:无符号低于等于

JNA:无符号不高于

 

JNBE:无符号不低于等于

JA:无符号高于

即 JB
= JNAE、 JNB = JAE、JBE = JNA 和 JNBE =
JA

 

图片 1

 

②利用零位标志ZF的条件转移指令:

JZ:运算结果为0 (ZF=1)

JNZ:结果不为0 (ZF=0)

JE:两数相等 (ZF=1)

JNE:不相等 (ZF=0)

 

SPARC使用4种传统的状态位:负数,零,进位,和溢出。所有的算术和逻辑指令都可能设置它们,旧的体系结构中,这些位可能被所有的指令设置。明确的操作更利于流水线的实现。虽然状态位可能被其他操作影响,但是显式的比较可以用r0作为目的寄存器来生成。SPARC的条件跳转会比较所有的条件位来确定所有可能的跳转。浮点使用专门的条件位。第9版SPARC分支跳转扩展了4种情况:一个是为64bit设计的独立的条件编码;一个是跟0的各种情况比较(参考下面的MIPS);3种新的浮点条件码;最后是静态编码了的分支预测。


②利用进位标志CF的条件转移指令:

JC:运算结果有进位/借位(CF=1)

JNC:运算结果没有有进位/借位(CF=0)

 

Hitachi
SuperH只有一个单独的T状态位,可以通过比较指令设置。两个分支指令可以用来跳转,在T位是1的时候跳转(BT)或者T位是0的时候(BF)。这两种分支可以减少比较指令。

当你发现所有 Bxx 指令实际上是同一个指令的时候,紧要关头就到了。
接着你会想,如果你可以在一个分支指令上加上所有这些条件,那么对一个寄存器装载指令能否加上它们?
答案是可以。

下面是可获得的条件代码的列表:
EQ : 等于
如果一次比较之后设置了 Z 标志。
 
NE : 不等于
如果一次比较之后清除了 Z 标志。
 
VS : 溢出设置
如果在一次算术操作之后设置了 V 标志,计算的结果不适合放入一个 32bit
目标寄存器中。

 
VC : 溢出清除
如果清除了 V 标志,与 VS 相反。
 
HI : 高于(无符号)
如果一次比较之后设置了 C 标志并清除了 Z 标志。
 
LS : 低于或同于(无符号)
如果一次比较操作之后清除了 C 标志或设置了 Z 标志。
 
PL : 正号
如果一次算术操作之后清除了
N。出于定义‘正号’的目的,零是正数的原因是它不是负数...

 
MI : 负号
如果一次算术操作之后设置了 N 标志。
 
CS : 进位设置
如果一次算术操作或移位操作之后设置了 C 标志,操作的结果不能表示为
32bit。你可以把 C 标志当作结果的第 33 位。

 
CC : 进位清除
与 CS 相反。
 
GE : 大于或等于(有符号)
如果一次比较之后...设置了 N 标志并设置了 V 标志或者...清除了 N
标志并清除了 V 标志。

 
GT : 大于(有符号)
如果一次比较之后...设置了 N 标志并设置了 V 标志或者...清除了 N
标志并清除了 V 标志并且...清除了 Z 标志。

 
LE : 小于或等于(有符号)
如果一次比较之后...设置了 N 标志并清除了 V 标志或者...清除了 N
标志并设置了 V 标志并且...设置了 Z 标志。

 
LT : 小于(有符号)
如果一次比较之后...设置了 N 标志并清除了 V 标志。或者...清除了 N
标志并设置了 V 标志。

 
AL : 总是
缺省条件,所以不用明显声明。
 
NV : 从不
不是特别有用,它表示应当永远不执行这个指令。是穷人的 NOP。包含 NV
是为了完整性(与 AL 相对),你不应该在你的代码中使用它。

**有一个在最后的条件代码
S,它以相反的方式工作。当用于一个指令的时候,导致更改状态标志。这不是自动发生的

标志状态作为条件:

M32R也只有一个单独的条件状态码(C),有符号比较和无符号比较(CMP,CMPI,CMPU,CMPUI)都用C位来标识一个寄存器的值是否小于另一个,就像MIPS的小于置位指令一样。灵感废纸指令测试C位是否为1或0:BC和BNC。M32R也包含相等跳转,不相等跳转(BEQ和BNE),以及一个寄存器值跟0比较(BGEZ,BGTZ,BLEZ,BLTZ,BEQZ,BNEZ).后面这些都是32位宽指令。

  1. 使用这个值来找到要被执行的代码的例程的地址(使用查找表等)。

②两数大小关系作为条件

  ㈠比较无符号整数的大小:

      低于、不低于、低于等于、高于

  ㈡比较有符号整数大小:

      小于、不小于、小于等于、大于

 

ARM跟SPARC类似,指令中提供四种可以选择设置的状态条件码。CMP用一个操作数减去另外一个操作数的结果来设置状态位。负数比较(MN)用一个操作数加上另外一个操作数,用和来设置状态位。TST用两个操作数逻辑与来设置所有的状态码,TEQ用独有的或操作来设置前三个状态码。跟SPARC一样,ARM分支指令通过测试状态位来判断所有的有符号和无符号关系。我们会在“SPARC
v.9的指令独特点”中看到,ARM的一个不常用的特点是,每条指令都可以根据状态码来选择是否执行。(这个PA-RISC的选项类似,见“Alpha的独特点”)。

            Status = op_1 AND op_2

①单个标志状态作为条件

  5个状态标志ZF、CF、SF、OF和PF的10种状态

图19嵌入式RISC条件分支汇总


⑤利用奇偶标志PF的条件转移指令:

JP:低8位结果中1的个数为偶或0(PF=1)

JPE:低8位结果中1的个数为偶或0(PF=1)

JNP:低8位结果中1的个数为奇(PF=0)

JPO:低8位结果中1的个数为奇(PF=0)

 

图片 2


⑵两个有符号整数大小关系的条件转移指令:

有符号数大小用大(Greater)、小(Less)助记符

JL:小于

JNGE:不大于等于

 

JNL:不小于

JGE:大于等于

 

JLE:小于等于

JNG:不大于

 

JNLE:不小于等于

JG:大于

即JL =
JNGE、JNL = JGE、JLE = JNG 和 JNLE = JG

MIPS用寄存器来获取分支状态。可以用任意的两个寄存器来构造一条相等(BEQ)或者不相等(BNE)指令,通过他们的结果来决定分支是否跳转。小于置位指令(SLT,SLTI,SLTU,SLTIU)比较两个操作数然后设置目的寄存器,如果小于就设置为1,否则就将目的寄存器设置为0。这些指令就可以组合出所有的可能。因为跟0比较很常见,所以MIPS还包括一些特殊的跟0的比较跳转指令:大于等于0(BGEZ),大于0(BGTZ),小于等于0(BLEZ),还有小于0(BLTZ)。当然,等于或者不等于也可以由r0跟BEQ和BNE组合出来。跟SPARC一样,MIPS
I为浮点比较和跳转指令提供一个单独的状态码;MIPS
IV将状态码扩展到8个,来标识浮点的比较和条件指令状态。

MUL提供 32 位整数乘法。如果操作数是有符号的,可以假定结果也是有符号的。

④利用符号标志SF的条件转移指令:

JS:运算结果是负、最高位为1(SF=1)

JNS:结果是正、最高位为0(SF=0)

 

PA-RISC有很多分支选项,我们在“Alpha的指令独特点”小结会看到。最直接的是比较并且跳转(COMB),比较两个寄存器,然后根据它们的结果来判断是否跳转,并且测试比较的最低有效位。


JCC:根据指定的条件确定程序是否发生转移,条件满足,发生转移,否则,顺序执行下条指令

MIPS16保留了小于置位指令(SLT,SLTI,SLTU,SLTIU),但是不再将结果放到8个寄存器中,而是放到一个专门的T寄存器。MIPS16总是在完整的32位MIPS指令集机器上面实现,所以,T寄存器实际上就是完整MIPS体系结构中的寄存器24。MIPS16的分支指令测试一个寄存器是否等于0(BEQZ和BNEZ)。也有测试T寄存器是否为0的(BTEQZ和BTNEZ)。为了测试两个寄存器中的值是否相等,MIPS还添加了比较指令(CMP,CMPI),指令会把或的结果存到T寄存器。MIPS16删减了寄存器是否等于的比较跳转(BEQ和BNE)。

象我说过的那样,地址 &08 包含跳转到另一个地址的一个指令,就是实际的 SWI
程序的地址!

③利用溢出标志OF的条件转移指令:

JO:运算结果有溢出(OF=1)

JNO:结果没有溢出(OF=0)

 

图18桌面RISC条件分支汇总。PA-RISC的浮点分支实现需要将FP状态寄存器拷贝到整数寄存器,然后用分支指令测试FP的比较结果。SPARC的整数比较是由使用R0作为目的寄存器的算术指令组合出来的。

JMP:无条件跳转,相当于C语言的goto

图18和图19汇总了条件分支的设计。

0 0 0
0 1 0
1 0 0
1 1 1
 
BIC : 位清除
(Bit Clear)
BIC{条件}{S} <dest>, <op 1>, <op 2>

JECXZ:ECX为0则跳转

Alpha指令(CMPEQ,CMPLE,CMPLE,CMPULT,CMPULE)比较两个寄存器的值,然后设置第三个寄存器的值,条件为真设置为1,否则这是为0。浮点指令(CMTEQ,CMTLT,CMTLE,CMTUN)在判断条件为真的时候将结果设置为2.0,否则设置为0。分支指令将一个寄存器的值跟0比较(BEQ,BGE,BGT,BLE,BLT,BNE),或者它的最低有效位(BLBC,BLBS),如果条件成立就跳转。


跳转指令有:JMP、JECXZ、JA、JB、JG、JL、JE、JZ、JS、JC、JO、JP等等

显然的,Thumb跟ARM很像。不同的地方是状态码不再可选,没有了TEQ指令,也没有了条件执行的指令。

条件执行的一个例子

指令格式
译注:CMP 和 CMP 是算术指令,TEQ 和 TST
是逻辑指令。把它们归入一类的原因是它们的 S
位总是设置的,就是说,它们总是影响标志位。
CMN : 比较取负的值
(Compare Negative)
CMN{条件}{P} <op 1>, <op 2>

· NV - NeVer,不是非常有用。你无论如何不要使用这个代码...

SWI 指令

· 我说要装载 R14。那么为什么要把它放入 PC 中? 原因是此时 R14
存储的值包含返回地址。我们也可以采用:LDMFD R13!, {R0-R12,R14}

· ** MOV PC, R14但是直接恢复到 PC 中可以省略这个 MOV语句。**

            Status = op_1 EOR op_2

首先查看一下如何使用它。一个 SWI 指令(汇编语言)看起来如下:
SWI &02

WriteIRtn
; 写 R0 中的位 0 - 7 中的字符。

            dest = op_1 AND op_2
  1. 恢复寄存器 r0-r12。
  1. 把这个指令装载到一个寄存器。

0 0 0
0 1 1
1 0 1
1 1 1
 
RSB : 反向减法
(Reverse Subtraction)
RSB{条件}{S} <dest>, <op 1>, <op 2>

作为对比,ARM 处理器只提供了:
B 分支
** BL 带连接的分支**

** ADDEQS R0, R0, R1**

在进入超级用户模式的时候,还把 r14_svc 设置为在这个 SWI
指令之后的地址。

            dest = op_1 EOR op_2

还有两个代码,
· AL - ALways,缺省条件所以不须指定




下面是条件执行的一个工作中的例子。你把寄存器 0 与存储在寄存器 10
中内容相比较。

注解:
· SWI 编号就象我写的这样。在 RISC OS 下,它是给
Econet_DoImmediate的编号。不要字面的接受它,这只是一个例子!

Nava Whiteford 解释了 SWI 是如何工作的(最初在 Frobnicate issue
12?)...


SWI 是什么?

** .loop ; 标记循环开始位置**
** CMP R0, R10 ; 把 R0 与 R10 相比较**
** SWINE &40017 ; 不等于: 调用 SWI &40017**
** ADDNE R0, R0, #1 ; 向 R0 加 1**
** BNE loop ; 分支到 'loop'**
** MOV R10, #0 ; 等于 : 设置 R10 为零**
** LDMFD R13!, {R0-R12,PC} ; 返回到调用者**

转载本站文章请注明出处:澳门新葡亰官方网站 http://www.radioritmo-bl.com/?p=829

上一篇:

下一篇:

相关文章