#!/bin/bash #***********************************************# # rc.halfd # # written by Jesse Keating # # Jan 13, 2003 # # hacked to death by Robert Sanders # # Version 0.04 # # Run halfd for every HLDS user # #***********************************************# #***********************************************# #Copyright (c) 2003, # #SIT Technologies LLC & j2Solutions # #All rights reserved. # # # #Redistribution and use in source and binary # #forms, with or without modification, are # #permitted provided that the following # #conditions are met: # # # # * Redistributions of source code must # # retain the above copyright notice, # # this list of conditions and the # # following disclaimer. # # * Redistributions in binary form must # # reproduce the above copyright notice, # # this list of conditions and the # # following disclaimer in the # # documentation and/or other materials # # provided with the distribution. # # * Neither the name of the Owners nor # # the names of its contributors may be # # used to endorse or promote products # # derived from this software without # # specific prior written permission. # # # #THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT # #HOLDERS AND CONTRIBUTORS "AS IS" AND ANY # #EXPRESS OR IMPLIED WARRANTIES, INCLUDING, # #BUT NOT LIMITED TO, THE IMPLIED WARRANTIES # #OF MERCHANTABILITY AND FITNESS FOR A # #PARTICULAR PURPOSE ARE DISCLAIMED. IN NO # #EVENT SHALL THE COPYRIGHT OWNER OR # #CONTRIBUTORS BE LIABLE FOR ANY DIRECT, # #INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, # #OR CONSEQUENTIAL DAMAGES (INCLUDING, # #BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE # #GOODS OR SERVICES; LOSS OF USE, DATA, OR # #PROFITS; OR BUSINESS INTERRUPTION) HOWEVER # #CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER # #IN CONTRACT, STRICT LIABILITY, OR TORT # #(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING # #IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, # #EVEN IF ADVISED OF THE POSSIBILITY OF SUCH # #DAMAGE. # #***********************************************# #***********************************************# # TODO Make this script GPL for re-release # TODO Check for already running process for each user # TODO RS - more involved kill and user checks, ties with PID # TODO RS - hide killall output, or fix kill and PID hlds_comment="hlds_user" halfd="/usr/local/bin/halfd" rc_failed="1" # ----------------------------------------------------- # # check for root # # ----------------------------------------------------- # if [ ! "$UID" -eq 0 ] # Will the real "root" please stand up? then echo >&2 "Will the real \"root\" please stand up? (You have to be root to run this)" exit 67 fi # ----------------------------------------------------- # # get_hlds_users () # # Gets all users in /etc/passwd that is an hlds user. # # Looks for "hlds_user" in the comment field of passwd. # # Returns: List of users that run hlds. # # ----------------------------------------------------- # get_hlds_users () { grep -w $hlds_comment /etc/passwd |awk -F : '{ print $1 }' } # ----------------------------------------------------- # # get_user_home () # # Gets the home directory of a user # # Looks for "user" in passwd file, grabs home field # # Takes: Username to look for # # Returns: Home directory of user passed # # ----------------------------------------------------- # get_user_home () { if [ -z "$1" ] # Did a user get passed to get_user_home ? then echo >&2 "No user got passed to this get_user_home... what the hell did we break?" exit 1 fi if [ ! $(awk -F : "/^$1/ { print \$6 }" /etc/passwd) ] # Does the user have a $HOME? then echo >&2 "Oh give $1 a home, where his hlds files may roam, and the snipers are not campy all day!" exit 1 fi awk -F : "/^$1/ { print \$6 }" /etc/passwd # After checking above, run again so that we return the home } # ----------------------------------------------------- # # start () # # Starts halfd process for all users, or specified user # # Takes a username or nothing as an argument. # # Returns: 0 on success, !0 on exit # # ----------------------------------------------------- # start () { # ----------------------------------------------------- # # check halfd # # ----------------------------------------------------- # if [ ! -x $halfd ] # Can we execute halfd ? then echo >&2 "We can't execute halfd.. what did you do Rob?" exit 1 fi # ----------------------------------------------------- # # case start with no specified user, starts all users # # ----------------------------------------------------- # if [ ! $1 ] then # ----------------------------------------------------- # # cycles through users found in get_hlds_users () and # # starts the halfd process for them. # # ----------------------------------------------------- # for user in `get_hlds_users` # Get users from the passwd file do user_home=`get_user_home "$user"` if [ ! -d $user_home/hlds_l ] # Does the user have a hlds_l directory? then echo >&2 "User's hlds_l directory doesn't exist! Not starting for user: $user" continue # Skip the rest, go on to the next user. fi if [ ! -r $user_home/.game_type ] # Does the user have a set gametype? then echo >&2 "Can't read gametype file! Not starting user: $user" continue # Skip the rest, go on to the next user. fi read game <$user_home/.game_type # Get the gametype from the user's file case "$game" in # Test to make sure that game_type is a valid type. cstrike|dod|firearms|tfc|ns ) ;; # If it matches, just break out of the case * ) echo >&2 "Invalid game type! Beat the user! Not starting for user: $user"; continue ;; # Skip the rest, go on to the next user. esac su -l $user -c "$halfd -g $game -d $user_home/hlds_l/ &" # Starts halfd echo "Starting halfd for $user, game type: $game" echo done # ----------------------------------------------------- # # cycles through users found in get_hlds_users () and # # and checks for the requested user # # if the user is found, and passes directory and game # # checks, starts halfd for that user only # # ----------------------------------------------------- # else for user in `get_hlds_users` # Get users from the passwd file do if [ $1 = $user ] then user_home=`get_user_home "$user"` if [ ! -d $user_home/hlds_l ] # Does the user have a hlds_l directory? then echo >&2 "User's hlds_l directory doesn't exist! Not starting for user: $user" continue fi if [ ! -r $user_home/.game_type ] # Does the user have a set gametype? then echo >&2 "Can't read gametype file! Not starting user: $user" continue fi read game <$user_home/.game_type # Get the gametype from the user's file case "$game" in # Test to make sure that game_type is a valid type. cstrike|dod|firearms|tfc|ns ) ;; # If it matches, just break out of the case * ) echo >&2 "Invalid game type! Beat the user! Not starting for user: $user"; continue ;; # Skip the rest, go on to the next user. esac su -l $user -c "$halfd -g $game -d $user_home/hlds_l/ &" # Starts halfd echo "Starting halfd for $user, game type: $game" echo err_ck1="1" fi done if [ ! $err_ck1 ] then echo >&2 "No such user, or failed user $1." fi fi } # ----------------------------------------------------- # # stop () # # cycles through users found in get_hlds_users () and # # stop the halfd process for them. # # Takes a user name as an argument. # # Returns 0 on success, !0 on failure # # ----------------------------------------------------- # stop () { # ----------------------------------------------------- # # functions for stop all. stop alone returns error to # # prevent acidental hosing of all users # # ----------------------------------------------------- # if [ ! $1 ] then echo >&2 "Please specify user name or all. Use list to list registered users" elif [ $1 = "all" ] then for user in `get_hlds_users` # Get users from the passwd file do su -l $user -c "killall halfd" su -l $user -c "killall hlds" echo "Stopping Halfd and HLDS for user $user" echo done else # ----------------------------------------------------- # # stop one user # # ----------------------------------------------------- # for user in `get_hlds_users` # Get users from the passwd file do if [ $1 = $user ] then su -l $user -c "killall halfd" || return=$rc_failed su -l $user -c "killall hlds" || return=$rc_failed echo "Stopping Halfd and HLDS for user $user" err_ck1="1" fi done # ----------------------------------------------------- # # check to see if we found a user, report a fat finger # # or invalid user name # # ----------------------------------------------------- # if [ ! $err_ck1 ] then echo >&2 "No such user: $1, use `basename $0` list" fi fi } # ----------------------------------------------------- # # restart () # # cycles through users found in get_hlds_users () and # # restarts the halfd process for them. # # Takes a username as an argument. # # Returns 0 on success, !0 on error. # # ----------------------------------------------------- # restart () { # ----------------------------------------------------- # # functions for restart all. restart alone returns err # # prevent acidental hosing of all users # # ----------------------------------------------------- # if [ ! $1 ] then echo >&2 "Please specify user name or all. Use list to list registered users" elif [ $1 = "all" ] then $0 stop all && $0 start || return=$rc_failed # ----------------------------------------------------- # # restart one user # # ----------------------------------------------------- # else for user in `get_hlds_users` # Get users from the passwd file do if [ $1 = $user ] then $0 stop $2 && $0 start $2 || return=$rc_failed err_ck1="1" fi done # ----------------------------------------------------- # # check to see if we found a user, report a fat finger # # or invalid user name # # ----------------------------------------------------- # if [ ! $err_ck1 ] then echo >&2 "No such user, use `basename $0` list" fi fi } # ----------------------------------------------------- # # list () # # list users, we all forget ;) # # ----------------------------------------------------- # list () { for user in `get_hlds_users` # Get users from the passwd file do echo $user done } # ----------------------------------------------------- # # usage () # # list the possible usage of this file # # ----------------------------------------------------- # usage () { echo "Usage: `basename $0` {start|stop|restart|list} start and stop take a username as an argument. This will start/top halfd/hlds for just that user." exit 1 } # ----------------------------------------------------- # # Main switch. This is where we decide what to do # # ----------------------------------------------------- # case "$1" in start) if [ $2 ] then start "$2" else start fi ;; stop) if [ $2 ] then stop "$2" else stop fi ;; restart) if [ $2 ] then restart "$2" else restart fi ;; list) list ;; *) usage ;; esac exit 0 ########################################### # Changelog # # Wed Jan 15 2003 Jesse Keating 0.04 # - Major clean up, code alignment stuff like that # - Made all our cases actual functions, looks much cleaner, easier to alter later # - Made all error echo's go to stderr # - Added "j2Solutions" to copyright... not sure if this is all that is needed # - Bumped version, due to my happy hacking # # Tue Jan 14 2003 Robert Sanders 0.03 # - started init work, start functions # - added if logic to determine users or all # - added stop, restart functions # - realized user list is needed, added list functions # - added err_ck1 to report a non-existant user request # - updated start functions with options to specify user # - added heavy comments, maybe to heavy.. # - updated stop to report users # - added BSD style license # # Tue Jan 14 2003 Jesse Keating 0.02 # - forgot a fi... silly me. # - needed to wrap the get_hlds_users in backticks in the for loop. # - started a TODO list at the top # - return not needed in the get_hlds_users function.. silly me. # - grr, must remove backticks as well in get_hlds_users # - various bugfixes, seems to atleast function now. # # Mon Jan 13 2003 Jesse Keating 0.01 # - initial build. Hope it works (;