2 * Copyright (c) 1991, 1992 Paul Kranenburg <pk@cs.few.eur.nl>
3 * Copyright (c) 1993 Branko Lankester <branko@hacktic.nl>
4 * Copyright (c) 1993, 1994, 1995, 1996 Rick Sladkey <jrs@world.std.com>
5 * Copyright (c) 1996-1999 Wichert Akkerman <wichert@cistron.nl>
6 * Copyright (c) 1999 IBM Deutschland Entwicklung GmbH, IBM Corporation
7 * Linux for s390 port by D.J. Barrow
8 * <barrow_dj@mail.yahoo.com,djbarrow@de.ibm.com>
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions
14 * 1. Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer.
16 * 2. Redistributions in binary form must reproduce the above copyright
17 * notice, this list of conditions and the following disclaimer in the
18 * documentation and/or other materials provided with the distribution.
19 * 3. The name of the author may not be used to endorse or promote products
20 * derived from this software without specific prior written permission.
22 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
23 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
24 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
25 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
26 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
27 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
31 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
42 #include <sys/syscall.h>
43 #include <sys/param.h>
47 #ifndef PTRACE_PEEKUSR
48 # define PTRACE_PEEKUSR PTRACE_PEEKUSER
50 #elif defined(HAVE_LINUX_PTRACE_H)
52 # ifdef HAVE_STRUCT_IA64_FPREG
53 # define ia64_fpreg XXX_ia64_fpreg
55 # ifdef HAVE_STRUCT_PT_ALL_USER_REGS
56 # define pt_all_user_regs XXX_pt_all_user_regs
58 #include <linux/ptrace.h>
60 # undef pt_all_user_regs
63 #if defined (LINUX) && defined (SPARC64)
64 # undef PTRACE_GETREGS
65 # define PTRACE_GETREGS PTRACE_GETREGS64
66 # undef PTRACE_SETREGS
67 # define PTRACE_SETREGS PTRACE_SETREGS64
68 #endif /* LINUX && SPARC64 */
70 #if defined(LINUX) && defined(IA64)
71 # include <asm/ptrace_offsets.h>
75 #define NR_SYSCALL_BASE 0
78 #define ERESTARTSYS 512
80 #ifndef ERESTARTNOINTR
81 #define ERESTARTNOINTR 513
83 #ifndef ERESTARTNOHAND
84 #define ERESTARTNOHAND 514 /* restart if no handler.. */
87 #define ENOIOCTLCMD 515 /* No ioctl command */
89 #ifndef ERESTART_RESTARTBLOCK
90 #define ERESTART_RESTARTBLOCK 516 /* restart by calling sys_restart_syscall */
93 #warning: NSIG is not defined, using 32
97 /* Ugh. Is this really correct? ARM has no RT signals?! */
100 #undef NR_SYSCALL_BASE
101 #define NR_SYSCALL_BASE __NR_SYSCALL_BASE
107 /* Define these shorthand notations to simplify the syscallent files. */
108 #define TD TRACE_DESC
109 #define TF TRACE_FILE
111 #define TN TRACE_NETWORK
112 #define TP TRACE_PROCESS
113 #define TS TRACE_SIGNAL
114 #define NF SYSCALL_NEVER_FAILS
116 static const struct sysent sysent0[] = {
117 #include "syscallent.h"
120 #if SUPPORTED_PERSONALITIES >= 2
121 static const struct sysent sysent1[] = {
122 #include "syscallent1.h"
126 #if SUPPORTED_PERSONALITIES >= 3
127 static const struct sysent sysent2[] = {
128 #include "syscallent2.h"
132 /* Now undef them since short defines cause wicked namespace pollution. */
143 * `ioctlent.h' may be generated from `ioctlent.raw' by the auxiliary
144 * program `ioctlsort', such that the list is sorted by the `code' field.
145 * This has the side-effect of resolving the _IO.. macros into
146 * plain integers, eliminating the need to include here everything
151 static const char *const errnoent0[] = {
152 #include "errnoent.h"
154 static const char *const signalent0[] = {
155 #include "signalent.h"
157 static const struct ioctlent ioctlent0[] = {
158 #include "ioctlent.h"
160 enum { nsyscalls0 = ARRAY_SIZE(sysent0) };
161 enum { nerrnos0 = ARRAY_SIZE(errnoent0) };
162 enum { nsignals0 = ARRAY_SIZE(signalent0) };
163 enum { nioctlents0 = ARRAY_SIZE(ioctlent0) };
164 int qual_flags0[MAX_QUALS];
166 #if SUPPORTED_PERSONALITIES >= 2
167 static const char *const errnoent1[] = {
168 #include "errnoent1.h"
170 static const char *const signalent1[] = {
171 #include "signalent1.h"
173 static const struct ioctlent ioctlent1[] = {
174 #include "ioctlent1.h"
176 enum { nsyscalls1 = ARRAY_SIZE(sysent1) };
177 enum { nerrnos1 = ARRAY_SIZE(errnoent1) };
178 enum { nsignals1 = ARRAY_SIZE(signalent1) };
179 enum { nioctlents1 = ARRAY_SIZE(ioctlent1) };
180 int qual_flags1[MAX_QUALS];
183 #if SUPPORTED_PERSONALITIES >= 3
184 static const char *const errnoent2[] = {
185 #include "errnoent2.h"
187 static const char *const signalent2[] = {
188 #include "signalent2.h"
190 static const struct ioctlent ioctlent2[] = {
191 #include "ioctlent2.h"
193 enum { nsyscalls2 = ARRAY_SIZE(sysent2) };
194 enum { nerrnos2 = ARRAY_SIZE(errnoent2) };
195 enum { nsignals2 = ARRAY_SIZE(signalent2) };
196 enum { nioctlents2 = ARRAY_SIZE(ioctlent2) };
197 int qual_flags2[MAX_QUALS];
201 const struct sysent *sysent;
202 const char *const *errnoent;
203 const char *const *signalent;
204 const struct ioctlent *ioctlent;
211 int current_personality;
213 #ifndef PERSONALITY0_WORDSIZE
214 # define PERSONALITY0_WORDSIZE sizeof(long)
216 const int personality_wordsize[SUPPORTED_PERSONALITIES] = {
217 PERSONALITY0_WORDSIZE,
218 #if SUPPORTED_PERSONALITIES > 1
219 PERSONALITY1_WORDSIZE,
221 #if SUPPORTED_PERSONALITIES > 2
222 PERSONALITY2_WORDSIZE,
227 set_personality(int personality)
229 switch (personality) {
231 errnoent = errnoent0;
234 nsyscalls = nsyscalls0;
235 ioctlent = ioctlent0;
236 nioctlents = nioctlents0;
237 signalent = signalent0;
238 nsignals = nsignals0;
239 qual_flags = qual_flags0;
242 #if SUPPORTED_PERSONALITIES >= 2
244 errnoent = errnoent1;
247 nsyscalls = nsyscalls1;
248 ioctlent = ioctlent1;
249 nioctlents = nioctlents1;
250 signalent = signalent1;
251 nsignals = nsignals1;
252 qual_flags = qual_flags1;
256 #if SUPPORTED_PERSONALITIES >= 3
258 errnoent = errnoent2;
261 nsyscalls = nsyscalls2;
262 ioctlent = ioctlent2;
263 nioctlents = nioctlents2;
264 signalent = signalent2;
265 nsignals = nsignals2;
266 qual_flags = qual_flags2;
271 current_personality = personality;
275 static int qual_syscall(), qual_signal(), qual_fault(), qual_desc();
277 static const struct qual_options {
279 const char *option_name;
280 int (*qualify)(const char *, int, int);
281 const char *argument_name;
283 { QUAL_TRACE, "trace", qual_syscall, "system call" },
284 { QUAL_TRACE, "t", qual_syscall, "system call" },
285 { QUAL_ABBREV, "abbrev", qual_syscall, "system call" },
286 { QUAL_ABBREV, "a", qual_syscall, "system call" },
287 { QUAL_VERBOSE, "verbose", qual_syscall, "system call" },
288 { QUAL_VERBOSE, "v", qual_syscall, "system call" },
289 { QUAL_RAW, "raw", qual_syscall, "system call" },
290 { QUAL_RAW, "x", qual_syscall, "system call" },
291 { QUAL_SIGNAL, "signal", qual_signal, "signal" },
292 { QUAL_SIGNAL, "signals", qual_signal, "signal" },
293 { QUAL_SIGNAL, "s", qual_signal, "signal" },
294 { QUAL_FAULT, "fault", qual_fault, "fault" },
295 { QUAL_FAULT, "faults", qual_fault, "fault" },
296 { QUAL_FAULT, "m", qual_fault, "fault" },
297 { QUAL_READ, "read", qual_desc, "descriptor" },
298 { QUAL_READ, "reads", qual_desc, "descriptor" },
299 { QUAL_READ, "r", qual_desc, "descriptor" },
300 { QUAL_WRITE, "write", qual_desc, "descriptor" },
301 { QUAL_WRITE, "writes", qual_desc, "descriptor" },
302 { QUAL_WRITE, "w", qual_desc, "descriptor" },
303 { 0, NULL, NULL, NULL },
307 qualify_one(int n, int bitflag, int not, int pers)
309 if (pers == 0 || pers < 0) {
311 qual_flags0[n] &= ~bitflag;
313 qual_flags0[n] |= bitflag;
316 #if SUPPORTED_PERSONALITIES >= 2
317 if (pers == 1 || pers < 0) {
319 qual_flags1[n] &= ~bitflag;
321 qual_flags1[n] |= bitflag;
323 #endif /* SUPPORTED_PERSONALITIES >= 2 */
325 #if SUPPORTED_PERSONALITIES >= 3
326 if (pers == 2 || pers < 0) {
328 qual_flags2[n] &= ~bitflag;
330 qual_flags2[n] |= bitflag;
332 #endif /* SUPPORTED_PERSONALITIES >= 3 */
336 qual_syscall(const char *s, int bitflag, int not)
341 if (isdigit((unsigned char)*s)) {
343 if (i < 0 || i >= MAX_QUALS)
345 qualify_one(i, bitflag, not, -1);
348 for (i = 0; i < nsyscalls0; i++)
349 if (strcmp(s, sysent0[i].sys_name) == 0) {
350 qualify_one(i, bitflag, not, 0);
354 #if SUPPORTED_PERSONALITIES >= 2
355 for (i = 0; i < nsyscalls1; i++)
356 if (strcmp(s, sysent1[i].sys_name) == 0) {
357 qualify_one(i, bitflag, not, 1);
360 #endif /* SUPPORTED_PERSONALITIES >= 2 */
362 #if SUPPORTED_PERSONALITIES >= 3
363 for (i = 0; i < nsyscalls2; i++)
364 if (strcmp(s, sysent2[i].sys_name) == 0) {
365 qualify_one(i, bitflag, not, 2);
368 #endif /* SUPPORTED_PERSONALITIES >= 3 */
374 qual_signal(const char *s, int bitflag, int not)
379 if (isdigit((unsigned char)*s)) {
381 if (signo < 0 || signo >= MAX_QUALS)
383 qualify_one(signo, bitflag, not, -1);
386 if (strlen(s) >= sizeof buf)
390 if (strncasecmp(s, "SIG", 3) == 0)
392 for (i = 0; i <= NSIG; i++)
393 if (strcasecmp(s, signame(i) + 3) == 0) {
394 qualify_one(i, bitflag, not, -1);
401 qual_fault(const char *s, int bitflag, int not)
407 qual_desc(const char *s, int bitflag, int not)
409 if (isdigit((unsigned char)*s)) {
411 if (desc < 0 || desc >= MAX_QUALS)
413 qualify_one(desc, bitflag, not, -1);
420 lookup_class(const char *s)
422 if (strcmp(s, "file") == 0)
424 if (strcmp(s, "ipc") == 0)
426 if (strcmp(s, "network") == 0)
427 return TRACE_NETWORK;
428 if (strcmp(s, "process") == 0)
429 return TRACE_PROCESS;
430 if (strcmp(s, "signal") == 0)
432 if (strcmp(s, "desc") == 0)
438 qualify(const char *s)
440 const struct qual_options *opt;
446 opt = &qual_options[0];
447 for (i = 0; (p = qual_options[i].option_name); i++) {
449 if (strncmp(s, p, n) == 0 && s[n] == '=') {
450 opt = &qual_options[i];
460 if (strcmp(s, "none") == 0) {
464 if (strcmp(s, "all") == 0) {
465 for (i = 0; i < MAX_QUALS; i++) {
466 qualify_one(i, opt->bitflag, not, -1);
470 for (i = 0; i < MAX_QUALS; i++) {
471 qualify_one(i, opt->bitflag, !not, -1);
473 if (!(copy = strdup(s))) {
474 fprintf(stderr, "out of memory\n");
477 for (p = strtok(copy, ","); p; p = strtok(NULL, ",")) {
478 if (opt->bitflag == QUAL_TRACE && (n = lookup_class(p)) > 0) {
479 for (i = 0; i < nsyscalls0; i++)
480 if (sysent0[i].sys_flags & n)
481 qualify_one(i, opt->bitflag, not, 0);
483 #if SUPPORTED_PERSONALITIES >= 2
484 for (i = 0; i < nsyscalls1; i++)
485 if (sysent1[i].sys_flags & n)
486 qualify_one(i, opt->bitflag, not, 1);
487 #endif /* SUPPORTED_PERSONALITIES >= 2 */
489 #if SUPPORTED_PERSONALITIES >= 3
490 for (i = 0; i < nsyscalls2; i++)
491 if (sysent2[i].sys_flags & n)
492 qualify_one(i, opt->bitflag, not, 2);
493 #endif /* SUPPORTED_PERSONALITIES >= 3 */
497 if (opt->qualify(p, opt->bitflag, not)) {
498 fprintf(stderr, "strace: invalid %s `%s'\n",
499 opt->argument_name, p);
508 dumpio(struct tcb *tcp)
512 if (tcp->u_arg[0] < 0 || tcp->u_arg[0] >= MAX_QUALS)
514 if (tcp->scno < 0 || tcp->scno >= nsyscalls)
516 if (sysent[tcp->scno].sys_func == printargs)
518 if (qual_flags[tcp->u_arg[0]] & QUAL_READ) {
519 if (sysent[tcp->scno].sys_func == sys_read ||
520 sysent[tcp->scno].sys_func == sys_pread ||
521 sysent[tcp->scno].sys_func == sys_pread64 ||
522 sysent[tcp->scno].sys_func == sys_recv ||
523 sysent[tcp->scno].sys_func == sys_recvfrom)
524 dumpstr(tcp, tcp->u_arg[1], tcp->u_rval);
525 else if (sysent[tcp->scno].sys_func == sys_readv)
526 dumpiov(tcp, tcp->u_arg[2], tcp->u_arg[1]);
529 if (qual_flags[tcp->u_arg[0]] & QUAL_WRITE) {
530 if (sysent[tcp->scno].sys_func == sys_write ||
531 sysent[tcp->scno].sys_func == sys_pwrite ||
532 sysent[tcp->scno].sys_func == sys_pwrite64 ||
533 sysent[tcp->scno].sys_func == sys_send ||
534 sysent[tcp->scno].sys_func == sys_sendto)
535 dumpstr(tcp, tcp->u_arg[1], tcp->u_arg[2]);
536 else if (sysent[tcp->scno].sys_func == sys_writev)
537 dumpiov(tcp, tcp->u_arg[2], tcp->u_arg[1]);
543 enum subcall_style { shift_style, deref_style, mask_style, door_style };
545 enum subcall_style { shift_style, deref_style, mask_style, door_style, table_style };
553 static const struct subcall subcalls_table[] = {
554 { SYS_shmsys, 5, { SYS_shmat, SYS_shmctl, SYS_shmdt, SYS_shmget, SYS_shmctl } },
556 { SYS_semsys, 4, { SYS___semctl, SYS_semget, SYS_semop, SYS_semconfig } },
558 { SYS_semsys, 3, { SYS___semctl, SYS_semget, SYS_semop } },
560 { SYS_msgsys, 4, { SYS_msgctl, SYS_msgget, SYS_msgsnd, SYS_msgrcv } },
564 #if !(defined(LINUX) && ( defined(ALPHA) || defined(MIPS) || defined(__ARM_EABI__) ))
567 decode_subcall(struct tcb *tcp, int subcall, int nsubcalls, enum subcall_style style)
569 unsigned long addr, mask;
571 int size = personality_wordsize[current_personality];
575 if (tcp->u_arg[0] < 0 || tcp->u_arg[0] >= nsubcalls)
577 tcp->scno = subcall + tcp->u_arg[0];
578 if (sysent[tcp->scno].nargs != -1)
579 tcp->u_nargs = sysent[tcp->scno].nargs;
582 for (i = 0; i < tcp->u_nargs; i++)
583 tcp->u_arg[i] = tcp->u_arg[i + 1];
586 if (tcp->u_arg[0] < 0 || tcp->u_arg[0] >= nsubcalls)
588 tcp->scno = subcall + tcp->u_arg[0];
589 addr = tcp->u_arg[1];
590 for (i = 0; i < sysent[tcp->scno].nargs; i++) {
591 if (size == sizeof(int)) {
593 if (umove(tcp, addr, &arg) < 0)
597 else if (size == sizeof(long)) {
599 if (umove(tcp, addr, &arg) < 0)
607 tcp->u_nargs = sysent[tcp->scno].nargs;
610 mask = (tcp->u_arg[0] >> 8) & 0xff;
611 for (i = 0; mask; i++)
615 tcp->u_arg[0] &= 0xff;
616 tcp->scno = subcall + i;
617 if (sysent[tcp->scno].nargs != -1)
618 tcp->u_nargs = sysent[tcp->scno].nargs;
622 * Oh, yuck. The call code is the *sixth* argument.
623 * (don't you mean the *last* argument? - JH)
625 if (tcp->u_arg[5] < 0 || tcp->u_arg[5] >= nsubcalls)
627 tcp->scno = subcall + tcp->u_arg[5];
628 if (sysent[tcp->scno].nargs != -1)
629 tcp->u_nargs = sysent[tcp->scno].nargs;
635 for (i = 0; i < ARRAY_SIZE(subcalls_table); i++)
636 if (subcalls_table[i].call == tcp->scno) break;
637 if (i < ARRAY_SIZE(subcalls_table) &&
638 tcp->u_arg[0] >= 0 && tcp->u_arg[0] < subcalls_table[i].nsubcalls) {
639 tcp->scno = subcalls_table[i].subcalls[tcp->u_arg[0]];
640 for (i = 0; i < tcp->u_nargs; i++)
641 tcp->u_arg[i] = tcp->u_arg[i + 1];
649 struct tcb *tcp_last = NULL;
652 internal_syscall(struct tcb *tcp)
655 * We must always trace a few critical system calls in order to
656 * correctly support following forks in the presence of tracing
661 if (tcp->scno < 0 || tcp->scno >= nsyscalls)
664 func = sysent[tcp->scno].sys_func;
666 if ( sys_fork == func
667 #if defined(FREEBSD) || defined(LINUX) || defined(SUNOS4)
677 return internal_fork(tcp);
679 if ( sys_execve == func
680 #if defined(SPARC) || defined(SPARC64) || defined(SUNOS4)
684 || sys_rexecve == func
687 return internal_exec(tcp);
696 # elif defined (IA64)
697 long r8, r10, psr; /* TODO: make static? */
698 long ia32 = 0; /* not static */
699 # elif defined (POWERPC)
700 static long result, flags;
701 # elif defined (M68K)
706 static struct pt_regs regs;
707 # elif defined (ALPHA)
710 # elif defined(AVR32)
711 static struct pt_regs regs;
712 # elif defined (SPARC) || defined (SPARC64)
713 static struct pt_regs regs;
714 static unsigned long trap;
715 # elif defined(LINUX_MIPSN32)
721 # elif defined(S390) || defined(S390X)
724 static long syscall_mode;
731 # elif defined(X86_64)
733 # elif defined(CRISV10) || defined(CRISV32)
735 # elif defined(MICROBLAZE)
740 struct reg regs; /* TODO: make static? */
744 get_scno(struct tcb *tcp)
749 # if defined(S390) || defined(S390X)
750 if (tcp->flags & TCB_WAITEXECVE) {
752 * When the execve system call completes successfully, the
753 * new process still has -ENOSYS (old style) or __NR_execve
754 * (new style) in gpr2. We cannot recover the scno again
755 * by disassembly, because the image that executed the
756 * syscall is gone now. Fortunately, we don't want it. We
757 * leave the flag set so that syscall_fixup can fake the
760 if (tcp->flags & TCB_INSYSCALL)
763 * This is the SIGTRAP after execve. We cannot try to read
764 * the system call here either.
766 tcp->flags &= ~TCB_WAITEXECVE;
770 if (upeek(tcp, PT_GPR2, &syscall_mode) < 0)
773 if (syscall_mode != -ENOSYS) {
775 * Since kernel version 2.5.44 the scno gets passed in gpr2.
780 * Old style of "passing" the scno via the SVC instruction.
783 long opcode, offset_reg, tmp;
785 static const int gpr_offset[16] = {
786 PT_GPR0, PT_GPR1, PT_ORIGGPR2, PT_GPR3,
787 PT_GPR4, PT_GPR5, PT_GPR6, PT_GPR7,
788 PT_GPR8, PT_GPR9, PT_GPR10, PT_GPR11,
789 PT_GPR12, PT_GPR13, PT_GPR14, PT_GPR15
792 if (upeek(tcp, PT_PSWADDR, &pc) < 0)
795 opcode = ptrace(PTRACE_PEEKTEXT, tcp->pid, (char *)(pc-sizeof(long)), 0);
797 perror("peektext(pc-oneword)");
802 * We have to check if the SVC got executed directly or via an
803 * EXECUTE instruction. In case of EXECUTE it is necessary to do
804 * instruction decoding to derive the system call number.
805 * Unfortunately the opcode sizes of EXECUTE and SVC are differently,
806 * so that this doesn't work if a SVC opcode is part of an EXECUTE
807 * opcode. Since there is no way to find out the opcode size this
808 * is the best we can do...
811 if ((opcode & 0xff00) == 0x0a00) {
813 scno = opcode & 0xff;
816 /* SVC got executed by EXECUTE instruction */
819 * Do instruction decoding of EXECUTE. If you really want to
820 * understand this, read the Principles of Operations.
822 svc_addr = (void *) (opcode & 0xfff);
825 offset_reg = (opcode & 0x000f0000) >> 16;
826 if (offset_reg && (upeek(tcp, gpr_offset[offset_reg], &tmp) < 0))
831 offset_reg = (opcode & 0x0000f000) >> 12;
832 if (offset_reg && (upeek(tcp, gpr_offset[offset_reg], &tmp) < 0))
836 scno = ptrace(PTRACE_PEEKTEXT, tcp->pid, svc_addr, 0);
845 offset_reg = (opcode & 0x00f00000) >> 20;
846 if (offset_reg && (upeek(tcp, gpr_offset[offset_reg], &tmp) < 0))
849 scno = (scno | tmp) & 0xff;
852 # elif defined (POWERPC)
853 if (upeek(tcp, sizeof(unsigned long)*PT_R0, &scno) < 0)
855 if (!(tcp->flags & TCB_INSYSCALL)) {
856 /* Check if we return from execve. */
857 if (scno == 0 && (tcp->flags & TCB_WAITEXECVE)) {
858 tcp->flags &= ~TCB_WAITEXECVE;
864 if (!(tcp->flags & TCB_INSYSCALL)) {
865 /* TODO: speed up strace by not doing this at every syscall.
866 * We only need to do it after execve.
872 /* Check for 64/32 bit mode. */
873 if (upeek(tcp, sizeof(unsigned long)*PT_MSR, &val) < 0)
875 /* SF is bit 0 of MSR */
880 if (currpers != current_personality) {
881 static const char *const names[] = {"64 bit", "32 bit"};
882 set_personality(currpers);
883 fprintf(stderr, "[ Process PID=%d runs in %s mode. ]\n",
884 pid, names[current_personality]);
888 # elif defined(AVR32)
890 * Read complete register set in one go.
892 if (ptrace(PTRACE_GETREGS, tcp->pid, NULL, ®s) < 0)
896 * We only need to grab the syscall number on syscall entry.
898 if (!(tcp->flags & TCB_INSYSCALL)) {
901 /* Check if we return from execve. */
902 if (tcp->flags & TCB_WAITEXECVE) {
903 tcp->flags &= ~TCB_WAITEXECVE;
908 if (upeek(tcp, PT_ORIG_P0, &scno))
910 # elif defined (I386)
911 if (upeek(tcp, 4*ORIG_EAX, &scno) < 0)
913 # elif defined (X86_64)
914 if (upeek(tcp, 8*ORIG_RAX, &scno) < 0)
917 if (!(tcp->flags & TCB_INSYSCALL)) {
918 /* TODO: speed up strace by not doing this at every syscall.
919 * We only need to do it after execve.
925 /* Check CS register value. On x86-64 linux it is:
926 * 0x33 for long mode (64 bit)
927 * 0x23 for compatibility mode (32 bit)
928 * It takes only one ptrace and thus doesn't need
931 if (upeek(tcp, 8*CS, &val) < 0)
934 case 0x23: currpers = 1; break;
935 case 0x33: currpers = 0; break;
937 fprintf(stderr, "Unknown value CS=0x%02X while "
938 "detecting personality of process "
939 "PID=%d\n", (int)val, pid);
940 currpers = current_personality;
944 /* This version analyzes the opcode of a syscall instruction.
945 * (int 0x80 on i386 vs. syscall on x86-64)
946 * It works, but is too complicated.
948 unsigned long val, rip, i;
950 if (upeek(tcp, 8*RIP, &rip) < 0)
951 perror("upeek(RIP)");
953 /* sizeof(syscall) == sizeof(int 0x80) == 2 */
957 call = ptrace(PTRACE_PEEKTEXT, pid, (char *)rip, (char *)0);
959 fprintf(stderr, "ptrace_peektext failed: %s\n",
961 switch (call & 0xffff) {
962 /* x86-64: syscall = 0x0f 0x05 */
963 case 0x050f: currpers = 0; break;
964 /* i386: int 0x80 = 0xcd 0x80 */
965 case 0x80cd: currpers = 1; break;
967 currpers = current_personality;
969 "Unknown syscall opcode (0x%04X) while "
970 "detecting personality of process "
971 "PID=%d\n", (int)call, pid);
975 if (currpers != current_personality) {
976 static const char *const names[] = {"64 bit", "32 bit"};
977 set_personality(currpers);
978 fprintf(stderr, "[ Process PID=%d runs in %s mode. ]\n",
979 pid, names[current_personality]);
983 # define IA64_PSR_IS ((long)1 << 34)
984 if (upeek(tcp, PT_CR_IPSR, &psr) >= 0)
985 ia32 = (psr & IA64_PSR_IS) != 0;
986 if (!(tcp->flags & TCB_INSYSCALL)) {
988 if (upeek(tcp, PT_R1, &scno) < 0) /* orig eax */
991 if (upeek(tcp, PT_R15, &scno) < 0)
994 /* Check if we return from execve. */
995 if (tcp->flags & TCB_WAITEXECVE) {
996 tcp->flags &= ~TCB_WAITEXECVE;
1000 /* syscall in progress */
1001 if (upeek(tcp, PT_R8, &r8) < 0)
1003 if (upeek(tcp, PT_R10, &r10) < 0)
1006 # elif defined (ARM)
1008 * Read complete register set in one go.
1010 if (ptrace(PTRACE_GETREGS, tcp->pid, NULL, (void *)®s) == -1)
1014 * We only need to grab the syscall number on syscall entry.
1016 if (regs.ARM_ip == 0) {
1017 if (!(tcp->flags & TCB_INSYSCALL)) {
1018 /* Check if we return from execve. */
1019 if (tcp->flags & TCB_WAITEXECVE) {
1020 tcp->flags &= ~TCB_WAITEXECVE;
1026 * Note: we only deal with only 32-bit CPUs here.
1028 if (regs.ARM_cpsr & 0x20) {
1030 * Get the Thumb-mode system call number
1035 * Get the ARM-mode system call number
1038 scno = ptrace(PTRACE_PEEKTEXT, tcp->pid, (void *)(regs.ARM_pc - 4), NULL);
1042 if (scno == 0 && (tcp->flags & TCB_WAITEXECVE)) {
1043 tcp->flags &= ~TCB_WAITEXECVE;
1047 /* Handle the EABI syscall convention. We do not
1048 bother converting structures between the two
1049 ABIs, but basic functionality should work even
1050 if strace and the traced program have different
1052 if (scno == 0xef000000) {
1055 if ((scno & 0x0ff00000) != 0x0f900000) {
1056 fprintf(stderr, "syscall: unknown syscall trap 0x%08lx\n",
1062 * Fixup the syscall number
1067 if (scno & 0x0f0000) {
1069 * Handle ARM specific syscall
1076 if (tcp->flags & TCB_INSYSCALL) {
1077 fprintf(stderr, "pid %d stray syscall entry\n", tcp->pid);
1078 tcp->flags &= ~TCB_INSYSCALL;
1081 if (!(tcp->flags & TCB_INSYSCALL)) {
1082 fprintf(stderr, "pid %d stray syscall exit\n", tcp->pid);
1083 tcp->flags |= TCB_INSYSCALL;
1086 # elif defined (M68K)
1087 if (upeek(tcp, 4*PT_ORIG_D0, &scno) < 0)
1089 # elif defined (LINUX_MIPSN32)
1090 unsigned long long regs[38];
1092 if (ptrace(PTRACE_GETREGS, tcp->pid, NULL, (long) ®s) < 0)
1097 if (!(tcp->flags & TCB_INSYSCALL)) {
1100 /* Check if we return from execve. */
1101 if (scno == 0 && tcp->flags & TCB_WAITEXECVE) {
1102 tcp->flags &= ~TCB_WAITEXECVE;
1106 if (scno < 0 || scno > nsyscalls) {
1107 if (a3 == 0 || a3 == -1) {
1109 fprintf(stderr, "stray syscall exit: v0 = %ld\n", scno);
1114 # elif defined (MIPS)
1115 if (upeek(tcp, REG_A3, &a3) < 0)
1117 if (!(tcp->flags & TCB_INSYSCALL)) {
1118 if (upeek(tcp, REG_V0, &scno) < 0)
1121 /* Check if we return from execve. */
1122 if (scno == 0 && tcp->flags & TCB_WAITEXECVE) {
1123 tcp->flags &= ~TCB_WAITEXECVE;
1127 if (scno < 0 || scno > nsyscalls) {
1128 if (a3 == 0 || a3 == -1) {
1130 fprintf(stderr, "stray syscall exit: v0 = %ld\n", scno);
1135 if (upeek(tcp, REG_V0, &r2) < 0)
1138 # elif defined (ALPHA)
1139 if (upeek(tcp, REG_A3, &a3) < 0)
1142 if (!(tcp->flags & TCB_INSYSCALL)) {
1143 if (upeek(tcp, REG_R0, &scno) < 0)
1146 /* Check if we return from execve. */
1147 if (scno == 0 && tcp->flags & TCB_WAITEXECVE) {
1148 tcp->flags &= ~TCB_WAITEXECVE;
1153 * Do some sanity checks to figure out if it's
1154 * really a syscall entry
1156 if (scno < 0 || scno > nsyscalls) {
1157 if (a3 == 0 || a3 == -1) {
1159 fprintf(stderr, "stray syscall exit: r0 = %ld\n", scno);
1165 if (upeek(tcp, REG_R0, &r0) < 0)
1168 # elif defined (SPARC) || defined (SPARC64)
1169 /* Everything we need is in the current register set. */
1170 if (ptrace(PTRACE_GETREGS, tcp->pid, (char *)®s, 0) < 0)
1173 /* If we are entering, then disassemble the syscall trap. */
1174 if (!(tcp->flags & TCB_INSYSCALL)) {
1175 /* Retrieve the syscall trap instruction. */
1177 # if defined(SPARC64)
1178 trap = ptrace(PTRACE_PEEKTEXT, tcp->pid, (char *)regs.tpc, 0);
1181 trap = ptrace(PTRACE_PEEKTEXT, tcp->pid, (char *)regs.pc, 0);
1186 /* Disassemble the trap to see what personality to use. */
1189 /* Linux/SPARC syscall trap. */
1193 /* Linux/SPARC64 syscall trap. */
1197 /* SunOS syscall trap. (pers 1) */
1198 fprintf(stderr, "syscall: SunOS no support\n");
1201 /* Solaris 2.x syscall trap. (per 2) */
1205 /* NetBSD/FreeBSD syscall trap. */
1206 fprintf(stderr, "syscall: NetBSD/FreeBSD not supported\n");
1209 /* Solaris 2.x gettimeofday */
1213 /* Unknown syscall trap. */
1214 if (tcp->flags & TCB_WAITEXECVE) {
1215 tcp->flags &= ~TCB_WAITEXECVE;
1218 # if defined (SPARC64)
1219 fprintf(stderr, "syscall: unknown syscall trap %08lx %016lx\n", trap, regs.tpc);
1221 fprintf(stderr, "syscall: unknown syscall trap %08lx %08lx\n", trap, regs.pc);
1226 /* Extract the system call number from the registers. */
1227 if (trap == 0x91d02027)
1230 scno = regs.u_regs[U_REG_G1];
1232 scno = regs.u_regs[U_REG_O0];
1233 memmove(®s.u_regs[U_REG_O0], ®s.u_regs[U_REG_O1], 7*sizeof(regs.u_regs[0]));
1236 # elif defined(HPPA)
1237 if (upeek(tcp, PT_GR20, &scno) < 0)
1239 if (!(tcp->flags & TCB_INSYSCALL)) {
1240 /* Check if we return from execve. */
1241 if ((tcp->flags & TCB_WAITEXECVE)) {
1242 tcp->flags &= ~TCB_WAITEXECVE;
1248 * In the new syscall ABI, the system call number is in R3.
1250 if (upeek(tcp, 4*(REG_REG0+3), &scno) < 0)
1254 /* Odd as it may seem, a glibc bug has been known to cause
1255 glibc to issue bogus negative syscall numbers. So for
1256 our purposes, make strace print what it *should* have been */
1257 long correct_scno = (scno & 0xff);
1260 "Detected glibc bug: bogus system call"
1261 " number = %ld, correcting to %ld\n",
1264 scno = correct_scno;
1267 if (!(tcp->flags & TCB_INSYSCALL)) {
1268 /* Check if we return from execve. */
1269 if (scno == 0 && tcp->flags & TCB_WAITEXECVE) {
1270 tcp->flags &= ~TCB_WAITEXECVE;
1274 # elif defined(SH64)
1275 if (upeek(tcp, REG_SYSCALL, &scno) < 0)
1279 if (!(tcp->flags & TCB_INSYSCALL)) {
1280 /* Check if we return from execve. */
1281 if (tcp->flags & TCB_WAITEXECVE) {
1282 tcp->flags &= ~TCB_WAITEXECVE;
1286 # elif defined(CRISV10) || defined(CRISV32)
1287 if (upeek(tcp, 4*PT_R9, &scno) < 0)
1289 # elif defined(TILE)
1290 if (upeek(tcp, PTREGS_OFFSET_REG(10), &scno) < 0)
1293 if (!(tcp->flags & TCB_INSYSCALL)) {
1294 /* Check if we return from execve. */
1295 if (tcp->flags & TCB_WAITEXECVE) {
1296 tcp->flags &= ~TCB_WAITEXECVE;
1300 # elif defined(MICROBLAZE)
1301 if (upeek(tcp, 0, &scno) < 0)
1307 if (upeek(tcp, uoff(u_arg[7]), &scno) < 0)
1310 /* new syscall ABI returns result in R0 */
1311 if (upeek(tcp, 4*REG_REG0, (long *)&r0) < 0)
1314 /* ABI defines result returned in r9 */
1315 if (upeek(tcp, REG_GENERAL(9), (long *)&r9) < 0)
1320 # ifdef HAVE_PR_SYSCALL
1321 scno = tcp->status.PR_SYSCALL;
1324 scno = tcp->status.PR_WHAT;
1326 if (pread(tcp->pfd_reg, ®s, sizeof(regs), 0) < 0) {
1330 switch (regs.r_eax) {
1333 pread(tcp->pfd, &scno, sizeof(scno), regs.r_esp + sizeof(int));
1339 # endif /* FREEBSD */
1340 # endif /* !HAVE_PR_SYSCALL */
1341 #endif /* USE_PROCFS */
1343 if (!(tcp->flags & TCB_INSYSCALL))
1350 known_scno(struct tcb *tcp)
1352 long scno = tcp->scno;
1353 #if SUPPORTED_PERSONALITIES > 1
1354 if (scno >= 0 && scno < nsyscalls && sysent[scno].native_scno != 0)
1355 scno = sysent[scno].native_scno;
1358 scno += NR_SYSCALL_BASE;
1362 /* Called in trace_syscall() at each syscall entry and exit.
1364 * 0: "ignore this syscall", bail out of trace_syscall() silently.
1365 * 1: ok, continue in trace_syscall().
1366 * other: error, trace_syscall() should print error indicator
1367 * ("????" etc) and bail out.
1370 syscall_fixup(struct tcb *tcp)
1373 int scno = known_scno(tcp);
1375 if (!(tcp->flags & TCB_INSYSCALL)) {
1376 if (tcp->status.PR_WHY != PR_SYSENTRY) {
1380 || scno == SYS_vfork
1381 #endif /* SYS_vfork */
1383 || scno == SYS_fork1
1384 #endif /* SYS_fork1 */
1386 || scno == SYS_forkall
1387 #endif /* SYS_forkall */
1389 || scno == SYS_rfork1
1390 #endif /* SYS_fork1 */
1392 || scno == SYS_rforkall
1393 #endif /* SYS_rforkall */
1395 /* We are returning in the child, fake it. */
1396 tcp->status.PR_WHY = PR_SYSENTRY;
1398 tcp->status.PR_WHY = PR_SYSEXIT;
1401 fprintf(stderr, "syscall: missing entry\n");
1402 tcp->flags |= TCB_INSYSCALL;
1407 if (tcp->status.PR_WHY != PR_SYSEXIT) {
1408 fprintf(stderr, "syscall: missing exit\n");
1409 tcp->flags &= ~TCB_INSYSCALL;
1412 #endif /* USE_PROCFS */
1414 if (!(tcp->flags & TCB_INSYSCALL)) {
1416 fprintf(stderr, "syscall: missing entry\n");
1417 tcp->flags |= TCB_INSYSCALL;
1424 * This happens when a signal handler
1425 * for a signal which interrupted a
1426 * a system call makes another system call.
1428 fprintf(stderr, "syscall: missing exit\n");
1430 tcp->flags &= ~TCB_INSYSCALL;
1436 if (upeek(tcp, 4*EAX, &eax) < 0)
1438 if (eax != -ENOSYS && !(tcp->flags & TCB_INSYSCALL)) {
1440 fprintf(stderr, "stray syscall exit: eax = %ld\n", eax);
1443 #elif defined (X86_64)
1444 if (upeek(tcp, 8*RAX, &rax) < 0)
1446 if (current_personality == 1)
1447 rax = (long int)(int)rax; /* sign extend from 32 bits */
1448 if (rax != -ENOSYS && !(tcp->flags & TCB_INSYSCALL)) {
1450 fprintf(stderr, "stray syscall exit: rax = %ld\n", rax);
1453 #elif defined (S390) || defined (S390X)
1454 if (upeek(tcp, PT_GPR2, &gpr2) < 0)
1456 if (syscall_mode != -ENOSYS)
1457 syscall_mode = tcp->scno;
1458 if (gpr2 != syscall_mode && !(tcp->flags & TCB_INSYSCALL)) {
1460 fprintf(stderr, "stray syscall exit: gpr2 = %ld\n", gpr2);
1463 else if (((tcp->flags & (TCB_INSYSCALL|TCB_WAITEXECVE))
1464 == (TCB_INSYSCALL|TCB_WAITEXECVE))
1465 && (gpr2 == -ENOSYS || gpr2 == tcp->scno)) {
1467 * Fake a return value of zero. We leave the TCB_WAITEXECVE
1468 * flag set for the post-execve SIGTRAP to see and reset.
1472 #elif defined (POWERPC)
1473 # define SO_MASK 0x10000000
1474 if (upeek(tcp, sizeof(unsigned long)*PT_CCR, &flags) < 0)
1476 if (upeek(tcp, sizeof(unsigned long)*PT_R3, &result) < 0)
1478 if (flags & SO_MASK)
1480 #elif defined (M68K)
1481 if (upeek(tcp, 4*PT_D0, &d0) < 0)
1483 if (d0 != -ENOSYS && !(tcp->flags & TCB_INSYSCALL)) {
1485 fprintf(stderr, "stray syscall exit: d0 = %ld\n", d0);
1493 if (upeek(tcp, PT_R0, &r0) < 0)
1495 #elif defined (HPPA)
1496 if (upeek(tcp, PT_GR28, &r28) < 0)
1499 if (upeek(tcp, PT_R10, &r10) < 0)
1501 if (upeek(tcp, PT_R8, &r8) < 0)
1503 if (ia32 && r8 != -ENOSYS && !(tcp->flags & TCB_INSYSCALL)) {
1505 fprintf(stderr, "stray syscall exit: r8 = %ld\n", r8);
1508 #elif defined(CRISV10) || defined(CRISV32)
1509 if (upeek(tcp, 4*PT_R10, &r10) < 0)
1511 if (r10 != -ENOSYS && !(tcp->flags & TCB_INSYSCALL)) {
1513 fprintf(stderr, "stray syscall exit: r10 = %ld\n", r10);
1516 #elif defined(MICROBLAZE)
1517 if (upeek(tcp, 3 * 4, &r3) < 0)
1519 if (r3 != -ENOSYS && !(tcp->flags & TCB_INSYSCALL)) {
1521 fprintf(stderr, "stray syscall exit: r3 = %ld\n", r3);
1531 * Check the syscall return value register value for whether it is
1532 * a negated errno code indicating an error, or a success return value.
1535 is_negated_errno(unsigned long int val)
1537 unsigned long int max = -(long int) nerrnos;
1538 if (personality_wordsize[current_personality] < sizeof(val)) {
1539 val = (unsigned int) val;
1540 max = (unsigned int) max;
1547 get_error(struct tcb *tcp)
1551 int check_errno = 1;
1552 if (tcp->scno >= 0 && tcp->scno < nsyscalls &&
1553 sysent[tcp->scno].sys_flags & SYSCALL_NEVER_FAILS) {
1556 # if defined(S390) || defined(S390X)
1557 if (check_errno && is_negated_errno(gpr2)) {
1565 # elif defined(I386)
1566 if (check_errno && is_negated_errno(eax)) {
1574 # elif defined(X86_64)
1575 if (check_errno && is_negated_errno(rax)) {
1583 # elif defined(IA64)
1588 if (check_errno && is_negated_errno(err)) {
1597 if (check_errno && r10) {
1605 # elif defined(MIPS)
1606 if (check_errno && a3) {
1613 # elif defined(POWERPC)
1614 if (check_errno && is_negated_errno(result)) {
1619 tcp->u_rval = result;
1622 # elif defined(M68K)
1623 if (check_errno && is_negated_errno(d0)) {
1632 if (check_errno && is_negated_errno(regs.ARM_r0)) {
1634 u_error = -regs.ARM_r0;
1637 tcp->u_rval = regs.ARM_r0;
1640 # elif defined(AVR32)
1641 if (check_errno && regs.r12 && (unsigned) -regs.r12 < nerrnos) {
1643 u_error = -regs.r12;
1646 tcp->u_rval = regs.r12;
1649 # elif defined(BFIN)
1650 if (check_errno && is_negated_errno(r0)) {
1657 # elif defined(ALPHA)
1658 if (check_errno && a3) {
1666 # elif defined(SPARC)
1667 if (check_errno && regs.psr & PSR_C) {
1669 u_error = regs.u_regs[U_REG_O0];
1672 tcp->u_rval = regs.u_regs[U_REG_O0];
1675 # elif defined(SPARC64)
1676 if (check_errno && regs.tstate & 0x1100000000UL) {
1678 u_error = regs.u_regs[U_REG_O0];
1681 tcp->u_rval = regs.u_regs[U_REG_O0];
1684 # elif defined(HPPA)
1685 if (check_errno && is_negated_errno(r28)) {
1694 /* interpret R0 as return value or error number */
1695 if (check_errno && is_negated_errno(r0)) {
1703 # elif defined(SH64)
1704 /* interpret result as return value or error number */
1705 if (check_errno && is_negated_errno(r9)) {
1713 # elif defined(CRISV10) || defined(CRISV32)
1714 if (check_errno && r10 && (unsigned) -r10 < nerrnos) {
1722 # elif defined(TILE)
1724 /* interpret result as return value or error number */
1725 if (upeek(tcp, PTREGS_OFFSET_REG(0), &rval) < 0)
1727 if (check_errno && rval < 0 && rval > -nerrnos) {
1735 # elif defined(MICROBLAZE)
1736 /* interpret result as return value or error number */
1737 if (check_errno && is_negated_errno(r3)) {
1748 /* get error code from user struct */
1749 if (upeek(tcp, uoff(u_error), &u_error) < 0)
1751 u_error >>= 24; /* u_error is a char */
1753 /* get system call return value */
1754 if (upeek(tcp, uoff(u_rval1), &tcp->u_rval) < 0)
1759 /* Judicious guessing goes a long way. */
1760 if (tcp->status.pr_reg[R_PSR] & 0x100000) {
1762 u_error = tcp->status.pr_reg[R_O0];
1765 tcp->u_rval = tcp->status.pr_reg[R_O0];
1770 /* Wanna know how to kill an hour single-stepping? */
1771 if (tcp->status.PR_REG[EFL] & 0x1) {
1773 u_error = tcp->status.PR_REG[EAX];
1776 tcp->u_rval = tcp->status.PR_REG[EAX];
1777 # ifdef HAVE_LONG_LONG
1779 ((unsigned long long) tcp->status.PR_REG[EDX] << 32) +
1780 tcp->status.PR_REG[EAX];
1786 /* Wanna know how to kill an hour single-stepping? */
1787 if (tcp->status.PR_REG[EFLAGS] & 0x1) {
1789 u_error = tcp->status.PR_REG[RAX];
1792 tcp->u_rval = tcp->status.PR_REG[RAX];
1795 # endif /* X86_64 */
1797 if (tcp->status.pr_reg[CTX_A3]) {
1799 u_error = tcp->status.pr_reg[CTX_V0];
1802 tcp->u_rval = tcp->status.pr_reg[CTX_V0];
1808 if (regs.r_eflags & PSL_C) {
1810 u_error = regs.r_eax;
1812 tcp->u_rval = regs.r_eax;
1814 ((unsigned long long) regs.r_edx << 32) + regs.r_eax;
1817 #endif /* FREEBSD */
1818 tcp->u_error = u_error;
1823 force_result(struct tcb *tcp, int error, long rval)
1826 # if defined(S390) || defined(S390X)
1827 gpr2 = error ? -error : rval;
1828 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)PT_GPR2, gpr2) < 0)
1830 # elif defined(I386)
1831 eax = error ? -error : rval;
1832 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(EAX * 4), eax) < 0)
1834 # elif defined(X86_64)
1835 rax = error ? -error : rval;
1836 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(RAX * 8), rax) < 0)
1838 # elif defined(IA64)
1840 r8 = error ? -error : rval;
1841 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_R8), r8) < 0)
1853 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_R8), r8) < 0 ||
1854 ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_R10), r10) < 0)
1857 # elif defined(BFIN)
1858 r0 = error ? -error : rval;
1859 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)PT_R0, r0) < 0)
1861 # elif defined(MIPS)
1870 /* PTRACE_POKEUSER is OK even for n32 since rval is only a long. */
1871 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_A3), a3) < 0 ||
1872 ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_V0), r2) < 0)
1874 # elif defined(POWERPC)
1875 if (upeek(tcp, sizeof(unsigned long)*PT_CCR, &flags) < 0)
1885 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(sizeof(unsigned long)*PT_CCR), flags) < 0 ||
1886 ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(sizeof(unsigned long)*PT_R3), result) < 0)
1888 # elif defined(M68K)
1889 d0 = error ? -error : rval;
1890 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(4*PT_D0), d0) < 0)
1893 regs.ARM_r0 = error ? -error : rval;
1894 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(4*0), regs.ARM_r0) < 0)
1896 # elif defined(AVR32)
1897 regs.r12 = error ? -error : rval;
1898 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)REG_R12, regs.r12) < 0)
1900 # elif defined(ALPHA)
1909 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_A3), a3) < 0 ||
1910 ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(REG_R0), r0) < 0)
1912 # elif defined(SPARC)
1913 if (ptrace(PTRACE_GETREGS, tcp->pid, (char *)®s, 0) < 0)
1917 regs.u_regs[U_REG_O0] = error;
1921 regs.u_regs[U_REG_O0] = rval;
1923 if (ptrace(PTRACE_SETREGS, tcp->pid, (char *)®s, 0) < 0)
1925 # elif defined(SPARC64)
1926 if (ptrace(PTRACE_GETREGS, tcp->pid, (char *)®s, 0) < 0)
1929 regs.tstate |= 0x1100000000UL;
1930 regs.u_regs[U_REG_O0] = error;
1933 regs.tstate &= ~0x1100000000UL;
1934 regs.u_regs[U_REG_O0] = rval;
1936 if (ptrace(PTRACE_SETREGS, tcp->pid, (char *)®s, 0) < 0)
1938 # elif defined(HPPA)
1939 r28 = error ? -error : rval;
1940 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(PT_GR28), r28) < 0)
1943 r0 = error ? -error : rval;
1944 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)(4*REG_REG0), r0) < 0)
1946 # elif defined(SH64)
1947 r9 = error ? -error : rval;
1948 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)REG_GENERAL(9), r9) < 0)
1954 if (ptrace(PTRACE_POKEUSER, tcp->pid, (char*)uoff(u_error),
1956 ptrace(PTRACE_POKEUSER, tcp->pid, (char*)uoff(u_rval1), rval) < 0)
1966 if (pread(tcp->pfd_reg, ®s, sizeof(regs), 0) < 0) {
1971 regs.r_eflags |= PSL_C;
1975 regs.r_eflags &= ~PSL_C;
1978 if (pwrite(tcp->pfd_reg, ®s, sizeof(regs), 0) < 0) {
1982 #endif /* FREEBSD */
1984 /* All branches reach here on success (only). */
1985 tcp->u_error = error;
1991 syscall_enter(struct tcb *tcp)
1994 # if defined(S390) || defined(S390X)
1996 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
1997 tcp->u_nargs = sysent[tcp->scno].nargs;
1999 tcp->u_nargs = MAX_ARGS;
2000 for (i = 0; i < tcp->u_nargs; i++) {
2001 if (upeek(tcp, i==0 ? PT_ORIGGPR2 : PT_GPR2 + i*sizeof(long), &tcp->u_arg[i]) < 0)
2004 # elif defined(ALPHA)
2006 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2007 tcp->u_nargs = sysent[tcp->scno].nargs;
2009 tcp->u_nargs = MAX_ARGS;
2010 for (i = 0; i < tcp->u_nargs; i++) {
2011 /* WTA: if scno is out-of-bounds this will bomb. Add range-check
2012 * for scno somewhere above here!
2014 if (upeek(tcp, REG_A0+i, &tcp->u_arg[i]) < 0)
2017 # elif defined(IA64)
2019 unsigned long *out0, cfm, sof, sol, i;
2021 /* be backwards compatible with kernel < 2.4.4... */
2023 # define PT_RBS_END PT_AR_BSP
2026 if (upeek(tcp, PT_RBS_END, &rbs_end) < 0)
2028 if (upeek(tcp, PT_CFM, (long *) &cfm) < 0)
2031 sof = (cfm >> 0) & 0x7f;
2032 sol = (cfm >> 7) & 0x7f;
2033 out0 = ia64_rse_skip_regs((unsigned long *) rbs_end, -sof + sol);
2035 if (tcp->scno >= 0 && tcp->scno < nsyscalls
2036 && sysent[tcp->scno].nargs != -1)
2037 tcp->u_nargs = sysent[tcp->scno].nargs;
2039 tcp->u_nargs = MAX_ARGS;
2040 for (i = 0; i < tcp->u_nargs; ++i) {
2041 if (umoven(tcp, (unsigned long) ia64_rse_skip_regs(out0, i),
2042 sizeof(long), (char *) &tcp->u_arg[i]) < 0)
2048 if (/* EBX = out0 */
2049 upeek(tcp, PT_R11, (long *) &tcp->u_arg[0]) < 0
2051 || upeek(tcp, PT_R9, (long *) &tcp->u_arg[1]) < 0
2053 || upeek(tcp, PT_R10, (long *) &tcp->u_arg[2]) < 0
2055 || upeek(tcp, PT_R14, (long *) &tcp->u_arg[3]) < 0
2057 || upeek(tcp, PT_R15, (long *) &tcp->u_arg[4]) < 0
2059 || upeek(tcp, PT_R13, (long *) &tcp->u_arg[5]) < 0)
2062 for (i = 0; i < 6; ++i)
2063 /* truncate away IVE sign-extension */
2064 tcp->u_arg[i] &= 0xffffffff;
2066 if (tcp->scno >= 0 && tcp->scno < nsyscalls
2067 && sysent[tcp->scno].nargs != -1)
2068 tcp->u_nargs = sysent[tcp->scno].nargs;
2072 # elif defined(LINUX_MIPSN32) || defined(LINUX_MIPSN64)
2073 /* N32 and N64 both use up to six registers. */
2074 unsigned long long regs[38];
2076 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2077 nargs = tcp->u_nargs = sysent[tcp->scno].nargs;
2079 nargs = tcp->u_nargs = MAX_ARGS;
2081 if (ptrace(PTRACE_GETREGS, tcp->pid, NULL, (long) ®s) < 0)
2084 for (i = 0; i < nargs; i++) {
2085 tcp->u_arg[i] = regs[REG_A0 + i];
2086 # if defined(LINUX_MIPSN32)
2087 tcp->ext_arg[i] = regs[REG_A0 + i];
2090 # elif defined(MIPS)
2094 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2095 nargs = tcp->u_nargs = sysent[tcp->scno].nargs;
2097 nargs = tcp->u_nargs = MAX_ARGS;
2099 if (upeek(tcp, REG_SP, &sp) < 0)
2101 for (i = 0; i < 4; i++) {
2102 if (upeek(tcp, REG_A0 + i, &tcp->u_arg[i]) < 0)
2105 umoven(tcp, sp+16, (nargs-4) * sizeof(tcp->u_arg[0]),
2106 (char *)(tcp->u_arg + 4));
2108 for (i = 0; i < nargs; i++) {
2109 if (upeek(tcp, REG_A0 + i, &tcp->u_arg[i]) < 0)
2113 # elif defined(POWERPC)
2115 # define PT_ORIG_R3 34
2118 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2119 tcp->u_nargs = sysent[tcp->scno].nargs;
2121 tcp->u_nargs = MAX_ARGS;
2122 for (i = 0; i < tcp->u_nargs; i++) {
2123 if (upeek(tcp, (i==0) ?
2124 (sizeof(unsigned long) * PT_ORIG_R3) :
2125 ((i+PT_R3) * sizeof(unsigned long)),
2126 &tcp->u_arg[i]) < 0)
2129 # elif defined(SPARC) || defined(SPARC64)
2131 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2132 tcp->u_nargs = sysent[tcp->scno].nargs;
2134 tcp->u_nargs = MAX_ARGS;
2135 for (i = 0; i < tcp->u_nargs; i++)
2136 tcp->u_arg[i] = regs.u_regs[U_REG_O0 + i];
2137 # elif defined(HPPA)
2139 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2140 tcp->u_nargs = sysent[tcp->scno].nargs;
2142 tcp->u_nargs = MAX_ARGS;
2143 for (i = 0; i < tcp->u_nargs; i++) {
2144 if (upeek(tcp, PT_GR26-4*i, &tcp->u_arg[i]) < 0)
2149 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2150 tcp->u_nargs = sysent[tcp->scno].nargs;
2152 tcp->u_nargs = MAX_ARGS;
2153 for (i = 0; i < tcp->u_nargs; i++)
2154 tcp->u_arg[i] = regs.uregs[i];
2155 # elif defined(AVR32)
2156 tcp->u_nargs = sysent[tcp->scno].nargs;
2157 tcp->u_arg[0] = regs.r12;
2158 tcp->u_arg[1] = regs.r11;
2159 tcp->u_arg[2] = regs.r10;
2160 tcp->u_arg[3] = regs.r9;
2161 tcp->u_arg[4] = regs.r5;
2162 tcp->u_arg[5] = regs.r3;
2163 # elif defined(BFIN)
2165 static const int argreg[] = { PT_R0, PT_R1, PT_R2, PT_R3, PT_R4, PT_R5 };
2167 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2168 tcp->u_nargs = sysent[tcp->scno].nargs;
2170 tcp->u_nargs = ARRAY_SIZE(argreg);
2172 for (i = 0; i < tcp->u_nargs; ++i)
2173 if (upeek(tcp, argreg[i], &tcp->u_arg[i]) < 0)
2177 static const int syscall_regs[] = {
2178 4 * (REG_REG0+4), 4 * (REG_REG0+5), 4 * (REG_REG0+6), 4 * (REG_REG0+7),
2179 4 * (REG_REG0 ), 4 * (REG_REG0+1), 4 * (REG_REG0+2)
2182 tcp->u_nargs = sysent[tcp->scno].nargs;
2183 for (i = 0; i < tcp->u_nargs; i++) {
2184 if (upeek(tcp, syscall_regs[i], &tcp->u_arg[i]) < 0)
2187 # elif defined(SH64)
2189 /* Registers used by SH5 Linux system calls for parameters */
2190 static const int syscall_regs[] = { 2, 3, 4, 5, 6, 7 };
2193 * TODO: should also check that the number of arguments encoded
2194 * in the trap number matches the number strace expects.
2197 assert(sysent[tcp->scno].nargs < ARRAY_SIZE(syscall_regs));
2200 tcp->u_nargs = sysent[tcp->scno].nargs;
2201 for (i = 0; i < tcp->u_nargs; i++) {
2202 if (upeek(tcp, REG_GENERAL(syscall_regs[i]), &tcp->u_arg[i]) < 0)
2205 # elif defined(X86_64)
2207 static const int argreg[SUPPORTED_PERSONALITIES][MAX_ARGS] = {
2208 { 8 * RDI, 8 * RSI, 8 * RDX, 8 * R10, 8 * R8 , 8 * R9 }, /* x86-64 ABI */
2209 { 8 * RBX, 8 * RCX, 8 * RDX, 8 * RSI, 8 * RDI, 8 * RBP } /* i386 ABI */
2212 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2213 tcp->u_nargs = sysent[tcp->scno].nargs;
2215 tcp->u_nargs = MAX_ARGS;
2216 for (i = 0; i < tcp->u_nargs; i++) {
2217 if (upeek(tcp, argreg[current_personality][i], &tcp->u_arg[i]) < 0)
2220 # elif defined(MICROBLAZE)
2222 if (tcp->scno >= 0 && tcp->scno < nsyscalls)
2223 tcp->u_nargs = sysent[tcp->scno].nargs;
2226 for (i = 0; i < tcp->u_nargs; i++) {
2227 if (upeek(tcp, (5 + i) * 4, &tcp->u_arg[i]) < 0)
2230 # elif defined(CRISV10) || defined(CRISV32)
2232 static const int crisregs[] = {
2233 4*PT_ORIG_R10, 4*PT_R11, 4*PT_R12,
2234 4*PT_R13 , 4*PT_MOF, 4*PT_SRP
2237 if (tcp->scno >= 0 && tcp->scno < nsyscalls)
2238 tcp->u_nargs = sysent[tcp->scno].nargs;
2241 for (i = 0; i < tcp->u_nargs; i++) {
2242 if (upeek(tcp, crisregs[i], &tcp->u_arg[i]) < 0)
2245 # elif defined(TILE)
2247 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2248 tcp->u_nargs = sysent[tcp->scno].nargs;
2250 tcp->u_nargs = MAX_ARGS;
2251 for (i = 0; i < tcp->u_nargs; ++i) {
2252 if (upeek(tcp, PTREGS_OFFSET_REG(i), &tcp->u_arg[i]) < 0)
2255 # elif defined(M68K)
2257 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2258 tcp->u_nargs = sysent[tcp->scno].nargs;
2260 tcp->u_nargs = MAX_ARGS;
2261 for (i = 0; i < tcp->u_nargs; i++) {
2262 if (upeek(tcp, (i < 5 ? i : i + 2)*4, &tcp->u_arg[i]) < 0)
2265 # else /* Other architecture (like i386) (32bits specific) */
2267 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2268 tcp->u_nargs = sysent[tcp->scno].nargs;
2270 tcp->u_nargs = MAX_ARGS;
2271 for (i = 0; i < tcp->u_nargs; i++) {
2272 if (upeek(tcp, i*4, &tcp->u_arg[i]) < 0)
2279 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2280 tcp->u_nargs = sysent[tcp->scno].nargs;
2282 tcp->u_nargs = MAX_ARGS;
2283 for (i = 0; i < tcp->u_nargs; i++) {
2286 if (upeek(tcp, uoff(u_arg[0]) +
2287 (i * sizeof(u->u_arg[0])), &tcp->u_arg[i]) < 0)
2294 * SGI is broken: even though it has pr_sysarg, it doesn't
2295 * set them on system call entry. Get a clue.
2297 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2298 tcp->u_nargs = sysent[tcp->scno].nargs;
2300 tcp->u_nargs = tcp->status.pr_nsysarg;
2301 if (tcp->u_nargs > 4) {
2302 memcpy(tcp->u_arg, &tcp->status.pr_reg[CTX_A0],
2303 4 * sizeof(tcp->u_arg[0]));
2304 umoven(tcp, tcp->status.pr_reg[CTX_SP] + 16,
2305 (tcp->u_nargs - 4) * sizeof(tcp->u_arg[0]), (char *) (tcp->u_arg + 4));
2308 memcpy(tcp->u_arg, &tcp->status.pr_reg[CTX_A0],
2309 tcp->u_nargs * sizeof(tcp->u_arg[0]));
2311 # elif UNIXWARE >= 2
2313 * Like SGI, UnixWare doesn't set pr_sysarg until system call exit
2315 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2316 tcp->u_nargs = sysent[tcp->scno].nargs;
2318 tcp->u_nargs = tcp->status.pr_lwp.pr_nsysarg;
2319 umoven(tcp, tcp->status.PR_REG[UESP] + 4,
2320 tcp->u_nargs * sizeof(tcp->u_arg[0]), (char *) tcp->u_arg);
2321 # elif defined(HAVE_PR_SYSCALL)
2323 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2324 tcp->u_nargs = sysent[tcp->scno].nargs;
2326 tcp->u_nargs = tcp->status.pr_nsysarg;
2327 for (i = 0; i < tcp->u_nargs; i++)
2328 tcp->u_arg[i] = tcp->status.pr_sysarg[i];
2329 # elif defined(I386)
2330 if (tcp->scno >= 0 && tcp->scno < nsyscalls && sysent[tcp->scno].nargs != -1)
2331 tcp->u_nargs = sysent[tcp->scno].nargs;
2334 if (tcp->u_nargs > 0)
2335 umoven(tcp, tcp->status.PR_REG[UESP] + 4,
2336 tcp->u_nargs * sizeof(tcp->u_arg[0]), (char *) tcp->u_arg);
2338 I DONT KNOW WHAT TO DO
2342 if (tcp->scno >= 0 && tcp->scno < nsyscalls &&
2343 sysent[tcp->scno].nargs > tcp->status.val)
2344 tcp->u_nargs = sysent[tcp->scno].nargs;
2346 tcp->u_nargs = tcp->status.val;
2347 if (tcp->u_nargs < 0)
2349 if (tcp->u_nargs > MAX_ARGS)
2350 tcp->u_nargs = MAX_ARGS;
2351 switch (regs.r_eax) {
2353 pread(tcp->pfd, &tcp->u_arg, tcp->u_nargs * sizeof(unsigned long),
2354 regs.r_esp + sizeof(int) + sizeof(quad_t));
2357 pread(tcp->pfd, &tcp->u_arg, tcp->u_nargs * sizeof(unsigned long),
2358 regs.r_esp + 2 * sizeof(int));
2361 pread(tcp->pfd, &tcp->u_arg, tcp->u_nargs * sizeof(unsigned long),
2362 regs.r_esp + sizeof(int));
2365 #endif /* FREEBSD */
2370 trace_syscall_exiting(struct tcb *tcp)
2377 /* Measure the exit time as early as possible to avoid errors. */
2379 gettimeofday(&tv, NULL);
2381 /* BTW, why we don't just memorize syscall no. on entry
2382 * in tcp->something?
2384 scno_good = res = get_scno(tcp);
2388 res = syscall_fixup(tcp);
2392 res = get_error(tcp);
2396 internal_syscall(tcp);
2398 if (res == 1 && filtered(tcp)) {
2399 tcp->flags &= ~TCB_INSYSCALL;
2403 if (tcp->flags & TCB_REPRINT) {
2408 else if (tcp->scno >= nsyscalls || tcp->scno < 0)
2409 tprintf("syscall_%lu", tcp->scno);
2411 tprintf("%s", sysent[tcp->scno].sys_name);
2412 tprintf(" resumed> ");
2416 struct timeval t = tv;
2417 int rc = count_syscall(tcp, &t);
2418 if (cflag == CFLAG_ONLY_STATS) {
2419 tcp->flags &= ~TCB_INSYSCALL;
2427 tprintf("= ? <unavailable>");
2429 tcp->flags &= ~TCB_INSYSCALL;
2433 if (tcp->scno >= nsyscalls || tcp->scno < 0
2434 || (qual_flags[tcp->scno] & QUAL_RAW))
2435 sys_res = printargs(tcp);
2437 if (not_failing_only && tcp->u_error)
2438 return 0; /* ignore failed syscalls */
2439 sys_res = (*sysent[tcp->scno].sys_func)(tcp);
2442 u_error = tcp->u_error;
2445 if (tcp->scno >= nsyscalls || tcp->scno < 0 ||
2446 qual_flags[tcp->scno] & QUAL_RAW) {
2448 tprintf("= -1 (errno %ld)", u_error);
2450 tprintf("= %#lx", tcp->u_rval);
2452 else if (!(sys_res & RVAL_NONE) && u_error) {
2456 tprintf("= ? ERESTARTSYS (To be restarted)");
2458 case ERESTARTNOINTR:
2459 tprintf("= ? ERESTARTNOINTR (To be restarted)");
2461 case ERESTARTNOHAND:
2462 tprintf("= ? ERESTARTNOHAND (To be restarted)");
2464 case ERESTART_RESTARTBLOCK:
2465 tprintf("= ? ERESTART_RESTARTBLOCK (To be restarted)");
2471 tprintf("E??? (errno %ld)", u_error);
2472 else if (u_error < nerrnos)
2473 tprintf("%s (%s)", errnoent[u_error],
2476 tprintf("ERRNO_%ld (%s)", u_error,
2480 if ((sys_res & RVAL_STR) && tcp->auxstr)
2481 tprintf(" (%s)", tcp->auxstr);
2484 if (sys_res & RVAL_NONE)
2487 switch (sys_res & RVAL_MASK) {
2489 tprintf("= %#lx", tcp->u_rval);
2492 tprintf("= %#lo", tcp->u_rval);
2495 tprintf("= %lu", tcp->u_rval);
2498 tprintf("= %ld", tcp->u_rval);
2500 #ifdef HAVE_LONG_LONG
2502 tprintf("= %#llx", tcp->u_lrval);
2505 tprintf("= %#llo", tcp->u_lrval);
2507 case RVAL_LUDECIMAL:
2508 tprintf("= %llu", tcp->u_lrval);
2511 tprintf("= %lld", tcp->u_lrval);
2516 "invalid rval format\n");
2520 if ((sys_res & RVAL_STR) && tcp->auxstr)
2521 tprintf(" (%s)", tcp->auxstr);
2524 tv_sub(&tv, &tv, &tcp->etime);
2525 tprintf(" <%ld.%06ld>",
2526 (long) tv.tv_sec, (long) tv.tv_usec);
2531 if (fflush(tcp->outf) == EOF)
2533 tcp->flags &= ~TCB_INSYSCALL;
2538 trace_syscall_entering(struct tcb *tcp)
2543 scno_good = res = get_scno(tcp);
2547 res = syscall_fixup(tcp);
2551 res = syscall_enter(tcp);
2557 tcp->flags &= ~TCB_REPRINT;
2560 tprintf("????" /* anti-trigraph gap */ "(");
2561 else if (tcp->scno >= nsyscalls || tcp->scno < 0)
2562 tprintf("syscall_%lu(", tcp->scno);
2564 tprintf("%s(", sysent[tcp->scno].sys_name);
2566 * " <unavailable>" will be added later by the code which
2567 * detects ptrace errors.
2569 tcp->flags |= TCB_INSYSCALL;
2573 switch (known_scno(tcp)) {
2574 #ifdef SYS_socket_subcall
2575 case SYS_socketcall:
2576 decode_subcall(tcp, SYS_socket_subcall,
2577 SYS_socket_nsubcalls, deref_style);
2580 #ifdef SYS_ipc_subcall
2582 decode_subcall(tcp, SYS_ipc_subcall,
2583 SYS_ipc_nsubcalls, shift_style);
2587 #ifdef SYS_pgrpsys_subcall
2589 decode_subcall(tcp, SYS_pgrpsys_subcall,
2590 SYS_pgrpsys_nsubcalls, shift_style);
2592 #endif /* SYS_pgrpsys_subcall */
2593 #ifdef SYS_sigcall_subcall
2595 decode_subcall(tcp, SYS_sigcall_subcall,
2596 SYS_sigcall_nsubcalls, mask_style);
2598 #endif /* SYS_sigcall_subcall */
2600 decode_subcall(tcp, SYS_msgsys_subcall,
2601 SYS_msgsys_nsubcalls, shift_style);
2604 decode_subcall(tcp, SYS_shmsys_subcall,
2605 SYS_shmsys_nsubcalls, shift_style);
2608 decode_subcall(tcp, SYS_semsys_subcall,
2609 SYS_semsys_nsubcalls, shift_style);
2612 decode_subcall(tcp, SYS_sysfs_subcall,
2613 SYS_sysfs_nsubcalls, shift_style);
2616 decode_subcall(tcp, SYS_spcall_subcall,
2617 SYS_spcall_nsubcalls, shift_style);
2619 #ifdef SYS_context_subcall
2621 decode_subcall(tcp, SYS_context_subcall,
2622 SYS_context_nsubcalls, shift_style);
2624 #endif /* SYS_context_subcall */
2625 #ifdef SYS_door_subcall
2627 decode_subcall(tcp, SYS_door_subcall,
2628 SYS_door_nsubcalls, door_style);
2630 #endif /* SYS_door_subcall */
2631 #ifdef SYS_kaio_subcall
2633 decode_subcall(tcp, SYS_kaio_subcall,
2634 SYS_kaio_nsubcalls, shift_style);
2642 decode_subcall(tcp, 0, 0, table_style);
2647 decode_subcall(tcp, SYS_semsys_subcall,
2648 SYS_semsys_nsubcalls, shift_style);
2651 decode_subcall(tcp, SYS_msgsys_subcall,
2652 SYS_msgsys_nsubcalls, shift_style);
2655 decode_subcall(tcp, SYS_shmsys_subcall,
2656 SYS_shmsys_nsubcalls, shift_style);
2661 internal_syscall(tcp);
2663 if ((tcp->scno >= 0 && tcp->scno < nsyscalls &&
2664 !(qual_flags[tcp->scno] & QUAL_TRACE)) ||
2665 (tracing_paths && !pathtrace_match(tcp))) {
2666 tcp->flags |= TCB_INSYSCALL | TCB_FILTERED;
2670 tcp->flags &= ~TCB_FILTERED;
2672 if (cflag == CFLAG_ONLY_STATS) {
2673 tcp->flags |= TCB_INSYSCALL;
2674 gettimeofday(&tcp->etime, NULL);
2679 tcp->flags &= ~TCB_REPRINT;
2681 if (tcp->scno >= nsyscalls || tcp->scno < 0)
2682 tprintf("syscall_%lu(", tcp->scno);
2684 tprintf("%s(", sysent[tcp->scno].sys_name);
2685 if (tcp->scno >= nsyscalls || tcp->scno < 0 ||
2686 ((qual_flags[tcp->scno] & QUAL_RAW) &&
2687 sysent[tcp->scno].sys_func != sys_exit))
2688 sys_res = printargs(tcp);
2690 sys_res = (*sysent[tcp->scno].sys_func)(tcp);
2691 if (fflush(tcp->outf) == EOF)
2693 tcp->flags |= TCB_INSYSCALL;
2694 /* Measure the entrance time as late as possible to avoid errors. */
2696 gettimeofday(&tcp->etime, NULL);
2701 trace_syscall(struct tcb *tcp)
2703 return exiting(tcp) ?
2704 trace_syscall_exiting(tcp) : trace_syscall_entering(tcp);
2708 printargs(struct tcb *tcp)
2710 if (entering(tcp)) {
2713 for (i = 0; i < tcp->u_nargs; i++)
2714 tprintf("%s%#lx", i ? ", " : "", tcp->u_arg[i]);
2720 getrval2(struct tcb *tcp)
2725 #if defined (SPARC) || defined (SPARC64)
2726 struct pt_regs regs;
2727 if (ptrace(PTRACE_GETREGS, tcp->pid, (char *)®s, 0) < 0)
2729 val = regs.u_regs[U_REG_O1];
2731 if (upeek(tcp, 4*(REG_REG0+1), &val) < 0)
2734 if (upeek(tcp, PT_R9, &val) < 0)
2740 if (upeek(tcp, uoff(u_rval2), &val) < 0)
2746 val = tcp->status.PR_REG[R_O1];
2749 val = tcp->status.PR_REG[EDX];
2752 val = tcp->status.PR_REG[RDX];
2755 val = tcp->status.PR_REG[CTX_V1];
2761 pread(tcp->pfd_reg, ®s, sizeof(regs), 0);
2769 * Apparently, indirect system calls have already be converted by ptrace(2),
2770 * so if you see "indir" this program has gone astray.
2773 sys_indir(struct tcb *tcp)
2777 if (entering(tcp)) {
2778 if ((scno = tcp->u_arg[0]) > nsyscalls) {
2779 fprintf(stderr, "Bogus syscall: %u\n", scno);
2782 nargs = sysent[scno].nargs;
2783 tprintf("%s", sysent[scno].sys_name);
2784 for (i = 0; i < nargs; i++)
2785 tprintf(", %#lx", tcp->u_arg[i+1]);
2792 is_restart_error(struct tcb *tcp)
2797 switch (tcp->u_error) {
2799 case ERESTARTNOINTR:
2800 case ERESTARTNOHAND:
2801 case ERESTART_RESTARTBLOCK: