1. DEVICE_ATTR 创建设备节点,可以write/read信息,操作gpio等,很实用.
参考官方文档:documentation/driver-model/Device.txt
先看看DEVICE_ATTR的原型:
DEVICE_ATTR(_name, _mode, _show, _store)
_name:名称,也就是将在sys fs中生成的文件名称。
_mode:上述文件的访问权限,与普通文件相同,UGO的格式。
_show:显示函数,cat该文件时,此函数被调用。
_store:写函数,echo内容到该文件时,此函数被调用。
2. DEVICE_ATTR函数原型(include/linux/device.h)
#define DEVICE_ATTR(_name, _mode, _show, _store) \
struct device_attribute dev_attr_##_name = __ATTR(_name, _mode, _show, _store)
/* interface for exporting device attributes */
struct device_attribute {
struct attribute attr;
ssize_t (*show)(struct device *dev, struct device_attribute *attr,
char *buf);
ssize_t (*store)(struct device *dev, struct device_attribute *attr,
const char *buf, size_t count);
};
3 . 主要修改show,store两个函数
static DEVICE_ATTR(camera1, S_IRUGO | S_IWUSR, my_show_camera1, my_store_camera1);
注意: my_store_camera1:
return count,一般count大小就是一个PAGE_SIZE。 如果这个函数 return 0,这个store函数将被无限循环调用导致系统crash
static ssize_t my_store_camera1(struct device* cd, struct device_attribute *attr,
const char* buf, size_t len){
return len;
}
static ssize_t my_show_camera1(struct device* cd,struct device_attribute *attr, char* buf){
ssize_t ret = 0;
if (tc_camera_id1 == 1){
sprintf(buf, "imx577\n");
} else{
sprintf(buf, "find not camera\n");
}
ret = strlen(buf) + 1;
return ret;
}
static DEVICE_ATTR(camera1, S_IRUGO | S_IWUSR, my_show_camera1, my_store_camera1);
4.device_create_file
static int my_create_sysfs(struct platform_device *client){
struct device *dev = &(client->dev);
int err = 0;
if ((err = device_create_file(dev, &dev_attr_camera1))){
goto err_out;
}
return 0;
err_out:
return err;
}
5. 在对应的probe里面加入device_create_file的调用即可
static int cam_req_mgr_probe(struct platform_device *pdev){
....
my_create_sysfs(pdev);
....
}