xref: /dragonfly/sys/sys/caps.h (revision 0ac6bf9d)
1 /*
2  * SYS/CAPS.H
3  *
4  *	Implements an architecture independant Capability Service API
5  *
6  * $DragonFly: src/sys/sys/caps.h,v 1.9 2006/05/20 02:42:13 dillon Exp $
7  */
8 
9 #ifndef _SYS_CAPS_H_
10 #define _SYS_CAPS_H_
11 
12 #ifndef _SYS_TYPES_H_
13 #include <sys/types.h>
14 #endif
15 #ifndef _SYS_MSGPORT_H_
16 #include <sys/msgport.h>
17 #endif
18 #ifndef _SYS_XIO_H_
19 #include <sys/xio.h>
20 #endif
21 
22 typedef enum caps_msg_state {
23 	CAPMS_REQUEST,
24 	CAPMS_REQUEST_RETRY, 	/* internal / FUTURE */
25 	CAPMS_REPLY,
26 	CAPMS_REPLY_RETRY,	/* internal / FUTURE */
27 	CAPMS_DISPOSE
28 } caps_msg_state_t;
29 
30 typedef struct caps_msgid {
31 	off_t			c_id;
32 	caps_msg_state_t	c_state;
33 	int			c_reserved01;
34 } *caps_msgid_t;
35 
36 typedef enum caps_type {
37 	CAPT_UNKNOWN, CAPT_CLIENT, CAPT_SERVICE, CAPT_REMOTE, CAPT_FORKED
38 } caps_type_t;
39 
40 typedef int64_t	caps_gen_t;
41 
42 /*
43  * Note: upper 16 bits reserved for kernel use
44  */
45 #define CAPF_UFLAGS	0xFFFF
46 #define CAPF_USER	0x0001
47 #define CAPF_GROUP	0x0002
48 #define CAPF_WORLD	0x0004
49 #define CAPF_EXCL	0x0008
50 #define CAPF_ANYCLIENT	(CAPF_USER|CAPF_GROUP|CAPF_WORLD)
51 #define CAPF_WCRED	0x0010	/* waiting for cred */
52 #define CAPF_NOFORK	0x0020	/* do not create a dummy entry on fork */
53 #define CAPF_WAITSVC	0x0040	/* block if service not available */
54 /* FUTURE: CAPF_ASYNC - support async services */
55 /* FUTURE: CAPF_NOGROUPS - don't bother filling in the groups[] array */
56 /* FUTURE: CAPF_TERM - send termination request to existing service */
57 /* FUTURE: CAPF_TAKE - take over existing service's connections */
58 /* FUTURE: CAPF_DISPOSE_IMM - need immediate dispose wakeups */
59 
60 /*
61  * Abort codes
62  */
63 #define CAPS_ABORT_NOTIMPL	0	/* abort not implemented, no action */
64 #define CAPS_ABORT_RETURNED	1	/* already returned, no action */
65 #define CAPS_ABORT_BEFORESERVER	2	/* caught before the server got it */
66 #define CAPS_ABORT_ATSERVER	3	/* server had retrieved message */
67 
68 #define CAPF_ABORT_HARD		0x0001	/* rip out from under server (3) */
69 
70 #define CAPS_MAXGROUPS	16
71 #define CAPS_MAXNAMELEN	64
72 #define CAPS_MAXINPROG	128
73 
74 struct thread;
75 
76 typedef struct caps_port {
77 	struct lwkt_port	cp_lport;
78 	int			cp_portid;	/* caps port id */
79 	int			cp_upcallid;	/* upcall id */
80 } *caps_port_t;
81 
82 typedef struct caps_cred {
83 	pid_t			pid;
84 	uid_t			uid;
85 	uid_t			euid;
86 	gid_t			gid;
87 	int			ngroups;
88 	int			cacheid;
89 	gid_t			groups[CAPS_MAXGROUPS];
90 } *caps_cred_t;
91 
92 #if defined(_KERNEL) || defined(_KERNEL_STRUCTURES)
93 
94 struct proc;
95 struct caps_kmsg;
96 
97 TAILQ_HEAD(caps_kmsg_queue, caps_kmsg);
98 
99 /*
100  * caps_kinfo -	Holds a client or service registration
101  *
102  * ci_msgpendq: holds the kernel copy of the message after it has been
103  * 		sent to the local port.  The message is matched up against
104  *		replies and automatically replied if the owner closes its
105  *		connection.
106  */
107 typedef struct caps_kinfo {
108 	struct lwkt_port	ci_lport;	/* embedded local port */
109 	struct caps_kinfo	*ci_tdnext;	/* per-process list */
110 	struct caps_kinfo	*ci_hnext;	/* registration hash table */
111 	struct thread		*ci_td;		/* owner */
112 	struct caps_kmsg_queue	ci_msgpendq;	/* pending reply (just rcvd) */
113 	struct caps_kmsg_queue	ci_msguserq;	/* pending reply (user holds) */
114 	struct caps_kinfo	*ci_rcaps;	/* connected to remote */
115 	int			ci_cmsgcount;	/* client in-progress msgs */
116 	int			ci_id;
117 	int			ci_flags;
118 	int			ci_refs;
119 	caps_type_t		ci_type;
120 	caps_gen_t		ci_gen;
121 	uid_t			ci_uid;
122 	gid_t			ci_gid;
123 	int			ci_namelen;
124 	char			ci_name[4];	/* variable length */
125 	/* ci_name must be last element */
126 } *caps_kinfo_t;
127 
128 /* note: user flags are held in the low 16 bits */
129 #define CAPKF_TDLIST	0x00010000
130 #define CAPKF_HLIST	0x00020000
131 #define CAPKF_FLUSH	0x00040000
132 #define CAPKF_RCAPS	0x00080000
133 #define CAPKF_CLOSED	0x00100000
134 #define CAPKF_MWAIT	0x00200000
135 
136 /*
137  * Kernel caps message.  The kernel keepps track of messagse received,
138  * undergoing processing by the service, and returned.  User-supplied data
139  * is copied on reception rather then transmission.
140  */
141 typedef struct caps_kmsg {
142 	TAILQ_ENTRY(caps_kmsg)	km_node;
143 	caps_kinfo_t		km_mcaps;	/* message sender */
144 	struct xio		km_xio;		/* mcaps user data */
145 	struct caps_cred	km_ccr;		/* caps cred for msg */
146 	struct caps_msgid	km_msgid;
147 	int			km_flags;
148 } *caps_kmsg_t;
149 
150 #define km_state	km_msgid.c_state
151 
152 #define CAPKMF_ONUSERQ		0x0001
153 #define CAPKMF_ONPENDQ		0x0002
154 #define CAPKMF_REPLY		0x0004
155 #define CAPKMF_CDONE		0x0008
156 #define CAPKMF_PEEKED		0x0010
157 #define CAPKMF_ABORTED		0x0020
158 
159 #endif
160 
161 #ifdef _KERNEL
162 
163 /*
164  * kernel support
165  */
166 void caps_exit(struct thread *td);
167 void caps_fork(struct proc *p1, struct proc *p2, int flags);
168 
169 #else
170 
171 /*
172  * Userland API (libcaps)
173  */
174 caps_port_t caps_service(const char *, uid_t, gid_t, mode_t, int);
175 caps_port_t caps_client(const char *, uid_t, gid_t, int);
176 
177 /*
178  * Syscall API
179  */
180 int caps_sys_service(const char *, uid_t, gid_t, int, int);
181 int caps_sys_client(const char *, uid_t, gid_t, int, int);
182 off_t caps_sys_put(int, void *, int);
183 int caps_sys_reply(int, void *, int, off_t);
184 int caps_sys_get(int, void *, int, caps_msgid_t, caps_cred_t);
185 int caps_sys_wait(int, void *, int, caps_msgid_t, caps_cred_t);
186 int caps_sys_abort(int, off_t, int);
187 int caps_sys_setgen(int, caps_gen_t);
188 caps_gen_t caps_sys_getgen(int);
189 int caps_sys_close(int);
190 
191 #endif
192 
193 #endif
194 
195