1 #!/bin/bash
2 #
3 # This file and its contents are supplied under the terms of the
4 # Common Development and Distribution License ("CDDL"), version 1.0.
5 # You may only use this file in accordance with the terms of version
6 # 1.0 of the CDDL.
7 #
8 # A full copy of the text of the CDDL should have accompanied this
9 # source. A copy of the CDDL is also available via the Internet at
10 # http://www.illumos.org/license/CDDL.
11 #
12
13 #
14 # Copyright 2012 (c), Joyent, Inc.
15 #
16
17 #
18 # mdb test driver
19 #
20 unalias -a
21 shopt -s xpg_echo
22 #set -o xtrace
23
24 mt_arg0=$(basename $0)
25 mt_ksh="/usr/bin/ksh"
26 mt_mdb="/usr/bin/mdb"
27 mt_outdir=
28 mt_keep=
29 mt_all=
30 mt_tests=
31 mt_tnum=0
32 mt_tfail=0
33 mt_tsuc=0
34
35 function usage
36 {
37 local msg="$*"
38 [[ -z "$msg" ]] || echo "$msg" 2>&1
39 cat <<USAGE >&2
40 Usage: $mt_arg0 [ -o dir ] [ -k ] [ -m executable ] [ -a | test ... ]
41
42 -o dir Sets 'dir' as the output directory
43 -a Runs all tests, ignores tests passed in
44 -k Keep output from all tests, not just failures
45 -m mdb binary to test
46 USAGE
47 exit 2
48 }
49
50 function fatal
51 {
52 local msg="$*"
53 [[ -z "$msg" ]] && msg="failed"
54 echo "$mt_arg0: $msg" >&2
55 exit 1
56 }
57
58 function setup_outdir
59 {
60 mt_outdir="$mt_outdir/$mt_arg0.$$"
61 mkdir -p $mt_outdir || fatal "failed to make output dir $mt_outdir"
62 }
63
64 function run_single
65 {
66 local name=$1
67 local expect base ext exe command odir res reason input
68
69 [[ -z "$name" ]] && fail "missing test to run"
70 base=${name##*/}
71 ext=${base##*.}
72 expect=${base%%.*}
73 odir="$mt_outdir/current"
74 [[ -z "$ext" ]] && fatal "found test without ext: $name"
75 [[ -z "$expect" ]] && fatal "found test without prefix: $name"
76
77 case "$ext" in
78 "ksh")
79 command="$mt_ksh $name"
80 ;;
81 "mdb")
82 command="$mt_mdb"
83 input="$name"
84 ;;
85 "out")
86 #
87 # This is the file format for checking output against.
88 #
89 return 0
90 ;;
91 *)
92 echo "skipping test $name (unknown extensino)"
93 return 0
94 ;;
95 esac
96
97 echo "Executing test $name ... \c"
98 mkdir -p "$odir" >/dev/null || fatal "can't make output directory"
99 if [[ -z "$input" ]]; then
100 MDB=$mt_mdb $command > "$odir/stdout" 2>"$odir/stderr"
101 res=$?
102 else
103 MDB=$mt_mdb $command < $input > "$odir/stdout" 2>"$odir/stderr"
104 res=$?
105 fi
106
107 if [[ -f "$name.out" ]] && ! diff "$name.out" "$odir/stdout" >/dev/null; then
108 cp $name.out $odir/$base.out
109 reason="stdout mismatch"
110 elif [[ "$expect" == "tst" && $res -ne 0 ]]; then
111 reason="test exited $res, not zero"
112 elif [[ "$expect" == "err" && $res -eq 0 ]]; then
113 reason="test exited $res, not non-zero"
114 fi
115
116 if [[ -n "$reason" ]]; then
117 echo "$reason"
118 ((mt_tfail++))
119 mv "$odir" "$mt_outdir/failure.$mt_tfail" || fatal \
120 "failed to move test output directory"
121 cp "$name" "$mt_outdir/failure.$mt_tfail/test" || fatal \
122 "failed to copy test into output directory"
123 else
124 echo "passed"
125 ((mt_tsuc++))
126 mv "$odir" "$mt_outdir/success.$mt_tsuc" || fatal \
127 "failed to move test directory"
128 fi
129
130 ((mt_tnum++))
131 }
132
133 function run_all
134 {
135 local tests t
136
137 tests=$(find . -type f -name '[tst,err]*.*.[ksh,mdb]*')
138 for t in $tests; do
139 run_single $t
140 done
141 }
142
143 function welcome
144 {
145 cat <<WELCOME
146 Starting tests...
147 mtest target: $mt_mdb
148 output directory: $mt_outdir
149 WELCOME
150 }
151
152 function cleanup
153 {
154 [[ -n "$mt_keep" ]] && return
155 rm -rf "$mt_outdir"/success.* || fatal \
156 "failed to remove successful test cases"
157 if [[ $mt_tfail -eq 0 ]]; then
158 rmdir "$mt_outdir" || fatal \
159 "failed to remove test output directory"
160 fi
161 }
162
163 function goodbye
164 {
165 cat <<EOF
166
167 -------------
168 Results
169 -------------
170
171 Tests passed: $mt_tsuc
172 Tests failed: $mt_tfail
173 Tests ran: $mt_tnum
174
175 EOF
176 if [[ $mt_tfail -eq 0 ]]; then
177 echo "Congrats, mdb isn't completely broken, the tests pass".
178 else
179 echo "Some tests failed, you have some work to do."
180 fi
181 }
182
183 while getopts ":ahko:m:" c $@; do
184 case "$c" in
185 a)
186 mt_all="y"
187 ;;
188 k)
189 mt_keep="y"
190 ;;
191 m)
192 mt_mdb="$OPTARG"
193 ;;
194 o)
195 mt_outdir="$OPTARG"
196 ;;
197 h)
198 usage
199 ;;
200 :)
201 usage "option requires an argument -- $OPTARG"
202 ;;
203 *)
204 usage "invalid option -- $OPTARG"
205 ;;
206 esac
207 done
208
209 shift $((OPTIND-1))
210
211 [[ -z "$mt_all" && $# == 0 ]] && usage "no tests to run"
212
213 [[ -x "$mt_mdb" ]] || fatal "unable to execute mdb binary: $mt_mdb"
214
215 [[ -z "$mt_outdir" ]] && mt_outdir=/var/tmp
216
217 setup_outdir
218 welcome
219
220 if [[ ! -z "$mt_all" ]]; then
221 run_all
222 else
223 for t in $@; do
224 [[ -f $t ]] || fatal "cannot find test $t"
225 run_single $t
226 done
227 fi
228
229 goodbye
230 cleanup
231
232 #
233 # Exit 1 if we have tests that return non-zero
234 #
235 [[ $mt_tfai -eq 0 ]]