多級頁表與快表


之前頁表結構的不足

之前的頁表結構看起來挺好的呀,有什么問題呢?

如果每個頁的大小是4k,也就是2的12次方。如果是32位的地址話,也就是說,有2的20次方個頁。

那么對應到頁表,也就說頁表應該有2的20次方個項。因為每個項表示的是一個內存地址,也就說一個項的大小是32位,也就是4個字節。

這樣算下來,對應於一個32位的內存地址,一個頁表應該4M大小。看起來還可以接受啊。

但注意,每個進程都有一個頁表。看下,我的電腦現在有280個進程,也就說如果采用之前的結構,光頁表結構就得占用280*4M=1120M,大約1個G的大小。如果是64位系統,會更加可怕。

引入多級頁表

之前的一級頁表,我們對於32位系統,4k為一頁的時候,我們如果要去訪問2的20次方的頁表,去查找空閑空間,或者訪問某一個頁內數據。

現在,我們采用多級頁表,如上圖所示的是二級頁表。

我們如果想訪問某一個地址,我們首先通過一個頁目錄號,在第一個頁表(頁目錄表)中獲得一個地址。這個地址指向第二個頁表的開始位置,然后用頁號作為偏移,在第二個頁表中獲得地址,進而訪問內存中的塊。

想象這樣一個場景:如果,你現在有一本書,你想跳轉到某一頁。這本書每一頁都沒有頁碼,只有目錄有相關頁碼。

我們想要翻到的頁碼,提供這些信息:

  • 它是屬於內存相關內容的
  • 它在所在章節開始位置處的第60頁

於是,你打開了目錄,但是這個目錄也跟平時不一樣,它只有顯示每一章的頁碼,比如:第一章,進程,100頁;第二章,內存,200頁。沒有節的頁碼。

現在,我們想訪問的內容知道是屬於第二章的,於是我們直接來到第200頁。

(我們從頁目錄表來到了第二級頁表)。

最后我們從這個位置,往后找到第60頁的位置。

(從二級頁表偏移頁號找到對應的頁)

多級頁表的內存占用

多級頁表的內存占用和 頁目錄號、頁號的位數分配有關系。假定我們假設頁目錄號、頁號各占10位。

在 Linux 0.11 中,頁目錄號是所有進程共享的,有的系統每個進程都有一個頁目錄號,當然也都有一個頁表。

所以,一個進程中有2的10次方(1K)的頁目錄表 和 2的10次方(1K)的頁號。因為每個表項大小為4字節,總共,一個進程才占 8K 而已。比之前的 4M,大大節省了內存。

快表

至此,看起來,已經優化的差不多了。

但是,人們不止於此,想進一步提高性能。那么如何提高性能呢?

緩存。

對於很多大量需要訪問的問題,都使用緩存,利用了程序的局部性原理。像我們的CPU的多級緩存都是使用這種原理。但是,一般緩存使用的寄存器價格都比較昂貴,所以一般存儲都有限。

快表,實質上也是緩存。

快表,TLB(translation lookasider buffer),翻譯后備緩沖器。

他就是保存最近的訪問的一些查表信息,如果有一個新的地址需要去訪問,先到 TLB 中看能不能找到,如果找不到,再按照之前的方式老老實實查詢,如果可以找到,直接返回結果。

更多細節,我們在后面講解。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM