From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1M1RTr-0002VW-FA for qemu-devel@nongnu.org; Tue, 05 May 2009 16:43:11 -0400 Received: from exim by lists.gnu.org with spam-scanned (Exim 4.43) id 1M1RTq-0002VK-1p for qemu-devel@nongnu.org; Tue, 05 May 2009 16:43:11 -0400 Received: from [199.232.76.173] (port=56442 helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1M1RTp-0002VH-UZ for qemu-devel@nongnu.org; Tue, 05 May 2009 16:43:09 -0400 Received: from naru.obs2.net ([84.20.150.76]:37964) by monty-python.gnu.org with esmtps (TLS-1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.60) (envelope-from ) id 1M1RTp-0005CA-Af for qemu-devel@nongnu.org; Tue, 05 May 2009 16:43:09 -0400 Date: Tue, 5 May 2009 23:43:03 +0300 From: Riku Voipio Message-ID: <20090505204303.GA32298@kos.to> References: <20090505133048.GA29646@kos.to> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <20090505133048.GA29646@kos.to> Subject: [Qemu-devel] [PATCH] linux-user: implement pipe2 syscall [v2] List-Id: qemu-devel.nongnu.org List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Cc: martin.mohring@opensuse.org On Tue, May 05, 2009 at 04:30:48PM +0300, Riku Voipio wrote: > implement pipe2 syscall. instead of calling pipe2 directly > (which was introduced in 2.6.27), emulate the flag functionality > with fcntl. and badly tested from me. failed to build on mips and sh4 targets. >>From bf49a705ddbec1821163c54f326782b924729310 Mon Sep 17 00:00:00 2001 From: Riku Voipio Date: Tue, 5 May 2009 12:10:04 +0300 Subject: [PATCH] linux-user: implement pipe2 [v2] implement pipe2 syscall. instead of calling pipe2 directly (which was introduced in 2.6.27), emulate the flag functionality with fcntl. [v2] fix do_pipe build on mips and sh4 Signed-off-by: Riku Voipio --- linux-user/syscall.c | 70 +++++++++++++++++++++++++++++++++++++------------- 1 files changed, 52 insertions(+), 18 deletions(-) diff --git a/linux-user/syscall.c b/linux-user/syscall.c index 1096bb1..e3cd185 100644 --- a/linux-user/syscall.c +++ b/linux-user/syscall.c @@ -943,6 +943,52 @@ static abi_long do_select(int n, return ret; } +static abi_long pipe_set_flag(int fd, int readcmd, int writecmd, long newflag) +{ + int flags = fcntl(fd, readcmd); + if (flags<0) + return get_errno(flags); + flags |= newflag; + flags = fcntl(fd, writecmd, flags); + return get_errno(flags); +} + +static abi_long do_pipe(void *cpu_env, int pipedes, int flags) +{ + int host_pipe[2]; + abi_long ret; + ret = pipe(host_pipe); + if (is_error(ret)) + return get_errno(ret); +#if defined(TARGET_MIPS) + ((CPUMIPSState*)cpu_env)->active_tc.gpr[3] = host_pipe[1]; + ret = host_pipe[0]; +#elif defined(TARGET_SH4) + ((CPUSH4State*)cpu_env)->gregs[1] = host_pipe[1]; + ret = host_pipe[0]; +#else + if (put_user_s32(host_pipe[0], pipedes) + || put_user_s32(host_pipe[1], pipedes + sizeof(host_pipe[0]))) + return -TARGET_EFAULT; +#endif + if (flags & O_NONBLOCK) { + ret = pipe_set_flag(host_pipe[0], F_GETFL, F_SETFL, O_NONBLOCK); + if (is_error(ret)) + return get_errno(ret); + ret = pipe_set_flag(host_pipe[1], F_GETFL, F_SETFL, O_NONBLOCK); + if (is_error(ret)) + return get_errno(ret); + } + if (flags & O_CLOEXEC) { + ret = pipe_set_flag(host_pipe[0], F_GETFD, F_SETFD, FD_CLOEXEC); + if (is_error(ret)) + return get_errno(ret); + ret = pipe_set_flag(host_pipe[1], F_GETFD, F_SETFD, FD_CLOEXEC); + if (is_error(ret)) + return get_errno(ret); + } + return get_errno(ret); +} static inline abi_long target_to_host_ip_mreq(struct ip_mreqn *mreqn, abi_ulong target_addr, @@ -4525,25 +4571,13 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1, ret = get_errno(dup(arg1)); break; case TARGET_NR_pipe: - { - int host_pipe[2]; - ret = get_errno(pipe(host_pipe)); - if (!is_error(ret)) { -#if defined(TARGET_MIPS) - CPUMIPSState *env = (CPUMIPSState*)cpu_env; - env->active_tc.gpr[3] = host_pipe[1]; - ret = host_pipe[0]; -#elif defined(TARGET_SH4) - ((CPUSH4State*)cpu_env)->gregs[1] = host_pipe[1]; - ret = host_pipe[0]; -#else - if (put_user_s32(host_pipe[0], arg1) - || put_user_s32(host_pipe[1], arg1 + sizeof(host_pipe[0]))) - goto efault; -#endif - } - } + ret = do_pipe(cpu_env, arg1, 0); + break; +#ifdef TARGET_NR_pipe2 + case TARGET_NR_pipe2: + ret = do_pipe(cpu_env, arg1, arg2); break; +#endif case TARGET_NR_times: { struct target_tms *tmsp; -- 1.6.2.1