#!/bin/bash
############################################################
# autoinst.sh	Linux Automation OS installer
# 9/11/09	install OS files for booting into for Automation mode, this
#		installer will be embedded within an archive attached to the
#		extractor (apkgsfx.sh), determine destination for OS files,
#		create  menu.lst file entry, setup config file for autoutil
# 11/10/09	use grub.conf-? to hold grub configuration data, use grub.conf
#		as primary conf file and menu.lst as secondary, don't advertise
#		-n option now autoutil doesn't support it
# 11/30/09	look for root param embedded in kernel line of grub config
# 12/1/09	remove autoutil and conf during uninstall (1906391), uninstall
#		previous instance during install (1905079), remove saved grub
#		production config during uninstall
# 12/2/09	location of install directories changed to use /boot/altiris as
#		root with individual install directories there, default will be
#		/boot/altiris/default
# 12/14/09	default execution, log file will be provided, place in /boot,
#		else no log file provided use default log file and location
############################################################

TRUE=1
FALSE=0
NAME="default"
LOG=""
LOG_DIR="/tmp"
WORK_LOG="autoinst.log"
VERBOSE="$TRUE"
ARCHIVE="auto.tar"
INSTALL="$TRUE"
DESTDIR=""
CURDIR=""
DEBUG=""
GC=""		## production grub configuration file

#---------------------------------------
## use for normal program output and recording in WORK_LOG
#  if debug out is enabled will display these messages also
function EchoLog()
{
  if [ "$VERBOSE" = "$TRUE" -o "$DEBUG" = "$TRUE" ]; then
    echo -e "$*"
  fi;
  echo "[installer `date +\"%Y-%m-%d %H:%M:%S\"`] :$*" >> $WORK_LOG
}

#---------------------------------------
## use for debug program output and recording in WORK_LOG
function WriteLog()
{
  if [ "$DEBUG" = "$TRUE" ]; then
    echo -e "$*"
  fi;
  echo "[installer `date +\"%Y-%m-%d %H:%M:%S\"`] :$*" >> $WORK_LOG
}

#---------------------------------------
function usage()
{
  echo -e "Linux Automation OS Installer\n"
  echo -e "  Usage: $0 [options]\n"
  echo -e "         [options]"
  echo -e "         -d | --debug      display debug info"
#  echo -e "         -n | --name ID    name of Automation OS"
  echo -e "         -q | --quiet      do not display status info"
  echo -e "         -u | --uninstall  uninstall automation boot directory"
  echo -e "         -h | --help       display this help\n"
}

#===========================================================
while [ "$1" != "" ]; do
  case $1 in
    -d | --debug )       DEBUG=$TRUE
                         ;;
    -l | --log )         shift
                         LOG=$1
                         ;;
    -n | --name )        shift
                         NAME=$1
                         ;;
    -q | --quiet )       VERBOSE=$FALSE
                         ;;
    -u | --uninstall )   INSTALL=$FALSE
                         ;;
    -h | --help )        usage
                         exit
                         ;;
  esac;
  shift
done;

## if run from extractor LOG will be provided, place in /boot
if [ -n "$LOG" ]; then
  if [ -e /boot ]; then
    WORK_LOG="/boot/$LOG"
  else
    WORK_LOG="$LOG_DIR/$LOG"
  fi;
else
  WORK_LOG="$LOG_DIR/$WORK_LOG"
fi;

EchoLog "Linux Automation OS Installer\n"

WriteLog " - using log file $WORK_LOG"

if [ $UID -ne 0 ]; then
  EchoLog "Installer requires 'root' privileges, unable to continue"
  exit 13
fi;

CURDIR=`dirname $0`
if [ "$CURDIR" = "." ]; then
  CURDIR=$PWD
fi;

if [ ! -L /boot/grub/grub.conf -a -e /boot/grub/grub.conf ]; then
  GC="/boot/grub/grub.conf"
elif [ ! -L /boot/grub/menu.lst -a -e /boot/grub/menu.lst ]; then
  GC="/boot/grub/menu.lst"
fi;

EchoLog " - current directory: $CURDIR"

if [ "$INSTALL" = "$TRUE" ]; then
  if [ ! -e "$CURDIR/autoutil" ]; then
    EchoLog "autoutil not provided in archive, archive may not be complete, unable to continue"
    exit 14
  fi;
  if [ ! -e "$CURDIR/autoutil.conf" ]; then
    EchoLog "autoutil.conf not provided in archive, archive may not be complete, unable to continue"
    exit 14
  fi;
  if [ ! -e "$CURDIR/$ARCHIVE" ]; then
    EchoLog "$ARCHIVE not provided in archive, unable to continue"
    exit 15
  fi;

  if [ -n "$GC" ]; then
    DESTDIR="/boot/altiris/$NAME"
    if [ `dirname $DESTDIR` = "/" ]; then
      #NAME var is empty so path is bad, don't do anything bad here
      EchoLog "Destination directory name is empty, unable to continue"
      exit 12
    fi;
    if [ -d "$DESTDIR" ]; then
      EchoLog " - Destination directory $DESTDIR exists, contents will be overwritten"
      if [ -e "$DESTDIR/autoinst.sh" ]; then
        EchoLog " - calling uninstall for previous version"
        $DESTDIR/autoinst.sh -n $NAME -q -u
      else
        rm -Rf $DESTDIR
        rm -f /sbin/autoutil
        rm -f /etc/autoutil.conf
        [ -e "/boot/grub/grub.conf-p" ] && rm -f /boot/grub/grub.conf-p
      fi;
    fi;
    EchoLog " - creating Destination directory $DESTDIR"
    mkdir -p -m 0754 "$DESTDIR"
  else
    EchoLog "Grub menu file not found, unable to continue"
    exit 11
  fi;

  EchoLog " - expanding archive to $DESTDIR directory"
  tar -xf "$CURDIR/$ARCHIVE" -C "$DESTDIR"
  rc=$?
  if [ $rc -ne 0 ]; then
    EchoLog "Archive expansion returned an error: $rc, install terminated"
    exit 16
  fi;

  if [ -e "/sbin/autoutil" ]; then
    EchoLog " - autoutil was found in /sbin, included version not copied"
  fi;

  ## copy autoutil, change path in autoutil.conf
  cp -p $CURDIR/autoutil /sbin
  chmod 750 $CURDIR/autoutil

  cat $CURDIR/autoutil.conf | tr -d '\r' | sed 's#^path.*$#path=/sbin#' > /etc/autoutil.conf

  if [ ! -e "$DESTDIR/boot.ini" ]; then
    EchoLog "boot.ini file not found in archive, unable to configure"
    exit 18
  fi;
  b_name=`cat $DESTDIR/boot.ini | awk -F= '/^name/ {print $2}'`
  b_desc=`cat $DESTDIR/boot.ini | awk -F= '/^desc/ {print $2}'`
  b_kern=`cat $DESTDIR/boot.ini | awk -F= '/^kern/ {print $2}'`
  b_rootfs=`cat $DESTDIR/boot.ini | awk -F= '/^rootfs/ {print $2}'`
  b_root=`cat $DESTDIR/boot.ini | awk -F= '/^root=/ {print $2}'`
  b_ramdisk=`cat $DESTDIR/boot.ini | awk -F= '/^ramdisk/ {print $2}'`
  b_opts=`cat $DESTDIR/boot.ini | awk -F= '/^option/ {print $2}'`
  b_msg=`cat $DESTDIR/boot.ini | awk -F= '/^message/ {print $2}'`

  root_param="root (hd0,0)"
  ## look for root device embedded in kernel line first 'kernel (hd0,1)/boot/linux' ala SLES 9
  if egrep -q "^[^#].*ernel.*\(hd.,.\)" $GC; then
    root_line=`egrep -v "^#" $GC | sed 's/^[ \t]*//' | egrep "^kernel.*\(hd.,.\)/" | head -n 1 | awk '{print $2}'`
    root_param=`echo $root_line | sed 's#/.*$##'`
    root_param="root $root_param"
    t_kern=`echo $root_line | sed 's#^.*hd.,..##'`
  else
    n=`grep root $GC | egrep -v "^#" | sed 's/^[ \t]*//' | egrep "^root" | wc -l`
    if [ $n -ge 1 ]; then
      root_param=`grep root $GC | egrep -v "^#" | sed 's/^[ \t]*//' | egrep "^root" | head -n 1`
    fi;
    t_kern=`grep kernel $GC | egrep -v "^#" | grep -v "altiris" | sed 's/^[ \t]*//' | egrep "^kernel" | awk '{print $2}' | head -n 1`
  fi;

  if [ `dirname $t_kern` = "/" ]; then
    WriteLog " - boot entries relative to /boot partition"
    b_kern="/altiris/$NAME/$b_kern"
    b_rootfs="/altiris/$NAME/$b_rootfs"
  else
    WriteLog " - boot entries relative to /root partition"
    b_kern="/boot/altiris/$NAME/$b_kern"
    b_rootfs="/boot/altiris/$NAME/$b_rootfs"
  fi;

  ## create grub conf for automation booting
  echo "default 0" >$DESTDIR/grub.conf-a
  echo "timeout 3" >>$DESTDIR/grub.conf-a
  echo "" >>$DESTDIR/grub.conf-a
  echo "title $b_name" >>$DESTDIR/grub.conf-a
  echo "$root_param" >>$DESTDIR/grub.conf-a
  echo "kernel $b_kern root=$b_root" ramdisk_size=$b_ramdisk $b_opts>>$DESTDIR/grub.conf-a
  echo "initrd $b_rootfs" >>$DESTDIR/grub.conf-a
  echo "" >>$DESTDIR/grub.conf-a

  ## save copy of installer for doing uninstalls
  EchoLog " - saving installer in $DESTDIR"
  cp -p $0 $DESTDIR

  ## leave atrsboot file in /boot/altiris to indicate we've been here
  #  may need to check contents of /DESTDIR/atrsboot some day when/if other
  #  automation boot dirs are used
  touch /boot/altiris/atrsboot

  EchoLog " - installation complete"
else
  ## Uninstall automation boot directory
  if [ -d "/boot/altiris/$NAME" ]; then
    DESTDIR="/boot/altiris/$NAME"
    if [ `dirname $DESTDIR` = "/" ]; then
      #NAME var is empty so path is bad, don't do anything bad here
      EchoLog "Destination directory name is empty, unable to continue"
      exit 12
    fi;
    EchoLog " - uninstalling /boot/altiris/$NAME"
    rm -Rf $DESTDIR
    if [ -e "/sbin/autoutil" ]; then
      EchoLog " - removing /sbin/autoutil"
      rm -f /sbin/autoutil
    fi;
    if [ -e "/etc/autoutil.conf" ]; then
      EchoLog " - removing /etc/autoutil.conf"
      rm -f /etc/autoutil.conf
    fi;
    if [ -e "/boot/grub/grub.conf-p" ]; then
      EchoLog " - removing saved grub production configuration"
      rm -f /boot/grub/grub.conf-p
    fi;
    if ! ls -d /boot/altiris/*/ > /dev/null 2>&1; then
      EchoLog " - removing root install directory"
      rm -Rf /boot/altiris
    fi;
  else
    EchoLog "Destination directory /boot/altiris/$NAME does not exist, uninstall terminated"
    exit 17
  fi;
fi;

exit 0
 
