7acc79472bb73c35163fec10f9c319da5fb1aa4d
[dragonfly.git] / sys / sys / devfs.h
1 /*
2  * Copyright (c) 2009 The DragonFly Project.  All rights reserved.
3  *
4  * This code is derived from software contributed to The DragonFly Project
5  * by Alex Hornung <ahornung@gmail.com>
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in
15  *    the documentation and/or other materials provided with the
16  *    distribution.
17  * 3. Neither the name of The DragonFly Project nor the names of its
18  *    contributors may be used to endorse or promote products derived
19  *    from this software without specific, prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
25  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
27  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
30  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
31  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32  * SUCH DAMAGE.
33  */
34 #ifndef _SYS_DEVFS_H_
35 #define _SYS_DEVFS_H_
36
37 #if defined(_KERNEL) || defined(_KERNEL_STRUCTURES)
38
39 #ifndef _SYS_QUEUE_H_
40 #include <sys/queue.h>
41 #endif
42 #ifndef _SYS_LOCK_H_
43 #include <sys/lock.h>
44 #endif
45 #ifndef _SYS_CONF_H_
46 #include <sys/conf.h>
47 #endif
48 #ifndef _SYS_MSGPORT_H_
49 #include <sys/msgport.h>
50 #endif
51 #ifndef _SYS_DIRENT_H_
52 #include <sys/dirent.h>
53 #endif
54 #ifndef _SYS_DEVICE_H_
55 #include <sys/device.h>
56 #endif
57 #ifndef _SYS_UCRED_H_
58 #include <sys/ucred.h>
59 #endif
60
61
62 typedef enum {
63         Proot,          /* the filesystem root */
64         Plink,
65         Preg,
66         Pdir,
67         Pdev
68 } devfs_nodetype;
69
70 struct devfs_dirent {
71         ino_t           d_ino;          /* file number of entry */
72         uint16_t        d_namlen;       /* strlen(d_name) */
73         uint8_t         d_type;         /* file type */
74         char            *d_name;
75 };
76
77 struct devfs_fid {
78         uint16_t        fid_len;        /* Length of structure. */
79         uint16_t        fid_pad;        /* Force 32-bit alignment. */
80         uint32_t        fid_gen;
81         ino_t           fid_ino;        /* File number (ino). */
82 };
83
84 struct devfs_node {
85         cdev_t          d_dev;          /* device assoicated with this node */
86
87         struct mount    *mp;            /* mount point of this node */
88         struct devfs_dirent d_dir;      /* dirent data (name, inode, ...) */
89         struct vnode    *v_node;        /* assoicated vnode */
90         struct devfs_node *parent;      /* parent of this node */
91         devfs_nodetype  node_type;      /* devfs node type */
92
93         u_int64_t       refs;           /* number of open references */
94         size_t          nchildren;      /* number of children of a parent */
95         u_int64_t       cookie_jar;     /* cookie pool for children */
96         u_int64_t       cookie;         /* directory entry cookie for readdir */
97
98         struct devfs_node *link_target; /* target of this autolink-type node */
99         size_t          nlinks;         /* hard links */
100
101         char            *symlink_name;  /* symlink name for readlink */
102         size_t          symlink_namelen; /* symlink name length for readlink */
103
104         u_short         mode;           /* files access mode and type */
105         uid_t           uid;            /* owner user id */
106         gid_t           gid;            /* owner group id */
107         u_long          flags;
108
109         struct timespec atime;          /* time of last access */
110         struct timespec mtime;          /* time of last modification */
111         struct timespec ctime;          /* time file changed */
112
113         TAILQ_ENTRY(devfs_node) link;
114         TAILQ_HEAD(, devfs_node) list;  /* linked list of children */
115 };
116
117 struct devfs_orphan {
118         struct devfs_node *node;
119         TAILQ_ENTRY(devfs_orphan) link;
120 };
121
122 struct devfs_mnt_data {
123         TAILQ_HEAD(, devfs_orphan) orphan_list;
124         TAILQ_ENTRY(devfs_mnt_data) link;
125
126         struct devfs_node *root_node;
127         struct mount    *mp;
128         uint32_t        mnt_type;
129         long            leak_count;
130         long            file_count;
131         int             jailed;
132         size_t          mntonnamelen;
133 };
134
135 struct devfs_clone_handler {
136         char            *name;
137         u_char          namlen;
138         d_clone_t       *nhandler;
139         TAILQ_ENTRY(devfs_clone_handler) link;
140 };
141
142
143 struct devfs_alias {
144         char            *name;
145         size_t          namlen;
146         cdev_t          dev_target;
147         TAILQ_ENTRY(devfs_alias) link;
148 };
149
150 struct devfs_dev_ops {
151         struct dev_ops *ops;
152         int     ref_count;
153         int id;
154         TAILQ_ENTRY(devfs_dev_ops) link;
155 };
156
157 typedef struct devfs_msg {
158         struct lwkt_msg hdr;
159
160         union {
161                 struct {
162                         cdev_t  dev;
163                         uid_t   uid;
164                         gid_t   gid;
165                         int     perms;
166                 } __m_dev;
167                 struct {
168                         struct devfs_mnt_data *mnt;
169                 } __m_mnt;
170                 struct {
171                         const char      *name;
172                         d_clone_t       *nhandler;
173                 } __m_chandler;
174                 struct {
175                         void *load;
176                         void *load2;
177                 } __m_gen;
178                 struct {
179                         void *resp;
180                 } __m_resp;
181                 struct {
182                         udev_t  udev;
183                 } __m_udev;
184                 struct {
185                         cdev_t  cdev;
186                 } __m_cdev;
187                 struct {
188                         char    *name;
189                 } __m_name;
190                 struct {
191                         char    *basename;
192                         u_char  unit;
193                         struct vnode *vp;
194                 } __m_clone;
195                 struct {
196                         struct devfs_node *node;
197                 } __m_node;
198                 struct {
199                         char    *name;
200                         char    *target;
201                         struct mount *mp;
202                 } __m_link;
203                 struct {
204                         struct dev_ops *ops;
205                         int     minor;
206                 } __m_ops;
207                 struct {
208                         char    *name;
209                         uint32_t        flag;
210                 } __m_flags;
211                 struct {
212                         ino_t   ino;
213                         struct vnode *vp;
214                         struct mount *mp;
215                 } __m_ino;
216         } __m_u;
217 } *devfs_msg_t;
218
219 #define mdv_chandler    __m_u.__m_chandler
220 #define mdv_mnt         __m_u.__m_mnt.mnt
221 #define mdv_load        __m_u.__m_gen.load
222 #define mdv_load2       __m_u.__m_gen.load2
223 #define mdv_response    __m_u.__m_resp.resp
224 #define mdv_dev         __m_u.__m_dev
225 #define mdv_link        __m_u.__m_link
226 #define mdv_udev        __m_u.__m_udev.udev
227 #define mdv_cdev        __m_u.__m_cdev.cdev
228 #define mdv_name        __m_u.__m_name.name
229 #define mdv_clone       __m_u.__m_clone
230 #define mdv_node        __m_u.__m_node.node
231 #define mdv_ops         __m_u.__m_ops
232 #define mdv_flags       __m_u.__m_flags
233 #define mdv_ino         __m_u.__m_ino
234
235
236 typedef struct devfs_core_args {
237         thread_t     td;
238 } *devfs_core_args_t;
239
240 TAILQ_HEAD(devfs_node_head, devfs_node);
241 TAILQ_HEAD(devfs_dev_head, cdev);
242 TAILQ_HEAD(devfs_mnt_head, devfs_mnt_data);
243 TAILQ_HEAD(devfs_chandler_head, devfs_clone_handler);
244 TAILQ_HEAD(devfs_alias_head, devfs_alias);
245 TAILQ_HEAD(devfs_dev_ops_head, devfs_dev_ops);
246
247 typedef void (devfs_scan_t)(cdev_t, void *);
248 typedef void* (devfs_iterate_callback_t)(struct devfs_node *, void *);
249
250 #define DEVFS_NODE(x)           ((struct devfs_node *)((x)->v_data))
251 #define DEVFS_MNTDATA(x)        ((struct devfs_mnt_data *)((x)->mnt_data))
252 #define DEVFS_ORPHANLIST(x)     (&(DEVFS_MNTDATA(x)->orphan_list))
253 #define DEVFS_DENODE_HEAD(x)    (&((x)->list))
254 #define DEVFS_ISDIGIT(x)        ((x >= '0') && (x <= '9'))
255
256 /*
257  * -rwxr-xr-x
258  */
259 #define DEVFS_DEFAULT_MODE      ((VREAD|VWRITE|VEXEC) | ((VREAD|VEXEC)>>3) | \
260                                  ((VREAD|VEXEC)>>6));
261
262 #define DEVFS_DEFAULT_UID       0       /* root */
263 #define DEVFS_DEFAULT_GID       0       /* wheel */
264
265 /*
266  * debug levels
267  */
268 #define DEVFS_DEBUG_SHOW        0x00
269 #define DEVFS_DEBUG_WARNING     0x01
270 #define DEVFS_DEBUG_INFO        0x02
271 #define DEVFS_DEBUG_DEBUG       0x03
272
273 /*
274  * Message ids
275  */
276 #define DEVFS_TERMINATE_CORE            0x01
277 #define DEVFS_DEVICE_CREATE             0x02
278 #define DEVFS_DEVICE_DESTROY            0x03
279 #define DEVFS_MOUNT_ADD                 0x04
280 #define DEVFS_MOUNT_DEL                 0x05
281 #define DEVFS_CREATE_ALL_DEV            0x06
282 #define DEVFS_DESTROY_SUBNAMES          0x07
283 #define DEVFS_DESTROY_DEV_BY_OPS        0x08
284 #define DEVFS_CHANDLER_ADD              0x09
285 #define DEVFS_CHANDLER_DEL              0x0A
286 #define DEVFS_FIND_DEVICE_BY_UDEV       0x0B
287 #define DEVFS_FIND_DEVICE_BY_NAME       0x0C
288 #define DEVFS_MAKE_ALIAS                0x0D
289 #define DEVFS_APPLY_RULES               0x0F
290 #define DEVFS_RESET_RULES               0x10
291 #define DEVFS_SCAN_CALLBACK             0x11
292 #define DEVFS_CLR_SUBNAMES_FLAG         0x12
293 #define DEVFS_DESTROY_SUBNAMES_WO_FLAG  0x13
294 #define DEVFS_INODE_TO_VNODE            0x14
295 #define DEVFS_SYNC                      0x99
296
297 /*
298  * Node flags
299  *
300  * HIDDEN       Makes node inaccessible, apart from already allocated vnodes
301  * INVISIBLE    Makes node invisible in a readdir()
302  */
303 #define DEVFS_NODE_LINKED               0x001   /* Linked into topology */
304 #define DEVFS_USER_CREATED              0x002   /* Node was user-created */
305 #define DEVFS_ORPHANED                  0x004   /* on orphan list */
306 #define DEVFS_CLONED                    0x008   /* Created by cloning code */
307 #define DEVFS_HIDDEN                    0x010   /* Makes node inaccessible */
308 #define DEVFS_INVISIBLE                 0x020   /* Makes node invisible */
309 #define DEVFS_PTY                       0x040   /* PTY device */
310 #define DEVFS_DESTROYED                 0x080   /* Sanity check */
311 #define DEVFS_RULE_CREATED              0x100   /* Node was rule-created */
312 #define DEVFS_RULE_HIDDEN               0x200   /* Node was hidden by a rule */
313
314 /*
315  * Clone helper stuff
316  */
317 #define DEVFS_BITMAP_INITIAL_SIZE       1
318 #define DEVFS_CLONE_BITMAP(name)        devfs_ ## name ## _clone_bitmap
319 #define DEVFS_DECLARE_CLONE_BITMAP(name) \
320                                 struct devfs_bitmap DEVFS_CLONE_BITMAP(name)
321
322 struct devfs_bitmap {
323         int             chunks;
324         unsigned long   *bitmap;
325 };
326
327 struct devfs_unit_hash {
328         struct devfs_unit_hash *next;
329         int             unit_no;
330         cdev_t          dev;
331 };
332
333 void devfs_clone_bitmap_init(struct devfs_bitmap *);
334 void devfs_clone_bitmap_uninit(struct devfs_bitmap *);
335 void devfs_clone_bitmap_resize(struct devfs_bitmap *, int);
336 int devfs_clone_bitmap_fff(struct devfs_bitmap *);
337 void devfs_clone_bitmap_set(struct devfs_bitmap *, int);
338 int devfs_clone_bitmap_get(struct devfs_bitmap *, int);
339 int devfs_clone_bitmap_chk(struct devfs_bitmap *, int);
340 void devfs_clone_bitmap_put(struct devfs_bitmap *, int);
341
342 /*
343  * Prototypes
344  */
345 int devfs_debug(int level, char *fmt, ...) __printflike(2, 3);
346 int devfs_allocv(struct vnode **, struct devfs_node *);
347 struct devfs_node *devfs_allocp(devfs_nodetype, char *, struct devfs_node *,
348                                 struct mount *, cdev_t);
349 int devfs_allocvp(struct mount *, struct vnode **, devfs_nodetype, char *,
350                                 struct devfs_node *, cdev_t);
351
352 int devfs_freep(struct devfs_node *);
353
354 int devfs_unlinkp(struct devfs_node *);
355
356 void devfs_tracer_add_orphan(struct devfs_node *);
357 void devfs_tracer_del_orphan(struct devfs_node *);
358 size_t devfs_tracer_orphan_count(struct mount *, int);
359
360 int devfs_set_perms(struct devfs_node *, uid_t, gid_t, u_short, u_long);
361 int devfs_gc(struct devfs_node *);
362
363 int devfs_create_dev(cdev_t, uid_t, gid_t, int);
364 int devfs_destroy_dev(cdev_t);
365
366 devfs_msg_t devfs_msg_send_sync(uint32_t, devfs_msg_t);
367 void devfs_msg_send(uint32_t, devfs_msg_t);
368 void devfs_msg_send_dev(uint32_t, cdev_t dev, uid_t, gid_t, int);
369 void devfs_msg_send_mount(uint32_t, struct devfs_mnt_data *);
370 void devfs_msg_send_ops(uint32_t, struct dev_ops *, int);
371 void devfs_msg_send_chandler(uint32_t, char *, d_clone_t);
372 void devfs_msg_send_generic(uint32_t, void *);
373 void devfs_msg_send_name(uint32_t, char *);
374 void devfs_msg_send_link(uint32_t, char *, char *, struct mount *);
375
376 devfs_msg_t devfs_msg_get(void);
377 int devfs_msg_put(devfs_msg_t);
378
379 int devfs_mount_add(struct devfs_mnt_data *);
380 int devfs_mount_del(struct devfs_mnt_data *);
381
382 int devfs_create_all_dev(struct devfs_node *);
383
384 struct devfs_node *devfs_resolve_or_create_path(
385                                 struct devfs_node *, char *, int);
386 int devfs_resolve_name_path(char *, char *, char **, char **);
387 struct devfs_node *devfs_create_device_node(struct devfs_node *, cdev_t,
388                       char *, char *, ...) __printf0like(4, 5);
389
390 int devfs_destroy_device_node(struct devfs_node *, cdev_t);
391 int devfs_destroy_subnames(char *);
392 int devfs_destroy_dev_by_ops(struct dev_ops *, int);
393 struct devfs_node *devfs_find_device_node_by_name(struct devfs_node *, char *);
394
395 cdev_t devfs_new_cdev(struct dev_ops *, int, struct dev_ops *);
396 void devfs_assume_knotes(cdev_t dev, struct kqinfo *kqi);
397
398 cdev_t devfs_find_device_by_name(const char *, ...) __printflike(1, 2);
399 cdev_t devfs_find_device_by_udev(udev_t);
400
401 struct vnode *devfs_inode_to_vnode(struct mount *, ino_t);
402
403 int devfs_clone_handler_add(const char *, d_clone_t *);
404 int devfs_clone_handler_del(const char *);
405 cdev_t devfs_clone(cdev_t, const char *, size_t, int, struct ucred *);
406
407 int devfs_link_dev(cdev_t);
408
409 int devfs_make_alias(const char *, cdev_t);
410
411 int devfs_alias_create(char *, struct devfs_node *, int);
412
413 int devfs_apply_rules(char *);
414 int devfs_reset_rules(char *);
415
416 int devfs_scan_callback(devfs_scan_t *, void *);
417
418 int devfs_clr_subnames_flag(char *, uint32_t);
419 int devfs_destroy_subnames_without_flag(char *, uint32_t);
420 int devfs_node_is_accessible(struct devfs_node *);
421
422 int devfs_reference_ops(struct dev_ops *);
423 void devfs_release_ops(struct dev_ops *);
424
425 void devfs_config(void);
426
427 void *devfs_iterate_topology(struct devfs_node *node,
428                 devfs_iterate_callback_t *callback, void *arg1);
429
430 void *devfs_find_device_node_callback(struct devfs_node *, cdev_t);
431
432 #endif /* KERNEL */
433
434 #define DEVFS_MNT_RULESET       0x01
435 #define DEVFS_MNT_JAIL          0x02
436
437 struct devfs_mount_info {
438         int flags;
439 };
440
441 #endif /* _SYS_DEVFS_H_ */