2 # -*- Mode: Perl; tab-width: 4; indent-tabs-mode: nil; -*-
3 # ***** BEGIN LICENSE BLOCK *****
4 # Version: MPL 1.1/GPL 2.0/LGPL 2.1
6 # The contents of this file are subject to the Mozilla Public License Version
7 # 1.1 (the "License"); you may not use this file except in compliance with
8 # the License. You may obtain a copy of the License at
9 # http://www.mozilla.org/MPL/
11 # Software distributed under the License is distributed on an "AS IS" basis,
12 # WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
13 # for the specific language governing rights and limitations under the
16 # The Original Code is Mozilla JavaScript Testing Utilities
18 # The Initial Developer of the Original Code is
19 # Mozilla Corporation.
20 # Portions created by the Initial Developer are Copyright (C) 2007
21 # the Initial Developer. All Rights Reserved.
23 # Contributor(s): Bob Clary <bclary@bclary.com>
25 # Alternatively, the contents of this file may be used under the terms of
26 # either the GNU General Public License Version 2 or later (the "GPL"), or
27 # the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
28 # in which case the provisions of the GPL or the LGPL are applicable instead
29 # of those above. If you wish to allow use of your version of this file only
30 # under the terms of either the GPL or the LGPL, and not to allow others to
31 # use your version of this file under the terms of the MPL, indicate your
32 # decision by deleting the provisions above and replace them with the notice
33 # and other provisions required by the GPL or the LGPL. If you do not delete
34 # the provisions above, a recipient may use your version of this file under
35 # the terms of any one of the MPL, the GPL or the LGPL.
37 # ***** END LICENSE BLOCK *****
39 use Getopt
::Mixed
"nextOption";
40 use File
::Temp qw
/ tempfile tempdir /;
49 my $debug = $ENV{DEBUG
};
50 my $test_dir = $ENV{TEST_DIR
};
52 die "FATAL ERROR: environment variable TEST_DIR must be set to the Sisyphus root directory" unless ($test_dir);
54 # required for mac os x 10.5 to prevent sort from
55 # complaining about illegal byte sequences
58 (undef, $temp) = tempfile
();
60 open TEMP
, ">$temp" or
61 die "FATAL ERROR: Unable to open temporary file $temp for writing: $!\n";
65 $tmp_test_exit_status,
77 @expected_exit_code_list,
82 local $test_memory = 0;
83 local $test_cpuspeed = 0;
84 local %test_reported = ();
85 local $test_repo = 'CVS';
87 while ($file = shift @ARGV)
93 my $filename = basename
$file;
95 dbg
"filename: $file";
97 local ($test_date, $test_product, $test_branchid, $test_buildtype,
99 $test_machine,$test_global_target) = split /,/, $filename;
101 $test_branchid =~ s/[^0-9.]//g;
102 $test_global_target =~ s/.log$//;
104 local ($test_timezone) = $test_date;
105 $test_timezone =~ s/.*([-+]\d{4,4})/$1/;
109 if ($file =~ /\.bz2$/)
111 $filemode = "bzcat $file|";
113 elsif ($file =~ /\.gz$/)
115 $filemode = "zcat $file|";
119 $filemode = "<$file";
122 open FILE
, "$filemode" or die "FATAL ERROR: unable to open $file for reading: $!\n";
124 dbg
"process header with environment variables used in test";
132 # remove carriage returns, bels and other annoyances.
135 $_ =~ s/[\x01-\x08]//g;
143 last if ( $_ =~ /^arguments:/);
145 if (($envval) = $_ =~ /^environment: TEST_MOZILLA_HG=http:\/\
/hg.mozilla.org\/(.*)/ )
147 $test_repo = $envval;
149 elsif (($envvar, $envval) = $_ =~ /^environment: (TEST_[A-Z0-9_]*)=(.*)/ )
151 dbg
"envvar=$envvar, envval=$envval";
152 if ($envvar =~ /TEST_KERNEL/)
154 $envval =~ s/([0-9]+)\.([0-9]+)\.([0-9]+).*/$1.$2.$3/;
155 dbg
"found TEST_KERNEL";
157 $envvar =~ tr/A-Z/a-z/;
159 dbg
$envvar . "=" . $$envvar;
161 elsif (($envval) = $_ =~ /^environment: OSID=(.*)/ )
167 if ($test_cpuspeed < 4)
169 $test_cpuspeed = 'slow';
171 elsif ($test_cpuspeed < 9)
173 $test_cpuspeed = 'medium';
177 $test_cpuspeed = 'fast';
180 if ($test_product eq "js")
182 $test_type = "shell";
184 elsif ($test_product eq "firefox" || $test_product eq "thunderbird")
186 $test_buildtype = "nightly" unless $test_buildtype;
187 $test_type = "browser";
190 # Expected sequence if all output written to the log.
193 # -----------------------------
194 # JavaScriptTest: Begin Run
195 # JavaScriptTest: Begin Test t;
198 # JavaScriptTest: End Test t
199 # JavaScriptTest: End Run
204 $test_exit_status = '';
218 $_ =~ s/[\x01-\x08]//g;
221 if ( /^JavaScriptTest: Begin Run/)
225 if ($state eq 'idle')
231 warn "WARNING: state: $state, expected: idle, log: $file";
235 elsif ( ($tmp_test_id) = $_ =~ /^JavaScriptTest: Begin Test ([^ ]*)/)
237 dbg
"Begin Test: $tmp_test_id";
239 if ($state eq 'beginrun' || $state eq 'endtest')
241 $state = 'runningtest';
245 warn "WARNING: state: $state, expected: beginrun, endtest, log: $file";
246 $state = 'runningtest';
249 $test_id{$state} = $tmp_test_id;
251 @expected_exit_code_list = ();
252 $expected_exit_code = ();
256 $test_exit_status = 'NORMAL'; # default to normal, so subtests will have a NORMAL status
257 $test_description = '';
259 push @expected_exit_code_list, (3) if ($tmp_test_id =~ /-n.js$/);
262 elsif ( ($expected_exit_code) = $_ =~ /WE EXPECT EXIT CODE ([0-9]*)/ )
264 dbg
"Expected Exit Code: $expected_exit_code";
266 push @expected_exit_code_list, ($expected_exit_code);
268 elsif ( ($tmp_test_id) = $_ =~ /^jstest: (.*?) *bug:/)
270 dbg
"jstest: $tmp_test_id";
272 # if ($test_id{$state} && $tmp_test_id ne $test_id{$state})
274 # warn "WARNING: state: $state, expected runningtest, reportingtest. mismatched test_id: expected: $tmp_test_id, actual: $test_id{$state}, log: $file";
277 if ($state eq 'runningtest')
279 $state = 'reportingtest';
281 elsif ($state eq 'reportingtest')
283 $state = 'reportingtest';
287 warn "WARNING: test_id: $test_id{$state}, state: $state, expected: runningtest, reportingtest, log: $file";
288 $state = 'reportingtest';
291 ($test_result) = $_ =~ /result: (.*?) *type:/;
292 ($tmp_test_type) = $_ =~ /type: (.*?) *description:/;
294 die "FATAL ERROR: test_id: $test_id{$state}, jstest test type mismatch: start test_type: $test_type, current test_type: $tmp_test_type, test state: $state, log: $file"
295 if ($test_type ne $tmp_test_type);
297 ($test_description) = $_ =~ /description: (.*)/;
299 if (!$test_description)
301 $test_description = "";
303 $test_description .= '; messages: ' . (join '; ', @messages) . ';';
305 outputrecord
$tmp_test_id, $test_description, $test_result;
307 $test_id{$state} = $tmp_test_id;
309 elsif ( $state ne 'idle' && (($tmp_test_id) = $_ =~ /^([^:]*):.* EXIT STATUS: NORMAL/))
311 $test_exit_status = 'NORMAL';
312 dbg
"Exit Status Normal: $tmp_test_id, $test_exit_status";
314 if ($test_id{$state} && $tmp_test_id ne $test_id{$state})
316 warn "WARNING: state: $state, mismatched test_id: expected: $tmp_test_id, actual: $test_id{$state}, log: $file";
319 if ($state eq 'reportingtest' || $state eq 'runningtest')
321 $state = 'exitedtest';
325 warn "WARNING: state: $state, expected: reportingtest, runningtest, log: $file";
326 $state = 'exitedtest';
329 if (! $test_reported{$tmp_test_id})
331 dbg
"No test results reported: $tmp_test_id";
333 $test_result = 'FAILED';
334 $test_description = 'No test results reported; messages: ' . (join '; ', @messages) . ';';
336 outputrecord
$tmp_test_id, $test_description, $test_result;
339 $test_id{$state} = $tmp_test_id;
341 elsif ( $state ne 'idle' && (($tmp_test_id) = $_ =~ /^([^:]*):.* EXIT STATUS: TIMED OUT/))
343 $test_exit_status = 'TIMED OUT';
344 dbg
"Exit Status Timed Out: $tmp_test_id, $test_exit_status";
346 if ($test_id{$state} && $tmp_test_id ne $test_id{$state})
348 warn "WARNING: state: $state, mismatched test_id: expected: $tmp_test_id, actual: $test_id{$state}, log: $file";
351 if ($state eq 'reportingtest' || $state eq 'runningtest')
353 $state = 'exitedtest';
357 dbg
"state: $state, expected: reportingtest, runningtest";
358 $state = 'exitedtest';
361 $test_result = 'FAILED';
362 $test_description .= '; messages: ' . (join '; ', @messages) . ';';
364 outputrecord
$tmp_test_id, $test_description, $test_result;
366 $test_id{$state} = $tmp_test_id;
368 elsif ( $state ne 'idle' && (($tmp_test_id, $tmp_test_exit_status) = $_ =~ /^([^:]*):.* EXIT STATUS: (CRASHED signal [0-9]+ [A-Z]+) \([0-9.]+ seconds\)/))
370 $test_exit_status = $tmp_test_exit_status;
371 dbg
"Exit Status Crashed: $tmp_test_id, $test_exit_status";
373 if ($test_id{$state} && $tmp_test_id ne $test_id{$state})
375 warn "WARNING: state: $state, mismatched test_id: expected: $tmp_test_id, actual: $test_id{$state}, log: $file";
378 if ($state eq 'reportingtest' || $state eq 'runningtest')
380 $state = 'exitedtest';
384 dbg
"state: $state, expected: reportingtest, runningtest";
385 $state = 'exitedtest';
388 $test_result = 'FAILED';
389 $test_description .= '; messages: ' . (join '; ', @messages) . ';';
391 outputrecord
$tmp_test_id, $test_description, $test_result;
393 $test_id{$state} = $tmp_test_id;
395 elsif ( $state ne 'idle' && (($tmp_test_id, $tmp_test_exit_status) = $_ =~ /^([^:]*):.* EXIT STATUS: (ABNORMAL [0-9]+) \([0-9.]+ seconds\)/))
397 $test_exit_status = $tmp_test_exit_status;
398 dbg
"Exit Status Abnormal: $tmp_test_id, $test_exit_status";
400 if ($test_id{$state} && $tmp_test_id ne $test_id{$state})
402 warn "WARNING: state: $state, mismatched test_id: expected: $tmp_test_id, actual: $test_id{$state}, log: $file";
405 if ($state eq 'reportingtest' || $state eq 'runningtest')
407 $state = 'exitedtest';
411 dbg
"state: $state, expected: reportingtest, runningtest";
412 $state = 'exitedtest';
415 ($exit_code) = $test_exit_status =~ /ABNORMAL ([0-9]+)/;
417 if (grep /$exit_code/, @expected_exit_code_list)
419 $test_result = 'PASSED';
423 $test_result = 'FAILED';
426 $test_description .= '; messages: ' . (join '; ', @messages) . ';';
428 dbg
"Exit Code: $exit_code, Test Result: $test_result, Expected Exit Codes: " . (join '; ', @expected_exit_code_list);
430 outputrecord
$tmp_test_id, $test_description, $test_result;
432 $test_id{$state} = $tmp_test_id;
434 elsif ( ($tmp_test_id) = $_ =~ /^JavaScriptTest: End Test ([^ ]*)/)
436 dbg
"End Test: $tmp_test_id";
438 if ($test_id{$state} && $tmp_test_id ne $test_id{$state})
440 warn "WARNING: state: $state, mismatched test_id: expected: $tmp_test_id, actual: $test_id{$state}, log: $file";
443 if ($state eq 'exitedtest' || $state eq 'runningtest' || $state eq 'reportingtest')
449 warn "WARNING: state: $state, expected: runningtest, reportingtest, exitedtest, log: $file";
453 $test_id{$state} = $tmp_test_id;
455 elsif ( /^JavaScriptTest: End Run/)
459 if ($state eq 'endtest')
465 warn "WARNING: state: $state, expected: endtest, log: $file";
471 !/^(STATUS:| *PASSED!| *FAILED!)/ &&
472 !/^JavaScriptTest:/ &&
474 !/^[-+]{2,2}(WEBSHELL|DOMWINDOW)/ &&
476 !/real.*user.*sys.*$/ &&
477 !/user.*system.*elapsed/)
479 if ('runningtest, reportingtest' =~ /$state/)
482 if (/error: can.t allocate region/ || /set a breakpoint in malloc_error_break/ ||
483 /set a breakpoint in szone_error to debug/ || /malloc:.*mmap/ || /vm_allocate/ ||
484 /terminate called after throwing an instance of .*bad_alloc/)
486 dbg
"Adding message: $_ converted to /$test_id{$state}:0: out of memory";
487 push @messages, ('/' . $test_id{$state} . ':0: out of memory');
489 elsif (/\.js, line [0-9]+: out of memory/ )
491 s/\.js, line ([0-9]+): out of memory/\.js:$1:/;
492 dbg
"Adding message: $_ converted to /$test_id{$state}:0: out of memory";
493 push @messages, ('/' . $test_id{$state} . ':0: out of memory');
497 dbg
"Adding message: $_";
498 push @messages, ($_);
509 if ($test_id{$state})
511 dbg
"test_id{$state}=$test_id{$state}, " . (join '; ', @messages);
515 dbg
"state=$state, " . (join '; ', @messages);
519 if ($state eq 'endrun')
523 die "FATAL ERROR: Test run terminated prematurely. state: $state, log: $file" if ($state ne 'success');
529 undef $test_branchid;
531 undef $test_buildtype;
544 print STDERR
"DEBUG: $msg\n";
550 dbg
"sorting temp file $temp";
551 system("sort -u < $temp");
552 dbg
"finished sorting";
557 my ($test_id, $test_description, $test_result) = @_;
559 # cut off the extra jstest: summaries as they duplicate the other
560 # output and follow it.
561 $test_description =~ s/jstest:.*//;
563 # if (length($test_description) > 6000)
565 # $test_description = substr($test_description, 0, 6000);
570 "TEST_ID=$test_id, " .
571 "TEST_BRANCH=$test_branchid, " .
572 "TEST_REPO=$test_repo, " .
573 "TEST_BUILDTYPE=$test_buildtype, " .
574 "TEST_TYPE=$test_type, " .
575 "TEST_OS=$test_os, " .
576 "TEST_KERNEL=$test_kernel, " .
577 "TEST_PROCESSORTYPE=$test_processortype, " .
578 "TEST_MEMORY=$test_memory, " .
579 "TEST_CPUSPEED=$test_cpuspeed, " .
580 "TEST_TIMEZONE=$test_timezone, " .
581 "TEST_RESULT=$test_result, " .
582 "TEST_EXITSTATUS=$test_exit_status, " .
583 "TEST_DESCRIPTION=$test_description, " .
584 "TEST_MACHINE=$test_machine, " .
585 "TEST_DATE=$test_date" .
590 dbg
"RECORD: $output";
594 $test_reported{$test_id} = 1;