* syscall.c (dumpio): Call dumpiov_in_msghdr if
the target function is recvmsg or sendmsg.

* net.c (extractmsghdr): New function derived from
`printmsghdr'.
(printmsghdr): Use `extractmsghdr'.
(dumpiov_in_msghdr): New function.

* defs.h: Add a declaration for `dumpiov_in_msghdr'.

Here is an example session:

    $ ./strace -e write=all ip link change dev enp0s25 mtu 1501 > /dev/null
    sendmsg(3, {msg_name(12)={sa_family=AF_NETLINK, pid=0, groups=00000000}, 
msg_iov(1)=[{"(...
     * 40 bytes in buffer 0
     | 00000  28 00 00 00 10 00 05 00  d0 d9 aa 53 00 00 00 00  
(..........S.... |
     | 00010  00 00 00 00 02 00 00 00  00 00 00 00 00 00 00 00  
................ |
     | 00020  08 00 04 00 dd 05 00 00                           ........        
 |
    ...

    $ ./strace -e read=all ip link show > /dev/null
    recvmsg(3, {msg_name(12)={sa_family=AF_NETLINK, pid=0, groups=00000000}, 
msg_iov(1)=[{"...
     * 8192 bytes in buffer 0
     | 00000  34 00 00 00 02 00 00 00  00 00 00 00 ff 23 00 00  
4............#.. |
     | 00010  ff ff ff ff 20 00 00 00  10 00 05 00 00 00 00 00  .... 
........... |
    ...

Signed-off-by: Masatake YAMATO <yam...@redhat.com>
---
 defs.h    |  1 +
 net.c     | 45 +++++++++++++++++++++++++++++++--------------
 syscall.c |  4 ++++
 3 files changed, 36 insertions(+), 14 deletions(-)

diff --git a/defs.h b/defs.h
index 1a3b483..39eb1be 100644
--- a/defs.h
+++ b/defs.h
@@ -676,6 +676,7 @@ extern int printargs_ld(struct tcb *);
 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(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 08341ad..36ab8cc 100644
--- a/net.c
+++ b/net.c
@@ -392,29 +392,46 @@ struct mmsghdr32 {
        uint32_t /* unsigned */ msg_len;
 };
 
-static void
-printmsghdr(struct tcb *tcp, long addr, unsigned long data_size)
+static int
+extractmsghdr(struct tcb *tcp, long addr, struct msghdr *msg)
 {
-       struct msghdr msg;
-
 #if SUPPORTED_PERSONALITIES > 1 && SIZEOF_LONG > 4
        if (current_wordsize == 4) {
                struct msghdr32 msg32;
 
                if (umove(tcp, addr, &msg32) < 0) {
-                       tprintf("%#lx", addr);
-                       return;
+                       return -1;
                }
-               msg.msg_name       = (void*)(long)msg32.msg_name;
-               msg.msg_namelen    =              msg32.msg_namelen;
-               msg.msg_iov        = (void*)(long)msg32.msg_iov;
-               msg.msg_iovlen     =              msg32.msg_iovlen;
-               msg.msg_control    = (void*)(long)msg32.msg_control;
-               msg.msg_controllen =              msg32.msg_controllen;
-               msg.msg_flags      =              msg32.msg_flags;
+               msg->msg_name       = (void*)(long)msg32.msg_name;
+               msg->msg_namelen    =              msg32.msg_namelen;
+               msg->msg_iov        = (void*)(long)msg32.msg_iov;
+               msg->msg_iovlen     =              msg32.msg_iovlen;
+               msg->msg_control    = (void*)(long)msg32.msg_control;
+               msg->msg_controllen =              msg32.msg_controllen;
+               msg->msg_flags      =              msg32.msg_flags;
        } else
 #endif
-       if (umove(tcp, addr, &msg) < 0) {
+       if (umove(tcp, addr, msg) < 0) {
+                       return -1;
+               }
+       return 0;
+}
+
+void
+dumpiov_in_msghdr(struct tcb *tcp, long addr)
+{
+       struct msghdr msg;
+
+       if (extractmsghdr(tcp, addr, &msg) >= 0)
+               dumpiov(tcp, msg.msg_iovlen, (long)msg.msg_iov);
+}
+
+static void
+printmsghdr(struct tcb *tcp, long addr, unsigned long data_size)
+{
+       struct msghdr msg;
+
+       if (extractmsghdr(tcp, addr, &msg) < 0) {
                tprintf("%#lx", addr);
                return;
        }
diff --git a/syscall.c b/syscall.c
index b0ad47e..518ef13 100644
--- a/syscall.c
+++ b/syscall.c
@@ -2494,6 +2494,8 @@ dumpio(struct tcb *tcp)
                        dumpstr(tcp, tcp->u_arg[1], tcp->u_rval);
                else if (func == sys_readv)
                        dumpiov(tcp, tcp->u_arg[2], tcp->u_arg[1]);
+               else if (func == sys_recvmsg)
+                       dumpiov_in_msghdr(tcp, tcp->u_arg[1]);
                return;
        }
        if (qual_flags[tcp->u_arg[0]] & QUAL_WRITE) {
@@ -2504,6 +2506,8 @@ dumpio(struct tcb *tcp)
                        dumpstr(tcp, tcp->u_arg[1], tcp->u_arg[2]);
                else if (func == sys_writev)
                        dumpiov(tcp, tcp->u_arg[2], tcp->u_arg[1]);
+               else if (func == sys_sendmsg)
+                       dumpiov_in_msghdr(tcp, tcp->u_arg[1]);
                return;
        }
 }
-- 
1.9.0


------------------------------------------------------------------------------
Open source business process management suite built on Java and Eclipse
Turn processes into business applications with Bonita BPM Community Edition
Quickly connect people, data, and systems into organized workflows
Winner of BOSSIE, CODIE, OW2 and Gartner awards
http://p.sf.net/sfu/Bonitasoft
_______________________________________________
Strace-devel mailing list
Strace-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/strace-devel

Reply via email to