linux misc 驅動模型分析
閱讀led驅動程式的**的時候,沒有發現ldd3中提到的各種字元裝置註冊函式,而是發現了乙個misc_register函式,這說明led裝置是作為雜項裝置出現在核心中的,在核心中,misc雜項裝置驅動介面是對一些字元裝置的簡單封裝,他們共享乙個主裝置號,有不同的次裝置號,共享乙個open呼叫,其他的操作函式在開啟後運用linux驅動程式的方法過載進行裝載。
1. 主要資料結構
核心維護乙個misc_list鍊錶,misc裝置在misc_register註冊的時候鏈結到這個鍊錶,在misc_deregister中解除鏈結。主要的裝置結構就是miscdevice。定義如下:[plain]view plain
copy
struct miscdevice ;
這個結構體是misc裝置基本的結構體,在註冊misc裝置的時候必須要宣告並初始化乙個這樣的結構體,但其中一般只需填充name minor fops欄位就可以了。下面就是led驅動程式中初始化miscdevice的**:
[plain]view plain
copy
static struct miscdevice misc = ;
一般的時候在fops不用實現open方法,因為最初的方法misc_ops包含了open方法。其中minor如果填充misc_dynamic_minor,則是動態次裝置號,次裝置號由misc_register動態分配的。2. misc_init 函式
misc也是作為乙個模組被載入到核心的,只不過是靜態模組。這個函式是misc靜態模組載入時的初始化函式。[plain]view plain
copy
static int __init misc_init(void)
可以看出,這個初始化函式,最主要的功能就是註冊字元裝置 ,所用的註冊介面是2.4核心的register_chrdev。它註冊了主裝置號為misc_major,次裝置號為0-255的256個裝置。並且建立了乙個misc類。
3. misc_register()函式
misc_register()函式在misc.c中,最主要的功能是基於misc_class構造乙個裝置,將miscdevice結構掛載到misc_list列表上,並初始化與linux裝置模型相關的結構,它的引數是miscdevice結構體。[plain]view plain
copy
int misc_register(struct miscdevice * misc)
} //遍歷鍊錶如果發現次裝置號一樣的,返回錯誤
if (misc->minor == misc_dynamic_minor)
misc->minor = i;
} if (misc->minor < dynamic_minors)
misc_minors[misc->minor >> 3] |= 1 << (misc->minor & 7);
dev = mkdev(misc_major, misc->minor);
misc->this_device = device_create(misc_class, misc->parent, dev,
misc, "%s", misc->name);
//udev建立裝置節點使用,linux裝置模型相關
if (is_err(misc->this_device))
/*
* add it to the front, so that later devices can "override"
* earlier defaults
*/
list_add(&misc->list, &misc_list); //新增到misc_list之中
out:
mutex_unlock(&misc_mtx);
return err;
}
可以看出,這個函式首先遍歷misc_list鍊錶,查詢所用的次裝置號是否已經被註冊,防止衝突。如果是動態次裝置號則分配乙個,然後呼叫mkdev生成裝置號,從這裡可以看出所有的misc裝置共享乙個主裝置號misc_major,然後呼叫device_create,生成裝置檔案。最後加入到misc_list鍊錶中。
關於device_create,class_create 作用: class_create函式在misc.c中的模組初始化中被呼叫,現在一起說一下。這兩個函式看起來很陌生,沒有在ldd3中發現過,看源**的時候發現class_create會呼叫底層元件__class_regsiter()是說明它是註冊乙個類。而device_create是建立乙個裝置,他是建立裝置的便捷實現呼叫了device_register函式。他們都提供給linux裝置模型使用,從linux核心2.6的某個版本之後,devfs不復存在,udev成為devfs的替代。相比devfs,udev有很多優勢。[plain]view plain
copy
struct class *myclass = class_create(this_module, 「my_device_driver」);
class_device_create(myclass, null, mkdev(major_num, 0), null, 「my_device」);
這樣就建立了乙個類和裝置,模組被載入時,udev daemon就會自動在/dev下建立my_device裝置檔案節點。這樣就省去了自己建立裝置檔案的麻煩。這樣也有助於動態裝置的管理。4. 總結
雜項裝置作為字元裝置的封裝,為字元裝置提供的簡單的程式設計介面,如果編寫新的字元驅動,可以考慮使用雜項裝置介面,方便簡單,只需要初始化乙個miscdevice的結構,呼叫misc_register就可以了。系統最多有255個雜項裝置,因為雜項裝置模組自己占用了乙個次裝置號。可以發現,mini2440很多字元裝置都是以雜項裝置註冊到核心的,如mini2440_buttons,mini2440_adc,mini2440_pwm等。
原文見:
Linux misc裝置(一)misc驅動框架
copy from 文章目錄 linux misc裝置 一 misc驅動框架 一 misc簡介 二 misc驅動框架 三 misc原始碼剖析 四 misc裝置例項驅動編寫模板 一 misc簡介 linux的驅動設計是趨向於分層的,大多數裝置都有自己歸屬的型別,例如按鍵 觸控螢幕屬於輸入裝置,linu...
linux驅動模型分析總括
linux裝置驅動模型在2.4和2.6之間有非常大的變化。感覺最大的變化就是2.6中加入了一些面相物件的方法進行管理裝置驅動,其實在linux中早就使用了該方法。為了有乙個全面的了解,今天特意理清了一下思路,為下一步進入分析打下基礎。linux使用類似uinx方式管理裝置驅動,把裝置當作檔案來看待,...
資料分析是模型驅動還是資料驅動
在討論這個問題之前,需要理解清楚模型驅動與資料驅動兩個詞的含義。到底什麼是模型驅動?從認識世界的角度來講,我們理解的制度 禮儀 道德等等,基本上都可以理解為模型,通過這些模型,我們可以清楚地明白哪些是好的,哪些是壞的,哪些該做,哪些不該做。然而在資料側,在業務理解上,也可以類似地理解。我們需要梳理一...