王爽彙編語言 一個奇怪的程序

這裏寫圖片描述

先大概分析分析:
程序從 start: mov ax, 0 開始運行,運行到s0時,已經將s處替換成了s2處的 jmp short s1. 而程序編譯後,s2處的彙編語句:jmp short s1對應的機器碼是:EBF6(F6即-10的補碼)。 也就是說,此刻s處對應機器碼是EBF6。
然後執行s0:jmp short s,程序跳回s處,此刻s處對應的機器碼是EBF6,執行這條指令,IP向上移動10,即指向cs:0000H,也就是mov ax, 4c00H處,然後繼續執行,程序正常返回

下面用debug跟蹤:
mov ax, 4c00H 076A:0000
int 21H 076A:0003

程序從此處(start:處)開始執行
mov ax, 0 076A:0005 IP = 0005H
nop 076A:0008 IP = 0008H
nop 076A:0009 IP = 0009H
mov di, offset s 076A:000A IP = 000AH
mov si, offset s2 076A:000D IP = 000DH
mov ax, cs:[si] 076A:0010 IP = 0010H
mov cs:[di], ax 076A:0013 IP = 0013H
執行完以上指令時,已經將s2處指令:jmp short s1 拷貝到s處,而s2處對應的機器碼是EBF6(下面解釋爲什麼是F6),故此時,076A:0008處的值是EBF6(兩個nop指令即跳過兩個字節,剛好EBF6也是兩個字節)

接下來這樣執行:
jmp short s 076A:0016 IP = 0016H
jmp 0008
跳回s處,即076A:0008處,接下來這樣執行:
jmp short s1 076A:0008 IP = 0018H
jmp 0000
這裏你可能就有疑問了,不是jump 到s1嗎,爲什麼對應 指令是jmp 0000.爲什麼?因爲:
jmp short s1對應的機器碼是EBF6(下面解釋爲什麼是F6),所以當程序運行到EBF6(即jmp short s1)時,先將EBF6緩存到指令緩衝區,IP+2(即IP變成000A),然後執行EBF6,而F6是-10的補碼,所以IP-10,即IP變成了0000,此時cs:0000剛好指向了mov ax, 4c00H 指令
所以,接下來這樣執行
mov ax, 4c00H
int 21H
然後程序正常返回退出

到這裏可能你就只剩下一個疑問了,爲什麼jmp short s1對應的機器碼是EBF6呢?
源程序經過編譯鏈接,將彙編指令變成對應的機器碼,jmp指令對應的機器碼中,EB後面的補碼(本處是F6)對應的源碼(本處是-10),直接決定了IP的偏移量。
那麼爲什麼是F6,這就要有jmp指令和對應的標識處的位置決定。
s1: mov ax, 0 076A:0018
int 21H 076A:001B
mov ax, 0 076A:001D
s2: jmp short s1 076A:0020
nop 076A:0022

看:0018H - 0022H = -000AH,也就是-10啦!!
至於爲什麼是0018H - 0022H,裏面涉及地址計數器(AC)的知識,若想了解,可以看看本書的附註3

發佈了23 篇原創文章 · 獲贊 22 · 訪問量 2萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章