#!/bin/bash

# Copyright 2007 Ronny Aasen <ronny@skolelinux.no>
# Distributed under the terms of the GNU General Public License
# version 2 or any later version.

# compare the files in the swapdir, vs the running processes, vs the
# alive ltsp clients.  and remove the cruft UGLY UGLY remove all this
# when nbd-server is sane.

#set -x 

PATH=/bin:/usr/bin
export PATH

# exit if its already running
# (this shouldnt happen - but will happen if lsof hangs)
if ps fax | egrep -v "grep|^ *$$" | grep -q $0 ; then
    exit 0
fi

#known language
LANG=C
export $LANG

NBDQUERY_PORT=9211
export NBDQUERY_PORT

#only run if the services are installed.
test -x /usr/sbin/nbdswapd || exit 0
test -x /bin/nbd-server || exit 0

#only run if there is a SWAPDIR configured. 
test ! -r /etc/ltsp/nbdswapd.conf || . /etc/ltsp/nbdswapd.conf
if [ ${SWAPDIR:-0} = "0" ] ; then 
        exit 0
fi


#remove files not owned by any process, eg after a powerfailure. 
for file in $SWAPDIR/??????  ; do
   if [ -f $file ] ; then
       ps aux | grep -v grep | grep nbd-server | grep -q $file || rm $file
   fi
done

# Query the ltsp client on port 9211 to get a list of ports in use by
# nbd-clients.  stop nbd-server processes with no clients running,
# they can safely be removed.

pids=$(ps ax -o pid,args | grep -v grep | grep ' /usr/sbin/nbdswapd' | awk '{print $1}' )
for pid in $pids ; do
	# in case there are no nbdswapds running
	if [ ${pid:-0} -ne "0" ]; then
		#get the ports in use by nbdswapd
		for l_port in $(lsof -w  -P -p $pid | grep 9572 | grep TCP | head -n 1 | cut -d":" -f3 | cut -d" " -f1) ; do
			#figure out the ltps client hostname 
			host=$(lsof -w -P -p $pid | grep 9572 | grep TCP | head -n 1 | cut -d":" -f2 | cut -d">" -f2)
			
			#query the ltsp host for the nbd-client ports in use 
		 	r_port=$(nc $host $NBDQUERY_PORT 2>/dev/null || echo fail )
			#if host was unreachable (power off/network failure)
			if [ ${r_port} = "fail" ] ; then
				#kill all nbd's for this host
				for nbds_pid in $(ps ax --no-heading -o pid,ppid,args| grep $pid | grep -v grep | grep nbd-server | awk '{print $1}'); do
					#kill this nbd-server
					#it will take it's file and go. 
					kill -1 $nbds_pid
				done

			else   
				#if we got a reply
				if [ ${r_port:-0} -ne "0" ]; then
					#keep if it matches
					if [ "$l_port" -ne  "$r_port" ]; then 
						#what nbd-server is child of this nbdswapd
						for nbds_pid in $(ps ax --no-heading -o pid,ppid,args| grep $pid | grep -v grep | grep nbd-server | awk '{print $1}'); do
						#kill this nbd-server
						#it will take it's file and go. 
							kill -1 $nbds_pid
						done
					fi
				fi
			fi
		done
	fi
done

exit 0 

