linux操做系統分析

1、 進程管理命令
    Linux下,監控和管理進程的命令有不少,下面咱們以ps、top、pstree、lsof四個最經常使用的指令介紹若是有效的監控和管理linux下的各類進程。html


    (1)利用ps命令監控系統進程
ps是linux下最經常使用的進程監控命令,重點講述如何利用ps指令監控和管理系統進程。
舉例:
下面是apache進程的輸出信息
2016216113322165.png (520×255)linux

其中,UID是用戶的ID標識號,PID是進程的標識號,PPID表示父進程,STIME表示進程的啓動時間,TTY表示進程所屬的終端控制檯,TIME表示進程啓動後累計使用的CPU總時間,CMD表示正在執行的命令。而且root的PPID爲1,即爲Init的ID.
    
   另外一種指令方式查看子進程與父進程的對應關係:
2016216113342162.png (683×282)算法

其中,%CPU表示進程佔用的CPU百分比,%MEM表示進程佔用內存的百分比,VSZ表示進程虛擬大小,RSS表示進程的實際內存(駐留集)大小(單位是頁)。
    STAT表示進程的狀態,進程的狀態有不少種:用「R」表示正在運行中的進程,用「S」表示處於休眠狀態的進程,用「Z」表示僵死進程,用「<」表示優先級高的進程,用「N」表示優先級較低的進程,用「s」表示父進程,用「+」表示位於後臺的進程。START表示啓動進程的時間。
    這個例子將進程之間的關係用樹形結構形象的表示出來,能夠很清楚的看到,第一個進程爲父進程,而其它進程均爲子進程。同時從這個輸出還能夠看到每一個進程佔用CPU、內存的百分比,還有進程所處的狀態等等。apache


    (2)利用pstree監控系統進程
pstree命令以樹形結構顯示程序和進程之間的關係,使用格式以下:

數組

pstree [-acnpu] [<PID>/<user>]


具體選項內容可用pstree --help來查看,因爲顯示結果的樹形結構太長,就再也不貼圖.      
pstree清楚的顯示了程序和進程之間的關係,若是不指定進程的PID號,或者不指定用戶名稱,則將以init進程爲根進程,顯示系統的全部程序和進程信息,若指定用戶或PID,則將以用戶或PID爲根進程,顯示用戶或PID對應的全部程序和進程。數據結構


    (3)利用top監控系統進程
     top命令是監控系統進程必不可少的工具,與ps命令相比,top命令動態、實時的顯示進程狀態,而ps只能顯示進程某一時刻的信息,同時,top命令提供了一個交互界面,用戶能夠根據須要,人性化的定製本身的輸出,更清楚的瞭解進程的實時狀態。
    下面是top的顯示信息
2016216113400420.png (672×374)tcp

 

經過動態信息能夠看出一個進程從上次更新到如今佔用cpu時間,佔用物理內存(%MEM),從進程啓動到如今佔用cpu總時間(TIME+)等。經過了解這些信息,可使系統管理員掌握每一個進程對系統CPU、物理內存的使用情況。
  
    (4)利用lsof監控系統進程與程序
lsof全名list opened files,也就是列舉系統中已經被打開的文件,經過lsof,咱們就能夠根據文件找到對應的進程信息,也能夠根據進程信息找到進程打開的文件。
lsof指令功能強大,這裏介紹「-c,-g,-p,-i」這四個最經常使用參數的使用。更詳細的介紹請參看manlsof或者lsof --help。
1) lsoffilename:顯示使用filename文件的進程。
2)lsof -c abc:顯示abc進程如今打開的文件
3)lsof -g gid:顯示指定的進程組打開的文件狀況,使用進程組ID即GID
4)lsof -p PID:PID是進程號,經過進程號顯示程序打開的全部文件及相關進程,例如,想知道init進程打開了哪些文件的話,能夠執行「lsof-p  1」命令
5)lsof-i :經過監聽指定的協議、端口、主機等信息,顯示符合條件的進程信息。
例如:
 顯示系統中tcp協議對應的25端口進程信息:

函數

 
[root@localhost ~]# lsof-i tcp:25


顯示系統中80端口對應的進程信息:

工具

[root@localhost ~]# lsof-i :80


 (5) 計劃任務
計劃任務就是提早設定的一系列命名,來在特定時間裏自動完成,好比一些自動備份,自動關係,自動發郵件,廣播之類
計劃任務有三個比較重要的命令
1)at安排做業在某一時刻執行一次
2)Batch安排做業在系統負載不重時執行一次
3)Cron安排週期性運行的做業spa


(6)結束進程
Kill -1重啓進程
kill 進程號   結束進程
kill -9強制結束進程


(7) 設置程序的優先級
Niec :指定程序運行優先級別

 

、進程的轉換

(1)運行狀態(TASK_RUNNING)
當進程正在被CPU執行,或已經準備就緒隨時可由調度程序執行,則稱該進程爲處於運行狀態(running)。進程能夠在內核態運行,也能夠在用戶態運行。當系統資源已經可用時,進程就被喚醒而進入準備運行狀態,該狀態稱爲就緒態。這些狀態(圖中中間一列)在內核中表示方法相同,都被成爲處於TASK_RUNNING狀態。


(2)可中斷睡眠狀態(TASK_INTERRUPTIBLE)
當進程處於可中斷等待狀態時,系統不會調度該進程執行。當系統產生一箇中斷或者釋放了進程正在等待的資源,或者進程收到一個信號,均可以喚醒進程轉換到就緒狀態(運行狀態)。


(3)不可中斷睡眠狀態(TASK_UNINTERRUPTIBLE)
與可中斷睡眠狀態相似。但處於該狀態的進程只有被使用wake_up()函數明確喚醒時才能轉換到可運行的就緒狀態。


(4)暫停狀態(TASK_STOPPED)
當進程收到信號SIGSTOP、SIGTSTP、SIGTTIN或SIGTTOU時就會進入暫停狀態。可向其發送SIGCONT信號讓進程轉換到可運行狀態。在Linux 0.11中,還未實現對該狀態的轉換處理。處於該狀態的進程將被做爲進程終止來處理。


(5)僵死狀態(TASK_ZOMBIE)
當進程已中止運行,但其父進程尚未詢問其狀態時,則稱該進程處於僵死狀態。
當一個進程的運行時間片用完,系統就會使用調度程序強制切換到其它的進程去執行。另外,若是進程在內核態執行時須要等待系統的某個資源,此時該進程就會調用sleep_on()或sleep_on_interruptible()自願地放棄CPU的使用權,而讓調度程序去執行其它進程。進程則進入睡眠狀態(TASK_UNINTERRUPTIBLE或TASK_INTERRUPTIBLE)。
只有當進程從「內核運行態」轉移到「睡眠狀態」時,內核纔會進行進程切換操做。在內核態下運行的進程不能被其它進程搶佔,並且一個進程不能改變另外一個進程的狀態。爲了不進程切換時形成內核數據錯誤,內核在執行臨界區代碼時會禁止一切中斷。

 

 

 

3、進程的調度

 

  Linux O(1)調度器(O(1) scheduler) 是歷史上一個流行的Linux系統調度程序。命名爲這個名字是由於它可以在常數時間內執行任務調度,例如從執行隊列中選擇一個任務或將一個任務加入執行隊列,這與系統中的任務總數有關。

 (1) O(1)調度器

  在O(1)調度中,要問最重要的數據結構是運行隊列。運行隊列描繪了進程隊列的結構,在內核源碼中用runqueue結構體表示。

struct runqueue 
{   unsigned long nr_running; 
    task_t *curr;
    prio_array_t *active,*expired,arrays[2]; 
};

 (2)優先級數組

  O(1)算法的另外一個核心數據結構即爲prio_array結構體。該結構體中有一個用來表示進程動態優先級的數組queue,它包含了每一種優先級進程所造成的鏈表。

複製代碼
#define
 MAX_USER_RT_PRIO        100
#define
 MAX_RT_PRIO             MAX_USER_RT_PRIO
#define
 MAX_PRIO                (MAX_RT_PRIO + 40)
typedef struct prio_array
 prio_array_t;
struct prio_array
 {
      unsigned int nr_active;
      unsigned long bitmap[BITMAP_SIZE];
      struct list_head
 queue[MAX_PRIO];
};
複製代碼

 (3)靜態優先級和動態優先級

  進程有兩個優先級,一個是靜態優先級,一個是動態優先級.靜態優先級是用來計算進程運行的時間片長度的,動態優先級是在調度器進行調度時用到的,調度器每次都選取動態優先級最高的進程運行.

靜態優先級的計算:
nice值和靜態優先級之間的關係是:靜態優先級=100+nice+20
而nice值的範圍是-20~19,因此普通進程的靜態優先級的範圍是100~139
動態優先級的計算:
動態優先級=max(100 , min(靜態優先級 – bonus + 5 , 139))

 (4)時間片

  O(1)算法採用過時進程數組和活躍進程數組解決以往調度算法所帶來的O(n)複雜度問題。過時數組中的進程都已經用完了時間片,而活躍數組的進程還擁有時間片。當一個進程用完本身的時間片後,它就被移動到過時進程數組中,同時這個過時進程在被移動以前就已經計算好了新的時間片。能夠看到O(1)調度算法是採用分散計算時間片的方法,並不像以往算法中集中爲全部可運行進程從新計算時間片。當活躍進程數組中沒有任何進程時,說明此時全部可運行的進程都用完了本身的時間片。那麼此時只須要交換一下兩個數組便可將過時進程切換爲活躍進程,進而繼續被調度程序所調度。兩個數組之間的切換其實就是指針之間的交換,所以花費的時間是恆定的。

struct prop_array *array = rq->active;
if (array->nr_active != 0) {
    rq->active = rq->expired;
    rq->expired = array;
}

  上面的代碼說明了兩個數組之間的交換,經過分散計算時間片、交換過時和活躍兩個進程集合的方法可使得O(1)算法在恆定的時間內爲每一個進程從新計算好時間片。

進程運行的時間片長度的計算
靜態優先級<120,基本時間片=max((140-靜態優先級)*20, MIN_TIMESLICE)
靜態優先級>=120,基本時間片=max((140-靜態優先級)*5, MIN_TIMESLICE)

 (5)調度算法

  

在每次進程切換時,內核依次掃描就緒隊列上的每個進程,計算每一個進程的優先級,再選擇出優先級最高的進程來運行;儘管這個算法理解簡單,可是它花費在選擇優先級最高進程上的時間卻不容忽視。系統中可運行的進程越多,花費的時間就越大,時間複雜度爲O(n)。

//僞代碼
for (系統中的每一個進程) {
    從新計算時間片;
    從新計算優先級;
}

 

對操做系統進程模型的見解

操做系統線程模型不會一成不變,而是變得愈來愈完善,創新是最好的生產力,不一樣模型的消耗,算法和用戶體驗是不一樣的,模型的固定限制着技術的發展,我相信在不久的未來,此模型會迎來大的變革,計算機技術將會跨越一個新的時代。

5、參考

http://www.jb51.net/LINUXjishu/429990.html

https://blog.csdn.net/cosmoslhf/article/details/41486965

https://blog.csdn.net/qq_33650978/article/details/53559835

相關文章
相關標籤/搜索