#!/bin/sh
#
# adjust_flexlm_owner [-n]
#
# If the -n qualifier is used, adjust_flexlm_owner will be forced to run
# non-interactively, otherwise, adjust_flexlm_owner will go interactive if
# the required data is not found.  If -n is used and required data is not
# found then adjust_flexlm_owner will exit with the appropriate error message.
#
# This script modifies permissions and startup scripts appropriately so
# that the license daemon, lmgrd.ste, will not be started as a root owned
# daemon.  The first part of this script aquires a valid username.  If
# the environment variable, FLEXLM_OWNER, is set to be a valid username
# then this script will execute non-interactively.  WARNING: This mechanism
# will not work if this script is executed by the postinstall script called
# by pkgadd.  Instead if the desire is for this script to run non-interactively
# when using pkgadd to install SUNWlicsw, create the file,
# /etc/opt/licenses/flexlm_owner and place in it the username that is desired
# before executing the pkgadd.  The username must be valid and should be on
# the first line of the file (the only line in the file) with no surrounding
# spaces.
#
# If FLEXLM_OWNER is set to be an invalid username or flexlm_owner contains
# an invalid username the script will terminate generating an appropriate
# error message.  If FLEXLM_OWNER is not set at all and flexlm_owner does not
# exist, and the -n qualifier was not used, this script will become interactive 
# and prompt the user for a valid username to use.  The script will not let the 
# user continue until a valid username is entered.  
#
# Once a valid username is obtained, this script will proceed to make a
# couple of modifications.  First, it will change the permissions of the
# license manager software so that it has group read and execute privileges.
# It will also change the group the the license manager software belongs to,
# to that of the "username"'s group.  And lastly, it will modify the License
# Daemon startup script to start the icense daemon under the new username. 
#
# When this script is run with the -n qualifier it will remain non-interactive.
# If no valid username is found in the flexlm_owner file then the default
# username, nobody, will be used.
#
# This script must be run as root to ensure that the modifications can
# be made.
#

#
# Assume this is not a SunOS machine
#
SUNOS=0

#
# Flag to indicate whether or not this script will run interactively
#
INTERACTIVE=0

#
# Flag to indicate whether or not non-interaction will be forced
#
FORCE_NON_INTER=0

#
# Default username to be used when no other choice has been made
#
DEFAULT_NAME=nobody

#
# Username to be used to start license daemon
#
FLEX_OWNER=""

#
# flag to indicate whether or not a valid username has been obtained
#
VALID_USER=0

#
# Flag to indicate that a username has been obtained and needs to be 
# checked for validity
#
GOT_USERNAME=0

#
# Username to be checked for validity
#
USERNAME=""

#
# File that can be used to force this script to run non-interactively.
# This file should contain a single valid non-privileged username if 
# it is to be used.
#
FLEXLM_OWNER_FILE="/etc/opt/licenses/flexlm_owner"

#
# License manager software that must have its group premissions changed
# to allow group read and execute
#
lic_mgr_software="/etc/opt/licenses/suntechd /etc/opt/licenses/lic.SUNW \
/etc/opt/licenses/lmdown /etc/opt/licenses/lmremove /etc/opt/licenses/lmver \
/etc/opt/licenses/lmgrd.ste /etc/opt/licenses/lmreread \
/etc/opt/licenses/lic_srvr_start /etc/opt/licenses/lic_mgr"

#
# Check to see if this is a SunOS machine.  If it is, then some of the
# paths need to be changed.
#
if [ -f /vmunix ]; then
   SUNOS=1

   #
   # License daemon startup script
   #
   lic_startup_script="/etc/opt/licenses/lic_mgr"
   echo_cmd="/usr/bin/echo"
else
   SUNOS=0
   lic_startup_script="/etc/init.d/lic_mgr"
   echo_cmd="/usr/ucb/echo"
fi

#
# function to prompt user for a valid username when this script is
# running interactively
#
get_username()
{
   GOT_USERNAME=0

   while [ $GOT_USERNAME -eq 0 ]; do

      ${echo_cmd} "Enter a valid username to be used when starting the"
      ${echo_cmd} -n "license daemon (or enter ? for help): "
      read response

      if [ "$response" = "?" ]; then
         ${echo_cmd} 
         ${echo_cmd} "A valid non-privileged username is requested for use in starting"
         ${echo_cmd} "the license server daemon, lmgrd.ste.  As in the past, root may"
         ${echo_cmd} "still be used but it is highly discouraged.  If root is used, there"
         ${echo_cmd} "is a potential security risk that can be abused on UNIX systems."
         ${echo_cmd} "Once a valid username is entered, the group that the license manager"
         ${echo_cmd} "software belongs to will be updated with that of the group that"
         ${echo_cmd} "username belongs to.  The permissions on these files will also be"
         ${echo_cmd} "updated to allow group read and execute privileges so that \"username\""

         if [ $SUNOS -eq 0 ]; then
            ${echo_cmd} "can use them.  The license manager startup script, /etc/rc2.d/S85lmgrd,"
            ${echo_cmd} "will be modified to start the license daemon as \"username\" even though"
            ${echo_cmd} "S85lmgrd is still executed as root."
         else
            ${echo_cmd} "can use them.  The license manager startup script, /etc/opt/licenses/lic_mgr,"
            ${echo_cmd} "will be modified to start the license daemon as \"username\" even though"
            ${echo_cmd} "lic_mgr is still executed as root."
         fi

         ${echo_cmd} ""
         ${echo_cmd} "If you wish to limit access to the license manager daemon, you can"
         ${echo_cmd} "set up a non-privileged account specifically for this purpose. For"
         ${echo_cmd} "example the account \"flexlm\" can be created.  If you want to use"
         ${echo_cmd} "a username such as \"flexlm\" that currently does not exist you can"
         ${echo_cmd} "either create it now before continuing on or Control-C out of this"
         ${echo_cmd} "script and re-execute it later by becoming root and typing"
         ${echo_cmd} ""
         ${echo_cmd} "/etc/opt/licenses/adjust_flexlm_owner"
         ${echo_cmd} ""
         ${echo_cmd} "at the prompt.  You can also enter an existing username now and"
         ${echo_cmd} "change it later at any time by re-executing adjust_flexlm_owner."
         ${echo_cmd} "It is necessary to enter a valid username before the license "
         ${echo_cmd} "server can be started."
         ${echo_cmd}
      else
         USERNAME=$response
         GOT_USERNAME=1
      fi
   done
} # end get_username


# 
# function to ensure a valid username is used
#
validate_user()
{
   # check to see if a valid username was entered
   if [ $SUNOS -eq 0 ]; then
      /usr/bin/id $USERNAME > /dev/null 2>&1
      id_stat=$?
   else
      /usr/bin/su $USERNAME -c > /dev/null 2>&1
      id_stat=$?

      #
      # If the username has no home directory the su command
      # will fail, so as a final check, see if there is an
      # entry in the passwd file
      #
      if [ $id_stat -ne 0 ]; then
         grep "^$USERNAME:" /etc/passwd > /dev/null 2>&1
         id_stat=$?
      fi
   fi
   if [ ${id_stat} -eq 0 ]; then
      #
      # If we are in interactive mode and the user entered 'root' give them
      # another chance to change their answer
      #
      if [ $INTERACTIVE -eq 1 -a $USERNAME = "root" ]; then
         ${echo_cmd}
         ${echo_cmd} "WARNING: There is a potential security hole when using"
         ${echo_cmd} "root to start the license daemon.  The purpose of this"
         ${echo_cmd} "script is to allow the user to select an alternate"
         ${echo_cmd} "non-privileged username to start the license daemon."
         ${echo_cmd} "It is strongly suggested that an alternate username"
         ${echo_cmd} "is selected."
         ${echo_cmd}
         ${echo_cmd} -n "Do you wish to select something other than root? <y|n>: "
         read response

         if [ "${response}" = "n" -o "${response}" = "N" ]; then
            VALID_USER=1
         else
            VALID_USER=0
         fi
      else
         VALID_USER=1
      fi
   else
      ${echo_cmd} $USERNAME is not valid
      VALID_USER=0
   fi
   ${echo_cmd}
} # end validate_user

#
# Function to change the permissions of a file as well as the group
#
change_permissions()
{
   #
   # get the group name to use
   #
   # unfortunately can't use id username because this is not supported on 
   # Solaris 1.x and 2.4
   #
   group_name=`su $FLEX_OWNER -c /usr/bin/id | sed -e 's/^.*gid//' -e 's/).*//' -e 's/^.*(//'`

   if [ -f $1 ]; then
      #
      # change permissions on file to allow group read and execute
      #
      lpath=$1
      if [ -h $1 ]; then
         lpath=`/usr/bin/ls -l $1 | sed 's/^.*-> //'`
      fi

      # prepare to update package database
      installf SUNWlicsw $lpath f 0750 ? ${group_name}

      chmod 750 $1 > /dev/null 2>&1

      #
      # If this is a SunOS machine then chgrp on a symbolic link will not
      # change the group of what the link points to, so we need to get
      # the path of the correct file to change group on
      #
      if [ $SUNOS -eq 1 ]; then
         #
         # If the file is a symbolic link then get the pathname that the link
         # points to
         #
         if [ -h $1 ]; then
            chgrp ${group_name} ${lpath} > /dev/null 2>&1
            chgrp_stat=$?
         else
            chgrp ${group_name} $1 > /dev/null 2>&1
            chgrp_stat=$?
         fi
      else
         chgrp ${group_name} $1 > /dev/null 2>&1
         chgrp_stat=$?
      fi

      if [ ${chgrp_stat} -ne 0 ]; then
         ${echo_cmd} "ERROR occurred attempting to change the group of the"
         ${echo_cmd} "file $1 to $group_name. Terminating"
         ${echo_cmd} "execution."
         exit 1
      fi

      # update package database
      installf -f SUNWlicsw

   fi
} # end change_permissions


###################################################################
#
# Begin main
#
###################################################################

#
# Was this script started with the -n option?  If so force script
# to run non-interactively
#
if [ "$1" = "-n" ]; then
   FORCE_NON_INTER=1
fi

#
# This script needs to be run as root, if not terminate execution
#
if [ `/usr/ucb/whoami` != "root" ]; then
   ${echo_cmd} "ERROR: You must be root to execute this script."
   ${echo_cmd} "Terminating execution."
   exit 1
fi

# 
# First possible way for this script to execute non-interactively.
# Before going interactive check to see if the file exists that contains
# a username to be used.
#
if [ -f $FLEXLM_OWNER_FILE ]; then

   USERNAME=`cat $FLEXLM_OWNER_FILE`

   # make sure something was read from the file
   if [ "$USERNAME" = "" ]; then
      VALID_USER=0
   else
      validate_user $USERNAME
   fi

   if [ $VALID_USER -eq 0 ]; then
      ${echo_cmd}
      ${echo_cmd} "ERROR: The username, $USERNAME, read from the file, "
      ${echo_cmd} "$FLEXLM_OWNER_FILE, is not a valid username. Please refer"
      ${echo_cmd} "to the license installation documentation."
      ${echo_cmd} "Terminating execution."
      ${echo_cmd}
      exit 1
   fi
   ${echo_cmd} "username taken from $FLEXLM_OWNER_FILE"
   ${echo_cmd} "Executing in non-interactive mode."

#
# Second possible way for this script to execute non-interactively.
# Check to see if the the environment variable is set. If it is check to
# see if it is set to a valid user, if so remain non-interactive.
#
elif [ $FLEXLM_OWNER ]; then
   USERNAME=$FLEXLM_OWNER
   validate_user $USERNAME

   if [ $VALID_USER -eq 0 ]; then
      ${echo_cmd} "ERROR: The environment variable FLEXLM_OWNER is incorrectly set"
      ${echo_cmd} "to be an invalid username.  Please refer to the license"
      ${echo_cmd} "installation documentation.  Terminating execution."
      exit 1
   fi
   ${echo_cmd} "username taken from environment variable FLEXLM_OWNER"
   ${echo_cmd} "Executing in non-interactive mode."

else
   if [ $FORCE_NON_INTER -eq 1 ]; then

      #
      # If we are running non-interactively and the flexlm_owner file does not
      # exist and FLEXLM_OWNER is not set then use the the OS username, nobody,
      # as a default.
      #
      USERNAME=$DEFAULT_NAME

      validate_user $USERNAME

      if [ $VALID_USER -eq 0 ]; then
         ${echo_cmd}
         ${echo_cmd} "ERROR: The default username, $USERNAME, is not a valid "
         ${echo_cmd} "username on this system. Please refer to the license"
         ${echo_cmd} "installation documentation."
         ${echo_cmd} "Terminating execution."
         ${echo_cmd}
         exit 1
      fi
      ${echo_cmd} ""
      ${echo_cmd} "Default username, $DEFAULT_NAME, to be used."
      ${echo_cmd} "Executing in non-interactive mode."
      ${echo_cmd} "This can be changed at any time by running the script"
      ${echo_cmd} "/etc/opt/licenses/adjust_flexlm_owner as root"
      ${echo_cmd} ""

   else
      ${echo_cmd} "Executing in interactive mode."
      ${echo_cmd}
      INTERACTIVE=1
   fi
fi

#
# If we are in interactive mode then prompt the user
# for a valid username to use
#
if [ $INTERACTIVE -eq 1 ]; then
   while [ $VALID_USER -eq 0 ]; do
      get_username
      validate_user $USERNAME
   done
fi

FLEX_OWNER=$USERNAME

#
# Check to see if 'root' was entered and if so give a stern warning if
# in non-interactive mode.
#
if [ $FLEX_OWNER = "root" -a $INTERACTIVE -eq 0 ]; then
   ${echo_cmd}
   ${echo_cmd} "WARNING: There is a potential security hole when using"
   ${echo_cmd} "root to start the license daemon.  The purpose of this"
   ${echo_cmd} "script is to allow the user to select an alternate"
   ${echo_cmd} "non-privileged username to start the license daemon."
   ${echo_cmd} "It is strongly suggested that this script is run again"
   ${echo_cmd} "and an alternate user is selected.  Until then root"
   ${echo_cmd} "will be used.  You have been warned."
   ${echo_cmd}
fi

${echo_cmd} "$FLEX_OWNER will be used by the startup script, $lic_startup_script,"
${echo_cmd} "to start the license daemon"
${echo_cmd}

#
# Now that we have a valid username to use, we must change ownership
# of the license manager software to the username entered and update
# the script, /etc/rc2.d/S85lmgrd, (/etc/opt/licenses/lic_mgr if this
# is a SunOS machine) to use this username to start the license daemon.
#

#
# first change permissions of license manager software if the new ownername
# is not 'root'
#
if [ $FLEX_OWNER != "root" ]; then
   set $lic_mgr_software
   for args
   do
      change_permissions $args
   done
fi

#
# next update the startup script
#
new_line_1="        chown $FLEX_OWNER \$logfile"
new_line_2="      su $FLEX_OWNER -c \$lic_srvr_start"

if [ -f $lic_startup_script ]
then

   # prepare to update package database
   installf SUNWlicsw ${lic_startup_script} f 0744 ? ?

   /usr/bin/ed ${lic_startup_script} <<CMDS > /dev/null 2>&1
/FLEXLM_OWNER_CHG_1
+1
d
i
$new_line_1
.
/FLEXLM_OWNER_CHG_2
+1
d
i
$new_line_2
.
w
q
CMDS

fi

# check return status
if [ $? -ne 0 ]; then
   ${echo_cmd} "Error occurred attempting to update the license daemon startup"
   ${echo_cmd} "script, ${lic_startup_script}.  Terminating execution."
   exit 1
elif [ $INTERACTIVE -eq 0 ]; then

   # update package database
   installf -f SUNWlicsw

   ${echo_cmd} "The license daemon startup script has been successfully updated."

   if [ $SUNOS -eq 0 ]; then
      ${echo_cmd} "Execute the script, /etc/rc2.d/S85lmgrd, to restart the license"
   else
      ${echo_cmd} "Execute the script, /etc/opt/licenses/lic_mgr, to restart the license"
   fi

   ${echo_cmd} "server daemon."
   exit 0
else
   ${echo_cmd} "The license daemon startup script has been successfully updated."
   ${echo_cmd} "For these changes to be used, the license daemon must be stopped"
   ${echo_cmd} "(if it is running) and then restarted.  To stop the license daemon"
   ${echo_cmd} "as root type:"
   ${echo_cmd}

   if [ $SUNOS -eq 0 ]; then
      ${echo_cmd} "/etc/rc2.d/S85lmgrd stop"
   else
      ${echo_cmd} "/etc/opt/licenses/lic_mgr stop"
   fi

   ${echo_cmd}
   ${echo_cmd} "at the command line.  To restart the license server daemon, execute"
   ${echo_cmd} "the same line without the \"stop\""
   ${echo_cmd}
   exit 0
fi

# end adjust_flexlm_owner
