#!/bin/ksh
# IBM_PROLOG_BEGIN_TAG 
# This is an automatically generated prolog. 
#  
#  
#  
# Licensed Materials - Property of IBM 
#  
# (C) COPYRIGHT International Business Machines Corp. 2004,2007 
# All Rights Reserved 
#  
# US Government Users Restricted Rights - Use, duplication or 
# disclosure restricted by GSA ADP Schedule Contract with IBM Corp. 
#  
# IBM_PROLOG_END_TAG 
# @(#)51   1.18   src/rsct/sr/Tools/sr_diag.sh, registry, rsct_relgh, relghs001a 1/10/06 09:18:49

bindir=/usr/sbin/rsct/bin
ctdir=/var/ct
logfile=/tmp/sr_diag_log.$$
logging=off
pager=
logcontrol="$pager_control"
daemon_executable=""

uname=`uname`

if [ "$uname" = "Linux" ]
then
	debugger=gdb
	debugger_attach_flag="--pid="
else
	debugger=dbx
	debugger_attach_flag="-a "
fi

function dump_table
{
	table_path=/`echo $2 | sed 's/,/\//g'`
	echo "Dumping table $table_path in $ctdir/$1/registry/local_tree"
	$bindir/sr_dump_table $ctdir/$1/registry/local_tree $table_path
}

function dump_table_raw
{
	echo "Dumping table file $2 in $ctdir/$1/registry/local_tree"
	$bindir/sr_dump_table_raw $ctdir/$1/registry/local_tree/$2
}

function list_file_descriptors
{
	$bindir/sr_lsfds $ctdir/$1/registry/local_tree/$2
}

function corruption_test
{
	table_path=/`echo $2 | sed 's/,/\//g'`
	corruption_test=`$bindir/sr_dump_table $ctdir/$1/registry/local_tree $table_path CORRUPTION_TEST`
	if [ "$corruption_test" = "TABLE IS CORRUPT" ]
	then
		log "CORRUPT TABLE: name\($table_path\) file\($2\) registry\($ctdir/$1/registry/local_tree\)"
	fi
}

function log
{
	eval echo "===== \[`date`\] $*" $logcontrol
}

function setup_log_control
{
	case $pager in
		more)
			pager_control=" | more"
			;;
		less)
			pager_control=" | less"
			;;
		*)
			pager=
			pager_control=""
			;;
	esac

	case $logging in
		off)
			logcontrol="$pager_control"
			;;
		on)
			logcontrol=" | tee -a $logfile $pager_control"
			;;
	esac
}

function display_options
{
	echo ""
	echo "logfile($logfile) logging($logging) pager($pager)"
}

function select_options
{
	PS3="Select options: "

	display_options
	echo ""

	select options in quit display_options set_logfile set_logging set_pager
	do	case $options in
		quit)
			echo ""
			exit 0
			;;
		display_options)
			display_options
			echo ""
			;;
		set_logfile)
			temp=$logfile
			read logfile?"Logfile name ($logfile) : "
			if [ -z "$logfile" ]
			then	logfile=$temp
			fi
			if [ -f "$logfile" ]
			then
				read answer?"$logfile already exists.  Reset?(y/n): "
				if [ "$answer" = "y" ]
				then
					rm -f $logfile
				fi
			fi
			display_options
			echo ""
			;;
		set_logging)
			temp=$logging
			read logging?"Logging on/off ($logging) : "
			if [ -z "$logging" ]
			then	logging=$temp
			fi
			display_options
			echo ""
			;;
		set_pager)
			temp=$pager
			read pager?"Pager more/less/<other=none> ($pager) : "
			display_options
			echo ""
			;;
		esac

		setup_log_control

		PS3="Select options: "
	done

	echo ""
}

function set_daemon_executable
{
	case $1 in
		IBM.AuditRM)
			daemon_executable=IBM.AuditRMd
			;;
		IBM.CIMRM)
			daemon_executable=IBM.CIMRMd
			;;
		IBM.ConfigRM)
			daemon_executable=IBM.ConfigRMd
			;;
		IBM.CSMAgentRM)
			daemon_executable=IBM.CSMAgentRMd
			;;
		IBM.DRM)
			daemon_executable=IBM.DRMd
			;;
		IBM.ERRM)
			daemon_executable=IBM.ERrmd
			;;
		IBM.FSRM)
			daemon_executable=IBM.FSrmd
			;;
		IBM.FVT)
			daemon_executable=IBM.FVTd
			;;
		IBM.GFVTRM)
			daemon_executable=IBM.GFVTRMd
			;;
		IBM.HostRM)
			daemon_executable=IBM.HostRMd
			;;
		IBM.LANRM)
			daemon_executable=IBM.LANRMd
			;;
		IBM.LPRM)
			daemon_executable=IBM.LPRMd
			;;
		IBM.Sample)
			daemon_executable=IBM.Sampled
			;;
		IBM.SensorRM)
			daemon_executable=IBM.SensorRMd
			;;
		IBM.ServiceRM)
			daemon_executable=IBM.ServiceRMd
			;;
		IBM.StorageRM)
			daemon_executable=IBM.StorageRMd
			;;
		IBM.WLMRM)
			daemon_executable=IBM.WLMRMd
			;;
		*)
			read daemon_executable?"Subsystem executable name (e.g. IBM.ERrmd): "
			;;
	esac
}

function select_table_function
{
	cluster_domain=$1
	table=$2

	if [ "$table" = "ALL" ]
	then
		table_path="ALL TABLES"
	else
		table_path=/`echo $table | sed 's/,/\//g'`
	fi

	set dump dump_raw list_fds corruption_test
	PS3="Select table function for $table_path : "

	select table_function
	do	case $table_function in
		dump)
			real_table_function=dump_table
			;;
		dump_raw)
			real_table_function=dump_table_raw
			;;
		list_fds)
			real_table_function=list_file_descriptors
			;;
		corruption_test)
			real_table_function=corruption_test
			;;
		esac

		if [ "$table" = "ALL" ]
		then
			log "$real_table_function against all tables in $cluster_domain:"
			ls $ctdir/$cluster_domain/registry/local_tree | grep -v '\.rewrite$' | grep -v ',Lock' | while read filename
			do
				eval $real_table_function $cluster_domain $filename $logcontrol
			done
		else
			log "$real_table_function against $table in $cluster_domain:"
			eval $real_table_function $cluster_domain $table $logcontrol
		fi

		echo ""
	done
}

function select_table
{
	cluster_domain=$1
	set `ls $ctdir/$cluster_domain/registry/local_tree | grep -v '\.rewrite$' | grep -v ',Lock'` all
	PS3="Select table: "

	select table
	do	case $table in
		all)
				select_table_function $cluster_domain ALL
				echo ""
			;;
		*)
			if [ -z "$table" ]
			then
				echo "Invalid selection!"
				continue
			else
				select_table_function $cluster_domain $table
				echo ""
			fi
			;;
		esac

		PS3="Select table: "
	done
}

function select_core_files
{
	cluster_domain=$1
	subsystem=$2
	set "`ls $ctdir/$cluster_domain/run/mc/$subsystem`"

	if [ -z "$1" ]
	then
		echo ""
		echo "No core files for subsystem $subsystem!"
		return
	fi

	set $1

	PS3="Select core file: "

	select core_file
	do	case $core_file in
		*)
			if [ -z "$core_file" ]
			then
				echo "Invalid selection!"
				continue
			else
				eval $debugger /usr/sbin/rsct/bin/$daemon_executable $ctdir/$cluster_domain/run/mc/$subsystem/$core_file
				echo ""
			fi
			;;
		esac

		PS3="Select core file: "
	done
}

function select_core_subsystem
{
	cluster_domain=$1
	set "`ls $ctdir/$cluster_domain/run/mc`"

	if [ -z "$1" ]
	then
		echo ""
		echo "No subsystems for cluster domain $cluster_domain!"
		return
	fi

	set $1

	PS3="Select subsystem: "

	select subsystem
	do	case $subsystem in
		*)
			if [ -z "$subsystem" ]
			then
				echo "Invalid selection!"
				continue
			else
				set_daemon_executable $subsystem

				if [ -z "$daemon_executable"  ]
				then
					echo "Cannot execute debugger without subsystem executable name!"
					return 1
				fi

				select_core_files $cluster_domain $subsystem
				echo ""
			fi
			;;
		esac

		PS3="Select subsystem: "
	done
}

function select_trace_file_operations
{
	cluster_domain=$1
	subsystem=$2
	trace_file=$3
	set full registry_only
	PS3="Select trace file operation: "

	select operation
	do	case $operation in
		full)
			log "Full trace file\($ctdir/$cluster_domain/log/mc/$subsystem/$trace_file\)"
			eval "$bindir/rpttr $ctdir/$cluster_domain/log/mc/$subsystem/$trace_file" $logcontrol
			;;
		registry_only)
			log "SR trace file\($ctdir/$cluster_domain/log/mc/$subsystem/$trace_file\)"
			eval "$bindir/rpttr $ctdir/$cluster_domain/log/mc/$subsystem/$trace_file | $bindir/sr_filter_trace" $logcontrol
			;;
		esac

		PS3="Select trace file operation: "
	done
}

function select_trace_files
{
	cluster_domain=$1
	subsystem=$2
	set "`ls $ctdir/$cluster_domain/log/mc/$subsystem`"

	if [ -z "$1" ]
	then
		echo ""
		echo "No trace files for subsystem $subsystem!"
		return
	fi

	set $1

	PS3="Select trace file: "

	select trace_file
	do	case $trace_file in
		*)
			if [ -z "$trace_file" ]
			then
				echo "Invalid selection!"
				continue
			else
				select_trace_file_operations $cluster_domain $subsystem $trace_file
				echo ""
			fi
			;;
		esac

		PS3="Select trace file: "
	done
}

function select_trace_subsystem
{
	cluster_domain=$1
	set "`ls $ctdir/$cluster_domain/log/mc | grep -v default | grep -v trace`"

	if [ -z "$1" ]
	then
		echo ""
		echo "No subsystems for cluster domain $cluster_domain!"
		return
	fi

	set $1

	PS3="Select subsystem: "

	select subsystem
	do	case $subsystem in
		trace)
			select_trace_file_operations $cluster_domain ../mc trace
			echo ""
			;;
		*)
			if [ -z "$subsystem" ]
			then
				echo "Invalid selection!"
				continue
			else
				select_trace_files $cluster_domain $subsystem
				echo ""
			fi
			;;
		esac

		PS3="Select subsystem: "
	done
}

function select_cluster_domain_object
{
	cluster_domain=$1

	set tables trace core global_trace tree_lock_file_descriptors
	PS3="Select object: "

	select object
	do	case $object in
		tables)
			select_table $cluster_domain
			echo ""
			;;
		trace)
			select_trace_subsystem $cluster_domain
			echo ""
			;;
		core)
			select_core_subsystem $cluster_domain
			echo ""
			;;
		global_trace)
			if [ -f "/$ctdir/$cluster_domain/log/mc/trace" ]
			then
				log "Full trace file\($ctdir/$cluster_domain/log/mc/trace\)"
				eval "$bindir/rpttr $ctdir/$cluster_domain/log/mc/trace" $logcontrol
				eval echo "" $logcontrol
			else
				echo "Global trace file does not exist!"
				echo ""
			fi
			;;
		tree_lock_file_descriptors)
			log "File descriptors for the registry tree lock file \($ctdir/$cluster_domain/registry/local_tree/,Lock\):"
			eval $bindir/sr_lsfds $ctdir/$cluster_domain/registry/local_tree/,Lock $logcontrol
			eval echo "" $logcontrol
			;;
		esac

		PS3="Select object: "
	done
}

function select_cluster_domain
{
	set "`/usr/sbin/rsct/bin/lsclcfg -ax -D' ' | awk '{ print $1; }'`"

	if [ -z "$1" ]
	then
		echo ""
		echo "No cluster domains to select!"
		return
	fi

	set $1

	PS3="Select cluster domain: "

	select cluster_domain
	do	case $cluster_domain in
		*)
			if [ -z "$cluster_domain" ]
			then
				echo "Invalid selection!"
				continue
			else
				select_cluster_domain_object $cluster_domain
				echo ""
			fi
			;;
		esac

		PS3="Select cluster domain: "
	done
}

function select_subsystem_query
{
	subsystem=$1
	set daemon_long_status file_descriptors attach_debugger
	PS3="Select subsystem query: "

	select subsystem_query
	do	case $subsystem_query in
		daemon_long_status)
			log "Long status for subsystem $subsystem:"
			eval lssrc -ls $subsystem $logcontrol
			echo ""
			;;
		file_descriptors)
			pid=`lssrc -s $subsystem | grep $subsystem | awk '{ print $3; }'`

			log "File descriptors for subsystem $subsystem:"

			if [ "$pid" != "inoperative" ]
			then
				eval "$bindir/sr_lsfds | grep $pid" $logcontrol
			else
				echo "Subsystem $subsystem is inoperative!"
			fi
			echo ""
			;;
		attach_debugger)
			pid=`lssrc -s $subsystem | grep $subsystem | awk '{ print $3; }'`

			if [ "$pid" != "inoperative" ]
			then
				set_daemon_executable $subsystem
				eval $debugger $debugger_attach_flag$pid /usr/sbin/rsct/bin/$daemon_executable
			else
				echo "Subsystem $subsystem is inoperative!"
			fi
			echo ""
			;;
		esac

		PS3="Select subsystem query: "
	done
}


function select_subsystem
{
	set "`lssrc -a | grep rsct | awk '{ print $1; }'`"

	if [ -z "$1" ]
	then
		echo ""
		echo "No subsystems to select!"
		return
	fi

	set $1

	PS3="Select subsystem: "

	select subsystem
	do	case $subsystem in
		*)
			if [ -z "$subsystem" ]
			then
				echo "Invalid selection!"
				continue
			else
				select_subsystem_query $subsystem
				echo ""
			fi
			;;
		esac

		PS3="Select subsystem: "
	done
}

function select_top
{
	set select_options cluster_domains subsystems list_all_table_file_descriptors
	PS3="Select object: "

	select top_object
	do	case $top_object in
		select_options)
			select_options
			echo ""
			;;
		cluster_domains)
			select_cluster_domain
			echo ""
			;;
		subsystems)
			select_subsystem
			echo ""
			;;
		list_all_table_file_descriptors)
			log "Listing all table file descriptors:"
			eval $bindir/sr_lstfs $logcontrol
			eval echo "" $logcontrol
			;;
		esac

		PS3="Select object: "
	done
}

#function cleanup
#{
#	rm -f core 1>/dev/null 2>/dev/null
#}

trap select_options INT

#trap cleanup QUIT TERM EXIT

while getopts :lf:p: options
do	case $options in
		l)
			logging=on
			;;
		f)
			logfile=$OPTARG
			;;
		p)
			pager=$OPTARG
			;;
		:)
			echo "$0: -$OPTARG requires a value"
			echo "Usage: $0 [-f logfile] [-p more|less] [-l]"
			exit 1
			;;
		\?)
			echo "$0: Unknown option($OPTARG)"
			echo "Usage: $0 [-f logfile] [-p more|less] [-l]"
			exit 1
			;;
	esac
done
shift OPTIND-1

setup_log_control

if [ -f "$logfile" ]
then
	read answer?"$logfile already exists.  Reset?(y/n): "
	if [ "$answer" = "y" ]
	then
		rm -f $logfile
	fi
fi

echo "sr_diag:"
display_options
echo ""

select_top

echo ""

exit 0
