1 /* 2 * Copyright (C) 2007 Oracle. All rights reserved. 3 * 4 * This program is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU General Public 6 * License v2 as published by the Free Software Foundation. 7 * 8 * This program is distributed in the hope that it will be useful, 9 * but WITHOUT ANY WARRANTY; without even the implied warranty of 10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 11 * General Public License for more details. 12 * 13 * You should have received a copy of the GNU General Public 14 * License along with this program; if not, write to the 15 * Free Software Foundation, Inc., 59 Temple Place - Suite 330, 16 * Boston, MA 021110-1307, USA. 17 */ 18 19 #include <linux/sched.h> 20 #include <linux/slab.h> 21 #include <linux/spinlock.h> 22 #include <linux/completion.h> 23 #include <linux/buffer_head.h> 24 #include <linux/kobject.h> 25 #include <linux/bug.h> 26 #include <linux/genhd.h> 27 #include <linux/debugfs.h> 28 29 #include "ctree.h" 30 #include "disk-io.h" 31 #include "transaction.h" 32 #include "sysfs.h" 33 #include "volumes.h" 34 35 static inline struct btrfs_fs_info *to_fs_info(struct kobject *kobj); 36 37 static u64 get_features(struct btrfs_fs_info *fs_info, 38 enum btrfs_feature_set set) 39 { 40 struct btrfs_super_block *disk_super = fs_info->super_copy; 41 if (set == FEAT_COMPAT) 42 return btrfs_super_compat_flags(disk_super); 43 else if (set == FEAT_COMPAT_RO) 44 return btrfs_super_compat_ro_flags(disk_super); 45 else 46 return btrfs_super_incompat_flags(disk_super); 47 } 48 49 static void set_features(struct btrfs_fs_info *fs_info, 50 enum btrfs_feature_set set, u64 features) 51 { 52 struct btrfs_super_block *disk_super = fs_info->super_copy; 53 if (set == FEAT_COMPAT) 54 btrfs_set_super_compat_flags(disk_super, features); 55 else if (set == FEAT_COMPAT_RO) 56 btrfs_set_super_compat_ro_flags(disk_super, features); 57 else 58 btrfs_set_super_incompat_flags(disk_super, features); 59 } 60 61 static int can_modify_feature(struct btrfs_feature_attr *fa) 62 { 63 int val = 0; 64 u64 set, clear; 65 switch (fa->feature_set) { 66 case FEAT_COMPAT: 67 set = BTRFS_FEATURE_COMPAT_SAFE_SET; 68 clear = BTRFS_FEATURE_COMPAT_SAFE_CLEAR; 69 break; 70 case FEAT_COMPAT_RO: 71 set = BTRFS_FEATURE_COMPAT_RO_SAFE_SET; 72 clear = BTRFS_FEATURE_COMPAT_RO_SAFE_CLEAR; 73 break; 74 case FEAT_INCOMPAT: 75 set = BTRFS_FEATURE_INCOMPAT_SAFE_SET; 76 clear = BTRFS_FEATURE_INCOMPAT_SAFE_CLEAR; 77 break; 78 default: 79 printk(KERN_WARNING "btrfs: sysfs: unknown feature set %d\n", 80 fa->feature_set); 81 return 0; 82 } 83 84 if (set & fa->feature_bit) 85 val |= 1; 86 if (clear & fa->feature_bit) 87 val |= 2; 88 89 return val; 90 } 91 92 static ssize_t btrfs_feature_attr_show(struct kobject *kobj, 93 struct kobj_attribute *a, char *buf) 94 { 95 int val = 0; 96 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 97 struct btrfs_feature_attr *fa = to_btrfs_feature_attr(a); 98 if (fs_info) { 99 u64 features = get_features(fs_info, fa->feature_set); 100 if (features & fa->feature_bit) 101 val = 1; 102 } else 103 val = can_modify_feature(fa); 104 105 return snprintf(buf, PAGE_SIZE, "%d\n", val); 106 } 107 108 static ssize_t btrfs_feature_attr_store(struct kobject *kobj, 109 struct kobj_attribute *a, 110 const char *buf, size_t count) 111 { 112 struct btrfs_fs_info *fs_info; 113 struct btrfs_feature_attr *fa = to_btrfs_feature_attr(a); 114 struct btrfs_trans_handle *trans; 115 u64 features, set, clear; 116 unsigned long val; 117 int ret; 118 119 fs_info = to_fs_info(kobj); 120 if (!fs_info) 121 return -EPERM; 122 123 ret = kstrtoul(skip_spaces(buf), 0, &val); 124 if (ret) 125 return ret; 126 127 if (fa->feature_set == FEAT_COMPAT) { 128 set = BTRFS_FEATURE_COMPAT_SAFE_SET; 129 clear = BTRFS_FEATURE_COMPAT_SAFE_CLEAR; 130 } else if (fa->feature_set == FEAT_COMPAT_RO) { 131 set = BTRFS_FEATURE_COMPAT_RO_SAFE_SET; 132 clear = BTRFS_FEATURE_COMPAT_RO_SAFE_CLEAR; 133 } else { 134 set = BTRFS_FEATURE_INCOMPAT_SAFE_SET; 135 clear = BTRFS_FEATURE_INCOMPAT_SAFE_CLEAR; 136 } 137 138 features = get_features(fs_info, fa->feature_set); 139 140 /* Nothing to do */ 141 if ((val && (features & fa->feature_bit)) || 142 (!val && !(features & fa->feature_bit))) 143 return count; 144 145 if ((val && !(set & fa->feature_bit)) || 146 (!val && !(clear & fa->feature_bit))) { 147 btrfs_info(fs_info, 148 "%sabling feature %s on mounted fs is not supported.", 149 val ? "En" : "Dis", fa->kobj_attr.attr.name); 150 return -EPERM; 151 } 152 153 btrfs_info(fs_info, "%s %s feature flag", 154 val ? "Setting" : "Clearing", fa->kobj_attr.attr.name); 155 156 trans = btrfs_start_transaction(fs_info->fs_root, 0); 157 if (IS_ERR(trans)) 158 return PTR_ERR(trans); 159 160 spin_lock(&fs_info->super_lock); 161 features = get_features(fs_info, fa->feature_set); 162 if (val) 163 features |= fa->feature_bit; 164 else 165 features &= ~fa->feature_bit; 166 set_features(fs_info, fa->feature_set, features); 167 spin_unlock(&fs_info->super_lock); 168 169 ret = btrfs_commit_transaction(trans, fs_info->fs_root); 170 if (ret) 171 return ret; 172 173 return count; 174 } 175 176 static umode_t btrfs_feature_visible(struct kobject *kobj, 177 struct attribute *attr, int unused) 178 { 179 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 180 umode_t mode = attr->mode; 181 182 if (fs_info) { 183 struct btrfs_feature_attr *fa; 184 u64 features; 185 186 fa = attr_to_btrfs_feature_attr(attr); 187 features = get_features(fs_info, fa->feature_set); 188 189 if (can_modify_feature(fa)) 190 mode |= S_IWUSR; 191 else if (!(features & fa->feature_bit)) 192 mode = 0; 193 } 194 195 return mode; 196 } 197 198 BTRFS_FEAT_ATTR_INCOMPAT(mixed_backref, MIXED_BACKREF); 199 BTRFS_FEAT_ATTR_INCOMPAT(default_subvol, DEFAULT_SUBVOL); 200 BTRFS_FEAT_ATTR_INCOMPAT(mixed_groups, MIXED_GROUPS); 201 BTRFS_FEAT_ATTR_INCOMPAT(compress_lzo, COMPRESS_LZO); 202 BTRFS_FEAT_ATTR_INCOMPAT(big_metadata, BIG_METADATA); 203 BTRFS_FEAT_ATTR_INCOMPAT(extended_iref, EXTENDED_IREF); 204 BTRFS_FEAT_ATTR_INCOMPAT(raid56, RAID56); 205 BTRFS_FEAT_ATTR_INCOMPAT(skinny_metadata, SKINNY_METADATA); 206 BTRFS_FEAT_ATTR_INCOMPAT(no_holes, NO_HOLES); 207 208 static struct attribute *btrfs_supported_feature_attrs[] = { 209 BTRFS_FEAT_ATTR_PTR(mixed_backref), 210 BTRFS_FEAT_ATTR_PTR(default_subvol), 211 BTRFS_FEAT_ATTR_PTR(mixed_groups), 212 BTRFS_FEAT_ATTR_PTR(compress_lzo), 213 BTRFS_FEAT_ATTR_PTR(big_metadata), 214 BTRFS_FEAT_ATTR_PTR(extended_iref), 215 BTRFS_FEAT_ATTR_PTR(raid56), 216 BTRFS_FEAT_ATTR_PTR(skinny_metadata), 217 BTRFS_FEAT_ATTR_PTR(no_holes), 218 NULL 219 }; 220 221 static const struct attribute_group btrfs_feature_attr_group = { 222 .name = "features", 223 .is_visible = btrfs_feature_visible, 224 .attrs = btrfs_supported_feature_attrs, 225 }; 226 227 static ssize_t btrfs_show_u64(u64 *value_ptr, spinlock_t *lock, char *buf) 228 { 229 u64 val; 230 if (lock) 231 spin_lock(lock); 232 val = *value_ptr; 233 if (lock) 234 spin_unlock(lock); 235 return snprintf(buf, PAGE_SIZE, "%llu\n", val); 236 } 237 238 static ssize_t global_rsv_size_show(struct kobject *kobj, 239 struct kobj_attribute *ka, char *buf) 240 { 241 struct btrfs_fs_info *fs_info = to_fs_info(kobj->parent); 242 struct btrfs_block_rsv *block_rsv = &fs_info->global_block_rsv; 243 return btrfs_show_u64(&block_rsv->size, &block_rsv->lock, buf); 244 } 245 BTRFS_ATTR(global_rsv_size, 0444, global_rsv_size_show); 246 247 static ssize_t global_rsv_reserved_show(struct kobject *kobj, 248 struct kobj_attribute *a, char *buf) 249 { 250 struct btrfs_fs_info *fs_info = to_fs_info(kobj->parent); 251 struct btrfs_block_rsv *block_rsv = &fs_info->global_block_rsv; 252 return btrfs_show_u64(&block_rsv->reserved, &block_rsv->lock, buf); 253 } 254 BTRFS_ATTR(global_rsv_reserved, 0444, global_rsv_reserved_show); 255 256 #define to_space_info(_kobj) container_of(_kobj, struct btrfs_space_info, kobj) 257 #define to_raid_kobj(_kobj) container_of(_kobj, struct raid_kobject, kobj) 258 259 static ssize_t raid_bytes_show(struct kobject *kobj, 260 struct kobj_attribute *attr, char *buf); 261 BTRFS_RAID_ATTR(total_bytes, raid_bytes_show); 262 BTRFS_RAID_ATTR(used_bytes, raid_bytes_show); 263 264 static ssize_t raid_bytes_show(struct kobject *kobj, 265 struct kobj_attribute *attr, char *buf) 266 267 { 268 struct btrfs_space_info *sinfo = to_space_info(kobj->parent); 269 struct btrfs_block_group_cache *block_group; 270 int index = to_raid_kobj(kobj)->raid_type; 271 u64 val = 0; 272 273 down_read(&sinfo->groups_sem); 274 list_for_each_entry(block_group, &sinfo->block_groups[index], list) { 275 if (&attr->attr == BTRFS_RAID_ATTR_PTR(total_bytes)) 276 val += block_group->key.offset; 277 else 278 val += btrfs_block_group_used(&block_group->item); 279 } 280 up_read(&sinfo->groups_sem); 281 return snprintf(buf, PAGE_SIZE, "%llu\n", val); 282 } 283 284 static struct attribute *raid_attributes[] = { 285 BTRFS_RAID_ATTR_PTR(total_bytes), 286 BTRFS_RAID_ATTR_PTR(used_bytes), 287 NULL 288 }; 289 290 static void release_raid_kobj(struct kobject *kobj) 291 { 292 kfree(to_raid_kobj(kobj)); 293 } 294 295 struct kobj_type btrfs_raid_ktype = { 296 .sysfs_ops = &kobj_sysfs_ops, 297 .release = release_raid_kobj, 298 .default_attrs = raid_attributes, 299 }; 300 301 #define SPACE_INFO_ATTR(field) \ 302 static ssize_t btrfs_space_info_show_##field(struct kobject *kobj, \ 303 struct kobj_attribute *a, \ 304 char *buf) \ 305 { \ 306 struct btrfs_space_info *sinfo = to_space_info(kobj); \ 307 return btrfs_show_u64(&sinfo->field, &sinfo->lock, buf); \ 308 } \ 309 BTRFS_ATTR(field, 0444, btrfs_space_info_show_##field) 310 311 static ssize_t btrfs_space_info_show_total_bytes_pinned(struct kobject *kobj, 312 struct kobj_attribute *a, 313 char *buf) 314 { 315 struct btrfs_space_info *sinfo = to_space_info(kobj); 316 s64 val = percpu_counter_sum(&sinfo->total_bytes_pinned); 317 return snprintf(buf, PAGE_SIZE, "%lld\n", val); 318 } 319 320 SPACE_INFO_ATTR(flags); 321 SPACE_INFO_ATTR(total_bytes); 322 SPACE_INFO_ATTR(bytes_used); 323 SPACE_INFO_ATTR(bytes_pinned); 324 SPACE_INFO_ATTR(bytes_reserved); 325 SPACE_INFO_ATTR(bytes_may_use); 326 SPACE_INFO_ATTR(disk_used); 327 SPACE_INFO_ATTR(disk_total); 328 BTRFS_ATTR(total_bytes_pinned, 0444, btrfs_space_info_show_total_bytes_pinned); 329 330 static struct attribute *space_info_attrs[] = { 331 BTRFS_ATTR_PTR(flags), 332 BTRFS_ATTR_PTR(total_bytes), 333 BTRFS_ATTR_PTR(bytes_used), 334 BTRFS_ATTR_PTR(bytes_pinned), 335 BTRFS_ATTR_PTR(bytes_reserved), 336 BTRFS_ATTR_PTR(bytes_may_use), 337 BTRFS_ATTR_PTR(disk_used), 338 BTRFS_ATTR_PTR(disk_total), 339 BTRFS_ATTR_PTR(total_bytes_pinned), 340 NULL, 341 }; 342 343 static void space_info_release(struct kobject *kobj) 344 { 345 struct btrfs_space_info *sinfo = to_space_info(kobj); 346 percpu_counter_destroy(&sinfo->total_bytes_pinned); 347 kfree(sinfo); 348 } 349 350 struct kobj_type space_info_ktype = { 351 .sysfs_ops = &kobj_sysfs_ops, 352 .release = space_info_release, 353 .default_attrs = space_info_attrs, 354 }; 355 356 static const struct attribute *allocation_attrs[] = { 357 BTRFS_ATTR_PTR(global_rsv_reserved), 358 BTRFS_ATTR_PTR(global_rsv_size), 359 NULL, 360 }; 361 362 static ssize_t btrfs_label_show(struct kobject *kobj, 363 struct kobj_attribute *a, char *buf) 364 { 365 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 366 return snprintf(buf, PAGE_SIZE, "%s\n", fs_info->super_copy->label); 367 } 368 369 static ssize_t btrfs_label_store(struct kobject *kobj, 370 struct kobj_attribute *a, 371 const char *buf, size_t len) 372 { 373 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 374 struct btrfs_trans_handle *trans; 375 struct btrfs_root *root = fs_info->fs_root; 376 int ret; 377 378 if (len >= BTRFS_LABEL_SIZE) 379 return -EINVAL; 380 381 trans = btrfs_start_transaction(root, 0); 382 if (IS_ERR(trans)) 383 return PTR_ERR(trans); 384 385 spin_lock(&root->fs_info->super_lock); 386 strcpy(fs_info->super_copy->label, buf); 387 spin_unlock(&root->fs_info->super_lock); 388 ret = btrfs_commit_transaction(trans, root); 389 390 if (!ret) 391 return len; 392 393 return ret; 394 } 395 BTRFS_ATTR_RW(label, 0644, btrfs_label_show, btrfs_label_store); 396 397 static ssize_t btrfs_no_store(struct kobject *kobj, 398 struct kobj_attribute *a, 399 const char *buf, size_t len) 400 { 401 return -EPERM; 402 } 403 404 static ssize_t btrfs_nodesize_show(struct kobject *kobj, 405 struct kobj_attribute *a, char *buf) 406 { 407 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 408 409 return snprintf(buf, PAGE_SIZE, "%u\n", fs_info->super_copy->nodesize); 410 } 411 412 BTRFS_ATTR_RW(nodesize, 0444, btrfs_nodesize_show, btrfs_no_store); 413 414 static ssize_t btrfs_sectorsize_show(struct kobject *kobj, 415 struct kobj_attribute *a, char *buf) 416 { 417 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 418 419 return snprintf(buf, PAGE_SIZE, "%u\n", fs_info->super_copy->sectorsize); 420 } 421 422 BTRFS_ATTR_RW(sectorsize, 0444, btrfs_sectorsize_show, btrfs_no_store); 423 424 static ssize_t btrfs_clone_alignment_show(struct kobject *kobj, 425 struct kobj_attribute *a, char *buf) 426 { 427 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 428 429 return snprintf(buf, PAGE_SIZE, "%u\n", fs_info->super_copy->sectorsize); 430 } 431 432 BTRFS_ATTR_RW(clone_alignment, 0444, btrfs_clone_alignment_show, btrfs_no_store); 433 434 static struct attribute *btrfs_attrs[] = { 435 BTRFS_ATTR_PTR(label), 436 BTRFS_ATTR_PTR(nodesize), 437 BTRFS_ATTR_PTR(sectorsize), 438 BTRFS_ATTR_PTR(clone_alignment), 439 NULL, 440 }; 441 442 static void btrfs_release_super_kobj(struct kobject *kobj) 443 { 444 struct btrfs_fs_info *fs_info = to_fs_info(kobj); 445 complete(&fs_info->kobj_unregister); 446 } 447 448 static struct kobj_type btrfs_ktype = { 449 .sysfs_ops = &kobj_sysfs_ops, 450 .release = btrfs_release_super_kobj, 451 .default_attrs = btrfs_attrs, 452 }; 453 454 static inline struct btrfs_fs_info *to_fs_info(struct kobject *kobj) 455 { 456 if (kobj->ktype != &btrfs_ktype) 457 return NULL; 458 return container_of(kobj, struct btrfs_fs_info, super_kobj); 459 } 460 461 #define NUM_FEATURE_BITS 64 462 static char btrfs_unknown_feature_names[3][NUM_FEATURE_BITS][13]; 463 static struct btrfs_feature_attr btrfs_feature_attrs[3][NUM_FEATURE_BITS]; 464 465 static u64 supported_feature_masks[3] = { 466 [FEAT_COMPAT] = BTRFS_FEATURE_COMPAT_SUPP, 467 [FEAT_COMPAT_RO] = BTRFS_FEATURE_COMPAT_RO_SUPP, 468 [FEAT_INCOMPAT] = BTRFS_FEATURE_INCOMPAT_SUPP, 469 }; 470 471 static int addrm_unknown_feature_attrs(struct btrfs_fs_info *fs_info, bool add) 472 { 473 int set; 474 475 for (set = 0; set < FEAT_MAX; set++) { 476 int i; 477 struct attribute *attrs[2]; 478 struct attribute_group agroup = { 479 .name = "features", 480 .attrs = attrs, 481 }; 482 u64 features = get_features(fs_info, set); 483 features &= ~supported_feature_masks[set]; 484 485 if (!features) 486 continue; 487 488 attrs[1] = NULL; 489 for (i = 0; i < NUM_FEATURE_BITS; i++) { 490 struct btrfs_feature_attr *fa; 491 492 if (!(features & (1ULL << i))) 493 continue; 494 495 fa = &btrfs_feature_attrs[set][i]; 496 attrs[0] = &fa->kobj_attr.attr; 497 if (add) { 498 int ret; 499 ret = sysfs_merge_group(&fs_info->super_kobj, 500 &agroup); 501 if (ret) 502 return ret; 503 } else 504 sysfs_unmerge_group(&fs_info->super_kobj, 505 &agroup); 506 } 507 508 } 509 return 0; 510 } 511 512 static void __btrfs_sysfs_remove_one(struct btrfs_fs_info *fs_info) 513 { 514 kobject_del(&fs_info->super_kobj); 515 kobject_put(&fs_info->super_kobj); 516 wait_for_completion(&fs_info->kobj_unregister); 517 } 518 519 void btrfs_sysfs_remove_one(struct btrfs_fs_info *fs_info) 520 { 521 if (fs_info->space_info_kobj) { 522 sysfs_remove_files(fs_info->space_info_kobj, allocation_attrs); 523 kobject_del(fs_info->space_info_kobj); 524 kobject_put(fs_info->space_info_kobj); 525 } 526 kobject_del(fs_info->device_dir_kobj); 527 kobject_put(fs_info->device_dir_kobj); 528 addrm_unknown_feature_attrs(fs_info, false); 529 sysfs_remove_group(&fs_info->super_kobj, &btrfs_feature_attr_group); 530 __btrfs_sysfs_remove_one(fs_info); 531 } 532 533 const char * const btrfs_feature_set_names[3] = { 534 [FEAT_COMPAT] = "compat", 535 [FEAT_COMPAT_RO] = "compat_ro", 536 [FEAT_INCOMPAT] = "incompat", 537 }; 538 539 char *btrfs_printable_features(enum btrfs_feature_set set, u64 flags) 540 { 541 size_t bufsize = 4096; /* safe max, 64 names * 64 bytes */ 542 int len = 0; 543 int i; 544 char *str; 545 546 str = kmalloc(bufsize, GFP_KERNEL); 547 if (!str) 548 return str; 549 550 for (i = 0; i < ARRAY_SIZE(btrfs_feature_attrs[set]); i++) { 551 const char *name; 552 553 if (!(flags & (1ULL << i))) 554 continue; 555 556 name = btrfs_feature_attrs[set][i].kobj_attr.attr.name; 557 len += snprintf(str + len, bufsize - len, "%s%s", 558 len ? "," : "", name); 559 } 560 561 return str; 562 } 563 564 static void init_feature_attrs(void) 565 { 566 struct btrfs_feature_attr *fa; 567 int set, i; 568 569 BUILD_BUG_ON(ARRAY_SIZE(btrfs_unknown_feature_names) != 570 ARRAY_SIZE(btrfs_feature_attrs)); 571 BUILD_BUG_ON(ARRAY_SIZE(btrfs_unknown_feature_names[0]) != 572 ARRAY_SIZE(btrfs_feature_attrs[0])); 573 574 memset(btrfs_feature_attrs, 0, sizeof(btrfs_feature_attrs)); 575 memset(btrfs_unknown_feature_names, 0, 576 sizeof(btrfs_unknown_feature_names)); 577 578 for (i = 0; btrfs_supported_feature_attrs[i]; i++) { 579 struct btrfs_feature_attr *sfa; 580 struct attribute *a = btrfs_supported_feature_attrs[i]; 581 int bit; 582 sfa = attr_to_btrfs_feature_attr(a); 583 bit = ilog2(sfa->feature_bit); 584 fa = &btrfs_feature_attrs[sfa->feature_set][bit]; 585 586 fa->kobj_attr.attr.name = sfa->kobj_attr.attr.name; 587 } 588 589 for (set = 0; set < FEAT_MAX; set++) { 590 for (i = 0; i < ARRAY_SIZE(btrfs_feature_attrs[set]); i++) { 591 char *name = btrfs_unknown_feature_names[set][i]; 592 fa = &btrfs_feature_attrs[set][i]; 593 594 if (fa->kobj_attr.attr.name) 595 continue; 596 597 snprintf(name, 13, "%s:%u", 598 btrfs_feature_set_names[set], i); 599 600 fa->kobj_attr.attr.name = name; 601 fa->kobj_attr.attr.mode = S_IRUGO; 602 fa->feature_set = set; 603 fa->feature_bit = 1ULL << i; 604 } 605 } 606 } 607 608 static int add_device_membership(struct btrfs_fs_info *fs_info) 609 { 610 int error = 0; 611 struct btrfs_fs_devices *fs_devices = fs_info->fs_devices; 612 struct btrfs_device *dev; 613 614 fs_info->device_dir_kobj = kobject_create_and_add("devices", 615 &fs_info->super_kobj); 616 if (!fs_info->device_dir_kobj) 617 return -ENOMEM; 618 619 list_for_each_entry(dev, &fs_devices->devices, dev_list) { 620 struct hd_struct *disk; 621 struct kobject *disk_kobj; 622 623 if (!dev->bdev) 624 continue; 625 626 disk = dev->bdev->bd_part; 627 disk_kobj = &part_to_dev(disk)->kobj; 628 629 error = sysfs_create_link(fs_info->device_dir_kobj, 630 disk_kobj, disk_kobj->name); 631 if (error) 632 break; 633 } 634 635 return error; 636 } 637 638 /* /sys/fs/btrfs/ entry */ 639 static struct kset *btrfs_kset; 640 641 /* /sys/kernel/debug/btrfs */ 642 static struct dentry *btrfs_debugfs_root_dentry; 643 644 /* Debugging tunables and exported data */ 645 u64 btrfs_debugfs_test; 646 647 int btrfs_sysfs_add_one(struct btrfs_fs_info *fs_info) 648 { 649 int error; 650 651 init_completion(&fs_info->kobj_unregister); 652 fs_info->super_kobj.kset = btrfs_kset; 653 error = kobject_init_and_add(&fs_info->super_kobj, &btrfs_ktype, NULL, 654 "%pU", fs_info->fsid); 655 if (error) 656 return error; 657 658 error = sysfs_create_group(&fs_info->super_kobj, 659 &btrfs_feature_attr_group); 660 if (error) { 661 __btrfs_sysfs_remove_one(fs_info); 662 return error; 663 } 664 665 error = addrm_unknown_feature_attrs(fs_info, true); 666 if (error) 667 goto failure; 668 669 error = add_device_membership(fs_info); 670 if (error) 671 goto failure; 672 673 fs_info->space_info_kobj = kobject_create_and_add("allocation", 674 &fs_info->super_kobj); 675 if (!fs_info->space_info_kobj) { 676 error = -ENOMEM; 677 goto failure; 678 } 679 680 error = sysfs_create_files(fs_info->space_info_kobj, allocation_attrs); 681 if (error) 682 goto failure; 683 684 return 0; 685 failure: 686 btrfs_sysfs_remove_one(fs_info); 687 return error; 688 } 689 690 static int btrfs_init_debugfs(void) 691 { 692 #ifdef CONFIG_DEBUG_FS 693 btrfs_debugfs_root_dentry = debugfs_create_dir("btrfs", NULL); 694 if (!btrfs_debugfs_root_dentry) 695 return -ENOMEM; 696 697 debugfs_create_u64("test", S_IRUGO | S_IWUGO, btrfs_debugfs_root_dentry, 698 &btrfs_debugfs_test); 699 #endif 700 return 0; 701 } 702 703 int btrfs_init_sysfs(void) 704 { 705 int ret; 706 707 btrfs_kset = kset_create_and_add("btrfs", NULL, fs_kobj); 708 if (!btrfs_kset) 709 return -ENOMEM; 710 711 ret = btrfs_init_debugfs(); 712 if (ret) 713 return ret; 714 715 init_feature_attrs(); 716 ret = sysfs_create_group(&btrfs_kset->kobj, &btrfs_feature_attr_group); 717 718 return ret; 719 } 720 721 void btrfs_exit_sysfs(void) 722 { 723 sysfs_remove_group(&btrfs_kset->kobj, &btrfs_feature_attr_group); 724 kset_unregister(btrfs_kset); 725 debugfs_remove_recursive(btrfs_debugfs_root_dentry); 726 } 727 728