Skip site navigation (1)Skip section navigation (2)
Date:      Sat, 8 Jul 2006 13:49:19 GMT
From:      Roman Divacky <rdivacky@FreeBSD.org>
To:        Perforce Change Reviews <perforce@FreeBSD.org>
Subject:   PERFORCE change 101011 for review
Message-ID:  <200607081349.k68DnJBt036190@repoman.freebsd.org>

next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=101011

Change 101011 by rdivacky@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;



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