#!/bin/sh

### BEGIN INIT INFO
# Provides:          lustre_mnt
# Required-Start:    $network openibd
# Required-Stop:     $network openibd sendsigs umountnfs.sh
# Should-Start:      $network 
# Should-Stop:       $network
# Default-Start:     3 4 5
# Default-Stop:      0 1 6
# X-Start-Before:    ypbind pbs_mom
# X-Stop-After:      pbs_mom
# Short-Description: Mounting lustre filesystem.
### END INIT INFO

#--------------------------------------------------------------------------
#	Determine network interface: Infiniband / eth0.
#
grep -v '#' /etc/modprobe.d/lustre.conf | grep o2ib > /dev/null
if [ $? = 0 ]; then
    iface='ib0'
else
    iface='eth0'
fi
if [ -x /opt/ib/bin/ibv_devinfo ]; then
    ibv=/opt/ib/bin/ibv_devinfo
else
    ibv=/usr/bin/ibv_devinfo
fi

#--------------------------------------------------------------------------
#	Parse /opt/lustre/etc/cfs-*
#
myhost=`hostname | cut -d . -f 1`
fslist=`/bin/ls /opt/lustre/etc/cfs-* 2> /dev/null`
if [ -z "$fslist" ]; then
    echo "!!! Lustre: file not found: /opt/lustre/etc/cfs-*"
    exit 1
fi
if [ "$iface" = 'ib0' ]; then
    fserver=`grep "^FSIB:" $fslist`
else
    fserver=`grep "^FSETH:" $fslist`
fi
fs0=`echo "$fserver" | head -1`
fsys=`grep "^$myhost," $fslist`
if [ -z "$fsys" ]; then
    echo "!!! Lustre: no mount info."
    exit 1
else
    fs0_name=`echo $fs0 | cut -d : -f 2`
    fs0_addr=`echo $fs0 | cut -d : -f 3`
    fsys0=
    for fs in $fsys; do
	fs0_info=`echo "$fs" | cut -d , -f 2 | sed "s/$fs0_name/$fs0_addr/"`
	fs0_lmnt=`echo "$fs" | cut -d , -f 3`
	fsys0="$fsys0 $fs0_info:$fs0_lmnt"
    done
    fsys="$fsys0"
fi

#--------------------------------------------------------------------------
#	Start / Stop service.
#
case "$1" in
start)
    if [ $iface = 'ib0' ]; then
	echo "Lustre: Checking Infiniband port status ...."
	while [ 1 ]; do
	    $ibv | grep state: | head -1 | grep PORT_ACTIVE > /dev/null
	    [ $? = 0 ] && break
	    sleep 15
	done
    fi
    for fs in `echo "$fserver" | cut -d : -f 3`; do
	err=1
	echo "Lustre: Checking file servers status: $fs ...."
	for i in 1 2 3 4 5; do
	    ping -c 1 $fs > /dev/null
	    [ "$?" = 0 ] && err=0 && break
	    echo "Lustre: ping to file server: $fs ...."
	    sleep 5
	done
	[ "$err" != 0 ] && echo "Lustre: $fs: unavailable." && exit 0
    done
    if [ -x /opt/lustre/sbin/lnetctl ]; then
	/sbin/modprobe lnet
	sleep 2
	/opt/lustre/sbin/lnetctl set discovery 0
    fi

    mnt=`mount | grep lustre | awk '{print $1}'`
    for fs in $fsys; do
	hs=`echo $fs | cut -d : -f 1`
	ds=`echo $fs | cut -d : -f 2`
	ms=`echo $fs | cut -d : -f 3`
	echo "$mnt" | grep "$hs:$ds" > /dev/null
	[ $? = 0 ] && continue

	echo -n "Lustre: mount -t lustre -o flock $hs:$ds $ms .... "
	mount -t lustre -o flock $hs:$ds $ms
	if [ "$?" = 0 ]; then
	    echo "ok."
	else
	    echo "failed."
	fi
    done
    sleep 3
#    /opt/lustre/sbin/lctl set_param osc.*.grant_shrink=0
    ;;

stop)
    for fs in `mount | grep lustre | awk '{print $3}'`; do
	echo "Lustre: Terminate processes using $fs ...."
	pss=`lsof $fs | awk '{if(NR > 1) print $2}' | sort -u`
	if [ ! -z "$pss" ]; then
	    kill $pss
	    sleep 3
	fi
	pss=`lsof $fs | awk '{if(NR > 1) print $2}' | sort -u`
	if [ ! -z "$pss" ]; then
	    kill $pss
	    sleep 2
	fi
	echo "Lustre: Unmount $fs ...."
	umount $fs
    done
    sleep 2
    echo "Lustre: Unloading Lustre modules ...."
    /opt/lustre/sbin/lustre_rmmod
    sleep 2
    ;;
*)
    echo "Usage: $0 [start/stop]"
    ;;
esac
