android深度探索 HAL及驱动开发 第八章
第八章 讀書筆記
本章主要講蜂鳴器的驅動,蜂鳴器是S3cC6410開發板上帶的一個硬件設備,本節將介紹蜂鳴器的實現原理,并實現一個完整的蜂鳴器驅動。本節講介紹把linux驅動分成多個文件的方式。這些文件中的數據結構、函數的代碼也可以被多個不同的驅動使用,所以這也是代碼重用 的重要方法。Linux代碼的重用?重用=靜態重用(將要重用的代碼放到其他的文件的頭文件中聲明)+動態重用(使用另外一個Linux驅動中的資源,例如函數、變量、宏等)
1、編譯是由多個文件組成的Linux驅動(靜態重用)
對于復雜的Linux驅動,需要使用多個源代碼文件存放不同的功能代碼,這樣做有利于代碼分類和管理,那么就不得不編譯多個源代碼文件,最終生成.ko文件或編譯進Linux內核
下面,就介紹將3個.c文件分別編譯為3個.o文件,并將這3個.o文件鏈接(link)成一個.ko文件——靜態重用
假設C語言源代碼文件有main.c、fun.c、product.c、product.h,其中main.c是Linux驅動的主程序,在fun.c和product.c、product.h中定義和實現了在main.c中使用的函數,在main.c中通過extern關鍵字使用fun.c中的函數,通過包含product.h文件使用product.c文件中的函數
最關鍵一步就是編寫Makefile文件
#Makefile
obj-m := multi_file_driver(文件所在目錄).o
multi_file_driver-y := main.o fun.o product.o
總之,c或c++ 語言中編譯多個源代碼文件時,如果a.c使用了b.c文件中的函數,需要在a.c文件中使用extern預先定義b.c中的函數,extern的作用是告訴編譯器該函數的函數名、參數個數、參數類型、返回值類型,等到將a.o和b.o鏈接成可執行文件或程序庫時,編譯器再到b.o中尋找函數的具體實現。除此之外,還可以使用b.h文件定義b.c中的函數,然后在a.c中包含b.h文件。
2、Linux驅動模塊的依賴(動態重用)
在一個驅動模塊里使用另一個驅動模塊里的被導出的符號(常量、變量、函數等)
接下來學習了強行卸載linux驅動,只能卸載由于卸載異常情況而導致的linux驅動模塊無法卸載的情況。情況1:初始化函數崩潰 2:卸載函數被阻塞
?
蜂鳴器驅動是一個重點,通過相應的寄存器來控制蜂鳴器的打開和關閉,并且在實驗蜂鳴器驅動時,將打開和關閉蜂蜜器的函數放到另外的C源代碼文件中。PWM驅動由三個文件組成:PWM.C、PWM—fun.h、pwm-fun.c、其中pwm.c是驅動主程序。
本章主要講了Linux代碼的重用與強行卸載Linux驅動。
強行卸載Linux驅動
情況1:初始化函數崩潰
由于Linux驅動模塊的初始化函數進行了某些操作而崩潰,從而導致初始化函數無法正常返回,這種情況變現是當前Linux驅動模塊沒用被任何其他的Linux驅動模塊使用,但卻顯示已經被應用了一次
這種情況關鍵是引用計數器的值和引用者不一致。只需要將當前的Linux驅動模塊的引用計數器清零即可,修改計數器可以使用下面兩個函數
//是module指向的Linux驅動模塊的引用計數器加1,成功返回1,失敗返回0
static inline int try_module_get(struct module *module);
//是module指向的Linux驅動模塊的引用計數器減1
extern void module_put(struct module *module);
情況2:卸載函數被阻塞
在使用rmmod命令卸載Linux驅動時,系統會調用卸載函數,只有卸載函數成功返回時,Linux驅動才會被卸載,如果卸載函數被阻塞,rmmod命令也會被阻塞,也就是說永遠不會執行到卸載Linux驅動模塊的代碼,這種情況的表現是一執行rmmod命令就會停在那不動了,永遠也不會返回到系統的操作提示符
這種情況的問題根源就是卸載函數,只要將原來的卸載函數替換成一個空的卸載函數即可
總之,兩者情況都要解決一個不可回避的問題,就是要獲取表示要卸載的Linux驅動模塊的module結構體指針。
轉載于:https://www.cnblogs.com/haihaizhazha/p/5626985.html
總結
以上是生活随笔為你收集整理的android深度探索 HAL及驱动开发 第八章的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 蓝牙耳机性能测试软件,操作方便吗 蓝牙耳
- 下一篇: 生成n对括号的合法全排列