From ef3243ff91c6a97c248d74a4c7026ae1e6a38f51 Mon Sep 17 00:00:00 2001 From: Jonas Smedegaard Date: Thu, 15 Apr 2004 22:30:04 +0000 Subject: New script localuserconfig to contain user-editable parts of adduser.local and user-init. Currently contains only new code to set .winpassword for access to remote SMB share. --- localuserconfig | 492 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 492 insertions(+) create mode 100755 localuserconfig diff --git a/localuserconfig b/localuserconfig new file mode 100755 index 0000000..3a3f969 --- /dev/null +++ b/localuserconfig @@ -0,0 +1,492 @@ +#!/bin/sh +# +# /usr/local/bin/localuserconfig +# Copyright 2004 Jonas Smedegaard +# +# $Id: localuserconfig,v 1.1 2004-04-15 22:30:04 jonas Exp $ +# +# Set/change local account settings +# +# TODO: Use the following syntax to add info to .smbpasswd +# grep -q SomeOption ~/file || echo "line with SomeOption and such" >> ~/file +# +# TODO: Move relevant stuff from user-init and make it use this instead +# TODO: Use getopt, and implement --help +# TODO: Implement runmodes noninteractive and force (in addition to the default: interactive) +# TODO: Runmode noninteractive by default if no tty attached +# TODO: Implement verbosity levels (0=quiet 1=oneliner 2=default 3=chatty 4=debug) + +set -e + +# config (edit /etc/local/users.conf to override) + +# which are user accounts (adduser values are used if empty) +first_uid="" +last_uid="" + +do_quota="no" # Manage disk quota +do_distrib="no" # Distributed shares (software archive) +do_personal="no" # Personal shares (mac, pc, public_html) +do_xchange="no" # Group-readable shares +do_public="no" # Public share (web homepage) +do_mac="no" # AppleShare-optimized share (netatalk) +do_pc="no" # SMB-ptimized share (Samba) +do_server="no" # Personal share on remote SMB server + +quota_roots="" # space-delimited list of disk devices +quota_soft="100000" +quota_hard="1000000" +quota_newstyle="yes" # Woody used a different syntax... + +xchange_root="xchange" +xchange_sharedroot="/home/XCHANGE" + +mac_root="mac" + +pc_root="pc" + +server_name="SERVER" # SMB name of remote server +server_desc="remote server" +server_root="server" +server_conf="/etc/security/pam_mount.conf" +server_userconf=".winpassword" + +### No servicable parts below this line! ### + +if [ -e /etc/adduser.conf ]; then + . /etc/adduser.conf +else + echo "/etc/adduser.conf missing. Exiting..." + exit 1 +fi + +[ -r /etc/local/users.conf ] && . /etc/local/users.conf + +# Flags used internally +root_required="no" +runmode="interactive" + +user="`id -u -n`" +uid="`id -u`" +HOME="`getent passwd \"$user\" | awk -F: '{print $6}' | head -1`" +#TODO: Allow root to pass the above as options + +# Safety checks (disable silently - the user can't correct it anyway) + +[ "$do_mac" = "yes" -a -n "$mac_root" ] || do_mac="no" +[ "$do_pc" = "yes" -a -n "$pc_root" ] || do_pc="no" +[ "$do_xchange" = "yes" -a -n "$xchange_root" ] || do_xchange="no" +[ "$do_server" = "yes" -a -n "$server_root" ] || do_server="no" +#TODO: do a loop instead for the above + +# only do user accounts (checked against /etc/adduser.conf values) +[ -n "$first_uid" ] || first_uid="$FIRST_UID" +[ -n "$last_uid" ] || last_uid="$LAST_UID" +[ "$uid" -ge "$FIRST_UID" -a "$uid" -le "$LAST_UID" ] || exit 0 +#TODO: check if above is numeric +#TODO: Always use adduser values as strict outer limits + +if [ -z "$HOME" ]; then + echo "Error: Unable to resolve home of user $user!" + exit 1 +fi +if [ ! -d "$HOME" ]; then + echo "Error: Home of user $user doesn't exist: \"$HOME\"!" + exit 1 +fi + +if [ "$do_server" = "yes" ]; then + server_edit="1" + server_username=$user + if [ -r "$HOME/$server_userconf" ]; then + server_username="$(grep '^username' $HOME/$server_userconf | awk -F= '{print $2}' | head -1 | awk '{print $1}')" + server_password="$(grep '^password' $HOME/$server_userconf | awk -F= '{print $2}' | head -1 | awk '{print $1}')" + fi + if [ -n "$server_username" -o -n "$server_password" ]; then + server_edit="" + echo -n "Account info for $server_desc already exists. Edit (Y/n)? " + read server_overwrite + case $server_overwrite in + y|Y|"") + server_edit="1" + ;; + esac + fi + if [ "$server_edit" = "1" ]; then + if [ -n "$server_username" ]; then + echo -n "Username on $server_desc ($server_username): " + else + echo -n "Username on $server_desc: " + fi + read server_username_new + if [ -n "$server_username_new" ]; then + server_username="$server_username_new" + fi + echo -n "Password on $server_desc: " + read -s server_password + echo + echo -n "Password once more: " + read -s server_password_again + echo + if [ -n "$server_username" -a "$server_password" = "$server_password_again" ]; then + echo "username = $server_username" > $HOME/$server_userconf + echo "password = $server_password" >> $HOME/$server_userconf + else + echo "Setting server login info failed: problem getting either username or password" + fi + fi + if grep -v -q "^volume $user " "$server_conf"; then + root_required="yes" + fi +fi + +if [ "$root_required" = "yes" ]; then + echo "Note: Some of the current setup requires action by systems administrator" +#TODO: send email to root, unless invoked by root +#TODO: Collect actual items needing attention, to print and include in email +fi + +exit 0 +#FIXME: The remaining is to be implemented (lifted from user-init) + +#if [ -x /etc/local/quota.sh ]; then +# /etc/local/quota.sh $user +# fi +[ $quota_soft ] || quota_soft="0" +[ $quota_hard ] || quota_hard="0" +for quota_root in $quota_roots; do + if [ $quota_newstyle ]; then + setquota $user $quota_soft $quota_hard 0 0 $quota_root + else + setquota $user $quota_root $quota_soft $quota_hard 0 0 + fi +done + +mkdir -p $HOME/mail +if [ "$USE_MBOX" ]; then + touch $HOME/mail/mbox +elif [ -f $HOME/mail/mbox -a ! -s $HOME/mail/mbox ]; then + rm -f $HOME/mail/mbox +fi + +if [ $NETATALK ]; then + mkdir -p $HOME/$mac_root +fi +if [ $SAMBA ]; then + mkdir -p $HOME/$pc_root +fi + +if [ $XCHANGE ]; then + mkdir -p $xchange_sharedroot/users/root/$user +fi + +if [ $PUBLIC ]; then + mkdir -p $HOME/public_html +fi + +chown $user: $HOME +chmod u=rwX,go=rX $HOME + +# Mail handling +chown -R $user: $HOME/mail +chmod -R u=rw,go=,u+X $HOME/mail +if [ -f $HOME/.mailboxlist ]; then + chown $user: $HOME/.mailboxlist + chmod 0640 $HOME/.mailboxlist +fi +if [ -f $HOME/.forward ]; then + chown $user: $HOME/.forward + chmod 0640 $HOME/.forward +fi +if [ -f /var/mail/$user ]; then + chown $user:mail /var/mail/$user + chmod ug=rw,o= /var/mail/$user +elif [ -f /var/spool/mail/$user ]; then + chown $user:mail /var/spool/mail/$user + chmod ug=rw,o= /var/spool/mail/$user +fi + +# MySQL handling +if [ -f $HOME/.my.cnf ]; then + chown $user: $HOME/.my.cnf + chmod 0600 $HOME/.my.cnf +fi + +# Mac dir permissions +if [ -d $HOME/$mac_root ]; then + chown -R $user: $HOME/$mac_root + chmod -R u=rw,g=r,o=,ug+X $HOME/$mac_root + rm -rf $HOME/$mac_root/Network\ Trash\ Folder + mkdir $HOME/$mac_root/Network\ Trash\ Folder + chown nobody: $HOME/$mac_root/Network\ Trash\ Folder + chmod a= $HOME/$mac_root/Network\ Trash\ Folder +fi + +# PC dir permissions +if [ -d $HOME/$pc_root ]; then + chown -R $user: $HOME/$pc_root + chmod -R u=rw,g=r,o=,ug+X $HOME/$pc_root +fi + +# Exchange dir permissions +if [ -d $xchange_sharedroot/users/root/$user ]; then + chown -R $user:users $xchange_sharedroot/users/root/$user + chmod -R g=r,g+X $xchange_sharedroot/users/root/$user + if [ -e "x$HOME/$xchange_root" ]; then + if [ -L "x$HOME/$xchange_root" ]; then + ln -sf $xchange_sharedroot/users/root/$user $HOME/$xchange_root + else + echo "ERROR: $HOME/$xchange_root exists already. Leaving it as is..." + fi + else + ln -s $xchange_sharedroot/users/root/$user $HOME/$xchange_root + fi +fi + +# Public dir permissions +if [ -d $HOME/public_html ]; then + chown -R $user: $HOME/public_html + chmod -R u+rX,go=r,go+X $HOME/public_html + if [ $NETATALK ]; then + rm -rf $HOME/public_html/Network\ Trash\ Folder + mkdir $HOME/public_html/Network\ Trash\ Folder + chown nobody: $HOME/public_html/Network\ Trash\ Folder + chmod a= $HOME/public_html/Network\ Trash\ Folder + fi +fi + +# Fileshares: /shares./// +# : Either mac or win depending on which of netatalk and samba provides r/w access to the shares +# : Group with write access to the share (usually the default group of the owner) +# : Either rwgroup or secondary group with read-only access to the share +# owner must be member of both groups, and rwgroup members must also be members of rogroup +find "$HOME" -mindepth 1 -maxdepth 1 -type d -print | egrep "^$HOME/shares\." | (while read thisdir; do + sharetype="`basename \"$thisdir\" | awk -F. '{print $2}'`" + # Define dir and file exceptions + case "$sharetype" in + mac) + dirs_world_rw_create='.AppleDB' + dirs_group_rw_create='.AppleDesktop/Temporary Items/TheFindByContentFolder' + dirs_group_ro_create='TheVolumeSettingsFolder' + dirs_group_ro_update='.AppleDouble' + files_group_ro_update=':2eDS_Store' + dirs_no_access_purge='Network Trash Folder' + ;; + win) + ;; + *) + continue + ;; + esac + exceptions="$dirs_world_rw_create/$dirs_group_rw_create/$dirs_group_ro_create/$dirs_group_ro_update/$files_group_ro_update/$dirs_no_access_purge" + exception_dirs_create="$dirs_world_rw_create/$dirs_group_rw_create/$dirs_group_ro_create" + chown "$user": "$thisdir" + chmod a=rX "$thisdir" + find "$thisdir" -mindepth 1 -maxdepth 1 -type d -print | (while read thisdir; do + rogroup="`basename \"$thisdir\"`" + chown "$user":"$rogroup" "$thisdir" + chmod ug=rX,o= "$thisdir" + find "$thisdir" -mindepth 1 -maxdepth 1 -type d -print | (while read thisdir; do + rwgroup="`basename \"$thisdir\"`" + chown "$user":"$rwgroup" "$thisdir" + chmod a=rX,g+s "$thisdir" + find "$thisdir" -mindepth 1 -maxdepth 1 -type d -print | (while read thisdir; do + sharename="`basename \"$thisdir\"`" + chown "$user":"$rwgroup" "$thisdir" + chmod u=rw,go=r,a+X,g+s "$thisdir" + ifs="$IFS" + # Set default permissions + find "$thisdir" -mindepth 1 -maxdepth 1 -print | (while read thisdir; do + item="`basename \"$thisdir\"`" + IFS="/"; for exception in $exceptions; do IFS="$ifs"; + if [ "$item" = "$exception" ]; then + continue 2 + fi + done + chgrp -R "$rwgroup" "$thisdir" + chmod -R ug=rw,o=r,a+X,g+s "$thisdir" + done) + # Handle exception dirs to be created if not existing + IFS="/"; for dir in $exception_dirs_create; do IFS="$ifs"; + if [ ! -d "$thisdir/$dir" ]; then + rm -f "$thisdir/$dir" + fi + if [ ! -e "$thisdir/$dir" ]; then + mkdir "$thisdir/$dir" + fi + chown "$user":"$rwgroup" "$thisdir/$dir" + done + IFS="/"; for dir in $dirs_world_rw_create; do IFS="$ifs"; + if [ "$rogroup" = "$rwgroup" ]; then + chmod -R ug=rw,o=r,a+X,g+s "$thisdir/$dir" + else + chmod -R a=rw,a+X,g+s "$thisdir/$dir" + fi + done + IFS="/"; for dir in $dirs_group_rw_create; do IFS="$ifs"; + chmod -R ug=rw,o=r,a+X,g+s "$thisdir/$dir" + done + IFS="/"; for dir in $dirs_group_ro_create; do IFS="$ifs"; + chmod -R u=rw,go=r,a+X,g+s "$thisdir/$dir" + done + # Handle exception dirs to be updated if already there + IFS="/"; for dir in $dirs_group_ro_update; do IFS="$ifs"; + if [ -e "$thisdir/$dir" ]; then + chmod u=rw,go=r,a+X,g+s "$thisdir/$dir" + fi + done + # Handle exception files to be updated if already there + IFS="/"; for file in $files_group_ro_update; do IFS="$ifs"; + if [ -e "$thisdir/$file" ]; then + chmod u=rw,go=r,g+s "$thisdir/$file" + fi + done + # Handle exception dirs to be purged and recreated + IFS="/"; for dir in $dirs_no_access_purge; do IFS="$ifs"; + rm -rf "$thisdir/$dir" + mkdir -m a= "$thisdir/$dir" + chown nobody: "$thisdir/$dir" + done + IFS="$ifs" + done) + done) + done) +done) + +# Deprecated share permissions +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/shares_win"`; do + chgrp -R $user $dir + chmod -R u=rw,g=rw,o=,ug+X,g+s $dir +done +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/shares_mac"`; do + chgrp -R $user $dir + chmod -R u=rw,g=rw,o=,ug+X,g+s $dir + rm -rf $dir/Network\ Trash\ Folder + mkdir $dir/Network\ Trash\ Folder + chown nobody: $dir/Network\ Trash\ Folder + chmod a= $dir/Network\ Trash\ Folder +done + +# Ftp shares permissions +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/ftp_$USER$"`; do + chgrp -R $user $dir + chmod -R ug=rw,o=r,a+X,g+s $dir + rm -rf $dir/Network\ Trash\ Folder + mkdir $dir/Network\ Trash\ Folder + chown nobody: $dir/Network\ Trash\ Folder + chmod a= $dir/Network\ Trash\ Folder +done +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/ftp_${USER}_ro$"`; do + chown -R $user: $dir + chmod -R u=rw,go=r,a+X $dir + rm -rf $dir/Network\ Trash\ Folder + mkdir $dir/Network\ Trash\ Folder + chown nobody: $dir/Network\ Trash\ Folder + chmod a= $dir/Network\ Trash\ Folder +done + +# Web shares permissions +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/web_"`; do + chown -R $user: $dir +# chmod -R u=rw,go=r,a+X $webdir +#TODO: Only cgi scripts (.cgi and .pl) should be executable + chmod -R u+rw,go+r,a+X $dir + # leftover from ancient times with another policy + if [ $NETATALK ]; then + rm -rf $dir/Network\ Trash\ Folder + fi +done + +# Web shares permissions +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/websites"`; do + chown root: $dir + chmod a=r,u+w,a+X $dir +done +for dir in `find $HOME -mindepth 2 -maxdepth 2 -type d | egrep "^$HOME/websites/"`; do + chown -R $user: $dir +# chmod -R u=rw,go=r,a+X $webdir +#TODO: Only cgi scripts (.cgi and .pl) should be executable + chmod -R u+rw,go+r,a+X $dir + # leftover from ancient times with another policy + if [ $NETATALK ]; then + rm -rf $dir/Network\ Trash\ Folder + fi +done +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/webscripts"`; do + chown root: $dir + chmod a=r,u+w,a+X $dir +done +for dir in `find $HOME -mindepth 2 -maxdepth 2 -type d | egrep "^$HOME/webscripts/"`; do + chown -R $user: $dir +# chmod -R u=rw,go=r,a+X $webdir +#TODO: Only cgi scripts (.cgi and .pl) should be executable + chmod -R u+rw,go+r,a+X $dir +done +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/webdata"`; do + chown $user: $dir + chmod a=r,u+w,a+X $dir +done +for dir in `find $HOME -mindepth 2 -maxdepth 2 -type d | egrep "^$HOME/webdata/"`; do + chown -R $user: $dir + chmod -R u=rw,go=,u+X $dir +done +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/webshareddata"`; do + chown $user: $dir + chmod a=r,u+w,a+X $dir +done +for dir in `find $HOME -mindepth 2 -maxdepth 2 -type d | egrep "^$HOME/webshareddata/"`; do + chown -R $user: $dir + chmod -R u=rw,go=r,a+X $dir +done +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/webphpsites"`; do + chown root: $dir + chmod u=rw,go=r,a+X $dir +done +for dir in `find $HOME -mindepth 2 -maxdepth 2 -type d | egrep "^$HOME/webphpsites/"`; do + chown -R $user:www-data $dir +# chmod -R ug=rw,o=r,a+X $dir + chmod -R ug=rw,o=,ug+X $dir +done +for dir in `find $HOME -mindepth 1 -maxdepth 1 -type d | egrep "^$HOME/webphpdata"`; do + chown root: $dir + chmod a=r,u+w,a+X $dir +done +for dir in `find $HOME -mindepth 2 -maxdepth 2 -type d | egrep "^$HOME/webphpdata/"`; do + chown -R $user:www-data $dir + chmod -R ug=rw,o=,ug+X $dir +done + +# Dummy user restrictions +if [ -n "$REALUSERS_GROUPNAME" -a -n "$DUMMYSHAREDIR" -a -n "$DUMMYSHAREOWNER" -a -n "$DUMMYSHARENAME" ]; then + [ -e $DUMMYSHAREDIR/$user ] \ + || mkdir $DUMMYSHAREDIR/$user + chown $DUMMYSHAREOWNER: $DUMMYSHAREDIR/$user + chmod u=rw,go=r,a+X $DUMMYSHAREDIR/$user + if [ -e $HOME/$DUMMYSHARENAME ]; then + if [ -L $HOME/$DUMMYSHARENAME ]; then + ln -sf $DUMMYSHAREDIR/$user $HOME/$DUMMYSHARENAME + chown $user: $HOME/$DUMMYSHARENAME + else + echo "WARNING: $HOME/$DUMMYSHAREDIR exists already. Leaving it as is..." + fi + else + ln -s $DUMMYSHAREDIR/$user $HOME/$DUMMYSHARENAME + chown $user: $HOME/$DUMMYSHARENAME + fi + if [ -n "$DUMMYAPACHECFG" -a -n "$DUMMYAPACHESHAREDIR" ]; then + if [ -f /etc/apache/include.d/$DUMMYAPACHECFG -a -x /etc/init.d/apache ]; then + if [ -e /etc/apache/include.d/$DUMMYAPACHECFG-$user ]; then + echo "/etc/apache/include.d/$DUMMYAPACHECFG-$user exists already. Ignoring..." + else + echo "# Created automatically by adduser.local + + + require user $user + +" \ + > /etc/apache/include.d/$DUMMYAPACHECFG-$user + root_required="yes" + fi + fi + fi +fi -- cgit v1.2.3