QEMU-Devel Archive on lore.kernel.org
 help / color / Atom feed
From: Filip Bozuta <Filip.Bozuta@syrmia.com>
To: qemu-devel@nongnu.org
Cc: Riku Voipio <riku.voipio@iki.fi>,
	Laurent Vivier <laurent@vivier.eu>,
	Filip Bozuta <Filip.Bozuta@syrmia.com>
Subject: [PATCH 2/3] linux-user: Fix 'recvmmsg()' implementation
Date: Fri, 31 Jul 2020 21:06:36 +0200
Message-ID: <20200731190637.66698-3-Filip.Bozuta@syrmia.com> (raw)
In-Reply-To: <20200731190637.66698-1-Filip.Bozuta@syrmia.com>

Syscall 'recvmmsg()' takes an argument which is of type 'struct timespec'
that represents a timeout for the receive operation. Before changes from
this patch, the timeout argument was ignored. This was probably due to
the way 'recvmmsg()' was implemented with looping over 'recvmsg()' which
doesn't have the timeout argument. This was changed with the previous
patch in this series and which is why the timeout argument should be
added accordingly.

Implementation notes:

    Function 'do_sendrecvmmsg()' was changed with the addition of a new
    argument which represents the timeout. This argument is only passed
    in case of 'TARGET_NR_recvmmsg' and for 'TARGENT_NR_sendmmsg' 0 is
    passed. Function 'do_sendrecvmmsg()' was also updated accordingly in
    'do_socketcall()' for 'TARGET_SYS_recvmmsg' and 'TARGET_SYS_sendmmsg'.

Signed-off-by: Filip Bozuta <Filip.Bozuta@syrmia.com>
---
 linux-user/syscall.c | 22 +++++++++++++++-------
 1 file changed, 15 insertions(+), 7 deletions(-)

diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index 8cbefdb561..420d7e7334 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -3217,10 +3217,11 @@ static abi_long do_sendrecvmsg(int fd, abi_ulong target_msg,
 
 static abi_long do_sendrecvmmsg(int fd, abi_ulong target_msgvec_addr,
                                 unsigned int vlen, unsigned int flags,
-                                int send)
+                                abi_long timeout, int send)
 {
     struct mmsghdr *host_msgvec;
     struct target_mmsghdr *target_msgvec;
+    struct timespec ts;
     abi_long ret = 0;
     int num_sentrecv = 0;
     int num_iovec = 0;
@@ -3275,7 +3276,14 @@ static abi_long do_sendrecvmmsg(int fd, abi_ulong target_msgvec_addr,
         if (send) {
             ret = get_errno(safe_sendmmsg(fd, host_msgvec, i, flags));
         } else {
-            ret = get_errno(safe_recvmmsg(fd, host_msgvec, i, flags, NULL));
+            if (timeout) {
+                if (target_to_host_timespec(&ts, timeout)) {
+                    return -TARGET_EFAULT;
+                }
+                ret = get_errno(safe_recvmmsg(fd, host_msgvec, i, flags, &ts));
+            } else {
+                ret = get_errno(safe_recvmmsg(fd, host_msgvec, i, flags, NULL));
+            }
         }
     }
 
@@ -3611,10 +3619,10 @@ static abi_long do_socketcall(int num, abi_ulong vptr)
         return do_sendrecvmsg(a[0], a[1], a[2], 0);
     case TARGET_SYS_ACCEPT4: /* sockfd, addr, addrlen, flags */
         return do_accept4(a[0], a[1], a[2], a[3]);
-    case TARGET_SYS_RECVMMSG: /* sockfd, msgvec, vlen, flags */
-        return do_sendrecvmmsg(a[0], a[1], a[2], a[3], 0);
+    case TARGET_SYS_RECVMMSG: /* sockfd, msgvec, vlen, timeout, flags */
+        return do_sendrecvmmsg(a[0], a[1], a[2], a[3], a[4], 0);
     case TARGET_SYS_SENDMMSG: /* sockfd, msgvec, vlen, flags */
-        return do_sendrecvmmsg(a[0], a[1], a[2], a[3], 1);
+        return do_sendrecvmmsg(a[0], a[1], a[2], a[3], 0, 1);
     default:
         qemu_log_mask(LOG_UNIMP, "Unsupported socketcall: %d\n", num);
         return -TARGET_EINVAL;
@@ -9418,11 +9426,11 @@ static abi_long do_syscall1(void *cpu_env, int num, abi_long arg1,
 #endif
 #ifdef TARGET_NR_sendmmsg
     case TARGET_NR_sendmmsg:
-        return do_sendrecvmmsg(arg1, arg2, arg3, arg4, 1);
+        return do_sendrecvmmsg(arg1, arg2, arg3, arg4, 0, 1);
 #endif
 #ifdef TARGET_NR_recvmmsg
     case TARGET_NR_recvmmsg:
-        return do_sendrecvmmsg(arg1, arg2, arg3, arg4, 0);
+        return do_sendrecvmmsg(arg1, arg2, arg3, arg4, arg5, 0);
 #endif
 #ifdef TARGET_NR_sendto
     case TARGET_NR_sendto:
-- 
2.25.1



  parent reply index

Thread overview: 5+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-07-31 19:06 [PATCH 0/3] linux-user: Introducing support for 'recvmmsg_time64()' Filip Bozuta
2020-07-31 19:06 ` [PATCH 1/3] linux-user: Modify 'sendmmsg()' and 'recvmmsg()' implementation Filip Bozuta
2020-08-24 20:11   ` Laurent Vivier
2020-07-31 19:06 ` Filip Bozuta [this message]
2020-07-31 19:06 ` [PATCH 3/3] linux-user: Add support for 'recvmmsg_time64()' Filip Bozuta

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20200731190637.66698-3-Filip.Bozuta@syrmia.com \
    --to=filip.bozuta@syrmia.com \
    --cc=laurent@vivier.eu \
    --cc=qemu-devel@nongnu.org \
    --cc=riku.voipio@iki.fi \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

QEMU-Devel Archive on lore.kernel.org

Archives are clonable:
	git clone --mirror https://lore.kernel.org/qemu-devel/0 qemu-devel/git/0.git
	git clone --mirror https://lore.kernel.org/qemu-devel/1 qemu-devel/git/1.git

	# If you have public-inbox 1.1+ installed, you may
	# initialize and index your mirror using the following commands:
	public-inbox-init -V2 qemu-devel qemu-devel/ https://lore.kernel.org/qemu-devel \
		qemu-devel@nongnu.org
	public-inbox-index qemu-devel

Example config snippet for mirrors

Newsgroup available over NNTP:
	nntp://nntp.lore.kernel.org/org.nongnu.qemu-devel


AGPL code for this site: git clone https://public-inbox.org/public-inbox.git