虛擬內(nèi)存在操作系統(tǒng)里一直是一個(gè)很重要的概念挎扰,之前學(xué)過的都差不多忘記了在這里記錄一下翠订。首先要理解虛擬這個(gè)詞的含義。即在應(yīng)用程序運(yùn)行中看到的地址并不是真正的物理地址遵倦,而是經(jīng)過操作系統(tǒng)經(jīng)過映射后的虛擬地址尽超。那為什么要做呢?主要有以下幾個(gè)好處梧躺。
虛擬地址的意義
(1)給每個(gè)應(yīng)用程序提供了虛擬的獨(dú)立的地址空間似谁,程序員不需要關(guān)注內(nèi)存空間的地址結(jié)構(gòu),簡(jiǎn)化了鏈接和加載的過程(2)提供了安全性保證掠哥,在地址轉(zhuǎn)換的時(shí)候可以做安全性檢查巩踏,防止越權(quán)訪問。比如這個(gè)機(jī)制使得一個(gè)用戶態(tài)的程序試圖訪問內(nèi)核態(tài)的地址空間數(shù)據(jù)的時(shí)候MMU在映射時(shí)會(huì)檢測(cè)并阻止操作(3)提供了一定的共享機(jī)制续搀。雖然虛擬內(nèi)存使得程序隔離開來塞琼,但是我們可以使得不同的虛擬地址映射到同一塊物理地址實(shí)現(xiàn)共享。
現(xiàn)在我們需要了解一下這個(gè)映射的方式〗希現(xiàn)在的操作系統(tǒng)是使用的帶有多級(jí)頁表的段頁式映射彪杉。
分段
首先介紹一下什么是分段毅往。在一個(gè)程序運(yùn)行的時(shí)候可以分為數(shù)段比如代碼段,堆段派近,棧段等等攀唯。分段本質(zhì)就是把不同段映射到不同的物理地址,因?yàn)檫@些段關(guān)聯(lián)性較小沒有必要使用連續(xù)的地址空間渴丸。因此分段就誕生了侯嘀,他本質(zhì)是一個(gè)邏輯分段,分段在使用的時(shí)候需要指定段號(hào)和偏移量曙强。在進(jìn)行映射的時(shí)候使用哪一個(gè)段残拐,再加上后面的偏移量就可以得到真正的物理地址。每一個(gè)段的大小不一定一樣碟嘴。
分頁
分頁將物理地址分為了大小一致的幀(frame)溪食,并使用頁表(page table)來存儲(chǔ)每一個(gè)frame的起始位置。在將虛擬地址翻譯成物理地址的過程中先用高位作為虛擬頁號(hào)查詢頁表中的物理幀的地址再使用低位作為物理幀中的偏移量來獲得真實(shí)的物理地址娜扇。與分段不同的是虛擬頁和物理幀都是定長(zhǎng)的错沃。
頁表在使用的過程中存在著一些問題,具體原因有這兩個(gè)雀瓢。1.增加了訪問內(nèi)存的次數(shù)(因?yàn)槭褂昧隧摫硎辔觯黾恿嗽L問內(nèi)存的次數(shù))--> 解決方案是引入緩存TLB。頁表也是需要存儲(chǔ)的刃麸,占用了額外的內(nèi)存醒叁。由于這些段表頁表都是針對(duì)一個(gè)進(jìn)程存在的,如果進(jìn)程很多僅僅用來存儲(chǔ)頁表項(xiàng)的空間就要使用很大一部分空間泊业。 --> 使用多級(jí)頁表方案解決把沼。
TLB
TLB本質(zhì)就是緩存了從頁號(hào)到物理幀號(hào)的映射關(guān)系。如果TLB命中則不需要查詢頁表直接獲得幀號(hào)吁伺。如果沒有命中則需要更新TLB中的緩存項(xiàng)饮睬。少了一次查詢頁表的訪問內(nèi)存流程因此會(huì)更快。至于TLB緩存的淘汰機(jī)制留在下次記錄篮奄。
多級(jí)頁表
首先要知道多級(jí)頁表并不會(huì)擴(kuò)大尋址的空間捆愁,它存在的意義是提供更細(xì)粒度的控制減少頁表存儲(chǔ)的空間。具體操作就是在使用多級(jí)頁表的時(shí)候如果某一項(xiàng)沒有對(duì)應(yīng)的地址映射則后面更低級(jí)的就不再存儲(chǔ)窟却。有效的節(jié)省了頁表占用的空間昼丑。下面用圖來展示具體的流程。首先先看線性的頁表夸赫。
在線性頁表里即使不存在相關(guān)的項(xiàng)線性頁表也需要存儲(chǔ)導(dǎo)致空間的浪費(fèi)矾克。而在多級(jí)頁表中再第一級(jí)頁表中不存在的項(xiàng)相應(yīng)的二級(jí)頁表就不存在了,這就是多級(jí)頁表節(jié)省頁表大小的方式。多級(jí)頁表的第一級(jí)頁表一般是駐留在內(nèi)存里的胁附。
多級(jí)頁表的計(jì)算問題
在使用頁尋址機(jī)制的時(shí)候規(guī)定了邏輯的虛擬頁表和實(shí)際的幀大小一致酒繁,正是這個(gè)限制了尋址空間的大小。首先確定物理幀的大小決定了虛擬頁的大小控妻,虛擬頁的大小又限制了頁表里能夠存儲(chǔ)的頁表的項(xiàng)的大小州袒。多級(jí)頁表本質(zhì)是一個(gè)樹的結(jié)構(gòu)。如果頁太小的話單級(jí)頁表并不能并不能尋址到足夠多的空間弓候。涉及到一些計(jì)算問題在此記錄一下郎哭。
首先要會(huì)算尋址空間的大小。
比如一個(gè)頁表4KB每一個(gè)PTE 4B如果使用單級(jí)頁表能夠?qū)ぶ返目臻g為多少菇存? 首先我們可以知道一個(gè)頁表存儲(chǔ)了1K個(gè)頁表項(xiàng)夸研。每一個(gè)頁表項(xiàng)可以表示4K的空間。則尋址空間為1K * 4K = 4M依鸥。那二級(jí)頁表呢亥至?不論多少級(jí),頁表的大小是一樣的贱迟。那這樣第一級(jí)頁表也可以存儲(chǔ)1K的頁表項(xiàng)姐扮,而在一級(jí)頁表中的頁表項(xiàng)可以尋址4M,那么二級(jí)頁表就可以尋址1K * 4M = 4G的地址空間了衣吠。
如果知道了頁表大小和地址空間又應(yīng)該如何計(jì)算需要多少級(jí)頁表呢茶敏?
比如一個(gè)64的操作系統(tǒng),頁表大小為4K缚俏,每一個(gè)PTE為4B的話需要多少級(jí)頁表能夠覆蓋所有的地址空間惊搏?
首先還是可以知道一個(gè)頁表可以存儲(chǔ)1K個(gè)記錄。那我們需要多少個(gè)頁表記錄呢忧换?首先由于物理幀和頁大小是一樣的恬惯。如果頁表有4K,那么每一個(gè)物理幀也是4K包雀。我么知道PTE存的是frame的開始地址具體要到哪個(gè)地址需要offset宿崭。那這樣就需要有4K也就是2^12作為offset位亲铡。剩下的還有2^64/2^12 = 2 ^ 52才写。這個(gè)數(shù)據(jù)就是我們需要映射的頁表項(xiàng)的數(shù)目了。我們一級(jí)頁表可以映射1K也就是2^10個(gè)項(xiàng)奖蔓,每加一級(jí)頁表尋址空間都會(huì)擴(kuò)大1K倍赞草。6 * 10 > 52。所以我們需要6級(jí)頁表才能覆蓋所有的地址空間吆鹤。