Subject: [PATCH] [acpi driver model] Add interface for adding per-device proc files - Create acpi_device_proc_{add,remove} that create a per-device directory (in the driver's directory) and use the driver's proc structure to create lots of files for the device. Signed-off-by: Patrick Mochel --- drivers/acpi/drivers/core/proc.c | 88 ++++++++++++++++++++++++++++++++++++++ 1 files changed, 88 insertions(+), 0 deletions(-) applies-to: 4b4d3efefda6514ebcd27e81b2e9588e22ffdc1b b395362e3a1c3fa082f64161d9a552c2c84cddad diff --git a/drivers/acpi/drivers/core/proc.c b/drivers/acpi/drivers/core/proc.c index ad6c09a..65bfc12 100644 --- a/drivers/acpi/drivers/core/proc.c +++ b/drivers/acpi/drivers/core/proc.c @@ -52,3 +52,91 @@ void acpi_driver_proc_remove(struct acpi adp->p_parent = NULL; remove_proc_entry(adp->p_name, acpi_root_dir); } + + + +/** + * acpi_device_proc_add - Create per-device directory and files + * @ad: The ACPI device we're dealing with. + * + * This creates a per-device directory within the device's + * driver's directory. The name of the directory is obtained + * from acpi_dev_bid(), which is compatible with the old-school + * way of doing things. + * + * The directory is stored in @ad->proc_dir, which is + * (unfortunately) the only way we can retain it (as we wait + * patiently for this proc junk to go away..). + */ + +int acpi_device_proc_add(struct acpi_dev * ad) +{ + struct acpi_device_driver * drv = to_acpi_driver(ad->dev.driver); + struct acpi_driver_proc * adp = drv->d_proc; + struct proc_dir_entry * dir; + struct proc_dir_entry * file; + char * dir_name; + int i; + + if (!adp) + return 0; + + dir_name = acpi_dev_bid(ad); + dir = proc_mkdir(dir_name, adp->p_parent); + if (!dir) + return -ENODEV; + dir->owner = adp->p_owner; + + for (i = 0; i < adp->p_num_files; i++) { + file = create_proc_entry(adp->p_files[i].name, + adp->p_files[i].mode, + dir); + if (file) { + file->proc_fops = &adp->p_files[i].fops; + file->data = ad; + file->owner = adp->p_owner; + } else + goto Fail; + } + + ad->proc_dir = dir; + return 0; + +Fail: + /* + * Unwind and remove all the entries + */ + while (--i > 0) + remove_proc_entry(adp->p_files[i].name, dir); + remove_proc_entry(dir_name, adp->p_parent); + return -ENODEV; +} + + +/** + * acpi_device_proc_remove - Remove per-device directory and files. + * @ad: The ACPI device we're dealing with. + * + * This removes all of the per-devices files when a device is + * removed from a driver. The directory pointer is stored in + * @ad->proc_dir, and the list of files is in the per-driver + * proc structure. When done, we remove the per-device directory. + */ + +void acpi_device_proc_remove(struct acpi_dev * ad) +{ + struct acpi_device_driver * drv = to_acpi_driver(ad->dev.driver); + struct acpi_driver_proc * adp = drv->d_proc; + struct proc_dir_entry * dir = ad->proc_dir; + + if (adp) { + char * dir_name = acpi_dev_bid(ad); + int i; + + ad->proc_dir = NULL; + for (i = 0; i < adp->p_num_files; i++) + remove_proc_entry(adp->p_files[i].name, dir); + remove_proc_entry(dir_name, adp->p_parent); + } +} + --- 0.99.9.GIT