xref: /freebsd/sys/kern/sys_capability.c (revision d940bfec8c329dd82d8d54efebd81c8aa420503b)
1 /*-
2  * Copyright (c) 2008-2011 Robert N. M. Watson
3  * Copyright (c) 2010-2011 Jonathan Anderson
4  * Copyright (c) 2012 FreeBSD Foundation
5  * All rights reserved.
6  *
7  * This software was developed at the University of Cambridge Computer
8  * Laboratory with support from a grant from Google, Inc.
9  *
10  * Portions of this software were developed by Pawel Jakub Dawidek under
11  * sponsorship from the FreeBSD Foundation.
12  *
13  * Redistribution and use in source and binary forms, with or without
14  * modification, are permitted provided that the following conditions
15  * are met:
16  * 1. Redistributions of source code must retain the above copyright
17  *    notice, this list of conditions and the following disclaimer.
18  * 2. Redistributions in binary form must reproduce the above copyright
19  *    notice, this list of conditions and the following disclaimer in the
20  *    documentation and/or other materials provided with the distribution.
21  *
22  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
23  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
26  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32  * SUCH DAMAGE.
33  */
34 
35 /*
36  * FreeBSD kernel capability facility.
37  *
38  * Two kernel features are implemented here: capability mode, a sandboxed mode
39  * of execution for processes, and capabilities, a refinement on file
40  * descriptors that allows fine-grained control over operations on the file
41  * descriptor.  Collectively, these allow processes to run in the style of a
42  * historic "capability system" in which they can use only resources
43  * explicitly delegated to them.  This model is enforced by restricting access
44  * to global namespaces in capability mode.
45  *
46  * Capabilities wrap other file descriptor types, binding them to a constant
47  * rights mask set when the capability is created.  New capabilities may be
48  * derived from existing capabilities, but only if they have the same or a
49  * strict subset of the rights on the original capability.
50  *
51  * System calls permitted in capability mode are defined in capabilities.conf;
52  * calls must be carefully audited for safety to ensure that they don't allow
53  * escape from a sandbox.  Some calls permit only a subset of operations in
54  * capability mode -- for example, shm_open(2) is limited to creating
55  * anonymous, rather than named, POSIX shared memory objects.
56  */
57 
58 #include <sys/cdefs.h>
59 __FBSDID("$FreeBSD$");
60 
61 #include "opt_capsicum.h"
62 #include "opt_ktrace.h"
63 
64 #include <sys/param.h>
65 #include <sys/capability.h>
66 #include <sys/file.h>
67 #include <sys/filedesc.h>
68 #include <sys/kernel.h>
69 #include <sys/limits.h>
70 #include <sys/lock.h>
71 #include <sys/mutex.h>
72 #include <sys/proc.h>
73 #include <sys/syscallsubr.h>
74 #include <sys/sysproto.h>
75 #include <sys/sysctl.h>
76 #include <sys/systm.h>
77 #include <sys/ucred.h>
78 #include <sys/uio.h>
79 #include <sys/ktrace.h>
80 
81 #include <security/audit/audit.h>
82 
83 #include <vm/uma.h>
84 #include <vm/vm.h>
85 
86 #ifdef CAPABILITY_MODE
87 
88 FEATURE(security_capability_mode, "Capsicum Capability Mode");
89 
90 /*
91  * System call to enter capability mode for the process.
92  */
93 int
94 sys_cap_enter(struct thread *td, struct cap_enter_args *uap)
95 {
96 	struct ucred *newcred, *oldcred;
97 	struct proc *p;
98 
99 	if (IN_CAPABILITY_MODE(td))
100 		return (0);
101 
102 	newcred = crget();
103 	p = td->td_proc;
104 	PROC_LOCK(p);
105 	oldcred = p->p_ucred;
106 	crcopy(newcred, oldcred);
107 	newcred->cr_flags |= CRED_FLAG_CAPMODE;
108 	p->p_ucred = newcred;
109 	PROC_UNLOCK(p);
110 	crfree(oldcred);
111 	return (0);
112 }
113 
114 /*
115  * System call to query whether the process is in capability mode.
116  */
117 int
118 sys_cap_getmode(struct thread *td, struct cap_getmode_args *uap)
119 {
120 	u_int i;
121 
122 	i = IN_CAPABILITY_MODE(td) ? 1 : 0;
123 	return (copyout(&i, uap->modep, sizeof(i)));
124 }
125 
126 #else /* !CAPABILITY_MODE */
127 
128 int
129 sys_cap_enter(struct thread *td, struct cap_enter_args *uap)
130 {
131 
132 	return (ENOSYS);
133 }
134 
135 int
136 sys_cap_getmode(struct thread *td, struct cap_getmode_args *uap)
137 {
138 
139 	return (ENOSYS);
140 }
141 
142 #endif /* CAPABILITY_MODE */
143 
144 #ifdef CAPABILITIES
145 
146 FEATURE(security_capabilities, "Capsicum Capabilities");
147 
148 MALLOC_DECLARE(M_FILECAPS);
149 
150 static inline int
151 _cap_check(cap_rights_t have, cap_rights_t need, enum ktr_cap_fail_type type)
152 {
153 
154 
155 	if ((need & ~have) != 0) {
156 #ifdef KTRACE
157 		if (KTRPOINT(curthread, KTR_CAPFAIL))
158 			ktrcapfail(type, need, have);
159 #endif
160 		return (ENOTCAPABLE);
161 	}
162 	return (0);
163 }
164 
165 /*
166  * Test whether a capability grants the requested rights.
167  */
168 int
169 cap_check(cap_rights_t have, cap_rights_t need)
170 {
171 
172 	return (_cap_check(have, need, CAPFAIL_NOTCAPABLE));
173 }
174 
175 /*
176  * Convert capability rights into VM access flags.
177  */
178 u_char
179 cap_rights_to_vmprot(cap_rights_t have)
180 {
181 	u_char maxprot;
182 
183 	maxprot = VM_PROT_NONE;
184 	if (have & CAP_MMAP_R)
185 		maxprot |= VM_PROT_READ;
186 	if (have & CAP_MMAP_W)
187 		maxprot |= VM_PROT_WRITE;
188 	if (have & CAP_MMAP_X)
189 		maxprot |= VM_PROT_EXECUTE;
190 
191 	return (maxprot);
192 }
193 
194 /*
195  * Extract rights from a capability for monitoring purposes -- not for use in
196  * any other way, as we want to keep all capability permission evaluation in
197  * this one file.
198  */
199 cap_rights_t
200 cap_rights(struct filedesc *fdp, int fd)
201 {
202 
203 	return (fdp->fd_ofiles[fd].fde_rights);
204 }
205 
206 /*
207  * System call to limit rights of the given capability.
208  */
209 int
210 sys_cap_rights_limit(struct thread *td, struct cap_rights_limit_args *uap)
211 {
212 	struct filedesc *fdp;
213 	cap_rights_t rights;
214 	int error, fd;
215 
216 	fd = uap->fd;
217 	rights = uap->rights;
218 
219 	AUDIT_ARG_FD(fd);
220 	AUDIT_ARG_RIGHTS(rights);
221 
222 	if ((rights & ~CAP_ALL) != 0)
223 		return (EINVAL);
224 
225 	fdp = td->td_proc->p_fd;
226 	FILEDESC_XLOCK(fdp);
227 	if (fget_locked(fdp, fd) == NULL) {
228 		FILEDESC_XUNLOCK(fdp);
229 		return (EBADF);
230 	}
231 	error = _cap_check(cap_rights(fdp, fd), rights, CAPFAIL_INCREASE);
232 	if (error == 0) {
233 		fdp->fd_ofiles[fd].fde_rights = rights;
234 		if ((rights & CAP_IOCTL) == 0) {
235 			free(fdp->fd_ofiles[fd].fde_ioctls, M_FILECAPS);
236 			fdp->fd_ofiles[fd].fde_ioctls = NULL;
237 			fdp->fd_ofiles[fd].fde_nioctls = 0;
238 		}
239 		if ((rights & CAP_FCNTL) == 0)
240 			fdp->fd_ofiles[fd].fde_fcntls = 0;
241 	}
242 	FILEDESC_XUNLOCK(fdp);
243 	return (error);
244 }
245 
246 /*
247  * System call to query the rights mask associated with a capability.
248  */
249 int
250 sys_cap_rights_get(struct thread *td, struct cap_rights_get_args *uap)
251 {
252 	struct filedesc *fdp;
253 	cap_rights_t rights;
254 	int fd;
255 
256 	fd = uap->fd;
257 
258 	AUDIT_ARG_FD(fd);
259 
260 	fdp = td->td_proc->p_fd;
261 	FILEDESC_SLOCK(fdp);
262 	if (fget_locked(fdp, fd) == NULL) {
263 		FILEDESC_SUNLOCK(fdp);
264 		return (EBADF);
265 	}
266 	rights = cap_rights(fdp, fd);
267 	FILEDESC_SUNLOCK(fdp);
268 	return (copyout(&rights, uap->rightsp, sizeof(*uap->rightsp)));
269 }
270 
271 /*
272  * Test whether a capability grants the given ioctl command.
273  * If descriptor doesn't have CAP_IOCTL, then ioctls list is empty and
274  * ENOTCAPABLE will be returned.
275  */
276 int
277 cap_ioctl_check(struct filedesc *fdp, int fd, u_long cmd)
278 {
279 	u_long *cmds;
280 	ssize_t ncmds;
281 	long i;
282 
283 	FILEDESC_LOCK_ASSERT(fdp);
284 	KASSERT(fd >= 0 && fd < fdp->fd_nfiles,
285 	    ("%s: invalid fd=%d", __func__, fd));
286 
287 	ncmds = fdp->fd_ofiles[fd].fde_nioctls;
288 	if (ncmds == -1)
289 		return (0);
290 
291 	cmds = fdp->fd_ofiles[fd].fde_ioctls;
292 	for (i = 0; i < ncmds; i++) {
293 		if (cmds[i] == cmd)
294 			return (0);
295 	}
296 
297 	return (ENOTCAPABLE);
298 }
299 
300 /*
301  * Check if the current ioctls list can be replaced by the new one.
302  */
303 static int
304 cap_ioctl_limit_check(struct filedesc *fdp, int fd, const u_long *cmds,
305     size_t ncmds)
306 {
307 	u_long *ocmds;
308 	ssize_t oncmds;
309 	u_long i;
310 	long j;
311 
312 	oncmds = fdp->fd_ofiles[fd].fde_nioctls;
313 	if (oncmds == -1)
314 		return (0);
315 	if (oncmds < (ssize_t)ncmds)
316 		return (ENOTCAPABLE);
317 
318 	ocmds = fdp->fd_ofiles[fd].fde_ioctls;
319 	for (i = 0; i < ncmds; i++) {
320 		for (j = 0; j < oncmds; j++) {
321 			if (cmds[i] == ocmds[j])
322 				break;
323 		}
324 		if (j == oncmds)
325 			return (ENOTCAPABLE);
326 	}
327 
328 	return (0);
329 }
330 
331 int
332 kern_cap_ioctls_limit(struct thread *td, int fd, u_long *cmds, size_t ncmds)
333 {
334 	struct filedesc *fdp;
335 	u_long *ocmds;
336 	int error;
337 
338 	AUDIT_ARG_FD(fd);
339 
340 	fdp = td->td_proc->p_fd;
341 	FILEDESC_XLOCK(fdp);
342 
343 	if (fget_locked(fdp, fd) == NULL) {
344 		error = EBADF;
345 		goto out;
346 	}
347 
348 	error = cap_ioctl_limit_check(fdp, fd, cmds, ncmds);
349 	if (error != 0)
350 		goto out;
351 
352 	ocmds = fdp->fd_ofiles[fd].fde_ioctls;
353 	fdp->fd_ofiles[fd].fde_ioctls = cmds;
354 	fdp->fd_ofiles[fd].fde_nioctls = ncmds;
355 
356 	cmds = ocmds;
357 	error = 0;
358 out:
359 	FILEDESC_XUNLOCK(fdp);
360 	free(cmds, M_FILECAPS);
361 	return (error);
362 }
363 
364 int
365 sys_cap_ioctls_limit(struct thread *td, struct cap_ioctls_limit_args *uap)
366 {
367 	u_long *cmds;
368 	size_t ncmds;
369 	int error;
370 
371 	ncmds = uap->ncmds;
372 
373 	if (ncmds > 256)	/* XXX: Is 256 sane? */
374 		return (EINVAL);
375 
376 	if (ncmds == 0) {
377 		cmds = NULL;
378 	} else {
379 		cmds = malloc(sizeof(cmds[0]) * ncmds, M_FILECAPS, M_WAITOK);
380 		error = copyin(uap->cmds, cmds, sizeof(cmds[0]) * ncmds);
381 		if (error != 0) {
382 			free(cmds, M_FILECAPS);
383 			return (error);
384 		}
385 	}
386 
387 	return (kern_cap_ioctls_limit(td, uap->fd, cmds, ncmds));
388 }
389 
390 int
391 sys_cap_ioctls_get(struct thread *td, struct cap_ioctls_get_args *uap)
392 {
393 	struct filedesc *fdp;
394 	struct filedescent *fdep;
395 	u_long *cmds;
396 	size_t maxcmds;
397 	int error, fd;
398 
399 	fd = uap->fd;
400 	cmds = uap->cmds;
401 	maxcmds = uap->maxcmds;
402 
403 	AUDIT_ARG_FD(fd);
404 
405 	fdp = td->td_proc->p_fd;
406 	FILEDESC_SLOCK(fdp);
407 
408 	if (fget_locked(fdp, fd) == NULL) {
409 		error = EBADF;
410 		goto out;
411 	}
412 
413 	/*
414 	 * If all ioctls are allowed (fde_nioctls == -1 && fde_ioctls == NULL)
415 	 * the only sane thing we can do is to not populate the given array and
416 	 * return CAP_IOCTLS_ALL.
417 	 */
418 
419 	fdep = &fdp->fd_ofiles[fd];
420 	if (cmds != NULL && fdep->fde_ioctls != NULL) {
421 		error = copyout(fdep->fde_ioctls, cmds,
422 		    sizeof(cmds[0]) * MIN(fdep->fde_nioctls, maxcmds));
423 		if (error != 0)
424 			goto out;
425 	}
426 	if (fdep->fde_nioctls == -1)
427 		td->td_retval[0] = CAP_IOCTLS_ALL;
428 	else
429 		td->td_retval[0] = fdep->fde_nioctls;
430 
431 	error = 0;
432 out:
433 	FILEDESC_SUNLOCK(fdp);
434 	return (error);
435 }
436 
437 /*
438  * Test whether a capability grants the given fcntl command.
439  */
440 int
441 cap_fcntl_check(struct filedesc *fdp, int fd, int cmd)
442 {
443 	uint32_t fcntlcap;
444 
445 	KASSERT(fd >= 0 && fd < fdp->fd_nfiles,
446 	    ("%s: invalid fd=%d", __func__, fd));
447 
448 	fcntlcap = (1 << cmd);
449 	KASSERT((CAP_FCNTL_ALL & fcntlcap) != 0,
450 	    ("Unsupported fcntl=%d.", cmd));
451 
452 	if ((fdp->fd_ofiles[fd].fde_fcntls & fcntlcap) != 0)
453 		return (0);
454 
455 	return (ENOTCAPABLE);
456 }
457 
458 int
459 sys_cap_fcntls_limit(struct thread *td, struct cap_fcntls_limit_args *uap)
460 {
461 	struct filedesc *fdp;
462 	uint32_t fcntlrights;
463 	int fd;
464 
465 	fd = uap->fd;
466 	fcntlrights = uap->fcntlrights;
467 
468 	AUDIT_ARG_FD(fd);
469 	AUDIT_ARG_FCNTL_RIGHTS(fcntlrights);
470 
471 	if ((fcntlrights & ~CAP_FCNTL_ALL) != 0)
472 		return (EINVAL);
473 
474 	fdp = td->td_proc->p_fd;
475 	FILEDESC_XLOCK(fdp);
476 
477 	if (fget_locked(fdp, fd) == NULL) {
478 		FILEDESC_XUNLOCK(fdp);
479 		return (EBADF);
480 	}
481 
482 	if ((fcntlrights & ~fdp->fd_ofiles[fd].fde_fcntls) != 0) {
483 		FILEDESC_XUNLOCK(fdp);
484 		return (ENOTCAPABLE);
485 	}
486 
487 	fdp->fd_ofiles[fd].fde_fcntls = fcntlrights;
488 	FILEDESC_XUNLOCK(fdp);
489 
490 	return (0);
491 }
492 
493 int
494 sys_cap_fcntls_get(struct thread *td, struct cap_fcntls_get_args *uap)
495 {
496 	struct filedesc *fdp;
497 	uint32_t rights;
498 	int fd;
499 
500 	fd = uap->fd;
501 
502 	AUDIT_ARG_FD(fd);
503 
504 	fdp = td->td_proc->p_fd;
505 	FILEDESC_SLOCK(fdp);
506 	if (fget_locked(fdp, fd) == NULL) {
507 		FILEDESC_SUNLOCK(fdp);
508 		return (EBADF);
509 	}
510 	rights = fdp->fd_ofiles[fd].fde_fcntls;
511 	FILEDESC_SUNLOCK(fdp);
512 
513 	return (copyout(&rights, uap->fcntlrightsp, sizeof(rights)));
514 }
515 
516 /*
517  * For backward compatibility.
518  */
519 int
520 sys_cap_new(struct thread *td, struct cap_new_args *uap)
521 {
522 	struct filedesc *fdp;
523 	cap_rights_t rights;
524 	register_t newfd;
525 	int error, fd;
526 
527 	fd = uap->fd;
528 	rights = uap->rights;
529 
530 	AUDIT_ARG_FD(fd);
531 	AUDIT_ARG_RIGHTS(rights);
532 
533 	if ((rights & ~CAP_ALL) != 0)
534 		return (EINVAL);
535 
536 	fdp = td->td_proc->p_fd;
537 	FILEDESC_SLOCK(fdp);
538 	if (fget_locked(fdp, fd) == NULL) {
539 		FILEDESC_SUNLOCK(fdp);
540 		return (EBADF);
541 	}
542 	error = _cap_check(cap_rights(fdp, fd), rights, CAPFAIL_INCREASE);
543 	FILEDESC_SUNLOCK(fdp);
544 	if (error != 0)
545 		return (error);
546 
547 	error = do_dup(td, 0, fd, 0, &newfd);
548 	if (error != 0)
549 		return (error);
550 
551 	FILEDESC_XLOCK(fdp);
552 	/*
553 	 * We don't really care about the race between checking capability
554 	 * rights for the source descriptor and now. If capability rights
555 	 * were ok at that earlier point, the process had this descriptor
556 	 * with those rights, so we don't increase them in security sense,
557 	 * the process might have done the cap_new(2) a bit earlier to get
558 	 * the same effect.
559 	 */
560 	fdp->fd_ofiles[newfd].fde_rights = rights;
561 	if ((rights & CAP_IOCTL) == 0) {
562 		free(fdp->fd_ofiles[newfd].fde_ioctls, M_FILECAPS);
563 		fdp->fd_ofiles[newfd].fde_ioctls = NULL;
564 		fdp->fd_ofiles[newfd].fde_nioctls = 0;
565 	}
566 	if ((rights & CAP_FCNTL) == 0)
567 		fdp->fd_ofiles[newfd].fde_fcntls = 0;
568 	FILEDESC_XUNLOCK(fdp);
569 
570 	td->td_retval[0] = newfd;
571 
572 	return (0);
573 }
574 
575 #else /* !CAPABILITIES */
576 
577 /*
578  * Stub Capability functions for when options CAPABILITIES isn't compiled
579  * into the kernel.
580  */
581 
582 int
583 sys_cap_rights_limit(struct thread *td, struct cap_rights_limit_args *uap)
584 {
585 
586 	return (ENOSYS);
587 }
588 
589 int
590 sys_cap_rights_get(struct thread *td, struct cap_rights_get_args *uap)
591 {
592 
593 	return (ENOSYS);
594 }
595 
596 int
597 sys_cap_ioctls_limit(struct thread *td, struct cap_ioctls_limit_args *uap)
598 {
599 
600 	return (ENOSYS);
601 }
602 
603 int
604 sys_cap_ioctls_get(struct thread *td, struct cap_ioctls_get_args *uap)
605 {
606 
607 	return (ENOSYS);
608 }
609 
610 int
611 sys_cap_fcntls_limit(struct thread *td, struct cap_fcntls_limit_args *uap)
612 {
613 
614 	return (ENOSYS);
615 }
616 
617 int
618 sys_cap_fcntls_get(struct thread *td, struct cap_fcntls_get_args *uap)
619 {
620 
621 	return (ENOSYS);
622 }
623 
624 int
625 sys_cap_new(struct thread *td, struct cap_new_args *uap)
626 {
627 
628 	return (ENOSYS);
629 }
630 
631 #endif /* CAPABILITIES */
632