Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 31 Jul 2015 10:21:59 +0000 (UTC)
From:      Ed Schouten <ed@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r286122 - in head/sys: compat/cloudabi compat/linux kern sys
Message-ID:  <201507311021.t6VALx1J056150@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: ed
Date: Fri Jul 31 10:21:58 2015
New Revision: 286122
URL: https://svnweb.freebsd.org/changeset/base/286122

Log:
  Limit rights on process descriptors.
  
  On CloudABI, the rights bits returned by cap_rights_get() match up with
  the operations that you can actually perform on the file descriptor.
  
  Limiting the rights is good, because it makes it easier to get uniform
  behaviour across different operating systems. If process descriptors on
  FreeBSD would suddenly gain support for any new file operation, this
  wouldn't become exposed to CloudABI processes without first extending
  the rights.
  
  Extend fork1() to gain a 'struct filecaps' argument that allows you to
  construct process descriptors with custom rights. Use this in
  cloudabi_sys_proc_fork() to limit the rights to just fstat() and
  pdwait().
  
  Obtained from:	https://github.com/NuxiNL/freebsd

Modified:
  head/sys/compat/cloudabi/cloudabi_proc.c
  head/sys/compat/linux/linux_fork.c
  head/sys/kern/init_main.c
  head/sys/kern/kern_fork.c
  head/sys/kern/kern_kthread.c
  head/sys/sys/proc.h

Modified: head/sys/compat/cloudabi/cloudabi_proc.c
==============================================================================
--- head/sys/compat/cloudabi/cloudabi_proc.c	Fri Jul 31 10:00:45 2015	(r286121)
+++ head/sys/compat/cloudabi/cloudabi_proc.c	Fri Jul 31 10:21:58 2015	(r286122)
@@ -27,6 +27,8 @@
 __FBSDID("$FreeBSD$");
 
 #include <sys/param.h>
+#include <sys/capsicum.h>
+#include <sys/filedesc.h>
 #include <sys/imgact.h>
 #include <sys/lock.h>
 #include <sys/mutex.h>
@@ -67,10 +69,12 @@ int
 cloudabi_sys_proc_fork(struct thread *td,
     struct cloudabi_sys_proc_fork_args *uap)
 {
+	struct filecaps fcaps = {};
 	struct proc *p2;
 	int error, fd;
 
-	error = fork1(td, RFFDG | RFPROC | RFPROCDESC, 0, &p2, &fd, 0);
+	cap_rights_init(&fcaps.fc_rights, CAP_FSTAT, CAP_PDWAIT);
+	error = fork1(td, RFFDG | RFPROC | RFPROCDESC, 0, &p2, &fd, 0, &fcaps);
 	if (error != 0)
 		return (error);
 	/* Return the file descriptor to the parent process. */

Modified: head/sys/compat/linux/linux_fork.c
==============================================================================
--- head/sys/compat/linux/linux_fork.c	Fri Jul 31 10:00:45 2015	(r286121)
+++ head/sys/compat/linux/linux_fork.c	Fri Jul 31 10:21:58 2015	(r286122)
@@ -73,8 +73,8 @@ linux_fork(struct thread *td, struct lin
 		printf(ARGS(fork, ""));
 #endif
 
-	if ((error = fork1(td, RFFDG | RFPROC | RFSTOPPED, 0, &p2, NULL, 0))
-	    != 0)
+	if ((error = fork1(td, RFFDG | RFPROC | RFSTOPPED, 0, &p2, NULL, 0,
+	    NULL)) != 0)
 		return (error);
 
 	td2 = FIRST_THREAD_IN_PROC(p2);
@@ -108,7 +108,7 @@ linux_vfork(struct thread *td, struct li
 
 	/* Exclude RFPPWAIT */
 	if ((error = fork1(td, RFFDG | RFPROC | RFMEM | RFSTOPPED, 0, &p2,
-	    NULL, 0)) != 0)
+	    NULL, 0, NULL)) != 0)
 		return (error);
 
 
@@ -179,7 +179,7 @@ linux_clone_proc(struct thread *td, stru
 		if (args->parent_tidptr == NULL)
 			return (EINVAL);
 
-	error = fork1(td, ff, 0, &p2, NULL, 0);
+	error = fork1(td, ff, 0, &p2, NULL, 0, NULL);
 	if (error)
 		return (error);
 

Modified: head/sys/kern/init_main.c
==============================================================================
--- head/sys/kern/init_main.c	Fri Jul 31 10:00:45 2015	(r286121)
+++ head/sys/kern/init_main.c	Fri Jul 31 10:21:58 2015	(r286122)
@@ -831,7 +831,7 @@ create_init(const void *udata __unused)
 	int error;
 
 	error = fork1(&thread0, RFFDG | RFPROC | RFSTOPPED, 0, &initproc,
-	    NULL, 0);
+	    NULL, 0, NULL);
 	if (error)
 		panic("cannot fork init: %d\n", error);
 	KASSERT(initproc->p_pid == 1, ("create_init: initproc->p_pid != 1"));

Modified: head/sys/kern/kern_fork.c
==============================================================================
--- head/sys/kern/kern_fork.c	Fri Jul 31 10:00:45 2015	(r286121)
+++ head/sys/kern/kern_fork.c	Fri Jul 31 10:21:58 2015	(r286122)
@@ -104,7 +104,7 @@ sys_fork(struct thread *td, struct fork_
 	int error;
 	struct proc *p2;
 
-	error = fork1(td, RFFDG | RFPROC, 0, &p2, NULL, 0);
+	error = fork1(td, RFFDG | RFPROC, 0, &p2, NULL, 0, NULL);
 	if (error == 0) {
 		td->td_retval[0] = p2->p_pid;
 		td->td_retval[1] = 0;
@@ -127,7 +127,7 @@ sys_pdfork(td, uap)
 	 * itself from the parent using the return value.
 	 */
 	error = fork1(td, RFFDG | RFPROC | RFPROCDESC, 0, &p2,
-	    &fd, uap->flags);
+	    &fd, uap->flags, NULL);
 	if (error == 0) {
 		td->td_retval[0] = p2->p_pid;
 		td->td_retval[1] = 0;
@@ -144,7 +144,7 @@ sys_vfork(struct thread *td, struct vfor
 	struct proc *p2;
 
 	flags = RFFDG | RFPROC | RFPPWAIT | RFMEM;
-	error = fork1(td, flags, 0, &p2, NULL, 0);
+	error = fork1(td, flags, 0, &p2, NULL, 0, NULL);
 	if (error == 0) {
 		td->td_retval[0] = p2->p_pid;
 		td->td_retval[1] = 0;
@@ -163,7 +163,7 @@ sys_rfork(struct thread *td, struct rfor
 		return (EINVAL);
 
 	AUDIT_ARG_FFLAGS(uap->flags);
-	error = fork1(td, uap->flags, 0, &p2, NULL, 0);
+	error = fork1(td, uap->flags, 0, &p2, NULL, 0, NULL);
 	if (error == 0) {
 		td->td_retval[0] = p2 ? p2->p_pid : 0;
 		td->td_retval[1] = 0;
@@ -768,7 +768,7 @@ do_fork(struct thread *td, int flags, st
 
 int
 fork1(struct thread *td, int flags, int pages, struct proc **procp,
-    int *procdescp, int pdflags)
+    int *procdescp, int pdflags, struct filecaps *fcaps)
 {
 	struct proc *p1;
 	struct proc *newproc;
@@ -824,7 +824,8 @@ fork1(struct thread *td, int flags, int 
 	 * later.
 	 */
 	if (flags & RFPROCDESC) {
-		error = falloc(td, &fp_procdesc, procdescp, 0);
+		error = falloc_caps(td, &fp_procdesc, procdescp, 0,
+		fcaps);
 		if (error != 0)
 			return (error);
 	}

Modified: head/sys/kern/kern_kthread.c
==============================================================================
--- head/sys/kern/kern_kthread.c	Fri Jul 31 10:00:45 2015	(r286121)
+++ head/sys/kern/kern_kthread.c	Fri Jul 31 10:21:58 2015	(r286122)
@@ -89,7 +89,7 @@ kproc_create(void (*func)(void *), void 
 		panic("kproc_create called too soon");
 
 	error = fork1(&thread0, RFMEM | RFFDG | RFPROC | RFSTOPPED | flags,
-	    pages, &p2, NULL, 0);
+	    pages, &p2, NULL, 0, NULL);
 	if (error)
 		return error;
 

Modified: head/sys/sys/proc.h
==============================================================================
--- head/sys/sys/proc.h	Fri Jul 31 10:00:45 2015	(r286121)
+++ head/sys/sys/proc.h	Fri Jul 31 10:21:58 2015	(r286122)
@@ -161,6 +161,7 @@ struct pargs {
  * for write access.
  */
 struct cpuset;
+struct filecaps;
 struct kaioinfo;
 struct kaudit_record;
 struct kdtrace_proc;
@@ -916,7 +917,8 @@ int	enterpgrp(struct proc *p, pid_t pgid
 int	enterthispgrp(struct proc *p, struct pgrp *pgrp);
 void	faultin(struct proc *p);
 void	fixjobc(struct proc *p, struct pgrp *pgrp, int entering);
-int	fork1(struct thread *, int, int, struct proc **, int *, int);
+int	fork1(struct thread *, int, int, struct proc **, int *, int,
+	    struct filecaps *);
 void	fork_exit(void (*)(void *, struct trapframe *), void *,
 	    struct trapframe *);
 void	fork_return(struct thread *, struct trapframe *);



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201507311021.t6VALx1J056150>