Per gli script di shell, a volte ho nel sorgente l'equivalente della sysexist.h
shell con i codici di uscita riservati alla shell (con prefisso S_EX_
), che ho chiamatoexit.sh
È fondamentalmente:
EX_OK=0 # successful termination
EX__BASE=64 # base value for error messages
EX_USAGE=64 # command line usage error
EX_DATAERR=65 # data format error
EX_NOINPUT=66 # cannot open input
EX_NOUSER=67 # addressee unknown
EX_NOHOST=68 # host name unknown
EX_UNAVAILABLE=69 # service unavailable
EX_SOFTWARE=70 # internal software error
EX_OSERR=71 # system error (e.g., can't fork)
EX_OSFILE=72 # critical OS file missing
EX_CANTCREAT=73 # can't create (user) output file
EX_IOERR=74 # input/output error
EX_TEMPFAIL=75 # temp failure; user is invited to retry
EX_PROTOCOL=76 # remote error in protocol
EX_NOPERM=77 # permission denied
EX_CONFIG=78 # configuration error
EX__MAX=78 # maximum listed value
#System errors
S_EX_ANY=1 #Catchall for general errors
S_EX_SH=2 #Misuse of shell builtins (according to Bash documentation); seldom seen
S_EX_EXEC=126 #Command invoked cannot execute Permission problem or command is not an executable
S_EX_NOENT=127 #"command not found" illegal_command Possible problem with $PATH or a typo
S_EX_INVAL=128 #Invalid argument to exit exit 3.14159 exit takes only integer args in the range 0 - 255 (see first footnote)
#128+n Fatal error signal "n" kill -9 $PPID of script $? returns 137 (128 + 9)
#255* Exit status out of range exit -1 exit takes only integer args in the range 0 - 255
S_EX_HUP=129
S_EX_INT=130
#...
E può essere generato con:
#!/bin/sh
src=/usr/include/sysexits.h
echo "# Generated from \"$src\""
echo "# Please inspect the source file for more detailed descriptions"
echo
< "$src" sed -rn 's/^#define *(\w+)\s*(\d*)/\1=\2/p'| sed 's:/\*:#:; s:\*/::'
cat<<'EOF'
#System errors
S_EX_ANY=1 #Catchall for general errors
S_EX_SH=2 #Misuse of shell builtins (according to Bash documentation); seldom seen
S_EX_EXEC=126 #Command invoked cannot execute Permission problem or command is not an executable
S_EX_NOENT=127 #"command not found" illegal_command Possible problem with $PATH or a typo
S_EX_INVAL=128 #Invalid argument to exit exit 3.14159 exit takes only integer args in the range 0 - 255 (see first footnote)
#128+n Fatal error signal "n" kill -9 $PPID of script $? returns 137 (128 + 9)
#255* Exit status out of range exit -1 exit takes only integer args in the range 0 - 255
EOF
$(which kill) -l |tr ' ' '\n'| awk '{ printf "S_EX_%s=%s\n", $0, 128+NR; }'
Non lo uso molto, però, ma quello che uso è una funzione shell che inverte i codici di errore nei loro formati di stringa. L'ho chiamato exit2str
. Supponendo che tu abbia chiamato il exit.sh
generatore sopra exit.sh.sh
, il codice per exit2str
può essere generato con ( exit2str.sh.sh
):
#!/bin/sh
echo '
exit2str(){
case "$1" in'
./exit.sh.sh | sed -nEe's|^(S_)?EX_(([^_=]+_?)+)=([0-9]+).*|\4) echo "\1\2";;|p'
echo "
esac
}"
Lo uso nella PS1
mia shell interattiva in modo che dopo ogni comando che eseguo, posso vedere il suo stato di uscita e la sua forma di stringa (se ha una forma di stringa nota):
[15:58] pjump@laptop:~
(0=OK)$
[15:59] pjump@laptop:~
(0=OK)$ fdsaf
fdsaf: command not found
[15:59] pjump@laptop:~
(127=S_NOENT)$ sleep
sleep: missing operand
Try 'sleep --help' for more information.
[15:59] pjump@laptop:~
(1=S_ANY)$ sleep 100
^C
[15:59] pjump@laptop:~
(130=S_INT)$ sleep 100
^Z
[1]+ Stopped sleep 100
[15:59] pjump@laptop:~
(148=S_TSTP)$
Per ottenerli, è necessario un insourcable per la funzione exit2str:
$ ./exit2str.sh.sh > exit2str.sh #Place this somewhere in your PATH
e poi usalo nel tuo ~/.bashrc
per salvare e tradurre il codice di uscita su ogni prompt dei comandi e visualizzarlo come tuo ( PS1
):
# ...
. exit2str.sh
PROMPT_COMMAND='lastStatus=$(st="$?"; echo -n "$st"; str=$(exit2str "$st") && echo "=$str"); # ...'
PS1="$PS1"'\n($lastStatus)\$'
# ...
È abbastanza utile per osservare come alcuni programmi seguono le convenzioni del codice di uscita e altri no, per conoscere le convenzioni del codice di uscita o semplicemente per essere in grado di vedere cosa sta succedendo più facilmente. Avendolo usato da un po 'di tempo, posso dire che molti script di shell orientati al sistema seguono le convenzioni. EX_USAGE
è particolarmente abbastanza comune, anche se altri codici, non molto. Cerco di seguire le convenzioni di volta in volta, sebbene ci sia sempre $S_EX_ANY
(1) per i pigri (io sono uno).