I have a script like this:
script.sh
#!/bin/bash
clang -v
If I do a dtruss
on it then I would expect to see an execve
call to clang
.
$ sudo dtruss -f -a -e ./script.sh
However, the trace does not contain an execve
. Instead there is an error:
...
1703/0x16931: 856 4 0 sigaction(0x15, 0x7FFEE882A3B8, 0x7FFEE882A3F8) = 0 0
1703/0x16931: 858 4 0 sigaction(0x16, 0x7FFEE882A3C8, 0x7FFEE882A408) = 0 0
1703/0x16931: 874 4 0 sigaction(0x2, 0x7FFEE882A3C8, 0x7FFEE882A408) = 0 0
1703/0x16931: 881 4 0 sigaction(0x3, 0x7FFEE882A3C8, 0x7FFEE882A408) = 0 0
1703/0x16931: 883 4 0 sigaction(0x14, 0x7FFEE882A3C8, 0x7FFEE882A408) = 0 0
dtrace: error on enabled probe ID 2149 (ID 280: syscall::execve:return): invalid address (0x7fc2b5502c30) in action #12 at DIF offset 12
1703/0x16932: 2873: 0: 0 fork() = 0 0
1703/0x16932: 2879 138 5 thread_selfid(0x0, 0x0, 0x0) = 92466 0
1703/0x16932: 2958 8 0 issetugid(0x0, 0x0, 0x0) = 0 0
1703/0x16932: 2975 8 1 csrctl(0x0, 0x7FFEEE21DC3C, 0x4) = 0 0
1703/0x16932: 2985 12 6 csops(0x0, 0x0, 0x7FFEEE21E550) = 0 0
1703/0x16932: 3100 13 3 shared_region_check_np(0x7FFEEE21DA98, 0x0, 0x0)
...
- What is causing this error?
- How can I get the
execve
command to show so that I can see the program called and its arguments?
This means that the DTrace script that
dtruss
is using internally is accessing an invalid memory address, which is happening while it's trying to trace theexecve
call you're curious about. So basically,dtruss
(or possibly DTrace itself) appears to have a bug which is preventing you from getting the information you want. Apple hasn't been the best about keeping DTrace and the tools that depend on it working well on macOS, unfortunately :-/.For Bash / shell scripts in particular, you can make it print every command that it runs by adding
set -x
at the top of your script (more info in this other answer).If you want, you could also try using DTrace directly instead -- this is a pretty simple one-liner (haven't tried running this myself so apologies if there are typos):
The way this works is:
proc:::exec-success
: Trace allexec-success
events in the system, which fire in the subprocess when anexec*
-family syscall returns successfully./ppid == $target/
: Filter which means this only fires when the parent process's PID (ppid
) matches the PID returned for the process started by the-c
option we passed to thedtrace
command ($target
).{ trace(curpsinfo->pr_psargs); }
: This is the action to take when the event fires and it matches our filter. We simply print (trace
) the arguments passed to the process, which is stored in thecurpsinfo
variable.(If that fails with a similar-looking error, it's likely that the bug is in macOS's implementation of
curpsinfo
somewhere.)