通常一个汇编程序的基本框架如下:
- Assembly code
data segment ;input data segment code heredata endsstack segment ;input stack segment code herestack endscode segment assume cs:code,ds:data,ss:stackstart: mov ax,data mov ds,ax ;input code segment code here mov ah,4ch int 21hcode endsend; start
为什么只有数据段地址需要放入寄存器:
mov ax,data
mov ds,ax
code段和stack段,不需要相应的操作代码么?
既然已经assume ds:data了,干什么还要mov ds,ax
------解决方案--------------------------------------------------------
当你的程序开始执行时,代码段寄存器CS和指令指针IP已经指向你的程序,所以不需要初始化。实际上,你没有办法直接改变IP的内容。
编译器在编译汇编语言源程序时,需要通过几遍语法扫描,其中包括符号和语法的解析,以及确定程序中包含的段和节,最终确定各个段的长度和位置,并按照操作系统的要求为将来重定位各个段做静态准备。换句话说,为将来用link.exe链接目标文件做准备。为了确定各个段的位置和大小,必然需要assume伪指令来获得段和节的信息。
一个程序可以有多个段,甚至可以有多个代码段和多个数据段。程序的入口已经用start和主过程声明指定了,而数据段呢,是现用现指定的,所以,只能根据你自己的需要,随时在程序中指定。比如
mov ax,xxx
mov ds,ax
过一会,你又要切换到另一个不同的数据段,则可以
mov cx,yyy
mov ds,cx
在编译阶段,这里的xxx和yyy只是保留了一个汇编地址(符号地址),在实际加载到内存并开始执行前,还需要重定位。
理论上,应当指定栈段。如果没有,则程序依然可以运行。
------解决方案--------------------------------------------------------
堆栈段在定义时,有说明的,如:
stack segment stack
;input stack segment code here
stack ends
否则也要
mov ax,stack
mov ss,ax
------解决方案--------------------------------------------------------