Path: utzoo!utgpu!jarvis.csri.toronto.edu!cs.utexas.edu!usc!apple!motcsd!hpda!hpcupt1!hpisod2!decot From: decot@hpisod2.HP.COM (Dave Decot) Newsgroups: comp.unix.questions Subject: Re: Friendly UMASK wanted Message-ID: <10650080@hpisod2.HP.COM> Date: 3 Feb 90 00:31:16 GMT References: <2069@syma.sussex.ac.uk> Organization: Hewlett Packard, Cupertino Lines: 196 > X#!/bin/sh > X# @(#)mask 1.0 90/02/02 Maarten Litmaath > X# mask g-wx,o= > X# mask -s This does not conform to POSIX.2, in that it does not have an -o option to force octal output, the + operation does not seem to work (it always sets the involved mode parts to 0, regardless of the previous value), and most importantly, the modes are interpreted upside down. That is, this script assumes: $ umask -o 022 $ umask -s u=,g=w,o=w POSIX.2 requires: $ umask -o 022 $ umask -s u=rwx,g=rx,o=rx $ umask o+w,g-r $ umask -s u=rwx,g=x,o=rwx $ umask -o 0060 Here's a version of Maarten's script that fixes the above problems. The default output style when no arguments are present is implementation-defined, as far as POSIX.2 is concerned, but I prefer symbolic output by default, so my script does that. Some versions of sh don't understand that "[-+=])" as a case label means to test for -, but rather try to do something stupid with the - (probably ranges), so I also changed that. Dave ---------------- # This is a shell archive. Remove anything before this line, # then unpack it by saving it in a file and typing "sh file". # # Wrapped by Dave Decot on Fri Feb 2 16:21:42 1990 # # This archive contains: # mask # unset LANG echo x - mask cat >mask <<'@EOF' #!/bin/sh # @(#)mask 1.0 90/02/02 Maarten Litmaath # @(#)mask 1.1 90/02/03 Dave Decot # mask g-wx,o= # mask -s USAGE=" name=`basename $0` echo 'Usage: '\$name' mode' >&2 echo ' or: '\$name' [-s|-o]' >&2 echo 'mode: a symbolic string like \`g-wx,o='\\' >&2 echo ' or: the equivalent octal number' >&2 echo 'see chmod(1)' >&2 exit 1 " case $# in 0) arg="-s" ;; 1) arg="$1" ;; *) eval "$USAGE" ;; esac modes_7=___ modes_6=__x modes_5=_w_ modes_4=_wx modes_3=r__ modes_2=r_x modes_1=rw_ modes_0=rwx expr x"$arg" : 'x.*[^0-9]' > /dev/null || { echo umask "$arg" exit 0 } case "$arg" in -s) style=symbolic ;; -o) style=octal ;; -[rwx]*|x-*) ;; -*) eval "$USAGE" ;; x*) ;; esac set `umask \ | sed -e 's/^0*//' -e 's/^$/0/' -e 's/^.$/0&/' -e 's/^..$/0&/' -e 's/./& /g'` output=`eval echo "u="'$'"modes_$1,g="'$'"modes_$2,o="'$'"modes_$3"` case $style in symbolic) eval echo echo "$output" | tr -d _ exit 0 ;; octal) echo umask exit 0 ;; esac set -- `echo $output | sed -e "s/./& /g" -e "s/[=,ugo]//g"` for i in u g o do for j in r w x do eval ${i}_${j}=$1 shift done done set -- "$arg" set ` echo x"$1" | sed -e 's/.//' -e 's/^[-+=]/a&/' \ -e 's/,\\([-+=]\\)/,a\\1/g' \ -e 's/[-=],/-rwx,/g' -e 's/[-=]$/-rwx/' \ -e 's/+,/+rwx,/g' -e 's/+$/+rwx/' -e 's/./& /g' -e 's/$/,/' ` groups= perms= for i do case $i in [ugo]) groups="$groups $i" ;; a) groups="u g o" ;; -) op=$i ;; [+=]) op=$i ;; [rwx]) perms="$perms $i" ;; ,) for group in $groups do case $op in =) eval ${group}_r=_ eval ${group}_w=_ eval ${group}_x=_ esac for perm in $perms do case $op in -) bit=_ ;; *) bit=$perm ;; esac eval ${group}_$perm=$bit done done groups= perms= ;; *) eval "$USAGE" esac done ___=7 __x=6 _w_=5 _wx=4 r__=3 r_x=2 rw_=1 rwx=0 eval echo umask 0\${$u_r$u_w$u_x}\${$g_r$g_w$g_x}\${$o_r$o_w$o_x} @EOF chmod 755 mask exit 0