1. 程式人生 > >C++/C程式記憶體佈局及函式棧結構

C++/C程式記憶體佈局及函式棧結構

一:系統的程式佈局圖:

二、詳解:

程式空間:

包括.txt程式碼段,.data資料段, .bss段,堆段,棧段。程式的地址從低往高。堆空間增長方向從低地址往高地址增長。

棧空間從高地址往低地址方向增長。從左往右方向為單位元組增長方向。

棧空間:

棧空間由一個一個函式的棧幀構成,第一幀為main函式的棧幀。第二幀是被main函式呼叫的函式(假設為fun)的幀,

第三幀也就是當前幀是被fun呼叫的函式的棧幀。

第一幀的棧頂記憶體單元中值:0x7FFFFFFC,黃色標記,表示是第一幀的幀起始位置地址。

第二幀的棧頂記憶體單元值:0x7FFFFFF8,橙色標記,表示的是第二幀的幀起始位置地址。

當前幀的幀起始位置為0x7FFFF0C,綠色標記,由於當前幀是當前函式真正執行,其棧頂由ESP暫存器的值標記,

其幀起始位置存放在EBP中。

函式呼叫:

函式呼叫時,進入到被調函式中時,被調函式會保護前面的棧幀。並初始化本幀。

push %ebp    
mov %ebp, %esp

1)第一句:

把EBP儲存到棧中,也就是把前面一個棧幀的起始地址存入棧中。所以會出現前面所有棧幀的

棧頂都是存放了其自身幀起始地址(各種相同顏色的地址)。

2)第二句:

把esp的值存放到ebp中,此時esp指向當前函式的棧起始位置(因為剛進入函式,並未構建臨時變數),

那麼ebp就也指向了函式的棧幀起始位置。

3)所有函式呼叫都會重複以上步奏,那麼整個程式的棧空間都是類似的結構。

注:在被儲存的棧幀中,在棧頂記憶體單元中存放了幀起始的地址,緊接著其下,是被呼叫函式的返回地址,

再往下是第一個引數,再往下是第二個引數。