#!/bin/sh
#
# This script runs every day, trying to crack passwords, and then calls
# mailer to warn the users (and maybe also root) about that.

# One of two options should be passed to this script:
# start -- start running john
# stop -- stops running john

# The time when the script is called can be configured in /etc/cron.d/john

# You can pass options to john in /etc/cron.d/john. See john(1) for the possible
# options, and include them after "JOHN_OPTIONS=" below.

JOHNDIR=/usr/sbin
PASSWD=/etc/passwd
SHADOW=/etc/shadow
RUNDIR=/var/lib/john

# Gets the PID of the currently running "john" processes, checks which
# one we want, and sends SIGHUP to it.
#
john_stop()
{

PID=`pidof john`
for p in $PID; do
	PROCPATH=$(readlink /proc/$PID/exe)
	RELEVANTPATH=`echo $PROCPATH | sed -e"s^$JOHNDIR/john.*^$JOHNDIR/john^"`
	if [ "$RELEVANTPATH" = $JOHNDIR/john ]; then
		kill -2 $PID
	fi
done

}

# Starts john 
#
john_start()
{

PASSFILE=`grep -e "[ ]*passfile[ ]*=[ ]*" /etc/john-mail.conf |
          sed -e "s/#.*//" -e "s/.*=[ ]*//"`

if [ -z $PASSFILE ]; then
	mail -s "John cronjob is not configured yet!" root <<EOF
John was set up to run every day, but it needs you to specify a
temporary file, with a "passfile=" line in /etc/john-mail.conf.

Thank you,

John the Ripper, an automated password cracking tool.
EOF
	 exit 0
fi



# $TMPFILE is the file with the temporary passwords unshadowed. It
# will be passed to john if this is not a restore session. $PASSFILE is
# the same. The difference is that we may set $TMPFILE to "" in the case
# of a restore session, but $PASSFILE is kept so we can use the mailer
# later.

RESTOREFILE=""
if [ -f $RUNDIR/restore ]; then
	RESTOREFILE=`grep $PASSFILE $RUNDIR/restore`
	RESTORE_OPTION="-restore"
fi

# if RESTOREFILE is empty or does not exist, then there is 
# really nothing to restore
if [ -z "$RESTOREFILE" -o ! -f "$RESTOREFILE" ] ; then
	RESTORE_OPTION=""
	RESTOREFILE=""
	[ -f $RUNDIR/restore ] && rm -f $RUNDIR/restore
	TMPFILE=`mktemp $PASSFILE.XXXXXX` || exit 1
	chmod og-rwx $TMPFILE
	if [ -f $SHADOW ]; then
		$JOHNDIR/unshadow $PASSWD $SHADOW >> $TMPFILE
	else
		cat $PASSWD >> $TMPFILE
	fi
fi

# We capture the output of john, and check if there was a line with
# "guesses: 0" in it. If not, then either john exited abnormally, or
# passwords were guessed -- and in both cases we send all the output
# to stdout.
#
if [ ! -f /var/lock/john ]; then
	touch /var/lock/john

	cd $RUNDIR && $JOHNDIR/john $RESTORE_OPTION $JOHN_OPTIONS $TMPFILE &> /dev/null
	rm -f /var/lock/john
	if [ -z "$RESTOREFILE" ] ; then
		OUTPUT=`$JOHNDIR/mailer $TMPFILE 2>&1`
	else
		OUTPUT=`$JOHNDIR/mailer $RESTOREFILE 2>&1`
	fi
	if [ -z "$OUTPUT" ]; then
		rm -f $TMPFILE
	else
		echo $OUTPUT
	fi
else
	mail -s "John is running" root <<EOF
John is running at $HOSTNAME -- either the cronjob lasted too long,
or someone else is running john.
EOF
fi

}

if [ $# -ne 1 ]; then
	echo "$0 {start|stop} "
	exit 1;
else
	case "$1" in
		start)
			john_start
			;;
		stop)
			john_stop
			;;
		*)
			exit 1;
			;;
	esac
fi
