[PATCH 3/4] Add functions for dumping iovecs in mmsghdr used in sendmmsg and recvmmsg

Masatake YAMATO yamato at redhat.com
Thu Nov 6 16:23:26 UTC 2014


This patch is similar to what I did in commit
02f9f6b386741a52f58e1b31ad4e7fff60781ef8.  The commit was for sendmsg
and recvmsg system calls. This one is for sendmmsg and recvmmsg system
calls.

        $ ./strace -f -e write=all tests/mmsg
	...
	[pid  6730] sendmmsg(3,  <unfinished ...>
	...
	[pid  6730] <... sendmmsg resumed> ...
	 = 2 buffers in vector 0
	 * 3 bytes in buffer 0
	 | 00000  6f 6e 65                                          one              |
	 * 3 bytes in buffer 1
	 | 00000  74 77 6f                                          two              |
	 = 1 buffers in vector 1
	 * 5 bytes in buffer 0
	 | 00000  74 68 72 65 65                                    three            |
	...

        $ ./strace -f -e read=all tests/mmsg
        ...
	[pid  6819] recvmmsg(4,  <unfinished ...>
	[pid  6820] sendmmsg(3,  <unfinished ...>
	[pid  6819] <... recvmmsg resumed> ...
	 = 2 buffers in vector 0
	 * 3 bytes in buffer 0
	 | 00000  6f 6e 65                                          one              |
	 * 3 bytes in buffer 1
	 | 00000  74 77 6f                                          two              |
	 = 1 buffers in vector 1
	 * 5 bytes in buffer 0
	 | 00000  74 68 72 65 65                                    three            |
        ...

* configure.ac (sendmmsg): Check sendmmsg system call.

* defs.h (dumpiov_in_mmsghdr): New declaration.

* net.c (extractmmsghdr0, extractmmsghdr): New helper functions do the
  same as extractmsghdr but for mmsghdr.

  (extractmsghdr): Use copy_from_msghdr32.

  (dumpiov_in_mmsghdr): Do the same as dumpiov_in_msghdr but for mmsghdr.

  (printmmsghdr): Simplified with using extractmmsghdr.

* syscall.c (dumpio): call dumpiov_in_mmsghdr if revmmsg or sendmmsg is
  called.

Signed-off-by: Masatake YAMATO <yamato at redhat.com>
---
 configure.ac |  1 +
 defs.h       |  1 +
 net.c        | 80 ++++++++++++++++++++++++++++++++++++++++--------------------
 syscall.c    |  8 ++++++
 4 files changed, 63 insertions(+), 27 deletions(-)

diff --git a/configure.ac b/configure.ac
index 01df6f2..35d52ba 100644
--- a/configure.ac
+++ b/configure.ac
@@ -219,6 +219,7 @@ AC_CHECK_FUNCS(m4_normalize([
 	process_vm_readv
 	pwritev
 	sendmsg
+	sendmmsg
 	sigaction
 	stpcpy
 	strerror
diff --git a/defs.h b/defs.h
index d41af96..661de92 100644
--- a/defs.h
+++ b/defs.h
@@ -674,6 +674,7 @@ extern void addflags(const struct xlat *, int);
 extern int printflags(const struct xlat *, int, const char *);
 extern const char *sprintflags(const char *, const struct xlat *, int);
 extern void dumpiov_in_msghdr(struct tcb *, long);
+extern void dumpiov_in_mmsghdr(struct tcb *, long);
 extern void dumpiov(struct tcb *, int, long);
 extern void dumpstr(struct tcb *, long, int);
 extern void printstr(struct tcb *, long, long);
diff --git a/net.c b/net.c
index 53c2a02..68e7399 100644
--- a/net.c
+++ b/net.c
@@ -430,6 +430,36 @@ extractmsghdr(struct tcb *tcp, long addr, struct msghdr *msg)
 	return true;
 }
 
+static bool
+extractmmsghdr0(struct tcb *tcp, long addr, struct mmsghdr *mmsg)
+{
+#if SUPPORTED_PERSONALITIES > 1 && SIZEOF_LONG > 4
+	if (current_wordsize == 4) {
+		struct mmsghdr32 mmsg32;
+
+		if (umove(tcp, addr, &mmsg32) < 0)
+			return false;
+		copy_from_msghdr32(&mmsg->msg_hdr, &mmsg32.msg_hdr);
+		mmsg->msg_len = mmsg32.msg_len;
+	} else
+#endif
+	 if (umove(tcp, addr, mmsg) < 0)
+		 return false;
+	return true;
+}
+
+static bool
+extractmmsghdr(struct tcb *tcp, long addr, unsigned int idx, struct mmsghdr *mmsg)
+{
+#if SUPPORTED_PERSONALITIES > 1 && SIZEOF_LONG > 4
+	if (current_wordsize == 4)
+		addr += sizeof(struct mmsghdr32) * idx;
+	else
+#endif
+		addr += sizeof(*mmsg) * idx;
+	return extractmmsghdr0(tcp, addr, mmsg);
+}
+
 static void
 printmsghdr(struct tcb *tcp, long addr, unsigned long data_size)
 {
@@ -450,40 +480,36 @@ dumpiov_in_msghdr(struct tcb *tcp, long addr)
 		dumpiov(tcp, msg.msg_iovlen, (long)msg.msg_iov);
 }
 
+void
+dumpiov_in_mmsghdr(struct tcb *tcp, long addr)
+{
+	unsigned int len = tcp->u_rval;
+	unsigned int i;
+	struct mmsghdr mmsg;
+
+	for (i = 0; i < len; ++i)
+	{
+		if (extractmmsghdr(tcp, addr, i, &mmsg))
+		{
+			tprintf(" = %lu buffers in vector %u\n", mmsg.msg_hdr.msg_iovlen, i);
+			dumpiov(tcp, mmsg.msg_hdr.msg_iovlen, (long)mmsg.msg_hdr.msg_iov);
+		}
+	}
+}
+
 static void
 printmmsghdr(struct tcb *tcp, long addr, unsigned int idx, unsigned long msg_len)
 {
 	struct mmsghdr mmsg;
 
-#if SUPPORTED_PERSONALITIES > 1 && SIZEOF_LONG > 4
-	if (current_wordsize == 4) {
-		struct mmsghdr32 mmsg32;
-
-		addr += sizeof(mmsg32) * idx;
-		if (umove(tcp, addr, &mmsg32) < 0) {
-			tprintf("%#lx", addr);
-			return;
-		}
-		mmsg.msg_hdr.msg_name       = (void*)(long)mmsg32.msg_hdr.msg_name;
-		mmsg.msg_hdr.msg_namelen    =              mmsg32.msg_hdr.msg_namelen;
-		mmsg.msg_hdr.msg_iov        = (void*)(long)mmsg32.msg_hdr.msg_iov;
-		mmsg.msg_hdr.msg_iovlen     =              mmsg32.msg_hdr.msg_iovlen;
-		mmsg.msg_hdr.msg_control    = (void*)(long)mmsg32.msg_hdr.msg_control;
-		mmsg.msg_hdr.msg_controllen =              mmsg32.msg_hdr.msg_controllen;
-		mmsg.msg_hdr.msg_flags      =              mmsg32.msg_hdr.msg_flags;
-		mmsg.msg_len                =              mmsg32.msg_len;
-	} else
-#endif
+	if (extractmmsghdr(tcp, addr, idx, &mmsg))
 	{
-		addr += sizeof(mmsg) * idx;
-		if (umove(tcp, addr, &mmsg) < 0) {
-			tprintf("%#lx", addr);
-			return;
-		}
+		tprints("{");
+		do_msghdr(tcp, &mmsg.msg_hdr, msg_len ? msg_len : mmsg.msg_len);
+		tprintf(", %u}", mmsg.msg_len);
 	}
-	tprints("{");
-	do_msghdr(tcp, &mmsg.msg_hdr, msg_len ? msg_len : mmsg.msg_len);
-	tprintf(", %u}", mmsg.msg_len);
+	else
+		tprintf("%#lx", addr);
 }
 
 static void
diff --git a/syscall.c b/syscall.c
index fa761a9..005a079 100644
--- a/syscall.c
+++ b/syscall.c
@@ -2501,6 +2501,10 @@ dumpio(struct tcb *tcp)
 		else if (func == sys_recvmsg)
 			dumpiov_in_msghdr(tcp, tcp->u_arg[1]);
 #endif
+#if HAVE_SENDMMSG
+		else if (func == sys_recvmmsg)
+			dumpiov_in_mmsghdr(tcp, tcp->u_arg[1]);
+#endif
 		return;
 	}
 	if (qual_flags[tcp->u_arg[0]] & QUAL_WRITE) {
@@ -2515,6 +2519,10 @@ dumpio(struct tcb *tcp)
 		else if (func == sys_sendmsg)
 			dumpiov_in_msghdr(tcp, tcp->u_arg[1]);
 #endif
+#if HAVE_SENDMMSG
+		else if (func == sys_sendmmsg)
+			dumpiov_in_mmsghdr(tcp, tcp->u_arg[1]);
+#endif
 		return;
 	}
 }
-- 
1.9.3





More information about the Strace-devel mailing list