汇编语言简明教程 实验报告
汇编语言简明教程 实验报告提示本文是应燕山大学实验要求经抓耳挠腮大量掉发查阅资料后所得文章目录汇编语言简明教程 实验报告前言实验一 汇编语言源程序的输入1.1实验内容1.2实验过程1.3实验结果实验二 数 据 的 建 立 与 传 送 程 序2.1实验内容2.2实验过程2.3实验结果实验3 分 支 程 序 设 计3.1实验内容3.2实验过程3.3实验结果实验4 分 支 程 序 设 计4.1实验内容4.2实验过程4.3实验结果实验5 学 生 成 绩 名 次 表 实 验5.1实验内容5.2实验过程5.3实验结果总结前言提示以下是本篇文章正文内容实验一、二是在DOSBOX窗口中直接编写指令实验三、四、五是在MASMPlus中编写的。实验一 汇编语言源程序的输入1.1实验内容本实验要求在DEBUG状态下输入汇编源程序并用DEBUG命令进行调试。用单步跟踪的方法验证指令的功能。1.2实验过程-a开始输入指令-t按步执行指令查看执行完一条指令屏幕显示所有寄存器内容和下一条指令地址和指令查找对应寄存器或内存地址的数据直接连续输入指令之后-t查找就可1.3实验结果实验二 数 据 的 建 立 与 传 送 程 序2.1实验内容在DEBUG状态下分别输入下面各程序段每输入完一个程序段用G命令进行连续方式执行程序在连续执行时要记录程序的执行结果。将一段从小到大又从大到小的数据存储又传递给其他的数据段。2.2实验过程1.第一段程序指令令cx等于数据块的个数31是根据数据地址循环递增进行传递数据2.第二段程序指令MOVSB字符串传送指令指令按字节进行传送地址通过SI和DI两个寄存器控制字符串的源地址和目的地址将DS:SI这段地址中字节复制到ES:DI指向的地址。3.第三第四段程序指令在使用REP MOVSB指令中将位于DS段的由SI所指向的存储单元的字节或字传送给位于ES段的由DI所指出的存储单元修改SI和DI从而指向下一个元素其中CLD和STD都是用于串操作指令中操作方向标志位DFCLD设置DF复位即DF0STD设置DF置位即DF1。4.注意跳转指令。5.-g命令完成指令执行结束指令时需要-gXXXX XXXX前一个地址是运行的程序开始的地址后一个地址是程序运行结束的地址否则会遇到程序运行卡住的问题。2.3实验结果1.在内存10000H单元开始建立00H0FH00H 31个数要求00H0FH数据逐渐增大,0FH00H逐渐减小。该程序从内存CS:0100H地址开始输入。代码如下示例MOV AX, 1000H MOV DS, AX MOV SI,0MOV CL, 0FH XOR AX, AX PPE1 MOV[SI], AL INC SI INC AL DEC CL JNZ PPE1 MOV CX, 10H PPE2 MOV[SI], AL INC SI DEC AL LOOP PPE2 INT 20H结果示例2.把上一个程序的执行结果(建立的31个字节数据块其首地址在10000H)分几种方式传送到以下指定的区域。(a)检查内存数据块的传送情况可用“D”命令。代码如下示例MOV AX, 1000H MOV DS, AX MOV SI,0MOV DI, 5050H MOV CX, 1FH;数据块长度是31 PPEA MOV AL,[SI]MOV[DI], AL INC SI INC DI LOOP PPEA INT 20H内存数据块如下示例(b)用串传送指令MOVSB把数据块传送到15150H开始的区域该程序从内存CS:0200H开始输入。代码如下示例检查程序最后的执行结果可用“D”命令例如D1000:5150↙内存数据块如下示例©用重复串操作指令“REP MOVSB”把数据块传送到15250H开始的区域。该程序从CS:250H地址开始输入。指令代码如下示例检查程序的最后执行结果时可用D1000: 5250↙内存数据块如下示例(d)用串操作的减量工作方式把数据块传送到25050H开始的区域。该程序从CS:0300H开始输入。指令代码如下示例检查程序的最后执行结果用D命令D2000:5050↙内存数据块如下示例实验3 分 支 程 序 设 计3.1实验内容3.1.1给出三个有符号数编写一个比较相等关系的程序(1)如果这三个数都不相等则显示0(2)如果这三个数中有两个数相等则显示1(3)如果这三个数都相等则显示23.1.2找出字符串的大写字母和小写字母从键盘上输入一串字符到输入缓冲区找出其中的大写字母和小写字母并分别统计它们的个数结果放到变量num1和num2中要求在屏幕输出显示所有字母及变量num1和num2的值。3.2实验过程CMP比效指令INC加一指令DEC减一指令JNB 大于等于JNBE 大于LOOP 循环控制指令在输出字符串的时候需要有“$”才可以停止输出字符串输入有符号的字符串以及直接输出十进制数字时引入含有调用输入输出子程序的声明语句和宏定义的文件io.inc。3.3实验结果3.3.1指令代码如下示例include io.inc .model small .stack .data msg1 db10,13,Please input var1:$msg12 db10,13,Please input var2:$msg13 db10,13,Please input var3:$msg2 db10,13,Please ouput:$msg3 db10,13,$var1 db ? var2 db ? var3 db ? .code .startup mov dx,offset msg1;提示输入字符串 mov ah,9 int 21h call readsib;输入第一个字符 mov var1,al mov bl,var1 mov dx,offset msg12;提示输入字符串 mov ah,9 int 21h call readsib;输入第二个字符 mov var2,al mov cl,var2 mov dx,offset msg13;提示输入字符串 mov ah,9 int 21h call readsib;输入第三个字符 mov var3,al mov al,var3 mov dx,offset msg2;输出结果 mov ah,9 int 21h mov dl,0;记录最终结果cmpbl,cl jne one;若不相等跳转 inc dl;若相等加一 one:cmp al,cl jne two inc dl two:cmp bl,al jne three inc dl three:cmp dl,3h jne last dec dl last:add dl,30h mov ah,02h int 21h end bash指令代码检测结果如下示例3.3.2指令代码如下示例include io.inc .model small .stack .data buffer db60;字符串所占的字节数 db ?;输入字符串字符个数自动填充 db60dup(0);数组存储输入字符串 msg1 db10,13,Please input:$msg2 db10,13,varL:$msg3 db10,13,varS:$msg4 db10,13,$msg5 db10,13,Please ouput:$varL db0;大写字母个数 varS db0;小写字母个数 .code .startup mov dx,offset msg1;提示输入字符 mov ah,9 int 21h lea dx,buffer;输入字符串 mov ah,0ah int 21h mov bl,buffer1;若为空cmpbl,0 jzexitlea si,buffer2;两个字节代表一个字 mov cl,bl again: mov al,BYTE ptr[si]cmpal,zjnbe next;比z大跳过cmpal,a;比z小 jnb number2;大于等于a,小写字母数字增加cmpal,Z;比a小 jnbe next;比Z大跳过cmpal,A;比Z小 jnb number1;大于等于A jmp next;比A小跳过 number1:inc varL jmp next number2:inc varS jmp next next:inc si loop again mov bh,0addbx,dx mov BYTE ptr[bx2],$mov buffer,13 mov buffer1,10 exit: mov ah,9 int 21h mov dx,offset msg2;大写字母个数 mov ah,9 int 21h mov al,varL call dispsib mov dx,offset msg3;小写字母个数 mov ah,9 int 21h mov al,varS call dispsib end指令代码检测结果如下示例实验4 分 支 程 序 设 计4.1实验内容设有 10 个学生的成绩分别为 56、69、84、82、73、88、99、63、100 和 80 分。试编制程序分别统计低于 60 分、6069 分、7079 分、8089 分、9099 分及 100 分的人数存放到 s5、s6、s7、s8、s9 及 s10 单元中。这一题目的算法很简单成绩分等部分采用分支结构统计所有成绩则用循环结构完成。4.2实验过程注意dw与db所占的字节不同dw占据内存两个字节db占据内存一个字节在循环程序中改变的量——所加的偏移地址是目标字符串的类型。编写将存放于 S5、S6、S7、S8、S9 及 S10 单元中的数据在屏幕上显示出来的部分程序。4.3实验结果指令代码如下示例;PROGRAM TITLE GOES HERE――result;************************************ DATAREA SEGMENT;DEFINE DATA SEGMENT GRADE DW56,69,84,82,73,88,99,63,100,80 S5 DW0S6 DW0S7 DW0S8 DW0S9 DW0S10 DW0DATAREA ENDS;************************************ PROGNAM SEGMENT;DEFINE CODE SEGMENT;---------------------------- MAIN PROC FAR;MAIN PART OF PROGRAM ASSUME CS:PROGNAM, DS:DATAREA START:;STARTING EXECUTION ADDRESS;SET UP STACK FOR RETURN PUSH DS;SAVE OLD DATA SEGMENT SUB AX,AX;PUT ZERO IN AX PUSH AX;SAVE IT ON STACK;SET DS REGISTER TO CURRENT DATA SEGMENT MOV AX,DATAREA;DATAREA SEGMENT ADDR MOV DS,AX;INTO DS REGISTER;MAIN PART OF PROGRAM GOES HERE MOV S5,0;INITIALIZE COUNTER MOV S6,0MOV S7,0MOV S8,0MOV S9,0MOV S10,0MOV CX,10;INITIALIZE LOOP COUNT VALUE MOV BX, OFFSET GRADE;INITIALIZE FIRST ADDR12 COMPARE: MOV AX,[BX];GET A RESULT CMP AX,60;60? JL FIVE CMP AX,70;70? JL SIX CMP AX,80;80? JL SEVEN CMP AX,90;90? JL EIGHT CMP AX,100;100? JNE NINE INC S10 JMP SHORT CHANGE_ADDR NINE: INC S9 JMP SHORT CHANGE_ADDR EIGHT: INC S8 JMP SHORT CHANGE_ADDR SEVEN: INC S7 JMP SHORT CHANGE_ADDR SIX: INC S6 JMP SHORT CHANGE_ADDR FIVE: INC S5 CHANGE_ADDR: ADD BX,2LOOP COMPARE MOV CX,6;设置6个成绩阶段 MOV SI,OFFSET S5;从S5开始输出 AGAIN:MOV DX,[SI];ADD DX,30H;将数字转化为字符 MOV AH,02;调用02号ah输出字符 INT 21H;MOV DL,20H;在屏幕上显示空格20h MOV AH,02;调用02号ah输出字符 INT 21H ADD SI,2;一个Sx是dw类型占据两个字节 LOOP AGAIN;RET;RETURN TO DOS MAIN ENDP;END OF MAIN PART OF PROGRAM;------------------------------ PROGNAM ENDS;*************************** END START;END ASSEMBLY指令执行结果如下示例实验5 学 生 成 绩 名 次 表 实 验5.1实验内容将 0100 之间的 10 个成绩存入首址为 1000H 的单元中。1000Hi 表示学号为 i 的学生成绩,编写程序能在 2000H 开始的区域排出名次表。2000Hi 为学号 i 的学生的名次。5.2实验过程调用子程序将十六进制转化为十进制对数值进行除10求余压栈最后再逐一出栈进行显示需要注意的是入口参数是ax而数值是al需要将al进行符号数扩展后再调用子程序。5.3实验结果指令代码如下示例include io.inc CRLF MACRO MOV DL, 0DH MOV AH, 02H;回车 INT 21H MOV DL, 0AH MOV AH, 02H;换行 INT 21H ENDM DATA SEGMENT STUNUM EQU10MESS DBINPUT 10 STUDENTS SCORE: ,0DH,0AH,$;提示输入10位同学的成绩 ERROR DBINPUT ERROR!,0DH,0AH,$;提示输入错误 ORG 1000H SCORE DB10DUP(?);成绩 ORG 2000H SEQU DB10DUP(?)DATA ENDS STACK SEGMENT STA DW12DUP(?)TOP DW ? STACK ENDS CODE SEGMENT ASSUME CS:CODE,DS:DATA,ES:DATA,SS:STACK START: MOV AX, DATA MOV DS, AX MOV ES, AX MOV SP, TOP;初始化 MOV DX, OFFSET MESS MOV AH, 09H INT 21H;显示提示输入信息 MOV SI, OFFSET SCORE;成绩表首址 MOV CX, STUNUM;学生数送CX UUU: CALL GETNUM;读取键入数值送DX MOV[SI], DL;存入成绩表缓冲区 INC SI;指向下一单元 LOOP UUU MOV CX, STUNUM;学生数 MOV DI, OFFSET SEQU;名次表首址 VVV: CALL SCAN;扫描子程序 MOV AL, STUNUM;学生数 SUB AL, CL INC AL;计算名次 MOV BX, DX MOV[DIBX], AL;记DX学号对应名次 LOOP VVV MOV CX, STUNUM;学生数 MOV SI, OFFSET SEQU;名次表首址 WWW: MOV AL,[SI]CALL DISP1 CRLF INC SI LOOP WWW;显示排定的学生名次 MOV AX, 4C00H INT 21H SCAN PROC NEAR;子程序,每扫描一遍成绩表缓冲区, 找出其中成绩最高者由DX指针指示对应学生 之后将该成绩清除以便下一次扫描 PUSH CX MOV CX, STUNUM;学生数 MOV AL, 00H;最低成绩 MOV BX, OFFSET SCORE MOV SI, BX;指向成绩表首址 CCC: CMP AL,[SI]JAE JJJ;AL中的成绩不低于成绩表指针SI所指单元的成绩则转JJJ MOV AL,[SI];AL存放较高的成绩 MOV DX, SI SUB DX, BX;DX为对应学号 JJJ:INC SI;指向下一单元 LOOP CCC ADD BX, DX MOV BYTE PTR[BX], 00H;本次扫描成绩最高者清0 POP CX RET SCAN ENDP DISP1 PROC NEAR PUSH CX MOV BL, AL MOV DL, BL MOV CL, 04 ROL DL, CL AND DL, 0FH CALL DISPL MOV DL, BL AND DL, 0FH CALL DISPL POP CX RET DISP1 ENDP DISPL PROC NEAR JMP DDD2;将程序跳转到DDD2 DDD2: MOV AL,DL;将dl中的值传递给al CBW;子程序传递参数是ax将al字符扩展到ax CALL EXCHANGE;调用子程序将16进制转化为10进制 RET EXCHANGE PROC;PUSH AX PUSH BX PUSH CX PUSH DX XOR CX,CX CMP AX,0 JNE L1;ax不为0 ADD AX,0;ax为0时特殊处理 PUSH AX MOV AX,0 MOV CX,1 L1:MOV BL,AL;ADD BL,AH CMP BL,0 JNE L2;除10取余数不为0 JMP L3 L2: MOV DL,10 DIV DL;除10求余保存 MOV BX,0 MOV BL,AH ADD BL,0PUSH BX;位数加1 INC CX;商作为被除数继续循环 MOV AH,0 JMP L1 L3: POP DX;为0跳出 MOV AH,2 INT 21H LOOP L3 POP DX POP CX POP BX POP AX JMP EXIT EXIT:RET EXCHANGE ENDP DISPL ENDP GETNUM PROC NEAR PUSH CX XOR DX, DX GGG: MOV AH, 01H INT 21H CMP AL, 0DH JZ PPP CMP AL, 20H JZ PPP SUB AL, 30H JB KKK CMP AL, 0AH JB GETS CMP AL, 11H JB KKK SUB AL, 07H CMP AL, 0FH JBE GETS CMP AL, 2AH JB KKK CMP AL, 2FH JA KKK SUB AL, 20H GETS: MOV CL, 04 SHL DX, CL XOR AH, AH ADD DX, AX JMP GGG KKK: MOV AH, 09H MOV DX, OFFSET ERROR INT 21H PPP: PUSH DX CRLF POP DX POP CX RET GETNUM ENDP CODE ENDS END START指令执行结果如下示例总结以上就是鄙人的汇编语言简明教程2021实验课报告其中实验实验过程部分是小人在实验过程中遇到的问题经查资料之后的总结请各位大人多多指教。