From f41ae861a20f525ef0560c190f2abcef9bb7855c Mon Sep 17 00:00:00 2001 From: Sasha Goldshtein Date: Wed, 19 Oct 2016 01:14:30 +0300 Subject: [PATCH] Tools lint cleanup (#764) * argdist: linter cleanup * cpudist: linter cleanup * execsnoop: linter cleanup * funclatency: linter cleanup * gethostlatency: linter cleanup * hardirqs: linter cleanup * memleak: linter cleanup * mountsnoop: linter cleanup * offcputime: linter cleanup * softirqs: linter cleanup * solisten: linter cleanup and u+x mode * stacksnoop: linter cleanup * tplist: linter cleanup * trace: linter cleanup --- tools/argdist.py | 60 +++++++++++++++++-------------- tools/cpudist.py | 1 - tools/execsnoop.py | 6 ++-- tools/funclatency.py | 7 ++-- tools/gethostlatency.py | 3 +- tools/hardirqs.py | 10 +++--- tools/memleak.py | 6 ++-- tools/mountsnoop.py | 3 +- tools/offcputime.py | 23 ++++++------ tools/softirqs.py | 16 ++++----- tools/solisten.py | 26 ++++++++------ tools/stacksnoop.py | 4 +-- tools/tplist.py | 31 ++++++++-------- tools/trace.py | 78 +++++++++++++++++++++-------------------- 14 files changed, 147 insertions(+), 127 deletions(-) mode change 100644 => 100755 tools/solisten.py diff --git a/tools/argdist.py b/tools/argdist.py index 2bb44c057c96..9f41bdeeda84 100755 --- a/tools/argdist.py +++ b/tools/argdist.py @@ -19,7 +19,7 @@ class Probe(object): next_probe_index = 0 - aliases = { "$PID": "bpf_get_current_pid_tgid()" } + aliases = {"$PID": "bpf_get_current_pid_tgid()"} def _substitute_aliases(self, expr): if expr is None: @@ -37,8 +37,8 @@ def _parse_signature(self): # supported right now. index = param.rfind('*') index = index if index != -1 else param.rfind(' ') - param_type = param[0:index+1].strip() - param_name = param[index+1:].strip() + param_type = param[0:index + 1].strip() + param_name = param[index + 1:].strip() self.param_types[param_name] = param_type def _generate_entry(self): @@ -65,7 +65,7 @@ def _generate_entry(self): collect += """ u64 __time = bpf_ktime_get_ns(); %s.update(&pid, &__time); -""" % param_hash + """ % param_hash else: collect += "%s.update(&pid, &%s);\n" % \ (param_hash, pname) @@ -88,8 +88,8 @@ def _generate_entry_probe(self): self.param_types["__latency"] = "u64" # nanoseconds for pname in self.args_to_probe: if pname not in self.param_types: - raise ValueError("$entry(%s): no such param" \ - % arg) + raise ValueError("$entry(%s): no such param" % + arg) self.hashname_prefix = "%s_param_" % self.probe_hash_name text = "" @@ -156,8 +156,8 @@ def _validate_specifier(self): if len(parts) > 6: self._bail("extraneous ':'-separated parts detected") if parts[0] not in ["r", "p", "t", "u"]: - self._bail("probe type must be 'p', 'r', 't', or 'u' " + - "but got '%s'" % parts[0]) + self._bail("probe type must be 'p', 'r', 't', or 'u'" + + " but got '%s'" % parts[0]) if re.match(r"\w+\(.*\)", parts[2]) is None: self._bail(("function signature '%s' has an invalid " + "format") % parts[2]) @@ -263,8 +263,8 @@ def _generate_usdt_arg_assignment(self, i): expr = self.exprs[i] if self.probe_type == "u" and expr[0:3] == "arg": return (" u64 %s = 0;\n" + - " bpf_usdt_readarg(%s, ctx, &%s);\n") % \ - (expr, expr[3], expr) + " bpf_usdt_readarg(%s, ctx, &%s);\n") \ + % (expr, expr[3], expr) else: return "" @@ -294,7 +294,7 @@ def _generate_hash_decl(self): def _generate_key_assignment(self): if self.type == "hist": return self._generate_usdt_arg_assignment(0) + \ - ("%s __key = %s;\n" % \ + ("%s __key = %s;\n" % (self.expr_types[0], self.exprs[0])) else: text = "struct %s_key_t __key = {};\n" % \ @@ -323,10 +323,11 @@ def generate_text(self): program = "" probe_text = """ DATA_DECL -""" + ( - "TRACEPOINT_PROBE(%s, %s)" % (self.tp_category, self.tp_event) \ - if self.probe_type == "t" \ - else "int PROBENAME(struct pt_regs *ctx SIGNATURE)") + """ + """ + ( + "TRACEPOINT_PROBE(%s, %s)" % + (self.tp_category, self.tp_event) + if self.probe_type == "t" + else "int PROBENAME(struct pt_regs *ctx SIGNATURE)") + """ { PID_FILTER PREFIX @@ -353,7 +354,8 @@ def generate_text(self): # signatures. Other probes force it to (). signature = ", " + self.signature - program += probe_text.replace("PROBENAME", self.probe_func_name) + program += probe_text.replace("PROBENAME", + self.probe_func_name) program = program.replace("SIGNATURE", signature) program = program.replace("PID_FILTER", self._generate_pid_filter()) @@ -400,7 +402,8 @@ def _attach_k(self): def attach(self, bpf): self.bpf = bpf - if self.probe_type == "u": return; + if self.probe_type == "u": + return if self.is_user: self._attach_u() else: @@ -447,7 +450,7 @@ def display(self, top): if self.type == "freq": print(self.label or self.raw_spec) print("\t%-10s %s" % ("COUNT", "EVENT")) - sdata = sorted(data.items(), key=lambda kv: kv[1].value) + sdata = sorted(data.items(), key=lambda p: p[1].value) if top is not None: sdata = sdata[-top:] for key, value in sdata: @@ -461,11 +464,11 @@ def display(self, top): self._v2s(key.v0) else: key_str = self._display_key(key) - print("\t%-10s %s" % \ + print("\t%-10s %s" % (str(value.value), key_str)) elif self.type == "hist": label = self.label or (self._display_expr(0) - if not self.is_default_expr else "retval") + if not self.is_default_expr else "retval") data.print_log2_hist(val_type=label) if not self.cumulative: data.clear() @@ -478,8 +481,8 @@ class Tool(object): Probe specifier syntax: {p,r,t,u}:{[library],category}:function(signature)[:type[,type...]:expr[,expr...][:filter]][#label] Where: - p,r,t,u -- probe at function entry, function exit, kernel tracepoint, - or USDT probe + p,r,t,u -- probe at function entry, function exit, kernel + tracepoint, or USDT probe in exit probes: can use $retval, $entry(param), $latency library -- the library that contains the function (leave empty for kernel functions) @@ -506,7 +509,7 @@ class Tool(object): argdist -H 'r::__kmalloc(size_t size):u64:$latency/$entry(size)#ns per byte' Print a histogram of nanoseconds per byte from kmalloc allocations -argdist -C 'p::__kmalloc(size_t size, gfp_t flags):size_t:size:flags&GFP_ATOMIC' +argdist -C 'p::__kmalloc(size_t sz, gfp_t flags):size_t:sz:flags&GFP_ATOMIC' Print frequency count of kmalloc allocation sizes that have GFP_ATOMIC argdist -p 1005 -C 'p:c:write(int fd):int:fd' -T 5 @@ -520,7 +523,8 @@ class Tool(object): argdist -C 'r::__vfs_read():u32:$PID:$latency > 100000' Print frequency of reads by process where the latency was >0.1ms -argdist -H 'r::__vfs_read(void *file, void *buf, size_t count):size_t:$entry(count):$latency > 1000000' +argdist -H 'r::__vfs_read(void *file, void *buf, size_t count):size_t + $entry(count):$latency > 1000000' Print a histogram of read sizes that were longer than 1ms argdist -H \\ @@ -569,7 +573,8 @@ def __init__(self): parser.add_argument("-v", "--verbose", action="store_true", help="print resulting BPF program code before executing") parser.add_argument("-c", "--cumulative", action="store_true", - help="do not clear histograms and freq counts at each interval") + help="do not clear histograms and freq counts at " + + "each interval") parser.add_argument("-T", "--top", type=int, help="number of top results to show (not applicable to " + "histograms)") @@ -610,8 +615,9 @@ def _generate_program(self): for probe in self.probes: bpf_source += probe.generate_text() if self.args.verbose: - for text in [probe.usdt_ctx.get_text() \ - for probe in self.probes if probe.usdt_ctx]: + for text in [probe.usdt_ctx.get_text() + for probe in self.probes + if probe.usdt_ctx]: print(text) print(bpf_source) usdt_contexts = [probe.usdt_ctx diff --git a/tools/cpudist.py b/tools/cpudist.py index 40ccfa0c099b..152596f78b71 100755 --- a/tools/cpudist.py +++ b/tools/cpudist.py @@ -183,4 +183,3 @@ def pid_to_comm(pid): countdown -= 1 if exiting or countdown == 0: exit() - diff --git a/tools/execsnoop.py b/tools/execsnoop.py index 07b73cd720ee..8955c0c46ecc 100755 --- a/tools/execsnoop.py +++ b/tools/execsnoop.py @@ -88,7 +88,7 @@ const char __user *const __user *__argv, const char __user *const __user *__envp) { - // create data here and pass to submit_arg to save space on the stack (#555) + // create data here and pass to submit_arg to save stack space (#555) struct data_t data = {}; data.pid = bpf_get_current_pid_tgid() >> 32; bpf_get_current_comm(&data.comm, sizeof(data.comm)); @@ -167,8 +167,8 @@ class EventType(object): argv = defaultdict(list) # TODO: This is best-effort PPID matching. Short-lived processes may exit -# before we get a chance to read the PPID. This should be replaced with fetching -# PPID via C when available (#364). +# before we get a chance to read the PPID. This should be replaced with +# fetching PPID via C when available (#364). def get_ppid(pid): try: with open("/proc/%d/status" % pid) as status: diff --git a/tools/funclatency.py b/tools/funclatency.py index 4e6407c02727..13c18de41a0c 100755 --- a/tools/funclatency.py +++ b/tools/funclatency.py @@ -9,8 +9,8 @@ # # Run "funclatency -h" for full usage. # -# The pattern is a string with optional '*' wildcards, similar to file globbing. -# If you'd prefer to use regular expressions, use the -r option. +# The pattern is a string with optional '*' wildcards, similar to file +# globbing. If you'd prefer to use regular expressions, use the -r option. # # Currently nested or recursive functions are not supported properly, and # timestamps will be overwritten, creating dubious output. Try to match single @@ -202,7 +202,8 @@ def signal_ignore(signal, frame): matched = b.num_open_kprobes() else: b.attach_uprobe(name=library, sym_re=pattern, fn_name="trace_func_entry") - b.attach_uretprobe(name=library, sym_re=pattern, fn_name="trace_func_return") + b.attach_uretprobe(name=library, sym_re=pattern, + fn_name="trace_func_return") matched = b.num_open_uprobes() if matched == 0: diff --git a/tools/gethostlatency.py b/tools/gethostlatency.py index 38120c6e9feb..73e4ad2b7871 100755 --- a/tools/gethostlatency.py +++ b/tools/gethostlatency.py @@ -51,7 +51,8 @@ u32 pid = bpf_get_current_pid_tgid(); if (bpf_get_current_comm(&val.comm, sizeof(val.comm)) == 0) { - bpf_probe_read(&val.host, sizeof(val.host), (void *)PT_REGS_PARM1(ctx)); + bpf_probe_read(&val.host, sizeof(val.host), + (void *)PT_REGS_PARM1(ctx)); val.pid = bpf_get_current_pid_tgid(); val.ts = bpf_ktime_get_ns(); start.update(&pid, &val); diff --git a/tools/hardirqs.py b/tools/hardirqs.py index 05a88712c831..36549c72e4ce 100755 --- a/tools/hardirqs.py +++ b/tools/hardirqs.py @@ -18,7 +18,7 @@ from time import sleep, strftime import argparse -### arguments +# arguments examples = """examples: ./hardirqs # sum hard irq event time ./hardirqs -d # show hard irq event time as histograms @@ -49,7 +49,7 @@ label = "usecs" debug = 0 -### define BPF program +# define BPF program bpf_text = """ #include #include @@ -106,7 +106,7 @@ } """ -### code substitutions +# code substitutions if args.dist: bpf_text = bpf_text.replace('STORE', 'irq_key_t key = {.slot = bpf_log2l(delta)};' + @@ -121,7 +121,7 @@ if debug: print(bpf_text) -### load BPF program +# load BPF program b = BPF(text=bpf_text) # these should really use irq:irq_handler_entry/exit tracepoints: @@ -130,7 +130,7 @@ print("Tracing hard irq event time... Hit Ctrl-C to end.") -### output +# output exiting = 0 if args.interval else 1 dist = b.get_table("dist") while (1): diff --git a/tools/memleak.py b/tools/memleak.py index e8bf06ff3afc..04f0fea57a57 100755 --- a/tools/memleak.py +++ b/tools/memleak.py @@ -280,11 +280,13 @@ def print_outstanding(): alloc_info[info.stack_id].update(info.size) else: stack = list(stack_traces.walk(info.stack_id, decoder)) - alloc_info[info.stack_id] = Allocation(stack, info.size) + alloc_info[info.stack_id] = Allocation(stack, + info.size) if args.show_allocs: print("\taddr = %x size = %s" % (address.value, info.size)) - to_show = sorted(alloc_info.values(), key=lambda a: a.size)[-top_stacks:] + to_show = sorted(alloc_info.values(), + key=lambda a: a.size)[-top_stacks:] for alloc in to_show: print("\t%d bytes in %d allocations from stack\n\t\t%s" % (alloc.size, alloc.count, "\n\t\t".join(alloc.stack))) diff --git a/tools/mountsnoop.py b/tools/mountsnoop.py index dfaafc3642ad..a7a3973a6911 100755 --- a/tools/mountsnoop.py +++ b/tools/mountsnoop.py @@ -369,7 +369,8 @@ def print_event(mounts, umounts, cpu, data, size): event.type == EventType.EVENT_UMOUNT_RET): if event.type == EventType.EVENT_MOUNT_RET: syscall = mounts.pop(event.pid) - call = 'mount({source}, {target}, {type}, {flags}, {data}) = {retval}'.format( + call = ('mount({source}, {target}, {type}, {flags}, {data}) ' + + '= {retval}').format( source=decode_mount_string(syscall['source']), target=decode_mount_string(syscall['target']), type=decode_mount_string(syscall['type']), diff --git a/tools/offcputime.py b/tools/offcputime.py index 95da5465624f..1bab38bbb16d 100755 --- a/tools/offcputime.py +++ b/tools/offcputime.py @@ -40,8 +40,8 @@ def positive_nonzero_int(val): ./offcputime # trace off-CPU stack time until Ctrl-C ./offcputime 5 # trace for 5 seconds only ./offcputime -f 5 # 5 seconds, and output in folded format - ./offcputime -m 1000 # trace only events that last more than 1000 usec. - ./offcputime -M 10000 # trace only events that last less than 10000 usec. + ./offcputime -m 1000 # trace only events that last more than 1000 usec + ./offcputime -M 10000 # trace only events that last less than 10000 usec ./offcputime -p 185 # only trace threads for PID 185 ./offcputime -t 188 # only trace thread 188 ./offcputime -u # only trace user threads (no kernel) @@ -82,10 +82,12 @@ def positive_nonzero_int(val): help="duration of trace, in seconds") parser.add_argument("-m", "--min-block-time", default=1, type=positive_nonzero_int, - help="the amount of time in microseconds over which we store traces (default 1)") -parser.add_argument("-M", "--max-block-time", default=(1<<64)-1, + help="the amount of time in microseconds over which we " + + "store traces (default 1)") +parser.add_argument("-M", "--max-block-time", default=(1 << 64) - 1, type=positive_nonzero_int, - help="the amount of time in microseconds under which we store traces (default U64_MAX)") + help="the amount of time in microseconds under which we " + + "store traces (default U64_MAX)") args = parser.parse_args() if args.pid and args.tgid: parser.error("specify only one of -p and -t") @@ -198,13 +200,14 @@ def signal_ignore(signal, frame): bpf_text = bpf_text.replace('USER_STACK_GET', user_stack_get) bpf_text = bpf_text.replace('KERNEL_STACK_GET', kernel_stack_get) -need_delimiter = args.delimited and not (args.kernel_stacks_only or args.user_stacks_only) +need_delimiter = args.delimited and not (args.kernel_stacks_only or + args.user_stacks_only) # check for an edge case; the code below will handle this case correctly # but ultimately nothing will be displayed if args.kernel_threads_only and args.user_stacks_only: - print("ERROR: Displaying user stacks for kernel threads " \ - "doesn't make sense.", file=stderr) + print("ERROR: Displaying user stacks for kernel threads " + + "doesn't make sense.", file=stderr) exit(1) # initialize BPF @@ -240,8 +243,8 @@ def signal_ignore(signal, frame): for k, v in sorted(counts.items(), key=lambda counts: counts[1].value): # handle get_stackid erorrs if (not args.user_stacks_only and k.kernel_stack_id < 0) or \ - (not args.kernel_stacks_only and k.user_stack_id < 0 and \ - k.user_stack_id != -errno.EFAULT): + (not args.kernel_stacks_only and k.user_stack_id < 0 and + k.user_stack_id != -errno.EFAULT): missing_stacks += 1 # check for an ENOMEM error if k.kernel_stack_id == -errno.ENOMEM or \ diff --git a/tools/softirqs.py b/tools/softirqs.py index dd24231f76bd..0b2e50c7b72b 100755 --- a/tools/softirqs.py +++ b/tools/softirqs.py @@ -16,7 +16,7 @@ from time import sleep, strftime import argparse -### arguments +# arguments examples = """examples: ./softirqs # sum soft irq event time ./softirqs -d # show soft irq event time as histograms @@ -47,7 +47,7 @@ label = "usecs" debug = 0 -### define BPF program +# define BPF program bpf_text = """ #include @@ -92,7 +92,7 @@ } """ -### code substitutions +# code substitutions if args.dist: bpf_text = bpf_text.replace('STORE', 'irq_key_t key = {.ip = ip, .slot = bpf_log2l(delta)};' + @@ -105,22 +105,22 @@ if debug: print(bpf_text) -### load BPF program +# load BPF program b = BPF(text=bpf_text) # this should really use irq:softirq_entry/exit tracepoints; for now the # soft irq functions are individually traced (search your kernel for # open_softirq() calls, and adjust the following list as needed). for softirqfunc in ("blk_iopoll_softirq", "blk_done_softirq", - "rcu_process_callbacks", "run_rebalance_domains", "tasklet_action", - "tasklet_hi_action", "run_timer_softirq", "net_tx_action", - "net_rx_action"): + "rcu_process_callbacks", "run_rebalance_domains", "tasklet_action", + "tasklet_hi_action", "run_timer_softirq", "net_tx_action", + "net_rx_action"): b.attach_kprobe(event=softirqfunc, fn_name="trace_start") b.attach_kretprobe(event=softirqfunc, fn_name="trace_completion") print("Tracing soft irq event time... Hit Ctrl-C to end.") -### output +# output exiting = 0 if args.interval else 1 dist = b.get_table("dist") while (1): diff --git a/tools/solisten.py b/tools/solisten.py old mode 100644 new mode 100755 index 97976720e4e1..11926543428b --- a/tools/solisten.py +++ b/tools/solisten.py @@ -1,7 +1,7 @@ #!/usr/bin/env python # -# solisten Trace TCP listen events -# For Linux, uses BCC, eBPF. Embedded C. +# solisten Trace TCP listen events +# For Linux, uses BCC, eBPF. Embedded C. # # USAGE: solisten.py [-h] [-p PID] [--show-netns] # @@ -28,8 +28,8 @@ examples = """Examples: ./solisten.py # Stream socket listen ./solisten.py -p 1234 # Stream socket listen for specified PID only - ./solisten.py --netns 4242 # Stream socket listen for specified network namespace ID only - ./solisten.py --show-netns # Show network namespace ID. Probably usefull if you run containers + ./solisten.py --netns 4242 # " for the specified network namespace ID only + ./solisten.py --show-netns # Show network ns ID (useful for containers) """ parser = argparse.ArgumentParser( @@ -45,7 +45,7 @@ # BPF Program -bpf_text = """ +bpf_text = """ #include #include #include @@ -77,7 +77,8 @@ .backlog = backlog, }; - // Get process comm. Needs LLVM >= 3.7.1 see https://github.com/iovisor/bcc/issues/393 + // Get process comm. Needs LLVM >= 3.7.1 + // see https://github.com/iovisor/bcc/issues/393 bpf_get_current_comm(evt.task, TASK_COMM_LEN); // Get socket IP family @@ -107,7 +108,8 @@ bpf_probe_read(evt.laddr, sizeof(u32), &(inet->inet_rcv_saddr)); evt.laddr[0] = be32_to_cpu(evt.laddr[0]); } else if (family == AF_INET6) { - bpf_probe_read(evt.laddr, sizeof(evt.laddr), sk->__sk_common.skc_v6_rcv_saddr.in6_u.u6_addr32); + bpf_probe_read(evt.laddr, sizeof(evt.laddr), + sk->__sk_common.skc_v6_rcv_saddr.in6_u.u6_addr32); evt.laddr[0] = be64_to_cpu(evt.laddr[0]); evt.laddr[1] = be64_to_cpu(evt.laddr[1]); } @@ -157,7 +159,8 @@ def print_event(cpu, data, size): protocol += "v4" address = netaddr.IPAddress(event.laddr[0]) elif proto_type == socket.AF_INET6: - address = netaddr.IPAddress(event.laddr[0]<<64 | event.laddr[1], version=6) + address = netaddr.IPAddress(event.laddr[0] << 64 | event.laddr[1], + version=6) protocol += "v6" # Display @@ -195,11 +198,12 @@ def print_event(cpu, data, size): # Print headers if args.show_netns: - print("%-6s %-12s %-12s %-6s %-8s %-5s %-39s" % ("PID", "COMM", "NETNS", "PROTO", "BACKLOG", "PORT", "ADDR")) + print("%-6s %-12s %-12s %-6s %-8s %-5s %-39s" % + ("PID", "COMM", "NETNS", "PROTO", "BACKLOG", "PORT", "ADDR")) else: - print("%-6s %-12s %-6s %-8s %-5s %-39s" % ("PID", "COMM", "PROTO", "BACKLOG", "PORT", "ADDR")) + print("%-6s %-12s %-6s %-8s %-5s %-39s" % + ("PID", "COMM", "PROTO", "BACKLOG", "PORT", "ADDR")) # Read events while 1: b.kprobe_poll() - diff --git a/tools/stacksnoop.py b/tools/stacksnoop.py index 421ce1b65013..1eefc0afb3b0 100755 --- a/tools/stacksnoop.py +++ b/tools/stacksnoop.py @@ -114,8 +114,8 @@ def print_event(cpu, data, size): ts = time.time() - start_ts if verbose: - print("%-18.9f %-12.12s %-6d %-3d %s" % (ts, event.comm, event.pid, cpu, - function)) + print("%-18.9f %-12.12s %-6d %-3d %s" % + (ts, event.comm, event.pid, cpu, function)) else: print("%-18.9f %s" % (ts, function)) diff --git a/tools/tplist.py b/tools/tplist.py index c063b0011b19..627f20ed35a0 100755 --- a/tools/tplist.py +++ b/tools/tplist.py @@ -18,22 +18,23 @@ trace_root = "/sys/kernel/debug/tracing" event_root = os.path.join(trace_root, "events") -parser = argparse.ArgumentParser(description= - "Display kernel tracepoints or USDT probes and their formats.", - formatter_class=argparse.RawDescriptionHelpFormatter) -parser.add_argument("-p", "--pid", type=int, default=None, help= - "List USDT probes in the specified process") -parser.add_argument("-l", "--lib", default="", help= - "List USDT probes in the specified library or executable") -parser.add_argument("-v", dest="verbosity", action="count", help= - "Increase verbosity level (print variables, arguments, etc.)") -parser.add_argument(dest="filter", nargs="?", help= - "A filter that specifies which probes/tracepoints to print") +parser = argparse.ArgumentParser( + description="Display kernel tracepoints or USDT probes " + + "and their formats.", + formatter_class=argparse.RawDescriptionHelpFormatter) +parser.add_argument("-p", "--pid", type=int, default=None, + help="List USDT probes in the specified process") +parser.add_argument("-l", "--lib", default="", + help="List USDT probes in the specified library or executable") +parser.add_argument("-v", dest="verbosity", action="count", + help="Increase verbosity level (print variables, arguments, etc.)") +parser.add_argument(dest="filter", nargs="?", + help="A filter that specifies which probes/tracepoints to print") args = parser.parse_args() def print_tpoint_format(category, event): - fmt = open(os.path.join(event_root, category, event, "format") - ).readlines() + fmt = open(os.path.join(event_root, category, event, "format")) \ + .readlines() for line in fmt: match = re.search(r'field:([^;]*);', line) if match is None: @@ -81,7 +82,8 @@ def print_usdt_details(probe): print(" %d location(s)" % probe.num_locations) print(" %d argument(s)" % probe.num_arguments) else: - print("%s %s:%s" % (probe.bin_path, probe.provider, probe.name)) + print("%s %s:%s" % + (probe.bin_path, probe.provider, probe.name)) def print_usdt(pid, lib): reader = USDT(path=lib, pid=pid) @@ -103,4 +105,3 @@ def print_usdt(pid, lib): except: if sys.exc_info()[0] is not SystemExit: print(sys.exc_info()[1]) - diff --git a/tools/trace.py b/tools/trace.py index d6aef8d8cda4..d1169d36f539 100755 --- a/tools/trace.py +++ b/tools/trace.py @@ -106,8 +106,8 @@ def _parse_probe(self): if text[i] == ")": balance -= 1 if balance == 0: - self._parse_filter(text[:i+1]) - text = text[i+1:] + self._parse_filter(text[:i + 1]) + text = text[i + 1:] break if self.filter is None: self._bail("unmatched end of predicate") @@ -139,7 +139,7 @@ def _parse_spec(self, spec): self.tp_category = parts[1] self.tp_event = parts[2] self.library = "" # kernel - self.function = "" # generated from TRACEPOINT_PROBE + self.function = "" # from TRACEPOINT_PROBE elif self.probe_type == "u": self.library = parts[1] self.usdt_name = parts[2] @@ -155,7 +155,7 @@ def _find_usdt_probe(self): self.usdt = USDT(path=self.library, pid=Probe.pid) for probe in self.usdt.enumerate_probes(): if probe.name == self.usdt_name: - return # Found it, will enable later + return # Found it, will enable later self._bail("unrecognized USDT probe %s" % self.usdt_name) def _parse_filter(self, filt): @@ -163,7 +163,7 @@ def _parse_filter(self, filt): def _parse_types(self, fmt): for match in re.finditer( - r'[^%]%(s|u|d|llu|lld|hu|hd|x|llx|c|K|U)', fmt): + r'[^%]%(s|u|d|llu|lld|hu|hd|x|llx|c|K|U)', fmt): self.types.append(match.group(1)) fmt = re.sub(r'([^%]%)(u|d|llu|lld|hu|hd)', r'\1d', fmt) fmt = re.sub(r'([^%]%)(x|llx)', r'\1x', fmt) @@ -207,18 +207,18 @@ def _parse_action(self, action): def _replace_args(self, expr): for alias, replacement in Probe.aliases.items(): # For USDT probes, we replace argN values with the - # actual arguments for that probe obtained using special + # actual arguments for that probe obtained using # bpf_readarg_N macros emitted at BPF construction. if alias.startswith("arg") and self.probe_type == "u": continue expr = expr.replace(alias, replacement) return expr - p_type = { "u": ct.c_uint, "d": ct.c_int, - "llu": ct.c_ulonglong, "lld": ct.c_longlong, - "hu": ct.c_ushort, "hd": ct.c_short, - "x": ct.c_uint, "llx": ct.c_ulonglong, "c": ct.c_ubyte, - "K": ct.c_ulonglong, "U": ct.c_ulonglong } + p_type = {"u": ct.c_uint, "d": ct.c_int, + "llu": ct.c_ulonglong, "lld": ct.c_longlong, + "hu": ct.c_ushort, "hd": ct.c_short, + "x": ct.c_uint, "llx": ct.c_ulonglong, "c": ct.c_ubyte, + "K": ct.c_ulonglong, "U": ct.c_ulonglong} def _generate_python_field_decl(self, idx, fields): field_type = self.types[idx] @@ -245,12 +245,12 @@ def _generate_python_data_decl(self): return type(self.python_struct_name, (ct.Structure,), dict(_fields_=fields)) - c_type = { "u": "unsigned int", "d": "int", - "llu": "unsigned long long", "lld": "long long", - "hu": "unsigned short", "hd": "short", - "x": "unsigned int", "llx": "unsigned long long", - "c": "char", "K": "unsigned long long", - "U": "unsigned long long" } + c_type = {"u": "unsigned int", "d": "int", + "llu": "unsigned long long", "lld": "long long", + "hu": "unsigned short", "hd": "short", + "x": "unsigned int", "llx": "unsigned long long", + "c": "char", "K": "unsigned long long", + "U": "unsigned long long"} fmt_types = c_type.keys() def _generate_field_decl(self, idx): @@ -304,15 +304,15 @@ def _generate_field_assign(self, idx): text = "" if self.probe_type == "u" and expr[0:3] == "arg": text = (" u64 %s = 0;\n" + - " bpf_usdt_readarg(%s, ctx, &%s);\n") % \ - (expr, expr[3], expr) + " bpf_usdt_readarg(%s, ctx, &%s);\n") \ + % (expr, expr[3], expr) if field_type == "s": return text + """ if (%s != 0) { bpf_probe_read(&__data.v%d, sizeof(__data.v%d), (void *)%s); } -""" % (expr, idx, idx, expr) + """ % (expr, idx, idx, expr) if field_type in Probe.fmt_types: return text + " __data.v%d = (%s)%s;\n" % \ (idx, Probe.c_type[field_type], expr) @@ -322,7 +322,8 @@ def _generate_usdt_filter_read(self): text = "" if self.probe_type == "u": for arg, _ in Probe.aliases.items(): - if not (arg.startswith("arg") and (arg in self.filter)): + if not (arg.startswith("arg") and + (arg in self.filter)): continue arg_index = int(arg.replace("arg", "")) arg_ctype = self.usdt.get_probe_arg_ctype( @@ -346,12 +347,12 @@ def generate_program(self, include_self): pid_filter = """ u32 __pid = bpf_get_current_pid_tgid(); if (__pid != %d) { return 0; } -""" % Probe.pid + """ % Probe.pid elif not include_self: pid_filter = """ u32 __pid = bpf_get_current_pid_tgid(); if (__pid == %d) { return 0; } -""" % os.getpid() + """ % os.getpid() else: pid_filter = "" @@ -431,8 +432,8 @@ def _format_message(self, bpf, pid, values): # Replace each %K with kernel sym and %U with user sym in pid kernel_placeholders = [i for i in xrange(0, len(self.types)) if self.types[i] == 'K'] - user_placeholders = [i for i in xrange(0, len(self.types)) - if self.types[i] == 'U'] + user_placeholders = [i for i in xrange(0, len(self.types)) + if self.types[i] == 'U'] for kp in kernel_placeholders: values[kp] = bpf.ksymaddr(values[kp]) for up in user_placeholders: @@ -448,7 +449,7 @@ def print_event(self, bpf, cpu, data, size): msg = self._format_message(bpf, event.pid, values) time = strftime("%H:%M:%S") if Probe.use_localtime else \ Probe._time_off_str(event.timestamp_ns) - print("%-8s %-6d %-12s %-16s %s" % \ + print("%-8s %-6d %-12s %-16s %s" % (time[:8], event.pid, event.comm[:12], self._display_function(), msg)) @@ -493,7 +494,7 @@ def _attach_u(self, bpf): self._bail("unable to find library %s" % self.library) if self.probe_type == "u": - pass # Was already enabled by the BPF constructor + pass # Was already enabled by the BPF constructor elif self.probe_type == "r": bpf.attach_uretprobe(name=libpath, sym=self.function, @@ -534,26 +535,27 @@ class Tool(object): """ def __init__(self): - parser = argparse.ArgumentParser(description= - "Attach to functions and print trace messages.", - formatter_class=argparse.RawDescriptionHelpFormatter, - epilog=Tool.examples) + parser = argparse.ArgumentParser(description="Attach to " + + "functions and print trace messages.", + formatter_class=argparse.RawDescriptionHelpFormatter, + epilog=Tool.examples) parser.add_argument("-p", "--pid", type=int, help="id of the process to trace (optional)") parser.add_argument("-v", "--verbose", action="store_true", help="print resulting BPF program code before executing") parser.add_argument("-Z", "--string-size", type=int, default=80, help="maximum size to read from strings") - parser.add_argument("-S", "--include-self", action="store_true", + parser.add_argument("-S", "--include-self", + action="store_true", help="do not filter trace's own pid from the trace") parser.add_argument("-M", "--max-events", type=int, help="number of events to print before quitting") parser.add_argument("-o", "--offset", action="store_true", help="use relative time from first traced message") - parser.add_argument("-K", "--kernel-stack", action="store_true", - help="output kernel stack trace") - parser.add_argument("-U", "--user-stack", action="store_true", - help="output user stack trace") + parser.add_argument("-K", "--kernel-stack", + action="store_true", help="output kernel stack trace") + parser.add_argument("-U", "--user-stack", + action="store_true", help="output user stack trace") parser.add_argument(metavar="probe", dest="probes", nargs="+", help="probe specifier (see examples)") parser.add_argument("-I", "--include", action="append", @@ -609,7 +611,7 @@ def _main_loop(self): self.probes)) # Print header - print("%-8s %-6s %-12s %-16s %s" % \ + print("%-8s %-6s %-12s %-16s %s" % ("TIME", "PID", "COMM", "FUNC", "-" if not all_probes_trivial else "")) @@ -629,4 +631,4 @@ def run(self): print(sys.exc_info()[1]) if __name__ == "__main__": - Tool().run() + Tool().run()