#!/bin/sh
#
#     tiger - A UN*X security checking system
#     Copyright (C) 1993 Douglas Lee Schales, David K. Hess, David R. Safford
#
#    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, 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.
#
#     Please see the file `COPYING' for the complete copyright notice.
#
# check_group  - created 06/14/93
#
# check_group  - 07/05/2006 - jfs - Fix deprecated syntax with sort.
#    Thanks to Cyril Chaboisseau and Adam James for providing a patch
#    (Debian bug: #369501)
# check_group  - 04/03/2003 - rbrad - grpck does not always return non-0 values
#                                     on errors. 
# check_group  - 10/07/2003 - jfs - Delete temporary files
# check_group  - 08/14/2003 - jfs - Added OUTPUTMETHOD to dependancies
# check_group  - 08/09/2003 - jfs - Re-added RM to dependancies.
# check_group  - 08/08/2003 - jfs - Safe temporary file creation
# check_group  - 06/26/2003 - jfs - Added Ryan Braderitch's patch
#
#-----------------------------------------------------------------------------
#
TigerInstallDir='.'

#
# Set default base directory.
# Order or preference:
#      -B option
#      TIGERHOMEDIR environment variable
#      TigerInstallDir installed location
#
basedir=${TIGERHOMEDIR:=$TigerInstallDir}

for parm
do
   case $parm in
   -B) basedir=$2; break;;
   esac
done

#
# Verify that a config file exists there, and if it does
# source it.
#
[ ! -r $basedir/config ] && {
  echo "--ERROR-- [init002e] No 'config' file in \`$basedir'."
  exit 1
}

. $basedir/config

. $BASEDIR/initdefs
#
# If run in test mode (-t) this will verify that all required
# elements are set.
#
[ "$Tiger_TESTMODE" = 'Y' ] && {
  haveallcmds AWK CAT GEN_GROUP_SETS GREP JOIN MV SORT UNIQ RM OUTPUTMETHOD || exit 1
  haveallfiles BASEDIR WORKDIR || exit 1
  
  echo "--CONFIG-- [init003c] $0: Configuration ok..."
  exit 0
}

#------------------------------------------------------------------------
echo
echo "# Performing check of group files..."

haveallcmds AWK CAT GEN_GROUP_SETS GREP JOIN MV SORT UNIQ RM OUTPUTMETHOD || exit 1
haveallfiles BASEDIR WORKDIR || exit 1

safe_temp "$WORKDIR/grp.list.$$" "$WORKDIR/grp2.$$" "$WORKDIR/g1name.$$" "$WORKDIR/g2name.$$" "$WORKDIR/g1gid.$$" "$WORKDIR/g2gid.$$" "$WORKDIR/grp2new.$$"

trap 'delete "$WORKDIR/grp.list.$$" "$WORKDIR/grp2.$$" \
"$WORKDIR/g1name.$$" "$WORKDIR/g2name.$$" "$WORKDIR/g1gid.$$" \
"$WORKDIR/grp2new.$$" "$WORKDIR/g2gid.$$"; exit 1' 1 2 3 15

$GEN_GROUP_SETS > $WORKDIR/grp.list.$$

saveifs=$IFS

$CAT $WORKDIR/grp.list.$$ > $WORKDIR/grp2.$$
newfile=$WORKDIR/grp2new.$$

while read group1
do
  src1=`$CAT $group1.src`
  $SORT $group1 > $WORKDIR/g1name.$$
  $SORT -t: -k 3,3 $group1 > $WORKDIR/g1gid.$$

  $AWK -F: '{print $1}' $WORKDIR/g1name.$$ |
  $UNIQ -d |
  while read grpname
  do
    message WARN grp001w "" "Groupname \`$grpname' exists multiple times in $src1."
  done

  $AWK -F: '{print $3}' $WORKDIR/g1gid.$$ |
  $UNIQ -d |
  while read gid
  do
    message WARN grp002w "" "GID $gid exists multiple times in $src1."
  done

  # Avoid duplicate warnings (since PWCK should also say this)
  if [ -z "$PWCK" ]; then
    $AWK -F: 'NF != 4 {print}' $WORKDIR/g1gid.$$ |
    while read entry
    do
      message WARN grp003w "$entry" "Malformed entry in $src1:"
    done
  fi
 
  $GREP -v "^$group1\$" $WORKDIR/grp2.$$ |
  while read group2
  do
    src2=`$CAT $group2.src`

    $SORT $group2 > $WORKDIR/g2name.$$
    $SORT -t: -k 3,3 $group2 > $WORKDIR/g2gid.$$
    $JOIN -t: -o 1.1 1.3 2.3 $WORKDIR/g1name.$$ $WORKDIR/g2name.$$ |
    {
      IFS=:
      while read grpname gid1 gid2
      do
	IFS=$saveifs
	[ "$gid1" != "$gid2" ] && {
	  message WARN grp004w "" "GID conflict for group \`$grpname' between $src1 (gid = $gid1) and $src2 (gid = $gid2)."
	}
	IFS=:
      done
    }

    $JOIN -t: -j 3 -o 1.3 1.1 2.1 $WORKDIR/g1gid.$$ $WORKDIR/g2gid.$$ |
    {
      IFS=:
      while read gid name1 name2
      do
	IFS=$saveifs
	[ "$name1" != "$name2" ] && {
	  message WARN grp005w "" "Groupname conflict for gid $gid between $src1 (group $name1) and $src2 (group $name2)."
	}
	IFS=:
      done
    }
    echo "$group2" >> $newfile
    delete $WORKDIR/g2gid.$$ $WORKDIR/g2name.$$
  done
  delete $WORKDIR/g1gid.$$ $WORKDIR/g1name.$$ $WORKDIR/grp2.$$
  [ -s $newfile ] && $MV $newfile $WORKDIR/grp2.$$
done < $WORKDIR/grp.list.$$ |
$OUTPUTMETHOD

while read file
do
  delete $file $file.src
done < $WORKDIR/grp.list.$$

# Verify the group file format.
[ -n "$GRPCK" ] && {
  # TODO: Add the results to the report
  grpckerr=`$GRPCK 2>&1`
  if [ -n "$grpckerr" ] ; then
    message WARN grp006w "" "Integrity of group files questionable ($GRPCK)."
  fi
}

delete $WORKDIR/grp.list.$$ $WORKDIR/grp2new.$$
delete $WORKDIR/g2gid.$$ $WORKDIR/g2name.$$

exit 0
