Fix corner cases of socketcall syscall
* xlat/socketcalls.in: New file. * socketcall.c: New file. * Makefile.am (libstrace_a_SOURCES): Add it. * linux/dummy.h (sys_socketcall): Remove stub alias. * syscall.c (decode_socket_subcall): Treat 1st argument of socketcall as "int". Do not substitute syscall until all socketcall arguments have been fetched successfully.
This commit is contained in:
@ -66,6 +66,7 @@ libstrace_a_CFLAGS = $(strace_CFLAGS)
|
|||||||
libstrace_a_SOURCES = \
|
libstrace_a_SOURCES = \
|
||||||
fstatfs.c \
|
fstatfs.c \
|
||||||
fstatfs64.c \
|
fstatfs64.c \
|
||||||
|
socketcall.c \
|
||||||
statfs.c \
|
statfs.c \
|
||||||
statfs64.c \
|
statfs64.c \
|
||||||
sync_file_range.c \
|
sync_file_range.c \
|
||||||
|
@ -113,7 +113,6 @@
|
|||||||
#define sys_setsid printargs
|
#define sys_setsid printargs
|
||||||
#define sys_set_tid_address printargs
|
#define sys_set_tid_address printargs
|
||||||
#define sys_setup printargs
|
#define sys_setup printargs
|
||||||
#define sys_socketcall printargs
|
|
||||||
#define sys_sync printargs
|
#define sys_sync printargs
|
||||||
#define sys_syscall printargs
|
#define sys_syscall printargs
|
||||||
#define sys_vhangup printargs
|
#define sys_vhangup printargs
|
||||||
|
46
socketcall.c
Normal file
46
socketcall.c
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2016 Dmitry V. Levin <ldv@altlinux.org>
|
||||||
|
* All rights reserved.
|
||||||
|
*
|
||||||
|
* Redistribution and use in source and binary forms, with or without
|
||||||
|
* modification, are permitted provided that the following conditions
|
||||||
|
* are met:
|
||||||
|
* 1. Redistributions of source code must retain the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer.
|
||||||
|
* 2. Redistributions in binary form must reproduce the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer in the
|
||||||
|
* documentation and/or other materials provided with the distribution.
|
||||||
|
* 3. The name of the author may not be used to endorse or promote products
|
||||||
|
* derived from this software without specific prior written permission.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
||||||
|
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||||
|
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||||
|
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||||
|
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||||
|
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||||
|
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||||
|
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||||
|
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "defs.h"
|
||||||
|
#include "xlat/socketcalls.h"
|
||||||
|
|
||||||
|
SYS_FUNC(socketcall)
|
||||||
|
{
|
||||||
|
const unsigned int call = tcp->u_arg[0];
|
||||||
|
const char *str = xlookup(socketcalls, call);
|
||||||
|
|
||||||
|
if (str)
|
||||||
|
tprints(str);
|
||||||
|
else
|
||||||
|
tprintf("%d", call);
|
||||||
|
|
||||||
|
unsigned int i;
|
||||||
|
for (i = 1; i < MAX_ARGS; ++i)
|
||||||
|
tprintf(", %#lx", tcp->u_arg[i]);
|
||||||
|
|
||||||
|
return RVAL_DECODED;
|
||||||
|
}
|
35
syscall.c
35
syscall.c
@ -567,29 +567,26 @@ qualify(const char *s)
|
|||||||
static void
|
static void
|
||||||
decode_socket_subcall(struct tcb *tcp)
|
decode_socket_subcall(struct tcb *tcp)
|
||||||
{
|
{
|
||||||
unsigned long addr;
|
const int call = tcp->u_arg[0];
|
||||||
unsigned int n;
|
|
||||||
|
|
||||||
if (tcp->u_arg[0] < 0 || tcp->u_arg[0] >= SYS_socket_nsubcalls)
|
if (call < 1 || call >= SYS_socket_nsubcalls)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
tcp->scno = SYS_socket_subcall + tcp->u_arg[0];
|
const unsigned long scno = SYS_socket_subcall + call;
|
||||||
tcp->qual_flg = qual_flags[tcp->scno];
|
const unsigned int nargs = sysent[scno].nargs;
|
||||||
tcp->s_ent = &sysent[tcp->scno];
|
uint64_t buf[nargs];
|
||||||
addr = tcp->u_arg[1];
|
|
||||||
n = tcp->s_ent->nargs;
|
|
||||||
if (sizeof(tcp->u_arg[0]) == current_wordsize) {
|
|
||||||
memset(tcp->u_arg, 0, n * sizeof(tcp->u_arg[0]));
|
|
||||||
(void) umoven(tcp, addr, n * sizeof(tcp->u_arg[0]), tcp->u_arg);
|
|
||||||
} else {
|
|
||||||
unsigned int args[n];
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
memset(args, 0, sizeof(args));
|
if (umoven(tcp, tcp->u_arg[1], nargs * current_wordsize, buf) < 0)
|
||||||
(void) umove(tcp, addr, &args);
|
return;
|
||||||
for (i = 0; i < n; ++i)
|
|
||||||
tcp->u_arg[i] = args[i];
|
tcp->scno = scno;
|
||||||
}
|
tcp->qual_flg = qual_flags[scno];
|
||||||
|
tcp->s_ent = &sysent[scno];
|
||||||
|
|
||||||
|
unsigned int i;
|
||||||
|
for (i = 0; i < nargs; ++i)
|
||||||
|
tcp->u_arg[i] = (sizeof(uint32_t) == current_wordsize)
|
||||||
|
? ((uint32_t *) buf)[i] : buf[i];
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
20
xlat/socketcalls.in
Normal file
20
xlat/socketcalls.in
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
SYS_SOCKET 1
|
||||||
|
SYS_BIND 2
|
||||||
|
SYS_CONNECT 3
|
||||||
|
SYS_LISTEN 4
|
||||||
|
SYS_ACCEPT 5
|
||||||
|
SYS_GETSOCKNAME 6
|
||||||
|
SYS_GETPEERNAME 7
|
||||||
|
SYS_SOCKETPAIR 8
|
||||||
|
SYS_SEND 9
|
||||||
|
SYS_RECV 10
|
||||||
|
SYS_SENDTO 11
|
||||||
|
SYS_RECVFROM 12
|
||||||
|
SYS_SHUTDOWN 13
|
||||||
|
SYS_SETSOCKOPT 14
|
||||||
|
SYS_GETSOCKOPT 15
|
||||||
|
SYS_SENDMSG 16
|
||||||
|
SYS_RECVMSG 17
|
||||||
|
SYS_ACCEPT4 18
|
||||||
|
SYS_RECVMMSG 19
|
||||||
|
SYS_SENDMMSG 20
|
Reference in New Issue
Block a user