diff options
Diffstat (limited to 'fs/sysfs')
| -rw-r--r-- | fs/sysfs/Kconfig | 1 | ||||
| -rw-r--r-- | fs/sysfs/dir.c | 44 | ||||
| -rw-r--r-- | fs/sysfs/file.c | 23 | ||||
| -rw-r--r-- | fs/sysfs/group.c | 7 | ||||
| -rw-r--r-- | fs/sysfs/mount.c | 2 | 
5 files changed, 43 insertions, 34 deletions
diff --git a/fs/sysfs/Kconfig b/fs/sysfs/Kconfig index 8c41feacbac5..b2756014508c 100644 --- a/fs/sysfs/Kconfig +++ b/fs/sysfs/Kconfig  | |||
| @@ -1,6 +1,7 @@ | |||
| 1 | config SYSFS | 1 | config SYSFS | 
| 2 | bool "sysfs file system support" if EXPERT | 2 | bool "sysfs file system support" if EXPERT | 
| 3 | default y | 3 | default y | 
| 4 | select KERNFS | ||
| 4 | help | 5 | help | 
| 5 | The sysfs filesystem is a virtual filesystem that the kernel uses to | 6 | The sysfs filesystem is a virtual filesystem that the kernel uses to | 
| 6 | export internal kernel objects, their attributes, and their | 7 | export internal kernel objects, their attributes, and their | 
diff --git a/fs/sysfs/dir.c b/fs/sysfs/dir.c index ee0d761c3179..0b45ff42f374 100644 --- a/fs/sysfs/dir.c +++ b/fs/sysfs/dir.c  | |||
| @@ -19,39 +19,18 @@ | |||
| 19 | 19 | ||
| 20 | DEFINE_SPINLOCK(sysfs_symlink_target_lock); | 20 | DEFINE_SPINLOCK(sysfs_symlink_target_lock); | 
| 21 | 21 | ||
| 22 | /** | ||
| 23 | * sysfs_pathname - return full path to sysfs dirent | ||
| 24 | * @kn: kernfs_node whose path we want | ||
| 25 | * @path: caller allocated buffer of size PATH_MAX | ||
| 26 | * | ||
| 27 | * Gives the name "/" to the sysfs_root entry; any path returned | ||
| 28 | * is relative to wherever sysfs is mounted. | ||
| 29 | */ | ||
| 30 | static char *sysfs_pathname(struct kernfs_node *kn, char *path) | ||
| 31 | { | ||
| 32 | if (kn->parent) { | ||
| 33 | sysfs_pathname(kn->parent, path); | ||
| 34 | strlcat(path, "/", PATH_MAX); | ||
| 35 | } | ||
| 36 | strlcat(path, kn->name, PATH_MAX); | ||
| 37 | return path; | ||
| 38 | } | ||
| 39 | |||
| 40 | void sysfs_warn_dup(struct kernfs_node *parent, const char *name) | 22 | void sysfs_warn_dup(struct kernfs_node *parent, const char *name) | 
| 41 | { | 23 | { | 
| 42 | char *path; | 24 | char *buf, *path = NULL; | 
| 43 | 25 | ||
| 44 | path = kzalloc(PATH_MAX, GFP_KERNEL); | 26 | buf = kzalloc(PATH_MAX, GFP_KERNEL); | 
| 45 | if (path) { | 27 | if (buf) | 
| 46 | sysfs_pathname(parent, path); | 28 | path = kernfs_path(parent, buf, PATH_MAX); | 
| 47 | strlcat(path, "/", PATH_MAX); | ||
| 48 | strlcat(path, name, PATH_MAX); | ||
| 49 | } | ||
| 50 | 29 | ||
| 51 | WARN(1, KERN_WARNING "sysfs: cannot create duplicate filename '%s'\n", | 30 | WARN(1, KERN_WARNING "sysfs: cannot create duplicate filename '%s/%s'\n", | 
| 52 | path ? path : name); | 31 | path, name); | 
| 53 | 32 | ||
| 54 | kfree(path); | 33 | kfree(buf); | 
| 55 | } | 34 | } | 
| 56 | 35 | ||
| 57 | /** | 36 | /** | 
| @@ -122,9 +101,13 @@ void sysfs_remove_dir(struct kobject *kobj) | |||
| 122 | int sysfs_rename_dir_ns(struct kobject *kobj, const char *new_name, | 101 | int sysfs_rename_dir_ns(struct kobject *kobj, const char *new_name, | 
| 123 | const void *new_ns) | 102 | const void *new_ns) | 
| 124 | { | 103 | { | 
| 125 | struct kernfs_node *parent = kobj->sd->parent; | 104 | struct kernfs_node *parent; | 
| 105 | int ret; | ||
| 126 | 106 | ||
| 127 | return kernfs_rename_ns(kobj->sd, parent, new_name, new_ns); | 107 | parent = kernfs_get_parent(kobj->sd); | 
| 108 | ret = kernfs_rename_ns(kobj->sd, parent, new_name, new_ns); | ||
| 109 | kernfs_put(parent); | ||
| 110 | return ret; | ||
| 128 | } | 111 | } | 
| 129 | 112 | ||
| 130 | int sysfs_move_dir_ns(struct kobject *kobj, struct kobject *new_parent_kobj, | 113 | int sysfs_move_dir_ns(struct kobject *kobj, struct kobject *new_parent_kobj, | 
| @@ -133,7 +116,6 @@ int sysfs_move_dir_ns(struct kobject *kobj, struct kobject *new_parent_kobj, | |||
| 133 | struct kernfs_node *kn = kobj->sd; | 116 | struct kernfs_node *kn = kobj->sd; | 
| 134 | struct kernfs_node *new_parent; | 117 | struct kernfs_node *new_parent; | 
| 135 | 118 | ||
| 136 | BUG_ON(!kn->parent); | ||
| 137 | new_parent = new_parent_kobj && new_parent_kobj->sd ? | 119 | new_parent = new_parent_kobj && new_parent_kobj->sd ? | 
| 138 | new_parent_kobj->sd : sysfs_root_kn; | 120 | new_parent_kobj->sd : sysfs_root_kn; | 
| 139 | 121 | ||
diff --git a/fs/sysfs/file.c b/fs/sysfs/file.c index 810cf6e613e5..1b8b91b67fdb 100644 --- a/fs/sysfs/file.c +++ b/fs/sysfs/file.c  | |||
| @@ -372,6 +372,29 @@ void sysfs_remove_file_ns(struct kobject *kobj, const struct attribute *attr, | |||
| 372 | } | 372 | } | 
| 373 | EXPORT_SYMBOL_GPL(sysfs_remove_file_ns); | 373 | EXPORT_SYMBOL_GPL(sysfs_remove_file_ns); | 
| 374 | 374 | ||
| 375 | /** | ||
| 376 | * sysfs_remove_file_self - remove an object attribute from its own method | ||
| 377 | * @kobj: object we're acting for | ||
| 378 | * @attr: attribute descriptor | ||
| 379 | * | ||
| 380 | * See kernfs_remove_self() for details. | ||
| 381 | */ | ||
| 382 | bool sysfs_remove_file_self(struct kobject *kobj, const struct attribute *attr) | ||
| 383 | { | ||
| 384 | struct kernfs_node *parent = kobj->sd; | ||
| 385 | struct kernfs_node *kn; | ||
| 386 | bool ret; | ||
| 387 | |||
| 388 | kn = kernfs_find_and_get(parent, attr->name); | ||
| 389 | if (WARN_ON_ONCE(!kn)) | ||
| 390 | return false; | ||
| 391 | |||
| 392 | ret = kernfs_remove_self(kn); | ||
| 393 | |||
| 394 | kernfs_put(kn); | ||
| 395 | return ret; | ||
| 396 | } | ||
| 397 | |||
| 375 | void sysfs_remove_files(struct kobject *kobj, const struct attribute **ptr) | 398 | void sysfs_remove_files(struct kobject *kobj, const struct attribute **ptr) | 
| 376 | { | 399 | { | 
| 377 | int i; | 400 | int i; | 
diff --git a/fs/sysfs/group.c b/fs/sysfs/group.c index 6b579387c67a..aa0406895b53 100644 --- a/fs/sysfs/group.c +++ b/fs/sysfs/group.c  | |||
| @@ -70,8 +70,11 @@ static int create_files(struct kernfs_node *parent, struct kobject *kobj, | |||
| 70 | if (grp->bin_attrs) { | 70 | if (grp->bin_attrs) { | 
| 71 | for (bin_attr = grp->bin_attrs; *bin_attr; bin_attr++) { | 71 | for (bin_attr = grp->bin_attrs; *bin_attr; bin_attr++) { | 
| 72 | if (update) | 72 | if (update) | 
| 73 | sysfs_remove_bin_file(kobj, *bin_attr); | 73 | kernfs_remove_by_name(parent, | 
| 74 | error = sysfs_create_bin_file(kobj, *bin_attr); | 74 | (*bin_attr)->attr.name); | 
| 75 | error = sysfs_add_file_mode_ns(parent, | ||
| 76 | &(*bin_attr)->attr, true, | ||
| 77 | (*bin_attr)->attr.mode, NULL); | ||
| 75 | if (error) | 78 | if (error) | 
| 76 | break; | 79 | break; | 
| 77 | } | 80 | } | 
diff --git a/fs/sysfs/mount.c b/fs/sysfs/mount.c index 3eaf5c6622eb..a66ad6196f59 100644 --- a/fs/sysfs/mount.c +++ b/fs/sysfs/mount.c  | |||
| @@ -63,7 +63,7 @@ int __init sysfs_init(void) | |||
| 63 | { | 63 | { | 
| 64 | int err; | 64 | int err; | 
| 65 | 65 | ||
| 66 | sysfs_root = kernfs_create_root(NULL, NULL); | 66 | sysfs_root = kernfs_create_root(NULL, 0, NULL); | 
| 67 | if (IS_ERR(sysfs_root)) | 67 | if (IS_ERR(sysfs_root)) | 
| 68 | return PTR_ERR(sysfs_root); | 68 | return PTR_ERR(sysfs_root); | 
| 69 | 69 | ||
