aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorScott Lystig Fritchie <[email protected]>2011-11-17 00:44:30 -0600
committerPatrik Nyblom <[email protected]>2012-03-22 18:16:13 +0100
commit0331c29e0e494d4c1e4fdd05e48a3f88a8caea0b (patch)
tree4c08b3be38f82fa19c88faf68e65e5aae591cd4f
parent0721ac40f91295bb3995f86966e5dd031028ca85 (diff)
downloadotp-0331c29e0e494d4c1e4fdd05e48a3f88a8caea0b.tar.gz
otp-0331c29e0e494d4c1e4fdd05e48a3f88a8caea0b.tar.bz2
otp-0331c29e0e494d4c1e4fdd05e48a3f88a8caea0b.zip
Add DTrace support for OS X, Solaris, and Linux (via SystemTap), 2/4
Add D scripts in the `lib/dtrace/examples` directory. Add SystemTap README and sample scripts, contributed by Andreas Schultz <[email protected]>.
-rw-r--r--README.systemtap.md72
-rw-r--r--lib/dtrace/examples/dist.d62
-rw-r--r--lib/dtrace/examples/dist.systemtap76
-rw-r--r--lib/dtrace/examples/driver1.d114
-rw-r--r--lib/dtrace/examples/driver1.systemtap125
-rw-r--r--lib/dtrace/examples/efile_drv.d103
-rw-r--r--lib/dtrace/examples/efile_drv.systemtap112
-rw-r--r--lib/dtrace/examples/function-calls.d51
-rw-r--r--lib/dtrace/examples/function-calls.systemtap61
-rw-r--r--lib/dtrace/examples/garbage-collection.d39
-rw-r--r--lib/dtrace/examples/garbage-collection.systemtap49
-rw-r--r--lib/dtrace/examples/memory1.d41
-rw-r--r--lib/dtrace/examples/memory1.systemtap51
-rw-r--r--lib/dtrace/examples/messages.d94
-rw-r--r--lib/dtrace/examples/messages.systemtap87
-rw-r--r--lib/dtrace/examples/port1.d140
-rw-r--r--lib/dtrace/examples/port1.systemtap152
-rw-r--r--lib/dtrace/examples/process-scheduling.d35
-rw-r--r--lib/dtrace/examples/process-scheduling.systemtap45
-rw-r--r--lib/dtrace/examples/spawn-exit.d41
-rw-r--r--lib/dtrace/examples/spawn-exit.systemtap51
-rw-r--r--lib/dtrace/examples/user-probe.d36
-rw-r--r--lib/dtrace/examples/user-probe.systemtap46
23 files changed, 1683 insertions, 0 deletions
diff --git a/README.systemtap.md b/README.systemtap.md
new file mode 100644
index 0000000000..3bb3e626cd
--- /dev/null
+++ b/README.systemtap.md
@@ -0,0 +1,72 @@
+SystemTap and Erlang/OTP
+========================
+
+Introduction
+------------
+
+SystemTap is DTrace for Linux. In fact Erlang's SystemTap support
+is build using SystemTap's DTrace compatibility's layer. For an
+introduction to Erlang DTrace support read README.dtrace.md.
+
+Requisites
+----------
+
+* Linux Kernel with UTRACE support
+
+ check for UTRACE support in your current kernel:
+
+ # grep CONFIG_UTRACE /boot/config-`uname -r`
+ CONFIG_UTRACE=y
+
+ Fedora 16 is known to contain UTRACE, for most other Linux distributions
+ a custom build kernel will be required.
+ Check Fedora's SystemTap documentation for additional required packages
+ (e.g. Kernel Debug Symbols)
+
+* SystemTap > 1.6
+
+ A the time of writing this, the latest released version of SystemTap is
+ version 1.6. Erlang's DTrace support requires a MACRO that was introduced
+ after that release. So either get a newer release or build SystemTap from
+ git yourself (see: http://sourceware.org/systemtap/getinvolved.html)
+
+Building Erlang
+---------------
+
+Configure and build Erlang with SystemTap support:
+
+ # ./configure --enable-dtrace + whatever args you need
+ # make
+
+Testing
+-------
+
+SystemTap, unlike DTrace, needs to know what binary it is tracing and has to
+be able to read that binary before it starts tracing. Your probe script
+therefor has to reference the correct beam emulator and stap needs to be able
+to find that binary.
+The examples are written for "beam", but other versions such as "beam.smp" or
+"beam.debug.smp" might exist (depending on your configuration). Make sure you
+either specify the full the path of the binary in the probe or your "beam"
+binary is in the search path.
+
+All available probes can be listed like this:
+
+ # stap -L 'process("beam").mark("*")'
+
+or:
+
+ # PATH=/path/to/beam:$PATH stap -L 'process("beam").mark("*")'
+
+
+Probes in the dtrace.so NIF library like this:
+
+ # PATH=/path/to/dtrace/priv/lib:$PATH stap -L 'process("dtrace.so").mark("*")'
+
+Running SystemTap scripts
+-------------------------
+
+Adjust the process("beam") reference to your beam version and attach the script
+to a running "beam" instance:
+
+ # stap /path/to/probe/script/port1.systemtap -x <pid of beam>
diff --git a/lib/dtrace/examples/dist.d b/lib/dtrace/examples/dist.d
new file mode 100644
index 0000000000..f37c827f14
--- /dev/null
+++ b/lib/dtrace/examples/dist.d
@@ -0,0 +1,62 @@
+/* example usage: dtrace -q -s /path/to/dist.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::dist-monitor
+{
+ printf("monitor: pid %d, who %s, what %s, node %s, type %s, reason %s\n",
+ pid,
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), copyinstr(arg3),
+ copyinstr(arg4));
+}
+
+erlang*:::dist-port_busy
+{
+ printf("dist port_busy: node %s, port %s, remote_node %s, blocked pid %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), copyinstr(arg3));
+ blocked_procs[copyinstr(arg3)] = timestamp;
+}
+
+erlang*:::dist-port_busy
+{
+ printf("dist port_busy: node %s, port %s, remote_node %s, blocked pid %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), copyinstr(arg3));
+ blocked_procs[copyinstr(arg3)] = timestamp;
+}
+
+erlang*:::dist-output
+{
+ printf("dist output: node %s, port %s, remote_node %s bytes %d\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3);
+}
+
+erlang*:::dist-outputv
+{
+ printf("port outputv: node %s, port %s, remote_node %s bytes %d\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3);
+}
+
+erlang*:::process-scheduled
+/blocked_procs[copyinstr(arg0)]/
+{
+ pidstr = copyinstr(arg0);
+ printf("blocked pid %s scheduled now, waited %d microseconds\n",
+ pidstr, (timestamp - blocked_procs[pidstr]) / 1000);
+ blocked_procs[pidstr] = 0;
+}
diff --git a/lib/dtrace/examples/dist.systemtap b/lib/dtrace/examples/dist.systemtap
new file mode 100644
index 0000000000..af27b2cab6
--- /dev/null
+++ b/lib/dtrace/examples/dist.systemtap
@@ -0,0 +1,76 @@
+/* example usage: stap /path/to/dist.systemtap -x <pid> */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("beam").mark("dist-monitor")
+{
+ printf("monitor: pid %d, who %s, what %s, node %s, type %s, reason %s\n",
+ pid(),
+ user_string($arg1), user_string($arg2), user_string($arg3), user_string($arg4),
+ user_string($arg5));
+}
+
+probe process("beam").mark("dist-port_busy")
+{
+ printf("dist port_busy: node %s, port %s, remote_node %s, blocked pid %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), user_string($arg4));
+ blocked_procs[user_string($arg4)] = timestamp;
+}
+
+probe process("beam").mark("dist-port_busy")
+{
+ printf("dist port_busy: node %s, port %s, remote_node %s, blocked pid %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), user_string($arg4));
+ blocked_procs[user_string($arg4)] = timestamp;
+}
+
+probe process("beam").mark("dist-output")
+{
+ printf("dist output: node %s, port %s, remote_node %s bytes %d\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4);
+}
+
+probe process("beam").mark("dist-outputv")
+{
+ printf("port outputv: node %s, port %s, remote_node %s bytes %d\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4);
+}
+
+probe process("beam").mark("process-scheduled")
+{
+ pidstr = user_string($arg1);
+ if (pidstr in blocked_procs) {
+ printf("blocked pid %s scheduled now, waited %d microseconds\n",
+ pidstr, (timestamp - blocked_procs[pidstr]) / 1000);
+ delete blocked_procs[pidstr];
+ }
+}
+
+global blocked_procs;
diff --git a/lib/dtrace/examples/driver1.d b/lib/dtrace/examples/driver1.d
new file mode 100644
index 0000000000..9f53ffeb2a
--- /dev/null
+++ b/lib/dtrace/examples/driver1.d
@@ -0,0 +1,114 @@
+/* example usage: dtrace -q -s /path/to/driver1.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::driver-init
+{
+ printf("driver init name %s major %d minor %d flags %d\n",
+ copyinstr(arg0), arg1, arg2, arg3);
+}
+
+erlang*:::driver-start
+{
+ printf("driver start pid %s driver name %s port %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-stop
+{
+ printf("driver stop pid %s driver name %s port %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-finish
+{
+ printf("driver finish driver name %s port %s\n",
+ copyinstr(arg0), copyinstr(arg1));
+}
+
+erlang*:::driver-flush
+{
+ printf("driver flush pid %s port %s port name %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-output
+{
+ printf("driver output pid %s port %s port name %s bytes %d\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3);
+}
+
+erlang*:::driver-outputv
+{
+ printf("driver outputv pid %s port %s port name %s bytes %d\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3);
+}
+
+erlang*:::driver-control
+{
+ printf("driver control pid %s port %s port name %s command %d bytes %d\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3, arg4);
+}
+
+erlang*:::driver-call
+{
+ printf("driver call pid %s port %s port name %s command %d bytes %d\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3, arg4);
+}
+
+erlang*:::driver-event
+{
+ printf("driver event pid %s port %s port name %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-ready_input
+{
+ printf("driver ready_input pid %s port %s port name %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-ready_output
+{
+ printf("driver ready_output pid %s port %s port name %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-timeout
+{
+ printf("driver timeout pid %s port %s port name %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-ready_async
+{
+ printf("driver ready_async pid %s port %s port name %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-process_exit
+{
+ printf("driver process_exit pid %s port %s port name %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::driver-stop_select
+{
+ printf("driver stop_select driver name %s\n", copyinstr(arg0));
+}
diff --git a/lib/dtrace/examples/driver1.systemtap b/lib/dtrace/examples/driver1.systemtap
new file mode 100644
index 0000000000..8b99e465b7
--- /dev/null
+++ b/lib/dtrace/examples/driver1.systemtap
@@ -0,0 +1,125 @@
+/* example usage: stap /path/to/driver1.systemtap -x <pid> */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("beam").mark("driver-init")
+{
+ printf("driver init name %s major %d minor %d flags %d\n",
+ user_string($arg1), $arg2, $arg3, $arg4);
+}
+
+probe process("beam").mark("driver-start")
+{
+ printf("driver start pid %s driver name %s port %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-stop")
+{
+ printf("driver stop pid %s driver name %s port %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-finish")
+{
+ printf("driver finish driver name %s\n",
+ user_string($arg1));
+}
+
+probe process("beam").mark("driver-flush")
+{
+ printf("driver flush pid %s port %s port name %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-output")
+{
+ printf("driver output pid %s port %s port name %s bytes %d\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4);
+}
+
+probe process("beam").mark("driver-outputv")
+{
+ printf("driver outputv pid %s port %s port name %s bytes %d\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4);
+}
+
+probe process("beam").mark("driver-control")
+{
+ printf("driver control pid %s port %s port name %s command %d bytes %d\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4, $arg5);
+}
+
+probe process("beam").mark("driver-call")
+{
+ printf("driver call pid %s port %s port name %s command %d bytes %d\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4, $arg5);
+}
+
+probe process("beam").mark("driver-event")
+{
+ printf("driver event pid %s port %s port name %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-ready_input")
+{
+ printf("driver ready_input pid %s port %s port name %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-ready_output")
+{
+ printf("driver ready_output pid %s port %s port name %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-timeout")
+{
+ printf("driver timeout pid %s port %s port name %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-ready_async")
+{
+ printf("driver ready_async pid %s port %s port name %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-process_exit")
+{
+ printf("driver process_exit pid %s port %s port name %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("driver-stop_select")
+{
+ printf("driver stop_select driver name %s\n", user_string($arg1));
+}
diff --git a/lib/dtrace/examples/efile_drv.d b/lib/dtrace/examples/efile_drv.d
new file mode 100644
index 0000000000..c9c8080dba
--- /dev/null
+++ b/lib/dtrace/examples/efile_drv.d
@@ -0,0 +1,103 @@
+/* example usage: dtrace -q -s /path/to/efile_drv.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+BEGIN
+{
+ op_map[1] = "OPEN";
+ op_map[2] = "READ";
+ op_map[3] = "LSEEK";
+ op_map[4] = "WRITE";
+ op_map[5] = "FSTAT";
+ op_map[6] = "PWD";
+ op_map[7] = "READDIR";
+ op_map[8] = "CHDIR";
+ op_map[9] = "FSYNC";
+ op_map[10] = "MKDIR";
+ op_map[11] = "DELETE";
+ op_map[12] = "RENAME";
+ op_map[13] = "RMDIR";
+ op_map[14] = "TRUNCATE";
+ op_map[15] = "READ_FILE";
+ op_map[16] = "WRITE_INFO";
+ op_map[19] = "LSTAT";
+ op_map[20] = "READLINK";
+ op_map[21] = "LINK";
+ op_map[22] = "SYMLINK";
+ op_map[23] = "CLOSE";
+ op_map[24] = "PWRITEV";
+ op_map[25] = "PREADV";
+ op_map[26] = "SETOPT";
+ op_map[27] = "IPREAD";
+ op_map[28] = "ALTNAME";
+ op_map[29] = "READ_LINE";
+ op_map[30] = "FDATASYNC";
+ op_map[31] = "FADVISE";
+}
+
+erlang*:::aio_pool-add
+{
+ printf("async I/O pool port %s queue len %d\n", copyinstr(arg0), arg1);
+}
+
+erlang*:::aio_pool-get
+{
+ printf("async I/O pool port %s queue len %d\n", copyinstr(arg0), arg1);
+}
+
+erlang*:::efile_drv-entry
+{
+ printf("efile_drv enter tag={%d,%d} %s%s | %s (%d) | args: %s %s , %d %d (port %s)\n",
+ arg0, arg1,
+ arg2 == NULL ? "" : "user tag ",
+ arg2 == NULL ? "" : copyinstr(arg2),
+ op_map[arg3], arg3,
+ arg4 == NULL ? "" : copyinstr(arg4),
+ arg5 == NULL ? "" : copyinstr(arg5), arg6, arg7,
+ /* NOTE: port name in args[10] is experimental */
+ copyinstr((user_addr_t) args[10]))
+}
+
+erlang*:::efile_drv-int*
+{
+ printf("async I/O worker tag={%d,%d} | %s (%d) | %s\n",
+ arg0, arg1, op_map[arg2], arg2, probename);
+}
+
+/* efile_drv-return error case */
+erlang*:::efile_drv-return
+/arg4 == 0/
+{
+ printf("efile_drv return tag={%d,%d} %s%s | %s (%d) | errno %d\n",
+ arg0, arg1,
+ arg2 == NULL ? "" : "user tag ",
+ arg2 == NULL ? "" : copyinstr(arg2),
+ op_map[arg3], arg3,
+ arg5);
+}
+
+/* efile_drv-return success case */
+erlang*:::efile_drv-return
+/arg4 != 0/
+{
+ printf("efile_drv return tag={%d,%d} %s | %s (%d) ok\n",
+ arg0, arg1,
+ arg2 == NULL ? "" : copyinstr(arg2),
+ op_map[arg3], arg3);
+}
diff --git a/lib/dtrace/examples/efile_drv.systemtap b/lib/dtrace/examples/efile_drv.systemtap
new file mode 100644
index 0000000000..5a47b3e22b
--- /dev/null
+++ b/lib/dtrace/examples/efile_drv.systemtap
@@ -0,0 +1,112 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe begin
+{
+ op_map[1] = "OPEN";
+ op_map[2] = "READ";
+ op_map[3] = "LSEEK";
+ op_map[4] = "WRITE";
+ op_map[5] = "FSTAT";
+ op_map[6] = "PWD";
+ op_map[7] = "READDIR";
+ op_map[8] = "CHDIR";
+ op_map[9] = "FSYNC";
+ op_map[10] = "MKDIR";
+ op_map[11] = "DELETE";
+ op_map[12] = "RENAME";
+ op_map[13] = "RMDIR";
+ op_map[14] = "TRUNCATE";
+ op_map[15] = "READ_FILE";
+ op_map[16] = "WRITE_INFO";
+ op_map[19] = "LSTAT";
+ op_map[20] = "READLINK";
+ op_map[21] = "LINK";
+ op_map[22] = "SYMLINK";
+ op_map[23] = "CLOSE";
+ op_map[24] = "PWRITEV";
+ op_map[25] = "PREADV";
+ op_map[26] = "SETOPT";
+ op_map[27] = "IPREAD";
+ op_map[28] = "ALTNAME";
+ op_map[29] = "READ_LINE";
+ op_map[30] = "FDATASYNC";
+ op_map[31] = "FADVISE";
+}
+
+probe process("beam").mark("aio_pool-add")
+{
+ printf("async I/O pool port %s queue len %d\n", user_string($arg1), $arg2);
+}
+
+probe process("beam").mark("aio_pool-get")
+{
+ printf("async I/O pool port %s queue len %d\n", user_string($arg1), $arg2);
+}
+
+probe process("beam").mark("efile_drv-entry")
+{
+ printf("efile_drv enter tag={%d,%d} %s%s | %s (%d) | args: %s %s , %d %d (port %s)\n",
+ $arg1, $arg2,
+ $arg3 == NULL ? "" : "user tag ",
+ $arg3 == NULL ? "" : user_string($arg3),
+ op_map[$arg4], $arg4,
+ $arg5 == NULL ? "" : user_string($arg5),
+ $arg6 == NULL ? "" : user_string($arg6), $arg7, $arg8,
+ /* NOTE: port name in $arg[11] is experimental */
+ user_string($arg11))
+}
+
+probe process("beam").mark("efile_drv-int*")
+{
+ printf("async I/O worker tag={%d,%d} | %s (%d) | %s\n",
+ $arg1, $arg2, op_map[$arg3], $arg3, probefunc());
+}
+
+probe process("beam").mark("efile_drv-return")
+{
+ if ($arg5 == 0) {
+ /* efile_drv-return error case */
+ printf("efile_drv return tag={%d,%d} %s%s | %s (%d) | errno %d\n",
+ $arg1, $arg2,
+ $arg3 == NULL ? "" : "user tag ",
+ $arg3 == NULL ? "" : user_string($arg3),
+ op_map[$arg4], $arg4,
+ $arg6);
+ } else {
+ /* efile_drv-return success case */
+ printf("efile_drv return tag={%d,%d} %s | %s (%d) ok\n",
+ $arg1, $arg2,
+ $arg3 == NULL ? "" : user_string($arg3),
+ op_map[$arg4], $arg4);
+ }
+}
+
+global op_map;
diff --git a/lib/dtrace/examples/function-calls.d b/lib/dtrace/examples/function-calls.d
new file mode 100644
index 0000000000..238c5211ac
--- /dev/null
+++ b/lib/dtrace/examples/function-calls.d
@@ -0,0 +1,51 @@
+/* example usage: dtrace -q -s /path/to/function-calls.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::function-entry
+{
+ printf("pid %s enter %s depth %d\n",
+ copyinstr(arg0), copyinstr(arg1), arg2);
+}
+
+erlang*:::function-return
+{
+ printf("pid %s return %s depth %d\n",
+ copyinstr(arg0), copyinstr(arg1), arg2);
+}
+
+erlang*:::bif-entry
+{
+ printf("pid %s BIF entry mfa %s\n", copyinstr(arg0), copyinstr(arg1));
+}
+
+erlang*:::bif-return
+{
+ printf("pid %s BIF return mfa %s\n", copyinstr(arg0), copyinstr(arg1));
+}
+
+erlang*:::nif-entry
+{
+ printf("pid %s NIF entry mfa %s\n", copyinstr(arg0), copyinstr(arg1));
+}
+
+erlang*:::nif-return
+{
+ printf("pid %s NIF return mfa %s\n", copyinstr(arg0), copyinstr(arg1));
+}
diff --git a/lib/dtrace/examples/function-calls.systemtap b/lib/dtrace/examples/function-calls.systemtap
new file mode 100644
index 0000000000..8fc4375135
--- /dev/null
+++ b/lib/dtrace/examples/function-calls.systemtap
@@ -0,0 +1,61 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("beam").mark("function-entry")
+{
+ printf("pid %s enter %s depth %d\n",
+ user_string($arg1), user_string($arg2), $arg3);
+}
+
+probe process("beam").mark("function-return")
+{
+ printf("pid %s return %s depth %d\n",
+ user_string($arg1), user_string($arg2), $arg3);
+}
+
+probe process("beam").mark("bif-entry")
+{
+ printf("pid %s BIF entry mfa %s\n", user_string($arg1), user_string($arg2));
+}
+
+probe process("beam").mark("bif-return")
+{
+ printf("pid %s BIF return mfa %s\n", user_string($arg1), user_string($arg2));
+}
+
+probe process("beam").mark("nif-entry")
+{
+ printf("pid %s NIF entry mfa %s\n", user_string($arg1), user_string($arg2));
+}
+
+probe process("beam").mark("nif-return")
+{
+ printf("pid %s NIF return mfa %s\n", user_string($arg1), user_string($arg2));
+}
diff --git a/lib/dtrace/examples/garbage-collection.d b/lib/dtrace/examples/garbage-collection.d
new file mode 100644
index 0000000000..f234e7d4db
--- /dev/null
+++ b/lib/dtrace/examples/garbage-collection.d
@@ -0,0 +1,39 @@
+/* example usage: dtrace -q -s /path/to/garbage-collection.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::gc_major-start
+{
+ printf("GC major start pid %s need %d words\n", copyinstr(arg0), arg1);
+}
+
+erlang*:::gc_minor-start
+{
+ printf("GC minor start pid %s need %d words\n", copyinstr(arg0), arg1);
+}
+
+erlang*:::gc_major-end
+{
+ printf("GC major end pid %s reclaimed %d words\n", copyinstr(arg0), arg1);
+}
+
+erlang*:::gc_minor-start
+{
+ printf("GC minor end pid %s reclaimed %d words\n", copyinstr(arg0), arg1);
+}
diff --git a/lib/dtrace/examples/garbage-collection.systemtap b/lib/dtrace/examples/garbage-collection.systemtap
new file mode 100644
index 0000000000..64d69c6fbd
--- /dev/null
+++ b/lib/dtrace/examples/garbage-collection.systemtap
@@ -0,0 +1,49 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("beam").mark("gc_major-start")
+{
+ printf("GC major start pid %s need %d words\n", user_string($arg1), $arg2);
+}
+
+probe process("beam").mark("gc_minor-start")
+{
+ printf("GC minor start pid %s need %d words\n", user_string($arg1), $arg2);
+}
+
+probe process("beam").mark("gc_major-end")
+{
+ printf("GC major end pid %s reclaimed %d words\n", user_string($arg1), $arg2);
+}
+
+probe process("beam").mark("gc_minor-start")
+{
+ printf("GC minor end pid %s reclaimed %d words\n", user_string($arg1), $arg2);
+}
diff --git a/lib/dtrace/examples/memory1.d b/lib/dtrace/examples/memory1.d
new file mode 100644
index 0000000000..c2e16e0779
--- /dev/null
+++ b/lib/dtrace/examples/memory1.d
@@ -0,0 +1,41 @@
+/* example usage: dtrace -q -s /path/to/memory1.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::copy-struct
+{
+ printf("copy_struct %d bytes\n", arg0);
+}
+
+erlang*:::copy-object
+{
+ printf("copy_object pid %s %d bytes\n", copyinstr(arg0), arg1);
+}
+
+erlang*:::process-heap_grow
+{
+ printf("proc heap grow pid %s %d -> %d bytes\n", copyinstr(arg0),
+ arg1, arg2);
+}
+
+erlang*:::process-heap_shrink
+{
+ printf("proc heap shrink pid %s %d -> %d bytes\n", copyinstr(arg0),
+ arg1, arg2);
+}
diff --git a/lib/dtrace/examples/memory1.systemtap b/lib/dtrace/examples/memory1.systemtap
new file mode 100644
index 0000000000..9723f2d02d
--- /dev/null
+++ b/lib/dtrace/examples/memory1.systemtap
@@ -0,0 +1,51 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("beam").mark("copy-struct")
+{
+ printf("copy_struct %d bytes\n", $arg1);
+}
+
+probe process("beam").mark("copy-object")
+{
+ printf("copy_object pid %s %d bytes\n", user_string($arg1), $arg2);
+}
+
+probe process("beam").mark("process-heap_grow")
+{
+ printf("proc heap grow pid %s %d -> %d bytes\n", user_string($arg1),
+ $arg2, $arg3);
+}
+
+probe process("beam").mark("process-heap_shrink")
+{
+ printf("proc heap shrink pid %s %d -> %d bytes\n", user_string($arg1),
+ $arg2, $arg3);
+}
diff --git a/lib/dtrace/examples/messages.d b/lib/dtrace/examples/messages.d
new file mode 100644
index 0000000000..6361f3a220
--- /dev/null
+++ b/lib/dtrace/examples/messages.d
@@ -0,0 +1,94 @@
+/* example usage: dtrace -q -s /path/to/messages.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+BEGIN
+{
+ printf("\n");
+ printf("NOTE: message-queue message size 4294967295 means an external\n");
+ printf(" message that the code isn't smart enough to determine\n");
+ printf(" the actual size.\n");
+ printf("\n");
+}
+
+erlang*:::message-send
+/arg3 == 0 && arg4 == 0 && arg5 == 0/
+{
+ printf("send: %s -> %s: %d words\n",
+ copyinstr(arg0), copyinstr(arg1), arg2);
+}
+
+erlang*:::message-send
+/arg3 != 0 || arg4 != 0 || arg5 != 0/
+{
+ printf("send: %s label %d token {%d,%d} -> %s: %d words\n",
+ copyinstr(arg0),
+ arg3, arg4, arg5,
+ copyinstr(arg1), arg2);
+}
+
+/*
+ * TODO:
+ * Weird, on my OS X box, beam says arg6 = 0 but this script says 4294967296.
+ */
+
+erlang*:::message-send-remote
+/arg4 == 0 && arg5 == 0 && (arg6 == 0 || arg6 >= 4294967296)/
+{
+ printf("send : %s -> %s %s: %d words\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3);
+}
+
+erlang*:::message-send-remote
+/arg4 != 0 || arg5 != 0 || arg6 < 4294967296/
+{
+ printf("send : %s label %d token {%d,%d} -> %s %s: %d words\n",
+ copyinstr(arg0),
+ arg4, arg5, arg6,
+ copyinstr(arg1), copyinstr(arg2), arg3);
+}
+
+erlang*:::message-queued
+/arg3 == 0 && arg4 == 0 && arg5 == 0/
+{
+ printf("queued: %s: %d words, queue len %d\n", copyinstr(arg0), arg1, arg2);
+}
+
+erlang*:::message-queued
+/arg3 != 0 || arg4 != 0 || arg5 != 0/
+{
+ printf("queued: %s label %d token {%d,%d}: %d words, queue len %d\n",
+ copyinstr(arg0), arg3, arg4, arg5,
+ arg1, arg2);
+}
+
+erlang*:::message-receive
+/arg3 == 0 && arg4 == 0 && arg5 == 0/
+{
+ printf("receive: %s: %d words, queue len %d\n",
+ copyinstr(arg0), arg1, arg2);
+}
+
+erlang*:::message-receive
+/arg3 != 0 || arg4 != 0 || arg5 != 0/
+{
+ printf("receive: %s label %d token {%d,%d}: %d words, queue len %d\n",
+ copyinstr(arg0), arg3, arg4, arg5,
+ arg1, arg2);
+}
diff --git a/lib/dtrace/examples/messages.systemtap b/lib/dtrace/examples/messages.systemtap
new file mode 100644
index 0000000000..ff8f4076b1
--- /dev/null
+++ b/lib/dtrace/examples/messages.systemtap
@@ -0,0 +1,87 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe begin
+{
+ printf("\n");
+ printf("NOTE: message-queue message size 4294967295 means an external\n");
+ printf(" message that the code isn't smart enough to determine\n");
+ printf(" the actual size.\n");
+ printf("\n");
+}
+
+probe process("beam").mark("message-send")
+{
+ if ($arg4 == 0 && $arg5 == 0 && $arg6 == 0) {
+ printf("send: %s -> %s: %d words\n",
+ user_string($arg1), user_string($arg2), $arg3);
+ } else {
+ printf("send: %s label %d token {%d,%d} -> %s: %d words\n",
+ user_string($arg1),
+ $arg4, $arg5, $arg6,
+ user_string($arg2), $arg3);
+ }
+}
+
+probe process("beam").mark("message-send-remote")
+{
+ if ($arg5 == 0 && $arg6 == 0 && $arg7 == 0) {
+ printf("send : %s -> %s %s: %d words\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4);
+ } else {
+ printf("send : %s label %d token {%d,%d} -> %s %s: %d words\n",
+ user_string($arg1),
+ $arg5, $arg6, $arg7,
+ user_string($arg2), user_string($arg3), $arg4);
+ }
+}
+
+probe process("beam").mark("message-queued")
+{
+ if ($arg4 == 0 && $arg5 == 0 && $arg6 == 0) {
+ printf("queued: %s: %d words, queue len %d\n", user_string($arg1), $arg2, $arg3);
+ } else {
+ printf("queued: %s label %d token {%d,%d}: %d words, queue len %d\n",
+ user_string($arg1), $arg4, $arg5, $arg6,
+ $arg2, $arg3);
+ }
+}
+
+probe process("beam").mark("message-receive")
+{
+ if ($arg4 == 0 && $arg5 == 0 && $arg6 == 0) {
+ printf("receive: %s: %d words, queue len %d\n",
+ user_string($arg1), $arg2, $arg3);
+ } else {
+ printf("receive: %s label %d token {%d,%d}: %d words, queue len %d\n",
+ user_string($arg1), $arg4, $arg5, $arg6,
+ $arg2, $arg3);
+ }
+}
diff --git a/lib/dtrace/examples/port1.d b/lib/dtrace/examples/port1.d
new file mode 100644
index 0000000000..b82e783a14
--- /dev/null
+++ b/lib/dtrace/examples/port1.d
@@ -0,0 +1,140 @@
+/* example usage: dtrace -q -s /path/to/port1.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+BEGIN
+{
+ driver_map["tcp_inet", 1] = "OPEN";
+ driver_map["tcp_inet", 2] = "CLOSE";
+ driver_map["tcp_inet", 3] = "CONNECT";
+ driver_map["tcp_inet", 4] = "PEER";
+ driver_map["tcp_inet", 5] = "NAME";
+ driver_map["tcp_inet", 6] = "BIND";
+ driver_map["tcp_inet", 7] = "SETOPTS";
+ driver_map["tcp_inet", 8] = "GETOPTS";
+ driver_map["tcp_inet", 11] = "GETSTAT";
+ driver_map["tcp_inet", 12] = "GETHOSTNAME";
+ driver_map["tcp_inet", 13] = "FDOPEN";
+ driver_map["tcp_inet", 14] = "GETFD";
+ driver_map["tcp_inet", 15] = "GETTYPE";
+ driver_map["tcp_inet", 16] = "GETSTATUS";
+ driver_map["tcp_inet", 17] = "GETSERVBYNAME";
+ driver_map["tcp_inet", 18] = "GETSERVBYPORT";
+ driver_map["tcp_inet", 19] = "SETNAME";
+ driver_map["tcp_inet", 20] = "SETPEER";
+ driver_map["tcp_inet", 21] = "GETIFLIST";
+ driver_map["tcp_inet", 22] = "IFGET";
+ driver_map["tcp_inet", 23] = "IFSET";
+ driver_map["tcp_inet", 24] = "SUBSCRIBE";
+ driver_map["tcp_inet", 25] = "GETIFADDRS";
+ driver_map["tcp_inet", 40] = "ACCEPT";
+ driver_map["tcp_inet", 41] = "LISTEN";
+ driver_map["tcp_inet", 42] = "RECV";
+ driver_map["tcp_inet", 43] = "UNRECV";
+ driver_map["tcp_inet", 44] = "SHUTDOWN";
+ driver_map["tcp_inet", 60] = "RECV";
+ driver_map["tcp_inet", 61] = "LISTEN";
+ driver_map["tcp_inet", 62] = "BINDX";
+ /* No looping constructs, so repeat for udp_inet */
+ driver_map["udp_inet", 1] = "OPEN";
+ driver_map["udp_inet", 2] = "CLOSE";
+ driver_map["udp_inet", 3] = "CONNECT";
+ driver_map["udp_inet", 4] = "PEER";
+ driver_map["udp_inet", 5] = "NAME";
+ driver_map["udp_inet", 6] = "BIND";
+ driver_map["udp_inet", 7] = "SETOPTS";
+ driver_map["udp_inet", 8] = "GETOPTS";
+ driver_map["udp_inet", 11] = "GETSTAT";
+ driver_map["udp_inet", 12] = "GETHOSTNAME";
+ driver_map["udp_inet", 13] = "FDOPEN";
+ driver_map["udp_inet", 14] = "GETFD";
+ driver_map["udp_inet", 15] = "GETTYPE";
+ driver_map["udp_inet", 16] = "GETSTATUS";
+ driver_map["udp_inet", 17] = "GETSERVBYNAME";
+ driver_map["udp_inet", 18] = "GETSERVBYPORT";
+ driver_map["udp_inet", 19] = "SETNAME";
+ driver_map["udp_inet", 20] = "SETPEER";
+ driver_map["udp_inet", 21] = "GETIFLIST";
+ driver_map["udp_inet", 22] = "IFGET";
+ driver_map["udp_inet", 23] = "IFSET";
+ driver_map["udp_inet", 24] = "SUBSCRIBE";
+ driver_map["udp_inet", 25] = "GETIFADDRS";
+ driver_map["udp_inet", 40] = "ACCEPT";
+ driver_map["udp_inet", 41] = "LISTEN";
+ driver_map["udp_inet", 42] = "RECV";
+ driver_map["udp_inet", 43] = "UNRECV";
+ driver_map["udp_inet", 44] = "SHUTDOWN";
+ driver_map["udp_inet", 60] = "RECV";
+ driver_map["udp_inet", 61] = "LISTEN";
+ driver_map["udp_inet", 62] = "BINDX";
+}
+
+erlang*:::port-open
+{
+ printf("port open pid %s port name %s port %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::port-command
+{
+ printf("port command pid %s port %s port name %s command type %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), copyinstr(arg3));
+}
+
+erlang*:::port-control
+{
+ cmd = driver_map[copyinstr(arg2), arg3];
+ cmd_str = (cmd == 0) ? "unknown" : cmd;
+ printf("port control pid %s port %s port name %s command %d %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), arg3, cmd_str);
+}
+
+/* port-exit is fired as a result of port_close() or exit signal */
+
+erlang*:::port-exit
+{
+ printf("port exit pid %s port %s port name %s reason %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), copyinstr(arg3));
+}
+
+erlang*:::port-connect
+{
+ printf("port connect pid %s port %s port name %s new pid %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), copyinstr(arg3));
+}
+
+erlang*:::port-busy
+{
+ printf("port busy %s\n", copyinstr(arg0));
+}
+
+erlang*:::port-not_busy
+{
+ printf("port not busy %s\n", copyinstr(arg0));
+}
+
+erlang*:::aio_pool-add
+{
+ printf("async I/O pool add thread %d queue len %d\n", arg0, arg1);
+}
+
+erlang*:::aio_pool-get
+{
+ printf("async I/O pool get thread %d queue len %d\n", arg0, arg1);
+}
diff --git a/lib/dtrace/examples/port1.systemtap b/lib/dtrace/examples/port1.systemtap
new file mode 100644
index 0000000000..a63d9b670c
--- /dev/null
+++ b/lib/dtrace/examples/port1.systemtap
@@ -0,0 +1,152 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe begin
+{
+ driver_map["tcp_inet", 1] = "OPEN";
+ driver_map["tcp_inet", 2] = "CLOSE";
+ driver_map["tcp_inet", 3] = "CONNECT";
+ driver_map["tcp_inet", 4] = "PEER";
+ driver_map["tcp_inet", 5] = "NAME";
+ driver_map["tcp_inet", 6] = "BIND";
+ driver_map["tcp_inet", 7] = "SETOPTS";
+ driver_map["tcp_inet", 8] = "GETOPTS";
+ driver_map["tcp_inet", 11] = "GETSTAT";
+ driver_map["tcp_inet", 12] = "GETHOSTNAME";
+ driver_map["tcp_inet", 13] = "FDOPEN";
+ driver_map["tcp_inet", 14] = "GETFD";
+ driver_map["tcp_inet", 15] = "GETTYPE";
+ driver_map["tcp_inet", 16] = "GETSTATUS";
+ driver_map["tcp_inet", 17] = "GETSERVBYNAME";
+ driver_map["tcp_inet", 18] = "GETSERVBYPORT";
+ driver_map["tcp_inet", 19] = "SETNAME";
+ driver_map["tcp_inet", 20] = "SETPEER";
+ driver_map["tcp_inet", 21] = "GETIFLIST";
+ driver_map["tcp_inet", 22] = "IFGET";
+ driver_map["tcp_inet", 23] = "IFSET";
+ driver_map["tcp_inet", 24] = "SUBSCRIBE";
+ driver_map["tcp_inet", 25] = "GETIFADDRS";
+ driver_map["tcp_inet", 40] = "ACCEPT";
+ driver_map["tcp_inet", 41] = "LISTEN";
+ driver_map["tcp_inet", 42] = "RECV";
+ driver_map["tcp_inet", 43] = "UNRECV";
+ driver_map["tcp_inet", 44] = "SHUTDOWN";
+ driver_map["tcp_inet", 60] = "RECV";
+ driver_map["tcp_inet", 61] = "LISTEN";
+ driver_map["tcp_inet", 62] = "BINDX";
+ /* No looping constructs, so repeat for udp_inet */
+ driver_map["udp_inet", 1] = "OPEN";
+ driver_map["udp_inet", 2] = "CLOSE";
+ driver_map["udp_inet", 3] = "CONNECT";
+ driver_map["udp_inet", 4] = "PEER";
+ driver_map["udp_inet", 5] = "NAME";
+ driver_map["udp_inet", 6] = "BIND";
+ driver_map["udp_inet", 7] = "SETOPTS";
+ driver_map["udp_inet", 8] = "GETOPTS";
+ driver_map["udp_inet", 11] = "GETSTAT";
+ driver_map["udp_inet", 12] = "GETHOSTNAME";
+ driver_map["udp_inet", 13] = "FDOPEN";
+ driver_map["udp_inet", 14] = "GETFD";
+ driver_map["udp_inet", 15] = "GETTYPE";
+ driver_map["udp_inet", 16] = "GETSTATUS";
+ driver_map["udp_inet", 17] = "GETSERVBYNAME";
+ driver_map["udp_inet", 18] = "GETSERVBYPORT";
+ driver_map["udp_inet", 19] = "SETNAME";
+ driver_map["udp_inet", 20] = "SETPEER";
+ driver_map["udp_inet", 21] = "GETIFLIST";
+ driver_map["udp_inet", 22] = "IFGET";
+ driver_map["udp_inet", 23] = "IFSET";
+ driver_map["udp_inet", 24] = "SUBSCRIBE";
+ driver_map["udp_inet", 25] = "GETIFADDRS";
+ driver_map["udp_inet", 40] = "ACCEPT";
+ driver_map["udp_inet", 41] = "LISTEN";
+ driver_map["udp_inet", 42] = "RECV";
+ driver_map["udp_inet", 43] = "UNRECV";
+ driver_map["udp_inet", 44] = "SHUTDOWN";
+ driver_map["udp_inet", 60] = "RECV";
+ driver_map["udp_inet", 61] = "LISTEN";
+ driver_map["udp_inet", 62] = "BINDX";
+}
+
+probe process("beam").mark("port-open")
+{
+ printf("port open pid %s port name %s port %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("port-command")
+{
+ printf("port command pid %s port %s port name %s command type %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), user_string($arg4));
+}
+
+probe process("beam").mark("port-control")
+{
+ cmd = driver_map[user_string($arg3), $arg4];
+ cmd_str = (cmd == "") ? "unknown" : cmd;
+ printf("port control pid %s port %s port name %s command %d %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), $arg4, cmd_str);
+}
+
+/* port-exit is fired as a result of port_close() or exit signal */
+
+probe process("beam").mark("port-exit")
+{
+ printf("port exit pid %s port %s port name %s reason %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), user_string($arg4));
+}
+
+probe process("beam").mark("port-connect")
+{
+ printf("port connect pid %s port %s port name %s new pid %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), user_string($arg4));
+}
+
+probe process("beam").mark("port-busy")
+{
+ printf("port busy %s\n", user_string($arg1));
+}
+
+probe process("beam").mark("port-not_busy")
+{
+ printf("port not busy %s\n", user_string($arg1));
+}
+
+probe process("beam").mark("aio_pool-add")
+{
+ printf("async I/O pool add thread %d queue len %d\n", $arg1, $arg2);
+}
+
+probe process("beam").mark("aio_pool-get")
+{
+ printf("async I/O pool get thread %d queue len %d\n", $arg1, $arg2);
+}
+
+global driver_map; \ No newline at end of file
diff --git a/lib/dtrace/examples/process-scheduling.d b/lib/dtrace/examples/process-scheduling.d
new file mode 100644
index 0000000000..9e31da2774
--- /dev/null
+++ b/lib/dtrace/examples/process-scheduling.d
@@ -0,0 +1,35 @@
+/* example usage: dtrace -q -s /path/to/process-scheduling.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::process-scheduled
+{
+ printf(" Schedule pid %s mfa %s\n", copyinstr(arg0), copyinstr(arg1));
+}
+
+erlang*:::process-unscheduled
+{
+ printf("Unschedule pid %s\n", copyinstr(arg0));
+}
+
+erlang*:::process-hibernate
+{
+ printf(" Hibernate pid %s resume mfa %s\n",
+ copyinstr(arg0), copyinstr(arg1));
+}
diff --git a/lib/dtrace/examples/process-scheduling.systemtap b/lib/dtrace/examples/process-scheduling.systemtap
new file mode 100644
index 0000000000..c8cee60a07
--- /dev/null
+++ b/lib/dtrace/examples/process-scheduling.systemtap
@@ -0,0 +1,45 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("beam").mark("process-scheduled")
+{
+ printf(" Schedule pid %s mfa %s\n", user_string($arg1), user_string($arg2));
+}
+
+probe process("beam").mark("process-unscheduled")
+{
+ printf("Unschedule pid %s\n", user_string($arg1));
+}
+
+probe process("beam").mark("process-hibernate")
+{
+ printf(" Hibernate pid %s resume mfa %s\n",
+ user_string($arg1), user_string($arg2));
+}
diff --git a/lib/dtrace/examples/spawn-exit.d b/lib/dtrace/examples/spawn-exit.d
new file mode 100644
index 0000000000..7310f3343d
--- /dev/null
+++ b/lib/dtrace/examples/spawn-exit.d
@@ -0,0 +1,41 @@
+/* example usage: dtrace -q -s /path/to/spawn-exit.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::process-spawn
+{
+ printf("pid %s mfa %s\n", copyinstr(arg0), copyinstr(arg1));
+}
+
+erlang*:::process-exit
+{
+ printf("pid %s reason %s\n", copyinstr(arg0), copyinstr(arg1));
+}
+
+erlang*:::process-exit_signal
+{
+ printf("sender %s -> pid %s reason %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2));
+}
+
+erlang*:::process-exit_signal-remote
+{
+ printf("sender %s -> node %s pid %s reason %s\n",
+ copyinstr(arg0), copyinstr(arg1), copyinstr(arg2), copyinstr(arg3));
+}
diff --git a/lib/dtrace/examples/spawn-exit.systemtap b/lib/dtrace/examples/spawn-exit.systemtap
new file mode 100644
index 0000000000..5e3be9fc1b
--- /dev/null
+++ b/lib/dtrace/examples/spawn-exit.systemtap
@@ -0,0 +1,51 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("beam").mark("process-spawn")
+{
+ printf("pid %s mfa %s\n", user_string($arg1), user_string($arg2));
+}
+
+probe process("beam").mark("process-exit")
+{
+ printf("pid %s reason %s\n", user_string($arg1), user_string($arg2));
+}
+
+probe process("beam").mark("process-exit_signal")
+{
+ printf("sender %s -> pid %s reason %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3));
+}
+
+probe process("beam").mark("process-exit_signal-remote")
+{
+ printf("sender %s -> node %s pid %s reason %s\n",
+ user_string($arg1), user_string($arg2), user_string($arg3), user_string($arg4));
+}
diff --git a/lib/dtrace/examples/user-probe.d b/lib/dtrace/examples/user-probe.d
new file mode 100644
index 0000000000..13baff6a32
--- /dev/null
+++ b/lib/dtrace/examples/user-probe.d
@@ -0,0 +1,36 @@
+/* example usage: dtrace -q -s /path/to/user-probe.d */
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+
+erlang*:::user_trace-s1
+{
+ printf("%s\n", copyinstr(arg0));
+}
+
+erlang*:::user_trace-i4s4
+{
+ printf("%s %s %d %d %d %d '%s' '%s' '%s' '%s'\n",
+ copyinstr(arg0),
+ arg1 == NULL ? "" : copyinstr(arg1),
+ arg2, arg3, arg4, arg5,
+ arg6 == NULL ? "" : copyinstr(arg6),
+ arg7 == NULL ? "" : copyinstr(arg7),
+ arg8 == NULL ? "" : copyinstr(arg8),
+ arg9 == NULL ? "" : copyinstr(arg9));
+}
diff --git a/lib/dtrace/examples/user-probe.systemtap b/lib/dtrace/examples/user-probe.systemtap
new file mode 100644
index 0000000000..c80bf94697
--- /dev/null
+++ b/lib/dtrace/examples/user-probe.systemtap
@@ -0,0 +1,46 @@
+/*
+ * %CopyrightBegin%
+ *
+ * Copyright Scott Lystig Fritchie and Andreas Schultz, 2011. All Rights Reserved.
+ *
+ * The contents of this file are subject to the Erlang Public License,
+ * Version 1.1, (the "License"); you may not use this file except in
+ * compliance with the License. You should have received a copy of the
+ * Erlang Public License along with this software. If not, it can be
+ * retrieved online at http://www.erlang.org/.
+ *
+ * Software distributed under the License is distributed on an "AS IS"
+ * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
+ * the License for the specific language governing rights and limitations
+ * under the License.
+ *
+ * %CopyrightEnd%
+ */
+/*
+ * Note: This file assumes that you're using the non-SMP-enabled Erlang
+ * virtual machine, "beam". The SMP-enabled VM is called "beam.smp".
+ * Note that other variations of the virtual machine also have
+ * different names, e.g. the debug build of the SMP-enabled VM
+ * is "beam.debug.smp".
+ *
+ * To use a different virtual machine, replace each instance of
+ * "beam" with "beam.smp" or the VM name appropriate to your
+ * environment.
+ */
+
+probe process("dtrace.so").mark("user_trace-s1")
+{
+ printf("%s\n", user_string($arg1));
+}
+
+probe process("dtrace.so").mark("user_trace-i4s4")
+{
+ printf("%s %s %d %d %d %d '%s' '%s' '%s' '%s'\n",
+ user_string($arg1),
+ $arg2 == NULL ? "" : user_string($arg2),
+ $arg3, $arg4, $arg5, $arg6,
+ $arg7 == NULL ? "" : user_string($arg7),
+ $arg8 == NULL ? "" : user_string($arg8),
+ $arg9 == NULL ? "" : user_string($arg9),
+ $arg9 == NULL ? "" : user_string($arg9));
+}