]> git.ipfire.org Git - thirdparty/coreutils.git/commitdiff
tests: verify usage vs. getopt
authorBernhard Voelker <mail@bernhard-voelker.de>
Mon, 27 Nov 2017 22:46:51 +0000 (23:46 +0100)
committerBernhard Voelker <mail@bernhard-voelker.de>
Wed, 29 Nov 2017 12:29:00 +0000 (13:29 +0100)
Verify that all options mentioned in usage are actually recognized
by the program.

* tests/misc/usage_vs_getopt.sh: Add test.
* tests/local.mk (all_tests): Reference it.

Co-authored-by: Pádraig Brady <P@draigBrady.com>
tests/local.mk
tests/misc/usage_vs_getopt.sh [new file with mode: 0755]

index 8ee7c50399480574baeae32afe2becb67c0a6f53..612316b617dce9b642758adb8e84fadf3565b13d 100644 (file)
@@ -422,6 +422,7 @@ all_tests =                                 \
   tests/misc/truncate-relative.sh              \
   tests/misc/tsort.pl                          \
   tests/misc/tty.sh                            \
+  tests/misc/usage_vs_getopt.sh                        \
   tests/misc/unexpand.pl                       \
   tests/misc/uniq.pl                           \
   tests/misc/uniq-perf.sh                      \
diff --git a/tests/misc/usage_vs_getopt.sh b/tests/misc/usage_vs_getopt.sh
new file mode 100755 (executable)
index 0000000..1d6cf92
--- /dev/null
@@ -0,0 +1,92 @@
+#!/bin/sh
+# Verify that all options mentioned in usage are recognized by getopt.
+
+# Copyright (C) 2017 Free Software Foundation, Inc.
+
+# This program is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <https://www.gnu.org/licenses/>.
+
+. "${srcdir=.}/tests/init.sh"; path_prepend_ ./src
+
+checkprg () {
+  prg="$1"
+
+  # Get stderr output for unrecognized options for later use as a pattern.
+  # Also consider the expected exit status of each program.
+  rcexp=1
+  case "$prg" in
+    dir | ls | printenv | sort | tty | vdir ) rcexp=2 ;;
+    env | chroot | nice | nohup | stdbuf | timeout ) rcexp=125 ;;
+  esac
+  # Write the pattern for a long, unknown option into a pattern file.
+  o='thisoptiondoesnotexist'
+  returns_ $rcexp $prg --$o >/dev/null 2> err || fail=1
+  grep -F "$o" err || framework_failure_
+  sed -n "1s/--$o/OPT/p" < err > pat || framework_failure_
+
+  # Append the pattern for a short unkown option.
+  returns_ $rcexp $prg -/ >/dev/null 2> err || fail=1
+  grep -F "'/'" err || framework_failure_
+  sed -n "1s/'\/'/'OPT'/p" < err >> pat || framework_failure_
+
+  # Get output for --help.
+  $prg --help > help || fail=1
+
+  # Extract all options mention in the above --help output.
+  sed -n -e '/--version/q' \
+    -e 's/^ \{2,6\}-/-/; s/  .*//; s/[=[].*//; s/, /\'$'\n''/g; s/^-/-/p' help \
+    > opts || framework_failure_
+  cat opts  # for debugging purposes
+
+  # Test all options mentioned in usage (but --version).
+  while read opt; do
+    test "x$opt" = 'x--help' \
+      && continue
+    # Append --help to be on the safe side: the option under test either
+    # requires a further argument, or --help triggers usage(); so $prg should
+    # exit without performing its regular operation.
+    # Add a 2nd --help for the 'env -u --help' case.
+    $prg "$opt" --help --help </dev/null >out 2>err1
+    rc=$?
+    # In the --help case, i.e., when the option under test has been accepted,
+    # the exit code should be Zero.
+    if [ $rc = 0 ]; then
+      compare help out || fail=1
+    else
+      # Else $prg should have complained about a missing argument.
+      # Catch false positives.
+      case "$prg/$opt" in
+        'pr/-COLUMN') continue;;
+      esac
+      # Replace $opt in stderr output by the neutral placeholder.
+      # Handle both long and short option error messages.
+      sed -e "s/$opt/OPT/" -e "s/'.'/'OPT'/" < err1 > err || framework_failure_
+      # Fail if the stderr output matches the above provoked error.
+      grep -Ff pat err && { fail=1; cat err1; }
+    fi
+  done < opts
+}
+
+for prg in $built_programs; do
+  case "$prg" in
+    # Skip utilities entirely which have special option parsing.
+    '[' | expr | stty )
+      continue;;
+    # Wrap some utilities known by the shell by env.
+    echo | false | kill | printf | pwd | test | true )
+      prg="env $prg";;
+  esac
+  checkprg $prg
+done
+
+Exit $fail