mirror of
https://github.com/fish-shell/fish-shell.git
synced 2024-11-30 14:24:35 +08:00
b85a8bbbfe
Makes it harder to cause issues with aliases, see fish-shell#2245
217 lines
3.9 KiB
Fish
217 lines
3.9 KiB
Fish
|
|
function __fish_umask_parse -d "Internal umask function"
|
|
# Test if already a valid octal mask, and pad it with zeros
|
|
if echo $argv | __fish_sgrep -E '^0?[0-7]{1,3}$' >/dev/null
|
|
set -l char_count (echo $argv| wc -c)
|
|
for i in (seq (math 5 - $char_count)); set argv 0$argv; end
|
|
echo $argv
|
|
else
|
|
# Test if argument really is a valid symbolic mask
|
|
if not echo $argv | __fish_sgrep -E '^(((u|g|o|a|)(=|\+|-)|)(r|w|x)*)(,(((u|g|o|a|)(=|\+|-)|)(r|w|x)*))*$' >/dev/null
|
|
printf (_ "%s: Invalid mask '%s'\n") umask $argv >&2
|
|
return 1
|
|
end
|
|
|
|
set -l implicit_all
|
|
|
|
# Insert inverted umask into res variable
|
|
|
|
set -l mode
|
|
set -l val
|
|
set -l tmp $umask
|
|
set -l res
|
|
|
|
for i in 1 2 3
|
|
set tmp (echo $tmp|cut -c 2-)
|
|
set -l char_count (echo $tmp|cut -c 1)
|
|
set res[$i] (math 7 - $char_count)
|
|
end
|
|
|
|
set -l el (echo $argv|tr , \n)
|
|
for i in $el
|
|
switch $i
|
|
case 'u*'
|
|
set idx 1
|
|
set i (echo $i| cut -c 2-)
|
|
|
|
case 'g*'
|
|
set idx 2
|
|
set i (echo $i| cut -c 2-)
|
|
|
|
case 'o*'
|
|
set idx 3
|
|
set i (echo $i| cut -c 2-)
|
|
|
|
case 'a*'
|
|
set idx 1 2 3
|
|
set i (echo $i| cut -c 2-)
|
|
|
|
case '*'
|
|
set implicit_all 1
|
|
set idx 1 2 3
|
|
end
|
|
|
|
switch $i
|
|
case '=*'
|
|
set mode set
|
|
set i (echo $i| cut -c 2-)
|
|
|
|
case '+*'
|
|
set mode add
|
|
set i (echo $i| cut -c 2-)
|
|
|
|
case '-*'
|
|
set mode remove
|
|
set i (echo $i| cut -c 2-)
|
|
|
|
case '*'
|
|
if not count $implicit_all >/dev/null
|
|
printf (_ "%s: Invalid mask '%s'\n") umask $argv >&2
|
|
return
|
|
end
|
|
set mode set
|
|
end
|
|
|
|
if not echo $perm| __fish_sgrep -E '^(r|w|x)*$' >/dev/null
|
|
printf (_ "%s: Invalid mask '%s'\n") umask $argv >&2
|
|
return
|
|
end
|
|
|
|
set val 0
|
|
if echo $i | __fish_sgrep 'r' >/dev/null
|
|
set val 4
|
|
end
|
|
if echo $i | __fish_sgrep 'w' >/dev/null
|
|
set val (math $val + 2)
|
|
end
|
|
if echo $i | __fish_sgrep 'x' >/dev/null
|
|
set val (math $val + 1)
|
|
end
|
|
|
|
for j in $idx
|
|
switch $mode
|
|
case set
|
|
set res[$j] $val
|
|
|
|
case add
|
|
set res[$j] (perl -e 'print( ( '$res[$j]'|'$val[$j]' )."\n" )')
|
|
|
|
case remove
|
|
set res[$j] (perl -e 'print( ( (7-'$res[$j]')&'$val[$j]' )."\n" )')
|
|
end
|
|
end
|
|
end
|
|
|
|
for i in 1 2 3
|
|
set res[$i] (math 7 - $res[$i])
|
|
end
|
|
echo 0$res[1]$res[2]$res[3]
|
|
end
|
|
end
|
|
|
|
function __fish_umask_print_symbolic
|
|
set -l res ""
|
|
set -l letter a u g o
|
|
|
|
for i in 2 3 4
|
|
set res $res,$letter[$i]=
|
|
set val (echo $umask|cut -c $i)
|
|
|
|
if contains $val 0 1 2 3
|
|
set res {$res}r
|
|
end
|
|
|
|
if contains $val 0 1 4 5
|
|
set res {$res}w
|
|
end
|
|
|
|
if contains $val 0 2 4 6
|
|
set res {$res}x
|
|
end
|
|
|
|
end
|
|
|
|
echo $res|cut -c 2-
|
|
end
|
|
|
|
function umask --description "Set default file permission mask"
|
|
|
|
set -l as_command 0
|
|
set -l symbolic 0
|
|
|
|
set -l options
|
|
set -l shortopt pSh
|
|
if not getopt -T >/dev/null
|
|
# GNU getopt
|
|
set longopt -l as-command,symbolic,help
|
|
set options -o $shortopt $longopt --
|
|
# Verify options
|
|
if not getopt -n umask $options $argv >/dev/null
|
|
return 1
|
|
end
|
|
else
|
|
# Old getopt, used on OS X
|
|
set options $shortopt
|
|
# Verify options
|
|
if not getopt $options $argv >/dev/null
|
|
return 1
|
|
end
|
|
end
|
|
|
|
set -l tmp (getopt $options $argv)
|
|
eval set opt $tmp
|
|
|
|
while count $opt >/dev/null
|
|
|
|
switch $opt[1]
|
|
case -h --help
|
|
__fish_print_help umask
|
|
return 0
|
|
|
|
case -p --as-command
|
|
set as_command 1
|
|
|
|
case -S --symbolic
|
|
set symbolic 1
|
|
|
|
case --
|
|
set -e opt[1]
|
|
break
|
|
|
|
end
|
|
|
|
set -e opt[1]
|
|
|
|
end
|
|
|
|
switch (count $opt)
|
|
|
|
case 0
|
|
if not set -q umask
|
|
set -g umask 113
|
|
end
|
|
if test $as_command -eq 1
|
|
echo umask $umask
|
|
else
|
|
if test $symbolic -eq 1
|
|
__fish_umask_print_symbolic $umask
|
|
else
|
|
echo $umask
|
|
end
|
|
end
|
|
|
|
case 1
|
|
set -l parsed (__fish_umask_parse $opt)
|
|
if test (count $parsed) -eq 1
|
|
set -g umask $parsed
|
|
return 0
|
|
end
|
|
return 1
|
|
|
|
case '*'
|
|
printf (_ '%s: Too many arguments\n') umask >&2
|
|
|
|
end
|
|
|
|
end
|