Module Name: src Committed By: kre Date: Wed Aug 23 01:17:46 UTC 2017
Modified Files: src/usr.bin/sys_info: sys_info.1 sys_info.sh Log Message: Put back getopts - it is easier to get correct than hand rolled code. Add -L and -P flags to allow the library/cmd search paths to be set. Add support for getting vers info from sh, dhcpcd, and userland (/etc/release). Stop abusing "sh -x" to support -v - do it properly. Get rid of the duplicate list of components used when there are no args, instead make better use of sh capabilities to just process everything. Better use of what sh can do for us other places too. Add a (more or less random) set of libraries to include in output when no args are given. OK agc (well, earlier version...) To generate a diff of this commit: cvs rdiff -u -r1.2 -r1.3 src/usr.bin/sys_info/sys_info.1 cvs rdiff -u -r1.7 -r1.8 src/usr.bin/sys_info/sys_info.sh Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/usr.bin/sys_info/sys_info.1 diff -u src/usr.bin/sys_info/sys_info.1:1.2 src/usr.bin/sys_info/sys_info.1:1.3 --- src/usr.bin/sys_info/sys_info.1:1.2 Mon Aug 21 19:22:31 2017 +++ src/usr.bin/sys_info/sys_info.1 Wed Aug 23 01:17:46 2017 @@ -1,4 +1,4 @@ -.\" $NetBSD: sys_info.1,v 1.2 2017/08/21 19:22:31 agc Exp $ +.\" $NetBSD: sys_info.1,v 1.3 2017/08/23 01:17:46 kre Exp $ .\" .\" Copyright (c) 2016 Alistair Crooks <a...@netbsd.org> .\" All rights reserved. @@ -23,16 +23,18 @@ .\" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF .\" THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. .\" -.Dd August 21, 2017 +.Dd August 23, 2017 .Dt SYS_INFO 1 .Os .Sh NAME .Nm sys_info -.Nd script to show versioning information +.Nd script to show system version information .Sh SYNOPSIS .Nm .Op Fl v -.Op Ar +.Op Fl L Ar lib-path +.Op Fl P Ar path +.Op Ar component No ... .Sh DESCRIPTION The .Nm @@ -44,10 +46,29 @@ The utility uses a combination of ways to retrieve version information from the installed utilities. .Sh OPTIONS -The following option is available: +The following options are available: .Bl -tag -width inits +.It Fl L +Give a list of directories +.Pq "colon separated" +that are used when searching for libraries. +If not given the value of +.Ev LD_LIBRARY_PATH +is used if set in the environment, or otherwise +a standard (built-in) set of directories. +.It Fl P +Set +.Ev PATH . +If not given, the system default path, as obtained from +.Ic user.cs_path +via +.Xr sysctl 1 +is used. +To use the current value of $PATH from the caller, use: +.Dl -P \*q$PATH\*q .It Fl v -Perform operations in a verbose manner. +Show the commands used to obtain the version information +for each component .El .Pp Arguments may be given to sys_info. @@ -61,9 +82,17 @@ are reported. .Pp If arguments are provided, the output is displayed in alphabetical order, and duplicates are removed. +.Sh EXIT STATUS +.Nm +exits with status 2 if an unknown option is given, +otherwise with status 1 if an unknown component is specified, +otherwise, with status 0. .Sh SEE ALSO .Xr awk 1 , -.Xr strings 1 +.Xr sed 1 , +.Xr strings 1 , +.Xr sysctl 1 , +.Xr uname 1 .Sh HISTORY The .Nm @@ -74,3 +103,5 @@ The .Nm script was written by .An Alistair Crooks Aq Mt a...@netbsd.org . +.Sh BUGS +Component names containing spaces given as arguments do not work. Index: src/usr.bin/sys_info/sys_info.sh diff -u src/usr.bin/sys_info/sys_info.sh:1.7 src/usr.bin/sys_info/sys_info.sh:1.8 --- src/usr.bin/sys_info/sys_info.sh:1.7 Mon Aug 21 19:51:32 2017 +++ src/usr.bin/sys_info/sys_info.sh Wed Aug 23 01:17:46 2017 @@ -1,6 +1,6 @@ #! /bin/sh -# $NetBSD: sys_info.sh,v 1.7 2017/08/21 19:51:32 agc Exp $ +# $NetBSD: sys_info.sh,v 1.8 2017/08/23 01:17:46 kre Exp $ # Copyright (c) 2016 Alistair Crooks <a...@netbsd.org> # All rights reserved. @@ -26,23 +26,52 @@ # THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. # -SYS_INFO_VERSION=20170821 -LD_LIBRARY_PATH=${LD_LIBRARY_PATH:-/usr/lib:/usr/X11R7/lib} +SYS_INFO_VERSION=$( D="\$Date: 2017/08/23 01:17:46 $"; set -f; + IFS=" /"; set -- $D; printf %s "$2$3$4" ) + +PATH=$(sysctl -n user.cs_path) +export PATH + +LIBRARY_PATH=${LD_LIBRARY_PATH:-/usr/lib:/usr/X11R7/lib} + +# default libraries when no args are given (sorted...) +LIBS= +LIBS="${LIBS} libc" +LIBS="${LIBS} libcurses" +LIBS="${LIBS} libdrm" +LIBS="${LIBS} libm" +LIBS="${LIBS} libresolv" +LIBS="${LIBS} libsqlite" +LIBS="${LIBS} libssh" +LIBS="${LIBS} libstdc++" +LIBS="${LIBS} libterminfo" +LIBS="${LIBS} libutil" +LIBS="${LIBS} libX11" +LIBS="${LIBS} libXaw7" +LIBS="${LIBS} libXcb" +LIBS="${LIBS} libXfont" +LIBS="${LIBS} libXft" +LIBS="${LIBS} libXrandr" +LIBS="${LIBS} libXt" # short script to look for an executable $2, and if found, to place # path in $1 # taken from pkgsrc bootstrap which_prog() { + local IFS _var _name _d - + set -f + _var="$1"; _name="$2" - eval _tmp=\"\$$_var\" - if [ "x$_tmp" != "x" ]; then + eval _d=\"\$$_var\" + if [ -n "$_d" ]; then # Variable is already set (by the user, for example) return 0 fi - for _d in `echo $PATH | tr ':' ' '`; do + IFS=: + for _d in $PATH ; do if [ -f "$_d/$_name" ] && [ -x "$_d/$_name" ]; then # Program found eval $_var=\""$_d/$_name"\" @@ -53,139 +82,182 @@ which_prog() return 1 } -# print out the version for the given argument +savedIFS=unset +saveIFS() { savedIFS="${IFS-unset}"; IFS="$1"; } +restIFS() { test "${savedIFS}" = unset && unset IFS || IFS="${savedIFS}"; } + +run() { + # must send to stderr, as run is used in $() sometimes. + $verbose && printf >&2 '%s\n' "${PS4:-...: }${1}" + eval "$1" +} + +# print out the version for the given argument (or everything) + +# case patterns are sorted by output order so +# sys_info +# and +# sys_info | sort -f +# generate identical output + getversion() { case "$1" in + '') + # arriving here implies all==true, not possible otherwise + ;& awk) - awk --version | awk '{ print $1 "-" $3 }' - ;; - bind|named) - named -v | awk '{ gsub("-", "", $2); gsub("P", "pl", $2); print tolower($1) "-" $2 }' - ;; + run "awk --version | awk '{ print \$1 \"-\" \$3 }'" + $all || return 0 ;& + [Bb][Ii][Nn][Dd]|named) + run "named -v | awk '{ gsub(\"-\", \"\", \$2); gsub(\"P\", \"pl\", \$2); print tolower(\$1) \"-\" \$2 }'" + $all || return 0 ;& + bozohttpd|httpd) + v=$(run "/usr/libexec/httpd -G" 2>/dev/null) + case "${v}" in + "") + run "strings -a /usr/libexec/httpd | awk -F/ '\$1 == \"bozohttpd\" && NF == 2 { print \$1 \"-\" \$2; exit }'" + ;; + *) + printf '%s\n' "bozohttpd-${v##*/}" + ;; + esac + $all || return 0 ;& bzip2) - bzip2 --help 2>&1 | awk '{ sub(",", "", $7); print "bzip2-" $7; exit }' - ;; + run "bzip2 --help 2>&1 | awk '{ sub(\",\", \"\", \$7); print \"bzip2-\" \$7; exit }'" + $all || return 0 ;& calendar) - v=$(calendar -v 2>/dev/null || true) + v=$(run "calendar -v" 2>/dev/null || true) case "${v}" in - "") echo "calendar-20150701" ;; - *) echo ${v} ;; + "") printf '%s\n' "calendar-20150701" ;; + *) printf '%s\n' "${v}" ;; esac - ;; + $all || return 0 ;& + dhcpcd) + run "dhcpcd --version | sed -e 's/ /-/g' -e 1q" + $all || return 0 ;& ftpd) - strings -a /usr/libexec/ftpd | awk '$1 == "NetBSD-ftpd" { print "ftpd-" $2 }' - ;; + run "strings -a /usr/libexec/ftpd | awk '\$1 == \"NetBSD-ftpd\" { print \"ftpd-\" \$2 }'" + $all || return 0 ;& g++|c++) - g++ --version | awk '{ print $1 "-" $4; exit }' - ;; + run "g++ --version | awk '{ print \$1 \"-\" \$4; exit }'" + $all || return 0 ;& gcc|cc) - gcc --version | awk '{ print $1 "-" $4; exit }' - ;; + run "gcc --version | awk '{ print \$1 \"-\" \$4; exit }'" + $all || return 0 ;& grep) - grep --version | awk '{ print $1 "-" $4 $5; exit }' - ;; + run "grep --version | awk '{ print \$1 \"-\" \$4 \$5; exit }'" + $all || return 0 ;& gzip) - gzip --version 2>&1 | awk '{ print $2 "-" $3 }' - ;; - httpd|bozohttpd) - v=$(/usr/libexec/httpd -G 2>/dev/null || true) - case "${v}" in - "") - strings -a /usr/libexec/httpd | awk -F/ '$1 == "bozohttpd" && NF == 2 { print $1 "-" $2; exit }' - ;; - *) - echo bozohttpd-${v##*/} - ;; - esac - ;; + run "gzip --version 2>&1 | awk '{ print \$2 \"-\" \$3 }'" + $all || return 0 ;& lib*) - dlist=$(echo ${LD_LIBRARY_PATH} | awk '{ gsub(":", " "); print }') - for d in ${dlist}; do - if [ -e ${d}/$1.so ]; then - ls -al ${d}/$1.so | awk '{ sub(".*/", "", $11); sub("\\.so\\.", "-", $11); print $11 }' - break - fi + for L in ${1:-$LIBS}; do + saveIFS : + for d in ${LIBRARY_PATH} nowhere; do + restIFS + if [ -e ${d}/$L.so ]; then + run "ls -al \"${d}/$L.so\" | sed -e 's/^.*-> //' -e 's;^.*/;;' -e 's/\\.so\\./-/'" + break + fi + done + restIFS + test "$d" = nowhere && test -n "$1" && + printf 2>&1 '%s\n' "$0: library $1 not found" done - ;; - netbsd) - uname -sr | awk '{ print $1 "-" $2 }' - ;; + $all || return 0 ;& + [Nn]et[Bb][Ss][Dd]|kernel) + run "uname -sr | awk '{ print \$1 \"-\" \$2 }'" + $all || return 0 ;& netpgp) - netpgp -V | awk '{ sub("/.*", "", $3); print "netpgp-" $3; exit }' - ;; + run "netpgp -V | awk '{ sub(\"/.*\", \"\", \$3); print \"netpgp-\" \$3; exit }'" + $all || return 0 ;& netpgpverify) - netpgpverify -v | awk '{ print $1 "-" $3 }' - ;; + run "netpgpverify -v | awk '{ print \$1 \"-\" \$3 }'" + $all || return 0 ;& ntp) - ntpq --version | awk '{ sub("-.", ""); sub("p", "pl", $2); print "ntp-" $2 }' - ;; + run "ntpq --version | awk '{ sub(\"-.\", \"\"); sub(\"p\", \"pl\", \$2); print \"ntp-\" \$2 }'" + $all || return 0 ;& + openssh|ssh) + run "ssh -V 2>&1 | awk '{ sub(\"_\", \"-\", \$1); print tolower(\$1) }'" + $all || return 0 ;& + opensshd|sshd) + run "sshd -V 2>&1 | awk '/OpenSSH/ { sub(\"_\", \"D-\", \$1); print tolower(\$1) }'" + $all || return 0 ;& openssl) - openssl version 2>/dev/null | awk '{ print tolower($1) "-" $2 }' - ;; + run "openssl version 2>/dev/null | awk '{ print tolower(\$1) \"-\" \$2 }'" + $all || return 0 ;& + sh) + run "set -- \$NETBSD_SHELL; case \"\$1+\$2\" in *+BUILD*) ;; +) set -- ancient;; *) set -- \"\$1\";;esac; printf 'sh-%s\\n' \$1\${2:+-\${2#BUILD:}}" + $all || return 0 ;& sqlite|sqlite3) - sqlite3 --version | awk '{ print "sqlite3-" $1 }' - ;; - ssh|openssh) - ssh -V 2>&1 | awk '{ sub("_", "-", $1); print tolower($1) }' - ;; - sshd) - sshd -V 2>&1 | awk '/OpenSSH/ { sub("_", "D-", $1); print tolower($1) }' - ;; + run "sqlite3 --version | awk '{ print \"sqlite3-\" \$1 }'" + $all || return 0 ;& sys_info) - echo sys_info-${SYS_INFO_VERSION} - ;; + run "printf '%s\n' sys_info-${SYS_INFO_VERSION}" + $all || return 0 ;& tcsh) if which_prog tcshpath tcsh; then - ${tcshpath} --version | awk '{ print $1 "-" $2 }' + run "${tcshpath} --version | awk '{ print \$1 \"-\" \$2 }'" else - echo "tcsh: not found" + $all || printf >&2 '%s\n' "tcsh: not found" fi - ;; + $all || return 0 ;& tzdata) if [ -f /usr/share/zoneinfo/TZDATA_VERSION ]; then - cat /usr/share/zoneinfo/TZDATA_VERSION + run "cat /usr/share/zoneinfo/TZDATA_VERSION" + else + run "printf '%s\n' tzdata-too-old-to-matter" fi - ;; + $all || return 0 ;& unbound) if which_prog unboundpath unbound-control; then - ${unboundpath} -h | awk '/^Version/ { print "unbound-" $2 }' + run "${unboundpath} -h | awk '/^Version/ { print \"unbound-\" \$2 }'" else - echo "unbound: not found" + $all || printf >&2 '%s\n' "unbound: not found" fi - ;; + $all || return 0 ;& + [uU]ser[lL]and|release) + run "sed </etc/release -e 's/ /-/g' -e 's/^/userland-/' -e 1q" + $all || return 0 ;& xz) - xz --version | awk '{ print $1 "-" $4; exit }' + run "xz --version | awk '{ print \$1 \"-\" \$4; exit }'" + $all || return 0 ;& + + '') # never matches + ;; # but terminates ;& sequence + + *) printf >&2 '%s\n' "Unrecognised subsystem: $1" + ERRS=1 ;; esac } +verbose=false # check if we have our only option -while [ $# -gt 0 ]; do - case "$1" in - -v) set -x ;; - *) break ;; +while getopts "L:P:v" a; do + case "$a" in + v) verbose=true;; + L) LIBRARY_PATH=${OPTARG};; + P) PATH=${OPTARG};; + \?) printf >&2 '%s\n' \ + "Usage: $0 [-P path] [-L libdirs] [-v] [system...]" + exit 2 esac - shift done +shift $((OPTIND - 1)) -all=false -# if no arg specified, we want them all if [ $# -eq 0 ]; then + set -- '' all=true -fi - -# if we want to do every one, then let's get the arguments -# not really scalable -if ${all}; then - args='awk bind bzip2 calendar ftpd g++ gcc grep gzip httpd netbsd netpgp' - args="${args} netpgpverify ntp openssl sqlite ssh sshd sys_info tcsh" - args="${args} tzdata unbound xz" else - args=$(echo $@ | tr ' ' '\n' | sort | uniq) + # note this deletes any attempt to use '' as an arg. + set -- $( printf '%s\n' "$@" | sort -u ) + all=false fi -set -- ${args} +ERRS=0 while [ $# -gt 0 ]; do - getversion $1 + getversion "$1" shift done +exit $ERRS