#!/bin/bash
#
# Bind a linux host to kerberos
#
# $Id: $
#
#

# Location of the kerberos commands
kadmin=${KADMIN:-/usr/sbin/kadmin}
kinit=${KINIT:-/usr/bin/kinit}
kdestroy=${KDESTROY:-/usr/bin/kdestroy}
if [[ ! -x $kadmin ]]; then
    echo "$kadmin is not executable. Check the path or set the KADMIN variable"
fi
if [[ ! -x $kinit ]]; then
    echo "$kinit is not executable. Check the path or set the KINIT variable"
fi
if [[ ! -x $kdestroy ]]; then
    echo "$kdestroy is not executable. Check the path or set the KDESTROY variable"
fi

# Export the credentials cache location for all the krb5 commands
krb5ccname="/tmp/kerberos_bind_cc_$$" 

# Print usage information
usage () 
{
    scriptname=`basename $0`
    cat << EOF
Usage: $scriptname -u <admin username> [-h <hostname>] [-k <keytab>]

OPTIONS:
 -u username of the kerberos administrator
 -h hostname to generate a keytab for
 -k location of the keytab file

If -h is specified, then -k *must* be specified as well.
EOF
}

# Error condition convenience function
die () 
{
	echo "$@ failed: error code $?"
	exit 1
}

# kadmin convenience function
kadmin_command () 
{
    $kadmin -c $krb5ccname -q "$@" > /dev/null || die $@
}

# Read command line options
while getopts "h:k:u:" option
do
    case $option in
        h)
        hostname=$OPTARG
        ;;
        k)
        keytab=$OPTARG
        ;;
        u)
        username=$OPTARG
        ;;
        ?)
        usage
        exit
        ;;
    esac
done

# Check to make sure the username was specified
if [[ -z $username ]]; then
    echo "Error: no username specified"
    usage
    exit 1
fi

# Set the hostname and keytab variables if they were not specified on the command line.
# If a hostname was specified, then ensure the keytab was as well.
# If only a keytab was specified, we don't really care.
if [[ -z $hostname ]]; then
    hostname=`hostname -f`
    keytab=/etc/krb5.keytab
elif [[ -z $keytab ]]; then
    echo "Error: You must specify -k if you specify -h"
    usage
    exit 1
fi

# Destroy our credentials no matter what happens
trap "echo 'Destroying temporary kerberos credentials in $krb5ccname...'; $kdestroy; echo 'done'; exit 1" 1 2 3 5 15

# Create the credentials cache
echo ">> Creating temporary kerberos credentials cache, $krb5ccname..."
$kinit -S kadmin/admin -c $krb5ccname $username

# Create principals
echo ">> Creating principals..."
echo ">> Creating host/ principal..."
kadmin_command "addprinc -randkey host/$hostname"
echo ">> Creating nfs/ principal..."
kadmin_command "addprinc -randkey nfs/$hostname"
echo ">> Creating root/ principal..."
kadmin_command "addprinc -randkey root/$hostname"

# Add them to our keytab
echo ">> Updating keytab..."
echo ">> Getting host/ principal..."
kadmin_command "ktadd -k $keytab  host/$hostname"
echo ">> Getting nfs/ principal..."
kadmin_command "ktadd -k $keytab  root/$hostname"
echo ">> Getting root/ principal..."
kadmin_command "ktadd -k $keytab  -e des-cbc-crc:normal nfs/$hostname"

# Clean up
echo ">> Destroying temporary kerberos credentials in $krb5ccname..."
$kdestroy -c $krb5ccname

echo ">> Script completed successfully"
exit 0

# POD documentation

=head1 NAME

B<kerberos_bind> - binds a linux host to the Kerberos KDC

=head1 SYNOPSIS

B<kerberos_bind> admin_user_name

=head1 DESCRIPTION

B<kerberos_bind> creates the necessary principals to bind a Linux host to the KDC. It requires Kerberos to be configured in /etc/krb5.conf.
