blob: 15c53f14a5a6796afa57e58cb45e4fe44a0f1272 [file] [log] [blame]
njn9fb16f52003-04-23 17:47:13 +00001#! @PERL@
njna217f3d2002-09-27 08:26:27 +00002##--------------------------------------------------------------------##
3##--- Valgrind regression testing script vg_regtest ---##
4##--------------------------------------------------------------------##
njnc2e7f482002-09-27 08:44:17 +00005
njnb9c427c2004-12-01 14:14:42 +00006# This file is part of Valgrind, a dynamic binary instrumentation
7# framework.
njnc2e7f482002-09-27 08:44:17 +00008#
njn0e1b5142003-04-15 14:58:06 +00009# Copyright (C) 2003 Nicholas Nethercote
njn2bc10122005-05-08 02:10:27 +000010# njn@valgrind.org
njnc2e7f482002-09-27 08:44:17 +000011#
12# This program is free software; you can redistribute it and/or
13# modify it under the terms of the GNU General Public License as
14# published by the Free Software Foundation; either version 2 of the
15# License, or (at your option) any later version.
16#
17# This program is distributed in the hope that it will be useful, but
18# WITHOUT ANY WARRANTY; without even the implied warranty of
19# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20# General Public License for more details.
21#
22# You should have received a copy of the GNU General Public License
23# along with this program; if not, write to the Free Software
24# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
25# 02111-1307, USA.
26#
27# The GNU General Public License is contained in the file COPYING.
28
29#----------------------------------------------------------------------------
njna217f3d2002-09-27 08:26:27 +000030# usage: vg_regtest [options] <dirs | files>
njn25e49d8e72002-09-23 09:36:25 +000031#
njna217f3d2002-09-27 08:26:27 +000032# Options:
njna217f3d2002-09-27 08:26:27 +000033# --all: run tests in all subdirs
njn3ed89602006-10-23 18:38:35 +000034# --valgrind: valgrind launcher to use. Default is ./coregrind/valgrind.
35# (This option should probably only be used in conjunction with
36# --valgrind-lib.)
37# --valgrind-lib: valgrind libraries to use. Default is $tests_dir/.in_place.
38# (This option should probably only be used in conjunction with
39# --valgrind.)
njna217f3d2002-09-27 08:26:27 +000040#
njn4ba5a792002-09-30 10:23:54 +000041# The easiest way is to run all tests in valgrind/ with (assuming you installed
42# in $PREFIX):
43#
44# $PREFIX/bin/vg_regtest --all
45#
njna217f3d2002-09-27 08:26:27 +000046# You can specify individual files to test, or whole directories, or both.
jsgf855d93d2003-10-13 22:26:55 +000047# Directories are traversed recursively, except for ones named, for example,
48# CVS/ or docs/.
njn25e49d8e72002-09-23 09:36:25 +000049#
50# Each test is defined in a file <test>.vgtest, containing one or more of the
njna217f3d2002-09-27 08:26:27 +000051# following lines, in any order:
njn25e49d8e72002-09-23 09:36:25 +000052# - prog: <prog to run> (compulsory)
53# - args: <args for prog> (default: none)
njnf6b00762009-04-17 04:26:41 +000054# - vgopts: <Valgrind options> (default: none;
55# multiple are allowed)
njn25e49d8e72002-09-23 09:36:25 +000056# - stdout_filter: <filter to run stdout through> (default: none)
njna217f3d2002-09-27 08:26:27 +000057# - stderr_filter: <filter to run stderr through> (default: ./filter_stderr)
nethercotec5e1d802004-11-18 12:48:17 +000058# - prereq: <prerequisite command> (default: none)
njn734b8052007-11-01 04:40:37 +000059# - post: <post-test check command> (default: none)
60# - cleanup: <post-test cleanup cmd> (default: none)
njn25e49d8e72002-09-23 09:36:25 +000061#
njna217f3d2002-09-27 08:26:27 +000062# Note that filters are necessary for stderr results to filter out things that
63# always change, eg. process id numbers.
njn25e49d8e72002-09-23 09:36:25 +000064#
njn1ee25f02008-02-27 18:10:19 +000065# Expected stdout (filtered) is kept in <test>.stdout.exp* (can be more
nethercote4592db62004-02-29 01:31:09 +000066# than one expected output). It can be missing if it would be empty. Expected
sewardj79e88da2007-11-09 23:29:46 +000067# stderr (filtered) is kept in <test>.stderr.exp*. There must be at least
njne8ffe522008-03-02 22:48:14 +000068# one stderr.exp* file. Any .exp* file that ends in '~' or '#' is ignored;
69# this is because Emacs creates temporary files of these names.
njn25e49d8e72002-09-23 09:36:25 +000070#
71# If results don't match, the output can be found in <test>.std<strm>.out,
njn1ee25f02008-02-27 18:10:19 +000072# and the diff between expected and actual in <test>.std<strm>.diff*.
njn25e49d8e72002-09-23 09:36:25 +000073#
njn61485ab2009-03-04 04:15:16 +000074# The prerequisite command, if present, works like this:
75# - if it returns 0 the test is run
76# - if it returns 1 the test is skipped
77# - if it returns anything else the script aborts.
78# The idea here is results other than 0 or 1 are likely to be due to
79# problems with the commands, and you don't want to conflate them with the 1
80# case, which would happen if you just tested for zero or non-zero.
81#
82# The post-test command, if present, must return 0 and its stdout must match
83# the expected stdout which is kept in <test>.post.exp*.
84#
sewardj91368992006-05-26 00:13:21 +000085# Sometimes it is useful to run all the tests at a high sanity check
86# level or with arbitrary other flags. To make this simple, extra
87# options, applied to all tests run, are read from $EXTRA_REGTEST_OPTS,
88# and handed to valgrind prior to any other flags specified by the
89# .vgtest file.
90#
njn7358d522006-11-26 22:49:58 +000091# Some more notes on adding regression tests for a new tool are in
92# docs/xml/manual-writing-tools.xml.
njn25e49d8e72002-09-23 09:36:25 +000093#----------------------------------------------------------------------------
94
njn9fb16f52003-04-23 17:47:13 +000095use warnings;
njn25e49d8e72002-09-23 09:36:25 +000096use strict;
97
98#----------------------------------------------------------------------------
99# Global vars
100#----------------------------------------------------------------------------
sewardja8162b22007-11-30 21:24:05 +0000101my $usage="\n"
102 . "Usage:\n"
103 . " vg_regtest [--all, --valgrind, --valgrind-lib]\n"
104 . " Use EXTRA_REGTEST_OPTS to supply extra args for all tests\n"
105 . "\n";
njn25e49d8e72002-09-23 09:36:25 +0000106
107my $tmp="vg_regtest.tmp.$$";
108
109# Test variables
110my $vgopts; # valgrind options
111my $prog; # test prog
112my $args; # test prog args
113my $stdout_filter; # filter program to run stdout results file through
114my $stderr_filter; # filter program to run stderr results file through
nethercotec5e1d802004-11-18 12:48:17 +0000115my $prereq; # prerequisite test to satisfy before running test
njn734b8052007-11-01 04:40:37 +0000116my $post; # check command after running test
nethercote64bc5af2004-11-18 11:57:00 +0000117my $cleanup; # cleanup command to run
njn25e49d8e72002-09-23 09:36:25 +0000118
119my @failures; # List of failed tests
120
njn9fb16f52003-04-23 17:47:13 +0000121my $num_tests_done = 0;
njn734b8052007-11-01 04:40:37 +0000122my %num_failures = (stderr => 0, stdout => 0, post => 0);
njn25e49d8e72002-09-23 09:36:25 +0000123
njn71fe3e62003-04-23 21:48:20 +0000124# Default valgrind to use is this build tree's (uninstalled) one
njn71fe3e62003-04-23 21:48:20 +0000125my $valgrind = "./coregrind/valgrind";
njn25e49d8e72002-09-23 09:36:25 +0000126
127chomp(my $tests_dir = `pwd`);
128
njn3ed89602006-10-23 18:38:35 +0000129my $valgrind_lib = "$tests_dir/.in_place";
130
njn25e49d8e72002-09-23 09:36:25 +0000131# default filter is the one named "filter_stderr" in the test's directory
132my $default_stderr_filter = "filter_stderr";
133
134
135#----------------------------------------------------------------------------
136# Process command line, setup
137#----------------------------------------------------------------------------
138
139# If $prog is a relative path, it prepends $dir to it. Useful for two reasons:
140#
141# 1. Can prepend "." onto programs to avoid trouble with users who don't have
142# "." in their path (by making $dir = ".")
143# 2. Can prepend the current dir to make the command absolute to avoid
144# subsequent trouble when we change directories.
145#
146# Also checks the program exists and is executable.
nethercotef4928da2004-06-15 10:54:40 +0000147sub validate_program ($$$$)
njn25e49d8e72002-09-23 09:36:25 +0000148{
nethercotef4928da2004-06-15 10:54:40 +0000149 my ($dir, $prog, $must_exist, $must_be_executable) = @_;
njn25e49d8e72002-09-23 09:36:25 +0000150
151 # If absolute path, leave it alone. If relative, make it
152 # absolute -- by prepending current dir -- so we can change
153 # dirs and still use it.
154 $prog = "$dir/$prog" if ($prog !~ /^\//);
nethercotef4928da2004-06-15 10:54:40 +0000155 if ($must_exist) {
156 (-f $prog) or die "vg_regtest: `$prog' not found or not a file ($dir)\n";
157 }
njn71fe3e62003-04-23 21:48:20 +0000158 if ($must_be_executable) {
nethercotef4928da2004-06-15 10:54:40 +0000159 (-x $prog) or die "vg_regtest: `$prog' not executable ($dir)\n";
njn71fe3e62003-04-23 21:48:20 +0000160 }
njn25e49d8e72002-09-23 09:36:25 +0000161
162 return $prog;
163}
164
165sub process_command_line()
166{
167 my $alldirs = 0;
168 my @fs;
169
170 for my $arg (@ARGV) {
171 if ($arg =~ /^-/) {
njnd8ced862003-04-08 00:47:05 +0000172 if ($arg =~ /^--all$/) {
njn25e49d8e72002-09-23 09:36:25 +0000173 $alldirs = 1;
174 } elsif ($arg =~ /^--valgrind=(.*)$/) {
175 $valgrind = $1;
njn3ed89602006-10-23 18:38:35 +0000176 } elsif ($arg =~ /^--valgrind-lib=(.*)$/) {
177 $valgrind_lib = $1;
njn25e49d8e72002-09-23 09:36:25 +0000178 } else {
179 die $usage;
180 }
181 } else {
182 push(@fs, $arg);
183 }
184 }
nethercotef4928da2004-06-15 10:54:40 +0000185 $valgrind = validate_program($tests_dir, $valgrind, 1, 0);
njn25e49d8e72002-09-23 09:36:25 +0000186
187 if ($alldirs) {
188 @fs = ();
189 foreach my $f (glob "*") {
190 push(@fs, $f) if (-d $f);
191 }
192 }
193
194 (0 != @fs) or die "No test files or directories specified\n";
195
196 return @fs;
197}
198
199#----------------------------------------------------------------------------
200# Read a .vgtest file
201#----------------------------------------------------------------------------
202sub read_vgtest_file($)
203{
204 my ($f) = @_;
205
206 # Defaults.
njn0001fc32006-04-03 14:25:23 +0000207 ($vgopts, $prog, $args) = ("", undef, "");
208 ($stdout_filter, $stderr_filter) = (undef, undef);
njn734b8052007-11-01 04:40:37 +0000209 ($prereq, $post, $cleanup) = (undef, undef, undef);
njn25e49d8e72002-09-23 09:36:25 +0000210
211 # Every test directory must have a "filter_stderr"
nethercotef4928da2004-06-15 10:54:40 +0000212 $stderr_filter = validate_program(".", $default_stderr_filter, 1, 1);
njn25e49d8e72002-09-23 09:36:25 +0000213
214 open(INPUTFILE, "< $f") || die "File $f not openable\n";
215
216 while (my $line = <INPUTFILE>) {
sewardjb5f6f512005-03-10 23:59:00 +0000217 if ($line =~ /^\s*#/ || $line =~ /^\s*$/) {
218 next;
219 } elsif ($line =~ /^\s*vgopts:\s*(.*)$/) {
njnf6b00762009-04-17 04:26:41 +0000220 $vgopts = $vgopts . " " . $1; # Nb: Make sure there's a space!
njn25e49d8e72002-09-23 09:36:25 +0000221 } elsif ($line =~ /^\s*prog:\s*(.*)$/) {
nethercotef4928da2004-06-15 10:54:40 +0000222 $prog = validate_program(".", $1, 0, 0);
njn25e49d8e72002-09-23 09:36:25 +0000223 } elsif ($line =~ /^\s*args:\s*(.*)$/) {
224 $args = $1;
njn25e49d8e72002-09-23 09:36:25 +0000225 } elsif ($line =~ /^\s*stdout_filter:\s*(.*)$/) {
nethercotef4928da2004-06-15 10:54:40 +0000226 $stdout_filter = validate_program(".", $1, 1, 1);
njn25e49d8e72002-09-23 09:36:25 +0000227 } elsif ($line =~ /^\s*stderr_filter:\s*(.*)$/) {
nethercotef4928da2004-06-15 10:54:40 +0000228 $stderr_filter = validate_program(".", $1, 1, 1);
nethercotec5e1d802004-11-18 12:48:17 +0000229 } elsif ($line =~ /^\s*prereq:\s*(.*)$/) {
230 $prereq = $1;
njn734b8052007-11-01 04:40:37 +0000231 } elsif ($line =~ /^\s*post:\s*(.*)$/) {
232 $post = $1;
nethercote64bc5af2004-11-18 11:57:00 +0000233 } elsif ($line =~ /^\s*cleanup:\s*(.*)$/) {
234 $cleanup = $1;
njn25e49d8e72002-09-23 09:36:25 +0000235 } else {
236 die "Bad line in $f: $line\n";
237 }
238 }
239 close(INPUTFILE);
240
241 if (!defined $prog) {
nethercotef4928da2004-06-15 10:54:40 +0000242 $prog = ""; # allow no prog for testing error and --help cases
njn25e49d8e72002-09-23 09:36:25 +0000243 }
244}
245
246#----------------------------------------------------------------------------
247# Do one test
248#----------------------------------------------------------------------------
249# Since most of the program time is spent in system() calls, need this to
250# propagate a Ctrl-C enabling us to quit.
251sub mysystem($)
252{
njn734b8052007-11-01 04:40:37 +0000253 my $exit_code = system($_[0]);
254 ($exit_code == 2) and exit 1; # 2 is SIGINT
255 return $exit_code;
njn25e49d8e72002-09-23 09:36:25 +0000256}
257
nethercote137bc552003-11-14 17:47:54 +0000258# from a directory name like "/foo/cachesim/tests/" determine the tool name
259sub determine_tool()
njn25cac76cb2002-09-23 11:21:57 +0000260{
261 my $dir = `pwd`;
nethercote137bc552003-11-14 17:47:54 +0000262 $dir =~ /.*\/([^\/]+)\/tests.*/; # foo/tool_name/tests/foo
njn25cac76cb2002-09-23 11:21:57 +0000263 return $1;
264}
265
nethercote4592db62004-02-29 01:31:09 +0000266# Compare output against expected output; it should match at least one of
267# them.
268sub do_diffs($$$$)
269{
270 my ($fullname, $name, $mid, $f_exps) = @_;
271
272 for my $f_exp (@$f_exps) {
273 (-r $f_exp) or die "Could not read `$f_exp'\n";
274
njne8ffe522008-03-02 22:48:14 +0000275 # Emacs produces temporary files that end in '~' and '#'. We ignore
276 # these.
277 if ($f_exp !~ /[~#]$/) {
278 # $n is the (optional) suffix after the ".exp"; we tack it onto
279 # the ".diff" file.
280 my $n = "";
281 if ($f_exp =~ /.*\.exp(.*)$/) {
282 $n = $1;
283 } else {
284 $n = "";
285 ($f_exp eq "/dev/null") or die "Unexpected .exp file: $f_exp\n";
286 }
nethercote4592db62004-02-29 01:31:09 +0000287
njn0d2e58f2009-02-25 04:57:56 +0000288 mysystem("@DIFF@ $f_exp $name.$mid.out > $name.$mid.diff$n");
nethercote4592db62004-02-29 01:31:09 +0000289
njne8ffe522008-03-02 22:48:14 +0000290 if (not -s "$name.$mid.diff$n") {
291 # A match; remove .out and any previously created .diff files.
292 unlink("$name.$mid.out");
293 unlink(<$name.$mid.diff*>);
294 return;
295 }
nethercote4592db62004-02-29 01:31:09 +0000296 }
297 }
298 # If we reach here, none of the .exp files matched.
299 print "*** $name failed ($mid) ***\n";
300 push(@failures, sprintf("%-40s ($mid)", "$fullname"));
301 $num_failures{$mid}++;
302}
303
njn25e49d8e72002-09-23 09:36:25 +0000304sub do_one_test($$)
305{
306 my ($dir, $vgtest) = @_;
307 $vgtest =~ /^(.*)\.vgtest/;
308 my $name = $1;
309 my $fullname = "$dir/$name";
310
sewardj91368992006-05-26 00:13:21 +0000311 # Pull any extra options (for example, --sanity-level=4)
312 # from $EXTRA_REGTEST_OPTS.
313 my $maybe_extraopts = $ENV{"EXTRA_REGTEST_OPTS"};
314 my $extraopts = $maybe_extraopts ? $maybe_extraopts : "";
315
njn25e49d8e72002-09-23 09:36:25 +0000316 read_vgtest_file($vgtest);
317
nethercotec5e1d802004-11-18 12:48:17 +0000318 if (defined $prereq) {
njn61485ab2009-03-04 04:15:16 +0000319 my $prereq_res = system("$prereq");
320 if (0 == $prereq_res) {
321 # Do nothing (ie. continue with the test)
322 } elsif (256 == $prereq_res) {
323 # Nb: weird Perl-ism -- exit code of '1' is seen by Perl as 256...
324 # Prereq failed, skip.
nethercotec5e1d802004-11-18 12:48:17 +0000325 printf("%-16s (skipping, prereq failed: $prereq)\n", "$name:");
nethercote781bed42004-10-19 16:56:41 +0000326 return;
njn61485ab2009-03-04 04:15:16 +0000327 } else {
328 # Bad prereq; abort.
329 $prereq_res /= 256;
330 die "prereq returned $prereq_res: $prereq\n";
nethercote781bed42004-10-19 16:56:41 +0000331 }
nethercoteb1affa82004-01-19 19:14:18 +0000332 }
333
sewardj91368992006-05-26 00:13:21 +0000334 printf("%-16s valgrind $extraopts $vgopts $prog $args\n", "$name:");
njn25e49d8e72002-09-23 09:36:25 +0000335
nethercote137bc552003-11-14 17:47:54 +0000336 # Pass the appropriate --tool option for the directory (can be overridden
njnefc94ad2005-11-12 16:08:09 +0000337 # by an "args:" line, though). Set both VALGRIND_LIB and
338 # VALGRIND_LIB_INNER in case this Valgrind was configured with
339 # --enable-inner.
nethercote137bc552003-11-14 17:47:54 +0000340 my $tool=determine_tool();
njn3ed89602006-10-23 18:38:35 +0000341 mysystem("VALGRIND_LIB=$valgrind_lib VALGRIND_LIB_INNER=$valgrind_lib "
njnefc94ad2005-11-12 16:08:09 +0000342 . "$valgrind --command-line-only=yes --memcheck:leak-check=no "
sewardj91368992006-05-26 00:13:21 +0000343 . "--tool=$tool $extraopts $vgopts "
njnefc94ad2005-11-12 16:08:09 +0000344 . "$prog $args > $name.stdout.out 2> $name.stderr.out");
njn25e49d8e72002-09-23 09:36:25 +0000345
njn0001fc32006-04-03 14:25:23 +0000346 # Filter stdout
njn25e49d8e72002-09-23 09:36:25 +0000347 if (defined $stdout_filter) {
348 mysystem("$stdout_filter < $name.stdout.out > $tmp");
349 rename($tmp, "$name.stdout.out");
350 }
nethercote4592db62004-02-29 01:31:09 +0000351 # Find all the .stdout.exp files. If none, use /dev/null.
352 my @stdout_exps = <$name.stdout.exp*>;
353 @stdout_exps = ( "/dev/null" ) if (0 == scalar @stdout_exps);
njn0001fc32006-04-03 14:25:23 +0000354 do_diffs($fullname, $name, "stdout", \@stdout_exps);
njn25e49d8e72002-09-23 09:36:25 +0000355
njn0001fc32006-04-03 14:25:23 +0000356 # Filter stderr
357 mysystem("$stderr_filter < $name.stderr.out > $tmp");
358 rename($tmp, "$name.stderr.out");
sewardj79e88da2007-11-09 23:29:46 +0000359 # Find all the .stderr.exp files. At least one must exist.
nethercote4592db62004-02-29 01:31:09 +0000360 my @stderr_exps = <$name.stderr.exp*>;
sewardj79e88da2007-11-09 23:29:46 +0000361 (0 != scalar @stderr_exps) or die "Could not find `$name.stderr.exp*'\n";
nethercote4592db62004-02-29 01:31:09 +0000362 do_diffs($fullname, $name, "stderr", \@stderr_exps);
njn0001fc32006-04-03 14:25:23 +0000363
364 # Maybe do post-test check
njn734b8052007-11-01 04:40:37 +0000365 if (defined $post) {
366 if (mysystem("$post > $name.post.out") != 0) {
367 print("post check failed: $post\n");
368 $num_failures{"post"}++;
njn0001fc32006-04-03 14:25:23 +0000369 } else {
njn734b8052007-11-01 04:40:37 +0000370 # Find all the .post.exp files. If none, use /dev/null.
371 my @post_exps = <$name.post.exp*>;
372 @post_exps = ( "/dev/null" ) if (0 == scalar @post_exps);
373 do_diffs($fullname, $name, "post", \@post_exps);
njn0001fc32006-04-03 14:25:23 +0000374 }
375 }
nethercotec1f8ad92004-04-17 17:25:08 +0000376
nethercote64bc5af2004-11-18 11:57:00 +0000377 if (defined $cleanup) {
378 (system("$cleanup") == 0) or
379 print("(cleanup operation failed: $cleanup)\n");
nethercotec1f8ad92004-04-17 17:25:08 +0000380 }
381
njn9fb16f52003-04-23 17:47:13 +0000382 $num_tests_done++;
njn25e49d8e72002-09-23 09:36:25 +0000383}
384
385#----------------------------------------------------------------------------
njn25cac76cb2002-09-23 11:21:57 +0000386# Test one directory (and any subdirs)
njn25e49d8e72002-09-23 09:36:25 +0000387#----------------------------------------------------------------------------
njndb3c4692002-10-04 10:03:34 +0000388sub test_one_dir($$); # forward declaration
njn25cac76cb2002-09-23 11:21:57 +0000389
njndb3c4692002-10-04 10:03:34 +0000390sub test_one_dir($$)
njn25e49d8e72002-09-23 09:36:25 +0000391{
njndb3c4692002-10-04 10:03:34 +0000392 my ($dir, $prev_dirs) = @_;
njn25e49d8e72002-09-23 09:36:25 +0000393 $dir =~ s/\/$//; # trim a trailing '/'
394
nethercote362c0d22004-11-18 18:21:56 +0000395 # Ignore dirs into which we should not recurse.
mueller92f0b802003-11-19 00:55:32 +0000396 if ($dir =~ /^(BitKeeper|CVS|SCCS|docs|doc)$/) { return; }
njn25cac76cb2002-09-23 11:21:57 +0000397
njn107bc572009-02-16 00:42:10 +0000398 (-x "$tests_dir/tests/arch_test") or die
399 "vg_regtest: 'arch_test' is missing. Did you forget to 'make check'?\n";
njn52783ca2005-12-08 22:39:04 +0000400
nethercote362c0d22004-11-18 18:21:56 +0000401 # Ignore any dir whose name matches that of an architecture which is not
njn107bc572009-02-16 00:42:10 +0000402 # the architecture we are running on. Eg. when running on x86, ignore
403 # ppc/ directories ('arch_test' returns 1 for this case). Likewise for
404 # the OS and platform.
nethercote362c0d22004-11-18 18:21:56 +0000405 # Nb: weird Perl-ism -- exit code of '1' is seen by Perl as 256...
njn61485ab2009-03-04 04:15:16 +0000406 if (256 == system("$tests_dir/tests/arch_test $dir")) { return; }
407 if (256 == system("$tests_dir/tests/os_test $dir")) { return; }
njn107bc572009-02-16 00:42:10 +0000408 if ($dir =~ /(\w+)-(\w+)/ &&
409 256 == system("sh $tests_dir/tests/platform_test $1 $2")) { return; }
nethercote362c0d22004-11-18 18:21:56 +0000410
njn25e49d8e72002-09-23 09:36:25 +0000411 chdir($dir) or die "Could not change into $dir\n";
412
njn584eaac2002-10-04 15:30:48 +0000413 # Nb: Don't prepend a '/' to the base directory
414 my $full_dir = $prev_dirs . ($prev_dirs eq "" ? "" : "/") . $dir;
njndb3c4692002-10-04 10:03:34 +0000415 my $dashes = "-" x (50 - length $full_dir);
njn25cac76cb2002-09-23 11:21:57 +0000416
njndb3c4692002-10-04 10:03:34 +0000417 my @fs = glob "*";
njndb3c4692002-10-04 10:03:34 +0000418 my $found_tests = (0 != (grep { $_ =~ /\.vgtest$/ } @fs));
419
420 if ($found_tests) {
421 print "-- Running tests in $full_dir $dashes\n";
njndb3c4692002-10-04 10:03:34 +0000422 }
njn25cac76cb2002-09-23 11:21:57 +0000423 foreach my $f (@fs) {
424 if (-d $f) {
njndb3c4692002-10-04 10:03:34 +0000425 test_one_dir($f, $full_dir);
njn25cac76cb2002-09-23 11:21:57 +0000426 } elsif ($f =~ /\.vgtest$/) {
njndb3c4692002-10-04 10:03:34 +0000427 do_one_test($full_dir, $f);
njn25cac76cb2002-09-23 11:21:57 +0000428 }
njn25e49d8e72002-09-23 09:36:25 +0000429 }
njndb3c4692002-10-04 10:03:34 +0000430 if ($found_tests) {
431 print "-- Finished tests in $full_dir $dashes\n";
432 }
433
njn25e49d8e72002-09-23 09:36:25 +0000434 chdir("..");
njn25e49d8e72002-09-23 09:36:25 +0000435}
436
437#----------------------------------------------------------------------------
438# Summarise results
439#----------------------------------------------------------------------------
njn9fb16f52003-04-23 17:47:13 +0000440sub plural($)
441{
442 return ( $_[0] == 1 ? "" : "s" );
443}
444
njn25e49d8e72002-09-23 09:36:25 +0000445sub summarise_results
446{
njnd8ced862003-04-08 00:47:05 +0000447 my $x = ( $num_tests_done == 1 ? "test" : "tests" );
njnd8ced862003-04-08 00:47:05 +0000448
njn0001fc32006-04-03 14:25:23 +0000449 printf("\n== %d test%s, %d stderr failure%s, %d stdout failure%s, "
njn734b8052007-11-01 04:40:37 +0000450 . "%d post failure%s ==\n",
njn9fb16f52003-04-23 17:47:13 +0000451 $num_tests_done, plural($num_tests_done),
njn0001fc32006-04-03 14:25:23 +0000452 $num_failures{"stderr"}, plural($num_failures{"stderr"}),
453 $num_failures{"stdout"}, plural($num_failures{"stdout"}),
njn734b8052007-11-01 04:40:37 +0000454 $num_failures{"post"}, plural($num_failures{"post"}));
njn9fb16f52003-04-23 17:47:13 +0000455
456 foreach my $failure (@failures) {
457 print "$failure\n";
njn25e49d8e72002-09-23 09:36:25 +0000458 }
njn9fb16f52003-04-23 17:47:13 +0000459 print "\n";
njn25e49d8e72002-09-23 09:36:25 +0000460}
461
462#----------------------------------------------------------------------------
463# main(), sort of
464#----------------------------------------------------------------------------
sewardj91368992006-05-26 00:13:21 +0000465sub warn_about_EXTRA_REGTEST_OPTS()
466{
467 print "WARNING: \$EXTRA_REGTEST_OPTS is set. You probably don't want\n";
468 print "to run the regression tests with it set, unless you are doing some\n";
469 print "strange experiment, and/or you really know what you are doing.\n";
470 print "\n";
471}
njn25e49d8e72002-09-23 09:36:25 +0000472
daywalkerbb936982003-04-23 16:52:06 +0000473# nuke VALGRIND_OPTS
474$ENV{"VALGRIND_OPTS"} = "";
njn25e49d8e72002-09-23 09:36:25 +0000475
sewardj91368992006-05-26 00:13:21 +0000476if ($ENV{"EXTRA_REGTEST_OPTS"}) {
477 print "\n";
478 warn_about_EXTRA_REGTEST_OPTS();
479}
480
njn25e49d8e72002-09-23 09:36:25 +0000481my @fs = process_command_line();
482foreach my $f (@fs) {
483 if (-d $f) {
njn584eaac2002-10-04 15:30:48 +0000484 test_one_dir($f, "");
njn25e49d8e72002-09-23 09:36:25 +0000485 } else {
486 # Allow the .vgtest suffix to be given or omitted
487 if ($f =~ /.vgtest$/ && -r $f) {
488 # do nothing
489 } elsif (-r "$f.vgtest") {
490 $f = "$f.vgtest";
491 } else {
492 die "`$f' neither a directory nor a readable test file/name\n"
493 }
494 my $dir = `dirname $f`; chomp $dir;
495 my $file = `basename $f`; chomp $file;
496 chdir($dir) or die "Could not change into $dir\n";
497 do_one_test($dir, $file);
498 chdir($tests_dir);
499 }
500}
501summarise_results();
502
sewardj91368992006-05-26 00:13:21 +0000503if ($ENV{"EXTRA_REGTEST_OPTS"}) {
504 warn_about_EXTRA_REGTEST_OPTS();
505}
506
njn0001fc32006-04-03 14:25:23 +0000507if (0 == $num_failures{"stdout"} &&
508 0 == $num_failures{"stderr"} &&
njn734b8052007-11-01 04:40:37 +0000509 0 == $num_failures{"post"}) {
nethercoteab422192004-03-01 08:27:37 +0000510 exit 0;
511} else {
512 exit 1;
513}
514
njnc2e7f482002-09-27 08:44:17 +0000515##--------------------------------------------------------------------##
516##--- end vg_regtest ---##
517##--------------------------------------------------------------------##