Linux字元裝置驅動中container_of宏的作用
首先看看這個宏的原型:
container_of(ptr,type,member)
功能:根據一個結構體變量中的一個成員變量的指針來擷取指向整個結構體變量的指針。
參數:
ptr:已知的結構體成員的首位址(指針);
type:要擷取的結構體變量的類型
member:要擷取的結構體變量中成員的名字,而不是類型
傳回值:要擷取的結構體變量的首位址
驅動中常用的用法:
struct hello_device
{
struct cdev cdev;
char data [128];
}hello_device[2];
hello_device[0] //對應 裝置0
hello_device[1] //對應 裝置1
int hello_open(struct inode * inode,struct file * file)
{
struct hello_device * dev = container_of(inode->i_cdev,struct hello_device,cdev);
file->private_data = dev;
}
ssize_t hello_read(struct file*,char __user *buff,size_t count,loff_t*)
{
struct hello_device * dev = file->private_data;
//dev指向打開的裝置結構體
copy_to_user(buff,dev->data,count);
}
當我們成功insmod一個裝置驅動的時候,我們會通過mknod建立一個裝置節點和一個具體的裝置(驅動)關聯,這個節點就對應這個inode結構體的一個執行個體,這個執行個體有一個struct cdev類型的字段i_cdev,它會指向hello_device中的cdev結構體(初始化cdev時候完成的)。最終擷取到hello_device結構體的首位址,其cdev已經被執行個體化,對應一個具體的裝置。
是以我們可以根據dev->cdev.dev就可以獲得目前這個裝置的裝置号。然後包含具體裝置資訊的dev結構體就可以通過file中的private_data成員在open,read,write,ioctl之間傳遞。