Platform: msm8x60
Kernel: 2.6
要想了解裝置模型,首先需要知道它由哪些基本資料構成。包含有kobject、kset、device、device_driver、 bus、class、subsystem。下面分别介紹。
kobject
主要函數:
void kobject_init(struct kobject *kobj, struct kobj_type *ktype);
int kobject_add(struct kobject *kobj, struct kobject *parent,
const char *fmt, …)
void kobject_put(struct kobject *kobj)
struct kobject *kobject_get(struct kobject *kobj)
它是裝置模型中的基本結構,通常被嵌入到其他的結構中。每種kobject都關聯到ktype,由kobj_type表示,如下:
Ktype是為了描述kobject所具有的普遍特性。是以不需要每次kobject都分别定義,而是将這些特性在ktype中一次定義。
kset
主要函數:
void kset_init(struct kset *k)
static struct kset *kset_create(const char *name,
const struct kset_uevent_ops *uevent_ops,
struct kobject *parent_kobj)
int kset_register(struct kset *k)
static inline struct kset *kset_get(struct kset *k)
static inline void kset_put(struct kset *k)
一個kset是相同類型的kobject的一個集合。類型是kobj_type類型來描述的。Kset一定會在sysfs裡顯示出來,而kobject不一定。可認為kset是kobject的容器,在kset内部,包含了自己的kobject。上面一些對kset的處理函數其實都是調用kobject的相關函數來實作的。Kset也可以包含在另一個kset裡,和kobject一樣。下圖是kset和kobject的關系。
subsystem
struct subsystem{
struct kset kset;
struct rw_semaphore rwsem;
};
Subsystem是一個或者多個kset的集,它隻指向一個kset,或許有人有疑惑那如何找kset,但是多個ksets可以通過其subsys指針指向一個subsystem。
所有的kset都必須屬于subsystem,因為他們使用該讀寫信号量去通路同步通路他們的内部資料。
device
裝置模型中最重要的結構。對于基于總線的裝置,會在device基礎上衍生出很多類,如platform_device。
注冊過後的裝置在/sys/devices下可以看到。下面是與裝置屬性相關的内容。
device_driver
相關函數:
int driver_register(struct device_driver *drv)
int __must_check driver_attach(struct device_driver *drv);
它也是個比較重要的結構體。一般是嵌入到其他結構體來進行注冊的。如我們所使用的platform_driver,如下:
注冊的時候通過bus來和devices進行比對。一個driver可以對應多個devices。
bus
相關函數:
int bus_register(struct bus_type *bus)
裝置模型裡,所有的devices都通過bus相連,模型裡還有虛拟的bus。如platform總線。總線之間可以互相插入。每個總線都有自己的子系統,另外包括兩個kset,分别是devcie和drvier,是以會在/sys/bus/platform下看到device和driver目錄。而klist_devices和klist_drivers是總線支援的裝置及驅動連結清單,用于周遊總線上的驅動和裝置。
class
相關函數:
int __init classes_init(void)
類是一個裝置的高層視圖,它抽象出了底層的實作細節。比如驅動程式看到的是SCSI磁盤和ATA磁盤,但是在類的層次上,它們都是磁盤而已。類允許使用者空間使用裝置所能提供的功能,而不關心裝置是如何連接配接的,以及它們是如何工作的。