PERFORCE change 101011 for review
Roman Divacky
rdivacky at FreeBSD.org
Sat Jul 8 13:49:21 UTC 2006
http://perforce.freebsd.org/chv.cgi?CH=101011
Change 101011 by rdivacky at rdivacky_witten on 2006/07/08 13:48:40
FreeBSDify the linux_futex.c code and make it compile. Its mostly SCARG removal
and lwp -> thread translation.
Affected files ...
.. //depot/projects/soc2006/rdivacky_linuxolator/i386/linux/linux_futex.c#2 edit
.. //depot/projects/soc2006/rdivacky_linuxolator/i386/linux/linux_sysvec.c#7 edit
Differences ...
==== //depot/projects/soc2006/rdivacky_linuxolator/i386/linux/linux_futex.c#2 (text+ko) ====
@@ -32,24 +32,26 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(1, "$NetBSD: linux_futex.c,v 1.5 2005/11/23 16:14:57 manu Exp $");
+/* __KERNEL_RCSID(1, "$NetBSD: linux_futex.c,v 1.5 2005/11/23 16:14:57 manu Exp $"); */
+#include <sys/param.h>
#include <sys/types.h>
#include <sys/time.h>
#include <sys/systm.h>
#include <sys/proc.h>
-#include <sys/lwp.h>
#include <sys/queue.h>
#include <sys/lock.h>
+#include <sys/mutex.h>
#include <sys/malloc.h>
-#include <compat/linux/common/linux_futex.h>
-#include <compat/linux/linux_syscallargs.h>
+#include <i386/linux/linux_futex.h>
+#include <i386/linux/linux.h>
+#include <i386/linux/linux_proto.h>
struct futex;
struct waiting_proc {
- struct lwp *wp_l;
+ struct thread *wp_t;
struct futex *wp_new_futex;
TAILQ_ENTRY(waiting_proc) wp_list;
};
@@ -60,31 +62,20 @@
TAILQ_HEAD(lf_waiting_proc, waiting_proc) f_waiting_proc;
};
-static LIST_HEAD(futex_list, futex) futex_list;
-static struct lock *futex_lock = NULL;
+LIST_HEAD(futex_list, futex) futex_list;
+struct mtx futex_mtx;
-#define FUTEX_LOCK (void)lockmgr(futex_lock, LK_EXCLUSIVE, NULL)
-#define FUTEX_UNLOCK (void)lockmgr(futex_lock, LK_RELEASE, NULL)
+#define FUTEX_LOCK mtx_lock(&futex_mtx)
+#define FUTEX_UNLOCK mtx_unlock(&futex_mtx)
static struct futex *futex_get(void *);
static void futex_put(struct futex *);
-static int futex_sleep(struct futex *, struct lwp *, unsigned long);
+static int futex_sleep(struct futex *, struct thread *, unsigned long);
static int futex_wake(struct futex *, int, struct futex *);
int
-linux_sys_futex(l, v, retval)
- struct lwp *l;
- void *v;
- register_t *retval;
+linux_sys_futex(struct thread *td, struct linux_sys_futex_args *args)
{
- struct linux_sys_futex_args /* {
- syscallarg(int *) uaddr;
- syscallarg(int) op;
- syscallarg(int) val;
- syscallarg(const struct timespec *) timeout;
- syscallarg(int *) uaddr2;
- syscallarg(int) val3;
- } */ *uap = v;
int val;
int ret;
struct timespec timeout = { 0, 0 };
@@ -92,49 +83,42 @@
struct futex *f;
struct futex *newf;
int timeout_hz;
+ struct timeval tv = {0, 0};
- /* First time use */
- if (futex_lock == NULL) {
- futex_lock = malloc(sizeof(struct lock),
- M_EMULDATA, M_WAITOK);
- lockinit(futex_lock, PZERO|PCATCH, "lockfutex", 0, 0);
- FUTEX_LOCK;
- LIST_INIT(&futex_list);
- FUTEX_UNLOCK;
- }
-
- switch (SCARG(uap, op)) {
+ switch (args->op) {
case LINUX_FUTEX_WAIT:
- if ((error = copyin(SCARG(uap, uaddr),
+ if ((error = copyin(args->uaddr,
&val, sizeof(val))) != 0)
return error;
- if (val != SCARG(uap, val))
+ if (val != args->val)
return EWOULDBLOCK;
- if (SCARG(uap, timeout) != NULL) {
- if ((error = copyin(SCARG(uap, timeout),
+ if (args->timeout != NULL) {
+ if ((error = copyin(args->timeout,
&timeout, sizeof(timeout))) != 0)
return error;
}
-#ifdef DEBUG_LINUX_FUTEX
- printf("FUTEX_WAIT %d.%d: val = %d, uaddr = %p, "
- "*uaddr = %d, timeout = %d.%09ld\n",
- l->l_proc->p_pid, l->l_lid, SCARG(uap, val),
- SCARG(uap, uaddr), val, timeout.tv_sec, timeout.tv_nsec);
+#ifdef DEBUG
+ if (ldebug(sys_futex))
+ printf("FUTEX_WAIT %d.%d: val = %d, uaddr = %p, "
+ "*uaddr = %d, timeout = %d.%09ld\n",
+ l->l_proc->p_pid, l->l_lid, args->val,
+ args->uaddr, val, timeout.tv_sec, timeout.tv_nsec);
#endif
- timeout_hz =
- mstohz(timeout.tv_sec * 1000 + timeout.tv_nsec / 1000000);
+ tv.tv_usec = timeout.tv_sec * 1000 + timeout.tv_nsec / 1000000;
+ timeout_hz = tvtohz(&tv);
- f = futex_get(SCARG(uap, uaddr));
- ret = futex_sleep(f, l, timeout_hz);
+ f = futex_get(args->uaddr);
+ ret = futex_sleep(f, td, timeout_hz);
futex_put(f);
-#ifdef DEBUG_LINUX_FUTEX
- printf("FUTEX_WAIT %d.%d: uaddr = %p, "
- "ret = %d\n", l->l_proc->p_pid, l->l_lid,
- SCARG(uap, uaddr), ret);
+#ifdef DEBUG
+ if (ldebug(sys_futex))
+ printf("FUTEX_WAIT %d.%d: uaddr = %p, "
+ "ret = %d\n", l->l_proc->p_pid, l->l_lid,
+ args->uaddr, ret);
#endif
switch (ret) {
@@ -145,15 +129,17 @@
return EINTR;
break;
case 0: /* FUTEX_WAKE received */
-#ifdef DEBUG_LINUX_FUTEX
- printf("FUTEX_WAIT %d.%d: uaddr = %p, got FUTEX_WAKE\n",
- l->l_proc->p_pid, l->l_lid, SCARG(uap, uaddr));
+#ifdef DEBUG
+ if (ldebug(sys_futex))
+ printf("FUTEX_WAIT %d.%d: uaddr = %p, got FUTEX_WAKE\n",
+ l->l_proc->p_pid, l->l_lid, args->uaddr);
#endif
return 0;
break;
default:
-#ifdef DEBUG_LINUX_FUTEX
- printf("FUTEX_WAIT: unexpected ret = %d\n", ret);
+#ifdef DEBUG
+ if (ldebug(sys_futex))
+ printf("FUTEX_WAIT: unexpected ret = %d\n", ret);
#endif
break;
}
@@ -167,29 +153,30 @@
* corresponding to the same mapped memory in the sleeping
* and the waker process.
*/
-#ifdef DEBUG_LINUX_FUTEX
- printf("FUTEX_WAKE %d.%d: uaddr = %p, val = %d\n",
- l->l_proc->p_pid, l->l_lid,
- SCARG(uap, uaddr), SCARG(uap, val));
+#ifdef DEBUG
+ if (ldebug(sys_futex))
+ printf("FUTEX_WAKE %d.%d: uaddr = %p, val = %d\n",
+ l->l_proc->p_pid, l->l_lid,
+ args->uaddr, args->val);
#endif
- f = futex_get(SCARG(uap, uaddr));
- *retval = futex_wake(f, SCARG(uap, val), NULL);
+ f = futex_get(args->uaddr);
+ td->td_retval[0] = futex_wake(f, args->val, NULL);
futex_put(f);
break;
case LINUX_FUTEX_CMP_REQUEUE:
- if ((error = copyin(SCARG(uap, uaddr),
+ if ((error = copyin(args->uaddr,
&val, sizeof(val))) != 0)
return error;
- if (val != SCARG(uap, val3))
+ if (val != args->val3)
return EAGAIN;
/* FALLTHROUGH */
case LINUX_FUTEX_REQUEUE:
- f = futex_get(SCARG(uap, uaddr));
- newf = futex_get(SCARG(uap, uaddr2));
- *retval = futex_wake(f, SCARG(uap, val), newf);
+ f = futex_get(args->uaddr);
+ newf = futex_get(args->uaddr2);
+ td->td_retval[0] = futex_wake(f, args->val, newf);
futex_put(f);
futex_put(newf);
@@ -197,19 +184,18 @@
case LINUX_FUTEX_FD:
printf("linux_sys_futex: unimplemented op %d\n",
- SCARG(uap, op));
+ args->op);
break;
default:
printf("linux_sys_futex: unkonwn op %d\n",
- SCARG(uap, op));
+ args->op);
break;
}
return 0;
}
static struct futex *
-futex_get(uaddr)
- void *uaddr;
+futex_get(void *uaddr)
{
struct futex *f;
@@ -224,7 +210,7 @@
FUTEX_UNLOCK;
/* Not found, create it */
- f = malloc(sizeof(*f), M_EMULDATA, M_WAITOK);
+ f = malloc(sizeof(*f), M_LINUX, M_WAITOK);
f->f_uaddr = uaddr;
f->f_refcount = 1;
TAILQ_INIT(&f->f_waiting_proc);
@@ -244,31 +230,29 @@
FUTEX_LOCK;
LIST_REMOVE(f, f_list);
FUTEX_UNLOCK;
- free(f, M_EMULDATA);
+ free(f, M_LINUX);
}
return;
}
static int
-futex_sleep(f, l, timeout)
- struct futex *f;
- struct lwp *l;
- unsigned long timeout;
+futex_sleep(struct futex *f, struct thread *td, unsigned long timeout)
{
struct waiting_proc *wp;
int ret;
- wp = malloc(sizeof(*wp), M_EMULDATA, M_WAITOK);
- wp->wp_l = l;
+ wp = malloc(sizeof(*wp), M_LINUX, M_WAITOK);
+ wp->wp_t = td;
wp->wp_new_futex = NULL;
FUTEX_LOCK;
TAILQ_INSERT_TAIL(&f->f_waiting_proc, wp, wp_list);
FUTEX_UNLOCK;
-#ifdef DEBUG_LINUX_FUTEX
- printf("FUTEX --> %d.%d tlseep timeout = %ld\n", l->l_proc->p_pid,
- l->l_lid, timeout);
+#ifdef DEBUG
+ if (ldebug(sys_futex))
+ printf("FUTEX --> %d.%d tlseep timeout = %ld\n", l->l_proc->p_pid,
+ l->l_lid, timeout);
#endif
ret = tsleep(wp, PCATCH|PZERO, "linuxfutex", timeout);
@@ -277,20 +261,17 @@
FUTEX_UNLOCK;
if ((ret == 0) && (wp->wp_new_futex != NULL)) {
- ret = futex_sleep(wp->wp_new_futex, l, timeout);
+ ret = futex_sleep(wp->wp_new_futex, td, timeout);
futex_put(wp->wp_new_futex); /* futex_get called in wakeup */
}
- free(wp, M_EMULDATA);
+ free(wp, M_LINUX);
return ret;
}
static int
-futex_wake(f, n, newf)
- struct futex *f;
- int n;
- struct futex *newf;
+futex_wake(struct futex *f, int n, struct futex *newf)
{
struct waiting_proc *wp;
int count = 0;
==== //depot/projects/soc2006/rdivacky_linuxolator/i386/linux/linux_sysvec.c#7 (text+ko) ====
@@ -112,6 +112,8 @@
extern int linux_userret(struct thread *);
extern int linux_proc_exit(struct thread *);
extern struct rwlock emul_lock;
+extern LIST_HEAD(futex_list, futex) futex_list;
+extern struct mtx futex_mtx;
/*
* Linux syscalls return negative errno's, we do positive and map them
@@ -919,6 +921,8 @@
linux_proc_exit_p = linux_proc_exit;
linux_userret_p = linux_userret;
rw_init(&emul_lock, "emuldata lock");
+ LIST_INIT(&futex_list);
+ mtx_init(&futex_mtx, "futex protection lock", NULL, MTX_DEF);
break;
case MOD_UNLOAD:
for (brandinfo = &linux_brandlist[0]; *brandinfo != NULL;
@@ -943,6 +947,7 @@
linux_proc_exit_p = NULL;
linux_userret_p = NULL;
rw_destroy(&emul_lock);
+ mtx_destroy(&futex_mtx);
break;
default:
return EOPNOTSUPP;
More information about the p4-projects
mailing list