先大概分析分析:
程式從 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
《組合語言》王爽 乙個奇怪的程式之EBF6
參照和注釋吧 assume cs codesg codesg segment mov ax,4c00h int 21h start mov ax,0 程式入口點 s nop 這個位置的內容稍後被替換了 當這裡第二次執行時,就是那句ebf6了 nop 這個位置的內容稍後被替換了 當這裡第二次執行時,就...
組合語言 王爽
cpu有三條匯流排 位址 資料 控制線 位址匯流排確定儲存單元 控制匯流排傳送指令 資料匯流排 傳輸資料 cpu n個位址線 位址匯流排寬度為n 可以尋找2 n個記憶體單元 儲存單元 0開始編號,乙個儲存單元可以儲存乙個byte 8086cpu有16根位址線 1bit就是一根位址線 注意 儲存器以b...
組合語言 《組合語言》王爽 實驗一
從 1000 0 開始寫入命令 a 1000 0 mov ax,4e20 add ax,1416 mov bx,2000 add ax,bx mov bx,ax add ax,bx mov ax,001a mov bx,0026 add al,bl add ah,bl add bh,al mov a...