t_realpath.sh revision 1.1 1 1.1 kre # $NetBSD: t_realpath.sh,v 1.1 2022/07/21 09:52:49 kre Exp $
2 1.1 kre #
3 1.1 kre # Copyright (c) 2022 The NetBSD Foundation, Inc.
4 1.1 kre # All rights reserved.
5 1.1 kre #
6 1.1 kre # Redistribution and use in source and binary forms, with or without
7 1.1 kre # modification, are permitted provided that the following conditions
8 1.1 kre # are met:
9 1.1 kre # 1. Redistributions of source code must retain the above copyright
10 1.1 kre # notice, this list of conditions and the following disclaimer.
11 1.1 kre # 2. Redistributions in binary form must reproduce the above copyright
12 1.1 kre # notice, this list of conditions and the following disclaimer in the
13 1.1 kre # documentation and/or other materials provided with the distribution.
14 1.1 kre #
15 1.1 kre # THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
16 1.1 kre # ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
17 1.1 kre # TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
18 1.1 kre # PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
19 1.1 kre # BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20 1.1 kre # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
21 1.1 kre # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22 1.1 kre # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
23 1.1 kre # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24 1.1 kre # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25 1.1 kre # POSSIBILITY OF SUCH DAMAGE.
26 1.1 kre #
27 1.1 kre
28 1.1 kre # ===========================================================
29 1.1 kre #
30 1.1 kre # Test data and expected results
31 1.1 kre
32 1.1 kre # Note that the empty line calls realpath with no file arg
33 1.1 kre existing='.
34 1.1 kre
35 1.1 kre ../Dir/StdOut
36 1.1 kre ./S1
37 1.1 kre ./S1/../S4
38 1.1 kre ./Snr/../S4
39 1.1 kre S1/S2/File
40 1.1 kre S1/S3/Link
41 1.1 kre Snr/HoHo
42 1.1 kre Snr/Link
43 1.1 kre L
44 1.1 kre /
45 1.1 kre /bin
46 1.1 kre Self
47 1.1 kre Self/
48 1.1 kre S4/S1/'
49 1.1 kre
50 1.1 kre exist_results='Dir
51 1.1 kre Dir
52 1.1 kre Dir/StdOut
53 1.1 kre Dir/S1
54 1.1 kre Dir/S4
55 1.1 kre Dir/S4
56 1.1 kre Dir/S1/S2/File
57 1.1 kre Dir/S1/S2/File
58 1.1 kre Dir/Snr/HoHo
59 1.1 kre Dir/S1
60 1.1 kre Dir/StdOut
61 1.1 kre /
62 1.1 kre /bin
63 1.1 kre Dir
64 1.1 kre Dir
65 1.1 kre Dir/S1'
66 1.1 kre
67 1.1 kre exist_root_only='Snx/HaHa
68 1.1 kre Snx/Link'
69 1.1 kre
70 1.1 kre exist_root_results='Dir/Snx/HaHa
71 1.1 kre Dir/S1/S2/File'
72 1.1 kre
73 1.1 kre nofile='-
74 1.1 kre trash
75 1.1 kre Snr/Haha
76 1.1 kre T1
77 1.1 kre T2
78 1.1 kre T3
79 1.1 kre T4
80 1.1 kre T5
81 1.1 kre ../Dir/T2
82 1.1 kre ../Dir/T3
83 1.1 kre /nonsense
84 1.1 kre /bin/../nonsense
85 1.1 kre ./Self/Self/Self/Self/S1/../Self/../Dir/Self/T1
86 1.1 kre Self/nonsense'
87 1.1 kre
88 1.1 kre nofile_results='Dir/-
89 1.1 kre Dir/trash
90 1.1 kre Dir/Snr/Haha
91 1.1 kre Dir/NoSuchFile
92 1.1 kre Dir/S1/NoSuchFile
93 1.1 kre Dir/S1/NoSuchFile
94 1.1 kre Dir/S1/S2/NoSuchFile
95 1.1 kre Dir/S1/S2/NoSuchFile
96 1.1 kre Dir/S1/NoSuchFile
97 1.1 kre Dir/S1/NoSuchFile
98 1.1 kre /nonsense
99 1.1 kre /nonsense
100 1.1 kre Dir/NoSuchFile
101 1.1 kre Dir/nonsense'
102 1.1 kre
103 1.1 kre always_fail='StdOut/
104 1.1 kre StdOut/../StdErr
105 1.1 kre Loop
106 1.1 kre S1/S5/Link
107 1.1 kre Loop/../StdOut
108 1.1 kre BigLoop
109 1.1 kre U1
110 1.1 kre U2
111 1.1 kre U3
112 1.1 kre U4
113 1.1 kre U5
114 1.1 kre U6
115 1.1 kre U7
116 1.1 kre U8
117 1.1 kre U9
118 1.1 kre T1/NoSuchFile
119 1.1 kre T1/../NoSuchFile
120 1.1 kre U9/../NoSuchFile
121 1.1 kre U9/../StdOut'
122 1.1 kre
123 1.1 kre
124 1.1 kre # ===========================================================
125 1.1 kre # Helper functions
126 1.1 kre #
127 1.1 kre
128 1.1 kre # Create the test environment
129 1.1 kre setup()
130 1.1 kre {
131 1.1 kre atf_require_prog /usr/bin/mktemp
132 1.1 kre atf_require_prog /bin/ln
133 1.1 kre atf_require_prog /bin/cp
134 1.1 kre atf_require_prog /bin/mkdir
135 1.1 kre atf_require_prog /bin/chmod
136 1.1 kre
137 1.1 kre DIR=${PWD}/$(mktemp -d Dir.XXXXX) ||
138 1.1 kre atf_fail "Did not make test directory"
139 1.1 kre cd "${DIR}" || atf_fail "Unable to cd $DIR"
140 1.1 kre
141 1.1 kre ID=$( set -- $( type id ) && test "$1" = id && test "$2" = is &&
142 1.1 kre test $# -eq 3 && printf %s "$3" || printf no-id-program)
143 1.1 kre
144 1.1 kre mkdir Dir && cd Dir || atf_fail "enter Dir"
145 1.1 kre
146 1.1 kre >StdOut || atf_fail "setup StdOut"
147 1.1 kre >StdErr || atf_fail "setup StdErr"
148 1.1 kre ln -s ../Dir Dir || atf_fail "setup Dir"
149 1.1 kre ln -s Loop Loop || atf_fail "setup Loop"
150 1.1 kre ln -s . Self || atf_fail "setup Self"
151 1.1 kre mkdir S1 S1/S2 S1/S3 S4 S4/S5 || atf_fail "setup subdirs"
152 1.1 kre echo S1/S2/File > S1/S2/File || atf_fail "setup File"
153 1.1 kre ln -s ../S2/File S1/S3/Link || atf_fail "setup S3/Link"
154 1.1 kre ln -s ../S1 S4/S1 || atf_fail "setup S4/S1"
155 1.1 kre ln -s StdOut L1 || atf_fail "setup L1"
156 1.1 kre ln -s L1 L2 || atf_fail "setup L2"
157 1.1 kre ln -s ../L2 S1/L3 || atf_fail "setup L3"
158 1.1 kre ln -s ../L3 S1/S2/L4 || atf_fail "setup L4"
159 1.1 kre ln -s ../S2/L4 S1/S3/L5 || atf_fail "setup L5"
160 1.1 kre ln -s S1/S3/L5 L || atf_fail "setup L"
161 1.1 kre ln -s ${PWD}/S1 S4/PWDS1 || atf_fail "setup PWDS1"
162 1.1 kre ln -s ${PWD}/S9 S4/PWDS9 || atf_fail "setup PWDS9"
163 1.1 kre ln -s ${PWD}/S9/File S4/PWDS9F || atf_fail "setup PWDS9F"
164 1.1 kre ln -s ../S4/BigLoop S1/BigLoop || atf_fail "setup S1/BigLoop"
165 1.1 kre ln -s ../BigLoop S4/BigLoop || atf_fail "setup S4/BigLoop"
166 1.1 kre ln -s "${DIR}"/Dir/S1/BigLoop BigLoop || atf_fail "setup BigLoop"
167 1.1 kre mkdir Snx || atf_fail "setup Snx"
168 1.1 kre cp /dev/null Snx/HaHa || atf_fail "setup Snx/HaHa"
169 1.1 kre ln -s "${DIR}"/Dir/S1/S2/File Snx/Link || atf_fail "setup Snx/Link"
170 1.1 kre mkdir Snr || atf_fail "setup Snr"
171 1.1 kre cp /dev/null Snr/HoHo || atf_fail "setup Snr/HoHo"
172 1.1 kre ln -s "${DIR}"/Dir/S4/PWDS1 Snr/Link || atf_fail "setup Snr/Link"
173 1.1 kre ln -s ../Snx/HaHa Snr/HaHa || atf_fail "setup HaHa"
174 1.1 kre ln -s "${DIR}"/Dir/NoSuchFile T1 || atf_fail "setup T1"
175 1.1 kre ln -s "${DIR}"/Dir/S1/NoSuchFile T2 || atf_fail "setup T2"
176 1.1 kre ln -s S1/NoSuchFile T3 || atf_fail "setup T3"
177 1.1 kre ln -s "${DIR}"/Dir/S1/S2/NoSuchFile T4 || atf_fail "setup T4"
178 1.1 kre ln -s S1/S2/NoSuchFile T5 || atf_fail "setup T5"
179 1.1 kre ln -s "${DIR}"/Dir/StdOut/CannotExist T6 || atf_fail "setup T6"
180 1.1 kre ln -s "${DIR}"/Dir/NoDir/WhoKnows U1 || atf_fail "setup U1"
181 1.1 kre ln -s "${DIR}"/Dir/S1/NoDir/WhoKnows U2 || atf_fail "setup U2"
182 1.1 kre ln -s "${DIR}"/Dir/S1/S2/NoDir/WhoKnows U3 || atf_fail "setup U3"
183 1.1 kre ln -s "${DIR}"/Dir/S1/../NoDir/WhoKnows U4 || atf_fail "setup U4"
184 1.1 kre ln -s "${DIR}"/Dir/NoDir/../StdOut U5 || atf_fail "setup U5"
185 1.1 kre ln -s NoDir/../StdOut U6 || atf_fail "setup U6"
186 1.1 kre ln -s S1/NoDir/../../StdOut U7 || atf_fail "setup U7"
187 1.1 kre ln -s "${DIR}"/Dir/Missing/NoDir/WhoKnows U8 || atf_fail "setup U8"
188 1.1 kre ln -s "${DIR}"/Dir/Missing/NoDir/../../StdOut U9 || atf_fail "setup U9"
189 1.1 kre chmod a+r,a-x Snx || atf_fail "setup a-x "
190 1.1 kre chmod a+x,a-r Snr || atf_fail "setup a-r"
191 1.1 kre }
192 1.1 kre
193 1.1 kre # ATF will remove all the files we made, just ensure perms are OK
194 1.1 kre cleanup()
195 1.1 kre {
196 1.1 kre chmod -R u+rwx .
197 1.1 kre return 0
198 1.1 kre }
199 1.1 kre
200 1.1 kre run_tests_pass()
201 1.1 kre {
202 1.1 kre opt=$1
203 1.1 kre tests=$2
204 1.1 kre results=$3
205 1.1 kre
206 1.1 kre FAILS=
207 1.1 kre FAILURES=0
208 1.1 kre T=0
209 1.1 kre
210 1.1 kre while [ "${#tests}" -gt 0 ]
211 1.1 kre do
212 1.1 kre FILE=${tests%%$'\n'*}
213 1.1 kre EXP=${results%%$'\n'*}
214 1.1 kre
215 1.1 kre tests=${tests#"${FILE}"}; tests=${tests#$'\n'}
216 1.1 kre results=${results#"${EXP}"}; results=${results#$'\n'}
217 1.1 kre
218 1.1 kre test -z "${EXP}" && atf_fail "Too few results (test botch)"
219 1.1 kre
220 1.1 kre T=$(( $T + 1 ))
221 1.1 kre
222 1.1 kre GOT=$(realpath $opt -- ${FILE:+"${FILE}"})
223 1.1 kre STATUS=$?
224 1.1 kre
225 1.1 kre case "${GOT}" in
226 1.1 kre '') ;; # nothing printed, deal with that below
227 1.1 kre
228 1.1 kre /*) # Full Path (what we want)
229 1.1 kre # Remove the unpredictable ATF dir prefix (if present)
230 1.1 kre GOT=${GOT#"${DIR}/"}
231 1.1 kre # Now it might be a relative path, that's OK
232 1.1 kre # at least it can be compared (its prefix is known)
233 1.1 kre ;;
234 1.1 kre
235 1.1 kre *) # a relative path was printed
236 1.1 kre FAILURES=$(($FAILURES + 1))
237 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
238 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}'"
239 1.1 kre FAILS="${FAILS}: output relative path '${GOT}'"
240 1.1 kre FAILS="${FAILS}, and exit($STATUS)"
241 1.1 kre continue
242 1.1 kre ;;
243 1.1 kre esac
244 1.1 kre
245 1.1 kre
246 1.1 kre if [ $STATUS -ne 0 ] || [ "${EXP}" != "${GOT}" ]
247 1.1 kre then
248 1.1 kre FAILURES=$(($FAILURES + 1))
249 1.1 kre if [ $STATUS -ne 0 ]
250 1.1 kre then
251 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
252 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}'"
253 1.1 kre FAILS="${FAILS} failed: status ${STATUS}"
254 1.1 kre else
255 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
256 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}'"
257 1.1 kre FAILS="${FAILS} expected '${EXP}' received '${GOT}'"
258 1.1 kre fi
259 1.1 kre fi
260 1.1 kre done
261 1.1 kre
262 1.1 kre if test -n "${results}"
263 1.1 kre then
264 1.1 kre FAILURES=$(( $FAILURES + 1 ))
265 1.1 kre
266 1.1 kre N=$(( $(printf '%s\n' "${results}" | wc -l) ))
267 1.1 kre s=s; if [ $N -eq 1 ]; then s=; fi
268 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"After $T tests"
269 1.1 kre FAILS="still $N more result$s (test botch)"
270 1.1 kre fi
271 1.1 kre
272 1.1 kre if [ $FAILURES -gt 0 ]
273 1.1 kre then
274 1.1 kre s=s
275 1.1 kre if [ $FAILURES -eq 1 ]; then s=; fi
276 1.1 kre printf >&2 '%d path%s resolved incorrectly:\n%s\n' \
277 1.1 kre "$FAILURES" "$s" "${FAILS}"
278 1.1 kre atf_fail "$FAILURES path$s resolved incorrectly; see stderr"
279 1.1 kre fi
280 1.1 kre return 0
281 1.1 kre }
282 1.1 kre
283 1.1 kre run_tests_fail()
284 1.1 kre {
285 1.1 kre opt=$1
286 1.1 kre tests=$2
287 1.1 kre
288 1.1 kre FAILS=
289 1.1 kre FAILURES=0
290 1.1 kre T=0
291 1.1 kre
292 1.1 kre while [ "${#tests}" -gt 0 ]
293 1.1 kre do
294 1.1 kre FILE=${tests%%$'\n'*}
295 1.1 kre
296 1.1 kre tests=${tests#"${FILE}"}; tests=${tests#$'\n'}
297 1.1 kre
298 1.1 kre test -z "${FILE}" && continue
299 1.1 kre
300 1.1 kre T=$(( $T + 1 ))
301 1.1 kre
302 1.1 kre GOT=$(realpath $opt -- "${FILE}" 2>StdErr)
303 1.1 kre STATUS=$?
304 1.1 kre
305 1.1 kre ERR=$(cat StdErr)
306 1.1 kre
307 1.1 kre if [ $STATUS -eq 0 ] || [ "${GOT}" ] || ! [ "${ERR}" ]
308 1.1 kre then
309 1.1 kre FAILURES=$(($FAILURES + 1))
310 1.1 kre if [ "${STATUS}" -eq 0 ]
311 1.1 kre then
312 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T: "
313 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}' worked;"
314 1.1 kre FAILS="${FAILS} received: '${GOT}'}"
315 1.1 kre
316 1.1 kre if [ "${ERR}" ]; then
317 1.1 kre FAILS="${FAILS} and on stderr '${ERR}'"
318 1.1 kre fi
319 1.1 kre elif [ "${GOT}" ]
320 1.1 kre then
321 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
322 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}' failed,"
323 1.1 kre FAILS="${FAILS} but with '${GOT}' on stdout"
324 1.1 kre
325 1.1 kre if [ "${ERR}" ]; then
326 1.1 kre FAILS="${FAILS}, and on stderr '${ERR}'"
327 1.1 kre else
328 1.1 kre FAILS="${FAILS}, and empty stderr"
329 1.1 kre fi
330 1.1 kre else
331 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
332 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}' failed,"
333 1.1 kre FAILS="${FAILS} but with no error message"
334 1.1 kre fi
335 1.1 kre fi
336 1.1 kre done
337 1.1 kre if [ $FAILURES -gt 0 ]
338 1.1 kre then
339 1.1 kre S=s
340 1.1 kre if [ $FAILURES -eq 1 ]; then s=; fi
341 1.1 kre printf >&2 '%d path%s resolved incorrectly:\n%s\n' \
342 1.1 kre "$FAILURES" "$s" "${FAILS}"
343 1.1 kre atf_fail "$FAILURES path$s resolved incorrectly; see stderr"
344 1.1 kre fi
345 1.1 kre return 0
346 1.1 kre }
347 1.1 kre
348 1.1 kre # ===================================================================
349 1.1 kre # Test cases setup follows (but almost all the work is earlier)
350 1.1 kre
351 1.1 kre atf_test_case a__e_ok cleanup
352 1.1 kre realpath_e_ok_head()
353 1.1 kre {
354 1.1 kre atf_set descr "Test realpath (with -e) cases which should work"
355 1.1 kre }
356 1.1 kre a__e_ok_body()
357 1.1 kre {
358 1.1 kre setup
359 1.1 kre run_tests_pass -e "${existing}" "${exist_results}"
360 1.1 kre
361 1.1 kre if [ -x "${ID}" ] && [ "$("$ID" -u)" = 0 ]
362 1.1 kre then
363 1.1 kre run_tests_pass -e "${exist_root_only}" "${exist_root_results}"
364 1.1 kre fi
365 1.1 kre }
366 1.1 kre a__e_ok_cleanup()
367 1.1 kre {
368 1.1 kre cleanup
369 1.1 kre }
370 1.1 kre
371 1.1 kre atf_test_case b__E_ok cleanup
372 1.1 kre b__E_ok_head()
373 1.1 kre {
374 1.1 kre atf_set descr "Test realpath (with -E) cases which should work"
375 1.1 kre }
376 1.1 kre b__E_ok_body() {
377 1.1 kre setup
378 1.1 kre # everything which works with -e should also work with -E
379 1.1 kre run_tests_pass -E "${existing}" "${exist_results}"
380 1.1 kre run_tests_pass -E "${nofile}" "${nofile_results}"
381 1.1 kre
382 1.1 kre if [ -x "${ID}" ] && [ "$("${ID}" -u)" = 0 ]
383 1.1 kre then
384 1.1 kre run_tests_pass -E "${exist_root_only}" "${exist_root_results}"
385 1.1 kre fi
386 1.1 kre }
387 1.1 kre b__E_ok_cleanup()
388 1.1 kre {
389 1.1 kre cleanup
390 1.1 kre }
391 1.1 kre
392 1.1 kre atf_test_case c__ok cleanup
393 1.1 kre c__ok_head()
394 1.1 kre {
395 1.1 kre atf_set descr "Test realpath (without -e or -E) cases which should work"
396 1.1 kre }
397 1.1 kre c__ok_body() {
398 1.1 kre setup
399 1.1 kre # Our default for realpath is -E, so the -E tests should work
400 1.1 kre run_tests_pass '' "${existing}" "${exist_results}"
401 1.1 kre # but more should work as well
402 1.1 kre run_tests_pass '' "${nofile}" "${nofile_results}"
403 1.1 kre
404 1.1 kre if [ -x "${ID}" ] && [ "$("${ID}" -u)" = 0 ]
405 1.1 kre then
406 1.1 kre run_tests_pass '' "${exist_root_only}" "${exist_root_results}"
407 1.1 kre fi
408 1.1 kre }
409 1.1 kre c__ok_cleanup()
410 1.1 kre {
411 1.1 kre cleanup
412 1.1 kre }
413 1.1 kre
414 1.1 kre atf_test_case d__E_fail
415 1.1 kre d__E_fail_head()
416 1.1 kre {
417 1.1 kre atf_set descr "Test realpath -e cases which should not work"
418 1.1 kre }
419 1.1 kre d__E_fail_body()
420 1.1 kre {
421 1.1 kre setup
422 1.1 kre run_tests_fail -E "${always_fail}"
423 1.1 kre if [ -x "${ID}" ] && [ "$("${ID}" -u)" != 0 ]
424 1.1 kre then
425 1.1 kre run_tests_fail -E "${exist_root_only}"
426 1.1 kre fi
427 1.1 kre }
428 1.1 kre d__E_fail_cleanup()
429 1.1 kre {
430 1.1 kre cleanup
431 1.1 kre }
432 1.1 kre
433 1.1 kre atf_test_case e__e_fail
434 1.1 kre e__e_fail_head()
435 1.1 kre {
436 1.1 kre atf_set descr "Test realpath -e cases which should not work"
437 1.1 kre }
438 1.1 kre e__e_fail_body()
439 1.1 kre {
440 1.1 kre setup
441 1.1 kre # Some -E tests that work should fail with -e
442 1.1 kre run_tests_fail -e "${nofile}"
443 1.1 kre run_tests_fail -e "${always_fail}"
444 1.1 kre if [ -x "${ID}" ] && [ "$("${ID}" -u)" != 0 ]
445 1.1 kre then
446 1.1 kre run_tests_fail -e "${exist_root_only}"
447 1.1 kre fi
448 1.1 kre }
449 1.1 kre e__e_fail_cleanup()
450 1.1 kre {
451 1.1 kre cleanup
452 1.1 kre }
453 1.1 kre
454 1.1 kre atf_test_case f__fail
455 1.1 kre f__fail_head()
456 1.1 kre {
457 1.1 kre atf_set descr "Test realpath cases which should not work (w/o -[eE])"
458 1.1 kre }
459 1.1 kre f__fail_body()
460 1.1 kre {
461 1.1 kre setup
462 1.1 kre run_tests_fail '' "${always_fail}"
463 1.1 kre if [ -x "${ID}" ] && [ "$("${ID}" -u)" != 0 ]
464 1.1 kre then
465 1.1 kre run_tests_fail '' "${exist_root_only}"
466 1.1 kre fi
467 1.1 kre }
468 1.1 kre f__fail_cleanup()
469 1.1 kre {
470 1.1 kre cleanup
471 1.1 kre }
472 1.1 kre
473 1.1 kre atf_test_case g__q cleanup
474 1.1 kre g__q_head()
475 1.1 kre {
476 1.1 kre atf_set descr "Test realpath's -q option; also test usage message"
477 1.1 kre }
478 1.1 kre g__q_body()
479 1.1 kre {
480 1.1 kre setup
481 1.1 kre
482 1.1 kre # Just run these tests here, the paths have been tested
483 1.1 kre # already, all we care about is that -q suppresses err messages
484 1.1 kre # about the ones that fail, so just test those. Since those
485 1.1 kre # always fail, it is irrlevant which of -e or -E we would use,
486 1.1 kre # so simply use neither.
487 1.1 kre
488 1.1 kre # This is adapted from run_tests_fail
489 1.1 kre
490 1.1 kre FAILURES=0
491 1.1 kre FAILS=
492 1.1 kre
493 1.1 kre opt=-q
494 1.1 kre
495 1.1 kre T=0
496 1.1 kre for FILE in ${always_fail}
497 1.1 kre do
498 1.1 kre
499 1.1 kre test -z "${FILE}" && continue
500 1.1 kre
501 1.1 kre T=$(( $T + 1 ))
502 1.1 kre
503 1.1 kre GOT=$(realpath $opt -- "${FILE}" 2>StdErr)
504 1.1 kre STATUS=$?
505 1.1 kre
506 1.1 kre ERR=$(cat StdErr)
507 1.1 kre
508 1.1 kre if [ $STATUS -eq 0 ] || [ "${GOT}" ] || [ "${ERR}" ]
509 1.1 kre then
510 1.1 kre FAILURES=$(($FAILURES + 1))
511 1.1 kre if [ "${STATUS}" -eq 0 ]
512 1.1 kre then
513 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T: "
514 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}' worked;"
515 1.1 kre FAILS="${FAILS} received: '${GOT}'}"
516 1.1 kre
517 1.1 kre if [ "${ERR}" ]; then
518 1.1 kre FAILS="${FAILS} and on stderr '${ERR}'"
519 1.1 kre fi
520 1.1 kre elif [ "${GOT}" ]
521 1.1 kre then
522 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
523 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}' failed,"
524 1.1 kre FAILS="${FAILS} but with '${GOT}' on stdout"
525 1.1 kre
526 1.1 kre if [ "${ERR}" ]; then
527 1.1 kre FAILS="${FAILS}, and on stderr '${ERR}'"
528 1.1 kre else
529 1.1 kre FAILS="${FAILS}, and empty stderr"
530 1.1 kre fi
531 1.1 kre else
532 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
533 1.1 kre FAILS="${FAILS}${opt:+ $opt} '${FILE}' failed,"
534 1.1 kre FAILS="${FAILS} stderr: '${ERR}'"
535 1.1 kre fi
536 1.1 kre fi
537 1.1 kre done
538 1.1 kre
539 1.1 kre # There are a couple of cases where -q does not suppress stderr
540 1.1 kre
541 1.1 kre for FILE in '' -wObBl@ --
542 1.1 kre do
543 1.1 kre
544 1.1 kre T=$(( $T + 1 ))
545 1.1 kre
546 1.1 kre unset XTRA
547 1.1 kre case "${FILE}" in
548 1.1 kre '') ;;
549 1.1 kre --) XTRA=;;
550 1.1 kre -*) XTRA=/junk;;
551 1.1 kre esac
552 1.1 kre
553 1.1 kre # Note lack of -- in the following, so $FILE can be either
554 1.1 kre # a file name (well, kind of...), or options.
555 1.1 kre
556 1.1 kre GOT=$(realpath $opt "${FILE}" ${XTRA+"${XTRA}"} 2>StdErr)
557 1.1 kre STATUS=$?
558 1.1 kre
559 1.1 kre ERR=$(cat StdErr)
560 1.1 kre
561 1.1 kre if [ $STATUS -eq 0 ] || [ "${GOT}" ] || ! [ "${ERR}" ]
562 1.1 kre then
563 1.1 kre FAILURES=$(($FAILURES + 1))
564 1.1 kre if [ "${STATUS}" -eq 0 ]
565 1.1 kre then
566 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T: "
567 1.1 kre FAILS="${FAILS}${opt:+ $opt} ${FILE:-''}"
568 1.1 kre FAILS="${FAILS}${XTRA:+ $XTRA} worked;"
569 1.1 kre FAILS="${FAILS} received: '${GOT}'}"
570 1.1 kre
571 1.1 kre if [ "${ERR}" ]; then
572 1.1 kre FAILS="${FAILS} and on stderr '${ERR}'"
573 1.1 kre fi
574 1.1 kre elif [ "${GOT}" ]
575 1.1 kre then
576 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
577 1.1 kre FAILS="${FAILS}${opt:+ $opt} ${FILE:-''}"
578 1.1 kre FAILS="${FAILS}${XTRA:+ ${XTRA}} failed,"
579 1.1 kre FAILS="${FAILS} but with '${GOT}' on stdout"
580 1.1 kre
581 1.1 kre if [ "${ERR}" ]; then
582 1.1 kre FAILS="${FAILS}, and on stderr '${ERR}'"
583 1.1 kre else
584 1.1 kre FAILS="${FAILS}, and empty stderr"
585 1.1 kre fi
586 1.1 kre else
587 1.1 kre FAILS=${FAILS:+"${FAILS}"$'\n'}"Path $T:"
588 1.1 kre FAILS="${FAILS}${opt:+ $opt} ${FILE:-''}"
589 1.1 kre FAILS="${FAILS}${XTRA:+ ${XTRA}} failed,"
590 1.1 kre FAILS="${FAILS} with stderr empty"
591 1.1 kre fi
592 1.1 kre fi
593 1.1 kre done
594 1.1 kre
595 1.1 kre if [ $FAILURES -gt 0 ]
596 1.1 kre then
597 1.1 kre s=s
598 1.1 kre if [ $FAILURES -eq 1 ]; then s=; fi
599 1.1 kre printf >&2 '%d path%s resolved incorrectly:\n%s\n' \
600 1.1 kre "$FAILURES" "$s" "${FAILS}"
601 1.1 kre atf_fail "$FAILURES path$s resolved incorrectly; see stderr"
602 1.1 kre fi
603 1.1 kre return 0
604 1.1 kre }
605 1.1 kre g__q_cleanup()
606 1.1 kre {
607 1.1 kre cleanup
608 1.1 kre }
609 1.1 kre
610 1.1 kre atf_test_case h__n_args
611 1.1 kre h__n_args_head()
612 1.1 kre {
613 1.1 kre atf_set descr "Test realpath with multiple file args"
614 1.1 kre }
615 1.1 kre h__n_args_body()
616 1.1 kre {
617 1.1 kre setup
618 1.1 kre
619 1.1 kre # Since these paths have already (hopefully) tested and work
620 1.1 kre # (if a__e_ok had any failures, fix those before even looking
621 1.1 kre # at any failure here)
622 1.1 kre
623 1.1 kre # Since we are assuming that the test cases all work, simply
624 1.1 kre # Count how many there are, and then expect the same number
625 1.1 kre # of answers
626 1.1 kre
627 1.1 kre unset IFS
628 1.1 kre set -- ${existing}
629 1.1 kre # Note that any empty line (no args) case just vanished...
630 1.1 kre # That would be meaningless here, removing it is correct.
631 1.1 kre
632 1.1 kre GOT=$(realpath -e -- "$@" 2>StdErr)
633 1.1 kre STATUS=$?
634 1.1 kre
635 1.1 kre ERR=$(cat StdErr; printf X)
636 1.1 kre ERR=${ERR%X}
637 1.1 kre
638 1.1 kre NR=$(( $(printf '%s\n' "${GOT}" | wc -l) ))
639 1.1 kre
640 1.1 kre if [ $NR -ne $# ] || [ $STATUS -ne 0 ] || [ -s StdErr ]
641 1.1 kre then
642 1.1 kre printf >&2 'Stderr from test:\n%s\n' "${ERR}"
643 1.1 kre if [ $STATUS -eq 0 ]; then S="OK"; else S="FAIL($STATUS)"; fi
644 1.1 kre if [ ${#ERR} -ne 0 ]
645 1.1 kre then
646 1.1 kre E="${#ERR} bytes on stderr"
647 1.1 kre else
648 1.1 kre E="nothing on stderr"
649 1.1 kre fi
650 1.1 kre atf_fail 'Given %d args, got %d results; Status:%s; %s\n' \
651 1.1 kre "$#" "${NR}" "${S}" "${E}"
652 1.1 kre fi
653 1.1 kre return 0
654 1.1 kre }
655 1.1 kre h__n_args_cleanup()
656 1.1 kre {
657 1.1 kre cleanup
658 1.1 kre }
659 1.1 kre
660 1.1 kre atf_init_test_cases()
661 1.1 kre {
662 1.1 kre atf_add_test_case a__e_ok
663 1.1 kre atf_add_test_case b__E_ok
664 1.1 kre atf_add_test_case c__ok
665 1.1 kre atf_add_test_case d__E_fail
666 1.1 kre atf_add_test_case e__e_fail
667 1.1 kre atf_add_test_case f__fail
668 1.1 kre atf_add_test_case g__q
669 1.1 kre atf_add_test_case h__n_args
670 1.1 kre }
671