diff options
-rw-r--r-- | fs/sysfs/group.c | 59 | ||||
-rw-r--r-- | include/linux/sysfs.h | 15 |
2 files changed, 74 insertions, 0 deletions
diff --git a/fs/sysfs/group.c b/fs/sysfs/group.c index 23c1e598792a..442f34ff1af8 100644 --- a/fs/sysfs/group.c +++ b/fs/sysfs/group.c | |||
@@ -148,6 +148,65 @@ void sysfs_remove_group(struct kobject * kobj, | |||
148 | sysfs_put(sd); | 148 | sysfs_put(sd); |
149 | } | 149 | } |
150 | 150 | ||
151 | /** | ||
152 | * sysfs_merge_group - merge files into a pre-existing attribute group. | ||
153 | * @kobj: The kobject containing the group. | ||
154 | * @grp: The files to create and the attribute group they belong to. | ||
155 | * | ||
156 | * This function returns an error if the group doesn't exist or any of the | ||
157 | * files already exist in that group, in which case none of the new files | ||
158 | * are created. | ||
159 | */ | ||
160 | int sysfs_merge_group(struct kobject *kobj, | ||
161 | const struct attribute_group *grp) | ||
162 | { | ||
163 | struct sysfs_dirent *dir_sd; | ||
164 | int error = 0; | ||
165 | struct attribute *const *attr; | ||
166 | int i; | ||
167 | |||
168 | if (grp) | ||
169 | dir_sd = sysfs_get_dirent(kobj->sd, NULL, grp->name); | ||
170 | else | ||
171 | dir_sd = sysfs_get(kobj->sd); | ||
172 | if (!dir_sd) | ||
173 | return -ENOENT; | ||
174 | |||
175 | for ((i = 0, attr = grp->attrs); *attr && !error; (++i, ++attr)) | ||
176 | error = sysfs_add_file(dir_sd, *attr, SYSFS_KOBJ_ATTR); | ||
177 | if (error) { | ||
178 | while (--i >= 0) | ||
179 | sysfs_hash_and_remove(dir_sd, NULL, (*--attr)->name); | ||
180 | } | ||
181 | sysfs_put(dir_sd); | ||
182 | |||
183 | return error; | ||
184 | } | ||
185 | EXPORT_SYMBOL_GPL(sysfs_merge_group); | ||
186 | |||
187 | /** | ||
188 | * sysfs_unmerge_group - remove files from a pre-existing attribute group. | ||
189 | * @kobj: The kobject containing the group. | ||
190 | * @grp: The files to remove and the attribute group they belong to. | ||
191 | */ | ||
192 | void sysfs_unmerge_group(struct kobject *kobj, | ||
193 | const struct attribute_group *grp) | ||
194 | { | ||
195 | struct sysfs_dirent *dir_sd; | ||
196 | struct attribute *const *attr; | ||
197 | |||
198 | if (grp) | ||
199 | dir_sd = sysfs_get_dirent(kobj->sd, NULL, grp->name); | ||
200 | else | ||
201 | dir_sd = sysfs_get(kobj->sd); | ||
202 | if (dir_sd) { | ||
203 | for (attr = grp->attrs; *attr; ++attr) | ||
204 | sysfs_hash_and_remove(dir_sd, NULL, (*attr)->name); | ||
205 | sysfs_put(dir_sd); | ||
206 | } | ||
207 | } | ||
208 | EXPORT_SYMBOL_GPL(sysfs_unmerge_group); | ||
209 | |||
151 | 210 | ||
152 | EXPORT_SYMBOL_GPL(sysfs_create_group); | 211 | EXPORT_SYMBOL_GPL(sysfs_create_group); |
153 | EXPORT_SYMBOL_GPL(sysfs_update_group); | 212 | EXPORT_SYMBOL_GPL(sysfs_update_group); |
diff --git a/include/linux/sysfs.h b/include/linux/sysfs.h index 96eb576d82fd..30b881555fa5 100644 --- a/include/linux/sysfs.h +++ b/include/linux/sysfs.h | |||
@@ -164,6 +164,10 @@ int sysfs_add_file_to_group(struct kobject *kobj, | |||
164 | const struct attribute *attr, const char *group); | 164 | const struct attribute *attr, const char *group); |
165 | void sysfs_remove_file_from_group(struct kobject *kobj, | 165 | void sysfs_remove_file_from_group(struct kobject *kobj, |
166 | const struct attribute *attr, const char *group); | 166 | const struct attribute *attr, const char *group); |
167 | int sysfs_merge_group(struct kobject *kobj, | ||
168 | const struct attribute_group *grp); | ||
169 | void sysfs_unmerge_group(struct kobject *kobj, | ||
170 | const struct attribute_group *grp); | ||
167 | 171 | ||
168 | void sysfs_notify(struct kobject *kobj, const char *dir, const char *attr); | 172 | void sysfs_notify(struct kobject *kobj, const char *dir, const char *attr); |
169 | void sysfs_notify_dirent(struct sysfs_dirent *sd); | 173 | void sysfs_notify_dirent(struct sysfs_dirent *sd); |
@@ -302,6 +306,17 @@ static inline void sysfs_remove_file_from_group(struct kobject *kobj, | |||
302 | { | 306 | { |
303 | } | 307 | } |
304 | 308 | ||
309 | static inline int sysfs_merge_group(struct kobject *kobj, | ||
310 | const struct attribute_group *grp) | ||
311 | { | ||
312 | return 0; | ||
313 | } | ||
314 | |||
315 | static inline void sysfs_unmerge_group(struct kobject *kobj, | ||
316 | const struct attribute_group *grp) | ||
317 | { | ||
318 | } | ||
319 | |||
305 | static inline void sysfs_notify(struct kobject *kobj, const char *dir, | 320 | static inline void sysfs_notify(struct kobject *kobj, const char *dir, |
306 | const char *attr) | 321 | const char *attr) |
307 | { | 322 | { |