1/* 2 * kernfs.h - pseudo filesystem decoupled from vfs locking 3 * 4 * This file is released under the GPLv2. 5 */ 6 7#ifndef __LINUX_KERNFS_H 8#define __LINUX_KERNFS_H 9 10#include <linux/kernel.h> 11#include <linux/err.h> 12#include <linux/list.h> 13#include <linux/mutex.h> 14#include <linux/idr.h> 15#include <linux/lockdep.h> 16#include <linux/rbtree.h> 17#include <linux/atomic.h> 18#include <linux/completion.h> 19 20struct file; 21struct dentry; 22struct iattr; 23struct seq_file; 24struct vm_area_struct; 25struct super_block; 26struct file_system_type; 27 28struct kernfs_open_node; 29struct kernfs_iattrs; 30 31enum kernfs_node_type { 32 KERNFS_DIR = 0x0001, 33 KERNFS_FILE = 0x0002, 34 KERNFS_LINK = 0x0004, 35}; 36 37#define KERNFS_TYPE_MASK 0x000f 38#define KERNFS_ACTIVE_REF KERNFS_FILE 39#define KERNFS_FLAG_MASK ~KERNFS_TYPE_MASK 40 41enum kernfs_node_flag { 42 KERNFS_REMOVED = 0x0010, 43 KERNFS_NS = 0x0020, 44 KERNFS_HAS_SEQ_SHOW = 0x0040, 45 KERNFS_HAS_MMAP = 0x0080, 46 KERNFS_LOCKDEP = 0x0100, 47 KERNFS_STATIC_NAME = 0x0200, 48}; 49 50/* type-specific structures for kernfs_node union members */ 51struct kernfs_elem_dir { 52 unsigned long subdirs; 53 /* children rbtree starts here and goes through kn->rb */ 54 struct rb_root children; 55 56 /* 57 * The kernfs hierarchy this directory belongs to. This fits 58 * better directly in kernfs_node but is here to save space. 59 */ 60 struct kernfs_root *root; 61}; 62 63struct kernfs_elem_symlink { 64 struct kernfs_node *target_kn; 65}; 66 67struct kernfs_elem_attr { 68 const struct kernfs_ops *ops; 69 struct kernfs_open_node *open; 70 loff_t size; 71}; 72 73/* 74 * kernfs_node - the building block of kernfs hierarchy. Each and every 75 * kernfs node is represented by single kernfs_node. Most fields are 76 * private to kernfs and shouldn't be accessed directly by kernfs users. 77 * 78 * As long as s_count reference is held, the kernfs_node itself is 79 * accessible. Dereferencing elem or any other outer entity requires 80 * active reference. 81 */ 82struct kernfs_node { 83 atomic_t count; 84 atomic_t active; 85#ifdef CONFIG_DEBUG_LOCK_ALLOC 86 struct lockdep_map dep_map; 87#endif 88 /* the following two fields are published */ 89 struct kernfs_node *parent; 90 const char *name; 91 92 struct rb_node rb; 93 94 union { 95 struct completion *completion; 96 struct kernfs_node *removed_list; 97 } u; 98 99 const void *ns; /* namespace tag */ 100 unsigned int hash; /* ns + name hash */ 101 union { 102 struct kernfs_elem_dir dir; 103 struct kernfs_elem_symlink symlink; 104 struct kernfs_elem_attr attr; 105 }; 106 107 void *priv; 108 109 unsigned short flags; 110 umode_t mode; 111 unsigned int ino; 112 struct kernfs_iattrs *iattr; 113}; 114 115/* 116 * kernfs_dir_ops may be specified on kernfs_create_root() to support 117 * directory manipulation syscalls. These optional callbacks are invoked 118 * on the matching syscalls and can perform any kernfs operations which 119 * don't necessarily have to be the exact operation requested. 120 */ 121struct kernfs_dir_ops { 122 int (*mkdir)(struct kernfs_node *parent, const char *name, 123 umode_t mode); 124 int (*rmdir)(struct kernfs_node *kn); 125 int (*rename)(struct kernfs_node *kn, struct kernfs_node *new_parent, 126 const char *new_name); 127}; 128 129struct kernfs_root { 130 /* published fields */ 131 struct kernfs_node *kn; 132 133 /* private fields, do not use outside kernfs proper */ 134 struct ida ino_ida; 135 struct kernfs_dir_ops *dir_ops; 136}; 137 138struct kernfs_open_file { 139 /* published fields */ 140 struct kernfs_node *kn; 141 struct file *file; 142 143 /* private fields, do not use outside kernfs proper */ 144 struct mutex mutex; 145 int event; 146 struct list_head list; 147 148 bool mmapped; 149 const struct vm_operations_struct *vm_ops; 150}; 151 152struct kernfs_ops { 153 /* 154 * Read is handled by either seq_file or raw_read(). 155 * 156 * If seq_show() is present, seq_file path is active. Other seq 157 * operations are optional and if not implemented, the behavior is 158 * equivalent to single_open(). @sf->private points to the 159 * associated kernfs_open_file. 160 * 161 * read() is bounced through kernel buffer and a read larger than 162 * PAGE_SIZE results in partial operation of PAGE_SIZE. 163 */ 164 int (*seq_show)(struct seq_file *sf, void *v); 165 166 void *(*seq_start)(struct seq_file *sf, loff_t *ppos); 167 void *(*seq_next)(struct seq_file *sf, void *v, loff_t *ppos); 168 void (*seq_stop)(struct seq_file *sf, void *v); 169 170 ssize_t (*read)(struct kernfs_open_file *of, char *buf, size_t bytes, 171 loff_t off); 172 173 /* 174 * write() is bounced through kernel buffer and a write larger than 175 * PAGE_SIZE results in partial operation of PAGE_SIZE. 176 */ 177 ssize_t (*write)(struct kernfs_open_file *of, char *buf, size_t bytes, 178 loff_t off); 179 180 int (*mmap)(struct kernfs_open_file *of, struct vm_area_struct *vma); 181 182#ifdef CONFIG_DEBUG_LOCK_ALLOC 183 struct lock_class_key lockdep_key; 184#endif 185}; 186 187#ifdef CONFIG_SYSFS 188 189static inline enum kernfs_node_type kernfs_type(struct kernfs_node *kn) 190{ 191 return kn->flags & KERNFS_TYPE_MASK; 192} 193 194/** 195 * kernfs_enable_ns - enable namespace under a directory 196 * @kn: directory of interest, should be empty 197 * 198 * This is to be called right after @kn is created to enable namespace 199 * under it. All children of @kn must have non-NULL namespace tags and 200 * only the ones which match the super_block's tag will be visible. 201 */ 202static inline void kernfs_enable_ns(struct kernfs_node *kn) 203{ 204 WARN_ON_ONCE(kernfs_type(kn) != KERNFS_DIR); 205 WARN_ON_ONCE(!RB_EMPTY_ROOT(&kn->dir.children)); 206 kn->flags |= KERNFS_NS; 207} 208 209/** 210 * kernfs_ns_enabled - test whether namespace is enabled 211 * @kn: the node to test 212 * 213 * Test whether namespace filtering is enabled for the children of @ns. 214 */ 215static inline bool kernfs_ns_enabled(struct kernfs_node *kn) 216{ 217 return kn->flags & KERNFS_NS; 218} 219 220struct kernfs_node *kernfs_find_and_get_ns(struct kernfs_node *parent, 221 const char *name, const void *ns); 222void kernfs_get(struct kernfs_node *kn); 223void kernfs_put(struct kernfs_node *kn); 224 225struct kernfs_root *kernfs_create_root(struct kernfs_dir_ops *kdops, 226 void *priv); 227void kernfs_destroy_root(struct kernfs_root *root); 228 229struct kernfs_node *kernfs_create_dir_ns(struct kernfs_node *parent, 230 const char *name, umode_t mode, 231 void *priv, const void *ns); 232struct kernfs_node *__kernfs_create_file(struct kernfs_node *parent, 233 const char *name, 234 umode_t mode, loff_t size, 235 const struct kernfs_ops *ops, 236 void *priv, const void *ns, 237 bool name_is_static, 238 struct lock_class_key *key); 239struct kernfs_node *kernfs_create_link(struct kernfs_node *parent, 240 const char *name, 241 struct kernfs_node *target); 242void kernfs_remove(struct kernfs_node *kn); 243int kernfs_remove_by_name_ns(struct kernfs_node *parent, const char *name, 244 const void *ns); 245int kernfs_rename_ns(struct kernfs_node *kn, struct kernfs_node *new_parent, 246 const char *new_name, const void *new_ns); 247int kernfs_setattr(struct kernfs_node *kn, const struct iattr *iattr); 248void kernfs_notify(struct kernfs_node *kn); 249 250const void *kernfs_super_ns(struct super_block *sb); 251struct dentry *kernfs_mount_ns(struct file_system_type *fs_type, int flags, 252 struct kernfs_root *root, const void *ns); 253void kernfs_kill_sb(struct super_block *sb); 254 255void kernfs_init(void); 256 257#else /* CONFIG_SYSFS */ 258 259static inline enum kernfs_node_type kernfs_type(struct kernfs_node *kn) 260{ return 0; } /* whatever */ 261 262static inline void kernfs_enable_ns(struct kernfs_node *kn) { } 263 264static inline bool kernfs_ns_enabled(struct kernfs_node *kn) 265{ return false; } 266 267static inline struct kernfs_node * 268kernfs_find_and_get_ns(struct kernfs_node *parent, const char *name, 269 const void *ns) 270{ return NULL; } 271 272static inline void kernfs_get(struct kernfs_node *kn) { } 273static inline void kernfs_put(struct kernfs_node *kn) { } 274 275static inline struct kernfs_root * 276kernfs_create_root(struct kernfs_dir_ops *kdops, void *priv) 277{ return ERR_PTR(-ENOSYS); } 278 279static inline void kernfs_destroy_root(struct kernfs_root *root) { } 280 281static inline struct kernfs_node * 282kernfs_create_dir_ns(struct kernfs_node *parent, const char *name, 283 umode_t mode, void *priv, const void *ns) 284{ return ERR_PTR(-ENOSYS); } 285 286static inline struct kernfs_node * 287__kernfs_create_file(struct kernfs_node *parent, const char *name, 288 umode_t mode, loff_t size, const struct kernfs_ops *ops, 289 void *priv, const void *ns, bool name_is_static, 290 struct lock_class_key *key) 291{ return ERR_PTR(-ENOSYS); } 292 293static inline struct kernfs_node * 294kernfs_create_link(struct kernfs_node *parent, const char *name, 295 struct kernfs_node *target) 296{ return ERR_PTR(-ENOSYS); } 297 298static inline void kernfs_remove(struct kernfs_node *kn) { } 299 300static inline int kernfs_remove_by_name_ns(struct kernfs_node *kn, 301 const char *name, const void *ns) 302{ return -ENOSYS; } 303 304static inline int kernfs_rename_ns(struct kernfs_node *kn, 305 struct kernfs_node *new_parent, 306 const char *new_name, const void *new_ns) 307{ return -ENOSYS; } 308 309static inline int kernfs_setattr(struct kernfs_node *kn, 310 const struct iattr *iattr) 311{ return -ENOSYS; } 312 313static inline void kernfs_notify(struct kernfs_node *kn) { } 314 315static inline const void *kernfs_super_ns(struct super_block *sb) 316{ return NULL; } 317 318static inline struct dentry * 319kernfs_mount_ns(struct file_system_type *fs_type, int flags, 320 struct kernfs_root *root, const void *ns) 321{ return ERR_PTR(-ENOSYS); } 322 323static inline void kernfs_kill_sb(struct super_block *sb) { } 324 325static inline void kernfs_init(void) { } 326 327#endif /* CONFIG_SYSFS */ 328 329static inline struct kernfs_node * 330kernfs_find_and_get(struct kernfs_node *kn, const char *name) 331{ 332 return kernfs_find_and_get_ns(kn, name, NULL); 333} 334 335static inline struct kernfs_node * 336kernfs_create_dir(struct kernfs_node *parent, const char *name, umode_t mode, 337 void *priv) 338{ 339 return kernfs_create_dir_ns(parent, name, mode, priv, NULL); 340} 341 342static inline struct kernfs_node * 343kernfs_create_file_ns(struct kernfs_node *parent, const char *name, 344 umode_t mode, loff_t size, const struct kernfs_ops *ops, 345 void *priv, const void *ns) 346{ 347 struct lock_class_key *key = NULL; 348 349#ifdef CONFIG_DEBUG_LOCK_ALLOC 350 key = (struct lock_class_key *)&ops->lockdep_key; 351#endif 352 return __kernfs_create_file(parent, name, mode, size, ops, priv, ns, 353 false, key); 354} 355 356static inline struct kernfs_node * 357kernfs_create_file(struct kernfs_node *parent, const char *name, umode_t mode, 358 loff_t size, const struct kernfs_ops *ops, void *priv) 359{ 360 return kernfs_create_file_ns(parent, name, mode, size, ops, priv, NULL); 361} 362 363static inline int kernfs_remove_by_name(struct kernfs_node *parent, 364 const char *name) 365{ 366 return kernfs_remove_by_name_ns(parent, name, NULL); 367} 368 369static inline struct dentry * 370kernfs_mount(struct file_system_type *fs_type, int flags, 371 struct kernfs_root *root) 372{ 373 return kernfs_mount_ns(fs_type, flags, root, NULL); 374} 375 376#endif /* __LINUX_KERNFS_H */