Here's a quick and dirty script I wrote several years ago, back when I
couldn't code a perl script to save my life...

Back by popular demand...

This is a shell script, but it runs perl to do some of the more
complicated stuff.  Eventually I'll re-write it in perl.


Shawn said:
> On Mon, 18 Aug 2003 20:30:22 -0500 (CDT)
> "Wayne Johnson" <waynej at dccmn.com> wrote:
>
>> If you read the manual closer, you'll see that -p requires the
>> encrypted password.  You need to call crypt with your password, and
>> pass the output to useradd.  At least thats the way it works on
>> RedHat.
>>
>> Unfortunatly, AFAIK, there is no shell script access to crypt. I
>> created a perl script to frontend useradd.
>>
>
> I didn't look into the password part that much on the man page.
> Although, I've got a need for it in the future.
>
> Any chance you can post the perl script?
>
>
> --
> Shawn
>
>   The difficult we do today; the impossible take a little longer.
>
>   Ne Obliviscaris --  "Forget Not"


-------------- next part --------------
# This script sets up a user account.  It picks a user name, creates the user, 
# and sets the password.  User information is read from a file, or stdin.

# File format is:
# User id (student id)
# User first name
# User last name

test=0
samba=0
while [ $# -gt 0 ]; do
  case "$1" in
  -t) test=1;;
  -S) samba=1;;
  -h)
    echo "$0 [-t] [-S] [useradd_options]"
    echo "      -t Don't execute, just print commands"
    echo "      -S Do smbpasswd"
    exit ;;
  *) options="$options $1";;
  esac
  shift
done

# This subroutine scans the passwd file to see if a user name ($id) exists
function checkid() {
grep -i "^$1:" /etc/passwd >/dev/null
return
}

# Subroutine to pick a password
function mkpasswd() {
perl -e '
open(DICT, "/usr/share/dict/words");

# Find size of dictionary
($dev,$ino,$mode,$nlink,$uid,$gid,$rdev,$size,
       $atime,$mtime,$ctime,$blksize,$blocks)
	   = stat(DICT);  

$length=0;
# Keep picking until we find one between 6 and 10 characters
while ($length < 6 or $length > 10) {
  seek(DICT, rand($size), 0);
  <DICT>;
  $_=<DICT>;
  chomp();
  $line=$_;
  print STDERR $line;
  $line=$line.int(rand(89)+10);
  $length=length($line);
}

#return password
print $line;'
}

# Subroutine to create crypt salt.
function salt() {
perl -e '
$table="abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789./";
print(substr($table, rand(28)).substr($table, rand(28)));'
}

# Subroutine to encrypt the password.  See crypt(3).
function crypt() {
	perl -e 'print(crypt($ARGV[0], $ARGV[1]));' $1 $2
}

function flast() {
  echo `expr "$1" : "\(.\)"``expr "$2" : "\(.\{1,7\}\)"`
}

function firstl() {
  echo `expr "$1" : "\(.\{1,7\}\)"``expr "$2" : "\(.\)"`
}

if [ -t 0 ]; then
  echo "Enter User-id First-Name Last-Name (ctrl-d to end)"
fi

while read id fname lname username passwd; do

  if [ `expr "$id" : "[0-9]*$"` -eq 0 ]; then 
    echo "Invalid user id $id.  Must be numeric"
    exit
  fi

  if [ $id -lt 0 -o $id -gt 65535 ]; then 
    echo "Invalid user id $id.  Must be in the range 0-65535"
    exit
  fi

  if [ `expr "$fname" : "[a-zA-Z]*$"` -eq 0 ]; then
    echo "Invalid first name $fname.  Must be alphabetic"
    exit
  fi

  if [ `expr "$lname" : "[a-zA-Z]*$"` -eq 0 ]; then
    echo "Invalid last name $lname.  Must be alaphabetic"
    exit
  fi

  if [ -z "$username" ]; then
    # create hash for user name
    # First try 7 characters of first name and first character of last name
    username=`flast $fname $lname`

    if checkid $username; then
      # next try first characters of first name and first 7 characters of last name
      username=`firstl $fname $lname`
      if checkid $username; then

	# Well, lets try a number after the first name
	x=1
	while checkid $fname$x; do
	  x=$(($x+1))
	done
	username=$fname$x
      fi
    fi
  fi

  username=`echo $username | tr "[A-Z]" "[a-z]"`

  if grep ".*:.*:$id:" /etc/passwd >/dev/null; then
    echo "user id $id is already in use"
    exit
  fi

  if [ -z "$passwd" ]; then
    # perl script to pick a random password
    passwd=`mkpasswd`
  fi

  # Pick a random salt value for crypt
  salt=`salt`

  # Now we need to crypt(3) the password
  epasswd=`crypt $passwd $salt`

  cmd="/usr/sbin/useradd -u $id -m -c \"$fname $lname\" -p \"$epasswd\" $options $username"
  if [ "$test" = 1 ]; then 
	  echo "$cmd"
  else
	  eval $cmd
  fi
  if [ "$samba" = 1 ]; then
    cmd="/usr/bin/smbpasswd -a $username $passwd"
    if [ "$test" = 1 ]; then 
	    echo "$cmd"
    else
	    eval $cmd
    fi
  fi

  echo "$id	$fname $lname	$username	$passwd"

# loop till no more data
done