1. 程式人生 > 實用技巧 >實驗2 彙編源程式編寫與彙編、除錯

實驗2 彙編源程式編寫與彙編、除錯

1. 實驗任務1

使用任意一款文字編輯器,編寫8086彙編源程式ex1.asm:

;ex1.asm
assume cs:code
code segment
  mov ax, 0b810h
  mov ds, ax
  mov byte ptr ds:[0], 1
  mov byte ptr ds:[1], 1
  mov byte ptr ds:[2], 2
  mov byte ptr ds:[3], 2
  mov byte ptr ds:[4], 3
  mov byte ptr ds:[5], 3
  mov byte ptr ds:[6], 4
  mov byte ptr ds:[7
], 4   mov ah, 4ch   int 21h code ends end

要求:使用8086彙編程式編寫、彙編、連結、執行、除錯方法,對ex1.asm進行彙編、連結、執行,使 用debug工具除錯可執行檔案。

使用masm、link對ex1.asm進行彙編、連結,得到可執行檔案ex1.exe,執行並觀察結果。

使用debug工具對程式進行除錯:

使用debug載入可執行檔案ex1.exe後,使用d命令檢視程式段字首PSP所佔的256個位元組。

結合可執行檔案中暫存器CX的值,使用u命令對ex1.exe進行精確反彙編

使用g命令執行到程式退出執行之前(即原始碼檔案中line16之前),觀察結果。

(1)首先編寫ex1.asm:

(2)對ex1.asm用masm工具進行彙編:

生成ex1.obj:

(3)再對生成的ex1.obj用link工具進行連線:

生成ex1.exe:

(4)直接執行ex1.exe:

發現並沒有任何內容輸出

(5)使用debug工具對程式進行除錯:

1)使用d命令檢視程式段字首PSP所佔的256個位元組:

2)結合可執行檔案中暫存器CX的值,使用u命令對ex1.exe進行精確反彙編:

3)使用g命令執行到line16退出執行之前:

2. 實驗任務2

使用任意一款文字編輯器,編寫8086彙編源程式ex2.asm:

; ex2.asm
assume cs:code code segment   mov ax, 0b810h   mov ds, ax   mov bx, 0   mov ax, 101H   mov cx, 4 s: mov [bx], ax   add bx, 2   add ax, 101H   loop s   mov ah, 4ch   int 21h code ends end

要求:使用8086彙編程式編寫、彙編、連結、執行、除錯方法,對ex2.asm進行彙編、連結、執行,使用debug工具除錯可執行檔案。

使用masm、link對ex2.asm進行彙編、連結,得到可執行檔案ex2.exe,執行並觀察結果。

使用debug工具對程式進行除錯:

結合可執行檔案中暫存器CX的值,使用u命令對ex2.exe進行精確反彙編

靈活使用t命令、p命令、g命令,對ex2.exe進行除錯。

把ex2.asm中line9 mov cx, 4 改成 mov cx, 8 ,儲存後重新彙編、連結、執行並觀察結果。

結合上述實驗和觀察,分析、對比ex2.asm和ex1.asm,它們實現的是否是相同的功能和效果?在 具體實現上有什麼不同?

(1)對ex2.asm進行彙編、連結、執行:

執行ex2.exe也無任何輸出

(2)使用debug工具對程式進行除錯:

1)結合可執行檔案中暫存器CX的值,使用u命令對ex2.exe進行精確反彙編:

2)靈活使用t命令、p命令、g命令,對ex2.exe進行除錯:

3)把ex2.asm中line9 mov cx, 4 改成 mov cx, 8 ,儲存後重新彙編、連結、執行並觀察結果:

3.結合上述實驗和觀察,分析、對比ex2.asm和ex1.asm,它們實現的是否是相同的功能和效果?在具體實現上有什麼不同?

答:兩者實現了相同的效果,但在功能上有所差別。ex1.asm是直接將資料存入記憶體裡,而ex2.asm是通過loop指令對一些大致相同且有規律可循的指令進行迴圈,從而縮短了程式碼。

3. 實驗任務3

綜合使用loop,[bx],編寫完整彙編程式,實現向記憶體b800:07b8開始的連續16個字單元重複填充字資料 0237H:

要求:

  • 編寫彙編源程式
  • 給出執行結果截圖
    1. 把填充的字資料,從0237H改成0239H,再次儲存後,彙編、連結、執行,觀察結果。
    2. 把填充的字資料,從0237H改成0437H,再次儲存後,彙編、連結、執行,觀察結果。
    3. 猜測並分析,這個字資料中高位位元組裡存放的是什麼資訊,低位位元組裡存放的是什麼資訊。

編寫程式碼:

;ex3.asm
assume cs:code
code segment
        mov ax,0b800H
        mov ds,ax

        mov bx,7b8H
        mov ax,0237H
        mov cx,10H
s:      mov [bx],ax
        add bx,2
        loop s

        mov ah,4ch
        int 21h
code ends
end

執行結果:

改成0239H後的執行結果:

改成0437H後的執行結果:

猜測並分析,這個字資料中高位位元組裡存放的是什麼資訊,低位位元組裡存放的是什麼資訊。

答:高位元組存放的是文字的顏色資訊,低位元組存放的是內容文字資訊。

4. 實驗任務4

編寫完整彙編源程式,實現向記憶體0:200~0:23F依次傳送資料0~63(3FH)。

編寫程式碼:

;ex4.asm
assume cs:code
code segment
    mov ax,0h
    mov ds,ax
    mov bx,0200h
    
    mov dx,0h    ;0~63(3fh)
    mov cx,40h
s:    mov ds:[bx],dl
    inc dx
    inc bx
    loop s
    
    mov ax,4c00h
    int 21h
code ends
end

對ex4.asm進行彙編、連線:

先使用u命令對ex4.exe進行精確反彙編:

先使用g命令除錯,然後在程式退出前,用d命令檢視 0:200~0:23F,確認是否將0~3F傳送至此段記憶體區域:

5. 實驗任務5

將“mov ax,4c00h"之前的指令複製到記憶體0:200處,補全程式。上機除錯,跟蹤執行結果:

補全程式碼:

;ex5.asm
assume cs:code
code segment
    mov ax,cs
    mov ds,ax
    mov ax,0020h
    mov es,ax
    mov bx,0
    mov cx,23
s:  mov al,[bx]
    mov es:[bx],al
    inc bx
    loop s

    mov ax,4c00h
    int 21h
code ends
end

對ex5.asm進行彙編、連線:

用r命令檢視記憶體,並用u命令進行反彙編:

使用g命令除錯程式,然後用d命令檢視0:200到217的位元組,再用u命令反彙編:

由上圖發現程式碼成功複製!

總結:

1.彙編和連線可以先輸入masm/link,再在後面輸入物件的檔名,也可以以簡化的方式進行,比如:masm ex1.asm;

2.ex1.exe與ex2.exe直接執行後並沒輸出結果,這是因為它們程式本身就不輸出任何東西,只有裡面的記憶體資料變了而已;

3.在遇到大量相似且有規律可循的程式碼,我們可以用loop指令去簡化程式碼。