Linux 驅動程式觀念解析, #4: Linux 驅動程式一般化設計流程

jollen 發表於 May 4, 2006 9:06 AM

了解重要的架構觀念面後,接著就是 Linux 驅動程式本身了!Linux 驅動程式的設計雖然沒有一定的標準流程,但是由「觀念」層面可以歸納出一個一般化的流程。

作者/陳俊宏
www.jollen.org

一般化設計流程

我們提過,依照驅動程式本身的實作,可以將 Linux 驅動程式分為 2 大部份:virtual device driver與physical device driver。

此流程為一個觀念流程,實際撰寫驅動程式時,並不會完全以這個流程來設計。但初學Linux驅動程式時,則應以此流程為主循序學習,才能理解基本的Linux驅動程式實作。

對Linux驅動程式而言,virtual device driver的重要性遠在physical device driver之上,乍聽之下這或許不太能理解,因為沒有physical device driver是無法真正驅動硬體的。但實作上,physical device driver是一成不變的程式寫法,能不能寫出好的驅動程式,關鍵是在virtual device driver的部份。

struct file_operations

struct file_operations 是 kernel 提供的一個重要資料結構,這是學習 Linux 驅動程式第一個會認識的對象,也是最重要的一個主題。

Linux 驅動程式建構在 file_operations 之上。file_operations定義驅動程式的system call與實作system call的函數,我們把file_operations任何一個部份拿出來討論的話,都能切成virtual device driver與physical device driver二個部份。

流程解說

Virtual device driver往上是為了連結Linux kernel的VFS層,physical device drvier往下是為了存取實體硬體。

Virtual Device Driver

Virtual device driver 的目的在於設計一個「機制」良好的kernel mode驅動程式,virtual device driver也必須考慮與user application的互動。實作上,則是需要善用kernel所提供的介面(interface),即kernel APIs。

Virtual device driver再分為3階段的觀念實作:

  1. 定義 file_operations
  2. 實作 system calls
  3. 註冊 driver (VFS)

fops 是指向 file_operations 結構的指標,驅動程式呼叫 register_chrdev() 將fops註冊到 kernel 裡後,fops 便成為該 device driver 所實作的system call進入點。實作system call的函數便是透過file_operations結構來定義,我們稱實作system call的函數為driver method。

kernel 會在需要時回呼 (callback) 我們所註冊的driver method。因此,當 driver 裡的 method 被呼叫時,kernel便將傳遞參數(parameters)給 driver method,driver method可由 kernel 所傳遞進來的參數取得驅動程式資訊。

註冊driver的動作呼叫register_chrdev()函數完成,此函數接受3個參數如下:

  1. major:要註冊的裝置 major number
  2. name:device 名稱
  3. fops:driver 的 file operation

「註冊」這個動作觀念上是將fops加到kernel的VFS層,因此user application必須透過「device file」才能呼叫到driver method。註冊這個動作的另一層涵意則是將driver method與不同的system call做「正確的對應」,當user application呼叫system call時,才能執行正確的driver method。

Physical Device Driver

Physical device driver的目的在於實作控制硬體的程式碼。Physical device driver 的設計必須隨時查閱晶片(chipsets)的 data sheet,並透過晶片的 control register 來控制裝置。

理論上,我們可以將晶片的暫存器分成3大類:

  1. data registers
  2. control registers
  3. status registers

Data register是晶片裡用來存放資料的暫存器,control register則是用來控制晶片行為的暫存器,status register則保存目前晶片的狀態。設計控制硬體周邊的驅動程式時,需要了解硬體使用的晶片組,晶片組則需要參考IC設計廠商所提供的「datasheet」才能了解晶片組的暫存器名稱與用途,通常不同的暫存器會對應到一個「相對」的偏移位址(offset)。

驅動程式則是要透過control register才能控制晶片,因此需要隨時查閱晶片的datasheet,並了解每一個暫存器的用途。通常暫存器的每個位元(bit)也都是有特定用途的,因此設計驅動程式時,必須要很熟悉C語言的位元運算用法。

實作上,首先會將晶片的 datasheet 寫成C語言的標頭檔,通常這個檔案都可以從 vendor 取得。

接著再定義一組操作暫存器的I/O函數,我們稱這組函數為I/O wrapper function。I/O wrapper functions通常是重新定義Linux kernel所提供的readb()、writeb()或inb()、outb()系列函數所寫成的。

最後,利用I/O wrapper function實作一系列的控制函數,以控制實際硬體,我們稱此函數為chipset control functions。Chipset control functions是由實作system calls的函數(driver method)所呼叫,因此在設計chipset control functions時也會回頭改寫driver method以符合此階段的實作。

讀者留言 (3)

  • 小石 於 February 18, 2009 14:38:

    目前看到的教學
    圖片連結都不見了!!

  • Jerry 於 December 18, 2010 10:14:

    請問可以給我所有圖片嗎?感恩

  • daniel 於 January 25, 2011 17:39:

    Hi jollen:

    >Virtual device driver往上是為了連結Linux kernel的VFS層

    以上之說法真的是我第一次聽到
    所有的周邊在linux 都被視為檔案
    所以 driver 都需提供檔案之操作介面函式
    但真的沒有人把這部分稱為virtual device driver.
    Or you can tell me which linux device driver book call this part as "virtual device driver".

    Virtual device driver 已經有很明確的意義是指無實體的device. 例如 loop back device.

    Please check again.
    Thank you.

    Daniel

留言功能維護中。將於近日重新開放。

連絡作者

Jollen Chen,Moko365(仕橙3G教室)講師,熱愛研究 Linux 與 Android 技術。曾為 Motorola、HTC、Foxconn、LG、OPPO、騰迅、廣達電腦、緯創、仁寶等超過 50 家企業講授課程。目前在 MokoVersity 擔任軟體工程師,撰寫 Node.js 程式,也在幾家科技廠兼任 Android Framework 研發顧問。您可透過電子郵件 <jollen (at) jollen (dot) org> 或這裡與我連絡。