線性位址 2

2021-06-22 21:52:32 字數 3474 閱讀 1943

linux核心對整個系統的物理記憶體是通過型別為struct page的陣列mem_map來管理的。系統中的夥伴系統分配演算法最終是通過操作這個陣列來記錄物理記憶體的分配、**等操作。在這裡不要被系統的高階記憶體、低端記憶體等概念搞混淆了,高、低端記憶體的分類主要在於區分物理記憶體位址是否可以直接對映到核心線性位址空間中。

我們知道,linux的核心位址空間大小為1g

(使用者空間

0~3g

,核心空間

3g~4g

,這種分法最常見),因此如果把這1g線性位址空間全部拿來直接一一對映物理記憶體的話,在核心態的所有程序(執行緒)能使用的物理記憶體總共最多只有1g,為了能使在核心態的所有程序能使用更多的物理記憶體,linux

採取了一種變通的形式:

它將1g

核心線性位址空間分為幾部分,第一部分為

1g的前

896m

,這部分核心線性空間與物理記憶體的

0~896m

一一對映(相差乙個為

0xc0000000

3g

的常數),後面

128m

的線性空間拿來動態對映剩下的所有物理記憶體,

由於動態對映的方法不一樣,後面的128m又分成了幾個部分,有興趣的可以檢視相關資料。在這裡,前面896m

線性空間對應的物理記憶體就是所謂的低端物理記憶體,剩下的物理記憶體就是高階物理記憶體。

從上面高、低端物理記憶體命名的由來我們可以知道,高、低端物理記憶體與具體的記憶體分配演算法無關,它們都是被mem_map陣列控制起來,再由夥伴分配系統實施管理。

關於程序及其記憶體分配

首先要明白乙個概念:

程序中使用的所有位址都是虛位址

。linux中程序可執行在使用者態和核心態,(典型配置情況下)當程序執行在使用者態時,它使用的線性位址只能位於0~3g範圍內,當程序執行於核心態時,它使用的線性位址位址範圍為3g~4g。

當程序執行於使用者態時,若其需要申請記憶體空間,核心首先會在其使用者線性空間中分配需要的線性位址空間,再通過夥伴分配系統分配物理記憶體並把分配的物理記憶體跟使用者空間線性位址對映起來,最後再修改程序的頁目錄項及頁表項寫入這些對映關係。

注;邏輯位址(

logical address

你在進行

c語言指標程式設計中,可以讀取指標變數本身值

(&操作

),實際上這個值就是邏輯位址

,它是相

對於你當前程序資料段的位址,不和絕對實體地址相干。只有在

intel

實模式下,邏輯位址才和實體地址相等(因為實模式沒有分段或分頁機制

,cpu

不進行自動位址轉換);邏輯也就是在

intel

保護模式下程式執行**段限長內的偏移位址(假定**段、資料段如果完全一樣)。應用程式設計師僅需與邏輯位址打交道,而分段和分頁機制對您來說是完全透明

的,僅由系統程式設計人員涉及。應用程式設計師雖然自己可以直接操作記憶體,那也只能在作業系統給你分配的記憶體段操作。

線性位址(

linear address

是邏輯位址到物理位址變換之間的中間層

。程式**會產生邏輯位址,或者說是段中的偏移位址,加上相應段的基位址就生成了乙個線性位址。如果啟用了分頁機

制,那麼線性位址可以再經變換以產生乙個實體地址。若沒有啟用分頁機制,那麼線性位址直接就是實體地址。

intel 80386

的線性位址空間容量為4g(

2的32次方即

32根位址匯流排定址)。

實體地址(

physical address

是指出現在

cpu外部位址匯流排上的定址物理記憶體的位址訊號,是位址變換的最終結果位址

。如果啟用了分頁機制,那麼線性位址會使用頁目錄和頁表中的項變換成實體地址。如果沒有啟用分頁機制,那麼線性位址就直接成為實體地址了。

虛擬記憶體(

virtual memory

是指計算機呈現出要比實際擁有的記憶體大得多的記憶體量。

因此它允許程式設計師編制並執行比實際系統擁有的記憶體大得多的程式。這使得許多大型專案也能夠在具有有限

記憶體資源的系統上實現。乙個很恰當的比喻是:你不需要很長的軌道就可以讓一列火車從上海開到北京。你只需要足夠長的鐵軌(比如說

3公里)就可以完成這個任

務。採取的方法是把後面的鐵軌立刻鋪到火車的前面,只要你的操作足夠快並能滿足要求,列車就能象在一條完整的軌道上執行。這也就是虛擬記憶體管理需要完成的

任務。在

linux 0.11

核心中,給每個程式(程序)都劃分了總容量為

64mb

的虛擬記憶體空間。因此程式的邏輯位址範圍是

0×0000000

到0×4000000

。與實體地址空間類似,線性位址空間也是平坦的

4gb位址空間,位址範圍從0到

0xffffffff

,線性空間中含有為系統定義的所有段和系統表。

有時我們也把邏輯位址稱為虛擬位址。因為與虛擬記憶體空間的概念類似,邏輯位址也是與實際物理記憶體容量無關的。

邏輯位址與實體地址的「差距

」是0xc0000000

,是由於虛擬位址

->

線性位址

->

物理位址對映正好差這個值。這個值是由作業系統指定的。

虛擬位址到實體地址的轉化方法是與體系結構相關的。一般來說有分段、分頁兩種方式。以現在的

x86 cpu

為例,分段分頁都是支援的。

memory mangement unit

負責從虛擬位址到實體地址的轉化。邏輯位址是段標識

+段內偏移量的形式,

mmu通過查詢段表,可以把邏輯位址轉化為線性位址。如果

cpu沒有開啟

分頁功能,那麼線性位址就是實體地址;如果

cpu開啟了分頁功能,

mmu邏輯位址

—-(段表)

—>

線性位址

— (頁表)

—>

實體地址

不同的邏輯位址可以對映到同乙個線性位址上;不同的線性位址也可以對映到同乙個實體地址上;所以是多對一的關係。另外,同乙個線性位址,在發生換頁以後,也可能被重新裝載到另外乙個實體地址上。所以這種多對一的對映關係也會隨時間發生變化。

this entry was posted in

linux,

核心 and tagged

kernel,

linear address,

linux,

longical address,

physical address,

process,

virtual memory,

核心,

蟈蟈每日程式小結 on

2013/04/01 by

shaoguangleo.

線性位址的管理

eprocess中 為什麼採用二叉樹的方式管理線性位址空間呢?最主要的原因是使用二叉樹查詢的效能會更好 涉及資料結構 這個startin pn和這個endin pn是以頁為單位也就是 4kb 0x1000 在startin pn這個位址後新增3個0,也就是這個結點描述的線性位址的起始位址 endin...

線性位址和實體地址

在保護模式下32位 還是採用段機制訪問記憶體 初始化臨時的要進入到ia 32e模式的gdt資料結構 label gdt64 dq 0x0000000000000000 label desc code64 dq 0x0020980000000000 label desc data64 dq 0x000...

邏輯位址,線性位址,實體地址

邏輯位址轉線性位址 機器語言指令中出現的記憶體位址,都是邏輯位址,需要轉換成線性位址,再經過 mmu cpu中的記憶體管理單元 轉換成實體地址才能夠被訪問到。我們寫個最簡單的 hello world 程式,用 gcc 編譯,再反彙編後會看到以下指令 mov 0x80495b0 eax 這裡的記憶體位...