4.3. 基本的虛擬記憶體概念

現代儲存技術之後所用的科技著實令人印象深刻;但系統管理者不太需要了解這些細節。事實上,系統管理者只要記得一點就夠了:

記憶體永遠不夠!

這句話乍聽之下「笑」果十足;但事實上,作業系統的設計師早已花上許多精力,只為了解決記憶體不足的窘境。這方法就是「虛擬記憶體(virtual memory)」 — 將實際的 RAM 與較慢的硬碟結合起來,讓系統所擁有的記憶體看起來比實際的還多。

4.3.1. 虛擬記憶體的兩三事

我們就從一個假設性的應用程式看起。假設這個應用程式的機械碼大小為 10,000 位元組,還需要 5,000 位元組的空間儲存資料與 I/O 緩衝區。這表示這作業系統需要 15,000 位元組的記憶體才能執行;少一個位元組都不行。

這 15,000 位元組就稱為應用程式的「定址空間(address space)」,這是需要容納應用程式與其資料的獨一無二空間大小。在第一批電腦上,記憶體的大小就得比最大的應用程式還大;不然的話,執行這程式就會得到「記憶體不足」的錯誤訊息。

之後的解決方法稱為「覆疊(overlaying)」,能讓程式設計師決定在何時、應用程式的哪一個部份要載入到記憶體中。用這種方式,程式中初始化的部份只要在一開始的時候載入,然後接下來要運行的程式載入時,會覆蓋先前初始化的程式碼,以善用同一塊空間。覆疊功能可以減輕記憶體不足的問題,但這過程非常複雜,又容易出錯。覆疊也沒有辦法解決執行期間,整個系統記憶體不足的問題。換句話說,覆疊的程式所需的記憶體比沒有覆疊的程式要來得少,但如果系統的記憶體比覆疊過後的程式還少,那結果還是一樣的 — 「記憶體不足」。

虛擬記憶體則賦予應用程式的定址空間一個全新的意義:它不在乎應用程式執行時,需要多「」記憶體;相反地,它不斷的在尋找一個問題:「應用程式執行時,需要多麼『』的記憶體?」

根據我們假想的應用程式,它需要 15,000 位元組的空間,回想一下第 4.1 節中的討論 — 記憶體存取傾向於循序、發生在鄰近的地點。所以,同一時間內執行這應用程式所需的記憶體數量會低於 15,000 位元組 — 通常要低得多。想想一個執行週期所需要用到的記憶體存取類型:

每次存取所需要的記憶體數量會因為 CPU 的架構、實際指令、以及資料型態而有所不同。然而,即使每個指令存取記憶體時,會用到 100 位元組的記憶體,那麼總共 300 位元組還是遠低於 15,000 位元組的定址空間。如果我們有個方法可以在應用程式執行時,監控程式的記憶體使用量,那麼我們就可以用遠低於定址空間的記憶體,執行這個程式。

但這不禁讓我們想問一個問題:

如果在某個特定時間,應用程式有一部分在記憶體中,那麼其他部份到哪裡去了?

4.3.2. 後勤單位 — 虛擬記憶體的最高指導原則

這答案很簡單,應用程式的其他部份都在硬碟上。換句話說,硬碟就像記憶體的「後勤單位」;用空間大、速度慢的儲存媒體,當作速度快、容量小儲存媒體的「備用空間」。乍看之下,這似乎會產生很大的效能問題 — 畢竟硬碟要比記憶體慢得多。

這說的沒錯,但我們可以利用應用程式循序與鄰近的存取模式,讓硬碟太慢的效能問題降到最低。我們可以仔細架構虛擬記憶體子系統,以確保應用程式現在需要的部份 — 或很快就會用到的部份 — 能保存在記憶體中,讓真正需要的時候,立即派得上用場。

這觀念跟快取與主記憶體間的依存關係很像:結合小量的快速儲存空間、以及大量的慢速空間,成為一個看似又快又大的儲存體。

有了這點概念之後,我們就可以深入探討這個過程。