84ee1a4b8955d637c09520750b4f43aff25848c5
[sbcl.git] / subr.sh
1 # To be sourced by shell scripts in the test suite.
2
3 # This software is part of the SBCL system. See the README file for
4 # more information.
5 #
6 # While most of SBCL is derived from the CMU CL system, the test
7 # files (like this one) were written from scratch after the fork
8 # from CMU CL.
9 #
10 # This software is in the public domain and is provided with
11 # absolutely no warranty. See the COPYING and CREDITS files for
12 # more information.
13
14 # Before sbcl-1.0.13 or so, we set up some environment variables to
15 # the absolute (POSIX) pathname naming the SBCL runtime, core, and
16 # home; but this runs afoul of the Bourne shell's repeated
17 # tokenization of its inputs, so now we use some shell functions.
18 . ../sbcl-pwd.sh
19 sbcl_pwd
20
21 # Make the shell bomb out whenever an unset shell variable is used.
22 # Note that scripts may toggle this if necessary.
23 set -u
24
25 # Initialize variables.
26 set -a # export all variables at assignment-time.
27 # Note: any script that uses the variables that name files should
28 # quote them (with double quotes), to contend with whitespace.
29 SBCL_HOME="$SBCL_PWD/../contrib"
30 SBCL_CORE="$SBCL_PWD/../output/sbcl.core"
31 SBCL_RUNTIME="$SBCL_PWD/../src/runtime/sbcl"
32 SBCL_ARGS="--noinform --no-sysinit --no-userinit --noprint --disable-debugger"
33
34 # Scripts that use these variables should quote them.
35 TEST_BASENAME="`basename $0`"
36 TEST_FILESTEM="`basename "${TEST_BASENAME}" | sed 's/\.sh$//'`"
37 TEST_FILESTEM="`echo "${TEST_FILESTEM}" | sed 's/\./-/g'`"
38 TEST_DIRECTORY="$SBCL_PWD/$TEST_FILESTEM-$$"
39
40 # "Ten four" is the closest numerical slang I can find to "OK", so
41 # it's the Unix status value that we expect from a successful test.
42 # (Of course, zero is the usual success value, but we don't want to
43 # use that because SBCL returns that by default, so we might think
44 # we passed a test when in fact some error caused us to exit SBCL
45 # in a weird unexpected way. In contrast, 104 is unlikely to be
46 # returned unless we exit through the intended explicit "test
47 # successful" path.
48 EXIT_TEST_WIN=104
49 # Shell scripts in this test suite also return 104, so we need a
50 # convention for distinguishing successful execution of SBCL in one of
51 # our scripts.
52 EXIT_LISP_WIN=52
53 # Any test that exits with status 1 is an explicit failure.
54 EXIT_LOSE=1
55
56 LANG=C
57 LC_ALL=C
58 set +a
59
60 run_sbcl () (
61     set -u
62     if [ $# -gt 0 ]; then
63         "$SBCL_RUNTIME" --core "$SBCL_CORE" $SBCL_ARGS "$@"
64     else
65         "$SBCL_RUNTIME" --core "$SBCL_CORE" $SBCL_ARGS
66     fi
67 )
68
69 run_sbcl_with_args () (
70     set -u
71     "$SBCL_RUNTIME" --core "$SBCL_CORE" "$@"
72 )
73
74 run_sbcl_with_core () (
75     set -u
76     core="$1"
77     shift
78     if [ $# -gt 0 ]; then
79         "$SBCL_RUNTIME" --core "$core" "$@"
80     else
81         "$SBCL_RUNTIME" --core "$core" $SBCL_ARGS
82     fi
83 )
84
85 # Most tests that run an SBCL have to check whether the child's exit
86 # status.  Our convention is that SBCL exits with status
87 # $EXIT_LISP_WIN to indicate a successful run; but some tests can't do
88 # this (e.g., ones that end in S-L-A-D), or need to indicate some
89 # other ways of succeeding.  So this routine takes a test name, the
90 # exit status of the child, and then an arbitrary number extra
91 # arguments that will be treated as status-code/message pairs for
92 # unusual successful ways for the inferior SBCL to exit.  If the exit
93 # code of the SBCL isn't found in the status-codes, the calling script
94 # will exit with a failure code.
95 check_status_maybe_lose () {
96     testname=$1
97     status=$2
98     lose=1
99     if [ $status = $EXIT_LISP_WIN ]; then
100         echo "test $testname ok"
101         lose=0
102     else
103         shift; shift;
104         while [ $# -gt 0 ]; do
105             if [ $status = $1 ]; then
106                 shift;
107                 echo "test $testname ok $1"
108                 lose=0
109                 break
110             fi
111             shift; shift
112         done
113     fi
114     if [ $lose = 1 ]; then
115         echo "test $testname failed: $status"
116         exit $EXIT_LOSE
117     fi
118     unset lose
119     unset status
120     unset testname
121 }
122
123 # Not every test needs to touch the file system, but enough do to have
124 # them consistently do so in subdirectories.  Note that such tests
125 # should not change their exit action, or do so only very carefully.
126 use_test_subdirectory () {
127     if test -d "$TEST_DIRECTORY"
128     then
129         cleanup_test_subdirectory
130     fi
131     mkdir "$TEST_DIRECTORY"
132     cd "$TEST_DIRECTORY"
133     trap "cleanup_test_subdirectory" EXIT
134 }
135
136 cleanup_test_subdirectory () {
137     cd "$SBCL_PWD"
138     ( set -f; rm -r "$TEST_DIRECTORY" )
139 }