Linux虛擬內(nèi)存管理基礎(chǔ)v2剖析_第1頁
Linux虛擬內(nèi)存管理基礎(chǔ)v2剖析_第2頁
Linux虛擬內(nèi)存管理基礎(chǔ)v2剖析_第3頁
Linux虛擬內(nèi)存管理基礎(chǔ)v2剖析_第4頁
Linux虛擬內(nèi)存管理基礎(chǔ)v2剖析_第5頁
已閱讀5頁,還剩19頁未讀, 繼續(xù)免費閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領(lǐng)

文檔簡介

1、Linux虛擬內(nèi)存管理基礎(chǔ)v2剖析3虛擬內(nèi)存管理的基本原理和基本過程。 CPU對虛擬內(nèi)存管理的支持。(ULK Ch.2)Linux如何管理頁表。(ULK Ch.2) Linux如何管理物理內(nèi)存(ULK Ch.8)Linux如何管理虛擬空間的內(nèi)核地址空間部分(ULK Ch.8) Linux如何管理虛擬空間的進程地址空間部分(ULK Ch.9) Linux如何在物理內(nèi)存和外出之間同步數(shù)據(jù)(ULK Ch.15)Linux如何主動回收物理內(nèi)存(ULK Ch.17)注:無法全部講 騷瑞4 Linux的虛擬內(nèi)存管理機制為應(yīng)用程序和驅(qū)動的虛擬內(nèi)存管理機制為應(yīng)用程序和驅(qū)動 程序提程序提供了兩種服務(wù):供了兩種服

2、務(wù): 使每個進程都擁有自己獨立的內(nèi)存地址空間;對于使每個進程都擁有自己獨立的內(nèi)存地址空間;對于32位位Linux而言,每個任務(wù)可尋址的內(nèi)存地址空間都為而言,每個任務(wù)可尋址的內(nèi)存地址空間都為0 x00000000 0 xFFFFFFFF(232, 4GB) 當(dāng)物理內(nèi)存不夠當(dāng)物理內(nèi)存不夠4GB時,虛擬內(nèi)存管理模塊會用外存時,虛擬內(nèi)存管理模塊會用外存空間模擬內(nèi)存空間,并且該模擬過程對應(yīng)用程序是透空間模擬內(nèi)存空間,并且該模擬過程對應(yīng)用程序是透明的。明的。5 Linux將每個進程的4GB的獨立地址空間又劃分為用戶地址空間(0 x00000000 0 xBFFFFFFF)和 內(nèi)核地址空間(0 xC0000

3、000 0 xFFFFFFFF)兩部分。 操作系統(tǒng)內(nèi)核代碼和數(shù)據(jù)存放在內(nèi)核地址空間;每個進程自己私有的代碼和數(shù)據(jù)存放在用戶地址空間 雖然Linux的內(nèi)核代碼和數(shù)據(jù)被映射到了每個進程的地址空間中(所有進程看到的內(nèi)容是相同的),但在實際的物理內(nèi)存中,只有內(nèi)核代碼和數(shù)據(jù)的一份拷貝。6用戶地址空間與內(nèi)核地址空間用戶地址空間與內(nèi)核地址空間用戶態(tài)與核心態(tài)用戶態(tài)與核心態(tài) 一般現(xiàn)代CPU都有幾種不同的指令執(zhí)行級別 在高執(zhí)行級別下,代碼可以執(zhí)行特權(quán)指令,訪問任意的物理地址,這種CPU執(zhí)行級別就對應(yīng)著內(nèi)核態(tài) 用戶態(tài)指相應(yīng)的低級別執(zhí)行狀態(tài),代碼的掌控范圍會受到限制,只能執(zhí)行CPU指令集的一個子集 舉例:intel

4、x86 CPU有四種不同的執(zhí)行級別0-3,Linux只使用了其中的0級和3級分別來表示內(nèi)核態(tài)和用戶態(tài) 0 xc0000000以上的內(nèi)核地址空間只能在內(nèi)核態(tài)下訪問,0 x000000000 xbfffffff的用戶地址空間在兩種狀態(tài)下都可以訪問 應(yīng)用程序可以通過Linux系統(tǒng)調(diào)用由用戶態(tài)進入內(nèi)核態(tài)8 邏輯地址:程序在運行過程中用來訪問存儲器的地址。程序員在編程時,只需知道邏輯地址,不需考慮該地址與實際物理硬件上的存儲單元如何對應(yīng)。編譯器在編譯源程序時,也只需考慮邏輯地址。 物理地址:表示物理存儲器中一個存儲單元的實際位置,地址總線上產(chǎn)生的就是物理地址。(總線地址) 在實地址模式下,邏輯地址等于物

5、理地址。在虛擬地址模式下,邏輯地址不等于物理地址,必須經(jīng)過查表才能轉(zhuǎn)換為物理地址,因此也叫虛擬地址。 線性地址:2維邏輯地址變?yōu)?維地址后,叫線性地址物理地址查表 轉(zhuǎn)換邏輯地址虛擬頁虛擬頁物理頁物理頁0 03 31 1nullnull2 21 13 3nullnull虛擬頁虛擬頁物理頁物理頁0 02 21 1nullnull2 21 13 3nullnull虛擬頁虛擬頁物理頁物理頁0 0nullnull1 1nullnull2 21 13 3nullnull物理頁物理頁takentaken進程進程idid0 0N Nnullnull1 1Y Yosos2 2Y Y2 23 3Y Y1 1進程

6、1 的頁表進程進程idid虛擬頁虛擬頁硬盤文件名硬盤文件名偏移量偏移量進程 2 的頁表進程 3 的頁表內(nèi)頁表外頁表CR3寄存器CPU負責(zé)查表(虛擬地址-物理地址),查表失敗時觸發(fā)缺頁異常(14號);OS負責(zé)填充各個表的內(nèi)容,并提供缺頁中斷的中斷服務(wù)器程序。10 MMU單元:(1)自動查表,將當(dāng)期指令中的邏輯地址轉(zhuǎn)化為物理地址; (2)觸發(fā)缺頁異常。 32bitCPU支持2級頁表:頁目錄表,頁表。10+10+12 64bitCPU支持4級頁表:9+9+9+9+12 專用寄存器CR3中存放了當(dāng)前有效的頁目錄表的物理地址。 專用寄存器CR2用于存放觸發(fā)缺頁異常的線性地址。 轉(zhuǎn)換旁視緩沖區(qū)TLB:將常

7、用的邏輯/物理轉(zhuǎn)換關(guān)系緩存到CPU。當(dāng)頁表被修改,或有效頁表切換時需調(diào)用專用指令刷新TLB。 flush_tlb_all, flush_tlb_mm, flush_tlb_range, flush_tlb_page11 在32位CPU上,地址空間為232,一個內(nèi)存頁大小為212,則共有220個頁,頁編號范圍0220-1,因此頁表中的一行至少要用3個字節(jié)(存儲頁編號是必須的),但實際上頁表中一行占4個字節(jié)。80386CPU中一個頁表項的定義如下:Present標(biāo)志、Accessed標(biāo)志、Dirty標(biāo)志、Read/Write標(biāo)志、User/Supervisor標(biāo)志、如果present標(biāo)志為0,分頁

8、單元就把這個線性地址存放在處理器的CR2寄存器中,并產(chǎn)生一個14號缺頁異常12 Present標(biāo)志:所指內(nèi)容是否存在 Accessded標(biāo)志:所指內(nèi)容被訪問之后自動置1 Dirty標(biāo)志:所指內(nèi)容被修改后自動置1 Read/Write標(biāo)志:所指內(nèi)容的讀寫權(quán)限 User/Supervisor標(biāo)志:所指內(nèi)容的訪問特權(quán)要求 PCD/PWT:是否運行被緩存至Cache PageSize:頁大小:4K,4M,2M Global標(biāo)志:防止頁從TLB中刷新出去13 為了節(jié)省內(nèi)存,32位CPU采用了兩級頁表第一級為頁目錄,每個表項存儲了第二級頁表的物理地址。 第二級頁表的每個表項存儲了一個虛擬頁所對應(yīng)物理頁的物

9、理地址。32位的虛擬地址被分成3個域目錄(directory)最高的10位頁表(Table)中間的10位頁內(nèi)偏移量(offset)最低的12位程序中每產(chǎn)生一個32位的虛擬地址,CPU的MMU首先用最高的10位查頁目錄獲得第二級頁表的物理地址,再用中間10位查第二級頁表獲得物理頁的起始地址,最后用該起始地址加上偏移量offset( 最低的12位 )就得到了最終的物理地址。1.兩次查表過程有可能會觸發(fā)2次缺頁中斷。2022-4-16Linux OS Analysis14/54Intel 80 x86處理器的分頁線性地址線性地址CR3頁目錄頁目錄頁表頁表頁頁2022-4-16Linux OS Ana

10、lysis15/54分頁舉例假設(shè)進程需要讀取0 x202X1406中的字節(jié)。分頁單元將該地址劃分為3個部分: 0 x202X1406=0010 0000 0000 0010 0001 0100 0000 0110b頁目錄索引(0 x80=128)頁表索引(0 x21)頁內(nèi)偏移(0 x406)CR3+p1的頁目錄p1的頁表+Present=0缺頁異常XxxxxxXxxxxXxxxxxxx16 如何將同一塊物理內(nèi)存同時映射到多個進程的地址空間中?(共享內(nèi)存是一種高效的進程間通信機制)如何將同一塊物理內(nèi)存同時映射到同一個進程地址空間的多個位置上? 。多個進程 同時裝載同一個動態(tài)鏈接庫時,該動態(tài)庫在每

11、個進程地址空間中的裝載位置相同嗎? 如何做到將Linux內(nèi)核代碼和數(shù)據(jù)映射到每個進程的地址空間,并且隨著進程切換只是改變用戶地址空間的內(nèi)容而內(nèi)核地址空間內(nèi)容保持不變? 已知工作在用戶態(tài)的應(yīng)用程序不能訪問內(nèi)核空間的內(nèi)存,那么如果一個應(yīng)用程序申請了一塊內(nèi)存,如果將指向該內(nèi)存的指針p傳遞給了一個內(nèi)核態(tài)程序(例如某中斷服務(wù)程序),那么內(nèi)核態(tài)程序能通過指針p訪問該內(nèi)存嗎?17如果一個物理頁中存儲了某個進程的代碼段,當(dāng)該物理頁因為內(nèi)存緊張需要被重新分配給另外的進程時,需不需要將該物理頁中的內(nèi)容回寫到磁盤交互文件中? 如何將一個硬盤文件映射到一個進程地址空間的指定位置上?(內(nèi)存映射函數(shù)mmap)對應(yīng)ARM等

12、不區(qū)分I/O地址空間和內(nèi)存地址空間的CPU,如果已經(jīng)知道了某外設(shè)寄存器的物理地址(通過該寄存器地址譯碼電路獲得),如何在Linux C程序中訪問該寄存器?void *ioremap(unsigned long phys_addr, unsigned long size)用于在頁表中增加一個物理地址到虛擬地址映射。如何設(shè)置內(nèi)存區(qū)域為“只讀”存儲區(qū)?如何以當(dāng)前進程為模板快速克隆出另外一個新的進程? (fork函數(shù)與Copy On Write技術(shù))如何實現(xiàn)物理內(nèi)存的“延遲分配”?18 int shmget(key_t key, size_t size, int flag);功能:得到一個共享內(nèi)存標(biāo)識

13、符或創(chuàng)建一個共享內(nèi)存對象并返回共享內(nèi)存標(biāo)識符key: 共享內(nèi)存對象的全局標(biāo)識,大于0的32位整數(shù)。通常要求此值來源于ftok返回的IPC鍵值。如果該內(nèi)存被映射到同一進程地址空間,則令key取值為IPC_PRIVATE。size:共享內(nèi)存區(qū)的字節(jié)數(shù)flag:讀寫的權(quán)限返回值:成功返回共享存儲的id,失敗返回-119 void *shmat(int shmid, const void *addr, int flag);功能:連接共享內(nèi)存標(biāo)識符為shmid的共享內(nèi)存,連接成功后把共享內(nèi)存區(qū)對象映射到調(diào)用進程的地址空間,隨后可像本地空間一樣訪問shmid:共享存儲的idaddr:一般為0,表示連接到由

14、內(nèi)核選擇的第一個可用地址上,否則,如果flag沒有指定SHM_RND,則連接到addr所指定的地址上,如果flag為SHM_RND,則地址取整flag:SHM_RDONLY:為只讀模式,其他為讀寫模式返回值:如果成功,返回共享存儲段地址,出錯返回-1int shmdt(void *addr);addr:共享存儲段的地址,以前調(diào)用shmat時的返回值返回值20int shmdt(void *addr);功能:與shmat函數(shù)相反,是用來斷開與共享內(nèi)存附加點的地址,禁止本進程訪問此片共享內(nèi)存addr:共享存儲段的地址,以前調(diào)用shmat時的返回值返回值:成功:0;出錯:-121 利用mmap函數(shù)可

15、以將一個磁盤文件或者其它設(shè)備對象映射到虛擬內(nèi)存空間。文件被映射到多個頁上,所有頁的大小之和大于等于文件大小。22void * mmap(void *start, size_t length, int prot , int flags, int fd, off_t offset)start:要映射到的虛擬內(nèi)存區(qū)域的起始地址,通常都是用NULL,NULL表示由內(nèi)核來指定該內(nèi)存地址length:要映射的內(nèi)存區(qū)域的大小prot:期望的內(nèi)存保護標(biāo)志,是以下的某個值,可以通過or運算符組合到一起1. PROT_EXEC 可執(zhí)行;2. PROT_READ可讀;3. PROT_WRITE可執(zhí)flags:指定映

16、射對象的類型,映射選項和映射頁是否可以共享。MAP_SHARED /MAP_PRIVATE/MAP_LOCKED/ MAP_ANONYMOUSfd:文件描述符(由open函數(shù)返回)offset:表示被映射對象(即文件)從那里開始對映,通常都是用0。 該值應(yīng)該為大小應(yīng)為PAGE_SIZE的整數(shù)倍 返回值:成功則返回被映射虛擬內(nèi)存區(qū)的指針,失敗返回-1。23 int munmap(void *start, size_t length)取消映射關(guān)系 int msync(const void *start, size_t length, int flags)將內(nèi)存中的內(nèi)容同步到文件 思考:思考:mmap函數(shù)執(zhí)行時會一次性將整個被映射文件讀入內(nèi)存嗎?即用mmap函數(shù)映射一個大文件時會很耗時嗎?24 快速讀寫大文件,簡化

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論