#!/bin/bash
# 
# This script is used for Administration of RSBAC general file/dir attributes
#
#
# Make sure we're really running bash.
#
[ -z "$BASH" ] && { echo "    bash" 1>&2; exit 1; }

#
# Cache function definitions, turn off posix compliance
#
set -h +o posix

# not used
ATTRIBUTES="security_level object_category data_type mac_check \
            pm_object_type pm_object_class rc_type \
            log_array_low log_array_high"

# This must be a unique temporary filename
if test -z "$TMPDIR" ; then TMPDIR=/tmp ; fi
TMPFILE=$TMPDIR/rsbac_dialog.$$

# set this to rsbac bin dir, if not in path (trailing / is mandatory!)
#
#if test -z "$RSBACPATH" ; then RSBACPATH=./ ; fi

# set this to initial dir on script startup
LASTDIR='/dev'

# test for LINES and COLUMNS (should be exported e.g. in /etc/profile)
if test -z "$LINES" ; then LINES=25 ; fi
if test -z "$COLUMNS" ; then COLUMNS=80 ; fi
declare -i BL=$LINES-4
declare -i BC=$COLUMNS-4
declare -i MAXLINES=$LINES-10
gl () {
  if test $1 -gt $MAXLINES
  then echo $MAXLINES
  else echo $1
  fi
}

if test -z "$BACKTITLE"
  then BACKTITLE="RSBAC   v1.1.0" ; fi
TITLE="`whoami`: RSBAC  "
ERRTITLE="RSBAC   - ERROR"

## no changes below this line!

get_attributes () {
  if test "$FILE" != "" 
    then
         if test -b "$FILE"
           then TYPE=block
                LASTDIR=`(cd $LASTDIR ; pwd)`
         elif test -c "$FILE"
           then TYPE=char
                LASTDIR=`(cd $LASTDIR ; pwd)`
         else TYPE=NONE
              SECLEVEL=""
              MACCAT=""
              OBJCAT=""
              DATATYPE=""
              PMOBJTYPE=""
              MACCHECK=""
              RCTYPE=""
              LOGLOW=""
              LOGHIGH=""
              return
         fi
         SECLEVEL=`$RSBACPATH""attr_get_file_dir DEV $FILE security_level`
         MACCAT=`$RSBACPATH""attr_get_file_dir DEV $FILE mac_categories`
         OBJCAT=`$RSBACPATH""attr_get_file_dir DEV $FILE object_category`
         DATATYPE=`$RSBACPATH""attr_get_file_dir DEV $FILE data_type`
         MACCHECK=`$RSBACPATH""attr_get_file_dir DEV $FILE mac_check`
         PMOBJTYPE=`$RSBACPATH""attr_get_file_dir DEV $FILE pm_object_type`
         PMCLASS=`$RSBACPATH""attr_get_file_dir DEV $FILE pm_object_class`
         RCTYPE=`$RSBACPATH""attr_get_file_dir DEV $FILE rc_type`
         LOGLOW=`$RSBACPATH""attr_get_file_dir DEV $FILE log_array_low`
         LOGHIGH=`$RSBACPATH""attr_get_file_dir DEV $FILE log_array_high`
  fi
}

onoff () {
   if test "$1" = "$2"
     then echo on
   else echo off
   fi
}

onoffb_ru () {
   if test "$1" = "1"
     then echo 
   else echo 
   fi
}
onoffb () {
   if test "$1" = "1"
     then echo on
   else echo off
   fi
}
list_item () {
   if test -b $1
   then echo $1 .
   elif test -c $1
   then echo $1 .
   else echo $1 NONE
   fi
}

type_name () {
  if test "$TYPE" = "NONE" -o -z "$1"
  then echo " "
  else if ! $RSBACPATH""rc_get_item TYPE $1 type_dev_name
       then echo "()"
       fi
  fi
}

get_vname () {
  if test "$TYPE" = "NONE"
    then echo " "
         return
  fi
  if test -z "$2"
    then echo "N/A"
         return
  fi

  case $1 in
    seclevel)
      case $2 in
        0) echo 
          ;;
        1) echo 
          ;;
        2) echo 
          ;;
        3) echo  
          ;;
        252) echo . 
          ;;
        254) echo 
          ;;
        *) echo N/A
          ;;
      esac 
      ;;
    objcat)
      case $2 in
        0) echo 
          ;;
        1) echo 
          ;;
        2) echo 
          ;;
        *) echo N/A
          ;;
      esac 
      ;;
    datatype)
      case $2 in
        0) echo None
          ;;
        1) echo CDI
          ;;
        2) echo CDIIC
          ;;
        3) echo SI
          ;;
        *) echo N/A
          ;;
      esac 
      ;;
    maccheck)
      case $2 in
        0) echo .
          ;;
        1) echo .
          ;;
        *) echo N/A
          ;;
      esac 
      ;;
    pmobjtype)
      case $2 in
        0) echo None
          ;;
        1) echo TP
          ;;
        2) echo  
          ;;
        3) echo - 
          ;;
        4) echo IPC
          ;;
        5) echo 
          ;;
        *) echo N/A
          ;;
      esac 
      ;;
    loglevel)
      case $2 in
        0) echo None
          ;;
        1) echo 
          ;;
        2) echo 
          ;;
        3) echo 
          ;;
        *) echo N/A
          ;;
      esac 
      ;;
    *) echo ERROR!
      ;;
  esac
}

gen_log_menu_items() {
  if test -e ${TMPFILE}.2
    then rm ${TMPFILE}.2
  fi
  for i in $REQUESTS
  do TMP=`$RSBACPATH""attr_get_file_dir DEV $FILE log_level $i`
     echo $i `get_vname loglevel $TMP`>>${TMPFILE}.2
  done
}

log_menu () {
  if test -z "$REQUESTS"
    then REQUESTS=`$RSBACPATH""attr_get_file_dir DEV $FILE log_level NONE 2>/dev/null|grep -v types`
  fi
  gen_log_menu_items
  while true ; do \
    if ! \
    dialog --title "$TITLE" \
           --backtitle "$BACKTITLE" \
           --menu "$FILE:    " $BL $BC `gl 37` \
                `cat ${TMPFILE}.2` \
                "Ende" "" \
         2>$TMPFILE
     then rm ${TMPFILE}.2
          LOGLOW=`$RSBACPATH""attr_get_file_dir DEV $FILE log_array_low`
          LOGHIGH=`$RSBACPATH""attr_get_file_dir DEV $FILE log_array_high`
          return
    fi
    REQ=`cat $TMPFILE`
    if test "$REQ" == "Ende"
    then rm ${TMPFILE}.2
         LOGLOW=`$RSBACPATH""attr_get_file_dir DEV $FILE log_array_low`
         LOGHIGH=`$RSBACPATH""attr_get_file_dir DEV $FILE log_array_high`
         return
    fi
    VAL=`grep "^$REQ " ${TMPFILE}.2|cut -f 2 -d ' '`
    if dialog --title "$TITLE" \
              --backtitle "$BACKTITLE" \
              --radiolist "    $FILE / $REQ" $BL $BC 5 \
                          0 `get_vname loglevel 0` `onoff None $VAL` \
                          1 `get_vname loglevel 1` `onoff Denied $VAL` \
                          2 `get_vname loglevel 2` `onoff Full $VAL` \
                          3 `get_vname loglevel 3` `onoff Request $VAL` \
       2>$TMPFILE
    then TMP=`cat $TMPFILE`
         if $RSBACPATH""attr_set_file_dir DEV $FILE log_level $REQ $TMP &>$TMPFILE
         then gen_log_menu_items
         else \
           dialog --title "$ERRTITLE" \
                  --backtitle "$BACKTITLE" \
                  --msgbox "`head -n 1 $TMPFILE`" $BL $BC
         fi
    fi
done
}

declare -i MAXCATLEN=$BC-38
cat_print () {
  if test $MAXCATLEN -ge 64
  then echo $1
  else echo "( )"
  fi
}

gen_cat_list () {
    for i in $*
    do
      TMP=`$RSBACPATH""attr_get_file_dir DEV $FILE mac_categories $i`
      echo $i `onoffb_ru $TMP` `onoffb $TMP`
    done
}

###################### Menu #################

if test "$1" != ""
then FILE=$1
else FILE=$LASTDIR
fi
get_attributes $FILE

while true ; do \
  if ! \
  dialog --title "$TITLE" \
         --backtitle "$BACKTITLE" \
         --menu " " $BL $BC `gl 16` \
                ". /:" " " \
                "----------------" " " \
                ".  :" "$FILE / $TYPE" \
                ". :" "$SECLEVEL / `get_vname seclevel $SECLEVEL`" \
                "MAC :" "`cat_print $MACCAT`" \
                ". :" "$OBJCAT / `get_vname objcat $OBJCAT`" \
                ". :" "$DATATYPE / `get_vname datatype $DATATYPE`" \
                "MAC :" "$MACCHECK / `get_vname maccheck $MACCHECK`" \
                "PM  :" "$PMOBJTYPE / `get_vname pmobjtype $PMOBJTYPE`" \
                "PM  :" "$PMCLASS" \
                "RC :" "$RCTYPE / `type_name $RCTYPE`" \
                "Log Array Low:" "$LOGLOW" \
                "Log Array High:" "$LOGHIGH" \
                "----------------" " " \
                ".  /:" " /" \
                ".  ACL :" " ACL " \
                "." "" \
         2>$TMPFILE
   then rm $TMPFILE ; exit
  fi

  case `cat $TMPFILE` in
    '. /:')
        if test ! -d $LASTDIR
        then $LASTDIR='/'
        fi
        TMP=`ls -1Fad $LASTDIR/* $LASTDIR/.*|tr '*' ' '`
        if dialog --title "$TITLE" \
                  --backtitle "$BACKTITLE" \
                  --menu " /" $BL $BC $MAXLINES \
                         `for i in $TMP ; do list_item $i ; done` \
           2>$TMPFILE
        then FILE=`cat $TMPFILE`
             get_attributes
        fi
      ;;

    ".  :")
        if dialog --title "$TITLE" \
                  --backtitle "$BACKTITLE" \
                  --inputbox " /" $BL $BC $FILE \
           2>$TMPFILE
        then FILE=`cat $TMPFILE`
             get_attributes
        fi
      ;;
    '. :')
        if test "$TYPE" != "NONE"
        then \
          if dialog --title "$TITLE" \
                    --backtitle "$BACKTITLE" \
                    --radiolist "    $FILE (. : $SECLEVEL)" $BL $BC 7 \
                                "." " " off \
                                0 "`get_vname seclevel 0`" `onoff 0 $SECLEVEL` \
                                1 "`get_vname seclevel 1`" `onoff 1 $SECLEVEL` \
                                2 "`get_vname seclevel 2`" `onoff 2 $SECLEVEL` \
                                3 "`get_vname seclevel 3`" `onoff 3 $SECLEVEL` \
                                252 "`get_vname seclevel 252`" `onoff 252 $SECLEVEL` \
                                254 "`get_vname seclevel 254`" `onoff 254 $SECLEVEL` \
             2>$TMPFILE
          then TMP=`cat $TMPFILE`
               if test "$TMP" == "."
               then
                 if dialog --title "$TITLE" \
                           --backtitle "$BACKTITLE" \
                           --inputbox "  MAC" $BL $BC "$SECLEVEL" \
                   2>$TMPFILE
                 then
                   TMP="`cat $TMPFILE`"
                   if test $TMP -gt 254
                   then
                     dialog --title "$ERRTITLE" \
                            --backtitle "$BACKTITLE" \
                            --msgbox "    $TMP!" $BL $BC
                     TMP=""
                   fi
                 else
                   TMP=""
                 fi
               fi
               if test -n "$TMP"
               then
                 if $RSBACPATH""attr_set_file_dir DEV $FILE security_level $TMP &>$TMPFILE
                 then SECLEVEL=$TMP
                 else \
                   dialog --title "$ERRTITLE" \
                          --backtitle "$BACKTITLE" \
                          --msgbox "`head -n 1 $TMPFILE`" $BL $BC
                 fi
               fi
          fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox " :     !" 5 $BC
        fi
      ;;


    'MAC :')
        if test "$TYPE" != "NONE"
        then \
          ALLCATNR=`$RSBACPATH""attr_get_file_dir list_category_nr`
          if dialog --title "MAC    $FILE" \
                    --backtitle "$BACKTITLE" \
                    --checklist ": $MACCAT" $BL $BC $MAXLINES \
                    `gen_cat_list $ALLCATNR` \
             2>$TMPFILE
          then TMP=`cat $TMPFILE|tr -d '"'`
               for i in $ALLCATNR
               do
                 if ! $RSBACPATH""attr_set_file_dir DEV $FILE mac_categories $i 0 &>$TMPFILE
                 then \ 
                   dialog --title "$ERRTITLE" \
                          --backtitle "$BACKTITLE" \
                          --msgbox "`head -n 1 $TMPFILE`" $BL $BC
                   continue
                 fi
               done
               for i in $TMP
               do
                 if ! $RSBACPATH""attr_set_file_dir DEV $FILE mac_categories $i 1 &>$TMPFILE
                 then \
                   dialog --title "$ERRTITLE" \
                          --backtitle "$BACKTITLE" \
                          --msgbox "`head -n 1 $TMPFILE`" $BL $BC
                   continue
                 fi
               done
               MACCAT=`$RSBACPATH""attr_get_file_dir DEV $FILE mac_categories`
          fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "MAC :   !" 5 $BC
        fi
      ;;

    '. :')
        if test "$TYPE" != "NONE"
        then \
          if dialog --title "$TITLE" \
                    --backtitle "$BACKTITLE" \
                    --radiolist "    $FILE" $BL $BC 3 \
                                0 "`get_vname objcat 0`" `onoff 0 $OBJCAT` \
                                1 "`get_vname objcat 1`" `onoff 1 $OBJCAT` \
                                2 "`get_vname objcat 2`" `onoff 2 $OBJCAT` \
             2>$TMPFILE
          then TMP=`cat $TMPFILE`
               if $RSBACPATH""attr_set_file_dir DEV $FILE object_category $TMP &>$TMPFILE
               then OBJCAT=$TMP
               else \
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "`head -n 1 $TMPFILE`" $BL $BC
               fi
          fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox " :   !" 5 $BC
        fi
      ;;

    '. :')
        if test "$TYPE" != "NONE"
        then \
          if dialog --title "$TITLE" \
                    --backtitle "$BACKTITLE" \
                    --radiolist "    $FILE" $BL $BC 5 \
                                0 "`get_vname datatype 0`" `onoff 0 $DATATYPE` \
                                1 "`get_vname datatype 1`" `onoff 1 $DATATYPE` \
                                2 "`get_vname datatype 2`" `onoff 2 $DATATYPE` \
                                3 "`get_vname datatype 3`" `onoff 3 $DATATYPE` \
             2>$TMPFILE
          then TMP=`cat $TMPFILE`
               if $RSBACPATH""attr_set_file_dir DEV $FILE data_type $TMP &>$TMPFILE
               then DATATYPE=$TMP
               else \
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "`head -n 1 $TMPFILE`" $BL $BC
               fi
          fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox " :    !!" 5 $BC
        fi
      ;;

    'MAC :')
        if test "$TYPE" != ""
        then \
           if test $MACCHECK = "0"
           then TMP="1"
           else TMP="0"
           fi
           if $RSBACPATH""attr_set_file_dir DEV $FILE mac_check $TMP &>$TMPFILE
           then MACCHECK=$TMP
           else \
             dialog --title "$ERRTITLE" \
                    --backtitle "$BACKTITLE" \
                    --msgbox "`head -n 1 $TMPFILE`" $BL $BC
           fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "Mac :   !!" 5 $BC
        fi
      ;;


    'PM  :')
        if test "$TYPE" != "NONE"
        then \
          if dialog --title "$TITLE" \
                    --backtitle "$BACKTITLE" \
                    --radiolist "Choose PM Object Type for $FILE" $BL $BC 6 \
                                0 "`get_vname pmobjtype 0`" `onoff 0 $PMOBJTYPE` \
                                1 "`get_vname pmobjtype 1`" `onoff 1 $PMOBJTYPE` \
                                2 "`get_vname pmobjtype 2`" `onoff 2 $PMOBJTYPE` \
                                3 "`get_vname pmobjtype 3`" `onoff 3 $PMOBJTYPE` \
                                4 "`get_vname pmobjtype 4`" `onoff 4 $PMOBJTYPE` \
                                5 "`get_vname pmobjtype 5`" `onoff 5 $PMOBJTYPE` \
             2>$TMPFILE
          then TMP=`cat $TMPFILE`
               if $RSBACPATH""attr_set_file_dir DEV $FILE pm_object_type $TMP &>$TMPFILE
               then PMOBJTYPE=$TMP
               else \
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "`head -n 1 $TMPFILE`" $BL $BC
               fi
          fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "PM  :    !" 5 $BC
        fi
      ;;

    'PM  :')
        if test "$TYPE" != "NONE"
        then \
           if dialog --title "$TITLE" \
                     --backtitle "$BACKTITLE" \
                     --inputbox "PM   (long integer)  $FILE" \
                                $BL $BC "$PMCLASS" \
              2>$TMPFILE
          then TMP=`cat $TMPFILE`
               if $RSBACPATH""attr_set_file_dir DEV $FILE pm_object_class $TMP &>$TMPFILE
               then PMCLASS=$TMP
               else \
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "`head -n 1 $TMPFILE`" $BL $BC
               fi
          fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "PM  :    !!" 5 $BC
        fi
      ;;

    'RC :')
        if test "$TYPE" != "NONE"
        then \
          if $RSBACPATH""rc_get_item list_used_dev_types >$TMPFILE
          then \
            if dialog --title "$TITLE" \
                      --backtitle "$BACKTITLE" \
                      --menu " RC   $FILE" $BL $BC $MAXLINES \
                      `cat $TMPFILE` \
               2>$TMPFILE
            then TMP=`cat $TMPFILE`
                 if $RSBACPATH""attr_set_file_dir DEV $FILE rc_type $TMP &>$TMPFILE
                 then RCTYPE=$TMP
                 else \
                   dialog --title "$ERRTITLE" \
                          --backtitle "$BACKTITLE" \
                          --msgbox "`head -n 1 $TMPFILE`" $BL $BC
                 fi
            fi
          else \
            if dialog --title "$TITLE" \
                      --backtitle "$BACKTITLE" \
                      --inputbox "RC  (integer)  $FILE" \
                                 $BL $BC "$RCTYPE" \
                2>$TMPFILE
            then TMP=`cat $TMPFILE`
                 if $RSBACPATH""attr_set_file_dir DEV $FILE rc_type $TMP &>$TMPFILE
                 then RCTYPE=$TMP
                 else \
                   dialog --title "$ERRTITLE" \
                          --backtitle "$BACKTITLE" \
                          --msgbox "`head -n 1 $TMPFILE`" $BL $BC
                 fi
            fi
          fi
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "RC :    !" 5 $BC
        fi
      ;;

    'Log Array Low:')
        if test "$TYPE" != "NONE"
        then \
          log_menu
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "Log Array Low:    !" 5 $BC
        fi
      ;;

    'Log Array High:')
        if test "$TYPE" != "NONE"
        then \
          log_menu
        else
                 dialog --title "$ERRTITLE" \
                        --backtitle "$BACKTITLE" \
                        --msgbox "Log Array High:    !" 5 $BC
        fi
      ;;

    '.   /:')
        $RSBACPATH""rsbac_fd_menu_ru "$FILE"
      ;;

    '.  ACL :')
        $RSBACPATH""rsbac_acl_menu_ru DEV "$FILE"
      ;;

    .)
        rm $TMPFILE ; exit
      ;;

    *)
        dialog --title "$ERRTITLE" \
               --backtitle "$BACKTITLE" \
               --msgbox " :  !" 5 $BC
  esac
# sleep 2
done
