久久婷婷香蕉热狠狠综合,精品无码国产自产拍在线观看蜜,寡妇房东在做爰3,中文字幕日本人妻久久久免费,国产成人精品三上悠亚久久

當前位置:首頁 > 學習資源 > 講師博文 > Linux內核發生死鎖怎么解決

Linux內核發生死鎖怎么解決 時間:2023-09-09      來源:華清遠見

一、什么是Linux內核死鎖

 死鎖是指多個進程(線程)因為長久等待已被其他進程占有的的資源而陷入阻塞的一種狀態。當等待的資源一直得不到釋放,死鎖會一直持續下去。死鎖一旦發生,程序本身是解決不了的,只能依靠外部力量使得程序恢復運行,例如重啟,開門狗復位等。

#Linux 提供了檢測死鎖的機制,主要分為 D 狀態死鎖和 R 狀態死鎖。

1.D 狀態死鎖:

     進程等待 I/O 資源無法得到滿足,長時間(系統默認配置 120 秒)處于 TASK_UNINTERRUPTIBLE 睡眠狀態,這種狀態下進程不響應異步信號(包括 kill -9)。如:進程與外設硬件的交互(如 read),通常使用這種狀態來保證進程與設備的交互過程不被打斷,否則設備可能處于不可控的狀態。對于這種死鎖的檢測 Linux 提供的是 hung task 機制。觸發該問題成因比較復雜多樣,可能因為 synchronized_irq、mutex lock、內存不足等。D 狀態死鎖只是局部多進程間互鎖,一般來說只是 hang 機、凍屏,機器某些功能沒法使用,但不會導致沒喂狗,而被狗咬死。

2.R 狀態死鎖:

     進程長時間(系統默認配置 60 秒)處于 TASK_RUNNING 狀態壟斷 CPU 而不發生切換,一般情況下是進程關搶占或關中斷后長時候執行任務、死循環,此時往往會導致多 CPU 間互鎖,整個系統無法正常調度,導致喂狗線程無法執行,無法喂狗而最終看門狗復位的重啟。該問題多為原子操作,spinlock 等 CPU 間并發操作處理不當造成。

#死鎖的產生需要滿足以下4個條件:

 1》 互斥條件:指運算單元(進程、線程或協程)對所分配到的資源具有排它性,也就是說在一段時間內某個鎖資源只能被一個運算單元所占用。

 2》 請求和保持條件:指運算單元已經保持至少一個資源,但又提出了新的資源請求,而該資源已被其它運算單元占有,此時請求運算單元阻塞,但又對自己已獲得的其它資源保持不放。

3》 不可剝奪條件:指運算單元已獲得的資源,在未使用完之前,不能被剝奪。

 4》 環路等待條件:指在發生死鎖時,必然存在運算單元和資源的環形鏈,即運算單元正在等待另一個運算單元占用的資源,而對方又在等待自己占用的資源,從而造成環路等待的情況。

#常見的死鎖有以下4種情況:

 (1)進程重復申請同一個鎖,稱為AA死鎖。例如,重復申請同一個自旋鎖;使用讀寫鎖,第一次申請讀鎖,第二次申請寫鎖。

 (2)進程申請自旋鎖時沒有禁止硬中斷,進程獲取自旋鎖以后,硬中斷搶占,申請同一個自旋鎖。這種AA死鎖很隱蔽,人工審查很難發現。

 (3)兩個進程都要獲取鎖L1和L2,進程1持有鎖L1,再去獲取鎖L2,如果這個時候進程2持有鎖L2并且正在嘗試獲取鎖L1,那么進程1和進程2就會死鎖,稱為AB-BA死鎖。

 (4)在一個處理器上進程1持有鎖L1,再去獲取鎖L2,在另一個處理器上進程2持有鎖L2,硬中斷搶占進程2以后獲取鎖L1。這種AB-BA死鎖很隱蔽,人工審查很難發現。

二、如何解決Linux內核死鎖

死鎖的常用解決方案有以下兩個:

1.按照順序加鎖:嘗試讓所有線程按照同一順序獲取鎖,從而避免死鎖。

 2.設置獲取鎖的超時時間:嘗試獲取鎖的線程在規定時間內沒有獲取到鎖,就放棄獲取鎖,避免因為長時間等待鎖而引起的死鎖。

Linux內核死鎖檢測lockdep

1.1 使用方法

死鎖檢測工具lockdep的配置宏如下:

 (1)CONFIG_LOCKDEP:在配置菜單中看不到這個配置宏,打開配置宏CONFIG_PROVE_LOCKING或CONFIG_DEBUG_LOCK_ALLOC的時候會自動打開這個配置宏。

(2)CONFIG_PROVE_LOCKING:允許內核報告死鎖問題。

(3)CONFIG_DEBUG_LOCK_ALLOC:檢查內核是否錯誤地釋放被持有的鎖。

 (4)CONFIG_DEBUG_LOCKING_API_SELFTESTS:內核在初始化的過程中運行一小段自我測試程序,自我測試程序檢查調試機制是否可以發現常見的鎖缺陷。

1.2 技術原理

 死鎖檢測工具lockdep操作的基本對象是鎖類,例如結構體里面的鎖是一個鎖類,結構體的每個實例里面的鎖是鎖類的一個實例。

 lockdep跟蹤每個鎖類的自身狀態,也跟蹤各個鎖類之間的依賴關系,通過一系列的驗證規則,確保鎖類狀態和鎖類之間的依賴總是正確的。另外,鎖類一旦在初次使用時被注冊,后續就會一直存在,它的所有具體實例都會關聯到它。

1)鎖類狀態

lockdep為鎖類定義了(4n+1)種使用歷史狀態,其中的4指代如下:

(1)該鎖曾在STATE上下文中被持有過。

(2)該鎖曾在STATE上下文中被以讀鎖形式持有過。

(3)該鎖曾在開啟STATE的情況下被持有過。

(4)該鎖曾在開啟STATE的情況下被以讀鎖形式持有過。

 其中的n是STATE狀態的個數,STATE狀態包括硬中斷(hardirq)、軟中斷(softirq)和reclaim_fs(__GFP_FS分配,表示允許向下調用到文件系統。如果文件系統持有鎖以后使用標志位__GFP_FS申請內存,在內存嚴重不足的情況下,需要回收文件頁,把修改過的文件頁寫回到存儲設備,遞歸調用文件系統的函數,可能導致死鎖)。其中的1是指該鎖曾經被使用過。

如果鎖曾在硬中斷上下文中被持有過,那么鎖是硬中斷安全的(hardirq-safe);
 如果鎖曾在開啟硬中斷的情況下被持有過,那么鎖是硬中斷不安全的(hardirq-unsafe)。

2)檢查規則

單鎖狀態規則如下:

(1)一個軟中斷不安全的鎖類也是硬中斷不安全的鎖類。

 (2)任何一個鎖類,不可能同時是硬中斷安全的和硬中斷不安全的,也不可能同時是軟中斷安全的和軟中斷不安全的。也就是說:硬中斷安全和硬中斷不安全是互斥的,軟中斷安全和軟中斷不安全也是互斥的。

多鎖依賴規則如下:

(1)同一個鎖類不能被獲取兩次,否則可能導致遞歸死鎖(AA死鎖)。

(2)不能以不同順序獲取兩個鎖類,否則導致AB-BA死鎖。

(3)不允許在獲取硬中斷安全的鎖類之后獲取硬中斷不安全的鎖類。

 硬中斷安全的鎖類可能被硬中斷獲取。假設處理器0上的進程首先獲取硬中斷安全的鎖類A,然后獲取硬中斷不安全的鎖類B;處理器1上的進程獲取鎖類B,硬中斷搶占進程,獲取鎖類A,可能導致AB-BA死鎖。

(4)不允許在獲取軟中斷安全的鎖類之后獲取軟中斷不安全的鎖類。

 軟中斷安全的鎖類可能被軟中斷獲取。假設處理器0上的進程首先獲取軟中斷安全的鎖類A,然后獲取軟中斷不安全的鎖類B;處理器1上的進程獲取鎖類B,軟中斷搶占進程,獲取鎖類A,可能導致AB-BA死鎖。

當鎖類的狀態發生變化時,檢查下面的依賴規則:

(1)如果鎖類的狀態變成硬中斷安全,檢查過去是否在獲取它之后獲取硬中斷不安全的鎖。

(2)如果鎖類的狀態變成軟中斷安全,檢查過去是否在獲取它之后獲取軟中斷不安全鎖。

(3)如果鎖類的狀態變成硬中斷不安全,檢查過去是否在獲取硬中斷安全的鎖之后獲取它。

(4)如果鎖類的狀態變成軟中斷不安全,檢查過去是否在獲取軟中斷安全的鎖之后獲取它。

如何防止Linux內核死鎖

1.減少同步代碼塊嵌套操作

2.降低鎖的使用粒度,不要幾個功能共用一把鎖

 3.盡量采用tryLock(timeout)的方法,可以設置超時時間,這樣超時之后,就可以主動退出,防止死鎖(關鍵)

上一篇:PLC和單片機哪個更有前途

下一篇:什么情況下需要考慮內存屏障

戳我查看嵌入式每月就業風云榜

點我了解華清遠見高校學霸學習秘籍

猜你關心企業是如何評價華清學員的

干貨分享
相關新聞
前臺專線:010-82525158 企業培訓洽談專線:010-82525379 院校合作洽談專線:010-82525379 Copyright © 2004-2024 北京華清遠見科技發展有限公司 版權所有 ,京ICP備16055225號-5京公海網安備11010802025203號

回到頂部