最近看orange's 乙個作業系統的實現,對其中字串顯示函式dispstr中的語句 mov esi:[ebp+8]很是費解.為何只壓入了乙個字串首位址,這裡需要加上8才到字串首位址?要明白這個問題,需要了解函式呼叫前後堆疊指標esp的變化.
假設有個彙編函式test如下:
test:
push ebp ;保護先前ebp指標, ebp入棧(即0xaaaaab0入棧,注意與返回位址區別), esp-=4h, esp = 0xaaaaa99
mov ebp, esp ;設定ebp指標指向棧頂 0xaaaaa99
mov eax, dword ptr [ebp+0ch] ;ebp+0ch為0xaaaaaa6即引數2的位置
mov ebx, dword ptr [ebp+08h] ;ebp+08h為0xaaaaaa2,即引數1的位置
sub esp, 8 ;區域性變數所佔空間esp-=8, esp = 0xaaaaa91
...add esp, 8 ;釋放區域性變數, esp+=8, esp = 0xaaaaa99
pop ebp ;出棧,恢復ebp, esp+=4, esp = 0xaaaaa9d,即把棧中位址0xaaaaa9d的內容pop到ebp中
ret 8 ;ret返回,彈出返回位址,esp+=4, esp=0xaaaaaa2, 後面加運算元8為平衡堆疊,esp+=8,esp=0xaaaaaaa, 恢復進入函式前的堆疊.
ebp是當前函式的訪問指標,即儲存或者讀取數時的指標基位址;esp就是當前函式的棧頂指標。每一次發生函式的呼叫(主函式呼叫子函式)時,在被呼叫函式初始時,都會把當前函式(主函式)的ebp壓棧,以便從子函式返回到主函式時可以獲取ebp。
假設test函式在呼叫時會提前壓入兩個引數,那麼esp的變化會如下
假設執行函式前堆疊指標esp為0xaaaaaaa ;ebp為0xaaaaab0
push p2 ;引數2入棧, esp -= 4h , esp = 0xaaaaaaa - 4h = 0xaaaaaa6
push p1 ;引數1入棧, esp -= 4h , esp = 0xaaaaaaa - 8h = 0xaaaaaa2
call test ;壓入返回位址 esp -= 4h, esp = 0xaaaaaaa- 0ch = 0xaaaaa9d,注意:這裡是test函式的返回位址,即在**段中的位址(偏移)。
最後call test之所以會有資料入棧,是因為test函式內部第一行有個push ebp
專案一筆記
1.hibernate持久層的通用實現 public class basedaoimplextends hibernatedaosupport implements ibasedao 在父類 basedaoimpl 的構造方法中動態獲得entityclass public basedaoimpl 2...
理解矩陣 一 筆記
僅記錄學習孟巖老師的 blog 時的收穫,孟巖老師的原文章見 1 空間的本質特徵 容納運動。事實上,不管是什麼空間,都必須容納和支援在其中發生的符合規則的運動 變換 你會發現,在某種空間中往往會存在一種相對應的變換,比如拓撲空間中有拓撲變換,線性空間中有線性變換,仿射空間中有仿射變換,其實這些變換都...
Python基礎一筆記
變數.rstrip 是刪除字串末尾空白,變數.lstrip 是刪除字串開頭空白,變數.strip是同時剔除字串兩端的空白 在列表中插入元素 使用變數.insert 引數1 列表中的位置,引數2 在這個位置處插入乙個元素 在列表中刪除元素 使用del語句 del 變數名 位置索引 注 使用del語句刪...