首页 > 技术文章 > 汇编(二)

xiongmao-cpp 2015-10-28 14:37 原文

  这次编程的内容是:用汇编实现从控制台输入一个简单的字符串,并将该字符串在控制台显示出来。

  用汇编来实现字符串的输入很简单,只要用到0AH DOS调用即可

  其代码如下:

  (代码1)

 1 stack segment stack
 2     db 2014 dup(?)
 3 stack ends
 4 data segment
 5     buffer db 81,0,81 dup(0)
 6 data ends
 7 code segment 'code'
 8     assume cs:code,ds:data,ss:stack
 9 start:
10     mov ax,data
11     mov ds,ax
12 
13     mov ah,0AH
14     mov dx,offset buffer
15     int 21H
16     
17 code    ends
18     end start

   上面的代码中,开辟了数据缓冲区buffer,用来存放输入的字符串。注意数据段中buffer缓冲区的定义:第一个字节存放着81,表示存放的最大字节数(包括回车)。第二个字节表示实际在这个缓冲区中存放的字节数。一直到第三个字节开始,才是真正存放输入字符串的开始位置。13、14、15行实现从控制台输入一个字符串并将该字符串保存到缓冲区buffer。

  上面就是用汇编实现的字符串读入。那么,如何用dos调用显示刚刚输入的字符串呢?对于显示自己输入的字符串,有些细节需要注意。

  首先来看看显示已经在数据段中定义好的字符串的方法,很简单,也是一个dos调用就解决了。

  (代码2)

 1 stack segment stack
 2     db 2014 dup(?)
 3 stack ends
 4 data segment
 5     buffer db ‘hello world!’,'$'
 6 data ends
 7 code segment 'code'
 8     assume cs:code,ds:data,ss:stack
 9 start:
10     mov ax,data
11     mov ds,ax
12     mov ah,09H
13     mov dx,offset buffer
14     int 21H
15     
16 code    ends
17     end start

  上面这段代码,先在数据段中定义一个字符串buffer,以$结尾(注意这里)。然后将buffer的首地址给dx,并调用09H号DOS调用就可以在屏幕上显示该字符串了。当然,看到上面的代码,会想着直接将两者结合起来就可以实现字符串输入并显示出刚刚输入的字符串的功能了。但是,如果在代码1中输入字符串结束之后,直接在后面跟上12、13、14行代码,发现显示在屏幕上的是乱码。

  这个就是一个细节的地方。首先,代码1中的buffer首地址不是字符串的首地址,其次,输入字符串后,buffer也不是以美元$符号结束的。所以,要输出输入的字符串,需要做以下调整:1、将字符串的首地址给dx,这个很简单,mov dx,buffer[2]就可以了。2、给输入的字符串加入结束符‘$’,这个需要根据实际输入的字符串来计算,比如如果输入了三个字符,就需要在buffer下标为5的位置插入$符号,其实就是执行mov buffer[7],'$'就可以了。

  完整实现如下:

 

 1 stack segment stack
 2     db 2014 dup(?)
 3 stack ends
 4 data segment
 5     buffer db 81,0,81 dup (?)
 6 data ends
 7 code segment 'code'
 8     assume cs:code,ds:data,ss:stack
 9 start:
10     mov ax,data
11     mov ds,ax
12     mov ah,09H
13     mov dx,offset buffer
14     int 21H
15     mov bx,2                ;将字符串首地址给bx
16     mov al,buffer[1]        ;将字符串长度给al
17     cbw                        ;对al进行位扩展
18     add bx,ax                ;将bx与ax相加,获得字符串结束的位置
19     mov buffer[bx],'$'        ;在字符串结束位置插入$符号
20     mov ah,02H                ;实现换行
21     mov dl,0dh
22     int 21H
23     mov dl,0Ah
24     int 21H
25     mov dx,offset buffer[2]    ;将字符串首地址给dx
26     mov ah,09H                ;dos调用显示字符串
27     int 21H
28     mov ah,4cH                ;返回dos
29     int 21H
30 code    ends
31     end start

 

推荐阅读