灵活运用汇编语言的转移指令

一、无条件转移指令

无条件转移指令 JMP 有多种形式的操作数。应用多种操作数可实现多种无条件转移。

  1. 段内转移

    (1)使用标号进行段内直接转移。例:

    使用标号进行段内直接转移

    (2)使用通用寄存器表示转移目标的偏移地址,实现段内间接转移。例:

    使用通用寄存器表示转移目标的偏移地址

    (3)以内存变量表示转移目标的偏移地址,实现段内间接转移。例:

    以内存变量表示转移目标的偏移地址

    1
    2
    
    LEA  BX, L1
    JMP  WORD PTR[BX]
    
  2. 段间转移

    (1)使用标号进行段间直接转移。例:

    使用标号进行段间直接转移

    (2)以内存变量表示转移目标的 32 位逻辑地址,实现段间间接转移。例:

    以内存变量表示转移目标的 32 位逻辑地址

二、条件转移指令

通常,使用条件转移指令 JCC 来实现分支。首先需要应用比较、算术或逻辑运算等影响标志位的指令,再用 JCC 指令判断转移条件,以实现分支转移。实质上,JCC 指令都是判断标志位的。因此,分支程序设计的关键在于准确把握指令对标志位的影响及正确运用条件转移指令。

比较两个数的大小要使用 CMP 等指令,然后再判断标志位。

CMP 指令实质是执行两个数相减操作,但不送回相减的结果,只是结果影响标志位。

那么,怎样根据标志来判断比较结果呢?

首先,如果所比较的两个操作数相等,那么标志位 ZF=1,所以,根据ZF就可以判断是否相等。

如果两数不等,则有以下两种情况。

  1. 两个无符号数的比较

    无符号数相减,CF 是借位标志。如果 CF=0,表示无借位,即被减数(目的操作数)大。

  2. 两个有符号数的比较

    有符号数的最高位表示符号,而符号标志 SF 总是和结果的最高位相同。所以,当两个正数相比较或两个负数相比较时,毫无疑问,可以用 SF 来判断被减数比减数大还是比减数小。如果 SF 为 0,则表示被减数比减数大;如果 SF 为 1,则表示被减数比减数小。

    如一个为正数,另一个为负数,当两者相比较或相减时,可能会出现这样的情况:比如,被减数为 127,减数为 -50,显然是被减数比减数大。但是,127-(-50)=177,在计算机中运算时,为:

    两个有符号数的比较

    按照带符号数的观点来看,结果为 -79,是一个负数。为什么一个正数减一个负数会得到一个负的结果呢?原因就在于正确的计算结果177已经超出了有符号范围 -128~+127,即产生了溢出,因此,在这种情况下,溢出标志 OF 为 1。也就是说,如果两个有符号数比较时,使得 OF=1,而且 SF=1,那么,结果为被减数大,减数小。

    同样,不难用被减数为 -50,减数为 127 的情况说明,如果两个有符号数比较时,使得 SF=0,而且 0F=1 时,那么,结果为被减数小,减数大。

    可见没有溢出时,只要用标志位 SF 来判断两数的比较结果就行了,当 SF=0 时,被减数比减数大,当 SF=1 时,被减数比减数小。

    在有溢出时,0F=1,这时,如果 SF=0,则被减数比减数小,如果 SF=1,则被减数比减数大。

    归纳上面两种情况以及两个正数和两个负数的情况(后面两种情况下,OF 始终为 0),对于有符号数的比较可得出结论:

    (1)如果得到溢出标志 0F 和符号标志 SF 的值相同(均为 1 或者均为 0),则说明被减数比减数大。

    (2)如果得到溢出标志 OF 和符号标志 SF 的值不同(一个为 0,另一个为 1),则说明被减数比减数小。

因此,对于有符号数的比较,要根据 OF 和 SF 两者的关系来判断结果。

在讲转移指令时,8086/8088 指令系统中分别提供了判断无符号数比较结果的条件转移指令以及判断有符号数比较结果的条件转移指令。这两组条件转移指令在执行时的差别就是前者只根据标志位 CF 来判断结果,后者则根据标志位 OF 和 SF 的关系来判断结果。

请参阅

(完)

comments powered by Disqus