#!/bin/sh
#
#  Copyright (c) 2005 Canonical LTD
#
#  Author: Matt Zimmerman <mdz@canonical.com>
#
#  2006, Oliver Grawert <ogra@canonical.com>
#        Vagrant Cascadian <vagrant@freegeek.org>
#  2007, Scott Balneaves <sbalneav@ltsp.org>
#        Oliver Grawert <ogra@canonical.com>
#  2008, Vagrant Cascadian <vagrant@freegeek.org>
#        Warren Togami <wtogami@redhat.com>
#        Oliver Grawert <ogra@canonical.com>
#  2009, Warren Togami <wtogami@redhat.com>
#
#  This program is free software; you can redistribute it and/or
#  modify it under the terms of the GNU General Public License as
#  published by the Free Software Foundation; either version 2 of the
#  License, or (at your option) any later version.
#
#  This program is distributed in the hope that it will be useful,
#  but WITHOUT ANY WARRANTY; without even the implied warranty of
#  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
#  GNU General Public License for more details.
#
#  You should have received a copy of the GNU General Public License
#  along with this program.  If not, you can find it on the World Wide
#  Web at http://www.gnu.org/copyleft/gpl.html, or write to the Free
#  Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston,
#  MA 02110-1301, USA.
#

set -e

usage() {
cat <<EOF
$0 [OPTION]
  -b, --basedir     Base of ltsp chroot.  Default is /opt/ltsp if unspecified.
  -t, --tftpdirs    List of tftpd dirs to update in. Defaults to
                    "/var/lib/tftpboot /tftpboot".
  -c, --copytftp    Copy files.  Defaults to "true".
  -d, --tftpbootdir Subdir within tftpdir where ltsp kernels are.  Defaults
                    to "ltsp".
  -h, --help        This message.
EOF
}

#
# Handle args
#

ARGS=$(getopt -o b:t:c:d:h --long base:,tftpdirs:,copytftp:,tftpbootdir:,help \
       -n $0 -- "$@")

[ $? != 0 ] && exit 1

eval set -- "${ARGS}"

while true ; do
    case "$1" in
        -b|--base)        BASE=$2 ; shift 2 ;;
        -t|--tftpdirs)    TFTPDIRS=$2 ; shift 2 ;;
        -c|--copytftp)    COPYTFTP=$2 ; shift 2 ;;
        -d|--tftpbootdir) TFTPBOOTDIR=$2 ; shift 2 ;;
        -h|--help)        usage ; exit 0 ;;
        --) shift ; break ;;
        *) echo "Internal error!" ; exit 1 ;;
    esac
done

if [ -f /etc/ltsp/ltsp-update-kernels.conf ]; then
    . /etc/ltsp/ltsp-update-kernels.conf
fi

BASE=${BASE:-"/opt/ltsp"}
TFTPDIRS=${TFTPDIRS:-"/var/lib/tftpboot /tftpboot"}
COPYTFTP=${COPYTFTP:-"true"}
TFTPBOOTDIR=${TFTPBOOTDIR:-"ltsp"}

for TFTPDIR in $TFTPDIRS ; do
    if [ ! -d $TFTPDIR ] ; then
        # skip directory
        continue
    fi

    TFTPBOOT="$TFTPDIR/$TFTPBOOTDIR"

    if [ "$TFTPDIR" = "$BASE" ]; then
        COPYTFTP="false"
        TFTPBOOT="$TFTPDIR"
    fi

    ALL_CHROOTS="$@"
    ALL_CHROOTS=${ALL_CHROOTS:-"$(find $BASE/ -mindepth 1 -maxdepth 1 -type d | \
                                  grep -v images)"}

    for CHROOT in $ALL_CHROOTS ; do
        if [ -x $CHROOT/bin/true ]; then
            echo "Updating $TFTPDIR directories for chroot: $CHROOT"
            export CHROOT_NAME="$(basename $CHROOT)"

            if [ "$COPYTFTP" = "true" ]; then
                mkdir -p $TFTPBOOT/$CHROOT_NAME
                cp -a $CHROOT/boot/. $TFTPBOOT/$CHROOT_NAME/
            fi

            # OFW on Mac is lame, they cannot tftp from directories
            if [ -e $TFTPBOOT/$CHROOT_NAME/yaboot ]; then
                ln -sf ltsp/$CHROOT_NAME/yaboot $TFTPDIR/yaboot
                ln -sf ltsp/$CHROOT_NAME/yaboot.conf $TFTPDIR/yaboot.conf
            fi
        else
            # not a valid chroot
            echo "Skipping invalid chroot: $CHROOT"
        fi
    done
    # Update selinux file contexts if necessary
    [ -f /selinux/enforce ] && /sbin/restorecon -R $TFTPDIR > /dev/null

    ### Cleanup old kernels and images from tftpboot directory ###
    # Find $version from vmlinuz-* filename
    # if corresponding /opt/ltsp/$arch/lib/modules/$version is missing
    # then delete kernel and images from tftpboot directory
    #
    # Some distros wont match vmlinuz-*, but this is at least safe
    # because it will simply cleanup nothing.
    removefiles() {
        # Common
        rm -f $archpath/vmlinuz-$version
        rm -f $archpath/config-$version
        rm -f $archpath/System.map-$version
        # Fedora
        rm -f $archpath/initrd-$version.img
        rm -f $archpath/elf-$version.img
        rm -f $archpath/wraplinux-nbi-$version.img
        rm -f $archpath/aout-$version.img
        # Debian
        rm -f $archpath/initrd.img-$version
        rm -f $archpath/nbi.img-$version
    }
    # Loop through every arch
    for archpath in $(find $TFTPDIR/$TFTPBOOTDIR -mindepth 1 -maxdepth 1 -type d); do
        arch=`basename $archpath`
        # Loop through every vmlinuz-* file
        for kernelpath in $(find $TFTPDIR/$TFTPBOOTDIR/$arch -name 'vmlinuz-*'); do
            kernel=`basename $kernelpath`
            version=${kernel##vmlinuz-}
            if [ ! -d /opt/ltsp/$arch/lib/modules/$version ]; then
                echo "Removing $kernelpath"
                removefiles
            fi
        done
    done
done
exit 0
