diff options
Diffstat (limited to 'fs/sysfs/group.c')
-rw-r--r-- | fs/sysfs/group.c | 92 |
1 files changed, 77 insertions, 15 deletions
diff --git a/fs/sysfs/group.c b/fs/sysfs/group.c index 09a1a25cd145..5f92cd2f61c1 100644 --- a/fs/sysfs/group.c +++ b/fs/sysfs/group.c | |||
@@ -3,8 +3,10 @@ | |||
3 | * | 3 | * |
4 | * Copyright (c) 2003 Patrick Mochel | 4 | * Copyright (c) 2003 Patrick Mochel |
5 | * Copyright (c) 2003 Open Source Development Lab | 5 | * Copyright (c) 2003 Open Source Development Lab |
6 | * Copyright (c) 2013 Greg Kroah-Hartman | ||
7 | * Copyright (c) 2013 The Linux Foundation | ||
6 | * | 8 | * |
7 | * This file is released undert the GPL v2. | 9 | * This file is released undert the GPL v2. |
8 | * | 10 | * |
9 | */ | 11 | */ |
10 | 12 | ||
@@ -19,8 +21,8 @@ | |||
19 | static void remove_files(struct sysfs_dirent *dir_sd, struct kobject *kobj, | 21 | static void remove_files(struct sysfs_dirent *dir_sd, struct kobject *kobj, |
20 | const struct attribute_group *grp) | 22 | const struct attribute_group *grp) |
21 | { | 23 | { |
22 | struct attribute *const* attr; | 24 | struct attribute *const *attr; |
23 | struct bin_attribute *const* bin_attr; | 25 | struct bin_attribute *const *bin_attr; |
24 | 26 | ||
25 | if (grp->attrs) | 27 | if (grp->attrs) |
26 | for (attr = grp->attrs; *attr; attr++) | 28 | for (attr = grp->attrs; *attr; attr++) |
@@ -33,8 +35,8 @@ static void remove_files(struct sysfs_dirent *dir_sd, struct kobject *kobj, | |||
33 | static int create_files(struct sysfs_dirent *dir_sd, struct kobject *kobj, | 35 | static int create_files(struct sysfs_dirent *dir_sd, struct kobject *kobj, |
34 | const struct attribute_group *grp, int update) | 36 | const struct attribute_group *grp, int update) |
35 | { | 37 | { |
36 | struct attribute *const* attr; | 38 | struct attribute *const *attr; |
37 | struct bin_attribute *const* bin_attr; | 39 | struct bin_attribute *const *bin_attr; |
38 | int error = 0, i; | 40 | int error = 0, i; |
39 | 41 | ||
40 | if (grp->attrs) { | 42 | if (grp->attrs) { |
@@ -129,6 +131,41 @@ int sysfs_create_group(struct kobject *kobj, | |||
129 | { | 131 | { |
130 | return internal_create_group(kobj, 0, grp); | 132 | return internal_create_group(kobj, 0, grp); |
131 | } | 133 | } |
134 | EXPORT_SYMBOL_GPL(sysfs_create_group); | ||
135 | |||
136 | /** | ||
137 | * sysfs_create_groups - given a directory kobject, create a bunch of attribute groups | ||
138 | * @kobj: The kobject to create the group on | ||
139 | * @groups: The attribute groups to create, NULL terminated | ||
140 | * | ||
141 | * This function creates a bunch of attribute groups. If an error occurs when | ||
142 | * creating a group, all previously created groups will be removed, unwinding | ||
143 | * everything back to the original state when this function was called. | ||
144 | * It will explicitly warn and error if any of the attribute files being | ||
145 | * created already exist. | ||
146 | * | ||
147 | * Returns 0 on success or error code from sysfs_create_group on error. | ||
148 | */ | ||
149 | int sysfs_create_groups(struct kobject *kobj, | ||
150 | const struct attribute_group **groups) | ||
151 | { | ||
152 | int error = 0; | ||
153 | int i; | ||
154 | |||
155 | if (!groups) | ||
156 | return 0; | ||
157 | |||
158 | for (i = 0; groups[i]; i++) { | ||
159 | error = sysfs_create_group(kobj, groups[i]); | ||
160 | if (error) { | ||
161 | while (--i >= 0) | ||
162 | sysfs_remove_group(kobj, groups[i]); | ||
163 | break; | ||
164 | } | ||
165 | } | ||
166 | return error; | ||
167 | } | ||
168 | EXPORT_SYMBOL_GPL(sysfs_create_groups); | ||
132 | 169 | ||
133 | /** | 170 | /** |
134 | * sysfs_update_group - given a directory kobject, update an attribute group | 171 | * sysfs_update_group - given a directory kobject, update an attribute group |
@@ -152,11 +189,18 @@ int sysfs_update_group(struct kobject *kobj, | |||
152 | { | 189 | { |
153 | return internal_create_group(kobj, 1, grp); | 190 | return internal_create_group(kobj, 1, grp); |
154 | } | 191 | } |
192 | EXPORT_SYMBOL_GPL(sysfs_update_group); | ||
155 | 193 | ||
156 | 194 | /** | |
157 | 195 | * sysfs_remove_group: remove a group from a kobject | |
158 | void sysfs_remove_group(struct kobject * kobj, | 196 | * @kobj: kobject to remove the group from |
159 | const struct attribute_group * grp) | 197 | * @grp: group to remove |
198 | * | ||
199 | * This function removes a group of attributes from a kobject. The attributes | ||
200 | * previously have to have been created for this group, otherwise it will fail. | ||
201 | */ | ||
202 | void sysfs_remove_group(struct kobject *kobj, | ||
203 | const struct attribute_group *grp) | ||
160 | { | 204 | { |
161 | struct sysfs_dirent *dir_sd = kobj->sd; | 205 | struct sysfs_dirent *dir_sd = kobj->sd; |
162 | struct sysfs_dirent *sd; | 206 | struct sysfs_dirent *sd; |
@@ -164,8 +208,9 @@ void sysfs_remove_group(struct kobject * kobj, | |||
164 | if (grp->name) { | 208 | if (grp->name) { |
165 | sd = sysfs_get_dirent(dir_sd, NULL, grp->name); | 209 | sd = sysfs_get_dirent(dir_sd, NULL, grp->name); |
166 | if (!sd) { | 210 | if (!sd) { |
167 | WARN(!sd, KERN_WARNING "sysfs group %p not found for " | 211 | WARN(!sd, KERN_WARNING |
168 | "kobject '%s'\n", grp, kobject_name(kobj)); | 212 | "sysfs group %p not found for kobject '%s'\n", |
213 | grp, kobject_name(kobj)); | ||
169 | return; | 214 | return; |
170 | } | 215 | } |
171 | } else | 216 | } else |
@@ -177,6 +222,27 @@ void sysfs_remove_group(struct kobject * kobj, | |||
177 | 222 | ||
178 | sysfs_put(sd); | 223 | sysfs_put(sd); |
179 | } | 224 | } |
225 | EXPORT_SYMBOL_GPL(sysfs_remove_group); | ||
226 | |||
227 | /** | ||
228 | * sysfs_remove_groups - remove a list of groups | ||
229 | * | ||
230 | * @kobj: The kobject for the groups to be removed from | ||
231 | * @groups: NULL terminated list of groups to be removed | ||
232 | * | ||
233 | * If groups is not NULL, remove the specified groups from the kobject. | ||
234 | */ | ||
235 | void sysfs_remove_groups(struct kobject *kobj, | ||
236 | const struct attribute_group **groups) | ||
237 | { | ||
238 | int i; | ||
239 | |||
240 | if (!groups) | ||
241 | return; | ||
242 | for (i = 0; groups[i]; i++) | ||
243 | sysfs_remove_group(kobj, groups[i]); | ||
244 | } | ||
245 | EXPORT_SYMBOL_GPL(sysfs_remove_groups); | ||
180 | 246 | ||
181 | /** | 247 | /** |
182 | * sysfs_merge_group - merge files into a pre-existing attribute group. | 248 | * sysfs_merge_group - merge files into a pre-existing attribute group. |
@@ -273,7 +339,3 @@ void sysfs_remove_link_from_group(struct kobject *kobj, const char *group_name, | |||
273 | } | 339 | } |
274 | } | 340 | } |
275 | EXPORT_SYMBOL_GPL(sysfs_remove_link_from_group); | 341 | EXPORT_SYMBOL_GPL(sysfs_remove_link_from_group); |
276 | |||
277 | EXPORT_SYMBOL_GPL(sysfs_create_group); | ||
278 | EXPORT_SYMBOL_GPL(sysfs_update_group); | ||
279 | EXPORT_SYMBOL_GPL(sysfs_remove_group); | ||