Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys Implement rump_lwproc: the new lwp/proc management routi...
details: https://anonhg.NetBSD.org/src/rev/7c77d3cd89d6
branches: trunk
changeset: 757513:7c77d3cd89d6
user: pooka <pooka%NetBSD.org@localhost>
date: Wed Sep 01 19:37:58 2010 +0000
description:
Implement rump_lwproc: the new lwp/proc management routines for
rump. These move the management of the pid/lwpid space from the
application into the kernel, make code more robust, and make it
possible to attach multiple lwp's to non-proc0 processes.
diffstat:
sys/rump/librump/rumpkern/Makefile.rumpkern | 8 +-
sys/rump/librump/rumpkern/emul.c | 23 +-
sys/rump/librump/rumpkern/lwproc.c | 339 ++++++++++++++++++++++++++++
sys/rump/librump/rumpkern/rump.c | 188 +-------------
sys/rump/librump/rumpkern/rump_private.h | 6 +-
sys/rump/librump/rumpkern/scheduler.c | 106 +++++---
sys/rump/librump/rumpkern/sysproxy_socket.c | 10 +-
sys/rump/librump/rumpkern/threads.c | 8 +-
sys/sys/lwp.h | 3 +-
9 files changed, 463 insertions(+), 228 deletions(-)
diffs (truncated from 911 to 300 lines):
diff -r 8b99667471e3 -r 7c77d3cd89d6 sys/rump/librump/rumpkern/Makefile.rumpkern
--- a/sys/rump/librump/rumpkern/Makefile.rumpkern Wed Sep 01 19:33:04 2010 +0000
+++ b/sys/rump/librump/rumpkern/Makefile.rumpkern Wed Sep 01 19:37:58 2010 +0000
@@ -1,4 +1,4 @@
-# $NetBSD: Makefile.rumpkern,v 1.95 2010/08/30 09:44:40 pooka Exp $
+# $NetBSD: Makefile.rumpkern,v 1.96 2010/09/01 19:37:58 pooka Exp $
#
.include "${RUMPTOP}/Makefile.rump"
@@ -15,9 +15,9 @@
#
# Source modules, first the ones specifically implemented for librump.
#
-SRCS= rump.c rumpcopy.c emul.c intr.c klock.c kobj_rename.c \
- ltsleep.c memalloc.c scheduler.c signals.c sleepq.c \
- sysproxy_socket.c threads.c vm.c
+SRCS= rump.c rumpcopy.c emul.c intr.c lwproc.c klock.c \
+ kobj_rename.c ltsleep.c memalloc.c scheduler.c \
+ signals.c sleepq.c sysproxy_socket.c threads.c vm.c
SRCS+= compat.c
# Multiprocessor or uniprocessor locking. TODO: select right
diff -r 8b99667471e3 -r 7c77d3cd89d6 sys/rump/librump/rumpkern/emul.c
--- a/sys/rump/librump/rumpkern/emul.c Wed Sep 01 19:33:04 2010 +0000
+++ b/sys/rump/librump/rumpkern/emul.c Wed Sep 01 19:37:58 2010 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: emul.c,v 1.144 2010/06/23 08:36:03 pooka Exp $ */
+/* $NetBSD: emul.c,v 1.145 2010/09/01 19:37:58 pooka Exp $ */
/*
* Copyright (c) 2007 Antti Kantee. All Rights Reserved.
@@ -28,7 +28,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: emul.c,v 1.144 2010/06/23 08:36:03 pooka Exp $");
+__KERNEL_RCSID(0, "$NetBSD: emul.c,v 1.145 2010/09/01 19:37:58 pooka Exp $");
#include <sys/param.h>
#include <sys/null.h>
@@ -158,6 +158,25 @@
(*l->l_syncobj->sobj_unsleep)(l, cleanup);
}
+void
+lwp_update_creds(struct lwp *l)
+{
+ struct proc *p;
+ kauth_cred_t oldcred;
+
+ p = l->l_proc;
+ oldcred = l->l_cred;
+ l->l_prflag &= ~LPR_CRMOD;
+
+ mutex_enter(p->p_lock);
+ kauth_cred_hold(p->p_cred);
+ l->l_cred = p->p_cred;
+ mutex_exit(p->p_lock);
+
+ if (oldcred != NULL)
+ kauth_cred_free(oldcred);
+}
+
vaddr_t
calc_cache_size(struct vm_map *map, int pct, int va_pct)
{
diff -r 8b99667471e3 -r 7c77d3cd89d6 sys/rump/librump/rumpkern/lwproc.c
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/sys/rump/librump/rumpkern/lwproc.c Wed Sep 01 19:37:58 2010 +0000
@@ -0,0 +1,339 @@
+/* $NetBSD: lwproc.c,v 1.1 2010/09/01 19:37:58 pooka Exp $ */
+
+/*
+ * Copyright (c) 2010 Antti Kantee. All Rights Reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+__KERNEL_RCSID(0, "$NetBSD: lwproc.c,v 1.1 2010/09/01 19:37:58 pooka Exp $");
+
+#include <sys/param.h>
+#include <sys/atomic.h>
+#include <sys/filedesc.h>
+#include <sys/kauth.h>
+#include <sys/kmem.h>
+#include <sys/lwp.h>
+#include <sys/pool.h>
+#include <sys/proc.h>
+#include <sys/queue.h>
+#include <sys/resourcevar.h>
+#include <sys/uidinfo.h>
+
+#include <rump/rumpuser.h>
+
+#include "rump_private.h"
+
+static void
+lwproc_proc_free(struct proc *p)
+{
+ kauth_cred_t cred;
+
+ mutex_enter(proc_lock);
+
+ KASSERT(p->p_nlwps == 0);
+ KASSERT(LIST_EMPTY(&p->p_lwps));
+ KASSERT(p->p_stat == SIDL || p->p_stat == SDEAD);
+
+ LIST_REMOVE(p, p_list);
+ LIST_REMOVE(p, p_sibling);
+ proc_free_pid(p->p_pid); /* decrements nprocs */
+ proc_leavepgrp(p); /* releases proc_lock */
+
+ cred = p->p_cred;
+ chgproccnt(kauth_cred_getuid(cred), -1);
+ if (rump_proc_vfs_release)
+ rump_proc_vfs_release(p);
+
+ limfree(p->p_limit);
+ pstatsfree(p->p_stats);
+ kauth_cred_free(p->p_cred);
+ proc_finispecific(p);
+
+ mutex_obj_free(p->p_lock);
+ mutex_destroy(&p->p_stmutex);
+ mutex_destroy(&p->p_auxlock);
+ rw_destroy(&p->p_reflock);
+ cv_destroy(&p->p_waitcv);
+ cv_destroy(&p->p_lwpcv);
+
+ proc_free_mem(p);
+}
+
+/*
+ * Allocate a new process. Mostly mimic fork by
+ * copying the properties of the parent. However, there are some
+ * differences. For example, we never share the fd table.
+ *
+ * Switch to the new lwp and return a pointer to it.
+ */
+static struct proc *
+lwproc_newproc(struct proc *parent)
+{
+ uid_t uid = kauth_cred_getuid(parent->p_cred);
+ struct proc *p;
+
+ /* maxproc not enforced */
+ atomic_inc_uint(&nprocs);
+
+ /* allocate process */
+ p = proc_alloc();
+ memset(&p->p_startzero, 0,
+ offsetof(struct proc, p_endzero)
+ - offsetof(struct proc, p_startzero));
+ memcpy(&p->p_startcopy, &parent->p_startcopy,
+ offsetof(struct proc, p_endcopy)
+ - offsetof(struct proc, p_startcopy));
+
+ p->p_stats = pstatscopy(parent->p_stats);
+
+ /* not based on parent */
+ p->p_vmspace = &vmspace0;
+ p->p_emul = &emul_netbsd;
+ p->p_fd = fd_init(NULL);
+ lim_addref(parent->p_limit);
+ p->p_limit = parent->p_limit;
+
+ LIST_INIT(&p->p_lwps);
+ LIST_INIT(&p->p_children);
+
+ p->p_lock = mutex_obj_alloc(MUTEX_DEFAULT, IPL_NONE);
+ mutex_init(&p->p_stmutex, MUTEX_DEFAULT, IPL_NONE);
+ mutex_init(&p->p_auxlock, MUTEX_DEFAULT, IPL_NONE);
+ rw_init(&p->p_reflock);
+ cv_init(&p->p_waitcv, "pwait");
+ cv_init(&p->p_lwpcv, "plwp");
+
+ p->p_pptr = parent;
+ p->p_ppid = parent->p_pid;
+
+ kauth_proc_fork(parent, p);
+
+ /* initialize cwd in rump kernels with vfs */
+ if (rump_proc_vfs_init)
+ rump_proc_vfs_init(p);
+
+ chgproccnt(uid, 1); /* not enforced */
+
+ /* publish proc various proc lists */
+ mutex_enter(proc_lock);
+ LIST_INSERT_HEAD(&allproc, p, p_list);
+ LIST_INSERT_HEAD(&parent->p_children, p, p_sibling);
+ LIST_INSERT_AFTER(parent, p, p_pglist);
+ mutex_exit(proc_lock);
+
+ return p;
+}
+
+static void
+lwproc_freelwp(struct lwp *l)
+{
+ struct proc *p;
+ bool freeproc;
+
+ p = l->l_proc;
+ mutex_enter(p->p_lock);
+
+ /* XXX: l_refcnt */
+ KASSERT(l->l_flag & LW_WEXIT);
+ KASSERT(l->l_refcnt == 0);
+
+ /* ok, zero references, continue with nuke */
+ LIST_REMOVE(l, l_sibling);
+ KASSERT(p->p_nlwps >= 1);
+ if (--p->p_nlwps == 0) {
+ KASSERT(p != &proc0);
+ p->p_stat = SDEAD;
+ }
+ freeproc = p->p_nlwps == 0;
+ cv_broadcast(&p->p_lwpcv); /* nobody sleeps on this in rump? */
+ kauth_cred_free(l->l_cred);
+ mutex_exit(p->p_lock);
+
+ mutex_enter(proc_lock);
+ LIST_REMOVE(l, l_list);
+ mutex_exit(proc_lock);
+
+ if (l->l_name)
+ kmem_free(l->l_name, MAXCOMLEN);
+ lwp_finispecific(l);
+
+ kmem_free(l, sizeof(*l));
+
+ if (p->p_stat == SDEAD)
+ lwproc_proc_free(p);
+}
+
+/*
+ * called with p_lock held, releases lock before return
+ */
+static void
+lwproc_makelwp(struct proc *p, struct lwp *l, bool doswitch, bool procmake)
+{
+
+ p->p_nlwps++;
+ l->l_refcnt = 1;
+ l->l_proc = p;
+
+ l->l_lid = p->p_nlwpid++;
+ LIST_INSERT_HEAD(&p->p_lwps, l, l_sibling);
+ mutex_exit(p->p_lock);
+
+ lwp_update_creds(l);
+
+ l->l_fd = p->p_fd;
+ l->l_cpu = NULL;
+ l->l_target_cpu = rump_cpu; /* Initial target CPU always the same */
+
+ lwp_initspecific(l);
+
+ if (doswitch) {
+ rump_lwproc_switch(l);
+ }
+
+ /* filedesc already has refcount 1 when process is created */
+ if (!procmake) {
+ fd_hold(l);
+ }
+
+ mutex_enter(proc_lock);
+ LIST_INSERT_HEAD(&alllwp, l, l_list);
+ mutex_exit(proc_lock);
+}
+
+struct lwp *
+rump__lwproc_allockernlwp(void)
+{
+ struct proc *p;
+ struct lwp *l;
+
+ l = kmem_zalloc(sizeof(*l), KM_SLEEP);
Home |
Main Index |
Thread Index |
Old Index