summaryrefslogtreecommitdiffstats
path: root/sys/amd64/linux32
diff options
context:
space:
mode:
authordchagin <dchagin@FreeBSD.org>2011-01-28 18:47:07 +0000
committerdchagin <dchagin@FreeBSD.org>2011-01-28 18:47:07 +0000
commit051ceeb5f3c8cf51e869949c05b1bba132d25804 (patch)
tree481deadfab18548058f8b5da6648a71e1f2eb473 /sys/amd64/linux32
parentcc6bdf663542811773e9cfd95af15b63ef575c5f (diff)
downloadFreeBSD-src-051ceeb5f3c8cf51e869949c05b1bba132d25804.zip
FreeBSD-src-051ceeb5f3c8cf51e869949c05b1bba132d25804.tar.gz
Implement a variation of the linux_common_wait() which should
be used by linuxolator itself. Move linux_wait4() to MD path as it requires native struct rusage translation to struct l_rusage on linux32/amd64. MFC after: 1 Month.
Diffstat (limited to 'sys/amd64/linux32')
-rw-r--r--sys/amd64/linux32/linux32_machdep.c43
1 files changed, 43 insertions, 0 deletions
diff --git a/sys/amd64/linux32/linux32_machdep.c b/sys/amd64/linux32/linux32_machdep.c
index 68d4e8d..80398ec 100644
--- a/sys/amd64/linux32/linux32_machdep.c
+++ b/sys/amd64/linux32/linux32_machdep.c
@@ -51,6 +51,7 @@ __FBSDID("$FreeBSD$");
#include <sys/syscallsubr.h>
#include <sys/sysproto.h>
#include <sys/unistd.h>
+#include <sys/wait.h>
#include <machine/frame.h>
#include <machine/pcb.h>
@@ -66,6 +67,7 @@ __FBSDID("$FreeBSD$");
#include <amd64/linux32/linux.h>
#include <amd64/linux32/linux32_proto.h>
#include <compat/linux/linux_ipc.h>
+#include <compat/linux/linux_misc.h>
#include <compat/linux/linux_signal.h>
#include <compat/linux/linux_util.h>
#include <compat/linux/linux_emul.h>
@@ -1272,3 +1274,44 @@ linux_set_thread_area(struct thread *td,
return (0);
}
+
+int
+linux_wait4(struct thread *td, struct linux_wait4_args *args)
+{
+ int error, options;
+ struct rusage ru, *rup;
+ struct l_rusage lru;
+ struct proc *p;
+
+#ifdef DEBUG
+ if (ldebug(wait4))
+ printf(ARGS(wait4, "%d, %p, %d, %p"),
+ args->pid, (void *)args->status, args->options,
+ (void *)args->rusage);
+#endif
+
+ options = (args->options & (WNOHANG | WUNTRACED));
+ /* WLINUXCLONE should be equal to __WCLONE, but we make sure */
+ if (args->options & __WCLONE)
+ options |= WLINUXCLONE;
+
+ if (args->rusage != NULL)
+ rup = &ru;
+ else
+ rup = NULL;
+ error = linux_common_wait(td, args->pid, args->status, options, rup);
+ if (error)
+ return (error);
+
+ p = td->td_proc;
+ PROC_LOCK(p);
+ sigqueue_delete(&p->p_sigqueue, SIGCHLD);
+ PROC_UNLOCK(p);
+
+ if (args->rusage != NULL) {
+ bsd_to_linux_rusage(rup, &lru);
+ error = copyout(&lru, args->rusage, sizeof(lru));
+ }
+
+ return (error);
+}
OpenPOWER on IntegriCloud