一条进程的栈区、堆区、数据区和代码区在内存中的映射
一條進程的棧區、堆區、數據區和代碼區在內存中的映射
?? ?1>棧區:主要用來存放局部變量, 傳遞參數, 存放函數的返回地址。.esp 始終指向棧頂, 棧中的數據越多, esp的值越小。
?? ?2>堆區:用于存放動態分配的對象, 當你使用 malloc和new 等進行分配時,所得到的空間就在堆中。動態分配得到的內存區域附帶有分配信息, 所以你 能夠 free和delete它們。
?? ?3>數據區:全局,靜態和常量是分配在數據區中的,數據區包括bss(未初始化數據區)和初始化數據區。
注意:
?? ?1)堆向高內存地址生長;
?? ?2)棧向低內存地址生長;
?? ?3)堆和棧相向而生,堆和棧之間有個臨界點,稱為stkbrk。
1、一條進程在內存中的映射
?? ?假設現在有一個程序,它的函數調用順序如下:
?? ?main(...) ->; func_1(...) ->; func_2(...) ->; func_3(...),即:主函數main調用函數func_1; 函數func_1調用函數func_2; 函數func_2調用函數func_3。
?? ?當一個程序被操作系統調入內存運行, 其對應的進程在內存中的映射如下圖所示:
?
?
注意:
?? ?1>隨著函數調用層數的增加,函數棧幀是一塊塊地向內存低地址方向延伸的;
?? ?2>隨著進程中函數調用層數的減少(即各函數調用的返回),棧幀會一塊塊地被遺棄而向內存的高址方向回縮;
?? ?3>各函數的棧幀大小隨著函數的性質的不同而不等, 由函數的局部變量的數目決定。
?? ?4>未初始化數據區(BSS):用于存放程序的靜態變量,這部分內存都是被初始化為零的;而初始化數據區用于存放可執行文件里的初始化數據。這兩個區統稱為數據區。
?? ?5>Text(代碼區):是個只讀區,存放了程序的代碼。任何嘗試對該區的寫操作會導致段違法出錯。代碼區是被多個運行該可執行文件的進程所共享的。? ?
?? ?6>進程對內存的動態申請是發生在Heap(堆)里的。隨著系統動態分配給進程的內存數量的增加,Heap(堆)有可能向高址或低址延伸, 這依賴于不同CPU的實現,但一般來說是向內存的高地址方向增長的。
?? ?7>在未初始化數據區(BSS)或者Stack(棧區)的增長耗盡了系統分配給進程的自由內存的情況下,進程將會被阻塞, 重新被操作系統用更大的內存模塊來調度運行。
?? ?8>函數的棧幀:包含了函數的參數(至于被調用函數的參數是放在調用函數的棧幀還是被調用函數棧幀, 則依賴于不同系統的實現)。函數的棧幀中的局部變量以及恢復該函數的主調函數的棧幀(即前一個棧幀)所需要的數據, 包含了主調函數的下一條執行指令的地址。
2、? 函數的棧幀
?? ?函數調用時所建立的棧幀包含下面的信息:
?? ?1)函數的返回地址。返回地址是存放在主調函數的棧幀還是被調用函數的棧幀里,取決于不同系統的實現;
?? ?2)主調函數的棧幀信息, 即棧頂和棧底;
?? ?3)為函數的局部變量分配的棧空間;
?? ?4)為被調用函數的參數分配的空間取決于不同系統的實現。
注意:
?? ?1>bss區(未初始化數據段):并不給該段的數據分配空間,僅僅是記錄了數據所需空間的大小。
?? ?2>data(初始化的數據段):為數據分配空間,數據保存在目標文件中。
?
http://zqwt.012.blog.163.com/blog/static/120446842010113091137224/
?
轉載于:https://www.cnblogs.com/liulipeng/p/3319675.html
總結
以上是生活随笔為你收集整理的一条进程的栈区、堆区、数据区和代码区在内存中的映射的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: C#数组按值和按引用传递数组区别
- 下一篇: 一、Cocos2dx在visualStu