strace.c revision c9251518b005cc5adb3cc2ba1d68856ec8e94ad2
1/* 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 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 3. The name of the author may not be used to endorse or promote products 17 * derived from this software without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 20 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 21 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 22 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 23 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 24 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 29 */ 30 31#include "defs.h" 32#include <stdarg.h> 33#include <sys/param.h> 34#include <fcntl.h> 35#include <signal.h> 36#include <sys/resource.h> 37#include <sys/wait.h> 38#include <sys/stat.h> 39#include <pwd.h> 40#include <grp.h> 41#include <dirent.h> 42#include <sys/utsname.h> 43#ifdef HAVE_PRCTL 44# include <sys/prctl.h> 45#endif 46 47#include "ptrace.h" 48#include "printsiginfo.h" 49 50/* In some libc, these aren't declared. Do it ourself: */ 51extern char **environ; 52extern int optind; 53extern char *optarg; 54 55#ifdef USE_LIBUNWIND 56/* if this is true do the stack trace for every system call */ 57bool stack_trace_enabled = false; 58#endif 59 60#if defined __NR_tkill 61# define my_tkill(tid, sig) syscall(__NR_tkill, (tid), (sig)) 62#else 63 /* kill() may choose arbitrarily the target task of the process group 64 while we later wait on a that specific TID. PID process waits become 65 TID task specific waits for a process under ptrace(2). */ 66# warning "tkill(2) not available, risk of strace hangs!" 67# define my_tkill(tid, sig) kill((tid), (sig)) 68#endif 69 70/* Glue for systems without a MMU that cannot provide fork() */ 71#if !defined(HAVE_FORK) 72# undef NOMMU_SYSTEM 73# define NOMMU_SYSTEM 1 74#endif 75#if NOMMU_SYSTEM 76# define fork() vfork() 77#endif 78 79const unsigned int syscall_trap_sig = SIGTRAP | 0x80; 80 81cflag_t cflag = CFLAG_NONE; 82unsigned int followfork = 0; 83unsigned int ptrace_setoptions = PTRACE_O_TRACESYSGOOD | PTRACE_O_TRACEEXEC; 84unsigned int xflag = 0; 85bool debug_flag = 0; 86bool Tflag = 0; 87bool iflag = 0; 88bool count_wallclock = 0; 89unsigned int qflag = 0; 90static unsigned int tflag = 0; 91static bool rflag = 0; 92static bool print_pid_pfx = 0; 93 94/* -I n */ 95enum { 96 INTR_NOT_SET = 0, 97 INTR_ANYWHERE = 1, /* don't block/ignore any signals */ 98 INTR_WHILE_WAIT = 2, /* block fatal signals while decoding syscall. default */ 99 INTR_NEVER = 3, /* block fatal signals. default if '-o FILE PROG' */ 100 INTR_BLOCK_TSTP_TOO = 4, /* block fatal signals and SIGTSTP (^Z) */ 101 NUM_INTR_OPTS 102}; 103static int opt_intr; 104/* We play with signal mask only if this mode is active: */ 105#define interactive (opt_intr == INTR_WHILE_WAIT) 106 107/* 108 * daemonized_tracer supports -D option. 109 * With this option, strace forks twice. 110 * Unlike normal case, with -D *grandparent* process exec's, 111 * becoming a traced process. Child exits (this prevents traced process 112 * from having children it doesn't expect to have), and grandchild 113 * attaches to grandparent similarly to strace -p PID. 114 * This allows for more transparent interaction in cases 115 * when process and its parent are communicating via signals, 116 * wait() etc. Without -D, strace process gets lodged in between, 117 * disrupting parent<->child link. 118 */ 119static bool daemonized_tracer = 0; 120 121#if USE_SEIZE 122static int post_attach_sigstop = TCB_IGNORE_ONE_SIGSTOP; 123# define use_seize (post_attach_sigstop == 0) 124#else 125# define post_attach_sigstop TCB_IGNORE_ONE_SIGSTOP 126# define use_seize 0 127#endif 128 129/* Sometimes we want to print only succeeding syscalls. */ 130bool not_failing_only = 0; 131 132/* Show path associated with fd arguments */ 133unsigned int show_fd_path = 0; 134 135static bool detach_on_execve = 0; 136/* Are we "strace PROG" and need to skip detach on first execve? */ 137static bool skip_one_b_execve = 0; 138/* Are we "strace PROG" and need to hide everything until execve? */ 139bool hide_log_until_execve = 0; 140 141static int exit_code = 0; 142static int strace_child = 0; 143static int strace_tracer_pid = 0; 144 145static char *username = NULL; 146static uid_t run_uid; 147static gid_t run_gid; 148 149unsigned int max_strlen = DEFAULT_STRLEN; 150static int acolumn = DEFAULT_ACOLUMN; 151static char *acolumn_spaces; 152 153static char *outfname = NULL; 154/* If -ff, points to stderr. Else, it's our common output log */ 155static FILE *shared_log; 156 157struct tcb *printing_tcp = NULL; 158static struct tcb *current_tcp; 159 160static struct tcb **tcbtab; 161static unsigned int nprocs, tcbtabsize; 162static const char *progname; 163 164unsigned os_release; /* generated from uname()'s u.release */ 165 166static void detach(struct tcb *tcp); 167static void cleanup(void); 168static void interrupt(int sig); 169static sigset_t empty_set, blocked_set; 170 171#ifdef HAVE_SIG_ATOMIC_T 172static volatile sig_atomic_t interrupted; 173#else 174static volatile int interrupted; 175#endif 176 177#ifndef HAVE_STRERROR 178 179#if !HAVE_DECL_SYS_ERRLIST 180extern int sys_nerr; 181extern char *sys_errlist[]; 182#endif 183 184const char * 185strerror(int err_no) 186{ 187 static char buf[sizeof("Unknown error %d") + sizeof(int)*3]; 188 189 if (err_no < 1 || err_no >= sys_nerr) { 190 sprintf(buf, "Unknown error %d", err_no); 191 return buf; 192 } 193 return sys_errlist[err_no]; 194} 195 196#endif /* HAVE_STERRROR */ 197 198static void 199usage(void) 200{ 201 printf("\ 202usage: strace [-CdffhiqrtttTvVwxxy] [-I n] [-e expr]...\n\ 203 [-a column] [-o file] [-s strsize] [-P path]...\n\ 204 -p pid... / [-D] [-E var=val]... [-u username] PROG [ARGS]\n\ 205 or: strace -c[dfw] [-I n] [-e expr]... [-O overhead] [-S sortby]\n\ 206 -p pid... / [-D] [-E var=val]... [-u username] PROG [ARGS]\n\ 207\n\ 208Output format:\n\ 209 -a column alignment COLUMN for printing syscall results (default %d)\n\ 210 -i print instruction pointer at time of syscall\n\ 211 -o file send trace output to FILE instead of stderr\n\ 212 -q suppress messages about attaching, detaching, etc.\n\ 213 -r print relative timestamp\n\ 214 -s strsize limit length of print strings to STRSIZE chars (default %d)\n\ 215 -t print absolute timestamp\n\ 216 -tt print absolute timestamp with usecs\n\ 217 -T print time spent in each syscall\n\ 218 -x print non-ascii strings in hex\n\ 219 -xx print all strings in hex\n\ 220 -y print paths associated with file descriptor arguments\n\ 221 -yy print protocol specific information associated with socket file descriptors\n\ 222\n\ 223Statistics:\n\ 224 -c count time, calls, and errors for each syscall and report summary\n\ 225 -C like -c but also print regular output\n\ 226 -O overhead set overhead for tracing syscalls to OVERHEAD usecs\n\ 227 -S sortby sort syscall counts by: time, calls, name, nothing (default %s)\n\ 228 -w summarise syscall latency (default is system time)\n\ 229\n\ 230Filtering:\n\ 231 -e expr a qualifying expression: option=[!]all or option=[!]val1[,val2]...\n\ 232 options: trace, abbrev, verbose, raw, signal, read, write\n\ 233 -P path trace accesses to path\n\ 234\n\ 235Tracing:\n\ 236 -b execve detach on execve syscall\n\ 237 -D run tracer process as a detached grandchild, not as parent\n\ 238 -f follow forks\n\ 239 -ff follow forks with output into separate files\n\ 240 -I interruptible\n\ 241 1: no signals are blocked\n\ 242 2: fatal signals are blocked while decoding syscall (default)\n\ 243 3: fatal signals are always blocked (default if '-o FILE PROG')\n\ 244 4: fatal signals and SIGTSTP (^Z) are always blocked\n\ 245 (useful to make 'strace -o FILE PROG' not stop on ^Z)\n\ 246\n\ 247Startup:\n\ 248 -E var remove var from the environment for command\n\ 249 -E var=val put var=val in the environment for command\n\ 250 -p pid trace process with process id PID, may be repeated\n\ 251 -u username run command as username handling setuid and/or setgid\n\ 252\n\ 253Miscellaneous:\n\ 254 -d enable debug output to stderr\n\ 255 -v verbose mode: print unabbreviated argv, stat, termios, etc. args\n\ 256 -h print help message\n\ 257 -V print version\n\ 258" 259#ifdef USE_LIBUNWIND 260" -k obtain stack trace between each syscall (experimental)\n\ 261" 262#endif 263/* ancient, no one should use it 264-F -- attempt to follow vforks (deprecated, use -f)\n\ 265 */ 266/* this is broken, so don't document it 267-z -- print only succeeding syscalls\n\ 268 */ 269, DEFAULT_ACOLUMN, DEFAULT_STRLEN, DEFAULT_SORTBY); 270 exit(0); 271} 272 273static void ATTRIBUTE_NORETURN 274die(void) 275{ 276 if (strace_tracer_pid == getpid()) { 277 cflag = 0; 278 cleanup(); 279 } 280 exit(1); 281} 282 283static void verror_msg(int err_no, const char *fmt, va_list p) 284{ 285 char *msg; 286 287 fflush(NULL); 288 289 /* We want to print entire message with single fprintf to ensure 290 * message integrity if stderr is shared with other programs. 291 * Thus we use vasprintf + single fprintf. 292 */ 293 msg = NULL; 294 if (vasprintf(&msg, fmt, p) >= 0) { 295 if (err_no) 296 fprintf(stderr, "%s: %s: %s\n", progname, msg, strerror(err_no)); 297 else 298 fprintf(stderr, "%s: %s\n", progname, msg); 299 free(msg); 300 } else { 301 /* malloc in vasprintf failed, try it without malloc */ 302 fprintf(stderr, "%s: ", progname); 303 vfprintf(stderr, fmt, p); 304 if (err_no) 305 fprintf(stderr, ": %s\n", strerror(err_no)); 306 else 307 putc('\n', stderr); 308 } 309 /* We don't switch stderr to buffered, thus fprintf(stderr) 310 * always flushes its output and this is not necessary: */ 311 /* fflush(stderr); */ 312} 313 314void error_msg(const char *fmt, ...) 315{ 316 va_list p; 317 va_start(p, fmt); 318 verror_msg(0, fmt, p); 319 va_end(p); 320} 321 322void error_msg_and_die(const char *fmt, ...) 323{ 324 va_list p; 325 va_start(p, fmt); 326 verror_msg(0, fmt, p); 327 die(); 328} 329 330void error_msg_and_help(const char *fmt, ...) 331{ 332 if (fmt != NULL) { 333 va_list p; 334 va_start(p, fmt); 335 verror_msg(0, fmt, p); 336 } 337 fprintf(stderr, "Try '%s -h' for more information.\n", progname); 338 die(); 339} 340 341void perror_msg(const char *fmt, ...) 342{ 343 va_list p; 344 va_start(p, fmt); 345 verror_msg(errno, fmt, p); 346 va_end(p); 347} 348 349void perror_msg_and_die(const char *fmt, ...) 350{ 351 va_list p; 352 va_start(p, fmt); 353 verror_msg(errno, fmt, p); 354 die(); 355} 356 357static void 358error_opt_arg(int opt, const char *arg) 359{ 360 error_msg_and_help("invalid -%c argument: '%s'", opt, arg); 361} 362 363static const char *ptrace_attach_cmd; 364 365static int 366ptrace_attach_or_seize(int pid) 367{ 368#if USE_SEIZE 369 int r; 370 if (!use_seize) 371 return ptrace_attach_cmd = "PTRACE_ATTACH", 372 ptrace(PTRACE_ATTACH, pid, 0L, 0L); 373 r = ptrace(PTRACE_SEIZE, pid, 0L, (unsigned long) ptrace_setoptions); 374 if (r) 375 return ptrace_attach_cmd = "PTRACE_SEIZE", r; 376 r = ptrace(PTRACE_INTERRUPT, pid, 0L, 0L); 377 return ptrace_attach_cmd = "PTRACE_INTERRUPT", r; 378#else 379 return ptrace_attach_cmd = "PTRACE_ATTACH", 380 ptrace(PTRACE_ATTACH, pid, 0L, 0L); 381#endif 382} 383 384/* 385 * Used when we want to unblock stopped traced process. 386 * Should be only used with PTRACE_CONT, PTRACE_DETACH and PTRACE_SYSCALL. 387 * Returns 0 on success or if error was ESRCH 388 * (presumably process was killed while we talk to it). 389 * Otherwise prints error message and returns -1. 390 */ 391static int 392ptrace_restart(int op, struct tcb *tcp, int sig) 393{ 394 int err; 395 const char *msg; 396 397 errno = 0; 398 ptrace(op, tcp->pid, (void *) 0, (long) sig); 399 err = errno; 400 if (!err) 401 return 0; 402 403 msg = "SYSCALL"; 404 if (op == PTRACE_CONT) 405 msg = "CONT"; 406 if (op == PTRACE_DETACH) 407 msg = "DETACH"; 408#ifdef PTRACE_LISTEN 409 if (op == PTRACE_LISTEN) 410 msg = "LISTEN"; 411#endif 412 /* 413 * Why curcol != 0? Otherwise sometimes we get this: 414 * 415 * 10252 kill(10253, SIGKILL) = 0 416 * <ptrace(SYSCALL,10252):No such process>10253 ...next decode... 417 * 418 * 10252 died after we retrieved syscall exit data, 419 * but before we tried to restart it. Log looks ugly. 420 */ 421 if (current_tcp && current_tcp->curcol != 0) { 422 tprintf(" <ptrace(%s):%s>\n", msg, strerror(err)); 423 line_ended(); 424 } 425 if (err == ESRCH) 426 return 0; 427 errno = err; 428 perror_msg("ptrace(PTRACE_%s,pid:%d,sig:%d)", msg, tcp->pid, sig); 429 return -1; 430} 431 432static void 433set_cloexec_flag(int fd) 434{ 435 int flags, newflags; 436 437 flags = fcntl(fd, F_GETFD); 438 if (flags < 0) { 439 /* Can happen only if fd is bad. 440 * Should never happen: if it does, we have a bug 441 * in the caller. Therefore we just abort 442 * instead of propagating the error. 443 */ 444 perror_msg_and_die("fcntl(%d, F_GETFD)", fd); 445 } 446 447 newflags = flags | FD_CLOEXEC; 448 if (flags == newflags) 449 return; 450 451 fcntl(fd, F_SETFD, newflags); /* never fails */ 452} 453 454static void 455kill_save_errno(pid_t pid, int sig) 456{ 457 int saved_errno = errno; 458 459 (void) kill(pid, sig); 460 errno = saved_errno; 461} 462 463/* 464 * When strace is setuid executable, we have to swap uids 465 * before and after filesystem and process management operations. 466 */ 467static void 468swap_uid(void) 469{ 470 int euid = geteuid(), uid = getuid(); 471 472 if (euid != uid && setreuid(euid, uid) < 0) { 473 perror_msg_and_die("setreuid"); 474 } 475} 476 477#ifdef _LARGEFILE64_SOURCE 478# ifdef HAVE_FOPEN64 479# define fopen_for_output fopen64 480# else 481# define fopen_for_output fopen 482# endif 483# define struct_stat struct stat64 484# define stat_file stat64 485# define struct_dirent struct dirent64 486# define read_dir readdir64 487# define struct_rlimit struct rlimit64 488# define set_rlimit setrlimit64 489#else 490# define fopen_for_output fopen 491# define struct_stat struct stat 492# define stat_file stat 493# define struct_dirent struct dirent 494# define read_dir readdir 495# define struct_rlimit struct rlimit 496# define set_rlimit setrlimit 497#endif 498 499static FILE * 500strace_fopen(const char *path) 501{ 502 FILE *fp; 503 504 swap_uid(); 505 fp = fopen_for_output(path, "w"); 506 if (!fp) 507 perror_msg_and_die("Can't fopen '%s'", path); 508 swap_uid(); 509 set_cloexec_flag(fileno(fp)); 510 return fp; 511} 512 513static int popen_pid = 0; 514 515#ifndef _PATH_BSHELL 516# define _PATH_BSHELL "/bin/sh" 517#endif 518 519/* 520 * We cannot use standard popen(3) here because we have to distinguish 521 * popen child process from other processes we trace, and standard popen(3) 522 * does not export its child's pid. 523 */ 524static FILE * 525strace_popen(const char *command) 526{ 527 FILE *fp; 528 int pid; 529 int fds[2]; 530 531 swap_uid(); 532 if (pipe(fds) < 0) 533 perror_msg_and_die("pipe"); 534 535 set_cloexec_flag(fds[1]); /* never fails */ 536 537 pid = vfork(); 538 if (pid < 0) 539 perror_msg_and_die("vfork"); 540 541 if (pid == 0) { 542 /* child */ 543 close(fds[1]); 544 if (fds[0] != 0) { 545 if (dup2(fds[0], 0)) 546 perror_msg_and_die("dup2"); 547 close(fds[0]); 548 } 549 execl(_PATH_BSHELL, "sh", "-c", command, NULL); 550 perror_msg_and_die("Can't execute '%s'", _PATH_BSHELL); 551 } 552 553 /* parent */ 554 popen_pid = pid; 555 close(fds[0]); 556 swap_uid(); 557 fp = fdopen(fds[1], "w"); 558 if (!fp) 559 die_out_of_memory(); 560 return fp; 561} 562 563void 564tprintf(const char *fmt, ...) 565{ 566 va_list args; 567 568 va_start(args, fmt); 569 if (current_tcp) { 570 int n = strace_vfprintf(current_tcp->outf, fmt, args); 571 if (n < 0) { 572 if (current_tcp->outf != stderr) 573 perror_msg("%s", outfname); 574 } else 575 current_tcp->curcol += n; 576 } 577 va_end(args); 578} 579 580#ifndef HAVE_FPUTS_UNLOCKED 581# define fputs_unlocked fputs 582#endif 583 584void 585tprints(const char *str) 586{ 587 if (current_tcp) { 588 int n = fputs_unlocked(str, current_tcp->outf); 589 if (n >= 0) { 590 current_tcp->curcol += strlen(str); 591 return; 592 } 593 if (current_tcp->outf != stderr) 594 perror_msg("%s", outfname); 595 } 596} 597 598void 599line_ended(void) 600{ 601 if (current_tcp) { 602 current_tcp->curcol = 0; 603 fflush(current_tcp->outf); 604 } 605 if (printing_tcp) { 606 printing_tcp->curcol = 0; 607 printing_tcp = NULL; 608 } 609} 610 611void 612printleader(struct tcb *tcp) 613{ 614 /* If -ff, "previous tcb we printed" is always the same as current, 615 * because we have per-tcb output files. 616 */ 617 if (followfork >= 2) 618 printing_tcp = tcp; 619 620 if (printing_tcp) { 621 current_tcp = printing_tcp; 622 if (printing_tcp->curcol != 0 && (followfork < 2 || printing_tcp == tcp)) { 623 /* 624 * case 1: we have a shared log (i.e. not -ff), and last line 625 * wasn't finished (same or different tcb, doesn't matter). 626 * case 2: split log, we are the same tcb, but our last line 627 * didn't finish ("SIGKILL nuked us after syscall entry" etc). 628 */ 629 tprints(" <unfinished ...>\n"); 630 printing_tcp->curcol = 0; 631 } 632 } 633 634 printing_tcp = tcp; 635 current_tcp = tcp; 636 current_tcp->curcol = 0; 637 638 if (print_pid_pfx) 639 tprintf("%-5d ", tcp->pid); 640 else if (nprocs > 1 && !outfname) 641 tprintf("[pid %5u] ", tcp->pid); 642 643 if (tflag) { 644 char str[sizeof("HH:MM:SS")]; 645 struct timeval tv, dtv; 646 static struct timeval otv; 647 648 gettimeofday(&tv, NULL); 649 if (rflag) { 650 if (otv.tv_sec == 0) 651 otv = tv; 652 tv_sub(&dtv, &tv, &otv); 653 tprintf("%6ld.%06ld ", 654 (long) dtv.tv_sec, (long) dtv.tv_usec); 655 otv = tv; 656 } 657 else if (tflag > 2) { 658 tprintf("%ld.%06ld ", 659 (long) tv.tv_sec, (long) tv.tv_usec); 660 } 661 else { 662 time_t local = tv.tv_sec; 663 strftime(str, sizeof(str), "%T", localtime(&local)); 664 if (tflag > 1) 665 tprintf("%s.%06ld ", str, (long) tv.tv_usec); 666 else 667 tprintf("%s ", str); 668 } 669 } 670 if (iflag) 671 print_pc(tcp); 672} 673 674void 675tabto(void) 676{ 677 if (current_tcp->curcol < acolumn) 678 tprints(acolumn_spaces + current_tcp->curcol); 679} 680 681/* Should be only called directly *after successful attach* to a tracee. 682 * Otherwise, "strace -oFILE -ff -p<nonexistant_pid>" 683 * may create bogus empty FILE.<nonexistant_pid>, and then die. 684 */ 685static void 686newoutf(struct tcb *tcp) 687{ 688 tcp->outf = shared_log; /* if not -ff mode, the same file is for all */ 689 if (followfork >= 2) { 690 char name[520 + sizeof(int) * 3]; 691 sprintf(name, "%.512s.%u", outfname, tcp->pid); 692 tcp->outf = strace_fopen(name); 693 } 694} 695 696static void 697expand_tcbtab(void) 698{ 699 /* Allocate some (more) TCBs (and expand the table). 700 We don't want to relocate the TCBs because our 701 callers have pointers and it would be a pain. 702 So tcbtab is a table of pointers. Since we never 703 free the TCBs, we allocate a single chunk of many. */ 704 unsigned int new_tcbtabsize, alloc_tcbtabsize; 705 struct tcb *newtcbs; 706 707 if (tcbtabsize) { 708 alloc_tcbtabsize = tcbtabsize; 709 new_tcbtabsize = tcbtabsize * 2; 710 } else { 711 new_tcbtabsize = alloc_tcbtabsize = 1; 712 } 713 714 newtcbs = xcalloc(alloc_tcbtabsize, sizeof(newtcbs[0])); 715 tcbtab = xreallocarray(tcbtab, new_tcbtabsize, sizeof(tcbtab[0])); 716 while (tcbtabsize < new_tcbtabsize) 717 tcbtab[tcbtabsize++] = newtcbs++; 718} 719 720static struct tcb * 721alloctcb(int pid) 722{ 723 unsigned int i; 724 struct tcb *tcp; 725 726 if (nprocs == tcbtabsize) 727 expand_tcbtab(); 728 729 for (i = 0; i < tcbtabsize; i++) { 730 tcp = tcbtab[i]; 731 if (!tcp->pid) { 732 memset(tcp, 0, sizeof(*tcp)); 733 tcp->pid = pid; 734#if SUPPORTED_PERSONALITIES > 1 735 tcp->currpers = current_personality; 736#endif 737 738#ifdef USE_LIBUNWIND 739 if (stack_trace_enabled) 740 unwind_tcb_init(tcp); 741#endif 742 743 nprocs++; 744 if (debug_flag) 745 error_msg("new tcb for pid %d, active tcbs:%d", 746 tcp->pid, nprocs); 747 return tcp; 748 } 749 } 750 error_msg_and_die("bug in alloctcb"); 751} 752 753void * 754get_tcb_priv_data(const struct tcb *tcp) 755{ 756 return tcp->_priv_data; 757} 758 759int 760set_tcb_priv_data(struct tcb *tcp, void *const priv_data, 761 void (*const free_priv_data)(void *)) 762{ 763 if (tcp->_priv_data) 764 return -1; 765 766 tcp->_free_priv_data = free_priv_data; 767 tcp->_priv_data = priv_data; 768 769 return 0; 770} 771 772void 773free_tcb_priv_data(struct tcb *tcp) 774{ 775 if (tcp->_priv_data) { 776 if (tcp->_free_priv_data) { 777 tcp->_free_priv_data(tcp->_priv_data); 778 tcp->_free_priv_data = NULL; 779 } 780 tcp->_priv_data = NULL; 781 } 782} 783 784static void 785droptcb(struct tcb *tcp) 786{ 787 if (tcp->pid == 0) 788 return; 789 790 free_tcb_priv_data(tcp); 791 792#ifdef USE_LIBUNWIND 793 if (stack_trace_enabled) { 794 unwind_tcb_fin(tcp); 795 } 796#endif 797 798 nprocs--; 799 if (debug_flag) 800 error_msg("dropped tcb for pid %d, %d remain", 801 tcp->pid, nprocs); 802 803 if (tcp->outf) { 804 if (followfork >= 2) { 805 if (tcp->curcol != 0) 806 fprintf(tcp->outf, " <detached ...>\n"); 807 fclose(tcp->outf); 808 } else { 809 if (printing_tcp == tcp && tcp->curcol != 0) 810 fprintf(tcp->outf, " <detached ...>\n"); 811 fflush(tcp->outf); 812 } 813 } 814 815 if (current_tcp == tcp) 816 current_tcp = NULL; 817 if (printing_tcp == tcp) 818 printing_tcp = NULL; 819 820 memset(tcp, 0, sizeof(*tcp)); 821} 822 823/* Detach traced process. 824 * Never call DETACH twice on the same process as both unattached and 825 * attached-unstopped processes give the same ESRCH. For unattached process we 826 * would SIGSTOP it and wait for its SIGSTOP notification forever. 827 */ 828static void 829detach(struct tcb *tcp) 830{ 831 int error; 832 int status; 833 834 /* 835 * Linux wrongly insists the child be stopped 836 * before detaching. Arghh. We go through hoops 837 * to make a clean break of things. 838 */ 839#if defined(SPARC) 840# undef PTRACE_DETACH 841# define PTRACE_DETACH PTRACE_SUNDETACH 842#endif 843 844 if (!(tcp->flags & TCB_ATTACHED)) 845 goto drop; 846 847 /* We attached but possibly didn't see the expected SIGSTOP. 848 * We must catch exactly one as otherwise the detached process 849 * would be left stopped (process state T). 850 */ 851 if (tcp->flags & TCB_IGNORE_ONE_SIGSTOP) 852 goto wait_loop; 853 854 error = ptrace(PTRACE_DETACH, tcp->pid, 0, 0); 855 if (!error) { 856 /* On a clear day, you can see forever. */ 857 goto drop; 858 } 859 if (errno != ESRCH) { 860 /* Shouldn't happen. */ 861 perror_msg("detach: ptrace(PTRACE_DETACH,%u)", tcp->pid); 862 goto drop; 863 } 864 /* ESRCH: process is either not stopped or doesn't exist. */ 865 if (my_tkill(tcp->pid, 0) < 0) { 866 if (errno != ESRCH) 867 /* Shouldn't happen. */ 868 perror_msg("detach: tkill(%u,0)", tcp->pid); 869 /* else: process doesn't exist. */ 870 goto drop; 871 } 872 /* Process is not stopped, need to stop it. */ 873 if (use_seize) { 874 /* 875 * With SEIZE, tracee can be in group-stop already. 876 * In this state sending it another SIGSTOP does nothing. 877 * Need to use INTERRUPT. 878 * Testcase: trying to ^C a "strace -p <stopped_process>". 879 */ 880 error = ptrace(PTRACE_INTERRUPT, tcp->pid, 0, 0); 881 if (!error) 882 goto wait_loop; 883 if (errno != ESRCH) 884 perror_msg("detach: ptrace(PTRACE_INTERRUPT,%u)", tcp->pid); 885 } 886 else { 887 error = my_tkill(tcp->pid, SIGSTOP); 888 if (!error) 889 goto wait_loop; 890 if (errno != ESRCH) 891 perror_msg("detach: tkill(%u,SIGSTOP)", tcp->pid); 892 } 893 /* Either process doesn't exist, or some weird error. */ 894 goto drop; 895 896 wait_loop: 897 /* We end up here in three cases: 898 * 1. We sent PTRACE_INTERRUPT (use_seize case) 899 * 2. We sent SIGSTOP (!use_seize) 900 * 3. Attach SIGSTOP was already pending (TCB_IGNORE_ONE_SIGSTOP set) 901 */ 902 for (;;) { 903 unsigned int sig; 904 if (waitpid(tcp->pid, &status, __WALL) < 0) { 905 if (errno == EINTR) 906 continue; 907 /* 908 * if (errno == ECHILD) break; 909 * ^^^ WRONG! We expect this PID to exist, 910 * and want to emit a message otherwise: 911 */ 912 perror_msg("detach: waitpid(%u)", tcp->pid); 913 break; 914 } 915 if (!WIFSTOPPED(status)) { 916 /* 917 * Tracee exited or was killed by signal. 918 * We shouldn't normally reach this place: 919 * we don't want to consume exit status. 920 * Consider "strace -p PID" being ^C-ed: 921 * we want merely to detach from PID. 922 * 923 * However, we _can_ end up here if tracee 924 * was SIGKILLed. 925 */ 926 break; 927 } 928 sig = WSTOPSIG(status); 929 if (debug_flag) 930 error_msg("detach wait: event:%d sig:%d", 931 (unsigned)status >> 16, sig); 932 if (use_seize) { 933 unsigned event = (unsigned)status >> 16; 934 if (event == PTRACE_EVENT_STOP /*&& sig == SIGTRAP*/) { 935 /* 936 * sig == SIGTRAP: PTRACE_INTERRUPT stop. 937 * sig == other: process was already stopped 938 * with this stopping sig (see tests/detach-stopped). 939 * Looks like re-injecting this sig is not necessary 940 * in DETACH for the tracee to remain stopped. 941 */ 942 sig = 0; 943 } 944 /* 945 * PTRACE_INTERRUPT is not guaranteed to produce 946 * the above event if other ptrace-stop is pending. 947 * See tests/detach-sleeping testcase: 948 * strace got SIGINT while tracee is sleeping. 949 * We sent PTRACE_INTERRUPT. 950 * We see syscall exit, not PTRACE_INTERRUPT stop. 951 * We won't get PTRACE_INTERRUPT stop 952 * if we would CONT now. Need to DETACH. 953 */ 954 if (sig == syscall_trap_sig) 955 sig = 0; 956 /* else: not sure in which case we can be here. 957 * Signal stop? Inject it while detaching. 958 */ 959 ptrace_restart(PTRACE_DETACH, tcp, sig); 960 break; 961 } 962 /* Note: this check has to be after use_seize check */ 963 /* (else, in use_seize case SIGSTOP will be mistreated) */ 964 if (sig == SIGSTOP) { 965 /* Detach, suppressing SIGSTOP */ 966 ptrace_restart(PTRACE_DETACH, tcp, 0); 967 break; 968 } 969 if (sig == syscall_trap_sig) 970 sig = 0; 971 /* Can't detach just yet, may need to wait for SIGSTOP */ 972 error = ptrace_restart(PTRACE_CONT, tcp, sig); 973 if (error < 0) { 974 /* Should not happen. 975 * Note: ptrace_restart returns 0 on ESRCH, so it's not it. 976 * ptrace_restart already emitted error message. 977 */ 978 break; 979 } 980 } 981 982 drop: 983 if (!qflag && (tcp->flags & TCB_ATTACHED)) 984 error_msg("Process %u detached", tcp->pid); 985 986 droptcb(tcp); 987} 988 989static void 990process_opt_p_list(char *opt) 991{ 992 while (*opt) { 993 /* 994 * We accept -p PID,PID; -p "`pidof PROG`"; -p "`pgrep PROG`". 995 * pidof uses space as delim, pgrep uses newline. :( 996 */ 997 int pid; 998 char *delim = opt + strcspn(opt, ", \n\t"); 999 char c = *delim; 1000 1001 *delim = '\0'; 1002 pid = string_to_uint(opt); 1003 if (pid <= 0) { 1004 error_msg_and_die("Invalid process id: '%s'", opt); 1005 } 1006 if (pid == strace_tracer_pid) { 1007 error_msg_and_die("I'm sorry, I can't let you do that, Dave."); 1008 } 1009 *delim = c; 1010 alloctcb(pid); 1011 if (c == '\0') 1012 break; 1013 opt = delim + 1; 1014 } 1015} 1016 1017static void 1018attach_tcb(struct tcb *const tcp) 1019{ 1020 if (followfork && tcp->pid != strace_child) { 1021 char procdir[sizeof("/proc/%d/task") + sizeof(int) * 3]; 1022 sprintf(procdir, "/proc/%d/task", tcp->pid); 1023 1024 DIR *dir = opendir(procdir); 1025 if (dir != NULL) { 1026 unsigned int ntid = 0, nerr = 0; 1027 struct_dirent *de; 1028 1029 while ((de = read_dir(dir)) != NULL) { 1030 if (de->d_fileno == 0) 1031 continue; 1032 1033 int tid = string_to_uint(de->d_name); 1034 if (tid <= 0) 1035 continue; 1036 1037 ++ntid; 1038 if (ptrace_attach_or_seize(tid) < 0) { 1039 ++nerr; 1040 if (debug_flag) 1041 perror_msg("attach: ptrace(%s, %d)", 1042 ptrace_attach_cmd, tid); 1043 continue; 1044 } 1045 if (debug_flag) 1046 error_msg("attach to pid %d succeeded", tid); 1047 1048 struct tcb *tid_tcp = 1049 (tid == tcp->pid) ? tcp : alloctcb(tid); 1050 tid_tcp->flags |= TCB_ATTACHED | TCB_STARTUP | post_attach_sigstop; 1051 newoutf(tid_tcp); 1052 } 1053 1054 closedir(dir); 1055 1056 ntid -= nerr; 1057 if (ntid == 0) { 1058 perror_msg("attach: ptrace(PTRACE_ATTACH, ...)"); 1059 droptcb(tcp); 1060 return; 1061 } 1062 1063 if (!qflag) { 1064 if (ntid > 1) 1065 error_msg("Process %u attached" 1066 " with %u threads", 1067 tcp->pid, ntid); 1068 else 1069 error_msg("Process %u attached", 1070 tcp->pid); 1071 } 1072 1073 if (!(tcp->flags & TCB_ATTACHED)) { 1074 /* -p PID, we failed to attach to PID itself 1075 * but did attach to some of its sibling threads. 1076 * Drop PID's tcp. 1077 */ 1078 droptcb(tcp); 1079 } 1080 1081 return; 1082 } /* if (opendir worked) */ 1083 } /* if (-f) */ 1084 1085 if (ptrace_attach_or_seize(tcp->pid) < 0) { 1086 perror_msg("attach: ptrace(%s, %d)", 1087 ptrace_attach_cmd, tcp->pid); 1088 droptcb(tcp); 1089 return; 1090 } 1091 1092 tcp->flags |= TCB_ATTACHED | TCB_STARTUP | post_attach_sigstop; 1093 newoutf(tcp); 1094 if (debug_flag) 1095 error_msg("attach to pid %d (main) succeeded", tcp->pid); 1096 1097 if (!qflag) 1098 error_msg("Process %u attached", tcp->pid); 1099} 1100 1101static void 1102startup_attach(void) 1103{ 1104 pid_t parent_pid = strace_tracer_pid; 1105 unsigned int tcbi; 1106 struct tcb *tcp; 1107 1108 /* 1109 * Block user interruptions as we would leave the traced 1110 * process stopped (process state T) if we would terminate in 1111 * between PTRACE_ATTACH and wait4() on SIGSTOP. 1112 * We rely on cleanup() from this point on. 1113 */ 1114 if (interactive) 1115 sigprocmask(SIG_BLOCK, &blocked_set, NULL); 1116 1117 if (daemonized_tracer) { 1118 pid_t pid = fork(); 1119 if (pid < 0) { 1120 perror_msg_and_die("fork"); 1121 } 1122 if (pid) { /* parent */ 1123 /* 1124 * Wait for grandchild to attach to straced process 1125 * (grandparent). Grandchild SIGKILLs us after it attached. 1126 * Grandparent's wait() is unblocked by our death, 1127 * it proceeds to exec the straced program. 1128 */ 1129 pause(); 1130 _exit(0); /* paranoia */ 1131 } 1132 /* grandchild */ 1133 /* We will be the tracer process. Remember our new pid: */ 1134 strace_tracer_pid = getpid(); 1135 } 1136 1137 for (tcbi = 0; tcbi < tcbtabsize; tcbi++) { 1138 tcp = tcbtab[tcbi]; 1139 1140 if (!tcp->pid) 1141 continue; 1142 1143 /* Is this a process we should attach to, but not yet attached? */ 1144 if (tcp->flags & TCB_ATTACHED) 1145 continue; /* no, we already attached it */ 1146 1147 if (tcp->pid == parent_pid || tcp->pid == strace_tracer_pid) { 1148 errno = EPERM; 1149 perror_msg("attach: pid %d", tcp->pid); 1150 droptcb(tcp); 1151 continue; 1152 } 1153 1154 attach_tcb(tcp); 1155 1156 if (interactive) { 1157 sigprocmask(SIG_SETMASK, &empty_set, NULL); 1158 if (interrupted) 1159 goto ret; 1160 sigprocmask(SIG_BLOCK, &blocked_set, NULL); 1161 } 1162 } /* for each tcbtab[] */ 1163 1164 if (daemonized_tracer) { 1165 /* 1166 * Make parent go away. 1167 * Also makes grandparent's wait() unblock. 1168 */ 1169 kill(parent_pid, SIGKILL); 1170 strace_child = 0; 1171 } 1172 1173 ret: 1174 if (interactive) 1175 sigprocmask(SIG_SETMASK, &empty_set, NULL); 1176} 1177 1178/* Stack-o-phobic exec helper, in the hope to work around 1179 * NOMMU + "daemonized tracer" difficulty. 1180 */ 1181struct exec_params { 1182 int fd_to_close; 1183 uid_t run_euid; 1184 gid_t run_egid; 1185 char **argv; 1186 char *pathname; 1187}; 1188static struct exec_params params_for_tracee; 1189 1190static void ATTRIBUTE_NOINLINE ATTRIBUTE_NORETURN 1191exec_or_die(void) 1192{ 1193 struct exec_params *params = ¶ms_for_tracee; 1194 1195 if (params->fd_to_close >= 0) 1196 close(params->fd_to_close); 1197 if (!daemonized_tracer && !use_seize) { 1198 if (ptrace(PTRACE_TRACEME, 0L, 0L, 0L) < 0) { 1199 perror_msg_and_die("ptrace(PTRACE_TRACEME, ...)"); 1200 } 1201 } 1202 1203 if (username != NULL) { 1204 /* 1205 * It is important to set groups before we 1206 * lose privileges on setuid. 1207 */ 1208 if (initgroups(username, run_gid) < 0) { 1209 perror_msg_and_die("initgroups"); 1210 } 1211 if (setregid(run_gid, params->run_egid) < 0) { 1212 perror_msg_and_die("setregid"); 1213 } 1214 if (setreuid(run_uid, params->run_euid) < 0) { 1215 perror_msg_and_die("setreuid"); 1216 } 1217 } 1218 else if (geteuid() != 0) 1219 if (setreuid(run_uid, run_uid) < 0) { 1220 perror_msg_and_die("setreuid"); 1221 } 1222 1223 if (!daemonized_tracer) { 1224 /* 1225 * Induce a ptrace stop. Tracer (our parent) 1226 * will resume us with PTRACE_SYSCALL and display 1227 * the immediately following execve syscall. 1228 * Can't do this on NOMMU systems, we are after 1229 * vfork: parent is blocked, stopping would deadlock. 1230 */ 1231 if (!NOMMU_SYSTEM) 1232 kill(getpid(), SIGSTOP); 1233 } else { 1234 alarm(3); 1235 /* we depend on SIGCHLD set to SIG_DFL by init code */ 1236 /* if it happens to be SIG_IGN'ed, wait won't block */ 1237 wait(NULL); 1238 alarm(0); 1239 } 1240 1241 execv(params->pathname, params->argv); 1242 perror_msg_and_die("exec"); 1243} 1244 1245static int 1246open_dummy_desc(void) 1247{ 1248 int fds[2]; 1249 1250 if (pipe(fds)) 1251 perror_msg_and_die("pipe"); 1252 close(fds[1]); 1253 return fds[0]; 1254} 1255 1256static void 1257startup_child(char **argv) 1258{ 1259 struct_stat statbuf; 1260 const char *filename; 1261 size_t filename_len; 1262 char pathname[PATH_MAX]; 1263 int pid; 1264 struct tcb *tcp; 1265 1266 filename = argv[0]; 1267 filename_len = strlen(filename); 1268 1269 if (filename_len > sizeof(pathname) - 1) { 1270 errno = ENAMETOOLONG; 1271 perror_msg_and_die("exec"); 1272 } 1273 if (strchr(filename, '/')) { 1274 strcpy(pathname, filename); 1275 } 1276#ifdef USE_DEBUGGING_EXEC 1277 /* 1278 * Debuggers customarily check the current directory 1279 * first regardless of the path but doing that gives 1280 * security geeks a panic attack. 1281 */ 1282 else if (stat_file(filename, &statbuf) == 0) 1283 strcpy(pathname, filename); 1284#endif /* USE_DEBUGGING_EXEC */ 1285 else { 1286 const char *path; 1287 size_t m, n, len; 1288 1289 for (path = getenv("PATH"); path && *path; path += m) { 1290 const char *colon = strchr(path, ':'); 1291 if (colon) { 1292 n = colon - path; 1293 m = n + 1; 1294 } 1295 else 1296 m = n = strlen(path); 1297 if (n == 0) { 1298 if (!getcwd(pathname, PATH_MAX)) 1299 continue; 1300 len = strlen(pathname); 1301 } 1302 else if (n > sizeof pathname - 1) 1303 continue; 1304 else { 1305 strncpy(pathname, path, n); 1306 len = n; 1307 } 1308 if (len && pathname[len - 1] != '/') 1309 pathname[len++] = '/'; 1310 if (filename_len + len > sizeof(pathname) - 1) 1311 continue; 1312 strcpy(pathname + len, filename); 1313 if (stat_file(pathname, &statbuf) == 0 && 1314 /* Accept only regular files 1315 with some execute bits set. 1316 XXX not perfect, might still fail */ 1317 S_ISREG(statbuf.st_mode) && 1318 (statbuf.st_mode & 0111)) 1319 break; 1320 } 1321 if (!path || !*path) 1322 pathname[0] = '\0'; 1323 } 1324 if (stat_file(pathname, &statbuf) < 0) { 1325 perror_msg_and_die("Can't stat '%s'", filename); 1326 } 1327 1328 params_for_tracee.fd_to_close = (shared_log != stderr) ? fileno(shared_log) : -1; 1329 params_for_tracee.run_euid = (statbuf.st_mode & S_ISUID) ? statbuf.st_uid : run_uid; 1330 params_for_tracee.run_egid = (statbuf.st_mode & S_ISGID) ? statbuf.st_gid : run_gid; 1331 params_for_tracee.argv = argv; 1332 /* 1333 * On NOMMU, can be safely freed only after execve in tracee. 1334 * It's hard to know when that happens, so we just leak it. 1335 */ 1336 params_for_tracee.pathname = NOMMU_SYSTEM ? xstrdup(pathname) : pathname; 1337 1338#if defined HAVE_PRCTL && defined PR_SET_PTRACER && defined PR_SET_PTRACER_ANY 1339 if (daemonized_tracer) 1340 prctl(PR_SET_PTRACER, PR_SET_PTRACER_ANY); 1341#endif 1342 1343 pid = fork(); 1344 if (pid < 0) { 1345 perror_msg_and_die("fork"); 1346 } 1347 if ((pid != 0 && daemonized_tracer) 1348 || (pid == 0 && !daemonized_tracer) 1349 ) { 1350 /* We are to become the tracee. Two cases: 1351 * -D: we are parent 1352 * not -D: we are child 1353 */ 1354 exec_or_die(); 1355 } 1356 1357 /* We are the tracer */ 1358 1359 if (!daemonized_tracer) { 1360 strace_child = pid; 1361 if (!use_seize) { 1362 /* child did PTRACE_TRACEME, nothing to do in parent */ 1363 } else { 1364 if (!NOMMU_SYSTEM) { 1365 /* Wait until child stopped itself */ 1366 int status; 1367 while (waitpid(pid, &status, WSTOPPED) < 0) { 1368 if (errno == EINTR) 1369 continue; 1370 perror_msg_and_die("waitpid"); 1371 } 1372 if (!WIFSTOPPED(status) || WSTOPSIG(status) != SIGSTOP) { 1373 kill_save_errno(pid, SIGKILL); 1374 perror_msg_and_die("Unexpected wait status %x", status); 1375 } 1376 } 1377 /* Else: NOMMU case, we have no way to sync. 1378 * Just attach to it as soon as possible. 1379 * This means that we may miss a few first syscalls... 1380 */ 1381 1382 if (ptrace_attach_or_seize(pid)) { 1383 kill_save_errno(pid, SIGKILL); 1384 perror_msg_and_die("attach: ptrace(%s, %d)", 1385 ptrace_attach_cmd, pid); 1386 } 1387 if (!NOMMU_SYSTEM) 1388 kill(pid, SIGCONT); 1389 } 1390 tcp = alloctcb(pid); 1391 if (!NOMMU_SYSTEM) 1392 tcp->flags |= TCB_ATTACHED | TCB_STARTUP | post_attach_sigstop; 1393 else 1394 tcp->flags |= TCB_ATTACHED | TCB_STARTUP; 1395 newoutf(tcp); 1396 } 1397 else { 1398 /* With -D, we are *child* here, the tracee is our parent. */ 1399 strace_child = strace_tracer_pid; 1400 strace_tracer_pid = getpid(); 1401 alloctcb(strace_child); 1402 /* attaching will be done later, by startup_attach */ 1403 /* note: we don't do newoutf(tcp) here either! */ 1404 1405 /* NOMMU BUG! -D mode is active, we (child) return, 1406 * and we will scribble over parent's stack! 1407 * When parent later unpauses, it segfaults. 1408 * 1409 * We work around it 1410 * (1) by declaring exec_or_die() NORETURN, 1411 * hopefully compiler will just jump to it 1412 * instead of call (won't push anything to stack), 1413 * (2) by trying very hard in exec_or_die() 1414 * to not use any stack, 1415 * (3) having a really big (PATH_MAX) stack object 1416 * in this function, which creates a "buffer" between 1417 * child's and parent's stack pointers. 1418 * This may save us if (1) and (2) failed 1419 * and compiler decided to use stack in exec_or_die() anyway 1420 * (happens on i386 because of stack parameter passing). 1421 * 1422 * A cleaner solution is to use makecontext + setcontext 1423 * to create a genuine separate stack and execute on it. 1424 */ 1425 } 1426 /* 1427 * A case where straced process is part of a pipe: 1428 * { sleep 1; yes | head -n99999; } | strace -o/dev/null sh -c 'exec <&-; sleep 9' 1429 * If strace won't close its fd#0, closing it in tracee is not enough: 1430 * the pipe is still open, it has a reader. Thus, "head" will not get its 1431 * SIGPIPE at once, on the first write. 1432 * 1433 * Preventing it by closing strace's stdin/out. 1434 * (Don't leave fds 0 and 1 closed, this is bad practice: future opens 1435 * will reuse them, unexpectedly making a newly opened object "stdin"). 1436 */ 1437 close(0); 1438 open_dummy_desc(); /* opens to fd#0 */ 1439 dup2(0, 1); 1440#if 0 1441 /* A good idea too, but we sometimes need to print error messages */ 1442 if (shared_log != stderr) 1443 dup2(0, 2); 1444#endif 1445} 1446 1447#if USE_SEIZE 1448static void 1449test_ptrace_seize(void) 1450{ 1451 int pid; 1452 1453 /* Need fork for test. NOMMU has no forks */ 1454 if (NOMMU_SYSTEM) { 1455 post_attach_sigstop = 0; /* this sets use_seize to 1 */ 1456 return; 1457 } 1458 1459 pid = fork(); 1460 if (pid < 0) 1461 perror_msg_and_die("fork"); 1462 1463 if (pid == 0) { 1464 pause(); 1465 _exit(0); 1466 } 1467 1468 /* PTRACE_SEIZE, unlike ATTACH, doesn't force tracee to trap. After 1469 * attaching tracee continues to run unless a trap condition occurs. 1470 * PTRACE_SEIZE doesn't affect signal or group stop state. 1471 */ 1472 if (ptrace(PTRACE_SEIZE, pid, 0, 0) == 0) { 1473 post_attach_sigstop = 0; /* this sets use_seize to 1 */ 1474 } else if (debug_flag) { 1475 error_msg("PTRACE_SEIZE doesn't work"); 1476 } 1477 1478 kill(pid, SIGKILL); 1479 1480 while (1) { 1481 int status, tracee_pid; 1482 1483 errno = 0; 1484 tracee_pid = waitpid(pid, &status, 0); 1485 if (tracee_pid <= 0) { 1486 if (errno == EINTR) 1487 continue; 1488 perror_msg_and_die("%s: unexpected wait result %d", 1489 __func__, tracee_pid); 1490 } 1491 if (WIFSIGNALED(status)) { 1492 return; 1493 } 1494 error_msg_and_die("%s: unexpected wait status %x", 1495 __func__, status); 1496 } 1497} 1498#else /* !USE_SEIZE */ 1499# define test_ptrace_seize() ((void)0) 1500#endif 1501 1502static unsigned 1503get_os_release(void) 1504{ 1505 unsigned rel; 1506 const char *p; 1507 struct utsname u; 1508 if (uname(&u) < 0) 1509 perror_msg_and_die("uname"); 1510 /* u.release has this form: "3.2.9[-some-garbage]" */ 1511 rel = 0; 1512 p = u.release; 1513 for (;;) { 1514 if (!(*p >= '0' && *p <= '9')) 1515 error_msg_and_die("Bad OS release string: '%s'", u.release); 1516 /* Note: this open-codes KERNEL_VERSION(): */ 1517 rel = (rel << 8) | atoi(p); 1518 if (rel >= KERNEL_VERSION(1,0,0)) 1519 break; 1520 while (*p >= '0' && *p <= '9') 1521 p++; 1522 if (*p != '.') { 1523 if (rel >= KERNEL_VERSION(0,1,0)) { 1524 /* "X.Y-something" means "X.Y.0" */ 1525 rel <<= 8; 1526 break; 1527 } 1528 error_msg_and_die("Bad OS release string: '%s'", u.release); 1529 } 1530 p++; 1531 } 1532 return rel; 1533} 1534 1535/* 1536 * Initialization part of main() was eating much stack (~0.5k), 1537 * which was unused after init. 1538 * We can reuse it if we move init code into a separate function. 1539 * 1540 * Don't want main() to inline us and defeat the reason 1541 * we have a separate function. 1542 */ 1543static void ATTRIBUTE_NOINLINE 1544init(int argc, char *argv[]) 1545{ 1546 int c, i; 1547 int optF = 0; 1548 struct sigaction sa; 1549 1550 progname = argv[0] ? argv[0] : "strace"; 1551 1552 /* Make sure SIGCHLD has the default action so that waitpid 1553 definitely works without losing track of children. The user 1554 should not have given us a bogus state to inherit, but he might 1555 have. Arguably we should detect SIG_IGN here and pass it on 1556 to children, but probably noone really needs that. */ 1557 signal(SIGCHLD, SIG_DFL); 1558 1559 strace_tracer_pid = getpid(); 1560 1561 os_release = get_os_release(); 1562 1563 shared_log = stderr; 1564 set_sortby(DEFAULT_SORTBY); 1565 set_personality(DEFAULT_PERSONALITY); 1566 qualify("trace=all"); 1567 qualify("abbrev=all"); 1568 qualify("verbose=all"); 1569#if DEFAULT_QUAL_FLAGS != (QUAL_TRACE | QUAL_ABBREV | QUAL_VERBOSE) 1570# error Bug in DEFAULT_QUAL_FLAGS 1571#endif 1572 qualify("signal=all"); 1573 while ((c = getopt(argc, argv, 1574 "+b:cCdfFhiqrtTvVwxyz" 1575#ifdef USE_LIBUNWIND 1576 "k" 1577#endif 1578 "D" 1579 "a:e:o:O:p:s:S:u:E:P:I:")) != EOF) { 1580 switch (c) { 1581 case 'b': 1582 if (strcmp(optarg, "execve") != 0) 1583 error_msg_and_die("Syscall '%s' for -b isn't supported", 1584 optarg); 1585 detach_on_execve = 1; 1586 break; 1587 case 'c': 1588 if (cflag == CFLAG_BOTH) { 1589 error_msg_and_help("-c and -C are mutually exclusive"); 1590 } 1591 cflag = CFLAG_ONLY_STATS; 1592 break; 1593 case 'C': 1594 if (cflag == CFLAG_ONLY_STATS) { 1595 error_msg_and_help("-c and -C are mutually exclusive"); 1596 } 1597 cflag = CFLAG_BOTH; 1598 break; 1599 case 'd': 1600 debug_flag = 1; 1601 break; 1602 case 'D': 1603 daemonized_tracer = 1; 1604 break; 1605 case 'F': 1606 optF = 1; 1607 break; 1608 case 'f': 1609 followfork++; 1610 break; 1611 case 'h': 1612 usage(); 1613 break; 1614 case 'i': 1615 iflag = 1; 1616 break; 1617 case 'q': 1618 qflag++; 1619 break; 1620 case 'r': 1621 rflag = 1; 1622 /* fall through to tflag++ */ 1623 case 't': 1624 tflag++; 1625 break; 1626 case 'T': 1627 Tflag = 1; 1628 break; 1629 case 'w': 1630 count_wallclock = 1; 1631 break; 1632 case 'x': 1633 xflag++; 1634 break; 1635 case 'y': 1636 show_fd_path++; 1637 break; 1638 case 'v': 1639 qualify("abbrev=none"); 1640 break; 1641 case 'V': 1642 printf("%s -- version %s\n", PACKAGE_NAME, VERSION); 1643 exit(0); 1644 break; 1645 case 'z': 1646 not_failing_only = 1; 1647 break; 1648 case 'a': 1649 acolumn = string_to_uint(optarg); 1650 if (acolumn < 0) 1651 error_opt_arg(c, optarg); 1652 break; 1653 case 'e': 1654 qualify(optarg); 1655 break; 1656 case 'o': 1657 outfname = xstrdup(optarg); 1658 break; 1659 case 'O': 1660 i = string_to_uint(optarg); 1661 if (i < 0) 1662 error_opt_arg(c, optarg); 1663 set_overhead(i); 1664 break; 1665 case 'p': 1666 process_opt_p_list(optarg); 1667 break; 1668 case 'P': 1669 pathtrace_select(optarg); 1670 break; 1671 case 's': 1672 i = string_to_uint(optarg); 1673 if (i < 0) 1674 error_opt_arg(c, optarg); 1675 max_strlen = i; 1676 break; 1677 case 'S': 1678 set_sortby(optarg); 1679 break; 1680 case 'u': 1681 username = xstrdup(optarg); 1682 break; 1683#ifdef USE_LIBUNWIND 1684 case 'k': 1685 stack_trace_enabled = true; 1686 break; 1687#endif 1688 case 'E': 1689 if (putenv(optarg) < 0) 1690 die_out_of_memory(); 1691 break; 1692 case 'I': 1693 opt_intr = string_to_uint(optarg); 1694 if (opt_intr <= 0 || opt_intr >= NUM_INTR_OPTS) 1695 error_opt_arg(c, optarg); 1696 break; 1697 default: 1698 error_msg_and_help(NULL); 1699 break; 1700 } 1701 } 1702 argv += optind; 1703 /* argc -= optind; - no need, argc is not used below */ 1704 1705 acolumn_spaces = xmalloc(acolumn + 1); 1706 memset(acolumn_spaces, ' ', acolumn); 1707 acolumn_spaces[acolumn] = '\0'; 1708 1709 if (!argv[0] && !nprocs) { 1710 error_msg_and_help("must have PROG [ARGS] or -p PID"); 1711 } 1712 1713 if (!argv[0] && daemonized_tracer) { 1714 error_msg_and_help("PROG [ARGS] must be specified with -D"); 1715 } 1716 1717 if (!followfork) 1718 followfork = optF; 1719 1720 if (followfork >= 2 && cflag) { 1721 error_msg_and_help("(-c or -C) and -ff are mutually exclusive"); 1722 } 1723 1724 if (count_wallclock && !cflag) { 1725 error_msg_and_help("-w must be given with (-c or -C)"); 1726 } 1727 1728 if (cflag == CFLAG_ONLY_STATS) { 1729 if (iflag) 1730 error_msg("-%c has no effect with -c", 'i'); 1731#ifdef USE_LIBUNWIND 1732 if (stack_trace_enabled) 1733 error_msg("-%c has no effect with -c", 'k'); 1734#endif 1735 if (rflag) 1736 error_msg("-%c has no effect with -c", 'r'); 1737 if (tflag) 1738 error_msg("-%c has no effect with -c", 't'); 1739 if (Tflag) 1740 error_msg("-%c has no effect with -c", 'T'); 1741 if (show_fd_path) 1742 error_msg("-%c has no effect with -c", 'y'); 1743 } 1744 1745#ifdef USE_LIBUNWIND 1746 if (stack_trace_enabled) 1747 unwind_init(); 1748#endif 1749 1750 /* See if they want to run as another user. */ 1751 if (username != NULL) { 1752 struct passwd *pent; 1753 1754 if (getuid() != 0 || geteuid() != 0) { 1755 error_msg_and_die("You must be root to use the -u option"); 1756 } 1757 pent = getpwnam(username); 1758 if (pent == NULL) { 1759 error_msg_and_die("Cannot find user '%s'", username); 1760 } 1761 run_uid = pent->pw_uid; 1762 run_gid = pent->pw_gid; 1763 } 1764 else { 1765 run_uid = getuid(); 1766 run_gid = getgid(); 1767 } 1768 1769 if (followfork) 1770 ptrace_setoptions |= PTRACE_O_TRACECLONE | 1771 PTRACE_O_TRACEFORK | 1772 PTRACE_O_TRACEVFORK; 1773 if (debug_flag) 1774 error_msg("ptrace_setoptions = %#x", ptrace_setoptions); 1775 test_ptrace_seize(); 1776 1777 if (fcntl(0, F_GETFD) == -1 || fcntl(1, F_GETFD) == -1) { 1778 /* 1779 * Something weird with our stdin and/or stdout - 1780 * for example, may be not open? In this case, 1781 * ensure that none of the future opens uses them. 1782 * 1783 * This was seen in the wild when /proc/sys/kernel/core_pattern 1784 * was set to "|/bin/strace -o/tmp/LOG PROG": 1785 * kernel runs coredump helper with fd#0 open but fd#1 closed (!), 1786 * therefore LOG gets opened to fd#1, and fd#1 is closed by 1787 * "don't hold up stdin/out open" code soon after. 1788 */ 1789 int fd = open_dummy_desc(); 1790 while (fd >= 0 && fd < 2) 1791 fd = dup(fd); 1792 if (fd > 2) 1793 close(fd); 1794 } 1795 1796 /* Check if they want to redirect the output. */ 1797 if (outfname) { 1798 /* See if they want to pipe the output. */ 1799 if (outfname[0] == '|' || outfname[0] == '!') { 1800 /* 1801 * We can't do the <outfname>.PID funny business 1802 * when using popen, so prohibit it. 1803 */ 1804 if (followfork >= 2) 1805 error_msg_and_help("piping the output and -ff are mutually exclusive"); 1806 shared_log = strace_popen(outfname + 1); 1807 } 1808 else if (followfork < 2) 1809 shared_log = strace_fopen(outfname); 1810 } else { 1811 /* -ff without -o FILE is the same as single -f */ 1812 if (followfork >= 2) 1813 followfork = 1; 1814 } 1815 1816 if (!outfname || outfname[0] == '|' || outfname[0] == '!') { 1817 char *buf = xmalloc(BUFSIZ); 1818 setvbuf(shared_log, buf, _IOLBF, BUFSIZ); 1819 } 1820 if (outfname && argv[0]) { 1821 if (!opt_intr) 1822 opt_intr = INTR_NEVER; 1823 if (!qflag) 1824 qflag = 1; 1825 } 1826 if (!opt_intr) 1827 opt_intr = INTR_WHILE_WAIT; 1828 1829 /* argv[0] -pPID -oFILE Default interactive setting 1830 * yes * 0 INTR_WHILE_WAIT 1831 * no 1 0 INTR_WHILE_WAIT 1832 * yes * 1 INTR_NEVER 1833 * no 1 1 INTR_WHILE_WAIT 1834 */ 1835 1836 sigemptyset(&empty_set); 1837 sigemptyset(&blocked_set); 1838 1839 /* startup_child() must be called before the signal handlers get 1840 * installed below as they are inherited into the spawned process. 1841 * Also we do not need to be protected by them as during interruption 1842 * in the startup_child() mode we kill the spawned process anyway. 1843 */ 1844 if (argv[0]) { 1845 if (!NOMMU_SYSTEM || daemonized_tracer) 1846 hide_log_until_execve = 1; 1847 skip_one_b_execve = 1; 1848 startup_child(argv); 1849 } 1850 1851 sa.sa_handler = SIG_IGN; 1852 sigemptyset(&sa.sa_mask); 1853 sa.sa_flags = 0; 1854 sigaction(SIGTTOU, &sa, NULL); /* SIG_IGN */ 1855 sigaction(SIGTTIN, &sa, NULL); /* SIG_IGN */ 1856 if (opt_intr != INTR_ANYWHERE) { 1857 if (opt_intr == INTR_BLOCK_TSTP_TOO) 1858 sigaction(SIGTSTP, &sa, NULL); /* SIG_IGN */ 1859 /* 1860 * In interactive mode (if no -o OUTFILE, or -p PID is used), 1861 * fatal signals are blocked while syscall stop is processed, 1862 * and acted on in between, when waiting for new syscall stops. 1863 * In non-interactive mode, signals are ignored. 1864 */ 1865 if (opt_intr == INTR_WHILE_WAIT) { 1866 sigaddset(&blocked_set, SIGHUP); 1867 sigaddset(&blocked_set, SIGINT); 1868 sigaddset(&blocked_set, SIGQUIT); 1869 sigaddset(&blocked_set, SIGPIPE); 1870 sigaddset(&blocked_set, SIGTERM); 1871 sa.sa_handler = interrupt; 1872 } 1873 /* SIG_IGN, or set handler for these */ 1874 sigaction(SIGHUP, &sa, NULL); 1875 sigaction(SIGINT, &sa, NULL); 1876 sigaction(SIGQUIT, &sa, NULL); 1877 sigaction(SIGPIPE, &sa, NULL); 1878 sigaction(SIGTERM, &sa, NULL); 1879 } 1880 if (nprocs != 0 || daemonized_tracer) 1881 startup_attach(); 1882 1883 /* Do we want pids printed in our -o OUTFILE? 1884 * -ff: no (every pid has its own file); or 1885 * -f: yes (there can be more pids in the future); or 1886 * -p PID1,PID2: yes (there are already more than one pid) 1887 */ 1888 print_pid_pfx = (outfname && followfork < 2 && (followfork == 1 || nprocs > 1)); 1889} 1890 1891static struct tcb * 1892pid2tcb(int pid) 1893{ 1894 unsigned int i; 1895 1896 if (pid <= 0) 1897 return NULL; 1898 1899 for (i = 0; i < tcbtabsize; i++) { 1900 struct tcb *tcp = tcbtab[i]; 1901 if (tcp->pid == pid) 1902 return tcp; 1903 } 1904 1905 return NULL; 1906} 1907 1908static void 1909cleanup(void) 1910{ 1911 unsigned int i; 1912 struct tcb *tcp; 1913 int fatal_sig; 1914 1915 /* 'interrupted' is a volatile object, fetch it only once */ 1916 fatal_sig = interrupted; 1917 if (!fatal_sig) 1918 fatal_sig = SIGTERM; 1919 1920 for (i = 0; i < tcbtabsize; i++) { 1921 tcp = tcbtab[i]; 1922 if (!tcp->pid) 1923 continue; 1924 if (debug_flag) 1925 error_msg("cleanup: looking at pid %u", tcp->pid); 1926 if (tcp->pid == strace_child) { 1927 kill(tcp->pid, SIGCONT); 1928 kill(tcp->pid, fatal_sig); 1929 } 1930 detach(tcp); 1931 } 1932 if (cflag) 1933 call_summary(shared_log); 1934} 1935 1936static void 1937interrupt(int sig) 1938{ 1939 interrupted = sig; 1940} 1941 1942static void 1943print_debug_info(const int pid, int status) 1944{ 1945 const unsigned int event = (unsigned int) status >> 16; 1946 char buf[sizeof("WIFEXITED,exitcode=%u") + sizeof(int)*3 /*paranoia:*/ + 16]; 1947 char evbuf[sizeof(",EVENT_VFORK_DONE (%u)") + sizeof(int)*3 /*paranoia:*/ + 16]; 1948 1949 strcpy(buf, "???"); 1950 if (WIFSIGNALED(status)) 1951#ifdef WCOREDUMP 1952 sprintf(buf, "WIFSIGNALED,%ssig=%s", 1953 WCOREDUMP(status) ? "core," : "", 1954 signame(WTERMSIG(status))); 1955#else 1956 sprintf(buf, "WIFSIGNALED,sig=%s", 1957 signame(WTERMSIG(status))); 1958#endif 1959 if (WIFEXITED(status)) 1960 sprintf(buf, "WIFEXITED,exitcode=%u", WEXITSTATUS(status)); 1961 if (WIFSTOPPED(status)) 1962 sprintf(buf, "WIFSTOPPED,sig=%s", signame(WSTOPSIG(status))); 1963#ifdef WIFCONTINUED 1964 /* Should never be seen */ 1965 if (WIFCONTINUED(status)) 1966 strcpy(buf, "WIFCONTINUED"); 1967#endif 1968 evbuf[0] = '\0'; 1969 if (event != 0) { 1970 static const char *const event_names[] = { 1971 [PTRACE_EVENT_CLONE] = "CLONE", 1972 [PTRACE_EVENT_FORK] = "FORK", 1973 [PTRACE_EVENT_VFORK] = "VFORK", 1974 [PTRACE_EVENT_VFORK_DONE] = "VFORK_DONE", 1975 [PTRACE_EVENT_EXEC] = "EXEC", 1976 [PTRACE_EVENT_EXIT] = "EXIT", 1977 /* [PTRACE_EVENT_STOP (=128)] would make biggish array */ 1978 }; 1979 const char *e = "??"; 1980 if (event < ARRAY_SIZE(event_names)) 1981 e = event_names[event]; 1982 else if (event == PTRACE_EVENT_STOP) 1983 e = "STOP"; 1984 sprintf(evbuf, ",EVENT_%s (%u)", e, event); 1985 } 1986 error_msg("[wait(0x%06x) = %u] %s%s", status, pid, buf, evbuf); 1987} 1988 1989static struct tcb * 1990maybe_allocate_tcb(const int pid, int status) 1991{ 1992 if (!WIFSTOPPED(status)) { 1993 if (detach_on_execve && pid == strace_child) { 1994 /* example: strace -bexecve sh -c 'exec true' */ 1995 strace_child = 0; 1996 return NULL; 1997 } 1998 /* 1999 * This can happen if we inherited an unknown child. 2000 * Example: (sleep 1 & exec strace true) 2001 */ 2002 error_msg("Exit of unknown pid %u ignored", pid); 2003 return NULL; 2004 } 2005 if (followfork) { 2006 /* We assume it's a fork/vfork/clone child */ 2007 struct tcb *tcp = alloctcb(pid); 2008 tcp->flags |= TCB_ATTACHED | TCB_STARTUP | post_attach_sigstop; 2009 newoutf(tcp); 2010 if (!qflag) 2011 error_msg("Process %d attached", pid); 2012 return tcp; 2013 } else { 2014 /* This can happen if a clone call used 2015 * CLONE_PTRACE itself. 2016 */ 2017 ptrace(PTRACE_CONT, pid, NULL, 0); 2018 error_msg("Stop of unknown pid %u seen, PTRACE_CONTed it", pid); 2019 return NULL; 2020 } 2021} 2022 2023static struct tcb * 2024maybe_switch_tcbs(struct tcb *tcp, const int pid) 2025{ 2026 FILE *fp; 2027 struct tcb *execve_thread; 2028 long old_pid = 0; 2029 2030 if (ptrace(PTRACE_GETEVENTMSG, pid, NULL, (long) &old_pid) < 0) 2031 return tcp; 2032 /* Avoid truncation in pid2tcb() param passing */ 2033 if (old_pid <= 0 || old_pid == pid) 2034 return tcp; 2035 if ((unsigned long) old_pid > UINT_MAX) 2036 return tcp; 2037 execve_thread = pid2tcb(old_pid); 2038 /* It should be !NULL, but I feel paranoid */ 2039 if (!execve_thread) 2040 return tcp; 2041 2042 if (execve_thread->curcol != 0) { 2043 /* 2044 * One case we are here is -ff: 2045 * try "strace -oLOG -ff test/threaded_execve" 2046 */ 2047 fprintf(execve_thread->outf, " <pid changed to %d ...>\n", pid); 2048 /*execve_thread->curcol = 0; - no need, see code below */ 2049 } 2050 /* Swap output FILEs (needed for -ff) */ 2051 fp = execve_thread->outf; 2052 execve_thread->outf = tcp->outf; 2053 tcp->outf = fp; 2054 /* And their column positions */ 2055 execve_thread->curcol = tcp->curcol; 2056 tcp->curcol = 0; 2057 /* Drop leader, but close execve'd thread outfile (if -ff) */ 2058 droptcb(tcp); 2059 /* Switch to the thread, reusing leader's outfile and pid */ 2060 tcp = execve_thread; 2061 tcp->pid = pid; 2062 if (cflag != CFLAG_ONLY_STATS) { 2063 printleader(tcp); 2064 tprintf("+++ superseded by execve in pid %lu +++\n", old_pid); 2065 line_ended(); 2066 tcp->flags |= TCB_REPRINT; 2067 } 2068 2069 return tcp; 2070} 2071 2072static void 2073print_signalled(struct tcb *tcp, const int pid, int status) 2074{ 2075 if (pid == strace_child) { 2076 exit_code = 0x100 | WTERMSIG(status); 2077 strace_child = 0; 2078 } 2079 2080 if (cflag != CFLAG_ONLY_STATS 2081 && (qual_flags[WTERMSIG(status)] & QUAL_SIGNAL) 2082 ) { 2083 printleader(tcp); 2084#ifdef WCOREDUMP 2085 tprintf("+++ killed by %s %s+++\n", 2086 signame(WTERMSIG(status)), 2087 WCOREDUMP(status) ? "(core dumped) " : ""); 2088#else 2089 tprintf("+++ killed by %s +++\n", 2090 signame(WTERMSIG(status))); 2091#endif 2092 line_ended(); 2093 } 2094} 2095 2096static void 2097print_exited(struct tcb *tcp, const int pid, int status) 2098{ 2099 if (pid == strace_child) { 2100 exit_code = WEXITSTATUS(status); 2101 strace_child = 0; 2102 } 2103 2104 if (cflag != CFLAG_ONLY_STATS && 2105 qflag < 2) { 2106 printleader(tcp); 2107 tprintf("+++ exited with %d +++\n", WEXITSTATUS(status)); 2108 line_ended(); 2109 } 2110} 2111 2112static void 2113print_stopped(struct tcb *tcp, const siginfo_t *si, const unsigned int sig) 2114{ 2115 if (cflag != CFLAG_ONLY_STATS 2116 && !hide_log_until_execve 2117 && (qual_flags[sig] & QUAL_SIGNAL) 2118 ) { 2119 printleader(tcp); 2120 if (si) { 2121 tprintf("--- %s ", signame(sig)); 2122 printsiginfo(si); 2123 tprints(" ---\n"); 2124 } else 2125 tprintf("--- stopped by %s ---\n", signame(sig)); 2126 line_ended(); 2127 } 2128} 2129 2130static void 2131startup_tcb(struct tcb *tcp) 2132{ 2133 if (debug_flag) 2134 error_msg("pid %d has TCB_STARTUP, initializing it", tcp->pid); 2135 2136 tcp->flags &= ~TCB_STARTUP; 2137 2138 if (!use_seize) { 2139 if (debug_flag) 2140 error_msg("setting opts 0x%x on pid %d", 2141 ptrace_setoptions, tcp->pid); 2142 if (ptrace(PTRACE_SETOPTIONS, tcp->pid, NULL, ptrace_setoptions) < 0) { 2143 if (errno != ESRCH) { 2144 /* Should never happen, really */ 2145 perror_msg_and_die("PTRACE_SETOPTIONS"); 2146 } 2147 } 2148 } 2149} 2150 2151/* Returns true iff the main trace loop has to continue. */ 2152static bool 2153trace(void) 2154{ 2155 int pid; 2156 int wait_errno; 2157 int status; 2158 bool stopped; 2159 unsigned int sig; 2160 unsigned int event; 2161 struct tcb *tcp; 2162 struct rusage ru; 2163 2164 if (interrupted) 2165 return false; 2166 2167 /* 2168 * Used to exit simply when nprocs hits zero, but in this testcase: 2169 * int main() { _exit(!!fork()); } 2170 * under strace -f, parent sometimes (rarely) manages 2171 * to exit before we see the first stop of the child, 2172 * and we are losing track of it: 2173 * 19923 clone(...) = 19924 2174 * 19923 exit_group(1) = ? 2175 * 19923 +++ exited with 1 +++ 2176 * Exiting only when wait() returns ECHILD works better. 2177 */ 2178 if (popen_pid != 0) { 2179 /* However, if -o|logger is in use, we can't do that. 2180 * Can work around that by double-forking the logger, 2181 * but that loses the ability to wait for its completion 2182 * on exit. Oh well... 2183 */ 2184 if (nprocs == 0) 2185 return false; 2186 } 2187 2188 if (interactive) 2189 sigprocmask(SIG_SETMASK, &empty_set, NULL); 2190 pid = wait4(-1, &status, __WALL, (cflag ? &ru : NULL)); 2191 wait_errno = errno; 2192 if (interactive) 2193 sigprocmask(SIG_BLOCK, &blocked_set, NULL); 2194 2195 if (pid < 0) { 2196 if (wait_errno == EINTR) 2197 return true; 2198 if (nprocs == 0 && wait_errno == ECHILD) 2199 return false; 2200 /* 2201 * If nprocs > 0, ECHILD is not expected, 2202 * treat it as any other error here: 2203 */ 2204 errno = wait_errno; 2205 perror_msg_and_die("wait4(__WALL)"); 2206 } 2207 2208 if (pid == popen_pid) { 2209 if (!WIFSTOPPED(status)) 2210 popen_pid = 0; 2211 return true; 2212 } 2213 2214 if (debug_flag) 2215 print_debug_info(pid, status); 2216 2217 /* Look up 'pid' in our table. */ 2218 tcp = pid2tcb(pid); 2219 2220 if (!tcp) { 2221 tcp = maybe_allocate_tcb(pid, status); 2222 if (!tcp) 2223 return true; 2224 } 2225 2226 if (WIFSTOPPED(status)) 2227 get_regs(pid); 2228 else 2229 clear_regs(); 2230 2231 event = (unsigned int) status >> 16; 2232 2233 if (event == PTRACE_EVENT_EXEC) { 2234 /* 2235 * Under Linux, execve changes pid to thread leader's pid, 2236 * and we see this changed pid on EVENT_EXEC and later, 2237 * execve sysexit. Leader "disappears" without exit 2238 * notification. Let user know that, drop leader's tcb, 2239 * and fix up pid in execve thread's tcb. 2240 * Effectively, execve thread's tcb replaces leader's tcb. 2241 * 2242 * BTW, leader is 'stuck undead' (doesn't report WIFEXITED 2243 * on exit syscall) in multithreaded programs exactly 2244 * in order to handle this case. 2245 * 2246 * PTRACE_GETEVENTMSG returns old pid starting from Linux 3.0. 2247 * On 2.6 and earlier, it can return garbage. 2248 */ 2249 if (os_release >= KERNEL_VERSION(3,0,0)) 2250 tcp = maybe_switch_tcbs(tcp, pid); 2251 2252 if (detach_on_execve && !skip_one_b_execve) { 2253 detach(tcp); /* do "-b execve" thingy */ 2254 return true; 2255 } 2256 skip_one_b_execve = 0; 2257 } 2258 2259 /* Set current output file */ 2260 current_tcp = tcp; 2261 2262 if (cflag) { 2263 tv_sub(&tcp->dtime, &ru.ru_stime, &tcp->stime); 2264 tcp->stime = ru.ru_stime; 2265 } 2266 2267 if (WIFSIGNALED(status)) { 2268 print_signalled(tcp, pid, status); 2269 droptcb(tcp); 2270 return true; 2271 } 2272 2273 if (WIFEXITED(status)) { 2274 print_exited(tcp, pid, status); 2275 droptcb(tcp); 2276 return true; 2277 } 2278 2279 if (!WIFSTOPPED(status)) { 2280 /* 2281 * Neither signalled, exited or stopped. 2282 * How could that be? 2283 */ 2284 error_msg("pid %u not stopped!", pid); 2285 droptcb(tcp); 2286 return true; 2287 } 2288 2289 /* Is this the very first time we see this tracee stopped? */ 2290 if (tcp->flags & TCB_STARTUP) { 2291 startup_tcb(tcp); 2292 if (get_scno(tcp) == 1) 2293 tcp->s_prev_ent = tcp->s_ent; 2294 } 2295 2296 sig = WSTOPSIG(status); 2297 2298 if (event != 0) { 2299 /* Ptrace event */ 2300#if USE_SEIZE 2301 if (event == PTRACE_EVENT_STOP) { 2302 /* 2303 * PTRACE_INTERRUPT-stop or group-stop. 2304 * PTRACE_INTERRUPT-stop has sig == SIGTRAP here. 2305 */ 2306 switch (sig) { 2307 case SIGSTOP: 2308 case SIGTSTP: 2309 case SIGTTIN: 2310 case SIGTTOU: 2311 stopped = true; 2312 goto show_stopsig; 2313 } 2314 } 2315#endif 2316 goto restart_tracee_with_sig_0; 2317 } 2318 2319 /* 2320 * Is this post-attach SIGSTOP? 2321 * Interestingly, the process may stop 2322 * with STOPSIG equal to some other signal 2323 * than SIGSTOP if we happend to attach 2324 * just before the process takes a signal. 2325 */ 2326 if (sig == SIGSTOP && (tcp->flags & TCB_IGNORE_ONE_SIGSTOP)) { 2327 if (debug_flag) 2328 error_msg("ignored SIGSTOP on pid %d", tcp->pid); 2329 tcp->flags &= ~TCB_IGNORE_ONE_SIGSTOP; 2330 goto restart_tracee_with_sig_0; 2331 } 2332 2333 if (sig != syscall_trap_sig) { 2334 siginfo_t si = {}; 2335 2336 /* 2337 * True if tracee is stopped by signal 2338 * (as opposed to "tracee received signal"). 2339 * TODO: shouldn't we check for errno == EINVAL too? 2340 * We can get ESRCH instead, you know... 2341 */ 2342 stopped = ptrace(PTRACE_GETSIGINFO, pid, 0, (long) &si) < 0; 2343#if USE_SEIZE 2344show_stopsig: 2345#endif 2346 print_stopped(tcp, stopped ? NULL : &si, sig); 2347 2348 if (!stopped) 2349 /* It's signal-delivery-stop. Inject the signal */ 2350 goto restart_tracee; 2351 2352 /* It's group-stop */ 2353 if (use_seize) { 2354 /* 2355 * This ends ptrace-stop, but does *not* end group-stop. 2356 * This makes stopping signals work properly on straced process 2357 * (that is, process really stops. It used to continue to run). 2358 */ 2359 if (ptrace_restart(PTRACE_LISTEN, tcp, 0) < 0) { 2360 /* Note: ptrace_restart emitted error message */ 2361 exit_code = 1; 2362 return false; 2363 } 2364 return true; 2365 } 2366 /* We don't have PTRACE_LISTEN support... */ 2367 goto restart_tracee; 2368 } 2369 2370 /* We handled quick cases, we are permitted to interrupt now. */ 2371 if (interrupted) 2372 return false; 2373 2374 /* 2375 * This should be syscall entry or exit. 2376 * Handle it. 2377 */ 2378 if (trace_syscall(tcp) < 0) { 2379 /* 2380 * ptrace() failed in trace_syscall(). 2381 * Likely a result of process disappearing mid-flight. 2382 * Observed case: exit_group() or SIGKILL terminating 2383 * all processes in thread group. 2384 * We assume that ptrace error was caused by process death. 2385 * We used to detach(tcp) here, but since we no longer 2386 * implement "detach before death" policy/hack, 2387 * we can let this process to report its death to us 2388 * normally, via WIFEXITED or WIFSIGNALED wait status. 2389 */ 2390 return true; 2391 } 2392 2393restart_tracee_with_sig_0: 2394 sig = 0; 2395 2396restart_tracee: 2397 if (ptrace_restart(PTRACE_SYSCALL, tcp, sig) < 0) { 2398 /* Note: ptrace_restart emitted error message */ 2399 exit_code = 1; 2400 return false; 2401 } 2402 2403 return true; 2404} 2405 2406int 2407main(int argc, char *argv[]) 2408{ 2409 init(argc, argv); 2410 2411 while (trace()) 2412 ; 2413 2414 cleanup(); 2415 fflush(NULL); 2416 if (shared_log != stderr) 2417 fclose(shared_log); 2418 if (popen_pid) { 2419 while (waitpid(popen_pid, NULL, 0) < 0 && errno == EINTR) 2420 ; 2421 } 2422 if (exit_code > 0xff) { 2423 /* Avoid potential core file clobbering. */ 2424 struct_rlimit rlim = {0, 0}; 2425 set_rlimit(RLIMIT_CORE, &rlim); 2426 2427 /* Child was killed by a signal, mimic that. */ 2428 exit_code &= 0xff; 2429 signal(exit_code, SIG_DFL); 2430 raise(exit_code); 2431 /* Paranoia - what if this signal is not fatal? 2432 Exit with 128 + signo then. */ 2433 exit_code += 128; 2434 } 2435 2436 return exit_code; 2437} 2438