2013-07-08 09:56:30 +04:00
#!/bin/sh
# This script parses /proc/locks and finds the processes that are holding
# locks on CTDB databases. For all those processes the script dumps a
# stack trace using gstack.
#
# This script can be used only if Samba is configured to use fcntl locks
# rather than mutex locks.
2013-11-04 05:56:39 +04:00
[ -n " $CTDB_BASE " ] || \
export CTDB_BASE = $( cd -P $( dirname " $0 " ) ; echo " $PWD " )
. " $CTDB_BASE /functions "
2013-11-26 06:27:46 +04:00
# Default fallback location for database directories.
# These can be overwritten from CTDB configuration
CTDB_DBDIR = " ${ CTDB_VARDIR } "
CTDB_DBDIR_PERSISTENT = " ${ CTDB_VARDIR } /persistent "
2013-11-04 05:56:39 +04:00
loadconfig ctdb
2013-11-15 11:59:04 +04:00
(
flock -n 9 || exit 1
echo " ===== Start of debug locks PID= $$ ===== "
# Create sed expression to convert inodes to names
sed_cmd = $( ls -li " $CTDB_DBDIR " /*.tdb.* " $CTDB_DBDIR_PERSISTENT " /*.tdb.* |
2013-11-04 05:56:39 +04:00
sed -e " s# ${ CTDB_DBDIR } /\(.*\)#\1# " \
-e " s# ${ CTDB_DBDIR_PERSISTENT } /\(.*\)#\1# " |
2014-09-25 06:46:22 +04:00
awk '{printf "s#[0-9a-f]*:[0-9a-f]*:%s #%s #\n", $1, $10}' )
2013-07-08 09:56:30 +04:00
2013-11-15 11:59:04 +04:00
# Parse /proc/locks and extract following information
# pid process_name tdb_name offsets [W]
out = $( cat /proc/locks |
2013-07-08 09:56:30 +04:00
grep -F "POSIX ADVISORY WRITE" |
awk '{ if($2 == "->") { print $6, $7, $8, $9, "W" } else { print $5, $6, $7, $8 } }' |
while read pid rest ; do
pname = $( readlink /proc/$pid /exe)
echo $pid $pname $rest
done | sed -e " $sed_cmd " | grep "\.tdb" )
2013-11-15 11:59:04 +04:00
if [ -n " $out " ] ; then
# Log information about locks
echo " $out "
# Find processes that are waiting for locks
dbs = $( echo " $out " | grep " W $" | awk '{print $3}' )
all_pids = ""
for db in $dbs ; do
pids = $( echo " $out " | grep -v " W $" | grep " $db " | grep -v ctdbd | awk '{print $1}' )
all_pids = " $all_pids $pids "
done
2013-11-26 08:41:50 +04:00
pids = $( echo $all_pids | tr " " "\n" | sort -u)
2013-11-15 11:59:04 +04:00
# For each process waiting, log stack trace
for pid in $pids ; do
echo " ----- Stack trace for PID= $pid ----- "
gstack $pid
# gcore -o /var/log/core-deadlock-ctdb $pid
done
fi
echo " ===== End of debug locks PID= $$ ===== "
) 9>" ${ CTDB_VARDIR } /debug_locks.lock " | script_log "ctdbd-lock"
2013-07-08 09:56:30 +04:00
exit 0