sysfs.c 6.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257
  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. #include <linux/sched.h>
  19. #include <linux/slab.h>
  20. #include <linux/spinlock.h>
  21. #include <linux/completion.h>
  22. #include <linux/buffer_head.h>
  23. #include <linux/module.h>
  24. #include <linux/kobject.h>
  25. #include "ctree.h"
  26. #include "disk-io.h"
  27. #include "transaction.h"
  28. static ssize_t root_blocks_used_show(struct btrfs_root *root, char *buf)
  29. {
  30. return snprintf(buf, PAGE_SIZE, "%llu\n",
  31. (unsigned long long)btrfs_root_used(&root->root_item));
  32. }
  33. static ssize_t root_block_limit_show(struct btrfs_root *root, char *buf)
  34. {
  35. return snprintf(buf, PAGE_SIZE, "%llu\n",
  36. (unsigned long long)btrfs_root_limit(&root->root_item));
  37. }
  38. static ssize_t super_blocks_used_show(struct btrfs_fs_info *fs, char *buf)
  39. {
  40. return snprintf(buf, PAGE_SIZE, "%llu\n",
  41. (unsigned long long)btrfs_super_bytes_used(&fs->super_copy));
  42. }
  43. static ssize_t super_total_blocks_show(struct btrfs_fs_info *fs, char *buf)
  44. {
  45. return snprintf(buf, PAGE_SIZE, "%llu\n",
  46. (unsigned long long)btrfs_super_total_bytes(&fs->super_copy));
  47. }
  48. static ssize_t super_blocksize_show(struct btrfs_fs_info *fs, char *buf)
  49. {
  50. return snprintf(buf, PAGE_SIZE, "%llu\n",
  51. (unsigned long long)btrfs_super_sectorsize(&fs->super_copy));
  52. }
  53. /* this is for root attrs (subvols/snapshots) */
  54. struct btrfs_root_attr {
  55. struct attribute attr;
  56. ssize_t (*show)(struct btrfs_root *, char *);
  57. ssize_t (*store)(struct btrfs_root *, const char *, size_t);
  58. };
  59. #define ROOT_ATTR(name, mode, show, store) \
  60. static struct btrfs_root_attr btrfs_root_attr_##name = __ATTR(name, mode, show, store)
  61. ROOT_ATTR(blocks_used, 0444, root_blocks_used_show, NULL);
  62. ROOT_ATTR(block_limit, 0644, root_block_limit_show, NULL);
  63. static struct attribute *btrfs_root_attrs[] = {
  64. &btrfs_root_attr_blocks_used.attr,
  65. &btrfs_root_attr_block_limit.attr,
  66. NULL,
  67. };
  68. /* this is for super attrs (actual full fs) */
  69. struct btrfs_super_attr {
  70. struct attribute attr;
  71. ssize_t (*show)(struct btrfs_fs_info *, char *);
  72. ssize_t (*store)(struct btrfs_fs_info *, const char *, size_t);
  73. };
  74. #define SUPER_ATTR(name, mode, show, store) \
  75. static struct btrfs_super_attr btrfs_super_attr_##name = __ATTR(name, mode, show, store)
  76. SUPER_ATTR(blocks_used, 0444, super_blocks_used_show, NULL);
  77. SUPER_ATTR(total_blocks, 0444, super_total_blocks_show, NULL);
  78. SUPER_ATTR(blocksize, 0444, super_blocksize_show, NULL);
  79. static struct attribute *btrfs_super_attrs[] = {
  80. &btrfs_super_attr_blocks_used.attr,
  81. &btrfs_super_attr_total_blocks.attr,
  82. &btrfs_super_attr_blocksize.attr,
  83. NULL,
  84. };
  85. static ssize_t btrfs_super_attr_show(struct kobject *kobj,
  86. struct attribute *attr, char *buf)
  87. {
  88. struct btrfs_fs_info *fs = container_of(kobj, struct btrfs_fs_info,
  89. super_kobj);
  90. struct btrfs_super_attr *a = container_of(attr,
  91. struct btrfs_super_attr,
  92. attr);
  93. return a->show ? a->show(fs, buf) : 0;
  94. }
  95. static ssize_t btrfs_super_attr_store(struct kobject *kobj,
  96. struct attribute *attr,
  97. const char *buf, size_t len)
  98. {
  99. struct btrfs_fs_info *fs = container_of(kobj, struct btrfs_fs_info,
  100. super_kobj);
  101. struct btrfs_super_attr *a = container_of(attr,
  102. struct btrfs_super_attr,
  103. attr);
  104. return a->store ? a->store(fs, buf, len) : 0;
  105. }
  106. static ssize_t btrfs_root_attr_show(struct kobject *kobj,
  107. struct attribute *attr, char *buf)
  108. {
  109. struct btrfs_root *root = container_of(kobj, struct btrfs_root,
  110. root_kobj);
  111. struct btrfs_root_attr *a = container_of(attr,
  112. struct btrfs_root_attr,
  113. attr);
  114. return a->show ? a->show(root, buf) : 0;
  115. }
  116. static ssize_t btrfs_root_attr_store(struct kobject *kobj,
  117. struct attribute *attr,
  118. const char *buf, size_t len)
  119. {
  120. struct btrfs_root *root = container_of(kobj, struct btrfs_root,
  121. root_kobj);
  122. struct btrfs_root_attr *a = container_of(attr,
  123. struct btrfs_root_attr,
  124. attr);
  125. return a->store ? a->store(root, buf, len) : 0;
  126. }
  127. static void btrfs_super_release(struct kobject *kobj)
  128. {
  129. struct btrfs_fs_info *fs = container_of(kobj, struct btrfs_fs_info,
  130. super_kobj);
  131. complete(&fs->kobj_unregister);
  132. }
  133. static void btrfs_root_release(struct kobject *kobj)
  134. {
  135. struct btrfs_root *root = container_of(kobj, struct btrfs_root,
  136. root_kobj);
  137. complete(&root->kobj_unregister);
  138. }
  139. static struct sysfs_ops btrfs_super_attr_ops = {
  140. .show = btrfs_super_attr_show,
  141. .store = btrfs_super_attr_store,
  142. };
  143. static struct sysfs_ops btrfs_root_attr_ops = {
  144. .show = btrfs_root_attr_show,
  145. .store = btrfs_root_attr_store,
  146. };
  147. static struct kobj_type btrfs_root_ktype = {
  148. .default_attrs = btrfs_root_attrs,
  149. .sysfs_ops = &btrfs_root_attr_ops,
  150. .release = btrfs_root_release,
  151. };
  152. static struct kobj_type btrfs_super_ktype = {
  153. .default_attrs = btrfs_super_attrs,
  154. .sysfs_ops = &btrfs_super_attr_ops,
  155. .release = btrfs_super_release,
  156. };
  157. static struct kset btrfs_kset;
  158. int btrfs_sysfs_add_super(struct btrfs_fs_info *fs)
  159. {
  160. int error;
  161. fs->super_kobj.kset = &btrfs_kset;
  162. fs->super_kobj.ktype = &btrfs_super_ktype;
  163. error = kobject_set_name(&fs->super_kobj, "%s",
  164. fs->sb->s_id);
  165. if (error)
  166. goto fail;
  167. error = kobject_register(&fs->super_kobj);
  168. if (error)
  169. goto fail;
  170. return 0;
  171. fail:
  172. printk(KERN_ERR "btrfs: sysfs creation for super failed\n");
  173. return error;
  174. }
  175. int btrfs_sysfs_add_root(struct btrfs_root *root)
  176. {
  177. int error;
  178. root->root_kobj.ktype = &btrfs_root_ktype;
  179. root->root_kobj.parent = &root->fs_info->super_kobj;
  180. error = kobject_set_name(&root->root_kobj, "%s", root->name);
  181. if (error) {
  182. goto fail;
  183. }
  184. error = kobject_register(&root->root_kobj);
  185. if (error)
  186. goto fail;
  187. return 0;
  188. fail:
  189. printk(KERN_ERR "btrfs: sysfs creation for root failed\n");
  190. return error;
  191. }
  192. void btrfs_sysfs_del_root(struct btrfs_root *root)
  193. {
  194. kobject_unregister(&root->root_kobj);
  195. wait_for_completion(&root->kobj_unregister);
  196. }
  197. void btrfs_sysfs_del_super(struct btrfs_fs_info *fs)
  198. {
  199. kobject_unregister(&fs->super_kobj);
  200. wait_for_completion(&fs->kobj_unregister);
  201. }
  202. int btrfs_init_sysfs()
  203. {
  204. kobj_set_kset_s(&btrfs_kset, fs_subsys);
  205. kobject_set_name(&btrfs_kset.kobj, "btrfs");
  206. return kset_register(&btrfs_kset);
  207. }
  208. void btrfs_exit_sysfs()
  209. {
  210. kset_unregister(&btrfs_kset);
  211. }