-
進程優(yōu)先級:
1.2. 進程優(yōu)先級的定義是什么?
進程優(yōu)先級指的是CPU資源分配的先后順序,即進程的優(yōu)先權(priority)。
1.3. 為何存在進程優(yōu)先級的概念?
根本原因在于資源的稀缺性。
在linux環(huán)境中,默認優(yōu)先級為80,且Linux的優(yōu)先級是可調的,范圍在【60,99】之間,共有40個級別。
Linux優(yōu)先級的本質是數字,數字越小,優(yōu)先級越高!
Linux系統(tǒng)允許用戶調整優(yōu)先級,但不能直接修改pri,而是通過修改nice值(不是優(yōu)先級,而是進程優(yōu)先級的修正數據)來實現。
pri = pri(old) + nice
1.4. 為什么Linux調整優(yōu)先級需要受限制?
如果不加限制,用戶可以將自己進程的優(yōu)先級設得極高,而將他人的優(yōu)先級設得極低,高優(yōu)先級的進程會優(yōu)先獲得資源,導致后續(xù)產生的進程難以享受到CPU資源,從而引發(fā)進程饑餓問題。
1.5. PRI與NICE的區(qū)別需要特別強調的是什么?
進程的nice值不是進程的優(yōu)先級,它們是不同的概念,但nice值會影響進程優(yōu)先級的變化。可以將nice值理解為進程優(yōu)先級的修正數據。
在Linux下,調整進程優(yōu)先級就是調整進程的nice值,nice值的范圍是-20至19,共有40個級別。
使用top命令更改已存在進程的nice值:進入top后按“r”->輸入進程PID->輸入nice值。
-
Linux的調度與切換:
2.1. 概念準備:
-
進程在運行時,是否必須在CPU上運行完整個代碼?
不是!現代操作系統(tǒng)是基于時間片進行輪轉執(zhí)行的(時間片:給每個進程規(guī)定的最大運行時間)。
-
進程的競爭性、獨立性、并行性和并發(fā)性:
競爭性:系統(tǒng)中進程數量眾多,而CPU資源有限,進程之間具有競爭屬性。為了高效完成任務和合理競爭資源,便有了優(yōu)先級。
獨立性:多進程運行時,需要獨享各種資源,多進程運行期間互不干擾。
并行:多個進程在多個CPU下分別、同時進行運行,稱之為并行。
并發(fā):多個進程在一個CPU下通過進程切換,在一段時間內讓多個進程都得以推進,稱之為并發(fā)。
2.2. 如何完成進程的調度和切換?
當一個進程的時間片到期后,如何保存進程以便下次調用?
CPU內部有許多寄存器,進程在運行過程中會產生大量臨時數據,存放在CPU的寄存器中。這些CPU內部的臨時數據稱為進程的硬件上下文。通過硬件上下文的保存,進程可以被再次調度時恢復運行。
因此,當進程再次被調度時,將之前保存的硬件上下文恢復,使進程繼續(xù)從上次運行的位置進行。
上下文并不是寄存器,而是寄存器的內容。CPU的寄存器只有一套,但寄存器內部保存的數據可以有多套。
所以,寄存器 ≠ 寄存器的內容。
雖然寄存器數據放在共享的CPU設備中,但所有數據實際上是進程私有的。
小結:所有的保存都是為了最終的恢復,所有的恢復都是為了繼續(xù)上次的運行位置繼續(xù)進行。
2.4 Linux實現進程調度的算法需要考慮哪些因素?
Linux實現進程調度的算法需要考慮優(yōu)先級、進程饑餓問題和效率問題。
解決優(yōu)先級問題:
普通優(yōu)先級:100~139(對應nice值的取值范圍)
實時優(yōu)先級:0~99(不關心)
時間片未結束的所有進程都按優(yōu)先級放在隊列中。nr_active表示總共有多少個運行狀態(tài)的進程,queue[140]表示一個元素就是一個進程隊列,相同優(yōu)先級的進程按照FIFO規(guī)則進行排隊調度,數組下標即優(yōu)先級。
從0下標開始遍歷queue[140],找到第一個非空隊列,該隊列必定是優(yōu)先級最高的隊列。選中隊列的第一個進程開始運行,調度完成,優(yōu)先級問題解決。
解決進程饑餓問題:
采用引入活動隊列和過期隊列來解決。
過期隊列和活動隊列結構相同,過期隊列上放置的是時間片耗盡的進程。當活動隊列上的進程都被處理完畢后,對過期隊列的進程進行時間片重新計算。
我們先將活動隊列中的進程都運行完畢,注意活動隊列上的進程運行完畢后會減少,不會增加,而過期隊列里的進程只會越來越多。此時需要將活動隊列的內容與過期隊列的內容進行交換。
交換方式:有兩個指針分別指向活動隊列和過期隊列,active指針永遠指向活動隊列,expired指針永遠指向過期隊列。活動隊列上的進程會越來越少,過期隊列上的進程會越來越多,因為進程時間片到期時一直存在。只要在合適的時候交換active指針和expired指針的內容,就相當于獲得了一批新的活動進程。注意交換時只是交換指針的內容。
解決效率問題:
遍歷queue[140]的時間復雜度是常數,但仍然不夠高效。
于是采用位圖方法解決:
bitmap[5]:一共140個優(yōu)先級,一共140個進程隊列。為了提高查找非空隊列的效率,可以用5*32個比特位表示隊列是否為空。我們每次可以先遍歷一個整數,如果這個整數是0,就可以直接跳過,到下一個整數,直到發(fā)現不等于0,再遍歷內部。
位圖將對數組的遍歷轉化為對比特位的遍歷,效率會高很多。
-
? 版權聲明
文章版權歸作者所有,未經允許請勿轉載。
THE END
喜歡就支持一下吧