前一段時間在面試總監的時候,總監問了我這樣的一個問題:你個我說說物理內存和虛擬內存究竟是怎麼一回事?
其實以前我看過這個問題,據我理解的,當時是這麼回答的「進程在運行的時候,操做系統都爲其分配一個4GB的地址空間,即所謂的虛擬地址空間,通常狀況下,當咱們的程序很大的時候,實際的物理內存根本不能知足咱們的需求的時候,這個時候操做系統就會藉助磁盤空間來作虛擬的內存空間,把當前進程不須要的數據放在磁盤上,等到用到的時候,在利用調度算法把所須要的數據從磁盤空間上調度到內存,虛擬內存就是爲了擴大內存的容量,每當咱們要運行一個程序的時候通過編譯之後造成的僅僅是邏輯上的空間,根本不是能夠直接運行的內存空間,因此它還存在一個地址映射的概念。」當時感受回答的非常籠統,只見總監在最後說了一句,你下去仍是把這一塊的內容在好好看看,因此今天就好好的把這個概念理一理。
首先我從最基本的概念提及,什麼是物理內存的概念,虛擬內存的概念?
物理內存,在應用中,天然是顧名思義,物理上,真實的插在板子上的內存是多大就是多大了。而在CPU中的概念,物理內存就是CPU的地址線能夠直接進行尋址的內存空間大小。好比8086只有20根地址線,那麼它的尋址空間就是1MB,咱們就說8086能支持1MB的物理內存,及時咱們安裝了128M的內存條在板子上,咱們也只能說8086擁有1MB的物理內存空間。同理咱們如今大部分使用的是32位的機子,32位的386以上CPU就能夠支持最大4GB的物理內存空間了。
先說說爲何會有虛擬內存和物理內存的區別。正在運行的一個進程,他所需的內存是有可能大於內存條容量之和的,好比你的內存條是256M,你的程序卻要建立一個2G的數據區,那麼不是全部數據都能一塊兒加載到內存(物理內存)中,勢必有一部分數據要放到其餘介質中(好比硬盤),待進程須要訪問那部分數據時,在經過調度進入物理內存。因此,虛擬內存是進程運行時全部內存空間的總和,而且可能有一部分不在物理內存中,而物理內存就是咱們平時所瞭解的內存條。有的地方呢,也叫這個虛擬內存爲內存交換區。關鍵的是不要把虛擬內存跟真實的插在主板上的內存條相掛鉤,虛擬內存它是「虛擬的」不存在,假的啦,它只是內存管理的一種抽象!
那麼,什麼是虛擬內存地址和物理內存地址呢。假設你的計算機是32位,那麼它的地址總線是32位的,也就是它能夠尋址0~0xFFFFFFFF(4G)的地址空間,但若是你的計算機只有256M的物理內存0x~0x0FFFFFFF(256M),同時你的進程產生了一個不在這256M地址空間中的地址,那麼計算機該如何處理呢?回答這個問題前,先說明計算機的內存分頁機制。
計算機會對虛擬內存地址空間(32位爲4G)分頁產生頁(page),對物理內存地址空間(假設256M)分頁產生頁幀(page frame),這個頁和頁幀的大小是同樣大的,因此呢,在這裏,虛擬內存頁的個數勢必要大於物理內存頁幀的個數。在計算機上有一個頁表(page table),就是映射虛擬內存頁到物理內存頁的,更確切的說是頁號到頁幀號的映射,並且是一對一的映射。可是問題來了,虛擬內存頁的個數 > 物理內存頁幀的個數,豈不是有些虛擬內存頁的地址永遠沒有對應的物理內存地址空間?不是的,操做系統是這樣處理的。操做系統有個頁面失效(page fault)功能。操做系統找到一個最少使用的頁幀,讓他失效,並把它寫入磁盤,隨後把須要訪問的頁放到頁幀中,並修改頁表中的映射,這樣就保證全部的頁都有被調度的可能了。這就是處理虛擬內存地址到物理內存的步驟。
如今來回答什麼是虛擬內存地址和物理內存地址。虛擬內存地址由頁號(與頁表中的頁號關聯)和偏移量組成。頁號就沒必要解釋了,上面已經說了,頁號對應的映射到一個頁幀。那麼,說說偏移量。偏移量就是我上面說的頁(或者頁幀)的大小,即這個頁(或者頁幀)到底能存多少數據。舉個例子,有一個虛擬地址它的頁號是4,偏移量是20,那麼他的尋址過程是這樣的:首先到頁表中找到頁號4對應的頁幀號(好比爲8),若是頁不在內存中,則用失效機制調入頁,不然把頁幀號和偏移量傳給MMU(CPU的內存管理單元)組成一個物理上真正存在的地址,接着就是訪問物理內存中的數據了。總結起來講,虛擬內存地址的大小是與地址總線位數相關,物理內存地址的大小跟物理內存條的容量相關。面試