然後platform_driver_unregister,他的引數 test_driver的結構如下
static struct platform_driver test_driver = ,
};int platform_driver_register(struct platform_driver *drv)
從上面**可以看出,在platform_driver中設定了probe, remove, shutdown, suspend或resume函式的話
則drv->driver也會設定成platform對應的函式
int driver_register(struct device_driver *drv)
//新增驅動到匯流排上
ret = bus_add_driver(drv);
if (ret)
return ret;
ret = driver_add_groups(drv, drv->groups);
if (ret)
bus_remove_driver(drv);
return ret;
}int bus_add_driver(struct device_driver *drv)
//初始化klist_devices鍊錶
klist_init(&priv->klist_devices, null, null);
//互相關聯
priv->driver = drv;
drv->p = priv;
//設定私有資料的父容器,在這一步中,設定了kset為platform下的drivers_kset結構,也就是drivers呢個目錄
priv->kobj.kset = bus->p->drivers_kset;
//初始化kobj物件,設定容器操作集並建立相應的目錄,這裡由於沒有提供parent,所以會使用父容器中的kobj為父物件
error = kobject_init_and_add(&priv->kobj, &driver_ktype, null,
"%s", drv->name);
if (error)
goto out_unregister;
//檢測所屬匯流排的drivers_autoprobe屬性是否為真
//為真則進行與裝置的匹配,到這裡,就會與我們之前註冊的test_device連線上了,至於如何連線,進行了什麼操作,將在別的文章中詳細描述
if (drv->bus->p->drivers_autoprobe)
//掛載到所屬匯流排驅動鏈表上
klist_add_tail(&priv->knode_bus, &bus->p->klist_drivers);
module_add_driver(drv->owner, drv);
//建立uevent屬性檔案
error = driver_create_file(drv, &driver_attr_uevent);
if (error)
//建立裝置屬性檔案
error = driver_add_attrs(bus, drv);
if (error)
error = add_bind_files(drv);
if (error)
kobject_uevent(&priv->kobj, kobj_add);
return error;
out_unregister:
kobject_put(&priv->kobj);
out_put_bus:
bus_put(bus);
return error;
}到這裡test_driver的模型就建立好了,圖就是最上面的層次圖,我就不再貼了
到這裡乙個基本的框架就建立起來了~
下面,我開始對kobject kset和ktype做分析
先說說關係,ktype與kobject和kset這兩者之前的關係較少,讓我畫乙個圖,是這樣的
現在已經為read和write操作準備好了
馬上進入到read操作中
整個流程如上圖所示,如何進入到sysfs_read_file在上面open的操作中已經說明了
我們就從sysfs_read_file開始分析(該檔案在/fs/sysfs/file.c中)
sysfs_read_file(struct file *file, char __user *buf, size_t count, loff_t *ppos)
pr_debug("%s: count = %zd, ppos = %lld, buf = %s\n",__func__, count, *ppos, buffer->page);
retval = ******_read_from_buffer(buf, count, ppos, buffer->page,
buffer->count);
out:
mutex_unlock(&buffer->mutex);
return retval;
}static int fill_read_buffer(struct dentry * dentry, struct sysfs_buffer * buffer)
if (count >= 0) else
return ret;
}現在進入bus_attr_show中
static ssize_t bus_attr_show(struct kobject *kobj, struct attribute *attr,char *buf)
static ssize_t show_drivers_autoprobe(struct bus_type *bus, char *buf)
沒什麼好介紹了就是列印 buf + bus->p->drivers_autoprobe 從結果來看~ buf是空的
到這裡,終於把核心的資訊給列印出來了,千辛萬苦,層層呼叫,就是為了取得上層kobject結構,逆運算再取得kobject的上層結構
大家是否對kobject有所了解了呢?~
在對kobject進行介紹之前 還是先把write操作講完吧 哈哈~
write操作和read操作重要的步驟基本是一致的,只不過在最後的呼叫中
static ssize_t store_drivers_autoprobe(struct bus_type *bus,
const char *buf, size_t count)
不進行列印而對核心的引數進行了修改而已
好~ 現在讓我們來看看kobject吧
kobject的結構如下
struct kobject ;
kobject描述的是較具體的物件,乙個裝置,乙個驅動,乙個匯流排,一類裝置
在層次圖上可以看出,每個存在於層次圖中的裝置,驅動,匯流排,類別都有自己的kobject
kobject與kobject之間的層次由kobject中的parent指標決定
而kset指標則表明了kobject的容器
像platform_bus 和test_device的kset都是devices_kset
呢parent和kset有什麼不同呢
我認為是人工和預設的區別,看下面這張圖 ,藍框為kset,紅框為kobject
**blog
個人對kobject的一點研究 4
現在到bus register了 註冊的引數platform bus type如下所示 struct bus type platform bus type int bus register struct bus type bus 建立drivers目錄 priv drivers kset kset ...
個人對kobject的一點研究 5
在platform模型裝置的建立中,需要2個部分的註冊,驅動的註冊和裝置的註冊 platform device register test device platform driver register test driver 首先看platform device register 註冊引數為tes...
個人對專注力的一點看法
假設乙個人總共擁有10個點的注意力,那麼對於以下簡單的數學公式,可以幫助我們理解分散注意力對學習效率的影響。1.10 0 10 2.10 2 8 3.10 2 2 6 4.10 2 2 2 4 如果完成一項工作需要10個點的注意力,那麼對於第乙個人需要一天的時間,第二個人需要 1.25天,第三個人需...