List the Open Files of a Hung Process with lsof on Linux
List what a hung process has open with lsof -p PID, or read /proc/PID/fd. The descriptors show the input file, the output file and where standard error goes.
A process hangs or leaks descriptors and you want to see every file, socket and pipe it holds.
echo data > in.txt
sleep 30 < in.txt > out.txt &
pid=$!
sleep 0.5
lsof -p "$pid" -a -d 0-9
for f in /proc/$pid/fd/*; do echo "fd ${f##*/} -> $(readlink "$f")"; done
kill $pidCOMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
sleep 2740 root 0r REG 0,185 5 3027775 /tmp/run/S1888-1/w/in.txt
sleep 2740 root 1w REG 0,185 0 3027776 /tmp/run/S1888-1/w/out.txt
sleep 2740 root 2w FIFO 0,16 0t0 14100374 pipe
fd 0 -> /tmp/run/S1888-1/w/in.txt
fd 1 -> /tmp/run/S1888-1/w/out.txt
fd 2 -> pipe:[14100374]lsof -p PID prints one line per open file with its descriptor, and -a -d 0-9 combined the PID with a descriptor range so that only the low numbers show. The run shows 0r reading in.txt, 1w writing out.txt and descriptor 2 on a pipe. The same facts come from /proc/PID/fd, where each entry is a link to the target, which the loop prints with readlink; the pipe is named by its inode. See proc_pid_fd.
lsof can take a long time on a busy system, and without root it shows only your own processes. -a makes the options AND together, and without it they OR, which gives much more output than expected. A deleted file shows (deleted) after its name while some process still holds it open.