这可以说是第一个我自己写的汇编程序,虽然很短。。
功能很简单,实现两个16位二进制数相加即可。
step 1.写汇编代码
下面是实现功能的相应代码:
DSEG SEGMENT
DATA_1 DW ?
DATA_2 DW ?
DSEG ENDS
SSEG SEGMENT STACK
TOP_PTR DB 20 DUP(0)
SSEG ENDS
CSEG SEGMENT
ASSUME DS : DSEG, SS : SSEG, CS : CSEG
BEG_: MOV AX, DSEG
MOV DS, AX
MOV AX, SSEG
MOV SS, AX
MOV SP, LENGTH TOP_PTR
MOV DATA_1, 0A1A1H
MOV DATA_2, 1A1AH
MOV AX, WORD PTR DATA_1
ADD AX, WORD PTR DATA_2 ;FINAL ANSWER IN 'AX' REGISTER
MOV AH, 4CH
INT 21H
CSEG ENDS
END BEG_
可以看到汇编代码和高级语言比起来确实是要冗长不少的,甚至会让人觉得有一点刻板。但是这也正是它得优点和魅力所在,这些特点也恰巧表明了汇编的高度严格,严谨,要编写好的汇编程序需要我们提前合理的编排程序,进行总体规划,方能实现复杂的功能。
step 2.汇编+链接+debug下运行
1.汇编+链接。
因为我的电脑是64位,无法直接运行。所以我下载了DOSBox来在d盘建立虚拟盘符。
2.debug下运行
进入Debug模式,输入命令U 0即可从将机器代码反汇编后从CS代码段偏移量为0的地方开始显示汇编代码,以供我们进行操作。
3.运算
从代码中就可以看到我们这里进行A1A1+1A1A的加法运行并将结果保存在AX寄存器中。
可以看到A1A1已被送到AX中,下面进行加法。
可以看到运算结果BBBB已被存到AX通用寄存器中。
再来看标志寄存器:
第一个状态为NV表示进行的这一次计算没有发生溢出,结果可以被我们正常使用。
第二、三个状态是方向标志和中断标志状态,这里不做讨论。
第四个标志位是NG,表示最高位为1。
第五个标志位是NZ,表示运算结果不为零。
第六个状态位是NA,表示没有发生低四位向高四位的进位。
第七个状态位是PE,表示结果中1的个数为偶数。
第八个状态位是NC,表示没有发生最高位向自然位的进位。
我们再在此基础上加上一个数让它发生溢出来看一次标志寄存器的变化情况。
可以看到我给BBBBH加上一个4445H得到的结果如AX中所示,为0000H。
- 标志位NV告诉我们,结果没有溢出。(溢出只可能发生在符号位相同的情况下进行的运算,而BBBBH符号位为1,4445H符号位为0,所以被认为不溢出)
- 标志位PL告诉我们最高位为0
- 标志位ZR告诉我们结果为0
- 标志位AC告诉我们发生了低四位向高四位的进位
- 标志位PE告诉我们结果中1的个数为偶数(0个)
- 标志位CY告诉我们发生了最高位向自然位的进位
step 3.总结
- 经过学习之后发现汇编真的非常有意思,能够给人真正窥探到天机并且能够随心所欲操控这台计算机的感觉。并且计算机cpu内部的运行原理也十分有意思。
- 需记忆各种寻址方式的寻址方法,特别是各种特殊情况,比如:
如果BP参与到寻址当中,则段寄存器默认为SS,其他情况几乎均为DS。
- 需要记忆各种debug模式下的汇编指令,例如:
A指令:编写代码的指令,不需要经过繁琐的汇编,链接,在运行等过程,可以在debug模式下直接进行编写。
D指令:查看段内容,后面加上段跨越符就可以查看任意段的内容。
T指令:单步运行。
P指令:单步运行,遇到子程序或者中断程序一次性执行完。
R指令:查看或者修改寄存器内容。
U指令:将机器代码进行反汇编得到汇编代码。