xref: /openbmc/linux/tools/testing/ktest/ktest.pl (revision 576f627c817dff0b7081374287a77247325b9cc0)
12545eb61SSteven Rostedt#!/usr/bin/perl -w
2d6ce2a0bSSteven Rostedt#
3d6ce2a0bSSteven Rostedt# Copywrite 2010 - Steven Rostedt <srostedt@redhat.com>, Red Hat Inc.
4d6ce2a0bSSteven Rostedt# Licensed under the terms of the GNU GPL License version 2
5d6ce2a0bSSteven Rostedt#
62545eb61SSteven Rostedt
72545eb61SSteven Rostedtuse strict;
82545eb61SSteven Rostedtuse IPC::Open2;
92545eb61SSteven Rostedtuse Fcntl qw(F_GETFL F_SETFL O_NONBLOCK);
107faafbd6SSteven Rostedtuse File::Path qw(mkpath);
117faafbd6SSteven Rostedtuse File::Copy qw(cp);
122545eb61SSteven Rostedtuse FileHandle;
132545eb61SSteven Rostedt
142545eb61SSteven Rostedt$#ARGV >= 0 || die "usage: autotest.pl config-file\n";
152545eb61SSteven Rostedt
162545eb61SSteven Rostedt$| = 1;
172545eb61SSteven Rostedt
182545eb61SSteven Rostedtmy %opt;
19a75fececSSteven Rostedtmy %default;
202545eb61SSteven Rostedt
212545eb61SSteven Rostedt#default opts
22a75fececSSteven Rostedt$default{"NUM_TESTS"}		= 5;
23a75fececSSteven Rostedt$default{"REBOOT_TYPE"}		= "grub";
24a75fececSSteven Rostedt$default{"TEST_TYPE"}		= "test";
25a75fececSSteven Rostedt$default{"BUILD_TYPE"}		= "randconfig";
26a75fececSSteven Rostedt$default{"MAKE_CMD"}		= "make";
27a75fececSSteven Rostedt$default{"TIMEOUT"}		= 120;
28a75fececSSteven Rostedt$default{"TMP_DIR"}		= "/tmp/autotest";
29a75fececSSteven Rostedt$default{"SLEEP_TIME"}		= 60;	# sleep time between tests
30a75fececSSteven Rostedt$default{"BUILD_NOCLEAN"}	= 0;
31a75fececSSteven Rostedt$default{"REBOOT_ON_ERROR"}	= 0;
32a75fececSSteven Rostedt$default{"POWEROFF_ON_ERROR"}	= 0;
33a75fececSSteven Rostedt$default{"REBOOT_ON_SUCCESS"}	= 1;
34a75fececSSteven Rostedt$default{"POWEROFF_ON_SUCCESS"}	= 0;
35a75fececSSteven Rostedt$default{"BUILD_OPTIONS"}	= "";
36a75fececSSteven Rostedt$default{"BISECT_SLEEP_TIME"}	= 60;   # sleep time between bisects
37a75fececSSteven Rostedt$default{"CLEAR_LOG"}		= 0;
38a75fececSSteven Rostedt$default{"SUCCESS_LINE"}	= "login:";
39a75fececSSteven Rostedt$default{"BOOTED_TIMEOUT"}	= 1;
40a75fececSSteven Rostedt$default{"DIE_ON_FAILURE"}	= 1;
412545eb61SSteven Rostedt
422545eb61SSteven Rostedtmy $version;
43a75fececSSteven Rostedtmy $machine;
44a75fececSSteven Rostedtmy $tmpdir;
45a75fececSSteven Rostedtmy $builddir;
46a75fececSSteven Rostedtmy $outputdir;
47a75fececSSteven Rostedtmy $test_type;
487faafbd6SSteven Rostedtmy $build_type;
49a75fececSSteven Rostedtmy $build_options;
50a75fececSSteven Rostedtmy $reboot_type;
51a75fececSSteven Rostedtmy $reboot_script;
52a75fececSSteven Rostedtmy $power_cycle;
53a75fececSSteven Rostedtmy $reboot_on_error;
54a75fececSSteven Rostedtmy $poweroff_on_error;
55a75fececSSteven Rostedtmy $die_on_failure;
56*576f627cSSteven Rostedtmy $powercycle_after_reboot;
57*576f627cSSteven Rostedtmy $poweroff_after_halt;
58a75fececSSteven Rostedtmy $power_off;
59a75fececSSteven Rostedtmy $grub_menu;
602545eb61SSteven Rostedtmy $grub_number;
612545eb61SSteven Rostedtmy $target;
622545eb61SSteven Rostedtmy $make;
638b37ca8cSSteven Rostedtmy $post_install;
645c42fc5bSSteven Rostedtmy $noclean;
655f9b6cedSSteven Rostedtmy $minconfig;
662b7d9b21SSteven Rostedtmy $addconfig;
675f9b6cedSSteven Rostedtmy $in_bisect = 0;
685f9b6cedSSteven Rostedtmy $bisect_bad = "";
69d6ce2a0bSSteven Rostedtmy $reverse_bisect;
706c5ee0beSSteven Rostedtmy $in_patchcheck = 0;
715a391fbfSSteven Rostedtmy $run_test;
726c5ee0beSSteven Rostedtmy $redirect;
737faafbd6SSteven Rostedtmy $buildlog;
747faafbd6SSteven Rostedtmy $dmesg;
757faafbd6SSteven Rostedtmy $monitor_fp;
767faafbd6SSteven Rostedtmy $monitor_pid;
777faafbd6SSteven Rostedtmy $monitor_cnt = 0;
78a75fececSSteven Rostedtmy $sleep_time;
79a75fececSSteven Rostedtmy $bisect_sleep_time;
80a75fececSSteven Rostedtmy $store_failures;
81a75fececSSteven Rostedtmy $timeout;
82a75fececSSteven Rostedtmy $booted_timeout;
83a75fececSSteven Rostedtmy $console;
84a75fececSSteven Rostedtmy $success_line;
85a75fececSSteven Rostedtmy $build_target;
86a75fececSSteven Rostedtmy $target_image;
87a75fececSSteven Rostedtmy $localversion;
88*576f627cSSteven Rostedtmy $iteration = 0;
892545eb61SSteven Rostedt
902545eb61SSteven Rostedtsub read_config {
912545eb61SSteven Rostedt    my ($config) = @_;
922545eb61SSteven Rostedt
932545eb61SSteven Rostedt    open(IN, $config) || die "can't read file $config";
942545eb61SSteven Rostedt
952545eb61SSteven Rostedt    while (<IN>) {
962545eb61SSteven Rostedt
972545eb61SSteven Rostedt	# ignore blank lines and comments
982545eb61SSteven Rostedt	next if (/^\s*$/ || /\s*\#/);
992545eb61SSteven Rostedt
1002545eb61SSteven Rostedt	if (/^\s*(\S+)\s*=\s*(.*?)\s*$/) {
1012545eb61SSteven Rostedt	    my $lvalue = $1;
1022545eb61SSteven Rostedt	    my $rvalue = $2;
1032545eb61SSteven Rostedt
104a75fececSSteven Rostedt	    if (defined($opt{$lvalue})) {
105a75fececSSteven Rostedt		die "Error: Option $lvalue defined more than once!\n";
106a75fececSSteven Rostedt	    }
1072545eb61SSteven Rostedt	    $opt{$lvalue} = $rvalue;
1082545eb61SSteven Rostedt	}
1092545eb61SSteven Rostedt    }
1102545eb61SSteven Rostedt
1112545eb61SSteven Rostedt    close(IN);
112a75fececSSteven Rostedt
113a75fececSSteven Rostedt    # set any defaults
114a75fececSSteven Rostedt
115a75fececSSteven Rostedt    foreach my $default (keys %default) {
116a75fececSSteven Rostedt	if (!defined($opt{$default})) {
117a75fececSSteven Rostedt	    $opt{$default} = $default{$default};
118a75fececSSteven Rostedt	}
119a75fececSSteven Rostedt    }
1202545eb61SSteven Rostedt}
1212545eb61SSteven Rostedt
1225f9b6cedSSteven Rostedtsub logit {
1232545eb61SSteven Rostedt    if (defined($opt{"LOG_FILE"})) {
1242545eb61SSteven Rostedt	open(OUT, ">> $opt{LOG_FILE}") or die "Can't write to $opt{LOG_FILE}";
1252545eb61SSteven Rostedt	print OUT @_;
1262545eb61SSteven Rostedt	close(OUT);
1272545eb61SSteven Rostedt    }
1282545eb61SSteven Rostedt}
1292545eb61SSteven Rostedt
1305f9b6cedSSteven Rostedtsub doprint {
1315f9b6cedSSteven Rostedt    print @_;
1325f9b6cedSSteven Rostedt    logit @_;
1335f9b6cedSSteven Rostedt}
1345f9b6cedSSteven Rostedt
1357faafbd6SSteven Rostedtsub run_command;
1367faafbd6SSteven Rostedt
1377faafbd6SSteven Rostedtsub reboot {
1387faafbd6SSteven Rostedt    # try to reboot normally
139*576f627cSSteven Rostedt    if (run_command "ssh $target reboot") {
140*576f627cSSteven Rostedt	if (defined($powercycle_after_reboot)) {
141*576f627cSSteven Rostedt	    sleep $powercycle_after_reboot;
142*576f627cSSteven Rostedt	    run_command "$power_cycle";
143*576f627cSSteven Rostedt	}
144*576f627cSSteven Rostedt    } else {
1457faafbd6SSteven Rostedt	# nope? power cycle it.
146a75fececSSteven Rostedt	run_command "$power_cycle";
1477faafbd6SSteven Rostedt    }
1487faafbd6SSteven Rostedt}
1497faafbd6SSteven Rostedt
150*576f627cSSteven Rostedtsub do_not_reboot {
151*576f627cSSteven Rostedt    my $i = $iteration;
152*576f627cSSteven Rostedt
153*576f627cSSteven Rostedt    return $test_type eq "build" ||
154*576f627cSSteven Rostedt	($test_type eq "patchcheck" && $opt{"PATCHCHECK_TYPE[$i]"} eq "build") ||
155*576f627cSSteven Rostedt	($test_type eq "bisect" && $opt{"BISECT_TYPE[$i]"} eq "build");
156*576f627cSSteven Rostedt}
157*576f627cSSteven Rostedt
1585c42fc5bSSteven Rostedtsub dodie {
1595a391fbfSSteven Rostedt    doprint "CRITICAL FAILURE... ", @_, "\n";
1605c42fc5bSSteven Rostedt
161*576f627cSSteven Rostedt    my $i = $iteration;
162*576f627cSSteven Rostedt
163*576f627cSSteven Rostedt    if ($reboot_on_error && !do_not_reboot) {
164*576f627cSSteven Rostedt
16575c3fda7SSteven Rostedt	doprint "REBOOTING\n";
1667faafbd6SSteven Rostedt	reboot;
16775c3fda7SSteven Rostedt
168a75fececSSteven Rostedt    } elsif ($poweroff_on_error && defined($power_off)) {
1695c42fc5bSSteven Rostedt	doprint "POWERING OFF\n";
170a75fececSSteven Rostedt	`$power_off`;
1715c42fc5bSSteven Rostedt    }
17275c3fda7SSteven Rostedt
173*576f627cSSteven Rostedt    die @_, "\n";
1745c42fc5bSSteven Rostedt}
1755c42fc5bSSteven Rostedt
1767faafbd6SSteven Rostedtsub open_console {
1777faafbd6SSteven Rostedt    my ($fp) = @_;
1787faafbd6SSteven Rostedt
1797faafbd6SSteven Rostedt    my $flags;
1807faafbd6SSteven Rostedt
181a75fececSSteven Rostedt    my $pid = open($fp, "$console|") or
182a75fececSSteven Rostedt	dodie "Can't open console $console";
1837faafbd6SSteven Rostedt
1847faafbd6SSteven Rostedt    $flags = fcntl($fp, F_GETFL, 0) or
185*576f627cSSteven Rostedt	dodie "Can't get flags for the socket: $!";
1867faafbd6SSteven Rostedt    $flags = fcntl($fp, F_SETFL, $flags | O_NONBLOCK) or
187*576f627cSSteven Rostedt	dodie "Can't set flags for the socket: $!";
1887faafbd6SSteven Rostedt
1897faafbd6SSteven Rostedt    return $pid;
1907faafbd6SSteven Rostedt}
1917faafbd6SSteven Rostedt
1927faafbd6SSteven Rostedtsub close_console {
1937faafbd6SSteven Rostedt    my ($fp, $pid) = @_;
1947faafbd6SSteven Rostedt
1957faafbd6SSteven Rostedt    doprint "kill child process $pid\n";
1967faafbd6SSteven Rostedt    kill 2, $pid;
1977faafbd6SSteven Rostedt
1987faafbd6SSteven Rostedt    print "closing!\n";
1997faafbd6SSteven Rostedt    close($fp);
2007faafbd6SSteven Rostedt}
2017faafbd6SSteven Rostedt
2027faafbd6SSteven Rostedtsub start_monitor {
2037faafbd6SSteven Rostedt    if ($monitor_cnt++) {
2047faafbd6SSteven Rostedt	return;
2057faafbd6SSteven Rostedt    }
2067faafbd6SSteven Rostedt    $monitor_fp = \*MONFD;
2077faafbd6SSteven Rostedt    $monitor_pid = open_console $monitor_fp;
208a75fececSSteven Rostedt
209a75fececSSteven Rostedt    return;
210a75fececSSteven Rostedt
211a75fececSSteven Rostedt    open(MONFD, "Stop perl from warning about single use of MONFD");
2127faafbd6SSteven Rostedt}
2137faafbd6SSteven Rostedt
2147faafbd6SSteven Rostedtsub end_monitor {
2157faafbd6SSteven Rostedt    if (--$monitor_cnt) {
2167faafbd6SSteven Rostedt	return;
2177faafbd6SSteven Rostedt    }
2187faafbd6SSteven Rostedt    close_console($monitor_fp, $monitor_pid);
2197faafbd6SSteven Rostedt}
2207faafbd6SSteven Rostedt
2217faafbd6SSteven Rostedtsub wait_for_monitor {
2227faafbd6SSteven Rostedt    my ($time) = @_;
2237faafbd6SSteven Rostedt    my $line;
2247faafbd6SSteven Rostedt
225a75fececSSteven Rostedt    doprint "** Wait for monitor to settle down **\n";
2267faafbd6SSteven Rostedt
2277faafbd6SSteven Rostedt    # read the monitor and wait for the system to calm down
2287faafbd6SSteven Rostedt    do {
2297faafbd6SSteven Rostedt	$line = wait_for_input($monitor_fp, $time);
230a75fececSSteven Rostedt	print "$line" if (defined($line));
2317faafbd6SSteven Rostedt    } while (defined($line));
232a75fececSSteven Rostedt    print "** Monitor flushed **\n";
2337faafbd6SSteven Rostedt}
2347faafbd6SSteven Rostedt
2352b7d9b21SSteven Rostedtsub fail {
2362b7d9b21SSteven Rostedt
237a75fececSSteven Rostedt	if ($die_on_failure) {
2382b7d9b21SSteven Rostedt		dodie @_;
2392b7d9b21SSteven Rostedt	}
2402b7d9b21SSteven Rostedt
241a75fececSSteven Rostedt	doprint "FAILED\n";
2427faafbd6SSteven Rostedt
243*576f627cSSteven Rostedt	my $i = $iteration;
244*576f627cSSteven Rostedt
245a75fececSSteven Rostedt	# no need to reboot for just building.
246*576f627cSSteven Rostedt	if (!do_not_reboot) {
2477faafbd6SSteven Rostedt	    doprint "REBOOTING\n";
2487faafbd6SSteven Rostedt	    reboot;
2497faafbd6SSteven Rostedt	    start_monitor;
250a75fececSSteven Rostedt	    wait_for_monitor $sleep_time;
2517faafbd6SSteven Rostedt	    end_monitor;
252a75fececSSteven Rostedt	}
2537faafbd6SSteven Rostedt
254*576f627cSSteven Rostedt	doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
255*576f627cSSteven Rostedt	doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
256a75fececSSteven Rostedt	doprint "**** Failed: ", @_, " ****\n";
257*576f627cSSteven Rostedt	doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
258*576f627cSSteven Rostedt	doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
259a75fececSSteven Rostedt
260a75fececSSteven Rostedt	return 1 if (!defined($store_failures));
2617faafbd6SSteven Rostedt
2627faafbd6SSteven Rostedt	my @t = localtime;
2637faafbd6SSteven Rostedt	my $date = sprintf "%04d%02d%02d%02d%02d%02d",
2647faafbd6SSteven Rostedt		1900+$t[5],$t[4],$t[3],$t[2],$t[1],$t[0];
2657faafbd6SSteven Rostedt
266a75fececSSteven Rostedt	my $dir = "$machine-$test_type-$build_type-fail-$date";
267a75fececSSteven Rostedt	my $faildir = "$store_failures/$dir";
2687faafbd6SSteven Rostedt
2697faafbd6SSteven Rostedt	if (!-d $faildir) {
2707faafbd6SSteven Rostedt	    mkpath($faildir) or
271a75fececSSteven Rostedt		die "can't create $faildir";
2727faafbd6SSteven Rostedt	}
273a75fececSSteven Rostedt	if (-f "$outputdir/.config") {
274a75fececSSteven Rostedt	    cp "$outputdir/.config", "$faildir/config" or
2757faafbd6SSteven Rostedt		die "failed to copy .config";
2767faafbd6SSteven Rostedt	}
2777faafbd6SSteven Rostedt	if (-f $buildlog) {
2787faafbd6SSteven Rostedt	    cp $buildlog, "$faildir/buildlog" or
2797faafbd6SSteven Rostedt		die "failed to move $buildlog";
2807faafbd6SSteven Rostedt	}
2817faafbd6SSteven Rostedt	if (-f $dmesg) {
2827faafbd6SSteven Rostedt	    cp $dmesg, "$faildir/dmesg" or
2837faafbd6SSteven Rostedt		die "failed to move $dmesg";
2847faafbd6SSteven Rostedt	}
2857faafbd6SSteven Rostedt
2867faafbd6SSteven Rostedt	doprint "*** Saved info to $faildir ***\n";
2877faafbd6SSteven Rostedt
2882b7d9b21SSteven Rostedt	return 1;
2892b7d9b21SSteven Rostedt}
2902b7d9b21SSteven Rostedt
2912545eb61SSteven Rostedtsub run_command {
2922545eb61SSteven Rostedt    my ($command) = @_;
293d6ce2a0bSSteven Rostedt    my $dolog = 0;
294d6ce2a0bSSteven Rostedt    my $dord = 0;
295d6ce2a0bSSteven Rostedt    my $pid;
296d6ce2a0bSSteven Rostedt
297d6ce2a0bSSteven Rostedt    doprint("$command ... ");
298d6ce2a0bSSteven Rostedt
299d6ce2a0bSSteven Rostedt    $pid = open(CMD, "$command 2>&1 |") or
3002b7d9b21SSteven Rostedt	(fail "unable to exec $command" and return 0);
3012545eb61SSteven Rostedt
3022545eb61SSteven Rostedt    if (defined($opt{"LOG_FILE"})) {
303d6ce2a0bSSteven Rostedt	open(LOG, ">>$opt{LOG_FILE}") or
304d6ce2a0bSSteven Rostedt	    dodie "failed to write to log";
305d6ce2a0bSSteven Rostedt	$dolog = 1;
3066c5ee0beSSteven Rostedt    }
3076c5ee0beSSteven Rostedt
3086c5ee0beSSteven Rostedt    if (defined($redirect)) {
309d6ce2a0bSSteven Rostedt	open (RD, ">$redirect") or
310d6ce2a0bSSteven Rostedt	    dodie "failed to write to redirect $redirect";
311d6ce2a0bSSteven Rostedt	$dord = 1;
3122545eb61SSteven Rostedt    }
3132545eb61SSteven Rostedt
314d6ce2a0bSSteven Rostedt    while (<CMD>) {
315d6ce2a0bSSteven Rostedt	print LOG if ($dolog);
316d6ce2a0bSSteven Rostedt	print RD  if ($dord);
317d6ce2a0bSSteven Rostedt    }
3182545eb61SSteven Rostedt
319d6ce2a0bSSteven Rostedt    waitpid($pid, 0);
3202545eb61SSteven Rostedt    my $failed = $?;
3212545eb61SSteven Rostedt
322d6ce2a0bSSteven Rostedt    close(CMD);
323d6ce2a0bSSteven Rostedt    close(LOG) if ($dolog);
324d6ce2a0bSSteven Rostedt    close(RD)  if ($dord);
325d6ce2a0bSSteven Rostedt
3262545eb61SSteven Rostedt    if ($failed) {
3272545eb61SSteven Rostedt	doprint "FAILED!\n";
3282545eb61SSteven Rostedt    } else {
3292545eb61SSteven Rostedt	doprint "SUCCESS\n";
3302545eb61SSteven Rostedt    }
3312545eb61SSteven Rostedt
3325f9b6cedSSteven Rostedt    return !$failed;
3335f9b6cedSSteven Rostedt}
3345f9b6cedSSteven Rostedt
3355f9b6cedSSteven Rostedtsub get_grub_index {
3365f9b6cedSSteven Rostedt
337a75fececSSteven Rostedt    if ($reboot_type ne "grub") {
338a75fececSSteven Rostedt	return;
339a75fececSSteven Rostedt    }
3405a391fbfSSteven Rostedt    return if (defined($grub_number));
3415f9b6cedSSteven Rostedt
3425f9b6cedSSteven Rostedt    doprint "Find grub menu ... ";
3435f9b6cedSSteven Rostedt    $grub_number = -1;
3445f9b6cedSSteven Rostedt    open(IN, "ssh $target cat /boot/grub/menu.lst |")
3455f9b6cedSSteven Rostedt	or die "unable to get menu.lst";
3465f9b6cedSSteven Rostedt    while (<IN>) {
347a75fececSSteven Rostedt	if (/^\s*title\s+$grub_menu\s*$/) {
3485f9b6cedSSteven Rostedt	    $grub_number++;
3495f9b6cedSSteven Rostedt	    last;
3505f9b6cedSSteven Rostedt	} elsif (/^\s*title\s/) {
3515f9b6cedSSteven Rostedt	    $grub_number++;
3525f9b6cedSSteven Rostedt	}
3535f9b6cedSSteven Rostedt    }
3545f9b6cedSSteven Rostedt    close(IN);
3555f9b6cedSSteven Rostedt
356a75fececSSteven Rostedt    die "Could not find '$grub_menu' in /boot/grub/menu on $machine"
3575f9b6cedSSteven Rostedt	if ($grub_number < 0);
3585f9b6cedSSteven Rostedt    doprint "$grub_number\n";
3592545eb61SSteven Rostedt}
3602545eb61SSteven Rostedt
3612545eb61SSteven Rostedtsub wait_for_input
3622545eb61SSteven Rostedt{
3632545eb61SSteven Rostedt    my ($fp, $time) = @_;
3642545eb61SSteven Rostedt    my $rin;
3652545eb61SSteven Rostedt    my $ready;
3662545eb61SSteven Rostedt    my $line;
3672545eb61SSteven Rostedt    my $ch;
3682545eb61SSteven Rostedt
3692545eb61SSteven Rostedt    if (!defined($time)) {
3702545eb61SSteven Rostedt	$time = $timeout;
3712545eb61SSteven Rostedt    }
3722545eb61SSteven Rostedt
3732545eb61SSteven Rostedt    $rin = '';
3742545eb61SSteven Rostedt    vec($rin, fileno($fp), 1) = 1;
3752545eb61SSteven Rostedt    $ready = select($rin, undef, undef, $time);
3762545eb61SSteven Rostedt
3772545eb61SSteven Rostedt    $line = "";
3782545eb61SSteven Rostedt
3792545eb61SSteven Rostedt    # try to read one char at a time
3802545eb61SSteven Rostedt    while (sysread $fp, $ch, 1) {
3812545eb61SSteven Rostedt	$line .= $ch;
3822545eb61SSteven Rostedt	last if ($ch eq "\n");
3832545eb61SSteven Rostedt    }
3842545eb61SSteven Rostedt
3852545eb61SSteven Rostedt    if (!length($line)) {
3862545eb61SSteven Rostedt	return undef;
3872545eb61SSteven Rostedt    }
3882545eb61SSteven Rostedt
3892545eb61SSteven Rostedt    return $line;
3902545eb61SSteven Rostedt}
3912545eb61SSteven Rostedt
39275c3fda7SSteven Rostedtsub reboot_to {
393a75fececSSteven Rostedt    if ($reboot_type eq "grub") {
3942545eb61SSteven Rostedt	run_command "ssh $target '(echo \"savedefault --default=$grub_number --once\" | grub --batch; reboot)'";
395a75fececSSteven Rostedt	return;
396a75fececSSteven Rostedt    }
397a75fececSSteven Rostedt
398a75fececSSteven Rostedt    run_command "$reboot_script";
3992545eb61SSteven Rostedt}
4002545eb61SSteven Rostedt
4015a391fbfSSteven Rostedtsub monitor {
4022545eb61SSteven Rostedt    my $booted = 0;
4032545eb61SSteven Rostedt    my $bug = 0;
4045c42fc5bSSteven Rostedt    my $skip_call_trace = 0;
4052b7d9b21SSteven Rostedt    my $loops;
4062545eb61SSteven Rostedt
4077faafbd6SSteven Rostedt    wait_for_monitor 5;
4082545eb61SSteven Rostedt
4092545eb61SSteven Rostedt    my $line;
4102545eb61SSteven Rostedt    my $full_line = "";
4112545eb61SSteven Rostedt
4127faafbd6SSteven Rostedt    open(DMESG, "> $dmesg") or
4137faafbd6SSteven Rostedt	die "unable to write to $dmesg";
4142545eb61SSteven Rostedt
41575c3fda7SSteven Rostedt    reboot_to;
4162545eb61SSteven Rostedt
4172545eb61SSteven Rostedt    for (;;) {
4182545eb61SSteven Rostedt
4192b7d9b21SSteven Rostedt	if ($booted) {
420a75fececSSteven Rostedt	    $line = wait_for_input($monitor_fp, $booted_timeout);
4212b7d9b21SSteven Rostedt	} else {
4227faafbd6SSteven Rostedt	    $line = wait_for_input($monitor_fp);
4232b7d9b21SSteven Rostedt	}
4242545eb61SSteven Rostedt
4252545eb61SSteven Rostedt	last if (!defined($line));
4262545eb61SSteven Rostedt
4272545eb61SSteven Rostedt	doprint $line;
4287faafbd6SSteven Rostedt	print DMESG $line;
4292545eb61SSteven Rostedt
4302545eb61SSteven Rostedt	# we are not guaranteed to get a full line
4312545eb61SSteven Rostedt	$full_line .= $line;
4322545eb61SSteven Rostedt
433a75fececSSteven Rostedt	if ($full_line =~ /$success_line/) {
4342545eb61SSteven Rostedt	    $booted = 1;
4352545eb61SSteven Rostedt	}
4362545eb61SSteven Rostedt
4375c42fc5bSSteven Rostedt	if ($full_line =~ /\[ backtrace testing \]/) {
4385c42fc5bSSteven Rostedt	    $skip_call_trace = 1;
4395c42fc5bSSteven Rostedt	}
4405c42fc5bSSteven Rostedt
4412545eb61SSteven Rostedt	if ($full_line =~ /call trace:/i) {
4425c42fc5bSSteven Rostedt	    $bug = 1 if (!$skip_call_trace);
4435c42fc5bSSteven Rostedt	}
4445c42fc5bSSteven Rostedt
4455c42fc5bSSteven Rostedt	if ($full_line =~ /\[ end of backtrace testing \]/) {
4465c42fc5bSSteven Rostedt	    $skip_call_trace = 0;
4475c42fc5bSSteven Rostedt	}
4485c42fc5bSSteven Rostedt
4495c42fc5bSSteven Rostedt	if ($full_line =~ /Kernel panic -/) {
4502545eb61SSteven Rostedt	    $bug = 1;
4512545eb61SSteven Rostedt	}
4522545eb61SSteven Rostedt
4532545eb61SSteven Rostedt	if ($line =~ /\n/) {
4542545eb61SSteven Rostedt	    $full_line = "";
4552545eb61SSteven Rostedt	}
4562545eb61SSteven Rostedt    }
4572545eb61SSteven Rostedt
4587faafbd6SSteven Rostedt    close(DMESG);
4592545eb61SSteven Rostedt
4602545eb61SSteven Rostedt    if ($bug) {
4612b7d9b21SSteven Rostedt	return 0 if ($in_bisect);
462*576f627cSSteven Rostedt	fail "failed - got a bug report" and return 0;
4632545eb61SSteven Rostedt    }
4645f9b6cedSSteven Rostedt
465a75fececSSteven Rostedt    if (!$booted) {
466a75fececSSteven Rostedt	return 0 if ($in_bisect);
467*576f627cSSteven Rostedt	fail "failed - never got a boot prompt." and return 0;
468a75fececSSteven Rostedt    }
469a75fececSSteven Rostedt
4702b7d9b21SSteven Rostedt    return 1;
4712545eb61SSteven Rostedt}
4722545eb61SSteven Rostedt
4732545eb61SSteven Rostedtsub install {
4742545eb61SSteven Rostedt
475a75fececSSteven Rostedt    run_command "scp $outputdir/$build_target $target:$target_image" or
4765c42fc5bSSteven Rostedt	dodie "failed to copy image";
4775f9b6cedSSteven Rostedt
4785f9b6cedSSteven Rostedt    my $install_mods = 0;
4795f9b6cedSSteven Rostedt
4805f9b6cedSSteven Rostedt    # should we process modules?
4815f9b6cedSSteven Rostedt    $install_mods = 0;
482a75fececSSteven Rostedt    open(IN, "$outputdir/.config") or dodie("Can't read config file");
4835f9b6cedSSteven Rostedt    while (<IN>) {
4845f9b6cedSSteven Rostedt	if (/CONFIG_MODULES(=y)?/) {
4855f9b6cedSSteven Rostedt	    $install_mods = 1 if (defined($1));
4865f9b6cedSSteven Rostedt	    last;
4875f9b6cedSSteven Rostedt	}
4885f9b6cedSSteven Rostedt    }
4895f9b6cedSSteven Rostedt    close(IN);
4905f9b6cedSSteven Rostedt
4915f9b6cedSSteven Rostedt    if (!$install_mods) {
4925f9b6cedSSteven Rostedt	doprint "No modules needed\n";
4935f9b6cedSSteven Rostedt	return;
4942545eb61SSteven Rostedt    }
4952545eb61SSteven Rostedt
496a75fececSSteven Rostedt    run_command "$make INSTALL_MOD_PATH=$tmpdir modules_install" or
4975f9b6cedSSteven Rostedt	dodie "Failed to install modules";
4985f9b6cedSSteven Rostedt
4992545eb61SSteven Rostedt    my $modlib = "/lib/modules/$version";
5005c42fc5bSSteven Rostedt    my $modtar = "autotest-mods.tar.bz2";
5012545eb61SSteven Rostedt
5025f9b6cedSSteven Rostedt    run_command "ssh $target rm -rf $modlib" or
5035c42fc5bSSteven Rostedt	dodie "failed to remove old mods: $modlib";
5042545eb61SSteven Rostedt
5055c42fc5bSSteven Rostedt    # would be nice if scp -r did not follow symbolic links
506a75fececSSteven Rostedt    run_command "cd $tmpdir && tar -cjf $modtar lib/modules/$version" or
5075c42fc5bSSteven Rostedt	dodie "making tarball";
5085c42fc5bSSteven Rostedt
509a75fececSSteven Rostedt    run_command "scp $tmpdir/$modtar $target:/tmp" or
5105c42fc5bSSteven Rostedt	dodie "failed to copy modules";
5115c42fc5bSSteven Rostedt
512a75fececSSteven Rostedt    unlink "$tmpdir/$modtar";
5135c42fc5bSSteven Rostedt
5145f9b6cedSSteven Rostedt    run_command "ssh $target '(cd / && tar xf /tmp/$modtar)'" or
5155c42fc5bSSteven Rostedt	dodie "failed to tar modules";
5165c42fc5bSSteven Rostedt
5175c42fc5bSSteven Rostedt    run_command "ssh $target rm -f /tmp/$modtar";
5188b37ca8cSSteven Rostedt
5198b37ca8cSSteven Rostedt    return if (!defined($post_install));
5208b37ca8cSSteven Rostedt
5218b37ca8cSSteven Rostedt    my $save_env = $ENV{KERNEL_VERSION};
5228b37ca8cSSteven Rostedt
5238b37ca8cSSteven Rostedt    $ENV{KERNEL_VERSION} = $version;
524*576f627cSSteven Rostedt    run_command "$post_install" or
525*576f627cSSteven Rostedt	dodie "Failed to run post install";
5268b37ca8cSSteven Rostedt
5278b37ca8cSSteven Rostedt    $ENV{KERNEL_VERSION} = $save_env;
5282545eb61SSteven Rostedt}
5292545eb61SSteven Rostedt
5306c5ee0beSSteven Rostedtsub check_buildlog {
5316c5ee0beSSteven Rostedt    my ($patch) = @_;
5326c5ee0beSSteven Rostedt
5336c5ee0beSSteven Rostedt    my @files = `git show $patch | diffstat -l`;
5346c5ee0beSSteven Rostedt
5356c5ee0beSSteven Rostedt    open(IN, "git show $patch |") or
5366c5ee0beSSteven Rostedt	dodie "failed to show $patch";
5376c5ee0beSSteven Rostedt    while (<IN>) {
5386c5ee0beSSteven Rostedt	if (m,^--- a/(.*),) {
5396c5ee0beSSteven Rostedt	    chomp $1;
5406c5ee0beSSteven Rostedt	    $files[$#files] = $1;
5416c5ee0beSSteven Rostedt	}
5426c5ee0beSSteven Rostedt    }
5436c5ee0beSSteven Rostedt    close(IN);
5446c5ee0beSSteven Rostedt
5456c5ee0beSSteven Rostedt    open(IN, $buildlog) or dodie "Can't open $buildlog";
5466c5ee0beSSteven Rostedt    while (<IN>) {
5476c5ee0beSSteven Rostedt	if (/^\s*(.*?):.*(warning|error)/) {
5486c5ee0beSSteven Rostedt	    my $err = $1;
5496c5ee0beSSteven Rostedt	    foreach my $file (@files) {
550a75fececSSteven Rostedt		my $fullpath = "$builddir/$file";
5516c5ee0beSSteven Rostedt		if ($file eq $err || $fullpath eq $err) {
5522b7d9b21SSteven Rostedt		    fail "$file built with warnings" and return 0;
5536c5ee0beSSteven Rostedt		}
5546c5ee0beSSteven Rostedt	    }
5556c5ee0beSSteven Rostedt	}
5566c5ee0beSSteven Rostedt    }
5576c5ee0beSSteven Rostedt    close(IN);
5582b7d9b21SSteven Rostedt
5592b7d9b21SSteven Rostedt    return 1;
5606c5ee0beSSteven Rostedt}
5616c5ee0beSSteven Rostedt
5622545eb61SSteven Rostedtsub build {
5632545eb61SSteven Rostedt    my ($type) = @_;
5645c42fc5bSSteven Rostedt    my $defconfig = "";
5655c42fc5bSSteven Rostedt    my $append = "";
5662545eb61SSteven Rostedt
5677faafbd6SSteven Rostedt    unlink $buildlog;
5687faafbd6SSteven Rostedt
56975c3fda7SSteven Rostedt    if ($type =~ /^useconfig:(.*)/) {
570a75fececSSteven Rostedt	run_command "cp $1 $outputdir/.config" or
57175c3fda7SSteven Rostedt	    dodie "could not copy $1 to .config";
5725f9b6cedSSteven Rostedt
57375c3fda7SSteven Rostedt	$type = "oldconfig";
57475c3fda7SSteven Rostedt    }
57575c3fda7SSteven Rostedt
5765c42fc5bSSteven Rostedt    # old config can ask questions
5775c42fc5bSSteven Rostedt    if ($type eq "oldconfig") {
5785c42fc5bSSteven Rostedt	$append = "yes ''|";
57975c3fda7SSteven Rostedt
58075c3fda7SSteven Rostedt	# allow for empty configs
581a75fececSSteven Rostedt	run_command "touch $outputdir/.config";
58275c3fda7SSteven Rostedt
583a75fececSSteven Rostedt	run_command "mv $outputdir/.config $outputdir/config_temp" or
5845c42fc5bSSteven Rostedt	    dodie "moving .config";
5855c42fc5bSSteven Rostedt
5865f9b6cedSSteven Rostedt	if (!$noclean && !run_command "$make mrproper") {
5875c42fc5bSSteven Rostedt	    dodie "make mrproper";
5885c42fc5bSSteven Rostedt	}
5895c42fc5bSSteven Rostedt
590a75fececSSteven Rostedt	run_command "mv $outputdir/config_temp $outputdir/.config" or
5915c42fc5bSSteven Rostedt	    dodie "moving config_temp";
5925c42fc5bSSteven Rostedt
5935c42fc5bSSteven Rostedt    } elsif (!$noclean) {
594a75fececSSteven Rostedt	unlink "$outputdir/.config";
5955f9b6cedSSteven Rostedt	run_command "$make mrproper" or
5965c42fc5bSSteven Rostedt	    dodie "make mrproper";
5975c42fc5bSSteven Rostedt    }
5982545eb61SSteven Rostedt
5992545eb61SSteven Rostedt    # add something to distinguish this build
600a75fececSSteven Rostedt    open(OUT, "> $outputdir/localversion") or dodie("Can't make localversion file");
601a75fececSSteven Rostedt    print OUT "$localversion\n";
6022545eb61SSteven Rostedt    close(OUT);
6032545eb61SSteven Rostedt
6045f9b6cedSSteven Rostedt    if (defined($minconfig)) {
6055f9b6cedSSteven Rostedt	$defconfig = "KCONFIG_ALLCONFIG=$minconfig";
6062545eb61SSteven Rostedt    }
6072545eb61SSteven Rostedt
608a75fececSSteven Rostedt    run_command "$append $defconfig $make $type" or
6095c42fc5bSSteven Rostedt	dodie "failed make config";
6102545eb61SSteven Rostedt
611a75fececSSteven Rostedt    $redirect = "$buildlog";
612a75fececSSteven Rostedt    if (!run_command "$make $build_options") {
6136c5ee0beSSteven Rostedt	undef $redirect;
6145f9b6cedSSteven Rostedt	# bisect may need this to pass
6152b7d9b21SSteven Rostedt	return 0 if ($in_bisect);
6162b7d9b21SSteven Rostedt	fail "failed build" and return 0;
6172545eb61SSteven Rostedt    }
6186c5ee0beSSteven Rostedt    undef $redirect;
6195f9b6cedSSteven Rostedt
6202b7d9b21SSteven Rostedt    return 1;
6212545eb61SSteven Rostedt}
6222545eb61SSteven Rostedt
62375c3fda7SSteven Rostedtsub halt {
624a75fececSSteven Rostedt    if (!run_command "ssh $target halt" or defined($power_off)) {
625*576f627cSSteven Rostedt	if (defined($poweroff_after_halt)) {
626*576f627cSSteven Rostedt	    sleep $poweroff_after_halt;
627*576f627cSSteven Rostedt	    run_command "$power_off";
628*576f627cSSteven Rostedt	}
629*576f627cSSteven Rostedt    } else {
63075c3fda7SSteven Rostedt	# nope? the zap it!
631a75fececSSteven Rostedt	run_command "$power_off";
63275c3fda7SSteven Rostedt    }
63375c3fda7SSteven Rostedt}
63475c3fda7SSteven Rostedt
6355f9b6cedSSteven Rostedtsub success {
6365f9b6cedSSteven Rostedt    my ($i) = @_;
6375f9b6cedSSteven Rostedt
6385f9b6cedSSteven Rostedt    doprint "\n\n*******************************************\n";
6395f9b6cedSSteven Rostedt    doprint     "*******************************************\n";
640a75fececSSteven Rostedt    doprint     "**           TEST $i SUCCESS!!!!         **\n";
6415f9b6cedSSteven Rostedt    doprint     "*******************************************\n";
6425f9b6cedSSteven Rostedt    doprint     "*******************************************\n";
6435f9b6cedSSteven Rostedt
644*576f627cSSteven Rostedt    if ($i != $opt{"NUM_TESTS"} && !do_not_reboot) {
645a75fececSSteven Rostedt	doprint "Reboot and wait $sleep_time seconds\n";
6465f9b6cedSSteven Rostedt	reboot;
6477faafbd6SSteven Rostedt	start_monitor;
648a75fececSSteven Rostedt	wait_for_monitor $sleep_time;
6497faafbd6SSteven Rostedt	end_monitor;
6505f9b6cedSSteven Rostedt    }
6515f9b6cedSSteven Rostedt}
6525f9b6cedSSteven Rostedt
6535f9b6cedSSteven Rostedtsub get_version {
6545f9b6cedSSteven Rostedt    # get the release name
6555f9b6cedSSteven Rostedt    doprint "$make kernelrelease ... ";
6565f9b6cedSSteven Rostedt    $version = `$make kernelrelease | tail -1`;
6575f9b6cedSSteven Rostedt    chomp($version);
6585f9b6cedSSteven Rostedt    doprint "$version\n";
6595f9b6cedSSteven Rostedt}
6605f9b6cedSSteven Rostedt
6615a391fbfSSteven Rostedtsub child_run_test {
6627faafbd6SSteven Rostedt    my $failed = 0;
6635a391fbfSSteven Rostedt
6647faafbd6SSteven Rostedt    # child should have no power
665a75fececSSteven Rostedt    $reboot_on_error = 0;
666a75fececSSteven Rostedt    $poweroff_on_error = 0;
667a75fececSSteven Rostedt    $die_on_failure = 1;
6687faafbd6SSteven Rostedt
6697faafbd6SSteven Rostedt    run_command $run_test or $failed = 1;
6705a391fbfSSteven Rostedt    exit $failed;
6715a391fbfSSteven Rostedt}
6725a391fbfSSteven Rostedt
6735a391fbfSSteven Rostedtmy $child_done;
6745a391fbfSSteven Rostedt
6755a391fbfSSteven Rostedtsub child_finished {
6765a391fbfSSteven Rostedt    $child_done = 1;
6775a391fbfSSteven Rostedt}
6785a391fbfSSteven Rostedt
6795a391fbfSSteven Rostedtsub do_run_test {
6805a391fbfSSteven Rostedt    my $child_pid;
6815a391fbfSSteven Rostedt    my $child_exit;
6825a391fbfSSteven Rostedt    my $line;
6835a391fbfSSteven Rostedt    my $full_line;
6845a391fbfSSteven Rostedt    my $bug = 0;
6855a391fbfSSteven Rostedt
6867faafbd6SSteven Rostedt    wait_for_monitor 1;
6875a391fbfSSteven Rostedt
6887faafbd6SSteven Rostedt    doprint "run test $run_test\n";
6895a391fbfSSteven Rostedt
6905a391fbfSSteven Rostedt    $child_done = 0;
6915a391fbfSSteven Rostedt
6925a391fbfSSteven Rostedt    $SIG{CHLD} = qw(child_finished);
6935a391fbfSSteven Rostedt
6945a391fbfSSteven Rostedt    $child_pid = fork;
6955a391fbfSSteven Rostedt
6965a391fbfSSteven Rostedt    child_run_test if (!$child_pid);
6975a391fbfSSteven Rostedt
6985a391fbfSSteven Rostedt    $full_line = "";
6995a391fbfSSteven Rostedt
7005a391fbfSSteven Rostedt    do {
7017faafbd6SSteven Rostedt	$line = wait_for_input($monitor_fp, 1);
7025a391fbfSSteven Rostedt	if (defined($line)) {
7035a391fbfSSteven Rostedt
7045a391fbfSSteven Rostedt	    # we are not guaranteed to get a full line
7055a391fbfSSteven Rostedt	    $full_line .= $line;
7065a391fbfSSteven Rostedt
7075a391fbfSSteven Rostedt	    if ($full_line =~ /call trace:/i) {
7085a391fbfSSteven Rostedt		$bug = 1;
7095a391fbfSSteven Rostedt	    }
7105a391fbfSSteven Rostedt
7115a391fbfSSteven Rostedt	    if ($full_line =~ /Kernel panic -/) {
7125a391fbfSSteven Rostedt		$bug = 1;
7135a391fbfSSteven Rostedt	    }
7145a391fbfSSteven Rostedt
7155a391fbfSSteven Rostedt	    if ($line =~ /\n/) {
7165a391fbfSSteven Rostedt		$full_line = "";
7175a391fbfSSteven Rostedt	    }
7185a391fbfSSteven Rostedt	}
7195a391fbfSSteven Rostedt    } while (!$child_done && !$bug);
7205a391fbfSSteven Rostedt
7215a391fbfSSteven Rostedt    if ($bug) {
7225a391fbfSSteven Rostedt	doprint "Detected kernel crash!\n";
7235a391fbfSSteven Rostedt	# kill the child with extreme prejudice
7245a391fbfSSteven Rostedt	kill 9, $child_pid;
7255a391fbfSSteven Rostedt    }
7265a391fbfSSteven Rostedt
7275a391fbfSSteven Rostedt    waitpid $child_pid, 0;
7285a391fbfSSteven Rostedt    $child_exit = $?;
7295a391fbfSSteven Rostedt
7305a391fbfSSteven Rostedt    if ($bug || $child_exit) {
7312b7d9b21SSteven Rostedt	return 0 if $in_bisect;
7322b7d9b21SSteven Rostedt	fail "test failed" and return 0;
7335a391fbfSSteven Rostedt    }
7342b7d9b21SSteven Rostedt    return 1;
7355a391fbfSSteven Rostedt}
7365a391fbfSSteven Rostedt
737a75fececSSteven Rostedtsub run_git_bisect {
738a75fececSSteven Rostedt    my ($command) = @_;
739a75fececSSteven Rostedt
740a75fececSSteven Rostedt    doprint "$command ... ";
741a75fececSSteven Rostedt
742a75fececSSteven Rostedt    my $output = `$command 2>&1`;
743a75fececSSteven Rostedt    my $ret = $?;
744a75fececSSteven Rostedt
745a75fececSSteven Rostedt    logit $output;
746a75fececSSteven Rostedt
747a75fececSSteven Rostedt    if ($ret) {
748a75fececSSteven Rostedt	doprint "FAILED\n";
749a75fececSSteven Rostedt	dodie "Failed to git bisect";
750a75fececSSteven Rostedt    }
751a75fececSSteven Rostedt
752a75fececSSteven Rostedt    doprint "SUCCESS\n";
753a75fececSSteven Rostedt    if ($output =~ m/^(Bisecting: .*\(roughly \d+ steps?\))\s+\[([[:xdigit:]]+)\]/) {
754a75fececSSteven Rostedt	doprint "$1 [$2]\n";
755a75fececSSteven Rostedt    } elsif ($output =~ m/^([[:xdigit:]]+) is the first bad commit/) {
756a75fececSSteven Rostedt	$bisect_bad = $1;
757a75fececSSteven Rostedt	doprint "Found bad commit... $1\n";
758a75fececSSteven Rostedt	return 0;
759a75fececSSteven Rostedt    } else {
760a75fececSSteven Rostedt	# we already logged it, just print it now.
761a75fececSSteven Rostedt	print $output;
762a75fececSSteven Rostedt    }
763a75fececSSteven Rostedt
764a75fececSSteven Rostedt    return 1;
765a75fececSSteven Rostedt}
766a75fececSSteven Rostedt
7675f9b6cedSSteven Rostedtsub run_bisect {
7685f9b6cedSSteven Rostedt    my ($type) = @_;
7695f9b6cedSSteven Rostedt
7702b7d9b21SSteven Rostedt    my $failed = 0;
7715f9b6cedSSteven Rostedt    my $result;
7725f9b6cedSSteven Rostedt    my $output;
7735f9b6cedSSteven Rostedt    my $ret;
7745f9b6cedSSteven Rostedt
7755f9b6cedSSteven Rostedt    if (defined($minconfig)) {
7762b7d9b21SSteven Rostedt	build "useconfig:$minconfig" or $failed = 1;
7775f9b6cedSSteven Rostedt    } else {
7785f9b6cedSSteven Rostedt	# ?? no config to use?
7792b7d9b21SSteven Rostedt	build "oldconfig" or $failed = 1;
7805f9b6cedSSteven Rostedt    }
7815f9b6cedSSteven Rostedt
7825f9b6cedSSteven Rostedt    if ($type ne "build") {
7837faafbd6SSteven Rostedt	dodie "Failed on build" if $failed;
7845f9b6cedSSteven Rostedt
7855f9b6cedSSteven Rostedt	# Now boot the box
7865f9b6cedSSteven Rostedt	get_grub_index;
7875f9b6cedSSteven Rostedt	get_version;
7885f9b6cedSSteven Rostedt	install;
7897faafbd6SSteven Rostedt
7907faafbd6SSteven Rostedt	start_monitor;
7912b7d9b21SSteven Rostedt	monitor or $failed = 1;
7925f9b6cedSSteven Rostedt
7935f9b6cedSSteven Rostedt	if ($type ne "boot") {
7947faafbd6SSteven Rostedt	    dodie "Failed on boot" if $failed;
7955a391fbfSSteven Rostedt
7962b7d9b21SSteven Rostedt	    do_run_test or $failed = 1;
7975f9b6cedSSteven Rostedt	}
7987faafbd6SSteven Rostedt	end_monitor;
7995f9b6cedSSteven Rostedt    }
8005f9b6cedSSteven Rostedt
8015f9b6cedSSteven Rostedt    if ($failed) {
8025f9b6cedSSteven Rostedt	$result = "bad";
8035a391fbfSSteven Rostedt
8045a391fbfSSteven Rostedt	# reboot the box to a good kernel
805a75fececSSteven Rostedt	if ($type ne "build") {
806a75fececSSteven Rostedt	    doprint "Reboot and sleep $bisect_sleep_time seconds\n";
8075a391fbfSSteven Rostedt	    reboot;
8087faafbd6SSteven Rostedt	    start_monitor;
809a75fececSSteven Rostedt	    wait_for_monitor $bisect_sleep_time;
8107faafbd6SSteven Rostedt	    end_monitor;
8115a391fbfSSteven Rostedt	}
8125f9b6cedSSteven Rostedt    } else {
8135f9b6cedSSteven Rostedt	$result = "good";
8145f9b6cedSSteven Rostedt    }
8155f9b6cedSSteven Rostedt
816d6ce2a0bSSteven Rostedt    # Are we looking for where it worked, not failed?
817d6ce2a0bSSteven Rostedt    if ($reverse_bisect) {
818d6ce2a0bSSteven Rostedt	if ($failed) {
819d6ce2a0bSSteven Rostedt	    $result = "good";
820d6ce2a0bSSteven Rostedt	} else {
821d6ce2a0bSSteven Rostedt	    $result = "bad";
822d6ce2a0bSSteven Rostedt	}
823d6ce2a0bSSteven Rostedt    }
824d6ce2a0bSSteven Rostedt
825a75fececSSteven Rostedt    return $result;
8265f9b6cedSSteven Rostedt}
8275f9b6cedSSteven Rostedt
8285f9b6cedSSteven Rostedtsub bisect {
8295f9b6cedSSteven Rostedt    my ($i) = @_;
8305f9b6cedSSteven Rostedt
8315f9b6cedSSteven Rostedt    my $result;
8325f9b6cedSSteven Rostedt
8335f9b6cedSSteven Rostedt    die "BISECT_GOOD[$i] not defined\n"	if (!defined($opt{"BISECT_GOOD[$i]"}));
8345f9b6cedSSteven Rostedt    die "BISECT_BAD[$i] not defined\n"	if (!defined($opt{"BISECT_BAD[$i]"}));
8355f9b6cedSSteven Rostedt    die "BISECT_TYPE[$i] not defined\n"	if (!defined($opt{"BISECT_TYPE[$i]"}));
8365f9b6cedSSteven Rostedt
8375f9b6cedSSteven Rostedt    my $good = $opt{"BISECT_GOOD[$i]"};
8385f9b6cedSSteven Rostedt    my $bad = $opt{"BISECT_BAD[$i]"};
8395f9b6cedSSteven Rostedt    my $type = $opt{"BISECT_TYPE[$i]"};
840a75fececSSteven Rostedt    my $start = $opt{"BISECT_START[$i]"};
841a75fececSSteven Rostedt    my $replay = $opt{"BISECT_REPLAY[$i]"};
8425f9b6cedSSteven Rostedt
843d6ce2a0bSSteven Rostedt    if (defined($opt{"BISECT_REVERSE[$i]"}) &&
844d6ce2a0bSSteven Rostedt	$opt{"BISECT_REVERSE[$i]"} == 1) {
845d6ce2a0bSSteven Rostedt	doprint "Performing a reverse bisect (bad is good, good is bad!)\n";
846d6ce2a0bSSteven Rostedt	$reverse_bisect = 1;
847d6ce2a0bSSteven Rostedt    } else {
848d6ce2a0bSSteven Rostedt	$reverse_bisect = 0;
849d6ce2a0bSSteven Rostedt    }
850d6ce2a0bSSteven Rostedt
8515f9b6cedSSteven Rostedt    $in_bisect = 1;
8525f9b6cedSSteven Rostedt
8535a391fbfSSteven Rostedt    # Can't have a test without having a test to run
8545a391fbfSSteven Rostedt    if ($type eq "test" && !defined($run_test)) {
8555a391fbfSSteven Rostedt	$type = "boot";
8565a391fbfSSteven Rostedt    }
8575a391fbfSSteven Rostedt
858a75fececSSteven Rostedt    my $check = $opt{"BISECT_CHECK[$i]"};
859a75fececSSteven Rostedt    if (defined($check) && $check ne "0") {
860a75fececSSteven Rostedt
861a75fececSSteven Rostedt	# get current HEAD
862a75fececSSteven Rostedt	doprint "git rev-list HEAD --max-count=1 ... ";
863a75fececSSteven Rostedt	my $head = `git rev-list HEAD --max-count=1`;
864a75fececSSteven Rostedt	my $ret = $?;
865a75fececSSteven Rostedt
866a75fececSSteven Rostedt	logit $head;
867a75fececSSteven Rostedt
868a75fececSSteven Rostedt	if ($ret) {
869a75fececSSteven Rostedt	    doprint "FAILED\n";
870a75fececSSteven Rostedt	    dodie "Failed to get git HEAD";
871a75fececSSteven Rostedt	}
872a75fececSSteven Rostedt
873a75fececSSteven Rostedt	print "SUCCESS\n";
874a75fececSSteven Rostedt
875a75fececSSteven Rostedt	chomp $head;
876a75fececSSteven Rostedt
877a75fececSSteven Rostedt	if ($check ne "good") {
878a75fececSSteven Rostedt	    doprint "TESTING BISECT BAD [$bad]\n";
879a75fececSSteven Rostedt	    run_command "git checkout $bad" or
880a75fececSSteven Rostedt		die "Failed to checkout $bad";
881a75fececSSteven Rostedt
882a75fececSSteven Rostedt	    $result = run_bisect $type;
883a75fececSSteven Rostedt
884a75fececSSteven Rostedt	    if ($result ne "bad") {
885a75fececSSteven Rostedt		fail "Tested BISECT_BAD [$bad] and it succeeded" and return 0;
886a75fececSSteven Rostedt	    }
887a75fececSSteven Rostedt	}
888a75fececSSteven Rostedt
889a75fececSSteven Rostedt	if ($check ne "bad") {
890a75fececSSteven Rostedt	    doprint "TESTING BISECT GOOD [$good]\n";
891a75fececSSteven Rostedt	    run_command "git checkout $good" or
892a75fececSSteven Rostedt		die "Failed to checkout $good";
893a75fececSSteven Rostedt
894a75fececSSteven Rostedt	    $result = run_bisect $type;
895a75fececSSteven Rostedt
896a75fececSSteven Rostedt	    if ($result ne "good") {
897a75fececSSteven Rostedt		fail "Tested BISECT_GOOD [$good] and it failed" and return 0;
898a75fececSSteven Rostedt	    }
899a75fececSSteven Rostedt	}
900a75fececSSteven Rostedt
901a75fececSSteven Rostedt	# checkout where we started
902a75fececSSteven Rostedt	run_command "git checkout $head" or
903a75fececSSteven Rostedt	    die "Failed to checkout $head";
904a75fececSSteven Rostedt    }
905a75fececSSteven Rostedt
906a75fececSSteven Rostedt    run_command "git bisect start" or
907a75fececSSteven Rostedt	dodie "could not start bisect";
908a75fececSSteven Rostedt
909a75fececSSteven Rostedt    run_command "git bisect good $good" or
910a75fececSSteven Rostedt	dodie "could not set bisect good to $good";
911a75fececSSteven Rostedt
912a75fececSSteven Rostedt    run_git_bisect "git bisect bad $bad" or
913a75fececSSteven Rostedt	dodie "could not set bisect bad to $bad";
914a75fececSSteven Rostedt
915a75fececSSteven Rostedt    if (defined($replay)) {
916a75fececSSteven Rostedt	run_command "git bisect replay $replay" or
917a75fececSSteven Rostedt	    dodie "failed to run replay";
918a75fececSSteven Rostedt    }
919a75fececSSteven Rostedt
920a75fececSSteven Rostedt    if (defined($start)) {
921a75fececSSteven Rostedt	run_command "git checkout $start" or
922a75fececSSteven Rostedt	    dodie "failed to checkout $start";
923a75fececSSteven Rostedt    }
924a75fececSSteven Rostedt
925a75fececSSteven Rostedt    my $test;
9265f9b6cedSSteven Rostedt    do {
9275f9b6cedSSteven Rostedt	$result = run_bisect $type;
928a75fececSSteven Rostedt	$test = run_git_bisect "git bisect $result";
929a75fececSSteven Rostedt    } while ($test);
9305f9b6cedSSteven Rostedt
9315f9b6cedSSteven Rostedt    run_command "git bisect log" or
9325f9b6cedSSteven Rostedt	dodie "could not capture git bisect log";
9335f9b6cedSSteven Rostedt
9345f9b6cedSSteven Rostedt    run_command "git bisect reset" or
9355f9b6cedSSteven Rostedt	dodie "could not reset git bisect";
9365f9b6cedSSteven Rostedt
9375f9b6cedSSteven Rostedt    doprint "Bad commit was [$bisect_bad]\n";
9385f9b6cedSSteven Rostedt
9395f9b6cedSSteven Rostedt    $in_bisect = 0;
9405f9b6cedSSteven Rostedt
9415f9b6cedSSteven Rostedt    success $i;
9425f9b6cedSSteven Rostedt}
9435f9b6cedSSteven Rostedt
9446c5ee0beSSteven Rostedtsub patchcheck {
9456c5ee0beSSteven Rostedt    my ($i) = @_;
9466c5ee0beSSteven Rostedt
9476c5ee0beSSteven Rostedt    die "PATCHCHECK_START[$i] not defined\n"
9486c5ee0beSSteven Rostedt	if (!defined($opt{"PATCHCHECK_START[$i]"}));
9496c5ee0beSSteven Rostedt    die "PATCHCHECK_TYPE[$i] not defined\n"
9506c5ee0beSSteven Rostedt	if (!defined($opt{"PATCHCHECK_TYPE[$i]"}));
9516c5ee0beSSteven Rostedt
9526c5ee0beSSteven Rostedt    my $start = $opt{"PATCHCHECK_START[$i]"};
9536c5ee0beSSteven Rostedt
9546c5ee0beSSteven Rostedt    my $end = "HEAD";
9556c5ee0beSSteven Rostedt    if (defined($opt{"PATCHCHECK_END[$i]"})) {
9566c5ee0beSSteven Rostedt	$end = $opt{"PATCHCHECK_END[$i]"};
9576c5ee0beSSteven Rostedt    }
9586c5ee0beSSteven Rostedt
9596c5ee0beSSteven Rostedt    my $type = $opt{"PATCHCHECK_TYPE[$i]"};
9606c5ee0beSSteven Rostedt
9616c5ee0beSSteven Rostedt    # Can't have a test without having a test to run
9626c5ee0beSSteven Rostedt    if ($type eq "test" && !defined($run_test)) {
9636c5ee0beSSteven Rostedt	$type = "boot";
9646c5ee0beSSteven Rostedt    }
9656c5ee0beSSteven Rostedt
9666c5ee0beSSteven Rostedt    open (IN, "git log --pretty=oneline $end|") or
9676c5ee0beSSteven Rostedt	dodie "could not get git list";
9686c5ee0beSSteven Rostedt
9696c5ee0beSSteven Rostedt    my @list;
9706c5ee0beSSteven Rostedt
9716c5ee0beSSteven Rostedt    while (<IN>) {
9726c5ee0beSSteven Rostedt	chomp;
9736c5ee0beSSteven Rostedt	$list[$#list+1] = $_;
9746c5ee0beSSteven Rostedt	last if (/^$start/);
9756c5ee0beSSteven Rostedt    }
9766c5ee0beSSteven Rostedt    close(IN);
9776c5ee0beSSteven Rostedt
9786c5ee0beSSteven Rostedt    if ($list[$#list] !~ /^$start/) {
9792b7d9b21SSteven Rostedt	fail "SHA1 $start not found";
9806c5ee0beSSteven Rostedt    }
9816c5ee0beSSteven Rostedt
9826c5ee0beSSteven Rostedt    # go backwards in the list
9836c5ee0beSSteven Rostedt    @list = reverse @list;
9846c5ee0beSSteven Rostedt
9856c5ee0beSSteven Rostedt    my $save_clean = $noclean;
9866c5ee0beSSteven Rostedt
9876c5ee0beSSteven Rostedt    $in_patchcheck = 1;
9886c5ee0beSSteven Rostedt    foreach my $item (@list) {
9896c5ee0beSSteven Rostedt	my $sha1 = $item;
9906c5ee0beSSteven Rostedt	$sha1 =~ s/^([[:xdigit:]]+).*/$1/;
9916c5ee0beSSteven Rostedt
9926c5ee0beSSteven Rostedt	doprint "\nProcessing commit $item\n\n";
9936c5ee0beSSteven Rostedt
9946c5ee0beSSteven Rostedt	run_command "git checkout $sha1" or
9956c5ee0beSSteven Rostedt	    die "Failed to checkout $sha1";
9966c5ee0beSSteven Rostedt
9976c5ee0beSSteven Rostedt	# only clean on the first and last patch
9986c5ee0beSSteven Rostedt	if ($item eq $list[0] ||
9996c5ee0beSSteven Rostedt	    $item eq $list[$#list]) {
10006c5ee0beSSteven Rostedt	    $noclean = $save_clean;
10016c5ee0beSSteven Rostedt	} else {
10026c5ee0beSSteven Rostedt	    $noclean = 1;
10036c5ee0beSSteven Rostedt	}
10046c5ee0beSSteven Rostedt
10056c5ee0beSSteven Rostedt	if (defined($minconfig)) {
10062b7d9b21SSteven Rostedt	    build "useconfig:$minconfig" or return 0;
10076c5ee0beSSteven Rostedt	} else {
10086c5ee0beSSteven Rostedt	    # ?? no config to use?
10092b7d9b21SSteven Rostedt	    build "oldconfig" or return 0;
10106c5ee0beSSteven Rostedt	}
10116c5ee0beSSteven Rostedt
10122b7d9b21SSteven Rostedt	check_buildlog $sha1 or return 0;
10136c5ee0beSSteven Rostedt
10146c5ee0beSSteven Rostedt	next if ($type eq "build");
10156c5ee0beSSteven Rostedt
10166c5ee0beSSteven Rostedt	get_grub_index;
10176c5ee0beSSteven Rostedt	get_version;
10186c5ee0beSSteven Rostedt	install;
10196c5ee0beSSteven Rostedt
10207faafbd6SSteven Rostedt	my $failed = 0;
10217faafbd6SSteven Rostedt
10227faafbd6SSteven Rostedt	start_monitor;
10237faafbd6SSteven Rostedt	monitor or $failed = 1;
10247faafbd6SSteven Rostedt
10257faafbd6SSteven Rostedt	if (!$failed && $type ne "boot"){
10267faafbd6SSteven Rostedt	    do_run_test or $failed = 1;
10277faafbd6SSteven Rostedt	}
10287faafbd6SSteven Rostedt	end_monitor;
10297faafbd6SSteven Rostedt	return 0 if ($failed);
10307faafbd6SSteven Rostedt
10316c5ee0beSSteven Rostedt    }
10326c5ee0beSSteven Rostedt    $in_patchcheck = 0;
10336c5ee0beSSteven Rostedt    success $i;
10342b7d9b21SSteven Rostedt
10352b7d9b21SSteven Rostedt    return 1;
10366c5ee0beSSteven Rostedt}
10376c5ee0beSSteven Rostedt
10382545eb61SSteven Rostedtread_config $ARGV[0];
10392545eb61SSteven Rostedt
10402545eb61SSteven Rostedt# mandatory configs
10412545eb61SSteven Rostedtdie "MACHINE not defined\n"		if (!defined($opt{"MACHINE"}));
10422545eb61SSteven Rostedtdie "SSH_USER not defined\n"		if (!defined($opt{"SSH_USER"}));
10432545eb61SSteven Rostedtdie "BUILD_DIR not defined\n"		if (!defined($opt{"BUILD_DIR"}));
10442545eb61SSteven Rostedtdie "OUTPUT_DIR not defined\n"		if (!defined($opt{"OUTPUT_DIR"}));
10452545eb61SSteven Rostedtdie "BUILD_TARGET not defined\n"	if (!defined($opt{"BUILD_TARGET"}));
104675c3fda7SSteven Rostedtdie "TARGET_IMAGE not defined\n"	if (!defined($opt{"TARGET_IMAGE"}));
10472545eb61SSteven Rostedtdie "POWER_CYCLE not defined\n"		if (!defined($opt{"POWER_CYCLE"}));
10482545eb61SSteven Rostedtdie "CONSOLE not defined\n"		if (!defined($opt{"CONSOLE"}));
10492545eb61SSteven Rostedtdie "LOCALVERSION not defined\n"	if (!defined($opt{"LOCALVERSION"}));
10502545eb61SSteven Rostedt
10512b7d9b21SSteven Rostedtif ($opt{"CLEAR_LOG"} && defined($opt{"LOG_FILE"})) {
10522b7d9b21SSteven Rostedt    unlink $opt{"LOG_FILE"};
10532b7d9b21SSteven Rostedt}
10542545eb61SSteven Rostedt
10552b7d9b21SSteven Rostedtdoprint "\n\nSTARTING AUTOMATED TESTS\n\n";
10562b7d9b21SSteven Rostedt
10572b7d9b21SSteven Rostedtforeach my $option (sort keys %opt) {
10582b7d9b21SSteven Rostedt    doprint "$option = $opt{$option}\n";
10592b7d9b21SSteven Rostedt}
10602545eb61SSteven Rostedt
1061a75fececSSteven Rostedtsub set_test_option {
10625a391fbfSSteven Rostedt    my ($name, $i) = @_;
10635a391fbfSSteven Rostedt
10645a391fbfSSteven Rostedt    my $option = "$name\[$i\]";
10655a391fbfSSteven Rostedt
10665a391fbfSSteven Rostedt    if (defined($opt{$option})) {
10675a391fbfSSteven Rostedt	return $opt{$option};
10685a391fbfSSteven Rostedt    }
10695a391fbfSSteven Rostedt
10705a391fbfSSteven Rostedt    if (defined($opt{$name})) {
10715a391fbfSSteven Rostedt	return $opt{$name};
10725a391fbfSSteven Rostedt    }
10735a391fbfSSteven Rostedt
10745a391fbfSSteven Rostedt    return undef;
10755a391fbfSSteven Rostedt}
10765a391fbfSSteven Rostedt
10772545eb61SSteven Rostedt# First we need to do is the builds
1078a75fececSSteven Rostedtfor (my $i = 1; $i <= $opt{"NUM_TESTS"}; $i++) {
10792545eb61SSteven Rostedt
1080*576f627cSSteven Rostedt    $iteration = $i;
1081*576f627cSSteven Rostedt
1082a75fececSSteven Rostedt    my $ssh_user = set_test_option("SSH_USER", $i);
1083a75fececSSteven Rostedt    my $makecmd = set_test_option("MAKE_CMD", $i);
1084a75fececSSteven Rostedt
1085a75fececSSteven Rostedt    $machine = set_test_option("MACHINE", $i);
1086a75fececSSteven Rostedt    $tmpdir = set_test_option("TMP_DIR", $i);
1087a75fececSSteven Rostedt    $outputdir = set_test_option("OUTPUT_DIR", $i);
1088a75fececSSteven Rostedt    $builddir = set_test_option("BUILD_DIR", $i);
1089a75fececSSteven Rostedt    $test_type = set_test_option("TEST_TYPE", $i);
1090a75fececSSteven Rostedt    $build_type = set_test_option("BUILD_TYPE", $i);
1091a75fececSSteven Rostedt    $build_options = set_test_option("BUILD_OPTIONS", $i);
1092a75fececSSteven Rostedt    $power_cycle = set_test_option("POWER_CYCLE", $i);
1093a75fececSSteven Rostedt    $noclean = set_test_option("BUILD_NOCLEAN", $i);
1094a75fececSSteven Rostedt    $minconfig = set_test_option("MIN_CONFIG", $i);
1095a75fececSSteven Rostedt    $run_test = set_test_option("TEST", $i);
1096a75fececSSteven Rostedt    $addconfig = set_test_option("ADD_CONFIG", $i);
1097a75fececSSteven Rostedt    $reboot_type = set_test_option("REBOOT_TYPE", $i);
1098a75fececSSteven Rostedt    $grub_menu = set_test_option("GRUB_MENU", $i);
10998b37ca8cSSteven Rostedt    $post_install = set_test_option("POST_INSTALL", $i);
1100a75fececSSteven Rostedt    $reboot_script = set_test_option("REBOOT_SCRIPT", $i);
1101a75fececSSteven Rostedt    $reboot_on_error = set_test_option("REBOOT_ON_ERROR", $i);
1102a75fececSSteven Rostedt    $poweroff_on_error = set_test_option("POWEROFF_ON_ERROR", $i);
1103a75fececSSteven Rostedt    $die_on_failure = set_test_option("DIE_ON_FAILURE", $i);
1104a75fececSSteven Rostedt    $power_off = set_test_option("POWER_OFF", $i);
1105*576f627cSSteven Rostedt    $powercycle_after_reboot = set_test_option("POWERCYCLE_AFTER_REBOOT", $i);
1106*576f627cSSteven Rostedt    $poweroff_after_halt = set_test_option("POWEROFF_AFTER_HALT", $i);
1107a75fececSSteven Rostedt    $sleep_time = set_test_option("SLEEP_TIME", $i);
1108a75fececSSteven Rostedt    $bisect_sleep_time = set_test_option("BISECT_SLEEP_TIME", $i);
1109a75fececSSteven Rostedt    $store_failures = set_test_option("STORE_FAILURES", $i);
1110a75fececSSteven Rostedt    $timeout = set_test_option("TIMEOUT", $i);
1111a75fececSSteven Rostedt    $booted_timeout = set_test_option("BOOTED_TIMEOUT", $i);
1112a75fececSSteven Rostedt    $console = set_test_option("CONSOLE", $i);
1113a75fececSSteven Rostedt    $success_line = set_test_option("SUCCESS_LINE", $i);
1114a75fececSSteven Rostedt    $build_target = set_test_option("BUILD_TARGET", $i);
1115a75fececSSteven Rostedt    $target_image = set_test_option("TARGET_IMAGE", $i);
1116a75fececSSteven Rostedt    $localversion = set_test_option("LOCALVERSION", $i);
1117a75fececSSteven Rostedt
1118a75fececSSteven Rostedt    chdir $builddir || die "can't change directory to $builddir";
1119a75fececSSteven Rostedt
1120a75fececSSteven Rostedt    if (!-d $tmpdir) {
1121a75fececSSteven Rostedt	mkpath($tmpdir) or
1122a75fececSSteven Rostedt	    die "can't create $tmpdir";
1123a75fececSSteven Rostedt    }
1124a75fececSSteven Rostedt
1125a75fececSSteven Rostedt    $target = "$ssh_user\@$machine";
1126a75fececSSteven Rostedt
1127a75fececSSteven Rostedt    $buildlog = "$tmpdir/buildlog-$machine";
1128a75fececSSteven Rostedt    $dmesg = "$tmpdir/dmesg-$machine";
1129a75fececSSteven Rostedt    $make = "$makecmd O=$outputdir";
1130a75fececSSteven Rostedt
1131a75fececSSteven Rostedt    if ($reboot_type eq "grub") {
1132*576f627cSSteven Rostedt	dodie "GRUB_MENU not defined" if (!defined($grub_menu));
1133a75fececSSteven Rostedt    } elsif (!defined($reboot_script)) {
1134*576f627cSSteven Rostedt	dodie "REBOOT_SCRIPT not defined"
1135a75fececSSteven Rostedt    }
1136a75fececSSteven Rostedt
1137a75fececSSteven Rostedt    my $run_type = $build_type;
1138a75fececSSteven Rostedt    if ($test_type eq "patchcheck") {
1139a75fececSSteven Rostedt	$run_type = $opt{"PATCHCHECK_TYPE[$i]"};
1140a75fececSSteven Rostedt    } elsif ($test_type eq "bisect") {
1141a75fececSSteven Rostedt	$run_type = $opt{"BISECT_TYPE[$i]"};
1142a75fececSSteven Rostedt    }
1143a75fececSSteven Rostedt
1144a75fececSSteven Rostedt    # mistake in config file?
1145a75fececSSteven Rostedt    if (!defined($run_type)) {
1146a75fececSSteven Rostedt	$run_type = "ERROR";
1147a75fececSSteven Rostedt    }
11482545eb61SSteven Rostedt
11492545eb61SSteven Rostedt    doprint "\n\n";
1150a75fececSSteven Rostedt    doprint "RUNNING TEST $i of $opt{NUM_TESTS} with option $test_type $run_type\n\n";
11517faafbd6SSteven Rostedt
11527faafbd6SSteven Rostedt    unlink $dmesg;
11537faafbd6SSteven Rostedt    unlink $buildlog;
11542545eb61SSteven Rostedt
11552b7d9b21SSteven Rostedt    if (!defined($minconfig)) {
11562b7d9b21SSteven Rostedt	$minconfig = $addconfig;
11572b7d9b21SSteven Rostedt
11582b7d9b21SSteven Rostedt    } elsif (defined($addconfig)) {
1159a75fececSSteven Rostedt	run_command "cat $addconfig $minconfig > $tmpdir/use_config" or
11602b7d9b21SSteven Rostedt	    dodie "Failed to create temp config";
1161a75fececSSteven Rostedt	$minconfig = "$tmpdir/use_config";
11622b7d9b21SSteven Rostedt    }
11632b7d9b21SSteven Rostedt
11646c5ee0beSSteven Rostedt    my $checkout = $opt{"CHECKOUT[$i]"};
11656c5ee0beSSteven Rostedt    if (defined($checkout)) {
11666c5ee0beSSteven Rostedt	run_command "git checkout $checkout" or
11676c5ee0beSSteven Rostedt	    die "failed to checkout $checkout";
11686c5ee0beSSteven Rostedt    }
11696c5ee0beSSteven Rostedt
1170a75fececSSteven Rostedt    if ($test_type eq "bisect") {
11715f9b6cedSSteven Rostedt	bisect $i;
11725f9b6cedSSteven Rostedt	next;
1173a75fececSSteven Rostedt    } elsif ($test_type eq "patchcheck") {
11746c5ee0beSSteven Rostedt	patchcheck $i;
11756c5ee0beSSteven Rostedt	next;
11765f9b6cedSSteven Rostedt    }
11775f9b6cedSSteven Rostedt
11787faafbd6SSteven Rostedt    if ($build_type ne "nobuild") {
11797faafbd6SSteven Rostedt	build $build_type or next;
11802545eb61SSteven Rostedt    }
11812545eb61SSteven Rostedt
1182a75fececSSteven Rostedt    if ($test_type ne "build") {
11835f9b6cedSSteven Rostedt	get_grub_index;
11845f9b6cedSSteven Rostedt	get_version;
11852545eb61SSteven Rostedt	install;
11865a391fbfSSteven Rostedt
11877faafbd6SSteven Rostedt	my $failed = 0;
11887faafbd6SSteven Rostedt	start_monitor;
11897faafbd6SSteven Rostedt	monitor or $failed = 1;;
1190a75fececSSteven Rostedt
1191a75fececSSteven Rostedt	if (!$failed && $test_type ne "boot" && defined($run_test)) {
11927faafbd6SSteven Rostedt	    do_run_test or $failed = 1;
11935a391fbfSSteven Rostedt	}
11947faafbd6SSteven Rostedt	end_monitor;
11957faafbd6SSteven Rostedt	next if ($failed);
1196a75fececSSteven Rostedt    }
11975a391fbfSSteven Rostedt
11985f9b6cedSSteven Rostedt    success $i;
119975c3fda7SSteven Rostedt}
12002545eb61SSteven Rostedt
12015c42fc5bSSteven Rostedtif ($opt{"POWEROFF_ON_SUCCESS"}) {
120275c3fda7SSteven Rostedt    halt;
1203*576f627cSSteven Rostedt} elsif ($opt{"REBOOT_ON_SUCCESS"} && !do_not_reboot) {
120475c3fda7SSteven Rostedt    reboot;
12055c42fc5bSSteven Rostedt}
120675c3fda7SSteven Rostedt
12072545eb61SSteven Rostedtexit 0;
1208