Memory
堆什麼時候用於動態記憶體分配?
每一篇關於記憶體分配的文章似乎都解釋瞭如何
mmap
使用或如何sbrk
使用,而不考慮如何將這些與堆關聯起來。我已經收集到堆在記憶體分配中的作用幾乎是微不足道的——事實上,我不確定它的作用:D,我請求有人讓我感到困惑。
這是我的理解:
- 當記憶體被分配時,未初始化數據段的末尾,BSS,被擴展。這種擴展(例如將地址移動
x
到x-n
)是呼叫 的結果sbrk
。在這個模型中,記憶體被分配到n
字節中(假設每個地址對應一個字節),這sbrk
減少了 BSS 段頭的位置。這個模型現在已經過時了。有些人將堆定義為所有此類擴展的聚合空間。其他人沒有——在後一種情況下,堆有什麼作用?2)在現代記憶體分配方案中,堆確實存在(出於什麼原因,我也不確定)。為了分配記憶體,
malloc
內部用於mmap
將數據儲存到作為頁面集合的記憶體區域中。這些記憶體區域獨立於堆。TLDR:
對於舊系統:如果記憶體分配儲存在增加末端 BSS 的偏移量後獲得的地址空間中,那麼堆是否有任何用途?
對於較新的系統:假設 mmap 主要用於記憶體分配,那麼堆的用途是什麼?
在這兩種情況下,堆真的有用嗎?
mmap
並且sbrk
是核心提供的用於為程序分配地址空間的系統呼叫。這些呼叫改變了虛擬地址到物理頁框的映射。在這些映射的地址限制之外定址記憶體是一個嚴格的禁忌,並且會導致分段錯誤。這是核心提供給程序的低級介面,以brk
地址結尾的記憶體區域通常稱為堆。核心不知道
malloc
orfree
,這些是 libc 中的庫函式。Libc 維護資料結構並記錄從記憶體分配的角度來看哪些記憶體區域是空閒的,例如 . 如果可以通過重用先前釋放的記憶體區域來滿足對的呼叫,則呼叫malloc
不一定會導致呼叫sbrk
或mmap
(取決於 Libc 如何實現動態記憶體分配)來擴展映射。malloc