From: Paul Chaignon Date: Mon, 1 Apr 2019 20:26:00 +0000 (+0200) Subject: Add -Z option to print only failing syscalls X-Git-Tag: v5.2~8 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=092e4968460c1efd61ee9e3bba2ede0ec1e983c4;p=strace Add -Z option to print only failing syscalls Existing -z option prints only successful syscalls. This change adds a -Z option to print only failing syscalls. Both options will start to behave properly with the subsequent commit. * strace.c (init): Handle new -Z option. * defs.h (failing_only): New prototype. * syscall.c (failing_only): New variable. (syscall_exiting_trace): Ignore failed syscalls if failing_only is set. References: https://github.com/strace/strace/issues/50 Co-Authored-by: Burkhard Kohl Signed-off-by: Paul Chaignon --- diff --git a/defs.h b/defs.h index a9c36d15..ca458d40 100644 --- a/defs.h +++ b/defs.h @@ -417,6 +417,7 @@ extern bool iflag; extern bool count_wallclock; extern unsigned int qflag; extern bool not_failing_only; +extern bool failing_only; extern unsigned int show_fd_path; /* are we filtering traces based on paths? */ extern struct path_set { diff --git a/strace.c b/strace.c index 74c44253..27027a30 100644 --- a/strace.c +++ b/strace.c @@ -109,8 +109,9 @@ static bool daemonized_tracer; static int post_attach_sigstop = TCB_IGNORE_ONE_SIGSTOP; #define use_seize (post_attach_sigstop == 0) -/* Sometimes we want to print only succeeding syscalls. */ +/* Sometimes we want to print succeeding/failing syscalls only. */ bool not_failing_only; +bool failing_only; /* Show path associated with fd arguments */ unsigned int show_fd_path; @@ -304,6 +305,7 @@ Miscellaneous:\n\ */ /* this is broken, so don't document it -z -- print only succeeding syscalls\n\ +-Z -- print only failing syscalls\n\ */ , DEFAULT_ACOLUMN, DEFAULT_STRLEN, DEFAULT_SORTBY); exit(0); @@ -1579,7 +1581,7 @@ init(int argc, char *argv[]) #ifdef ENABLE_STACKTRACE "k" #endif - "a:Ab:cCdDe:E:fFhiI:o:O:p:P:qrs:S:tTu:vVwxX:yz")) != EOF) { + "a:Ab:cCdDe:E:fFhiI:o:O:p:P:qrs:S:tTu:vVwxX:yzZ")) != EOF) { switch (c) { case 'a': acolumn = string_to_uint(optarg); @@ -1710,6 +1712,9 @@ init(int argc, char *argv[]) case 'z': not_failing_only = 1; break; + case 'Z': + failing_only = 1; + break; default: error_msg_and_help(NULL); break; diff --git a/syscall.c b/syscall.c index 9d4800fd..e73e4274 100644 --- a/syscall.c +++ b/syscall.c @@ -759,8 +759,10 @@ syscall_exiting_trace(struct tcb *tcp, struct timespec *ts, int res) * whereas the intended result is that open(...) line * is not shown at all. */ - if (not_failing_only && tcp->u_error) - return 0; /* ignore failed syscalls */ + if ((not_failing_only && syserror(tcp)) || + (failing_only && !syserror(tcp))) + return 0; /* ignore failed/successful + * syscalls */ if (tcp->sys_func_rval & RVAL_DECODED) sys_res = tcp->sys_func_rval; else