Regarding wrapper executables, I've landed up with the following script for PostgreSQL. (I've trimmed out various postgres-specific parts like discovering the supplied valgrind suppressions file).
#!/bin/bash
set -e -u -x
# Pop top two elements from path; the first is added by pg_regress
# and the next is us.
function join_by { local IFS="$1"; shift; echo "$*"; }
IFS=':' read -r -a PATHA <<< "$PATH"
export PATH=$(join_by ":" "${PATHA[@]:2}")
NEXT_POSTGRES=$(which postgres)
if [ "${NEXT_POSTGRES}" -ef "./valgrind/postgres" ]; then
echo "ERROR: attempt to execute self"
exit 1
fi
echo "Running ${NEXT_POSTGRES} under Valgrind"
valgrind --leak-check=full --show-leak-kinds=definite,possible \
--gen-suppressions=all --verbose --time-stamp=yes \
--log-file=valgrind-$$-%p.log --trace-children=yes \
--track-origins=yes --read-var-info=yes --malloc-fill=8f \
--free-fill=9f --num-callers=30 postgres "$@"
Note the PATH
manipulation to ensure that we don't try to exec postgres
from the same place again. In this case it was necessary that the wrapper script also be named exactly postgres
so I had to make sure it didn't recursively execute its self.
An alternative is to use whatis -a
to find the next executable in the path and run it directly. But I found that caused other issues for my use case.
BTW, if you get an error like
valgrind: mmap(0x58000000, 2347008) failed in UME with error 22 (Invalid argument).
valgrind: this can be caused by executables with very large text, data or bss segments.
... then it's quite possible you're trying to run valgrind under valgrind by mistake.