Commit ac9b1e5b authored by Dmitry Torokhov's avatar Dmitry Torokhov Committed by Matthew Garrett

asus-laptop: use attribute group to manage attributes

Instead of registering (and removing) every attribute individually
switch to using sysfs attribute group. This makes sure that we
properly unwind and do not try to remove non-existent attributes which
may not be safe to do in the future.
Signed-off-by: default avatarDmitry Torokhov <dtor@mail.ru>
Signed-off-by: default avatarMatthew Garrett <mjg@redhat.com>
parent 209009b2
...@@ -1200,82 +1200,70 @@ static void asus_acpi_notify(struct acpi_device *device, u32 event) ...@@ -1200,82 +1200,70 @@ static void asus_acpi_notify(struct acpi_device *device, u32 event)
static DEVICE_ATTR(infos, S_IRUGO, show_infos, NULL); static DEVICE_ATTR(infos, S_IRUGO, show_infos, NULL);
static DEVICE_ATTR(wlan, S_IRUGO | S_IWUSR, show_wlan, store_wlan); static DEVICE_ATTR(wlan, S_IRUGO | S_IWUSR, show_wlan, store_wlan);
static DEVICE_ATTR(bluetooth, S_IRUGO | S_IWUSR, show_bluetooth, static DEVICE_ATTR(bluetooth, S_IRUGO | S_IWUSR,
store_bluetooth); show_bluetooth, store_bluetooth);
static DEVICE_ATTR(display, S_IRUGO | S_IWUSR, show_disp, store_disp); static DEVICE_ATTR(display, S_IRUGO | S_IWUSR, show_disp, store_disp);
static DEVICE_ATTR(ledd, S_IRUGO | S_IWUSR, show_ledd, store_ledd); static DEVICE_ATTR(ledd, S_IRUGO | S_IWUSR, show_ledd, store_ledd);
static DEVICE_ATTR(ls_level, S_IRUGO | S_IWUSR, show_lslvl, store_lslvl); static DEVICE_ATTR(ls_level, S_IRUGO | S_IWUSR, show_lslvl, store_lslvl);
static DEVICE_ATTR(ls_switch, S_IRUGO | S_IWUSR, show_lssw, store_lssw); static DEVICE_ATTR(ls_switch, S_IRUGO | S_IWUSR, show_lssw, store_lssw);
static DEVICE_ATTR(gps, S_IRUGO | S_IWUSR, show_gps, store_gps); static DEVICE_ATTR(gps, S_IRUGO | S_IWUSR, show_gps, store_gps);
static void asus_sysfs_exit(struct asus_laptop *asus) static struct attribute *asus_attributes[] = {
{ &dev_attr_infos.attr,
struct platform_device *device = asus->platform_device; &dev_attr_wlan.attr,
&dev_attr_bluetooth.attr,
device_remove_file(&device->dev, &dev_attr_infos); &dev_attr_display.attr,
device_remove_file(&device->dev, &dev_attr_wlan); &dev_attr_ledd.attr,
device_remove_file(&device->dev, &dev_attr_bluetooth); &dev_attr_ls_level.attr,
device_remove_file(&device->dev, &dev_attr_display); &dev_attr_ls_switch.attr,
device_remove_file(&device->dev, &dev_attr_ledd); &dev_attr_gps.attr,
device_remove_file(&device->dev, &dev_attr_ls_switch); NULL
device_remove_file(&device->dev, &dev_attr_ls_level); };
device_remove_file(&device->dev, &dev_attr_gps);
}
static int asus_sysfs_init(struct asus_laptop *asus) static mode_t asus_sysfs_is_visible(struct kobject *kobj,
struct attribute *attr,
int idx)
{ {
struct platform_device *device = asus->platform_device; struct device *dev = container_of(kobj, struct device, kobj);
int err; struct platform_device *pdev = to_platform_device(dev);
struct asus_laptop *asus = platform_get_drvdata(pdev);
acpi_handle handle = asus->handle;
bool supported;
err = device_create_file(&device->dev, &dev_attr_infos); if (attr == &dev_attr_wlan.attr) {
if (err) supported = !acpi_check_handle(handle, METHOD_WLAN, NULL);
return err;
if (!acpi_check_handle(asus->handle, METHOD_WLAN, NULL)) { } else if (attr == &dev_attr_bluetooth.attr) {
err = device_create_file(&device->dev, &dev_attr_wlan); supported = !acpi_check_handle(handle, METHOD_BLUETOOTH, NULL);
if (err)
return err;
}
if (!acpi_check_handle(asus->handle, METHOD_BLUETOOTH, NULL)) {
err = device_create_file(&device->dev, &dev_attr_bluetooth);
if (err)
return err;
}
if (!acpi_check_handle(asus->handle, METHOD_SWITCH_DISPLAY, NULL)) { } else if (attr == &dev_attr_display.attr) {
err = device_create_file(&device->dev, &dev_attr_display); supported = !acpi_check_handle(handle, METHOD_SWITCH_DISPLAY, NULL);
if (err)
return err;
}
if (!acpi_check_handle(asus->handle, METHOD_LEDD, NULL)) { } else if (attr == &dev_attr_ledd.attr) {
err = device_create_file(&device->dev, &dev_attr_ledd); supported = !acpi_check_handle(handle, METHOD_LEDD, NULL);
if (err)
return err;
}
if (!acpi_check_handle(asus->handle, METHOD_ALS_CONTROL, NULL) && } else if (attr == &dev_attr_ls_switch.attr ||
!acpi_check_handle(asus->handle, METHOD_ALS_LEVEL, NULL)) { attr == &dev_attr_ls_level.attr) {
err = device_create_file(&device->dev, &dev_attr_ls_switch); supported = !acpi_check_handle(handle, METHOD_ALS_CONTROL, NULL) &&
if (err) !acpi_check_handle(handle, METHOD_ALS_LEVEL, NULL);
return err;
err = device_create_file(&device->dev, &dev_attr_ls_level);
if (err)
return err;
}
if (!acpi_check_handle(asus->handle, METHOD_GPS_ON, NULL) && } else if (attr == &dev_attr_gps.attr) {
!acpi_check_handle(asus->handle, METHOD_GPS_OFF, NULL) && supported = !acpi_check_handle(handle, METHOD_GPS_ON, NULL) &&
!acpi_check_handle(asus->handle, METHOD_GPS_STATUS, NULL)) { !acpi_check_handle(handle, METHOD_GPS_OFF, NULL) &&
err = device_create_file(&device->dev, &dev_attr_gps); !acpi_check_handle(handle, METHOD_GPS_STATUS, NULL);
if (err) } else {
return err; supported = true;
} }
return err; return supported ? attr->mode : 0;
} }
static const struct attribute_group asus_attr_group = {
.is_visible = asus_sysfs_is_visible,
.attrs = asus_attributes,
};
static int asus_platform_init(struct asus_laptop *asus) static int asus_platform_init(struct asus_laptop *asus)
{ {
int result; int result;
...@@ -1289,13 +1277,14 @@ static int asus_platform_init(struct asus_laptop *asus) ...@@ -1289,13 +1277,14 @@ static int asus_platform_init(struct asus_laptop *asus)
if (result) if (result)
goto fail_platform_device; goto fail_platform_device;
result = asus_sysfs_init(asus); result = sysfs_create_group(&asus->platform_device->dev.kobj,
&asus_attr_group);
if (result) if (result)
goto fail_sysfs; goto fail_sysfs;
return 0; return 0;
fail_sysfs: fail_sysfs:
asus_sysfs_exit(asus);
platform_device_del(asus->platform_device); platform_device_del(asus->platform_device);
fail_platform_device: fail_platform_device:
platform_device_put(asus->platform_device); platform_device_put(asus->platform_device);
...@@ -1304,7 +1293,7 @@ static int asus_platform_init(struct asus_laptop *asus) ...@@ -1304,7 +1293,7 @@ static int asus_platform_init(struct asus_laptop *asus)
static void asus_platform_exit(struct asus_laptop *asus) static void asus_platform_exit(struct asus_laptop *asus)
{ {
asus_sysfs_exit(asus); sysfs_remove_group(&asus->platform_device->dev.kobj, &asus_attr_group);
platform_device_unregister(asus->platform_device); platform_device_unregister(asus->platform_device);
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment