bashreadline
authorBrendan Gregg <brendan.d.gregg@gmail.com>
Fri, 29 Jan 2016 06:43:37 +0000 (22:43 -0800)
committerBrendan Gregg <brendan.d.gregg@gmail.com>
Fri, 29 Jan 2016 06:43:37 +0000 (22:43 -0800)
README.md
man/man8/bashreadline.8 [new file with mode: 0644]
tools/bashreadline.py [new file with mode: 0755]
tools/bashreadline_example.txt [new file with mode: 0644]

index 0eae60c..7d88ee1 100644 (file)
--- a/README.md
+++ b/README.md
@@ -65,6 +65,7 @@ Examples:
 
 Tools:
 
+- tools/[bashreadline](tools/bashreadline.py): Print entered bash commands system wide. [Examples](tools/bashreadline_example.txt).
 - tools/[biolatency](tools/biolatency.py): Summarize block device I/O latency as a histogram. [Examples](tools/biolatency_example.txt).
 - tools/[biosnoop](tools/biosnoop.py): Trace block device I/O with PID and latency. [Examples](tools/biosnoop_example.txt).
 - tools/[funccount](tools/funccount.py): Count kernel function calls. [Examples](tools/funccount_example.txt).
diff --git a/man/man8/bashreadline.8 b/man/man8/bashreadline.8
new file mode 100644 (file)
index 0000000..c5f93e4
--- /dev/null
@@ -0,0 +1,48 @@
+.TH bashreadline 8  "2016-01-28" "USER COMMANDS"
+.SH NAME
+bashreadline \- Print entered bash commands system wide. Uses Linux eBPF/bcc.
+.SH SYNOPSIS
+.B bashreadline
+.SH DESCRIPTION
+bashreadline traces the return of the readline() function using uprobes, to
+show the bash commands that were entered interactively, system wide. The
+entered command may fail: this is just showing what was entered.
+
+This program is also a basic example of eBPF/bcc and uprobes.
+
+Since this uses BPF, only the root user can use this tool.
+.SH REQUIREMENTS
+CONFIG_BPF and bcc.
+.SH EXAMPLES
+.TP
+Trace bash commands system wide:
+#
+.B bashreadline
+.SH FIELDS
+.TP
+TIME
+Time of the command (HH:MM:SS).
+.TP
+PID
+Process ID of the bash shell.
+.TP
+COMMAND
+Entered command.
+.SH OVERHEAD
+As the rate of interactive bash commands is expected to be very low (<<100/s),
+the overhead of this program is expected to be negligible.
+.SH SOURCE
+This is from bcc.
+.IP
+https://github.com/iovisor/bcc
+.PP
+Also look in the bcc distribution for a companion _examples.txt file containing
+example usage, output, and commentary for this tool.
+.SH OS
+Linux
+.SH STABILITY
+Unstable - in development.
+.SH AUTHOR
+Brendan Gregg
+.SH SEE ALSO
+opensnoop(8)
diff --git a/tools/bashreadline.py b/tools/bashreadline.py
new file mode 100755 (executable)
index 0000000..464dfda
--- /dev/null
@@ -0,0 +1,43 @@
+#!/usr/bin/python
+#
+# bashreadline  Print entered bash commands from all running shells.
+#               For Linux, uses BCC, eBPF. Embedded C.
+#
+# This works by tracing the readline() function using a uretprobe (uprobes).
+#
+# Copyright 2016 Netflix, Inc.
+# Licensed under the Apache License, Version 2.0 (the "License")
+#
+# 28-Jan-2016    Brendan Gregg   Created this.
+
+from __future__ import print_function
+from bcc import BPF
+from time import strftime
+
+# load BPF program
+bpf_text = """
+#include <uapi/linux/ptrace.h>
+int printret(struct pt_regs *ctx) {
+    if (!ctx->ax)
+        return 0;
+
+    char str[80] = {};
+    bpf_probe_read(&str, sizeof(str), (void *)ctx->ax);
+    bpf_trace_printk("%s\\n", &str);
+
+    return 0;
+};
+"""
+b = BPF(text=bpf_text)
+b.attach_uretprobe(name="/bin/bash", sym="readline", fn_name="printret")
+
+# header
+print("%-9s %-6s %s" % ("TIME", "PID", "COMMAND"))
+
+# format output
+while 1:
+    try:
+        (task, pid, cpu, flags, ts, msg) = b.trace_fields()
+    except ValueError:
+        continue
+    print("%-9s %-6d %s" % (strftime("%H:%M:%S"), pid, msg))
diff --git a/tools/bashreadline_example.txt b/tools/bashreadline_example.txt
new file mode 100644 (file)
index 0000000..861a89b
--- /dev/null
@@ -0,0 +1,21 @@
+Demonstrations of bashreadline, the Linux eBPF/bcc version.
+
+
+This prints bash commands from all running bash shells on the system. For
+example:
+
+# ./bashreadline
+TIME      PID    COMMAND
+05:28:25  21176  ls -l
+05:28:28  21176  date
+05:28:35  21176  echo hello world
+05:28:43  21176  foo this command failed
+05:28:45  21176  df -h
+05:29:04  3059   echo another shell
+05:29:13  21176  echo first shell again
+
+The entered command may fail. This is just showing what command lines were
+entered interactively for bash to process.
+
+It works by tracing the return of the readline() function using uprobes
+(specifically a uretprobe).