添加sysfs介面 使用device_create_file/ device_create_group 添加static DEVICE_ATTR(fm1288, 0666, fm1288_show, fm1288_store); ...
為了在sysfs下生成可控節點,方便上層調用。
sysfs是一個基於RAM的文件系統,它和Kobject一起,可以將Kernel的數據結構導出到用戶空間,以文件目錄結構的形式,提供對這些數據結構(以及數據結構的屬性)的訪問支持。Linux設備模型(4)_sysfs
原型:
類似的還有DRIVER_ATTR
,BUS_ATTR
,CLASS_ATTR
。區別就是,DEVICE_ATTR
對應的文件在/sys/devices/目錄中對應的device下麵。而其他幾個分別在driver
,bus
,class
中對應的目錄下。(待確認)
我實際測試,用DEVICE_ATTR
增加的I2C設備,節點是在/sys/bus/i2c/devices/0-0060/fm1288/
下的。按照上面的說法,應該fm1288
節點應該是在/sys/device
下
用法:
static ssize_t fm1288_store(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) { struct i2c_client *i2c = container_of(dev, struct i2c_client, dev); unsigned int reg = 0, write = 0; __u16 val = 0; int ret; sscanf(buf,"%x %x %x", &write, ®, (unsigned int *)&val);//用sscanf讀取sysfs寫入的值 echo "1 2 3" > fm1288_mode fm2018_write(i2c, reg, val); fm2018_read(i2c, reg, &val); } fm1288_showstatic ssize_t fm1288_show(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) { //read mode ssprintf("%d", mode); } static DEVICE_ATTR(fm1288, S_IWUSR,//模式可以只讀0444,只寫0222,或者讀寫都行0666 fm1288_show, //NULL,不需要該函數可以寫NULL fm1288_store); //註意_show和_store的命名一般習慣都是來自name+ _show / _store static int fm2018_i2c_probe(struct i2c_client *i2c, const struct i2c_device_id *id) { struct device *dev = &i2c->dev; ret = device_create_file(&i2c->dev, &dev_attr_register); if (ret) { dev_err(&i2c->dev, "failed to create sysfs files\n"); return ret; } }
也可以寫多個屬性,這時,使用sysfs_create_group
註冊就很方便,代替device_create_file
static DEVICE_ATTR(xtilt, S_IRUGO | S_IWUGO, show_tabletXtilt, store_tabletXtilt); static DEVICE_ATTR(ytilt, S_IRUGO | S_IWUGO, show_tabletYtilt, store_tabletYtilt); static struct attribute *aiptek_attributes[] = { &dev_attr_xtilt.attr,//名字 dev_attr_name.attr &dev_attr_ytilt.attr, NULL }; static struct attribute_group aiptek_attribute_group = { .attrs = aiptek_attributes, }; aiptek_probe(struct usb_interface *intf, const struct usb_device_id *id) { int err = -ENOMEM; err = sysfs_create_group(&intf->dev.kobj, &aiptek_attribute_group); if (err) { dev_warn(&intf->dev, "cannot create sysfs group err: %d\n", err); goto fail3; } fail3: return -1; }