1. 程式人生 > >硬碟分割槽、定址和系統啟動過程(轉)

硬碟分割槽、定址和系統啟動過程(轉)

前言筆記:

為了遮蔽複雜的硬體細節,現代的磁碟普遍使用一種叫做LBA(Logical Block Address)的方式,即整個磁碟中所有的扇區從0開始編號,一直到最後一個扇區,這個扇區編號叫做邏輯扇區號。邏輯扇區號拋棄了所有複雜的磁軌、盤面之類的概念。當我們給出一個邏輯的扇區號時,磁碟的電子裝置會將其轉換成實際的盤面、磁軌等這些位置。

檔案系統儲存了這些檔案的儲存結構,負責維護這些資料結構並且保證磁碟中每個扇區能夠有效的組織和利用。當Linux系統要讀取一個檔案的前4096個位元組時,我們會使用一個read系統呼叫來實現。檔案系統收到read請求後,判斷這個檔案的前4096個位元組位於磁碟的1000號邏輯扇區到1007號邏輯扇區。然後檔案系統就向硬碟驅動發出一個讀取邏輯扇區為1000號開始的8個扇區請求,磁碟驅動程式收到這個請求之後就向硬碟發出硬體命令。(注:紅標部分摘抄自《程式設計師的自我修養》)

硬碟物理結構

先看下硬碟物理結構

1 硬碟物理結構

硬碟物理上主要是碟片、機械手臂、磁頭、和主軸等組成。在碟片邏輯劃分上又分為磁軌、扇區,例如下圖:

2 碟片磁軌、扇區

磁軌:

當硬碟碟片旋轉時,磁頭若保持在一個位置上,則磁頭會在碟片表面劃出一個圓形軌跡,這些圓形軌跡就叫做磁軌。以碟片中心為圓心,由此可以劃分出很多磁軌來, 這些磁軌用肉眼是根本看不到的,因為它們僅 是盤面上以特殊方式磁化了的一些磁化區,硬碟上的資訊便是沿著這樣的軌道存放的,碟片上的磁軌由外向內依次從“0”開始進行編號。

柱面:

由於硬碟可以由很多碟片組成,不同碟片的相同磁軌就組成了柱面(cylinder),如圖1所示。

磁頭:

假設有N個碟片組成的硬碟,那麼有2N個盤面(一個碟片有2面),那麼磁頭也就有2N個,即每個盤面有一個磁頭。

扇區 :

早期的硬碟碟片的盤面以圓心開始向外放射狀將磁軌分割成等分的弧段,這些弧段便是硬碟的扇區(如圖2)。每個扇區一般規定大小為512byte,這裡大家應該比較疑惑,外圈周長很明顯比內圈要長,怎麼可能每個扇區都是512byte?其實答案早期硬碟外圈儲存比內圈儲存密度低一些,所以外圈很長但是仍然只能儲存512byte,因此如果我們知道了柱面數(磁軌數) Cylinders、磁頭數Heads、扇區數Sectors,基本上硬碟的容量我們能夠計算出來 硬碟總容量= Cylinders * Heads * Sectors * 512byte。 但是由於早期硬碟外圈密度低,導致碟片利用率不高,現在的硬碟碟片則採用內外儲存密度一致的方式,每個磁軌都劃分成以512byte大小的弧段,這樣也造成了內外磁軌上扇區數量會不一樣,外圈上的扇區數要多於內圈扇區數。

硬碟定址方式

硬碟存取、讀取資料,首先要做的就是定址,即定位到資料所在的實體地址,在硬碟上就要找到對應的柱面、磁頭以及對應的扇區,那麼怎麼定址呢?   有兩種方式:CHS和LBA

CHS模式:

CHS(Cylinder/Head/Sector)定址模式也稱為3D模式,是硬碟最早採用的定址模式,它是在硬碟容量較小的前提下產生的。

硬碟的C/H/S 3D引數既可以計算出硬碟的容量,也可以確定資料所在的具體位置。這是因為扇區的三維實體地址與硬碟上的物理扇區一一對應,即三維實體地址可完全確定硬碟上的物理扇區。三維實體地址通常以C/H/S的次序來書寫,如C/H/S為0/1/1,則第一個數字0指0柱面,第二個數字1指1磁頭(盤面),第三個數字1指1扇區,表示該資料位於硬碟1盤面上的0磁軌1扇區。現在定位已完成,硬碟內部的引數和主機板BIOS之間進行協議,正確發出定址訊號,從而正確定位資料位置。

早期硬碟一個磁軌上分63個扇區,物理磁頭最多16個(8個碟片,碟片多了硬碟那就真要加厚了)。採用8位定址方式,8位二進位制位的最大值是256(0-255),可以表示磁頭數,而扇區只有63個(1-63),只需要其中6個二進位制位即可表示,剩下2位拿去表示柱面,柱面數用10(8+2)位來表達,達到1024個柱面(0-1023),因此總扇區數(1024×16×63)。前面說一個扇區大小為512byte,這也就是說,如果以C/H/S定址模式定址,則IDE硬碟的最大容量只能為1024×16×63×512B= 500MB左右。

   可以思考下,在8位定址模式下,其實可以定址的硬碟最大容量為1024×256×63×512B =8G,那為啥CHS模式硬碟只支援到500MB呢?原因很簡單,我們的硬碟碟片不可能讓128片碟片重疊起來吧,那會是多厚??如果採用28位定址方式,那麼可以定址137G,碟片也不可能一直堆疊下去。  

LBA(Logical Block Addressing)

   經常去買硬碟的人都知道,目前硬碟經常都說單碟、雙碟,其實意思就是說硬碟碟片只有1個或者2個,而且都只是用一面,單碟一個磁頭而已,但是硬碟容量確是幾百G,而且硬碟柱面往往都大於1024個柱面,CHS是無法定址利用完這些硬碟容量的。

另外由於老硬碟的扇區劃分方式對硬碟利用率不高,因此出現了現在的等密度盤,外圈的扇區數要比內圈多,原來的3D定址方式也就不能適應這種方式,因此也就出現了新的定址方式LBA,這是以扇區為單位進行的線性定址方式,即從最外圈柱面0開始,依次將扇區號編為0、1….等等,舉個例子,假設硬碟有1024個柱面,由於是等密度硬碟,柱面0(最外圈)假設有128個扇區,依次編號為0-127,柱面1有120個扇區,則依次編號為127-246,…..依次最內圈柱面127只有扇區64個,則編號到最後。因此要定位到硬碟某個位置,只需要給出LBA數即可,這個就是邏輯數。

   在 LBA 模式下,為了保留原來CHS時的概念,也可以設定柱面、磁頭、扇區等引數,但是他們並不是實際硬碟的物理引數,只是為了計算方便而出的一個概念,1023之前的柱面號都一一物理對應,而1023以後的所有柱面號都記錄成1023磁頭最大數可以設定為255,而扇區數一般是每磁軌63個,硬碟控制器會把由柱面、磁頭、扇區等引數確定的地址轉換為LBA數。這裡我們再此明確兩個概念:

 物理扇區號:

一般我們稱CHS模式下的扇區號為物理扇區號,扇區編號開始位置是1

 邏輯扇區號:

LBA下的編號,扇區編號是從0開始。

CHS模式轉換到邏輯扇區號LBA

計算公式

LBA(邏輯扇區號)=磁頭數 × 每磁軌扇區數 × 當前所在柱面號 + 每磁軌扇區數 × 當前所在磁頭號 + 當前所在扇區號 – 1

例如:CHS=0/0/1,則根據公式LBA=255 × 63 × 0 + 63 × 0 + 1 – 1= 0

也就是說物理0柱面0磁頭1扇區,是邏輯0扇區。

硬碟分割槽

我們知道,一般使用硬碟,我們首先會對硬碟進行分割槽,然後對分割槽使用某個檔案系統格式(NTFS、FAT、ext2/ext3)進行分割槽格式化,然後才能正常使用。那麼分割槽是怎麼回事呢?我們常見的windows中說到的c、d、e盤是怎麼劃分出來的呢?其實,在裝windows系統過程中,一般我們只需要填寫每個分割槽的大小,看不出來分割槽過程的實際工作情況,我們可以從linux系統分割槽過程反而能反應底層實際分割槽情況。

柱面是分割槽的最小單位,即分割槽是以某個某個柱面號開始到某個柱面號結束的。

如圖,柱面1~200我們可以分為一個區,柱面201~500再劃分為一個區,501~1000再劃分為一個區,以此類推。大家可以看到,柱面0沒有在任何分割槽裡面,為何?這裡說說,前面說到硬碟從外圈(柱面0)到內圈扇區是依次編號,看似各個扇區沒有什麼區別,但是這裡硬碟的柱面0的第一個扇區(邏輯扇區0,CHS表示應該是0/0/1)卻是最重要的,因為硬碟的第一個扇區記錄了整個硬碟的重要資訊,第一個扇區(512個位元組)主要記錄了兩部分:

①    MBR(Master Boot Record):主載入程式就放在這裡,主載入程式是引導作業系統的一個程式,但是這部分只佔446位元組。

②    DPT(Disk Partition table):硬碟分割槽表也在這裡,分割槽表就是用來記錄硬碟的分割槽情況的,例如c盤是1~200柱面,d盤是201~500柱面,分割槽表總共只佔64位元組,可以看出,分割槽其實很簡單,就是在這個表裡面修改一下記錄就重新分割槽了,但是由於只有64位元組,而一條記錄就要佔用16位元組,這個分割槽表最多隻能記錄4個分割槽資訊,為了繼續分出更多分割槽來,引入了擴充套件分割槽的概念,也就是說,在這4個分割槽中,可以使用其中一條記錄來記錄擴充套件分割槽的資訊,然後在擴充套件分割槽中再繼續劃分邏輯分割槽,而邏輯分割槽的分割槽記錄則記錄在擴充套件分割槽的第一個扇區中,如此則可以像連結串列一樣劃分出很多分割槽來。但是請注意,一個分割槽表中可以有1~4條主分割槽,但是最多隻能有1個擴充套件分割槽。

舉例,主分割槽可以是P1:1~200,擴充套件分割槽P2: 2~1400,擴充套件分割槽開始的第一個扇區可以用來記錄擴充套件分割槽中劃分出來的邏輯分割槽。

分割槽錶鏈

       分割槽表之間是如何關聯的,詳細講一下,分割槽表是一個單向連結串列,第一個分割槽表,也就是位於硬碟第一個扇區中的DPT,可以有一項記錄擴充套件分割槽的起始位置柱面,類似於指標的概念,指向擴充套件分割槽(圖3),根據這項記錄我們可以找到擴充套件分割槽的某柱面0磁頭1扇區(CHS),而這個扇區中又存放了第二個分割槽表,第二個分割槽表第一項記錄一般表述了當前所在的邏輯分割槽的起始/終止柱面,第二項記錄表述了下一個邏輯分割槽所在的0磁頭1扇區(CHS),第三、第四項記錄不存任何資訊(圖4)。

  請看下圖,主引導記錄/分割槽表所在的是硬碟第一個分割槽,基本分割槽1、基本分2、基本分割槽3都是主分割槽、擴充套件分割槽內有2個邏輯分割槽,每個邏輯分割槽的第一個扇區都是分割槽表,至於引導扇區(DBR),在系統啟動一節中會提及。

系統啟動:

 之前提到MBR中安裝的引導載入程式,他的作用是什麼?

①    提供開機選單選項:可以供使用者選擇啟動哪個作業系統,這是多重引導功能。

②    載入作業系統核心:每個作業系統都有自己的核心,需要載入程式來載入

③    轉交給其他載入程式:可以將工作移交給其他載入程式來進行上述操作。

  其實引導載入程式除了可以安裝在MBR中,還可以直接安裝在每個分割槽的引導扇區(DBR)中,注意下,每個分割槽(主分割槽、邏輯分割槽)都有一個自己的啟動扇區,專門用來安裝引導載入程式,如上圖示3結構圖。

系統啟動過程:

①    首先,BIOS啟動後,讀取硬碟第一個扇區MBR中的引導載入程式(可能是windows或者linux的grub)

②    MBR中的載入程式提供開機選單,你可以選擇1)直接載入windows 核心 2)將工作轉交給windows 分割槽內的引導扇區中的載入程式,讓他自己去載入核心 3)轉交給linux分割槽內引導扇區,讓他去載入linux.

③    根據使用者選擇的選項和引導載入程式中記錄的分割槽,到分割槽表找對應的分割槽柱面號等分割槽資訊,啟動核心或者分割槽載入程式。

Window安裝時預設會自動將MBR和windows所在分割槽的引導扇區都裝上載入程式,而不會提供任何選項給使用者選擇,因此如果之前裝過其他作業系統,然後再另外裝一個windows時,會把公用的MBR覆蓋掉,如此,原來的作業系統就無法啟動了。如果先裝windows,然後裝linux,linux 會覆蓋MBR,然後讓使用者選擇是否將windows等其他作業系統的啟動項新增進來,如果你選擇了新增進來,那麼你在開機時就會有兩個選項讓使用者進行選擇了。

後記

l  這裡討論的全部是硬碟相關的東西,光碟不在此列,而且光碟的磁軌並不是從外圈到內圈編號,而是從內圈開始編號,這點注意。

l  硬碟第一個扇區是由MBR和分割槽表佔據,因此0柱面0磁頭上剩下的62個扇區一般會空出來保留(這部分保留稱為隱藏扇區,因為作業系統讀取不到這部分扇區,這部分扇區是提供給BIOS讀取的),而系統分割槽則從0柱面1磁頭1扇區開始,折算成LBA=255 × 63 × 0 + 63 × 1 + 1 – 1= 63,即從LBA 63號扇區開始分割槽。不過查閱有的資料提及到另外一種說法,那就是有的硬碟可能0柱面全部空下來,如果真是這樣,那浪費可就真的大了。

l  對於擴充套件分割槽的分割槽表我們知道也是由擴充套件分割槽的第一個扇區開始寫,而且是寫到每個邏輯驅動器的第一個扇區,同樣,擴充套件分割槽內的第一個扇區所在的磁軌剩餘的扇區也會全部空餘出來,這些保留的扇區作業系統也是無法讀取的,注意在擴充套件分割槽的第一個扇區裡面是沒有引導載入記錄的。引導載入記錄都是放在隱藏扇區後面的。可以看圖3,圖4