執行retn、call、leave指令的時候,esp和eip的變化情況
阿新 • • 發佈:2019-01-29
windows 32位彙編的環境下
0A10FF61 call 0A11FFAA
0A10FF66 MOV EAX,DWORD PTR SS:[EBP+3C]
- call
CALL 地址1
功能:呼叫地址1處的子程式
CALL指令分為兩種情況,一種是段內轉移;另一種是段間轉移。這兩種情況類似於JMP指令的相對跳轉和絕對跳轉(只不過相對跳轉的JMP指令會有short標識)。
在CALL指令進行的是段內轉移的情況時,跟在CALL後面的地址1為一個相對位移;而CALL指令進行的是段間轉移的情況時,跟在CALL後面的地址1為一個絕對記憶體地址。
(1)段內轉移
push eip
jmp 目的位置
也就是說,執行段內轉移的CALL指令時,相當於先後執行以上兩條指令。
(2)段間轉移的CALL指令等價於三條指令:
push CS
push eip
jmp 目的位置
esp = esp - 4
[esp] = 0A10FF66 //將返回地址壓入棧中
eip = 0A11FFAA //跳轉到函式地址
2. retn
RETN/RETF是跳出子程式的指令,被稱為返回指令。RETN指令用於從段內轉移CALL進的子程式中返回;RETF指令用於從段間轉移CALL進的子程式中返回。
RETN/RETF在反彙編程式碼中呈現的形式如下:
RETN
RETN 運算元1
RETF
RETF 運算元1
RETN等價於一條指令:POP eip
RETF等價於兩條指令:
POP eip
POP CS
而帶有運算元的RETN/RETF指令則是在POP(ESP+4)之後,執行ESP=ESP+運算元1。
eip = [esp]
esp = esp + 4 //將esp中的資料出棧到eip中,同時ESP+4
3. leave
mov esp,ebp
pop ebp //還原函式棧