




版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報或認(rèn)領(lǐng)
文檔簡介
1、嵌入式系統(tǒng)設(shè)計大學(xué)教程,第七章 設(shè)備驅(qū)動程序,主要內(nèi)容,7.1 概述 7.2 設(shè)備文件接口 7.3 中斷處理 7.4 應(yīng)用實例,7.1 概述,Linux作為unix的一個變種,它繼承了unix的設(shè)備管理方法,將所有的設(shè)備看作具體的文件,通過文件系統(tǒng)層對設(shè)備進(jìn)行訪問。所以在Linux/uclinux的框架結(jié)構(gòu)中,和設(shè)備相關(guān)的處理可以分為兩個層次文件系統(tǒng)層和設(shè)備驅(qū)動層。 設(shè)備驅(qū)動層屏蔽具體設(shè)備的細(xì)節(jié),文件系統(tǒng)層則向用戶提供一組統(tǒng)一的、規(guī)范的用戶接口。,7.1 概述,7.1.1 設(shè)備驅(qū)動原理 所有操作系統(tǒng)下設(shè)備驅(qū)動程序的共同目標(biāo)是屏蔽具體物理設(shè)備的操作細(xì)節(jié),實現(xiàn)設(shè)備無關(guān)性。在嵌入式操作系統(tǒng)中,設(shè)備驅(qū)
2、動程序通常是內(nèi)核的重要部分,運行在內(nèi)核模式,即設(shè)備驅(qū)動程序為內(nèi)核提供了一個I/O接口,用戶使用這個接口實現(xiàn)對設(shè)備的操作。圖 72顯示了一個操作系統(tǒng)的輸入輸出子系統(tǒng)中各層次結(jié)構(gòu)和功能。,7.1.1 設(shè)備驅(qū)動原理,圖 72 I/O系統(tǒng)層次結(jié)構(gòu)和功能,7.1 概述,7.1.2 模塊化編程 由于歷史原因及出于效率方面的考慮,Linux是一個宏內(nèi)核。雖然這種宏內(nèi)核給Linux帶來了效率高的優(yōu)點,但也給它帶來了某種程度的麻煩,即一旦需要在內(nèi)核的基礎(chǔ)上增加一項功能時,就必須重新編譯整個內(nèi)核,這無疑給內(nèi)核功能的擴(kuò)充帶來了不便。于是,Linux發(fā)展了可安裝內(nèi)核模塊的機(jī)制“module”。,7.1.2 模塊化編程
3、,從代碼特征上來看,模塊就是可完成一項獨立功能的一組函數(shù)的集合; 從使用特征上來看,它在需要時可以隨時被安裝,而在不需要時又可以隨時被卸載。 準(zhǔn)確地說,模塊就是一個已編譯但未連接的可執(zhí)行文件。利用這種機(jī)制,我們可以根據(jù)需要,在不重新編譯內(nèi)核的情況下,將編譯好的模塊動態(tài)地插入運行中的內(nèi)核,或者將內(nèi)核中已經(jīng)存在的某個模塊移走。,7.1.2 模塊化編程,為了增強(qiáng)內(nèi)核的靈活性和為了方便,設(shè)備驅(qū)動程度應(yīng)被設(shè)計為可動態(tài)安裝的內(nèi)核模。于是,一個典型的Linux設(shè)備驅(qū)動程序應(yīng)包含以下幾部分代碼: 驅(qū)動程序模塊的注冊與注銷函數(shù); 設(shè)備的打開、關(guān)閉、讀、寫及需要的其他操作函數(shù); 設(shè)備的中斷服務(wù)程序。,7.1 概述
4、,7.1.3 設(shè)備類型 Linux中的設(shè)備可以分為三類:字符設(shè)備、塊設(shè)備和網(wǎng)絡(luò)設(shè)備。 1.字符設(shè)備 字符設(shè)備是指數(shù)據(jù)處理以字節(jié)為單位按順序進(jìn)行的設(shè)備,它沒有緩沖區(qū),不支持隨機(jī)讀寫。 在對字符設(shè)備發(fā)出讀/寫請求時,實際的硬件I/O一般就緊接著發(fā)生了。,7.1.3 設(shè)備類型,作為最簡單的輸入輸出設(shè)備,操作系統(tǒng)將字符設(shè)備作為設(shè)備文件管理。其文件結(jié)點和目錄管理方式與普通文件相同。 字符設(shè)備的初始化在內(nèi)核啟動時進(jìn)行。某個字符設(shè)備初始化時,其驅(qū)動程序會構(gòu)造一個device_struct結(jié)構(gòu),將其作為字符向量數(shù)組chrdevs的一個元素向Linux內(nèi)核注冊。,7.1.3 設(shè)備類型,2.塊設(shè)備 塊設(shè)備是指那些
5、在輸入/輸出時數(shù)據(jù)處理以塊為單位的設(shè)備,它一般都采用了緩存技術(shù),支持?jǐn)?shù)據(jù)的隨機(jī)讀寫。典型的塊設(shè)備有硬盤、CD-ROM等。 對用戶來說,塊設(shè)備和字符設(shè)備的訪問接口都是一樣的,都是一組基于文件的系統(tǒng)調(diào)用,如read,write等,它們在實現(xiàn)上細(xì)節(jié)的區(qū)別僅在內(nèi)核和驅(qū)動程序的軟件接口上。,7.1.3 設(shè)備類型,3.網(wǎng)絡(luò)設(shè)備 在Linux中,整個網(wǎng)絡(luò)接口驅(qū)動程序的框架可分為四層,從上到下分別為協(xié)議接口層、網(wǎng)絡(luò)設(shè)備接口層、提供實際功能的設(shè)備驅(qū)動功能層、以及網(wǎng)絡(luò)設(shè)備和網(wǎng)絡(luò)媒介層。,7.1.3 設(shè)備類型,圖 74 網(wǎng)絡(luò)驅(qū)動程序體系結(jié)構(gòu),7.1.3 設(shè)備類型,(1)網(wǎng)絡(luò)設(shè)備接口 所謂的網(wǎng)絡(luò)設(shè)備接口,它既包括純軟
6、件網(wǎng)絡(luò)設(shè)備接口,如環(huán)路(loopback),也包括硬件網(wǎng)絡(luò)設(shè)備接口,如以太網(wǎng)卡。在Linux中,網(wǎng)絡(luò)設(shè)備接口是由數(shù)據(jù)結(jié)構(gòu)device來表示的。它操作的數(shù)據(jù)對象數(shù)據(jù)包是通過結(jié)構(gòu)sk_buff來封裝的。,7.1.3 設(shè)備類型,(2)網(wǎng)絡(luò)驅(qū)動程序加載方法 目前,Linux網(wǎng)絡(luò)設(shè)備驅(qū)動程序的加載有兩種方式。一種是系統(tǒng)啟動時,由內(nèi)核自動檢測并靜態(tài)加載,稱之為“啟動初始化方式”;另一種是通過模塊化機(jī)制在系統(tǒng)運行過程中根據(jù)需要由用戶或系統(tǒng)進(jìn)程動態(tài)加載,稱之為“模塊初始化方式”。,7.1 概述,7.1.4 設(shè)備號 傳統(tǒng)的設(shè)備管理中,除了設(shè)備類型外,Linux/uclinux內(nèi)核還需要一對被稱作為主設(shè)備號、次設(shè)
7、備號的參數(shù),才能唯一地標(biāo)識設(shè)備。 主設(shè)備號(major number)標(biāo)識設(shè)備對應(yīng)的驅(qū)動程序。系統(tǒng)中不同的設(shè)備可以有相同的主設(shè)備號,主設(shè)備號相同的設(shè)備使用相同的驅(qū)動程序,內(nèi)核利用主設(shè)備號將設(shè)備與相應(yīng)的驅(qū)動程序?qū)?yīng)。,7.1.4 設(shè)備號,次設(shè)備號(minor number)用來區(qū)分具體設(shè)備的驅(qū)動程序?qū)嵗?,只能由設(shè)備驅(qū)動程序使用,內(nèi)核的其他部分僅將它作為參數(shù)傳遞給驅(qū)動程序。 向系統(tǒng)添加一個驅(qū)動程序相當(dāng)于添加一個主設(shè)備號,字符型設(shè)備主設(shè)備號的添加和注銷分別通過調(diào)用函數(shù)register_chrdev()和unregister_chrdev()實現(xiàn)。,主要內(nèi)容,7.1 概述 7.2 設(shè)備文件接口 7.3
8、 中斷處理 7.4 應(yīng)用實例,7.2 設(shè)備文件接口,7.2.1 用戶訪問接口 1.open入口點 打開設(shè)備準(zhǔn)備I/O操作。對字符設(shè)備文件進(jìn)行打開操作,都會調(diào)用設(shè)備的open入口點。open子程序必須對將要進(jìn)行的I/O操作做好必要的準(zhǔn)備工作,如清除緩沖區(qū)等。如果設(shè)備是獨占的,即同一時刻只能有一個程序訪問此設(shè)備,則open子程序必須設(shè)置一些標(biāo)志以表示設(shè)備處于忙狀態(tài)。,7.2.1 用戶訪問接口,2.open入口點 close()函數(shù)的作用是關(guān)閉由open()函數(shù) 打開的文件,其調(diào)用格式為: int close(int handle); 該函數(shù)關(guān)閉文件描述字handle相連的文件。,7.2.1 用戶訪
9、問接口,3.read入口點 從設(shè)備上讀數(shù)據(jù)。對于有緩沖區(qū)的I/O操作, 一般是從緩沖區(qū)里讀數(shù)據(jù)。read()函數(shù)的調(diào)用格式為: int read(int handle,void *buf,int count); read()函數(shù)從handle(文件描述字)相連的文件中,讀取count個字節(jié)放到buf所指的緩沖區(qū)中,返回值為實際所讀字節(jié)數(shù),返回-1表示出錯。返回0表示文件結(jié)束。,7.2.1 用戶訪問接口,4.write入口點 往設(shè)備上寫數(shù)據(jù),對于有緩沖區(qū)的I/O操作,一般是把數(shù)據(jù)寫入緩沖區(qū)里。write()函數(shù)的調(diào)用格式為: int write(int handle,void *buf,int
10、count); write()函數(shù)把count個字節(jié)從buf指向的緩沖區(qū)寫入與handle相連的文件中,返回值為實際寫入的字節(jié)數(shù)。,7.2.1 用戶訪問接口,5.ioctl入口點 執(zhí)行讀、寫之外的操作。函數(shù)原型為: int ioctl(int fd,int cmd,) 參數(shù)cmd不經(jīng)修改地傳遞給驅(qū)動程序,可選的arg參數(shù)無論是指針還是整數(shù)值,都以unsigned long的形式傳遞給驅(qū)動程序。,7.2 設(shè)備文件接口,7.2.2 一些重要數(shù)據(jù)結(jié)構(gòu) 1.file_operations結(jié)構(gòu) 在Linux中,常用一個結(jié)構(gòu)作為調(diào)用設(shè)備驅(qū)動程序中各個函數(shù)的跳轉(zhuǎn)表,即把指向這組入口點的指針集中在一個結(jié)構(gòu)中。
11、這個結(jié)構(gòu)就是定義于linux/fs.h文件中的file_operations。,7.2.2 一些重要數(shù)據(jù)結(jié)構(gòu),2.文件結(jié)構(gòu) 在中定義的struct file是設(shè)備驅(qū)動程序的第二個最重要的數(shù)據(jù)結(jié)構(gòu)。File結(jié)構(gòu)代表一個“打開的文件”,它與由structinode表示的“磁盤設(shè)備文件”有所不同。File結(jié)構(gòu)由內(nèi)核在打開時創(chuàng)建,而且在關(guān)閉前作為參數(shù)傳遞給操作在設(shè)備上的函數(shù)。在文件關(guān)閉后,內(nèi)核釋放這個數(shù)據(jù)結(jié)構(gòu)。,7.2.2 一些重要數(shù)據(jù)結(jié)構(gòu),3.inode結(jié)構(gòu) inode結(jié)構(gòu)由內(nèi)核在內(nèi)部用來表示文件。因此,它和代表打開文件描述符的文件結(jié)構(gòu)是不同的。可能有代表單個文件的多個打開描述符的許多文件結(jié)構(gòu),但是
12、它們都指向一個單一的inode結(jié)構(gòu)。,7.2 設(shè)備文件接口,7.2.3 I/O操作 1.ioctl 大部分驅(qū)動除了需要讀寫設(shè)備的能力,往往還需要通過設(shè)備驅(qū)動進(jìn)行各種硬件控制的能力。用戶空間必須常常能夠請求設(shè)備進(jìn)行超出簡單的數(shù)據(jù)傳輸之外的操作。最常用的通過設(shè)備驅(qū)動程序完成控制動作的方法就是實現(xiàn)ioctl函數(shù)。,7.2.3 I/O操作,2.阻塞型和非阻塞型I/O操作 對于read調(diào)用,可能沒有數(shù)據(jù)可讀,而又沒有到達(dá)文件末尾;或者一個進(jìn)程可能試圖寫操作,但是設(shè)備因為輸出緩沖滿了還沒有準(zhǔn)備好接收數(shù)據(jù)。調(diào)用進(jìn)程往往不關(guān)心這種問題,程序員只希望調(diào)用read或write,并且使調(diào)用在必要的工作完成后返回。,
13、7.2.3 I/O操作,2.阻塞型和非阻塞型I/O操作 在這種情形下,驅(qū)動程序應(yīng)當(dāng)(缺省地)阻塞進(jìn)程,使它進(jìn)入睡眠直到請求可繼續(xù),即阻塞型I/O操作。有時為實現(xiàn)正確的unix語義,要求一個操作不阻塞,即便它不能完全地進(jìn)行下去,或者有時調(diào)用進(jìn)程通知你,不管I/O是否繼續(xù),它都不想阻塞,這就是非阻塞型I/O操作。,7.2.3 I/O操作,3.異步觸發(fā) 盡管大多數(shù)時候,阻塞型、非阻塞型I/O操作以及select的結(jié)合可以有效地查詢設(shè)備,但某些時候用這種技術(shù)管理就不夠高效了。例如,一個在低優(yōu)先級執(zhí)行長計算循環(huán)的進(jìn)程,需要盡可能快地處理輸入數(shù)據(jù)。更好的方法是通過使能異步觸發(fā),無論何時數(shù)據(jù)可用,這個進(jìn)程接
14、受一個信號并不需要自己去查詢。,7.2.3 I/O操作,要打開異步觸發(fā)機(jī)制,用戶程序必須執(zhí)行兩個步驟。 首先,指定一個進(jìn)程作為文件的擁有者(屬主)。當(dāng)一個進(jìn)程使用fcntl系統(tǒng)調(diào)用發(fā)出F_SETOWN命令時,這個擁有者進(jìn)程的ID被保存在filp-f_owner中; 第二步,為了確實打開異步觸發(fā)機(jī)制,用戶程序還必須通過另外一個fcntl命令F_SETFL設(shè)置設(shè)備的FASYNC標(biāo)志。,主要內(nèi)容,7.1概述 7.2設(shè)備文件接口 7.3中斷處理 7.4應(yīng)用實例,7.3 中斷處理,在現(xiàn)代操作系統(tǒng)中,中斷是發(fā)揮硬件尤其是CPU性能的一個重要方面。一般情況下操作系統(tǒng)向具體的硬件發(fā)出一個請求操作,該硬件就在自
15、己的設(shè)備控制器控制下工作,在它完成所請求的任務(wù)時,利用中斷來通知操作系統(tǒng),操作系統(tǒng)根據(jù)它的狀態(tài)調(diào)用相應(yīng)的處理函數(shù)進(jìn)行處理,這樣就避免了在硬件工作時操作系統(tǒng)的無效等待,提高了系統(tǒng)的運行效率。,7.3 中斷處理,7.3.1 注冊中斷處理程序 向內(nèi)核注冊中斷處理程序主要實現(xiàn)兩個功能:一是注冊中斷號,二是注冊中斷處理函數(shù)。在Linux中對應(yīng)的中斷處理注冊函數(shù)為: int request_irq(unsigned int irq,void(*handler)(int,void *,struct pt_regs *),unsigned long flags,const char *device,void
16、*dev_id);,7.3.1 注冊中斷處理程序,返回值: request_irq 返回0表示成功;返回-INVAL表示失敗(irq15或handler=NULL);返回-EBUSY表示中斷已經(jīng)被占用且不能共享。,7.3.1 注冊中斷處理程序,在一個設(shè)備驅(qū)動程序向內(nèi)核注冊了中斷服務(wù)程序后,中斷到來時的調(diào)度就由內(nèi)核的中斷處理子系統(tǒng)來完成了。中斷處理子系統(tǒng)的一個主要任務(wù)是根據(jù)中斷號找到正確的中斷處理代碼段。如圖 76所示,Linux中維護(hù)了一個irq_action指針指向的中斷函數(shù)處理向量表,該表由irqaction結(jié)構(gòu)組成。,7.3 中斷處理,7.3.2 中斷處理程序?qū)崿F(xiàn) 構(gòu)建了中斷處理的框架后
17、,接下來的任務(wù)就是根據(jù)實際任務(wù)實現(xiàn)中斷處理程序的具體功能。通常中斷處理程序的主要任務(wù)是喚醒那些在設(shè)備上睡眠的進(jìn)程,告訴它們進(jìn)入運行態(tài)的條件已經(jīng)具備,使之進(jìn)行相應(yīng)的處理。 中斷處理的一個主要特點是必須在中斷時間內(nèi)運行,這使得它的行為受到些限制。,7.3.2 中斷處理程序?qū)崿F(xiàn),中斷函數(shù)處理向量表示意圖,7.3.2 中斷處理程序?qū)崿F(xiàn),一般在中斷產(chǎn)生時,系統(tǒng)都要暫時關(guān)閉其它中斷,如果該中斷是快速中斷,它可以在很短的時間內(nèi)完成,這對其它的中斷影響很小。但對于那些耗時很多的中斷該怎么處理呢? 在現(xiàn)代操作系統(tǒng)中處理這種情況主要是將一個中斷處理分離成“上半部”和“下半部”兩個階段。,主要內(nèi)容,7.1 概述 7
18、.2 設(shè)備文件接口 7.3 中斷處理 7.4 應(yīng)用實例,7.4 應(yīng)用實例,7.4.1 字符設(shè)備按鍵驅(qū)動程序 構(gòu)建了中斷處理的框架后,接下來的任務(wù)就是根據(jù)實際任務(wù)實現(xiàn)中斷處理程序的具體功能。通常中斷處理程序的主要任務(wù)是喚醒那些在設(shè)備上睡眠的進(jìn)程,告訴它們進(jìn)入運行態(tài)的條件已經(jīng)具備,使之進(jìn)行相應(yīng)的處理。 中斷處理的一個主要特點是必須在中斷時間內(nèi)運行,這使得它的行為受到些限制。,7.4.1字符設(shè)備按鍵驅(qū)動程序,按鍵的硬件連接如圖 77所示。,圖 77 按鍵的硬件連接,7.4.1字符設(shè)備按鍵驅(qū)動程序,1.設(shè)備初始化 驅(qū)動程序在init_keyboard()中實現(xiàn)向系統(tǒng)注冊主次設(shè)備號、設(shè)備名,并初始化寄存
19、器。代碼如下: void init_dev_set(void) ICR = 0 x00;/低電平觸發(fā)中斷 PDDIR = 0 x80;/設(shè)置PD7為輸入 PDSEL = 0 x80;/PD7作為I/O與外部連接 PDKBEN = 0 x00;/鍵盤中斷使能 ,7.4.1字符設(shè)備按鍵驅(qū)動程序,int init_keyboard(void) #define keyboard_major 50/手動分配主設(shè)備號為50 #define keyboard_minor 0/次設(shè)備號為0 int rc; /向系統(tǒng)注冊字符設(shè)備 rc = register_chrdev(keyboard_major,keybo
20、ard,& keyboard_fops); if(rc0) /register_chrdev()的返回值小于零,注冊失敗 printk(Panic! Could not register keyboard-Drivern); else init_dev_set(); return rc; ;,7.4.1字符設(shè)備按鍵驅(qū)動程序,2.注冊中斷和中斷處理程序 在open函數(shù)中向內(nèi)核注冊中斷,代碼如下: static int keyboard_open(struct inode *inode,struct file *file) rc = request_irq(IRQ_MACHSPEC|IRQ6_IR
21、Q_NUM,keyboard_interrupt,IRQ_FLG_STD,keyboard-IRQ,NULL); if(rc)/返回值不為零,則注冊失敗 printk(keyboard-Driver:Error while installing interrupt handlern); return -ENODEV; ; MOD_INC_USE_COUNT; return 0; ,7.4.1字符設(shè)備按鍵驅(qū)動程序,中斷處理程序如下: static void keyboard_interrupt(int irq,void *dev_id,struct pt_regs *regs) ISR |= (
22、118); wake_up_interruptible(&wq);/喚醒隊列 #ifdef DEBUG printk(Ive woken up the processn); #endif return 0; ,7.4.1字符設(shè)備按鍵驅(qū)動程序,3.read的實現(xiàn) static int keyboard_read(struct inode *inode,struct file *file,char *buffer,int size) char * ch; #ifdef DEBUG /調(diào)用讀函數(shù)時的調(diào)試信息 printk(“Im reading the device!n”); #endif inte
23、rruptible_sleep_on(&wq); #ifdef DEBUG printk(Im wake up!n); #endif return 0; ,7.4 應(yīng)用實例,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序 1.CS8900A芯片特點 CS8900A芯片是一個高度集成的以太網(wǎng)控制器芯片,它集成了ISA總線接口、曼徹斯特編碼/解碼器、片上RAM、10BASET收發(fā)器、數(shù)據(jù)鏈路控制器MAC和芯上存儲管理器等,是嵌入式平臺實現(xiàn)10M以太網(wǎng)連接的很好的選擇方案。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,(1) EEPROM 如果不使用CS8900A芯片的默認(rèn)設(shè)置,EEPROM是必
24、須要操作的,因為芯片的MAC地址都存在這里。另外還有一些用戶設(shè)置,比如工作模式等,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,(2)工作模式 CS8900A有兩種工作模式:MEMORY模式和I/O模式。 在MEMORY模式下編程操作較為簡單,對任何寄存器都是直接操作,不過這需要硬件上多根地址線和網(wǎng)卡連接。 I/O模式下對任何寄存器操作均要通過I/O端口0X300寫入或讀出,但這種模式在硬件上實現(xiàn)比較方便,而且是芯片的默認(rèn)模式,所以在Linux中采用這種工作模式,它的傳輸效率是MEMORY模式的96左右。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,一般情況下它的流程如下: 測設(shè)備是否存
25、在; 檢測中斷號和I/O地址; 填充device結(jié)構(gòu)大部分屬性字段; 調(diào)用ether_setup(dev); 調(diào)用kmalloc申請需要的內(nèi)存空間。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,2.初始化函數(shù) 網(wǎng)絡(luò)設(shè)備的探測是在初始化函數(shù)里完成的。該函數(shù)唯一的參數(shù)是一個指向設(shè)備的指針,其返回值是0或者一個負(fù)的錯誤代碼。在采用“啟動初始化方式”加載驅(qū)動程序時,該函數(shù)在中被注冊進(jìn)內(nèi)核,在init進(jìn)程啟動時被net_dev_init()調(diào)用。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,3.設(shè)備打開函數(shù)與關(guān)閉函數(shù) 打開和關(guān)閉一個網(wǎng)絡(luò)接口是由ifconfig命令來完成的。當(dāng)使用ifconfig
26、為一個接口賦地址時,它完成兩項工作。 第一,它通過ioctl(SIOCSIFADDR)(即Socket I/O Control Set InterFace ADDRess)來賦地址; 第二,它通過ioctl(SIOCSIFFLAGS)(即Socket I/O Control Set InterFace FLAGS)對dev-flag中的IFF_UP置位來打開接口。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,一般情況下設(shè)備打開函數(shù)net_open的基本流程如下: 沒有在初始化函數(shù)中注冊中斷號和I/O地址,則在設(shè)備打開時要進(jìn)行注冊; 將該設(shè)備掛到irq2dev_map中。若使用基于中斷的數(shù)據(jù)
27、接收方式,以后就可以通過中斷號和irq2dev_map數(shù)組直接查找相應(yīng)的設(shè)備了; 初始化物理設(shè)備的寄存器; 設(shè)置接口相應(yīng)的dev的私有數(shù)據(jù)結(jié)構(gòu)(dev-priv)中的一些字段; 設(shè)置dev中的tbusy,interrupt和start等字段。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,4.數(shù)據(jù)包發(fā)送函數(shù) 當(dāng)系統(tǒng)需要發(fā)送數(shù)據(jù)時,它首先把數(shù)據(jù)打包成一個完整的sk_buff結(jié)構(gòu)體,然后調(diào)用hard_start_transmit()函數(shù)把它發(fā)送到網(wǎng)絡(luò)設(shè)備接口上。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,5.中斷處理函數(shù) 目前幾乎所有的網(wǎng)絡(luò)設(shè)備接口都是以中斷方式工作的,接口觸發(fā)中斷表明兩種
28、事件中的一種發(fā)生了:一個新包到達(dá)或一個包發(fā)送完成。中斷例程可以通過檢查硬件設(shè)備上的中斷狀態(tài)寄存器來判斷是什么事件觸發(fā)了中斷。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,一般的中斷服務(wù)程序的基本流程如下: 確定發(fā)生中斷的具體網(wǎng)絡(luò)接口; 打開標(biāo)志位dev-interrupt,表示本服務(wù)程序正在被使用; 讀取中斷狀態(tài)寄存器,根據(jù)寄存器判斷中斷發(fā)生的原因。有兩種可能,一種是有新數(shù)據(jù)包到達(dá);另一種是上次的數(shù)據(jù)傳輸已完成。 若是因為有新數(shù)據(jù)包到達(dá),則調(diào)用接收數(shù)據(jù)包的子函數(shù)net_rx(); 如果中斷是上次傳輸引起,則通知協(xié)議的上一層,修改接口的統(tǒng)計信息,關(guān)閉標(biāo)志位tbusy,為下次傳輸做準(zhǔn)備; 關(guān)閉
29、標(biāo)志位interrupt。,7.4.2 網(wǎng)絡(luò)設(shè)備CS8900A芯片驅(qū)動程序,6.數(shù)據(jù)包接收函數(shù) 在網(wǎng)絡(luò)上有新數(shù)據(jù)包到達(dá)時,中斷處理函數(shù)僅僅調(diào)用數(shù)據(jù)包接收子函數(shù)net_rx()即可。一般情況下net_rx()函數(shù)的操作流程如下: 申請skb緩存區(qū)存儲新的數(shù)據(jù)包; 從硬件中讀取新到達(dá)的數(shù)據(jù); 調(diào)用函數(shù)netif_rx(),將新的數(shù)據(jù)包向網(wǎng)絡(luò)協(xié)議的上一層傳送; 修改接口的統(tǒng)計函數(shù)。,7.4 應(yīng)用實例,7.4.3 CAN總線驅(qū)動開發(fā) 1. CAN總線介紹 CAN(Controller Area Network)總線最早是由德國BOSCH公司提出,實現(xiàn)汽車環(huán)境中的微控制器通訊,在車載各電子控制裝置ECU
30、之間交換信息,形成汽車電子控制網(wǎng)絡(luò)。由于其具有成本低,實時性好,容錯性高,設(shè)計靈活等特點,目前已被廣泛地應(yīng)用于各種工業(yè)領(lǐng)域,被公認(rèn)為是最有前途的現(xiàn)成總線之一。,7.4.3 CAN總線驅(qū)動開發(fā),本節(jié)所使用的CAN設(shè)備是Philips公司的SJA1000芯片。該芯片除支持PCA82C200模式(即默認(rèn)的BasicCAN模式)外,還支持PeliCAN模式,并提供INTEL和Motorola兩種尋址方式。PeliCAN模式的擴(kuò)展功能包括:可讀/寫訪問的錯誤計數(shù)器、可編程的錯誤報警限制、單次發(fā)送、只聽模式、支持熱插拔等等。,7.4.3 CAN總線驅(qū)動開發(fā),2.CAN驅(qū)動開發(fā)流程及其實現(xiàn),圖 79 SJA
31、1000與EP9315處理器的硬件連接,7.4.3 CAN總線驅(qū)動開發(fā),圖 710 CAN總線驅(qū)動程序流程,7.4.3 CAN總線驅(qū)動開發(fā),(1)模塊的初始化 模塊的初始化函數(shù)module_init負(fù)責(zé)注冊模塊所提供的任何設(shè)施。module_init的使用是強(qiáng)制性的,這個宏會在模塊的目標(biāo)代碼中增加一個特殊的段,用于說明內(nèi)核初始化函數(shù)所在的位置。沒有這個定義,初始化函數(shù)永遠(yuǎn)不會調(diào)用。,7.4.3 CAN總線驅(qū)動開發(fā),(2)服務(wù)于I/O請求的子程序 在這一部分中完成數(shù)據(jù)結(jié)構(gòu)file_operations的填充,實現(xiàn)該文件操作接口。本驅(qū)動中的file_operations結(jié)構(gòu)如下: Struct f
32、ile_operations fops = owner: THIS_MODULE, read: can_read, poll: can_poll, llseek: can_llseek, write: can_write, ioctl: can_ioctl, open: can_open, ,7.4.3 CAN總線驅(qū)動開發(fā),(3)中斷服務(wù)子程序 在模塊初始化時已經(jīng)利用request_irq()函數(shù)注冊了設(shè)備中斷,所以當(dāng)中斷請求IRQ產(chǎn)生時,將運行中斷服務(wù)例程ISR。在中斷服務(wù)程序中,首先要讀取SJA1000的中斷寄存器IR的值,識別中斷源,比如當(dāng)接收中斷位RI為1,則說明是接收中斷,進(jìn)而調(diào)用接收函數(shù)來接收數(shù)據(jù)。當(dāng)CPU讀取這個只讀存儲器時,除了RI位外的所有位都將被復(fù)位。,7.4.3 CAN總線驅(qū)動開發(fā),(4)緩沖區(qū)操作 SJA1000內(nèi)部設(shè)有發(fā)送緩沖器TXB(13個字節(jié))、接收緩沖器RXB(13個字節(jié))和RXF
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 2025至2031年中國氣壓維護(hù)裝置行業(yè)投資前景及策略咨詢研究報告
- 拉薩師范高等??茖W(xué)?!队脩趔w驗與交互設(shè)計》2023-2024學(xué)年第二學(xué)期期末試卷
- 鄭州科技學(xué)院《日語新聞聽力》2023-2024學(xué)年第二學(xué)期期末試卷
- 湖南司法警官職業(yè)學(xué)院《英語短篇小說佳作欣賞》2023-2024學(xué)年第二學(xué)期期末試卷
- 江蘇醫(yī)藥職業(yè)學(xué)院《成型技術(shù)基礎(chǔ)》2023-2024學(xué)年第二學(xué)期期末試卷
- 2025某建筑勞務(wù)分包合同
- 索鞍安裝施工方案
- 2025綠化工程供料合同范本
- 2025年“1+N”全景式假期成長實踐作業(yè)設(shè)計模板
- 2025至2030年中國鐵藝貨架數(shù)據(jù)監(jiān)測研究報告
- 國家發(fā)展改革委低空經(jīng)濟(jì)司
- 課題申報書:醫(yī)學(xué)院校研究生“導(dǎo)學(xué)思政”創(chuàng)新實踐路徑研究
- 2025年游泳教練資格認(rèn)證考試?yán)碚撛囶}集(初級)
- 委托律師簽署協(xié)議書
- 圖文工廠轉(zhuǎn)讓協(xié)議書
- 貨物貿(mào)易的居間合同
- 2025-2030中國療養(yǎng)院行業(yè)市場深度分析及前景趨勢與投資研究報告
- 2025年國企山東濟(jì)南公共交通集團(tuán)有限公司招聘筆試參考題庫附帶答案詳解
- 2024版《糖尿病健康宣教》課件
- 機(jī)油化學(xué)品安全技術(shù)(MSDS)說明書
- 《項脊軒志》公開課課件【一等獎】
評論
0/150
提交評論