Linux設備驅動的軟件架構思想與設備驅動的基礎內容總結
Linux是一個兼容性特別強的一個系統,而兼容性的實現與驅動強大的適應性密不可分。而這個具體的實現是離不開 總線bus和類class的管理方式。
Linux使用bus統一的管理一系列相似的驅動和設備,而又將具有同一類設備特色的設備利用同一個類class進行管理。 設備驅動模型中,每一種總線的註冊函數中都將關於使用此總線進行管理的設備的公共部分進行了封裝,而留給了驅動開發者進行一些設備獨有的信息的填充接口。
通過總線的管理,驅動只用管驅動,設備只管設備,總線則負責匹配驅動和設備,而驅動則以標準的途徑拿取設備的板載信息,這樣驅動就可以匹配多個不同的設備了。
關於設備和驅動的匹配,以paltform平臺總線爲例簡單的分析如下:
在驅動的註冊函數 platform_driver_register(struct platform_driver *drv)的實現中,驅動框架爲我完成了一部分通用的程序操作。 將與驅動相關的一些信息進行了填充,對回調函數進行了賦值,最後註冊了驅動:
Ret=platform_driver_register(&sunxi_keyboard_driver)
#define platform_driver_register(drv) __platform_driver_register(drv, THIS_MODULE)
int __platform_driver_register(struct platform_driver *drv,struct module *owner)
{
drv->driver.owner = owner;
drv->driver.bus = &platform_bus_type;
drv->driver.probe = platform_drv_probe;
drv->driver.remove = platform_drv_remove;
drv->driver.shutdown = platform_drv_shutdown;
return driver_register(&drv->driver);
}
Device_driver 和device分別表示驅動和設備,兩者只有依附於同一個總線才能一起工作,因此都會包含一個 struct bus_type 結構體類型變量。在驅動和設備分別註冊時他們互相併不知道對方的存在,各自涌向內核,然後尋找自己的另一半,最終通過 match 回調函數進行匹配捆綁,匹配的方式有多種,包括:設備樹分風格匹配、ACPI風格匹配、匹配ID表、name匹配。
struct bus_type platform_bus_type = {
.name = "platform",
.dev_groups = platform_dev_groups,
.match = platform_match,
.uevent = platform_uevent,
.pm = &platform_dev_pm_ops,
};
一旦匹配成功 sunxi_keyboard_driver 中的probe 回調函數就會被執行。
以platform平臺設備總線爲例引入設備總線的好處:
1.隔離BSP和驅動,在BSP中定義platform設備信息、設備使用到的資源、以及設備的配合信息,而在驅動中只需要使用固定的接口函數進行資源和數據的獲取,做到了驅動和設備的分離,使得驅動具有更好的擴展性。
2.適配更靈活,同一個驅動,可以通過改變不同的 platform_device 結構體變量,實現多份硬件的適配。