Linux設(shè)備驅(qū)動(dòng)程序課件(PPT 62頁(yè)).ppt_第1頁(yè)
Linux設(shè)備驅(qū)動(dòng)程序課件(PPT 62頁(yè)).ppt_第2頁(yè)
Linux設(shè)備驅(qū)動(dòng)程序課件(PPT 62頁(yè)).ppt_第3頁(yè)
Linux設(shè)備驅(qū)動(dòng)程序課件(PPT 62頁(yè)).ppt_第4頁(yè)
Linux設(shè)備驅(qū)動(dòng)程序課件(PPT 62頁(yè)).ppt_第5頁(yè)
已閱讀5頁(yè),還剩57頁(yè)未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說(shuō)明:本文檔由用戶(hù)提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡(jiǎn)介

1、Linux設(shè)備驅(qū)動(dòng),廣州嵌入式軟件公共技術(shù)支持中心 梁老師 2007年07月,設(shè)備驅(qū)動(dòng)概述,操作系統(tǒng)是通過(guò)各種驅(qū)動(dòng)程序來(lái)駕馭硬件設(shè)備,它為用戶(hù)屏蔽了各種各樣的設(shè)備,硬件設(shè)備的抽象。 設(shè)備驅(qū)動(dòng)程序:處理和管理硬件控制器的軟件。 設(shè)備驅(qū)動(dòng)程序是操作系統(tǒng)內(nèi)核和機(jī)器硬件之間的接口。,設(shè)備驅(qū)動(dòng)概述,設(shè)備由兩部分組成,一個(gè)是被稱(chēng)為控制器的電器部分,另一個(gè)是機(jī)械部分。 一組寄存器組被賦予到各個(gè)控制器。I/O端口包含4組寄存器,即狀態(tài)寄存器,控制寄存器,數(shù)據(jù)輸入寄存器,數(shù)據(jù)輸出寄存器。 狀態(tài)寄存器擁有可以被CPU讀取的(狀態(tài))位,用來(lái) 指示當(dāng)前命令是否執(zhí)行完畢,或者字節(jié)是否可以被讀出或?qū)懭耄约叭魏五e(cuò)誤提示。

2、 控制寄存器則用于啟動(dòng)一條命令(指令)或者改變?cè)O(shè)備的(工作)模式。 數(shù)據(jù)輸入寄存器用于獲取輸入的數(shù)據(jù)。 數(shù)據(jù)輸出寄存器則向CPU發(fā)送結(jié)果。 處理器和設(shè)備之間的基本界面是控制和狀態(tài)寄存器。,設(shè)備驅(qū)動(dòng)概述,寄存器擁有在I/O空間明確定義的地址范圍。 通常這些地址在啟動(dòng)時(shí)被分配。 如果設(shè)備是靜態(tài)加載的,各個(gè)設(shè)備的地址范圍可能被預(yù)分配。這意味內(nèi)核包含了已存在設(shè)備的驅(qū)動(dòng) 程序。通過(guò)運(yùn)行“cat /proc/ioports” 命令檢查其所使用的地址范圍。第一列輸出顯示了端口的范圍而第二列則是擁用這些端口的設(shè)備。,設(shè)備驅(qū)動(dòng)概述,設(shè)備驅(qū)動(dòng)的概念是非常抽象的并且處于一臺(tái)計(jì)算上所運(yùn)行軟件的最低層。 由于直接到設(shè)備

3、的硬件特性的限 制。每個(gè)設(shè)備驅(qū)動(dòng)都只管理一種單一類(lèi)型的設(shè)備。 如果一個(gè)應(yīng)用 程序向設(shè)備提出(操作)要求。內(nèi)核會(huì)聯(lián)系到對(duì)應(yīng)的設(shè)備驅(qū)動(dòng),設(shè)備驅(qū)動(dòng)接著向特定的設(shè)備發(fā)出命令。 設(shè)備驅(qū) 動(dòng)是一個(gè)函數(shù)集合:包含了許多調(diào)用入口,類(lèi)似于open,close,read,write,ioctl,llseek 等。,設(shè)備驅(qū)動(dòng)概述,Linux操作系統(tǒng)把設(shè)備納入文件系統(tǒng)的范疇來(lái)管理。 文件操作是對(duì)設(shè)備操作的組織和抽象。設(shè)備操作則是對(duì)文件操作的最終實(shí)現(xiàn)。 每個(gè)設(shè)備都對(duì)應(yīng)一個(gè)文件名,在內(nèi)核中也就對(duì)應(yīng)一個(gè)索引節(jié)點(diǎn)。 對(duì)文件操作的系統(tǒng)調(diào)用大都適用于設(shè)備文件。 從應(yīng)用程序的角度看,設(shè)備文件邏輯上的空間是一個(gè)線性空間(起始地址為0

4、,每讀取一個(gè)字節(jié)加1)。從這個(gè)邏輯空間到具體設(shè)備物理空間(如磁盤(pán)的磁道、扇區(qū))的映射則是由內(nèi)核提供,并被劃分為文件操作和設(shè)備驅(qū)動(dòng)兩個(gè)層次。,設(shè)備驅(qū)動(dòng)概述,Linux將設(shè)備分成兩大類(lèi)。 一類(lèi)像鍵盤(pán)那樣以字符(字節(jié))為單位,逐個(gè)字符進(jìn)行輸入輸出的設(shè)備,稱(chēng)為字符設(shè)備。 一類(lèi)是像磁盤(pán)那樣以塊或扇區(qū)為單位,成塊進(jìn)行輸入輸出的設(shè)備,稱(chēng)為塊設(shè)備。 文件系統(tǒng)通常都建立在塊設(shè)備上。,設(shè)備驅(qū)動(dòng)概述,文件操作和設(shè)備驅(qū)動(dòng)是對(duì)一個(gè)具體的設(shè)備操作的不同層次。從這種觀點(diǎn)出發(fā),從概念上可以把一個(gè)系統(tǒng)劃分為應(yīng)用、文件系統(tǒng)和設(shè)備驅(qū)動(dòng)三個(gè)層次。,設(shè)備驅(qū)動(dòng)概述,設(shè)備驅(qū)動(dòng)概述,要使一項(xiàng)設(shè)備可以被應(yīng)用程序訪問(wèn),首先要在系統(tǒng)中建立一個(gè)代表

5、此設(shè)備的設(shè)備文件,這是通過(guò)系統(tǒng)調(diào)用mknode()實(shí)現(xiàn)的。此外,更重要的是在設(shè)備驅(qū)動(dòng)層要有這種設(shè)備的驅(qū)動(dòng)程序。,設(shè)備驅(qū)動(dòng)概述,設(shè)備文件: 任何設(shè)備都被當(dāng)作路徑/dev 的設(shè)備文件處理,并通過(guò)這些設(shè)備文件提供訪問(wèn)硬件的方法。 每個(gè)設(shè)備文件除了設(shè)備名外,還有類(lèi)型、主設(shè)備號(hào)、次設(shè)備號(hào)這三個(gè)屬性。 設(shè)備文件是通過(guò)mknod系統(tǒng)調(diào)用創(chuàng)建的。其原型為:mknod(const char * filename, int mode, dev_t dev) mknod /dev/led0 c 253 0,設(shè)備驅(qū)動(dòng)概述,主設(shè)備號(hào)和次設(shè)備號(hào): 主設(shè)備號(hào)標(biāo)識(shí)設(shè)備對(duì)應(yīng)的驅(qū)動(dòng)程序。一般“一個(gè)主設(shè)備號(hào)對(duì)應(yīng)一個(gè)驅(qū)動(dòng)程序” 次設(shè)

6、備號(hào)用于確定設(shè)備文件所指的設(shè)備。 可通過(guò)ls l “設(shè)備文件名”命令查看設(shè)備的主次設(shè)備號(hào),以及設(shè)備的類(lèi)型。,設(shè)備驅(qū)動(dòng)概述,主設(shè)備號(hào)和次設(shè)備號(hào)的內(nèi)部表達(dá): Dev_t類(lèi)型用于保存設(shè)備號(hào),稱(chēng)為設(shè)備編號(hào)。/linux/types.h文件中定義。 目前設(shè)備編號(hào)dev_t是一個(gè)32位的整數(shù),其中12位表示主設(shè)備號(hào),20位表示次設(shè)備號(hào)。 通過(guò)設(shè)備編號(hào)獲取主次設(shè)備號(hào): MAJOR(dev_t dev); MINOR(dev_t dev); 通過(guò)主次設(shè)備號(hào)合成設(shè)備編號(hào): MKDEV(int major, int minor); Dev_t格式以后可能會(huì)發(fā)生變化,但只要使用這些宏,就可保證設(shè)備驅(qū)動(dòng)程序的正確性。

7、,一些重要的數(shù)據(jù)結(jié)構(gòu),大部分驅(qū)動(dòng)程序涉及三個(gè)重要的內(nèi)核數(shù)據(jù)結(jié)構(gòu): 文件操作file_operations結(jié)構(gòu)體 文件對(duì)象file結(jié)構(gòu)體 索引節(jié)點(diǎn)inode結(jié)構(gòu)體,一些重要的數(shù)據(jù)結(jié)構(gòu),文件操作結(jié)構(gòu)體file_operations 結(jié)構(gòu)體file_operations在頭文件 linux/fs.h中定義,用來(lái)存儲(chǔ)驅(qū)動(dòng)內(nèi)核模塊提供的對(duì)設(shè)備進(jìn)行各種操作的函數(shù)的指針。 結(jié)構(gòu)體的每個(gè)域都對(duì)應(yīng)著驅(qū)動(dòng)模塊用來(lái)處理某個(gè)被請(qǐng)求的事務(wù)的函數(shù)的地址。 struct file_operations struct module *owner; loff_t(*llseek) (struct file *, loff_t,

8、 int); ssize_t(*read) (struct file *, char _user *, size_t, loff_t *); ssize_t(*write) (struct file *, const char _user *, size_t, loff_t *); 。 ,一些重要的數(shù)據(jù)結(jié)構(gòu),file_operations重要的成員 Struct module *owner ,指向擁有該結(jié)構(gòu)體的模塊的指針。 方法llseek用來(lái)修改文件的當(dāng)前讀寫(xiě)位置,把新位置作為返回值返回。 方法read用來(lái)從設(shè)備中讀取數(shù)據(jù)。非負(fù)返回值表示成功讀取的直接數(shù)。 方法write向設(shè)備發(fā)送數(shù)據(jù)。 方

9、法ioctl提供一種執(zhí)行設(shè)備特定命令的方法。,一些重要的數(shù)據(jù)結(jié)構(gòu),file_operations重要的成員 驅(qū)動(dòng)內(nèi)核模塊是不需要實(shí)現(xiàn)每個(gè)函數(shù)的。相對(duì)應(yīng)的file_operations的項(xiàng)就為 NULL。 Gcc的語(yǔ)法擴(kuò)展,使得可以定義該結(jié)構(gòu)體: struct file_operations fops = read: device_read, write: device_write, open: device_open, release: device_release ; 這種語(yǔ)法清晰,沒(méi)有顯示聲明的結(jié)構(gòu)體成員都被gcc初始化為NULL。,一些重要的數(shù)據(jù)結(jié)構(gòu),file_operations重要的

10、成員 標(biāo)準(zhǔn)C的標(biāo)記化結(jié)構(gòu)體的初始化方法: struct file_operations fops = .read = device_read, .write = device_write, .open = device_open, .release = device_release ; 推薦使用該方法,提高移植性,方法允許對(duì)結(jié)構(gòu)體成員進(jìn)行重新排列。沒(méi)有顯示聲明的結(jié)構(gòu)體成員同樣都被gcc初始化為NULL。 指向結(jié)構(gòu)體file_operations的指針通常命名為fops。,一些重要的數(shù)據(jù)結(jié)構(gòu),文件對(duì)象file結(jié)構(gòu)體 文件對(duì)象file代表著一個(gè)打開(kāi)的文件。進(jìn)程通過(guò)文件描述符fd與已打開(kāi)文件的fil

11、e結(jié)構(gòu)相聯(lián)系。進(jìn)程通過(guò)它對(duì)文件的線性邏輯空間進(jìn)行操作。例如:file-f_op-read(); Struct file 在中定義。 指向結(jié)構(gòu)體struct file的指針通常命名為filp,或者file。建議使用文件指針filp。,一些重要的數(shù)據(jù)結(jié)構(gòu),文件對(duì)象file結(jié)構(gòu)體的成員 Struct file_operations *f_op; 與文件相關(guān)的操作結(jié)構(gòu)體指針。與文件相關(guān)的操作是在打開(kāi)文件的時(shí)候確定下來(lái)的,也就是確定該指針的值。可在需要的時(shí)候,改變指針?biāo)赶虻奈募僮鹘Y(jié)構(gòu)體。用C語(yǔ)言實(shí)現(xiàn)面向?qū)ο缶幊痰姆椒ㄖ剌d。 其他成員可先忽略,后面具體實(shí)例分析。因?yàn)樵O(shè)備驅(qū)動(dòng)模塊并不自己直接填充結(jié)構(gòu)體

12、file,只是使用file中的數(shù)據(jù)。,一些重要的數(shù)據(jù)結(jié)構(gòu),索引節(jié)點(diǎn)inode結(jié)構(gòu) 文件打開(kāi),在內(nèi)存建立副本后,由唯一的索引節(jié)點(diǎn)inode描述。 與file結(jié)構(gòu)不同。 file結(jié)構(gòu)是進(jìn)程使用的結(jié)構(gòu),進(jìn)程每打開(kāi)一個(gè)文件,就建立一個(gè)file結(jié)構(gòu)。不同的進(jìn)程打開(kāi)同一個(gè)文件,建立不同的file結(jié)構(gòu)。 Inode結(jié)構(gòu)是內(nèi)核使用的結(jié)構(gòu),文件在內(nèi)存建立副本,就建立一個(gè)inode結(jié)構(gòu)來(lái)描述。一個(gè)文件在內(nèi)存里面只有一個(gè)inode結(jié)構(gòu)對(duì)應(yīng)。,一些重要的數(shù)據(jù)結(jié)構(gòu),索引節(jié)點(diǎn)inode結(jié)構(gòu) Inode結(jié)構(gòu)包含大量描述文件信息的成員變量。 但是對(duì)于描述設(shè)備文件的inode,跟設(shè)備驅(qū)動(dòng)有關(guān)的成員只有兩個(gè)。 Dev_t i_r

13、dev; 包含真正的設(shè)備編號(hào)。 Struct cdev *i_cdev; 指向cdev結(jié)構(gòu)體的指針。cdev是表示字符設(shè)備的內(nèi)核數(shù)據(jù)結(jié)構(gòu)。 從inode中獲得主設(shè)備號(hào)和次設(shè)備號(hào)的宏: Unsigned int iminor(struct inode *inode); Unsigned int imajor(struct inode *inode);,驅(qū)動(dòng)程序中的內(nèi)存分配,在Linux內(nèi)核模式下,不能使用用戶(hù)態(tài)的malloc()和free()函數(shù)申請(qǐng)和釋放內(nèi)存。 內(nèi)核編程最常用的內(nèi)存申請(qǐng)和釋放函數(shù)為kmalloc()和kfree(),其原型為: include/linux/kernel.h vo

14、id *kmalloc(unsigned int len, int priority); void kfree(void *_ptr); priority參數(shù): 通常設(shè)置為GFP_KERNEL,可能會(huì)引起睡眠. 如果在中斷服務(wù)程序里申請(qǐng)內(nèi)存則要用GFP_ATOMIC參數(shù),在中斷中是不允許睡眠的。,初始化和卸載函數(shù),驅(qū)動(dòng)程序是內(nèi)核的一部分,因此我們需要給其添加模塊初始化函數(shù),該函數(shù)用來(lái)完成對(duì)所控設(shè)備的初始化工作,并調(diào)用register_chrdev() 函數(shù)注冊(cè)字符設(shè)備. int register_chrdev(unsigned int major, const char *name, stru

15、ct file_operations *fops); major 是給定的主設(shè)備號(hào)。為0代表什么? name 是驅(qū)動(dòng)的名字(將出現(xiàn)在 /proc/devices), fops 是設(shè)備驅(qū)動(dòng)的file_operations 結(jié)構(gòu)。 register_chrdev 將給設(shè)備分配 0 - 255 的次設(shè)備號(hào), 并且為每一個(gè)建立一個(gè)缺省的 cdev 結(jié)構(gòu)。 與模塊初始化函數(shù)對(duì)應(yīng)的就是模塊卸載函數(shù),需要調(diào)用register_chrdev()的反函數(shù),設(shè)備操作函數(shù)集的定義,file_operations結(jié)構(gòu)體,驅(qū)動(dòng)程序只是利用其中的一部分。 對(duì)于字符設(shè)備來(lái)說(shuō),要提供的主要入口有:open ()、releas

16、e ()、read ()、write ()、ioctl ()等。,設(shè)備操作函數(shù)集的定義,open()函數(shù) 對(duì)設(shè)備特殊文件進(jìn)行open()系統(tǒng)調(diào)用時(shí),將調(diào)用驅(qū)動(dòng)程序的open () 函數(shù): int (*open)(struct inode * ,struct file *); 參數(shù)inode為設(shè)備特殊文件的inode (索引結(jié)點(diǎn)) 結(jié)構(gòu)的指針, 參數(shù)file是指向這一設(shè)備的文件結(jié)構(gòu)的指針。 open()的主要任務(wù)是確定硬件處在就緒狀態(tài)、驗(yàn)證次設(shè)備號(hào)的合法性(次設(shè)備號(hào)可以用MINOR(inode- i - rdev) 取得)、控制使用設(shè)備的進(jìn)程數(shù)、根據(jù)執(zhí)行情況返回狀態(tài)碼(0表示成功,負(fù)數(shù)表示存在錯(cuò)

17、誤) 等;,設(shè)備操作函數(shù)集的定義,release()函數(shù) 當(dāng)最后一個(gè)打開(kāi)設(shè)備的用戶(hù)進(jìn)程執(zhí)行close ()系統(tǒng)調(diào)用時(shí),內(nèi)核將調(diào)用驅(qū)動(dòng)程序的release () 函數(shù): void (*release) (struct inode * ,struct file *) ; release 函數(shù)的主要任務(wù)是清理未結(jié)束的輸入/輸出操作、釋放資源、用戶(hù)自定義排他標(biāo)志的復(fù)位等.,設(shè)備操作函數(shù)集的定義,read()函數(shù) Read的任務(wù), 就是從設(shè)備拷貝數(shù)據(jù)到用戶(hù)空間。 當(dāng)對(duì)設(shè)備特殊文件進(jìn)行read() 系統(tǒng)調(diào)用時(shí),將調(diào)用驅(qū)動(dòng)程序read() 函數(shù): ssize_t read(struct file *filp

18、, char _user *buff, size_t count, loff_t *offp); filp 是文件對(duì)象指針, count 是請(qǐng)求的傳輸數(shù)據(jù)大小. buff 參數(shù)對(duì)write來(lái)說(shuō)是指向持有被寫(xiě)入數(shù)據(jù)的緩存, 對(duì)read則是放入新數(shù)據(jù)的空緩存. offp 是指向一個(gè)“l(fā)ong offset type”的指針, 它指出用戶(hù)正在存取的文件位置. 返回值是“signed size type”類(lèi)型;,設(shè)備操作函數(shù)集的定義,write( ) 函數(shù) Write的任務(wù),則從用戶(hù)空間拷貝數(shù)據(jù)到設(shè)備。 當(dāng)設(shè)備特殊文件進(jìn)行write () 系統(tǒng)調(diào)用時(shí),將調(diào)用驅(qū)動(dòng)程序的write () 函數(shù): ssize_t write(st

溫馨提示

  • 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶(hù)所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒(méi)有圖紙預(yù)覽就沒(méi)有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶(hù)上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶(hù)上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶(hù)因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。

評(píng)論

0/150

提交評(píng)論