《Linux核心設計與實現》——中斷和中斷處理
一、中斷
1、中斷本質上是一種特殊的電訊號,由硬體裝置發向處理器。處理器接收到中斷後,會馬上向作業系統反應此訊號的到來,然後就由作業系統負責處理這些新到來的資料。
2、不同的裝置對應的中斷不同,而每個中斷都通過一個唯一的數字標誌。這些中斷值通常被稱為中斷請求(IRQ)線,每個IRQ線都會被關聯一個數值量。
二、中斷處理程式
1、再響應一個特定中斷的時候,核心會執行一個函式,該函式叫做中斷處理程式或中斷服務例程(ISR)。
1)、產生中斷的每個裝置都有一個相應的中斷處理程式。
2)、一個裝置的中斷處理程式是它裝置驅動程式的一部分——裝置驅動程式是用於對裝置進行管理的核心程式碼。
2、中斷處理程式與其他核心函式的真正區別在於:中斷處理程式是被核心呼叫來響應中斷的,而他們執行在中斷上下文中,中斷上下文也稱原子上下文。
三、上半部和下半部的對比
1、中斷處理切為兩個部分
1)、中斷處理程式是上半部——接收到一箇中斷,它就立即開始執行,但製作嚴格限時的工作。
2)、能夠被允許稍後完成的工作會推遲到下半部去。此後,在合適的時機,下半部會被開中斷執行。
四、註冊中斷處理程式
1、驅動程式可以通過requeset_irq()函式註冊一箇中斷處理程式,並啟用給定的中斷線:
int requeset_irq(unsigned int irq, irq_handler_t handler,
unsigned long flags, const char *name, void *dev);
I、引數irq表示要分配的中斷號。
II、引數handler是一個指標,指向處理這個中斷的實際中斷處理程式。
2、中斷處理程式標誌
1)、引數flags可以為0,也可以是一個或多個標誌的位掩碼。
I、IRQF_DISABLED——該標誌被設定後,意味著核心在處理程式本身期間,要禁止所有的其他中斷。
II、IRQF_SAMPLE_RANDOM——此標誌表明這個裝置產生的中斷對核心熵池有貢獻。
III、IRQF_TIMER——此標誌是特別位系統定時器的中斷處理而準備的。
IV、IRQF_SHARED——此標誌表明可以在多個終端處理程式之間共享中斷線。
2)、引數name是與中斷有關的的裝置的ASCII文字表示。
3)、引數dev用於共享中斷線。
3、一箇中斷例子
4、釋放中斷處理程式
1)、解除安裝驅動程式時,需要登出相應的中斷處理程式,並釋放中斷線:
void free_irq(unsigned int irq, void *dev);
I、如果指定的中斷線不是共享的,那麼,該函式刪除處理程式的同時將禁用這條中斷線。
II、如果中斷線是共享的,則僅刪除dev所對應的處理程式,而這條中斷線本省只有在刪除了最後一個處理程式時才會被禁用。
五、編寫中斷處理程式
1、一箇中斷處理程式宣告:
static irqreturn_t intr_hanler(int irq, void *dev);
I、此函式的型別與request_irq()引數中的healer所要求的引數型別匹配。
II、第一個引數irq就是處理程式要響應的中斷的中斷號。
III、第二個引數dev是一個用用指標,它與中斷處理程式註冊時傳遞給request_irq()的引數dev必須一致。
IV、中斷處理程式的返回值型別是irqreturn_t。中斷處理程式可能返回兩個特殊值:IRQ_NONE和IRQ_HANDLED。
2、共享的中斷處理程式
1)、共享的處理程式與非共享的處理程式在註冊和執行方式上比較相似,但差異主要有一下三處:
I、request_irq()的引數flags必須設定IRQF_SHARED標誌。
II、對於每個註冊的中斷處理程式來說,dev引數必須唯一。
III、中斷處理程式必須能夠區分它的裝置是否產生了中斷。
2)、指定IRQF_SHARED標誌以呼叫request_irq()時,只有在以下兩種情況才能夠成功:
I、中斷線當前未被註冊。
II、在該線上的所有已註冊處理程式都指定了IRQF_SHARED。
3、中斷處理程式例項
六、中斷上下文
1、當執行一箇中斷處理程式時,核心處於中斷上下文中。
2、中斷上下文具有較為嚴格的時間限制,因為它打斷了其他的程式碼。中斷上下文中的程式碼應當迅速、簡潔、儘量不要使用迴圈去處理繁重的工作。
3、中斷處理程式棧是一個配置選項。
七、中斷處理機制的實現
1、中斷處理系統在Linux中的實現非常依賴於體系結構,實現依賴於處理器、所使用的中斷控制器的型別、體系結構的設計及及機器本身。
2、中斷從硬體到核心的路由(P100 圖7-1)
1)、在核心中,中斷開始於預定義的入口點。對於每條中斷線,處理器都會跳到對應的一個惟一的位置。
2)、初始入口點只是在棧中儲存這個號,並存放當前暫存器的值;然後,核心呼叫函式do_IRQ()。
unsigend int do_IRQ(struct pt_regs regs)
3)、pt_regs結構包含原始暫存器的值。中斷的值也會得以儲存,所以,do_IRQ()可以將它提取出來。
4)、計算出中斷號之後,do_IRQ()對所接收的中斷進行應答,禁止這條線上的中斷。
5)、接下來,do_IRQ()需要確保在這條中斷線上有一個有效的處理程式,而且這個程式已經啟動,但是當前並沒有執行。如是如此,do_IRQ()就呼叫handle_IRQ_event()來
執行為這條中斷線安裝的中斷處理程式。
八、/proc/interrupts
1、procfs是一個虛擬檔案系統,它只存在核心記憶體中,一般安裝於/proc目錄。在procfs中讀寫檔案都要呼叫核心函式,這些函式模擬從真實檔案中讀寫。
九、中斷控制
1、禁止和啟用中斷
1)、用於禁止當前處理器上的本地中斷,隨後又啟用它們的語句為:
local_irq_disable();
local_irq_enable();
I、在X86中,local_irq_disable()僅僅是cli指令,local_irq_enable()僅僅是sti指令。cli和sti分別是對clear和set允許中斷標誌的會變呼叫。
II、如果在呼叫local_irq_disable()例程之前已經禁止了中斷,那麼該例程往往會帶來潛在的危險;同樣相應的local_irq_enable()例程也存在潛在危險。
2)、在禁止中斷之前儲存中斷系統的狀態會更加安全一些。相反,在準備啟用中斷時,只需要把中斷恢復到他們原來的狀態:
unisgend long flags;
local_irq_save(flags);
/* . . . */
local_irq_restore(flags);
2、禁止指定中斷
1)、對中斷狀態操作之前禁止裝置中斷的傳遞。LInux提供了四個介面:
void disable_irq(unsigned int irq);
void disable_irq_nosync(unsigned int irq);
void enable_irq(unsigned int irq);
void synchronize_irq(unsigned int irq);
I、disable_irq和disable_irq_nosync禁止中斷控制器上指定的中斷線,即禁止給定中斷向系統所有處理器的傳遞。此外函式只有在當前正在執行的所有處理器程式完成
後,disable_irq才會返回。disable_irq_nosync不會等待當前中斷處理程式執行完畢。
II、函式synchronize_irq等待一個特定的中斷處理程式的退出。如果該處理程式正在執行,那麼該函式必須退出之後才能返回。
III、這些函式可以巢狀。但是記住在一條指定的中斷線上,對disable_irq和disable_irq_nosync的每次呼叫,都需要相應的呼叫一次enable_irq。
IV、以上函式可以從中斷或程式上下文中呼叫,而且不會休眠。但是從中斷上下文中呼叫必須注意。
2)、禁止多箇中斷處理程式共享的中斷時不合適的。禁止中斷線也就禁止了這條線上所有裝置的中斷傳遞。
3、中斷系統的狀態
1)、irqs_disable()定義在<asm/aystem.h>中。如果本地處理器上的中斷系統被禁止,則它返回非0,否則返回0。
2)、在<linux/hardirq.h>中定義的兩個巨集提供一個用來檢查核心的當前上下文的介面:
in_interrupt()
in_irq()
I、in_interrupt:如果核心處於任何型別的中斷處理中,它返回非0,說明核心此刻正在執行中斷處理程式或正在執行下半部處理程式。
II、in_irq:只有在核心確實正在執行中斷處理程式時才會返回非0。
3)、中斷控制方法列表(P106 表7-2)。
相關文章
- 中斷和中斷處理程式
- Linux 核心處理中斷全過程解析Linux
- Linux核心軟中斷Linux
- Linux系統程式設計之訊號中斷處理(下)Linux程式設計
- Linux系統程式設計之訊號中斷處理(上)Linux程式設計
- 中斷處理和GIC-V2
- Linux系統中對中斷的處理(學習筆記)Linux筆記
- linux核心設計與實現Linux
- LINUX中斷--申請中斷和解除安裝中斷Linux
- 【原創】Linux中斷子系統(二)-通用框架處理Linux框架
- Linux(核心剖析):19---中斷總體概述Linux
- Linux核心中斷Linux
- 《Linux核心設計與實現》學習【5】—— 核心同步Linux
- Linux中斷申請Linux
- linux中斷 簡介Linux
- react專案中不同寬度斷點處理React斷點
- PCIe掃盲——PCI匯流排的中斷和錯誤處理
- linux網路程式設計中的errno處理Linux程式設計
- 程式設計師被打斷:中斷和上下文切換的真正代價程式設計師
- Linux中斷子系統Linux
- ORACLE 11G DATAGUARD 日誌中斷處理方案Oracle
- 異常和中斷
- 熔斷原理與實現
- Linux核心筆記009 - 中斷、異常、陷阱、Bottom half、訊號Linux筆記
- Linux程式上下文和中斷上下文核心空間和使用者空間Linux
- Sentinel全域性Feign預設熔斷設計實現
- 中斷
- linux中的訊號處理與SROPLinux
- 作業系統--怎麼實現中斷作業系統
- js函式中的if判斷和a==b判斷JS函式
- 雲桌面使用中經常出現的一些問題該如何去判斷和處理
- 文書處理技術:WORD也在不斷變化中
- 【原創】Linux中斷子系統(三)-softirq和taskletLinux
- Linux的中斷可以巢狀嗎?Linux巢狀
- 硬中斷,軟中斷,訊號,異常
- 3.外設GPIO、中斷
- 【原創】Linux中斷子系統(一)-中斷控制器及驅動分析Linux
- Linux常用命令(不斷更新中)Linux
- Linux 效能優化之 CPU 篇 ----- Linux 軟中斷Linux優化