ktest: Allow overriding bisect test results
[linux-2.6-block.git] / tools / testing / ktest / ktest.pl
CommitLineData
2545eb61 1#!/usr/bin/perl -w
d6ce2a0b 2#
cce1dac8 3# Copyright 2010 - Steven Rostedt <srostedt@redhat.com>, Red Hat Inc.
d6ce2a0b
SR
4# Licensed under the terms of the GNU GPL License version 2
5#
2545eb61
SR
6
7use strict;
8use IPC::Open2;
9use Fcntl qw(F_GETFL F_SETFL O_NONBLOCK);
7faafbd6
SR
10use File::Path qw(mkpath);
11use File::Copy qw(cp);
2545eb61
SR
12use FileHandle;
13
e48c5293
SR
14my $VERSION = "0.2";
15
2545eb61
SR
16$| = 1;
17
18my %opt;
a57419b3
SR
19my %repeat_tests;
20my %repeats;
a75fecec 21my %default;
2545eb61
SR
22
23#default opts
a57419b3 24$default{"NUM_TESTS"} = 1;
bb8474b1 25$default{"TEST_TYPE"} = "build";
a75fecec
SR
26$default{"BUILD_TYPE"} = "randconfig";
27$default{"MAKE_CMD"} = "make";
28$default{"TIMEOUT"} = 120;
48920630 29$default{"TMP_DIR"} = "/tmp/ktest/\${MACHINE}";
a75fecec
SR
30$default{"SLEEP_TIME"} = 60; # sleep time between tests
31$default{"BUILD_NOCLEAN"} = 0;
32$default{"REBOOT_ON_ERROR"} = 0;
33$default{"POWEROFF_ON_ERROR"} = 0;
34$default{"REBOOT_ON_SUCCESS"} = 1;
35$default{"POWEROFF_ON_SUCCESS"} = 0;
36$default{"BUILD_OPTIONS"} = "";
37$default{"BISECT_SLEEP_TIME"} = 60; # sleep time between bisects
27d934b2 38$default{"PATCHCHECK_SLEEP_TIME"} = 60; # sleep time between patch checks
a75fecec 39$default{"CLEAR_LOG"} = 0;
c960bb9f 40$default{"BISECT_MANUAL"} = 0;
c23dca7c 41$default{"BISECT_SKIP"} = 1;
a75fecec 42$default{"SUCCESS_LINE"} = "login:";
f1a5b962 43$default{"DETECT_TRIPLE_FAULT"} = 1;
e0a8742e 44$default{"NO_INSTALL"} = 0;
a75fecec
SR
45$default{"BOOTED_TIMEOUT"} = 1;
46$default{"DIE_ON_FAILURE"} = 1;
e48c5293
SR
47$default{"SSH_EXEC"} = "ssh \$SSH_USER\@\$MACHINE \$SSH_COMMAND";
48$default{"SCP_TO_TARGET"} = "scp \$SRC_FILE \$SSH_USER\@\$MACHINE:\$DST_FILE";
49$default{"REBOOT"} = "ssh \$SSH_USER\@\$MACHINE reboot";
1c8a617a
SR
50$default{"STOP_AFTER_SUCCESS"} = 10;
51$default{"STOP_AFTER_FAILURE"} = 60;
2d01b26a 52$default{"STOP_TEST_AFTER"} = 600;
600bbf0a
SR
53
54# required, and we will ask users if they don't have them but we keep the default
55# value something that is common.
56$default{"REBOOT_TYPE"} = "grub";
8d1491ba 57$default{"LOCALVERSION"} = "-test";
600bbf0a
SR
58$default{"SSH_USER"} = "root";
59$default{"BUILD_TARGET"} = "arch/x86/boot/bzImage";
60$default{"TARGET_IMAGE"} = "/boot/vmlinuz-test";
2545eb61 61
8d1491ba 62my $ktest_config;
2545eb61 63my $version;
a75fecec 64my $machine;
e48c5293 65my $ssh_user;
a75fecec
SR
66my $tmpdir;
67my $builddir;
68my $outputdir;
51ad1dd1 69my $output_config;
a75fecec 70my $test_type;
7faafbd6 71my $build_type;
a75fecec 72my $build_options;
0bd6c1a3
SR
73my $pre_build;
74my $post_build;
75my $pre_build_die;
76my $post_build_die;
a75fecec
SR
77my $reboot_type;
78my $reboot_script;
79my $power_cycle;
e48c5293 80my $reboot;
a75fecec
SR
81my $reboot_on_error;
82my $poweroff_on_error;
83my $die_on_failure;
576f627c
SR
84my $powercycle_after_reboot;
85my $poweroff_after_halt;
e48c5293
SR
86my $ssh_exec;
87my $scp_to_target;
a75fecec
SR
88my $power_off;
89my $grub_menu;
2545eb61
SR
90my $grub_number;
91my $target;
92my $make;
8b37ca8c 93my $post_install;
e0a8742e 94my $no_install;
5c42fc5b 95my $noclean;
5f9b6ced 96my $minconfig;
4c4ab120 97my $start_minconfig;
35ce5952 98my $start_minconfig_defined;
4c4ab120
SR
99my $output_minconfig;
100my $ignore_config;
2b7d9b21 101my $addconfig;
5f9b6ced
SR
102my $in_bisect = 0;
103my $bisect_bad = "";
d6ce2a0b 104my $reverse_bisect;
c960bb9f 105my $bisect_manual;
c23dca7c 106my $bisect_skip;
30f75da5 107my $config_bisect_good;
c5dacb88
SR
108my $bisect_ret_good;
109my $bisect_ret_bad;
110my $bisect_ret_skip;
111my $bisect_ret_abort;
112my $bisect_ret_default;
6c5ee0be 113my $in_patchcheck = 0;
5a391fbf 114my $run_test;
6c5ee0be 115my $redirect;
7faafbd6 116my $buildlog;
a9dd5d63 117my $testlog;
7faafbd6
SR
118my $dmesg;
119my $monitor_fp;
120my $monitor_pid;
121my $monitor_cnt = 0;
a75fecec
SR
122my $sleep_time;
123my $bisect_sleep_time;
27d934b2 124my $patchcheck_sleep_time;
1990207d 125my $ignore_warnings;
a75fecec 126my $store_failures;
de5b6e3b 127my $store_successes;
9064af52 128my $test_name;
a75fecec
SR
129my $timeout;
130my $booted_timeout;
f1a5b962 131my $detect_triplefault;
a75fecec 132my $console;
2b803365 133my $reboot_success_line;
a75fecec 134my $success_line;
1c8a617a
SR
135my $stop_after_success;
136my $stop_after_failure;
2d01b26a 137my $stop_test_after;
a75fecec
SR
138my $build_target;
139my $target_image;
140my $localversion;
576f627c 141my $iteration = 0;
e48c5293 142my $successes = 0;
2545eb61 143
165708b2 144# set when a test is something other that just building or install
bb8474b1
SR
145# which would require more options.
146my $buildonly = 1;
147
dbd3783b
SR
148# set when creating a new config
149my $newconfig = 0;
150
8d1491ba
SR
151my %entered_configs;
152my %config_help;
77d942ce 153my %variable;
fcb3f16a 154my %force_config;
8d1491ba 155
4ab1cce5
SR
156# do not force reboots on config problems
157my $no_reboot = 1;
158
7bf51073
SR
159# default variables that can be used
160chomp ($variable{"PWD"} = `pwd`);
161
8d1491ba
SR
162$config_help{"MACHINE"} = << "EOF"
163 The machine hostname that you will test.
bb8474b1 164 For build only tests, it is still needed to differentiate log files.
8d1491ba
SR
165EOF
166 ;
167$config_help{"SSH_USER"} = << "EOF"
168 The box is expected to have ssh on normal bootup, provide the user
169 (most likely root, since you need privileged operations)
170EOF
171 ;
172$config_help{"BUILD_DIR"} = << "EOF"
173 The directory that contains the Linux source code (full path).
0e7a22de
SR
174 You can use \${PWD} that will be the path where ktest.pl is run, or use
175 \${THIS_DIR} which is assigned \${PWD} but may be changed later.
8d1491ba
SR
176EOF
177 ;
178$config_help{"OUTPUT_DIR"} = << "EOF"
179 The directory that the objects will be built (full path).
180 (can not be same as BUILD_DIR)
0e7a22de
SR
181 You can use \${PWD} that will be the path where ktest.pl is run, or use
182 \${THIS_DIR} which is assigned \${PWD} but may be changed later.
8d1491ba
SR
183EOF
184 ;
185$config_help{"BUILD_TARGET"} = << "EOF"
186 The location of the compiled file to copy to the target.
187 (relative to OUTPUT_DIR)
188EOF
189 ;
dbd3783b
SR
190$config_help{"BUILD_OPTIONS"} = << "EOF"
191 Options to add to \"make\" when building.
192 i.e. -j20
193EOF
194 ;
8d1491ba
SR
195$config_help{"TARGET_IMAGE"} = << "EOF"
196 The place to put your image on the test machine.
197EOF
198 ;
199$config_help{"POWER_CYCLE"} = << "EOF"
200 A script or command to reboot the box.
201
202 Here is a digital loggers power switch example
203 POWER_CYCLE = wget --no-proxy -O /dev/null -q --auth-no-challenge 'http://admin:admin\@power/outlet?5=CCL'
204
205 Here is an example to reboot a virtual box on the current host
206 with the name "Guest".
207 POWER_CYCLE = virsh destroy Guest; sleep 5; virsh start Guest
208EOF
209 ;
210$config_help{"CONSOLE"} = << "EOF"
211 The script or command that reads the console
212
213 If you use ttywatch server, something like the following would work.
214CONSOLE = nc -d localhost 3001
215
216 For a virtual machine with guest name "Guest".
217CONSOLE = virsh console Guest
218EOF
219 ;
220$config_help{"LOCALVERSION"} = << "EOF"
221 Required version ending to differentiate the test
222 from other linux builds on the system.
223EOF
224 ;
225$config_help{"REBOOT_TYPE"} = << "EOF"
226 Way to reboot the box to the test kernel.
227 Only valid options so far are "grub" and "script".
228
229 If you specify grub, it will assume grub version 1
230 and will search in /boot/grub/menu.lst for the title \$GRUB_MENU
231 and select that target to reboot to the kernel. If this is not
232 your setup, then specify "script" and have a command or script
233 specified in REBOOT_SCRIPT to boot to the target.
234
235 The entry in /boot/grub/menu.lst must be entered in manually.
236 The test will not modify that file.
237EOF
238 ;
239$config_help{"GRUB_MENU"} = << "EOF"
240 The grub title name for the test kernel to boot
241 (Only mandatory if REBOOT_TYPE = grub)
242
243 Note, ktest.pl will not update the grub menu.lst, you need to
244 manually add an option for the test. ktest.pl will search
245 the grub menu.lst for this option to find what kernel to
246 reboot into.
247
248 For example, if in the /boot/grub/menu.lst the test kernel title has:
249 title Test Kernel
250 kernel vmlinuz-test
251 GRUB_MENU = Test Kernel
252EOF
253 ;
254$config_help{"REBOOT_SCRIPT"} = << "EOF"
255 A script to reboot the target into the test kernel
256 (Only mandatory if REBOOT_TYPE = script)
257EOF
258 ;
259
dad98754
SR
260sub read_prompt {
261 my ($cancel, $prompt) = @_;
35ce5952
SR
262
263 my $ans;
264
265 for (;;) {
dad98754
SR
266 if ($cancel) {
267 print "$prompt [y/n/C] ";
268 } else {
269 print "$prompt [Y/n] ";
270 }
35ce5952
SR
271 $ans = <STDIN>;
272 chomp $ans;
273 if ($ans =~ /^\s*$/) {
dad98754
SR
274 if ($cancel) {
275 $ans = "c";
276 } else {
277 $ans = "y";
278 }
35ce5952
SR
279 }
280 last if ($ans =~ /^y$/i || $ans =~ /^n$/i);
dad98754
SR
281 if ($cancel) {
282 last if ($ans =~ /^c$/i);
283 print "Please answer either 'y', 'n' or 'c'.\n";
284 } else {
285 print "Please answer either 'y' or 'n'.\n";
286 }
287 }
288 if ($ans =~ /^c/i) {
289 exit;
35ce5952
SR
290 }
291 if ($ans !~ /^y$/i) {
292 return 0;
293 }
294 return 1;
295}
8d1491ba 296
dad98754
SR
297sub read_yn {
298 my ($prompt) = @_;
299
300 return read_prompt 0, $prompt;
301}
302
303sub read_ync {
304 my ($prompt) = @_;
305
306 return read_prompt 1, $prompt;
307}
308
8d1491ba
SR
309sub get_ktest_config {
310 my ($config) = @_;
815e2bd7 311 my $ans;
8d1491ba
SR
312
313 return if (defined($opt{$config}));
314
315 if (defined($config_help{$config})) {
316 print "\n";
317 print $config_help{$config};
318 }
319
320 for (;;) {
321 print "$config = ";
dbd3783b 322 if (defined($default{$config}) && length($default{$config})) {
8d1491ba
SR
323 print "\[$default{$config}\] ";
324 }
815e2bd7
SR
325 $ans = <STDIN>;
326 $ans =~ s/^\s*(.*\S)\s*$/$1/;
327 if ($ans =~ /^\s*$/) {
8d1491ba 328 if ($default{$config}) {
815e2bd7 329 $ans = $default{$config};
8d1491ba
SR
330 } else {
331 print "Your answer can not be blank\n";
332 next;
333 }
334 }
0e7a22de 335 $entered_configs{$config} = ${ans};
8d1491ba
SR
336 last;
337 }
338}
339
340sub get_ktest_configs {
341 get_ktest_config("MACHINE");
8d1491ba
SR
342 get_ktest_config("BUILD_DIR");
343 get_ktest_config("OUTPUT_DIR");
bb8474b1 344
dbd3783b
SR
345 if ($newconfig) {
346 get_ktest_config("BUILD_OPTIONS");
347 }
348
bb8474b1
SR
349 # options required for other than just building a kernel
350 if (!$buildonly) {
165708b2
SR
351 get_ktest_config("POWER_CYCLE");
352 get_ktest_config("CONSOLE");
353 }
354
355 # options required for install and more
356 if ($buildonly != 1) {
bb8474b1
SR
357 get_ktest_config("SSH_USER");
358 get_ktest_config("BUILD_TARGET");
359 get_ktest_config("TARGET_IMAGE");
bb8474b1
SR
360 }
361
8d1491ba
SR
362 get_ktest_config("LOCALVERSION");
363
bb8474b1
SR
364 return if ($buildonly);
365
8d1491ba
SR
366 my $rtype = $opt{"REBOOT_TYPE"};
367
368 if (!defined($rtype)) {
369 if (!defined($opt{"GRUB_MENU"})) {
370 get_ktest_config("REBOOT_TYPE");
371 $rtype = $entered_configs{"REBOOT_TYPE"};
372 } else {
373 $rtype = "grub";
374 }
375 }
376
377 if ($rtype eq "grub") {
378 get_ktest_config("GRUB_MENU");
379 } else {
380 get_ktest_config("REBOOT_SCRIPT");
381 }
382}
383
77d942ce 384sub process_variables {
8d735212 385 my ($value, $remove_undef) = @_;
77d942ce
SR
386 my $retval = "";
387
388 # We want to check for '\', and it is just easier
389 # to check the previous characet of '$' and not need
390 # to worry if '$' is the first character. By adding
391 # a space to $value, we can just check [^\\]\$ and
392 # it will still work.
393 $value = " $value";
394
395 while ($value =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
396 my $begin = $1;
397 my $var = $2;
398 my $end = $3;
399 # append beginning of value to retval
400 $retval = "$retval$begin";
401 if (defined($variable{$var})) {
402 $retval = "$retval$variable{$var}";
8d735212
SR
403 } elsif (defined($remove_undef) && $remove_undef) {
404 # for if statements, any variable that is not defined,
405 # we simple convert to 0
406 $retval = "${retval}0";
77d942ce
SR
407 } else {
408 # put back the origin piece.
409 $retval = "$retval\$\{$var\}";
410 }
411 $value = $end;
412 }
413 $retval = "$retval$value";
414
415 # remove the space added in the beginning
416 $retval =~ s/ //;
417
418 return "$retval"
419}
420
a57419b3 421sub set_value {
3d1cc414 422 my ($lvalue, $rvalue, $override, $overrides, $name) = @_;
a57419b3 423
cad96669
SR
424 my $prvalue = process_variables($rvalue);
425
426 if ($buildonly && $lvalue =~ /^TEST_TYPE(\[.*\])?$/ && $prvalue ne "build") {
bb8474b1
SR
427 # Note if a test is something other than build, then we
428 # will need other manditory options.
cad96669 429 if ($prvalue ne "install") {
165708b2
SR
430 $buildonly = 0;
431 } else {
432 # install still limits some manditory options.
433 $buildonly = 2;
434 }
bb8474b1
SR
435 }
436
a57419b3 437 if (defined($opt{$lvalue})) {
3d1cc414
SR
438 if (!$override || defined(${$overrides}{$lvalue})) {
439 my $extra = "";
440 if ($override) {
441 $extra = "In the same override section!\n";
442 }
443 die "$name: $.: Option $lvalue defined more than once!\n$extra";
444 }
cad96669 445 ${$overrides}{$lvalue} = $prvalue;
a57419b3 446 }
21a9679f
SR
447 if ($rvalue =~ /^\s*$/) {
448 delete $opt{$lvalue};
449 } else {
cad96669 450 $opt{$lvalue} = $prvalue;
21a9679f 451 }
a57419b3
SR
452}
453
77d942ce
SR
454sub set_variable {
455 my ($lvalue, $rvalue) = @_;
456
457 if ($rvalue =~ /^\s*$/) {
458 delete $variable{$lvalue};
459 } else {
460 $rvalue = process_variables($rvalue);
461 $variable{$lvalue} = $rvalue;
462 }
463}
464
ab7a3f52
SR
465sub process_compare {
466 my ($lval, $cmp, $rval) = @_;
467
468 # remove whitespace
469
470 $lval =~ s/^\s*//;
471 $lval =~ s/\s*$//;
472
473 $rval =~ s/^\s*//;
474 $rval =~ s/\s*$//;
475
476 if ($cmp eq "==") {
477 return $lval eq $rval;
478 } elsif ($cmp eq "!=") {
479 return $lval ne $rval;
480 }
481
482 my $statement = "$lval $cmp $rval";
483 my $ret = eval $statement;
484
485 # $@ stores error of eval
486 if ($@) {
487 return -1;
488 }
489
490 return $ret;
491}
492
9900b5dc
SR
493sub value_defined {
494 my ($val) = @_;
495
496 return defined($variable{$2}) ||
497 defined($opt{$2});
498}
499
8d735212
SR
500my $d = 0;
501sub process_expression {
502 my ($name, $val) = @_;
503
504 my $c = $d++;
505
506 while ($val =~ s/\(([^\(]*?)\)/\&\&\&\&VAL\&\&\&\&/) {
507 my $express = $1;
508
509 if (process_expression($name, $express)) {
510 $val =~ s/\&\&\&\&VAL\&\&\&\&/ 1 /;
511 } else {
512 $val =~ s/\&\&\&\&VAL\&\&\&\&/ 0 /;
513 }
514 }
515
516 $d--;
517 my $OR = "\\|\\|";
518 my $AND = "\\&\\&";
45d73a5d 519
8d735212
SR
520 while ($val =~ s/^(.*?)($OR|$AND)//) {
521 my $express = $1;
522 my $op = $2;
523
524 if (process_expression($name, $express)) {
525 if ($op eq "||") {
526 return 1;
527 }
528 } else {
529 if ($op eq "&&") {
530 return 0;
531 }
532 }
533 }
45d73a5d 534
ab7a3f52
SR
535 if ($val =~ /(.*)(==|\!=|>=|<=|>|<)(.*)/) {
536 my $ret = process_compare($1, $2, $3);
537 if ($ret < 0) {
538 die "$name: $.: Unable to process comparison\n";
539 }
540 return $ret;
541 }
542
9900b5dc
SR
543 if ($val =~ /^\s*(NOT\s*)?DEFINED\s+(\S+)\s*$/) {
544 if (defined $1) {
545 return !value_defined($2);
546 } else {
547 return value_defined($2);
548 }
549 }
550
45d73a5d
SR
551 if ($val =~ /^\s*0\s*$/) {
552 return 0;
553 } elsif ($val =~ /^\s*\d+\s*$/) {
554 return 1;
555 }
556
9900b5dc 557 die ("$name: $.: Undefined content $val in if statement\n");
8d735212
SR
558}
559
560sub process_if {
561 my ($name, $value) = @_;
562
563 # Convert variables and replace undefined ones with 0
564 my $val = process_variables($value, 1);
565 my $ret = process_expression $name, $val;
566
567 return $ret;
45d73a5d
SR
568}
569
2ed3b161
SR
570sub __read_config {
571 my ($config, $current_test_num) = @_;
2545eb61 572
2ed3b161
SR
573 my $in;
574 open($in, $config) || die "can't read file $config";
2545eb61 575
a57419b3
SR
576 my $name = $config;
577 $name =~ s,.*/(.*),$1,;
578
2ed3b161 579 my $test_num = $$current_test_num;
a57419b3
SR
580 my $default = 1;
581 my $repeat = 1;
582 my $num_tests_set = 0;
583 my $skip = 0;
584 my $rest;
a9f84424 585 my $line;
0df213ca 586 my $test_case = 0;
45d73a5d
SR
587 my $if = 0;
588 my $if_set = 0;
3d1cc414
SR
589 my $override = 0;
590
591 my %overrides;
a57419b3 592
2ed3b161 593 while (<$in>) {
2545eb61
SR
594
595 # ignore blank lines and comments
596 next if (/^\s*$/ || /\s*\#/);
597
0050b6bb 598 if (/^\s*(TEST_START|DEFAULTS)\b(.*)/) {
a57419b3 599
0050b6bb
SR
600 my $type = $1;
601 $rest = $2;
a9f84424 602 $line = $2;
a57419b3 603
0050b6bb
SR
604 my $old_test_num;
605 my $old_repeat;
3d1cc414 606 $override = 0;
0050b6bb
SR
607
608 if ($type eq "TEST_START") {
609
610 if ($num_tests_set) {
611 die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
612 }
a57419b3 613
0050b6bb
SR
614 $old_test_num = $test_num;
615 $old_repeat = $repeat;
a57419b3 616
0050b6bb
SR
617 $test_num += $repeat;
618 $default = 0;
619 $repeat = 1;
620 } else {
621 $default = 1;
622 }
a57419b3 623
a9f84424
SR
624 # If SKIP is anywhere in the line, the command will be skipped
625 if ($rest =~ s/\s+SKIP\b//) {
a57419b3
SR
626 $skip = 1;
627 } else {
0df213ca 628 $test_case = 1;
a57419b3
SR
629 $skip = 0;
630 }
631
a9f84424
SR
632 if ($rest =~ s/\sELSE\b//) {
633 if (!$if) {
634 die "$name: $.: ELSE found with out matching IF section\n$_";
635 }
636 $if = 0;
637
638 if ($if_set) {
639 $skip = 1;
640 } else {
641 $skip = 0;
3d1cc414 642 }
a57419b3
SR
643 }
644
a9f84424 645 if ($rest =~ s/\sIF\s+(.*)//) {
45d73a5d
SR
646 if (process_if($name, $1)) {
647 $if_set = 1;
648 } else {
649 $skip = 1;
650 }
651 $if = 1;
652 } else {
653 $if = 0;
a9f84424
SR
654 $if_set = 0;
655 }
656
657 if (!$skip) {
658 if ($type eq "TEST_START") {
659 if ($rest =~ s/\s+ITERATE\s+(\d+)//) {
660 $repeat = $1;
661 $repeat_tests{"$test_num"} = $repeat;
662 }
663 } elsif ($rest =~ s/\sOVERRIDE\b//) {
664 # DEFAULT only
665 $override = 1;
666 # Clear previous overrides
667 %overrides = ();
668 }
a57419b3
SR
669 }
670
a9f84424 671 if (!$skip && $rest !~ /^\s*$/) {
0050b6bb 672 die "$name: $.: Gargbage found after $type\n$_";
a57419b3
SR
673 }
674
0050b6bb 675 if ($skip && $type eq "TEST_START") {
a57419b3 676 $test_num = $old_test_num;
e48c5293 677 $repeat = $old_repeat;
a57419b3
SR
678 }
679
ab7a3f52 680 } elsif (/^\s*ELSE\b(.*)$/) {
45d73a5d
SR
681 if (!$if) {
682 die "$name: $.: ELSE found with out matching IF section\n$_";
683 }
684 $rest = $1;
685 if ($if_set) {
686 $skip = 1;
ab7a3f52 687 $rest = "";
45d73a5d
SR
688 } else {
689 $skip = 0;
690
ab7a3f52 691 if ($rest =~ /\sIF\s+(.*)/) {
45d73a5d
SR
692 # May be a ELSE IF section.
693 if (!process_if($name, $1)) {
694 $skip = 1;
695 }
ab7a3f52 696 $rest = "";
45d73a5d
SR
697 } else {
698 $if = 0;
699 }
700 }
701
ab7a3f52
SR
702 if ($rest !~ /^\s*$/) {
703 die "$name: $.: Gargbage found after DEFAULTS\n$_";
704 }
705
2ed3b161
SR
706 } elsif (/^\s*INCLUDE\s+(\S+)/) {
707
708 next if ($skip);
709
710 if (!$default) {
711 die "$name: $.: INCLUDE can only be done in default sections\n$_";
712 }
713
714 my $file = process_variables($1);
715
716 if ($file !~ m,^/,) {
717 # check the path of the config file first
718 if ($config =~ m,(.*)/,) {
719 if (-f "$1/$file") {
720 $file = "$1/$file";
721 }
722 }
723 }
724
725 if ( ! -r $file ) {
726 die "$name: $.: Can't read file $file\n$_";
727 }
728
729 if (__read_config($file, \$test_num)) {
730 $test_case = 1;
731 }
732
a57419b3
SR
733 } elsif (/^\s*([A-Z_\[\]\d]+)\s*=\s*(.*?)\s*$/) {
734
735 next if ($skip);
736
2545eb61
SR
737 my $lvalue = $1;
738 my $rvalue = $2;
739
a57419b3
SR
740 if (!$default &&
741 ($lvalue eq "NUM_TESTS" ||
742 $lvalue eq "LOG_FILE" ||
743 $lvalue eq "CLEAR_LOG")) {
744 die "$name: $.: $lvalue must be set in DEFAULTS section\n";
745 }
746
747 if ($lvalue eq "NUM_TESTS") {
748 if ($test_num) {
749 die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
750 }
751 if (!$default) {
752 die "$name: $.: NUM_TESTS must be set in default section\n";
753 }
754 $num_tests_set = 1;
755 }
756
757 if ($default || $lvalue =~ /\[\d+\]$/) {
3d1cc414 758 set_value($lvalue, $rvalue, $override, \%overrides, $name);
a57419b3
SR
759 } else {
760 my $val = "$lvalue\[$test_num\]";
3d1cc414 761 set_value($val, $rvalue, $override, \%overrides, $name);
a57419b3
SR
762
763 if ($repeat > 1) {
764 $repeats{$val} = $repeat;
765 }
a75fecec 766 }
77d942ce
SR
767 } elsif (/^\s*([A-Z_\[\]\d]+)\s*:=\s*(.*?)\s*$/) {
768 next if ($skip);
769
770 my $lvalue = $1;
771 my $rvalue = $2;
772
773 # process config variables.
774 # Config variables are only active while reading the
775 # config and can be defined anywhere. They also ignore
776 # TEST_START and DEFAULTS, but are skipped if they are in
777 # on of these sections that have SKIP defined.
778 # The save variable can be
779 # defined multiple times and the new one simply overrides
780 # the prevous one.
781 set_variable($lvalue, $rvalue);
782
a57419b3
SR
783 } else {
784 die "$name: $.: Garbage found in config\n$_";
2545eb61
SR
785 }
786 }
787
a57419b3
SR
788 if ($test_num) {
789 $test_num += $repeat - 1;
790 $opt{"NUM_TESTS"} = $test_num;
791 }
792
2ed3b161
SR
793 close($in);
794
795 $$current_test_num = $test_num;
796
797 return $test_case;
798}
799
c4261d0f
SR
800sub get_test_case {
801 print "What test case would you like to run?\n";
802 print " (build, install or boot)\n";
803 print " Other tests are available but require editing the config file\n";
804 my $ans = <STDIN>;
805 chomp $ans;
806 $default{"TEST_TYPE"} = $ans;
807}
808
2ed3b161
SR
809sub read_config {
810 my ($config) = @_;
811
812 my $test_case;
813 my $test_num = 0;
814
815 $test_case = __read_config $config, \$test_num;
816
8d1491ba
SR
817 # make sure we have all mandatory configs
818 get_ktest_configs;
819
0df213ca
SR
820 # was a test specified?
821 if (!$test_case) {
822 print "No test case specified.\n";
c4261d0f 823 get_test_case;
0df213ca
SR
824 }
825
a75fecec
SR
826 # set any defaults
827
828 foreach my $default (keys %default) {
829 if (!defined($opt{$default})) {
830 $opt{$default} = $default{$default};
831 }
832 }
2545eb61
SR
833}
834
23715c3c
SR
835sub __eval_option {
836 my ($option, $i) = @_;
837
838 # Add space to evaluate the character before $
839 $option = " $option";
840 my $retval = "";
f9dfb65b
RV
841 my $repeated = 0;
842 my $parent = 0;
843
844 foreach my $test (keys %repeat_tests) {
845 if ($i >= $test &&
846 $i < $test + $repeat_tests{$test}) {
847
848 $repeated = 1;
849 $parent = $test;
850 last;
851 }
852 }
23715c3c
SR
853
854 while ($option =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
855 my $start = $1;
856 my $var = $2;
857 my $end = $3;
858
859 # Append beginning of line
860 $retval = "$retval$start";
861
862 # If the iteration option OPT[$i] exists, then use that.
863 # otherwise see if the default OPT (without [$i]) exists.
864
865 my $o = "$var\[$i\]";
f9dfb65b 866 my $parento = "$var\[$parent\]";
23715c3c
SR
867
868 if (defined($opt{$o})) {
869 $o = $opt{$o};
870 $retval = "$retval$o";
f9dfb65b
RV
871 } elsif ($repeated && defined($opt{$parento})) {
872 $o = $opt{$parento};
873 $retval = "$retval$o";
23715c3c
SR
874 } elsif (defined($opt{$var})) {
875 $o = $opt{$var};
876 $retval = "$retval$o";
877 } else {
878 $retval = "$retval\$\{$var\}";
879 }
880
881 $option = $end;
882 }
883
884 $retval = "$retval$option";
885
886 $retval =~ s/^ //;
887
888 return $retval;
889}
890
891sub eval_option {
892 my ($option, $i) = @_;
893
894 my $prev = "";
895
896 # Since an option can evaluate to another option,
897 # keep iterating until we do not evaluate any more
898 # options.
899 my $r = 0;
900 while ($prev ne $option) {
901 # Check for recursive evaluations.
902 # 100 deep should be more than enough.
903 if ($r++ > 100) {
904 die "Over 100 evaluations accurred with $option\n" .
905 "Check for recursive variables\n";
906 }
907 $prev = $option;
908 $option = __eval_option($option, $i);
909 }
910
911 return $option;
912}
913
d1e2f22a 914sub _logit {
2545eb61
SR
915 if (defined($opt{"LOG_FILE"})) {
916 open(OUT, ">> $opt{LOG_FILE}") or die "Can't write to $opt{LOG_FILE}";
917 print OUT @_;
918 close(OUT);
919 }
920}
921
d1e2f22a
SR
922sub logit {
923 if (defined($opt{"LOG_FILE"})) {
924 _logit @_;
925 } else {
926 print @_;
927 }
928}
929
5f9b6ced
SR
930sub doprint {
931 print @_;
d1e2f22a 932 _logit @_;
5f9b6ced
SR
933}
934
7faafbd6 935sub run_command;
2728be41
AJ
936sub start_monitor;
937sub end_monitor;
938sub wait_for_monitor;
7faafbd6
SR
939
940sub reboot {
2728be41
AJ
941 my ($time) = @_;
942
2b803365
SR
943 if (defined($time)) {
944 start_monitor;
945 # flush out current monitor
946 # May contain the reboot success line
947 wait_for_monitor 1;
948 }
949
7faafbd6 950 # try to reboot normally
e48c5293 951 if (run_command $reboot) {
576f627c
SR
952 if (defined($powercycle_after_reboot)) {
953 sleep $powercycle_after_reboot;
954 run_command "$power_cycle";
955 }
956 } else {
7faafbd6 957 # nope? power cycle it.
a75fecec 958 run_command "$power_cycle";
7faafbd6 959 }
2728be41
AJ
960
961 if (defined($time)) {
2b803365 962 wait_for_monitor($time, $reboot_success_line);
2728be41
AJ
963 end_monitor;
964 }
7faafbd6
SR
965}
966
576f627c
SR
967sub do_not_reboot {
968 my $i = $iteration;
969
4ab1cce5 970 return $test_type eq "build" || $no_reboot ||
576f627c
SR
971 ($test_type eq "patchcheck" && $opt{"PATCHCHECK_TYPE[$i]"} eq "build") ||
972 ($test_type eq "bisect" && $opt{"BISECT_TYPE[$i]"} eq "build");
973}
974
5c42fc5b 975sub dodie {
5a391fbf 976 doprint "CRITICAL FAILURE... ", @_, "\n";
5c42fc5b 977
576f627c
SR
978 my $i = $iteration;
979
980 if ($reboot_on_error && !do_not_reboot) {
981
75c3fda7 982 doprint "REBOOTING\n";
7faafbd6 983 reboot;
75c3fda7 984
a75fecec 985 } elsif ($poweroff_on_error && defined($power_off)) {
5c42fc5b 986 doprint "POWERING OFF\n";
a75fecec 987 `$power_off`;
5c42fc5b 988 }
75c3fda7 989
f80802cb
SR
990 if (defined($opt{"LOG_FILE"})) {
991 print " See $opt{LOG_FILE} for more info.\n";
992 }
993
576f627c 994 die @_, "\n";
5c42fc5b
SR
995}
996
7faafbd6
SR
997sub open_console {
998 my ($fp) = @_;
999
1000 my $flags;
1001
a75fecec
SR
1002 my $pid = open($fp, "$console|") or
1003 dodie "Can't open console $console";
7faafbd6
SR
1004
1005 $flags = fcntl($fp, F_GETFL, 0) or
576f627c 1006 dodie "Can't get flags for the socket: $!";
7faafbd6 1007 $flags = fcntl($fp, F_SETFL, $flags | O_NONBLOCK) or
576f627c 1008 dodie "Can't set flags for the socket: $!";
7faafbd6
SR
1009
1010 return $pid;
1011}
1012
1013sub close_console {
1014 my ($fp, $pid) = @_;
1015
1016 doprint "kill child process $pid\n";
1017 kill 2, $pid;
1018
1019 print "closing!\n";
1020 close($fp);
1021}
1022
1023sub start_monitor {
1024 if ($monitor_cnt++) {
1025 return;
1026 }
1027 $monitor_fp = \*MONFD;
1028 $monitor_pid = open_console $monitor_fp;
a75fecec
SR
1029
1030 return;
1031
1032 open(MONFD, "Stop perl from warning about single use of MONFD");
7faafbd6
SR
1033}
1034
1035sub end_monitor {
1036 if (--$monitor_cnt) {
1037 return;
1038 }
1039 close_console($monitor_fp, $monitor_pid);
1040}
1041
1042sub wait_for_monitor {
2b803365
SR
1043 my ($time, $stop) = @_;
1044 my $full_line = "";
7faafbd6 1045 my $line;
2b803365 1046 my $booted = 0;
7faafbd6 1047
a75fecec 1048 doprint "** Wait for monitor to settle down **\n";
7faafbd6
SR
1049
1050 # read the monitor and wait for the system to calm down
2b803365 1051 while (!$booted) {
7faafbd6 1052 $line = wait_for_input($monitor_fp, $time);
2b803365
SR
1053 last if (!defined($line));
1054 print "$line";
1055 $full_line .= $line;
1056
1057 if (defined($stop) && $full_line =~ /$stop/) {
1058 doprint "wait for monitor detected $stop\n";
1059 $booted = 1;
1060 }
1061
1062 if ($line =~ /\n/) {
1063 $full_line = "";
1064 }
1065 }
a75fecec 1066 print "** Monitor flushed **\n";
7faafbd6
SR
1067}
1068
de5b6e3b
RV
1069sub save_logs {
1070 my ($result, $basedir) = @_;
1071 my @t = localtime;
1072 my $date = sprintf "%04d%02d%02d%02d%02d%02d",
1073 1900+$t[5],$t[4],$t[3],$t[2],$t[1],$t[0];
1074
1075 my $type = $build_type;
1076 if ($type =~ /useconfig/) {
1077 $type = "useconfig";
1078 }
1079
1080 my $dir = "$machine-$test_type-$type-$result-$date";
1081
1082 $dir = "$basedir/$dir";
1083
1084 if (!-d $dir) {
1085 mkpath($dir) or
1086 die "can't create $dir";
1087 }
1088
1089 my %files = (
1090 "config" => $output_config,
1091 "buildlog" => $buildlog,
1092 "dmesg" => $dmesg,
1093 "testlog" => $testlog,
1094 );
1095
1096 while (my ($name, $source) = each(%files)) {
1097 if (-f "$source") {
1098 cp "$source", "$dir/$name" or
1099 die "failed to copy $source";
1100 }
1101 }
1102
1103 doprint "*** Saved info to $dir ***\n";
1104}
1105
2b7d9b21
SR
1106sub fail {
1107
a75fecec 1108 if ($die_on_failure) {
2b7d9b21
SR
1109 dodie @_;
1110 }
1111
a75fecec 1112 doprint "FAILED\n";
7faafbd6 1113
576f627c
SR
1114 my $i = $iteration;
1115
a75fecec 1116 # no need to reboot for just building.
576f627c 1117 if (!do_not_reboot) {
a75fecec 1118 doprint "REBOOTING\n";
2728be41 1119 reboot $sleep_time;
a75fecec 1120 }
7faafbd6 1121
9064af52
SR
1122 my $name = "";
1123
1124 if (defined($test_name)) {
1125 $name = " ($test_name)";
1126 }
1127
576f627c
SR
1128 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1129 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
9064af52 1130 doprint "KTEST RESULT: TEST $i$name Failed: ", @_, "\n";
576f627c
SR
1131 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1132 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
a75fecec 1133
de5b6e3b
RV
1134 if (defined($store_failures)) {
1135 save_logs "fail", $store_failures;
1136 }
7faafbd6 1137
2b7d9b21
SR
1138 return 1;
1139}
1140
2545eb61
SR
1141sub run_command {
1142 my ($command) = @_;
d6ce2a0b
SR
1143 my $dolog = 0;
1144 my $dord = 0;
1145 my $pid;
1146
e48c5293
SR
1147 $command =~ s/\$SSH_USER/$ssh_user/g;
1148 $command =~ s/\$MACHINE/$machine/g;
1149
d6ce2a0b
SR
1150 doprint("$command ... ");
1151
1152 $pid = open(CMD, "$command 2>&1 |") or
2b7d9b21 1153 (fail "unable to exec $command" and return 0);
2545eb61
SR
1154
1155 if (defined($opt{"LOG_FILE"})) {
d6ce2a0b
SR
1156 open(LOG, ">>$opt{LOG_FILE}") or
1157 dodie "failed to write to log";
1158 $dolog = 1;
6c5ee0be
SR
1159 }
1160
1161 if (defined($redirect)) {
d6ce2a0b
SR
1162 open (RD, ">$redirect") or
1163 dodie "failed to write to redirect $redirect";
1164 $dord = 1;
2545eb61
SR
1165 }
1166
d6ce2a0b
SR
1167 while (<CMD>) {
1168 print LOG if ($dolog);
1169 print RD if ($dord);
1170 }
2545eb61 1171
d6ce2a0b 1172 waitpid($pid, 0);
2545eb61
SR
1173 my $failed = $?;
1174
d6ce2a0b
SR
1175 close(CMD);
1176 close(LOG) if ($dolog);
1177 close(RD) if ($dord);
1178
2545eb61
SR
1179 if ($failed) {
1180 doprint "FAILED!\n";
1181 } else {
1182 doprint "SUCCESS\n";
1183 }
1184
5f9b6ced
SR
1185 return !$failed;
1186}
1187
e48c5293
SR
1188sub run_ssh {
1189 my ($cmd) = @_;
1190 my $cp_exec = $ssh_exec;
1191
1192 $cp_exec =~ s/\$SSH_COMMAND/$cmd/g;
1193 return run_command "$cp_exec";
1194}
1195
1196sub run_scp {
1197 my ($src, $dst) = @_;
1198 my $cp_scp = $scp_to_target;
1199
1200 $cp_scp =~ s/\$SRC_FILE/$src/g;
1201 $cp_scp =~ s/\$DST_FILE/$dst/g;
1202
1203 return run_command "$cp_scp";
1204}
1205
5f9b6ced
SR
1206sub get_grub_index {
1207
a75fecec
SR
1208 if ($reboot_type ne "grub") {
1209 return;
1210 }
5a391fbf 1211 return if (defined($grub_number));
5f9b6ced
SR
1212
1213 doprint "Find grub menu ... ";
1214 $grub_number = -1;
e48c5293
SR
1215
1216 my $ssh_grub = $ssh_exec;
1217 $ssh_grub =~ s,\$SSH_COMMAND,cat /boot/grub/menu.lst,g;
1218
1219 open(IN, "$ssh_grub |")
5f9b6ced 1220 or die "unable to get menu.lst";
e48c5293 1221
eaa1fe25
SR
1222 my $found = 0;
1223
5f9b6ced 1224 while (<IN>) {
a75fecec 1225 if (/^\s*title\s+$grub_menu\s*$/) {
5f9b6ced 1226 $grub_number++;
eaa1fe25 1227 $found = 1;
5f9b6ced
SR
1228 last;
1229 } elsif (/^\s*title\s/) {
1230 $grub_number++;
1231 }
1232 }
1233 close(IN);
1234
a75fecec 1235 die "Could not find '$grub_menu' in /boot/grub/menu on $machine"
eaa1fe25 1236 if (!$found);
5f9b6ced 1237 doprint "$grub_number\n";
2545eb61
SR
1238}
1239
2545eb61
SR
1240sub wait_for_input
1241{
1242 my ($fp, $time) = @_;
1243 my $rin;
1244 my $ready;
1245 my $line;
1246 my $ch;
1247
1248 if (!defined($time)) {
1249 $time = $timeout;
1250 }
1251
1252 $rin = '';
1253 vec($rin, fileno($fp), 1) = 1;
1254 $ready = select($rin, undef, undef, $time);
1255
1256 $line = "";
1257
1258 # try to read one char at a time
1259 while (sysread $fp, $ch, 1) {
1260 $line .= $ch;
1261 last if ($ch eq "\n");
1262 }
1263
1264 if (!length($line)) {
1265 return undef;
1266 }
1267
1268 return $line;
1269}
1270
75c3fda7 1271sub reboot_to {
a75fecec 1272 if ($reboot_type eq "grub") {
c54367f9
SR
1273 run_ssh "'(echo \"savedefault --default=$grub_number --once\" | grub --batch)'";
1274 reboot;
a75fecec
SR
1275 return;
1276 }
1277
1278 run_command "$reboot_script";
2545eb61
SR
1279}
1280
a57419b3
SR
1281sub get_sha1 {
1282 my ($commit) = @_;
1283
1284 doprint "git rev-list --max-count=1 $commit ... ";
1285 my $sha1 = `git rev-list --max-count=1 $commit`;
1286 my $ret = $?;
1287
1288 logit $sha1;
1289
1290 if ($ret) {
1291 doprint "FAILED\n";
1292 dodie "Failed to get git $commit";
1293 }
1294
1295 print "SUCCESS\n";
1296
1297 chomp $sha1;
1298
1299 return $sha1;
1300}
1301
5a391fbf 1302sub monitor {
2545eb61
SR
1303 my $booted = 0;
1304 my $bug = 0;
5c42fc5b 1305 my $skip_call_trace = 0;
2b7d9b21 1306 my $loops;
2545eb61 1307
7faafbd6 1308 wait_for_monitor 5;
2545eb61
SR
1309
1310 my $line;
1311 my $full_line = "";
1312
7faafbd6
SR
1313 open(DMESG, "> $dmesg") or
1314 die "unable to write to $dmesg";
2545eb61 1315
75c3fda7 1316 reboot_to;
2545eb61 1317
1c8a617a
SR
1318 my $success_start;
1319 my $failure_start;
2d01b26a
SR
1320 my $monitor_start = time;
1321 my $done = 0;
f1a5b962 1322 my $version_found = 0;
1c8a617a 1323
2d01b26a 1324 while (!$done) {
2545eb61 1325
ecaf8e52
SR
1326 if ($bug && defined($stop_after_failure) &&
1327 $stop_after_failure >= 0) {
1328 my $time = $stop_after_failure - (time - $failure_start);
1329 $line = wait_for_input($monitor_fp, $time);
1330 if (!defined($line)) {
1331 doprint "bug timed out after $booted_timeout seconds\n";
1332 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
1333 last;
1334 }
1335 } elsif ($booted) {
a75fecec 1336 $line = wait_for_input($monitor_fp, $booted_timeout);
cd4f1d53
SR
1337 if (!defined($line)) {
1338 my $s = $booted_timeout == 1 ? "" : "s";
1339 doprint "Successful boot found: break after $booted_timeout second$s\n";
1340 last;
1341 }
2b7d9b21 1342 } else {
7faafbd6 1343 $line = wait_for_input($monitor_fp);
cd4f1d53
SR
1344 if (!defined($line)) {
1345 my $s = $timeout == 1 ? "" : "s";
1346 doprint "Timed out after $timeout second$s\n";
1347 last;
1348 }
2b7d9b21 1349 }
2545eb61 1350
2545eb61 1351 doprint $line;
7faafbd6 1352 print DMESG $line;
2545eb61
SR
1353
1354 # we are not guaranteed to get a full line
1355 $full_line .= $line;
1356
a75fecec 1357 if ($full_line =~ /$success_line/) {
2545eb61 1358 $booted = 1;
1c8a617a
SR
1359 $success_start = time;
1360 }
1361
1362 if ($booted && defined($stop_after_success) &&
1363 $stop_after_success >= 0) {
1364 my $now = time;
1365 if ($now - $success_start >= $stop_after_success) {
1366 doprint "Test forced to stop after $stop_after_success seconds after success\n";
1367 last;
1368 }
2545eb61
SR
1369 }
1370
5c42fc5b
SR
1371 if ($full_line =~ /\[ backtrace testing \]/) {
1372 $skip_call_trace = 1;
1373 }
1374
2545eb61 1375 if ($full_line =~ /call trace:/i) {
4651920e 1376 if (!$bug && !$skip_call_trace) {
1c8a617a
SR
1377 $bug = 1;
1378 $failure_start = time;
1379 }
1380 }
1381
1382 if ($bug && defined($stop_after_failure) &&
1383 $stop_after_failure >= 0) {
1384 my $now = time;
1385 if ($now - $failure_start >= $stop_after_failure) {
1386 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
1387 last;
1388 }
5c42fc5b
SR
1389 }
1390
1391 if ($full_line =~ /\[ end of backtrace testing \]/) {
1392 $skip_call_trace = 0;
1393 }
1394
1395 if ($full_line =~ /Kernel panic -/) {
10abf118 1396 $failure_start = time;
2545eb61
SR
1397 $bug = 1;
1398 }
1399
f1a5b962
SR
1400 # Detect triple faults by testing the banner
1401 if ($full_line =~ /\bLinux version (\S+).*\n/) {
1402 if ($1 eq $version) {
1403 $version_found = 1;
1404 } elsif ($version_found && $detect_triplefault) {
1405 # We already booted into the kernel we are testing,
1406 # but now we booted into another kernel?
1407 # Consider this a triple fault.
1408 doprint "Aleady booted in Linux kernel $version, but now\n";
1409 doprint "we booted into Linux kernel $1.\n";
1410 doprint "Assuming that this is a triple fault.\n";
1411 doprint "To disable this: set DETECT_TRIPLE_FAULT to 0\n";
1412 last;
1413 }
1414 }
1415
2545eb61
SR
1416 if ($line =~ /\n/) {
1417 $full_line = "";
1418 }
2d01b26a
SR
1419
1420 if ($stop_test_after > 0 && !$booted && !$bug) {
1421 if (time - $monitor_start > $stop_test_after) {
4d62bf51 1422 doprint "STOP_TEST_AFTER ($stop_test_after seconds) timed out\n";
2d01b26a
SR
1423 $done = 1;
1424 }
1425 }
2545eb61
SR
1426 }
1427
7faafbd6 1428 close(DMESG);
2545eb61 1429
a75fecec 1430 if ($bug) {
2b7d9b21 1431 return 0 if ($in_bisect);
576f627c 1432 fail "failed - got a bug report" and return 0;
2545eb61
SR
1433 }
1434
a75fecec 1435 if (!$booted) {
2b7d9b21 1436 return 0 if ($in_bisect);
576f627c 1437 fail "failed - never got a boot prompt." and return 0;
2545eb61 1438 }
5f9b6ced 1439
2b7d9b21 1440 return 1;
2545eb61
SR
1441}
1442
2b29b2f8
SR
1443sub eval_kernel_version {
1444 my ($option) = @_;
1445
1446 $option =~ s/\$KERNEL_VERSION/$version/g;
1447
1448 return $option;
1449}
1450
db05cfef
SR
1451sub do_post_install {
1452
1453 return if (!defined($post_install));
1454
2b29b2f8 1455 my $cp_post_install = eval_kernel_version $post_install;
db05cfef
SR
1456 run_command "$cp_post_install" or
1457 dodie "Failed to run post install";
1458}
1459
2545eb61
SR
1460sub install {
1461
e0a8742e
SR
1462 return if ($no_install);
1463
2b29b2f8
SR
1464 my $cp_target = eval_kernel_version $target_image;
1465
1466 run_scp "$outputdir/$build_target", "$cp_target" or
5c42fc5b 1467 dodie "failed to copy image";
2545eb61 1468
5f9b6ced 1469 my $install_mods = 0;
2545eb61 1470
5f9b6ced
SR
1471 # should we process modules?
1472 $install_mods = 0;
51ad1dd1 1473 open(IN, "$output_config") or dodie("Can't read config file");
5f9b6ced
SR
1474 while (<IN>) {
1475 if (/CONFIG_MODULES(=y)?/) {
1476 $install_mods = 1 if (defined($1));
1477 last;
5c42fc5b 1478 }
5f9b6ced
SR
1479 }
1480 close(IN);
5c42fc5b 1481
5f9b6ced 1482 if (!$install_mods) {
db05cfef 1483 do_post_install;
5f9b6ced
SR
1484 doprint "No modules needed\n";
1485 return;
1486 }
2545eb61 1487
a75fecec 1488 run_command "$make INSTALL_MOD_PATH=$tmpdir modules_install" or
5f9b6ced 1489 dodie "Failed to install modules";
5c42fc5b 1490
5f9b6ced 1491 my $modlib = "/lib/modules/$version";
a57419b3 1492 my $modtar = "ktest-mods.tar.bz2";
5c42fc5b 1493
e48c5293 1494 run_ssh "rm -rf $modlib" or
5f9b6ced 1495 dodie "failed to remove old mods: $modlib";
5c42fc5b 1496
5f9b6ced 1497 # would be nice if scp -r did not follow symbolic links
a75fecec 1498 run_command "cd $tmpdir && tar -cjf $modtar lib/modules/$version" or
5f9b6ced
SR
1499 dodie "making tarball";
1500
e48c5293 1501 run_scp "$tmpdir/$modtar", "/tmp" or
5f9b6ced
SR
1502 dodie "failed to copy modules";
1503
a75fecec 1504 unlink "$tmpdir/$modtar";
5f9b6ced 1505
e7b13441 1506 run_ssh "'(cd / && tar xjf /tmp/$modtar)'" or
5f9b6ced 1507 dodie "failed to tar modules";
2545eb61 1508
e48c5293 1509 run_ssh "rm -f /tmp/$modtar";
8b37ca8c 1510
db05cfef 1511 do_post_install;
2545eb61
SR
1512}
1513
ddf607e5
SR
1514sub get_version {
1515 # get the release name
1516 doprint "$make kernelrelease ... ";
1517 $version = `$make kernelrelease | tail -1`;
1518 chomp($version);
1519 doprint "$version\n";
1520}
1521
1522sub start_monitor_and_boot {
9f7424cc
SR
1523 # Make sure the stable kernel has finished booting
1524 start_monitor;
1525 wait_for_monitor 5;
1526 end_monitor;
1527
ddf607e5
SR
1528 get_grub_index;
1529 get_version;
1530 install;
1531
1532 start_monitor;
1533 return monitor;
1534}
1535
6c5ee0be
SR
1536sub check_buildlog {
1537 my ($patch) = @_;
1538
6c5ee0be
SR
1539 my @files = `git show $patch | diffstat -l`;
1540
1541 open(IN, "git show $patch |") or
1542 dodie "failed to show $patch";
1543 while (<IN>) {
1544 if (m,^--- a/(.*),) {
1545 chomp $1;
1546 $files[$#files] = $1;
1547 }
1548 }
1549 close(IN);
1550
1551 open(IN, $buildlog) or dodie "Can't open $buildlog";
1552 while (<IN>) {
1553 if (/^\s*(.*?):.*(warning|error)/) {
1554 my $err = $1;
1555 foreach my $file (@files) {
a75fecec 1556 my $fullpath = "$builddir/$file";
6c5ee0be 1557 if ($file eq $err || $fullpath eq $err) {
2b7d9b21 1558 fail "$file built with warnings" and return 0;
6c5ee0be
SR
1559 }
1560 }
1561 }
1562 }
1563 close(IN);
2b7d9b21
SR
1564
1565 return 1;
6c5ee0be
SR
1566}
1567
fcb3f16a
SR
1568sub apply_min_config {
1569 my $outconfig = "$output_config.new";
1570
1571 # Read the config file and remove anything that
1572 # is in the force_config hash (from minconfig and others)
1573 # then add the force config back.
1574
1575 doprint "Applying minimum configurations into $output_config.new\n";
1576
1577 open (OUT, ">$outconfig") or
1578 dodie "Can't create $outconfig";
1579
1580 if (-f $output_config) {
1581 open (IN, $output_config) or
1582 dodie "Failed to open $output_config";
1583 while (<IN>) {
1584 if (/^(# )?(CONFIG_[^\s=]*)/) {
1585 next if (defined($force_config{$2}));
1586 }
1587 print OUT;
1588 }
1589 close IN;
1590 }
1591 foreach my $config (keys %force_config) {
1592 print OUT "$force_config{$config}\n";
1593 }
1594 close OUT;
1595
1596 run_command "mv $outconfig $output_config";
1597}
1598
612b9e9b 1599sub make_oldconfig {
612b9e9b 1600
4c4ab120
SR
1601 my @force_list = keys %force_config;
1602
1603 if ($#force_list >= 0) {
1604 apply_min_config;
1605 }
fcb3f16a
SR
1606
1607 if (!run_command "$make oldnoconfig") {
612b9e9b
SR
1608 # Perhaps oldnoconfig doesn't exist in this version of the kernel
1609 # try a yes '' | oldconfig
1610 doprint "oldnoconfig failed, trying yes '' | make oldconfig\n";
fcb3f16a 1611 run_command "yes '' | $make oldconfig" or
612b9e9b
SR
1612 dodie "failed make config oldconfig";
1613 }
1614}
1615
fcb3f16a
SR
1616# read a config file and use this to force new configs.
1617sub load_force_config {
1618 my ($config) = @_;
1619
1620 open(IN, $config) or
1621 dodie "failed to read $config";
1622 while (<IN>) {
1623 chomp;
1624 if (/^(CONFIG[^\s=]*)(\s*=.*)/) {
1625 $force_config{$1} = $_;
1626 } elsif (/^# (CONFIG_\S*) is not set/) {
1627 $force_config{$1} = $_;
1628 }
1629 }
1630 close IN;
1631}
1632
2545eb61
SR
1633sub build {
1634 my ($type) = @_;
5c42fc5b 1635
7faafbd6
SR
1636 unlink $buildlog;
1637
4ab1cce5
SR
1638 # Failed builds should not reboot the target
1639 my $save_no_reboot = $no_reboot;
1640 $no_reboot = 1;
1641
0bd6c1a3
SR
1642 if (defined($pre_build)) {
1643 my $ret = run_command $pre_build;
1644 if (!$ret && defined($pre_build_die) &&
1645 $pre_build_die) {
1646 dodie "failed to pre_build\n";
1647 }
1648 }
1649
75c3fda7 1650 if ($type =~ /^useconfig:(.*)/) {
51ad1dd1 1651 run_command "cp $1 $output_config" or
75c3fda7 1652 dodie "could not copy $1 to .config";
5f9b6ced 1653
75c3fda7
SR
1654 $type = "oldconfig";
1655 }
1656
5c42fc5b
SR
1657 # old config can ask questions
1658 if ($type eq "oldconfig") {
9386c6ab 1659 $type = "oldnoconfig";
75c3fda7
SR
1660
1661 # allow for empty configs
51ad1dd1 1662 run_command "touch $output_config";
75c3fda7 1663
13488231
AJ
1664 if (!$noclean) {
1665 run_command "mv $output_config $outputdir/config_temp" or
1666 dodie "moving .config";
2545eb61 1667
13488231 1668 run_command "$make mrproper" or dodie "make mrproper";
2545eb61 1669
13488231
AJ
1670 run_command "mv $outputdir/config_temp $output_config" or
1671 dodie "moving config_temp";
1672 }
5c42fc5b
SR
1673
1674 } elsif (!$noclean) {
51ad1dd1 1675 unlink "$output_config";
5f9b6ced 1676 run_command "$make mrproper" or
5c42fc5b 1677 dodie "make mrproper";
5c42fc5b 1678 }
2545eb61
SR
1679
1680 # add something to distinguish this build
a75fecec
SR
1681 open(OUT, "> $outputdir/localversion") or dodie("Can't make localversion file");
1682 print OUT "$localversion\n";
2545eb61
SR
1683 close(OUT);
1684
5f9b6ced 1685 if (defined($minconfig)) {
fcb3f16a 1686 load_force_config($minconfig);
2545eb61
SR
1687 }
1688
fcb3f16a
SR
1689 if ($type ne "oldnoconfig") {
1690 run_command "$make $type" or
612b9e9b
SR
1691 dodie "failed make config";
1692 }
fcb3f16a
SR
1693 # Run old config regardless, to enforce min configurations
1694 make_oldconfig;
2545eb61 1695
a75fecec 1696 $redirect = "$buildlog";
0bd6c1a3
SR
1697 my $build_ret = run_command "$make $build_options";
1698 undef $redirect;
1699
1700 if (defined($post_build)) {
1701 my $ret = run_command $post_build;
1702 if (!$ret && defined($post_build_die) &&
1703 $post_build_die) {
1704 dodie "failed to post_build\n";
1705 }
1706 }
1707
1708 if (!$build_ret) {
5f9b6ced 1709 # bisect may need this to pass
4ab1cce5
SR
1710 if ($in_bisect) {
1711 $no_reboot = $save_no_reboot;
1712 return 0;
1713 }
2b7d9b21 1714 fail "failed build" and return 0;
2545eb61 1715 }
5f9b6ced 1716
4ab1cce5
SR
1717 $no_reboot = $save_no_reboot;
1718
2b7d9b21 1719 return 1;
2545eb61
SR
1720}
1721
75c3fda7 1722sub halt {
e48c5293 1723 if (!run_ssh "halt" or defined($power_off)) {
576f627c
SR
1724 if (defined($poweroff_after_halt)) {
1725 sleep $poweroff_after_halt;
1726 run_command "$power_off";
1727 }
1728 } else {
75c3fda7 1729 # nope? the zap it!
a75fecec 1730 run_command "$power_off";
75c3fda7
SR
1731 }
1732}
1733
5f9b6ced
SR
1734sub success {
1735 my ($i) = @_;
1736
e48c5293
SR
1737 $successes++;
1738
9064af52
SR
1739 my $name = "";
1740
1741 if (defined($test_name)) {
1742 $name = " ($test_name)";
1743 }
1744
5f9b6ced
SR
1745 doprint "\n\n*******************************************\n";
1746 doprint "*******************************************\n";
9064af52 1747 doprint "KTEST RESULT: TEST $i$name SUCCESS!!!! **\n";
5f9b6ced
SR
1748 doprint "*******************************************\n";
1749 doprint "*******************************************\n";
1750
de5b6e3b
RV
1751 if (defined($store_successes)) {
1752 save_logs "success", $store_successes;
1753 }
1754
576f627c 1755 if ($i != $opt{"NUM_TESTS"} && !do_not_reboot) {
a75fecec 1756 doprint "Reboot and wait $sleep_time seconds\n";
2728be41 1757 reboot $sleep_time;
5f9b6ced
SR
1758 }
1759}
1760
c960bb9f
SR
1761sub answer_bisect {
1762 for (;;) {
1763 doprint "Pass or fail? [p/f]";
1764 my $ans = <STDIN>;
1765 chomp $ans;
1766 if ($ans eq "p" || $ans eq "P") {
1767 return 1;
1768 } elsif ($ans eq "f" || $ans eq "F") {
1769 return 0;
1770 } else {
1771 print "Please answer 'P' or 'F'\n";
1772 }
1773 }
1774}
1775
5a391fbf 1776sub child_run_test {
7faafbd6 1777 my $failed = 0;
5a391fbf 1778
7faafbd6 1779 # child should have no power
a75fecec
SR
1780 $reboot_on_error = 0;
1781 $poweroff_on_error = 0;
1782 $die_on_failure = 1;
7faafbd6 1783
a9dd5d63 1784 $redirect = "$testlog";
7faafbd6 1785 run_command $run_test or $failed = 1;
a9dd5d63
RV
1786 undef $redirect;
1787
5a391fbf
SR
1788 exit $failed;
1789}
1790
1791my $child_done;
1792
1793sub child_finished {
1794 $child_done = 1;
1795}
1796
1797sub do_run_test {
1798 my $child_pid;
1799 my $child_exit;
5a391fbf
SR
1800 my $line;
1801 my $full_line;
1802 my $bug = 0;
5a391fbf 1803
7faafbd6 1804 wait_for_monitor 1;
5a391fbf 1805
7faafbd6 1806 doprint "run test $run_test\n";
5a391fbf
SR
1807
1808 $child_done = 0;
1809
1810 $SIG{CHLD} = qw(child_finished);
1811
1812 $child_pid = fork;
1813
1814 child_run_test if (!$child_pid);
1815
1816 $full_line = "";
1817
1818 do {
7faafbd6 1819 $line = wait_for_input($monitor_fp, 1);
5a391fbf
SR
1820 if (defined($line)) {
1821
1822 # we are not guaranteed to get a full line
1823 $full_line .= $line;
8ea0e063 1824 doprint $line;
5a391fbf
SR
1825
1826 if ($full_line =~ /call trace:/i) {
1827 $bug = 1;
1828 }
1829
1830 if ($full_line =~ /Kernel panic -/) {
1831 $bug = 1;
1832 }
1833
1834 if ($line =~ /\n/) {
1835 $full_line = "";
1836 }
1837 }
1838 } while (!$child_done && !$bug);
1839
1840 if ($bug) {
8ea0e063
SR
1841 my $failure_start = time;
1842 my $now;
1843 do {
1844 $line = wait_for_input($monitor_fp, 1);
1845 if (defined($line)) {
1846 doprint $line;
1847 }
1848 $now = time;
1849 if ($now - $failure_start >= $stop_after_failure) {
1850 last;
1851 }
1852 } while (defined($line));
1853
5a391fbf
SR
1854 doprint "Detected kernel crash!\n";
1855 # kill the child with extreme prejudice
1856 kill 9, $child_pid;
1857 }
1858
1859 waitpid $child_pid, 0;
1860 $child_exit = $?;
1861
c5dacb88
SR
1862 if (!$bug && $in_bisect) {
1863 if (defined($bisect_ret_good)) {
1864 if ($child_exit == $bisect_ret_good) {
1865 return 1;
1866 }
1867 }
1868 if (defined($bisect_ret_skip)) {
1869 if ($child_exit == $bisect_ret_skip) {
1870 return -1;
1871 }
1872 }
1873 if (defined($bisect_ret_abort)) {
1874 if ($child_exit == $bisect_ret_abort) {
1875 fail "test abort" and return -2;
1876 }
1877 }
1878 if (defined($bisect_ret_bad)) {
1879 if ($child_exit == $bisect_ret_skip) {
1880 return 0;
1881 }
1882 }
1883 if (defined($bisect_ret_default)) {
1884 if ($bisect_ret_default eq "good") {
1885 return 1;
1886 } elsif ($bisect_ret_default eq "bad") {
1887 return 0;
1888 } elsif ($bisect_ret_default eq "skip") {
1889 return -1;
1890 } elsif ($bisect_ret_default eq "abort") {
1891 return -2;
1892 } else {
1893 fail "unknown default action: $bisect_ret_default"
1894 and return -2;
1895 }
1896 }
1897 }
1898
5a391fbf 1899 if ($bug || $child_exit) {
2b7d9b21
SR
1900 return 0 if $in_bisect;
1901 fail "test failed" and return 0;
5a391fbf 1902 }
2b7d9b21 1903 return 1;
5a391fbf
SR
1904}
1905
a75fecec
SR
1906sub run_git_bisect {
1907 my ($command) = @_;
1908
1909 doprint "$command ... ";
1910
1911 my $output = `$command 2>&1`;
1912 my $ret = $?;
1913
1914 logit $output;
1915
1916 if ($ret) {
1917 doprint "FAILED\n";
1918 dodie "Failed to git bisect";
1919 }
1920
1921 doprint "SUCCESS\n";
1922 if ($output =~ m/^(Bisecting: .*\(roughly \d+ steps?\))\s+\[([[:xdigit:]]+)\]/) {
1923 doprint "$1 [$2]\n";
1924 } elsif ($output =~ m/^([[:xdigit:]]+) is the first bad commit/) {
1925 $bisect_bad = $1;
1926 doprint "Found bad commit... $1\n";
1927 return 0;
1928 } else {
1929 # we already logged it, just print it now.
1930 print $output;
1931 }
1932
1933 return 1;
1934}
1935
c23dca7c
SR
1936sub bisect_reboot {
1937 doprint "Reboot and sleep $bisect_sleep_time seconds\n";
2728be41 1938 reboot $bisect_sleep_time;
c23dca7c
SR
1939}
1940
1941# returns 1 on success, 0 on failure, -1 on skip
0a05c769
SR
1942sub run_bisect_test {
1943 my ($type, $buildtype) = @_;
5f9b6ced 1944
2b7d9b21 1945 my $failed = 0;
5f9b6ced
SR
1946 my $result;
1947 my $output;
1948 my $ret;
1949
0a05c769
SR
1950 $in_bisect = 1;
1951
1952 build $buildtype or $failed = 1;
5f9b6ced
SR
1953
1954 if ($type ne "build") {
c23dca7c
SR
1955 if ($failed && $bisect_skip) {
1956 $in_bisect = 0;
1957 return -1;
1958 }
7faafbd6 1959 dodie "Failed on build" if $failed;
5f9b6ced
SR
1960
1961 # Now boot the box
ddf607e5 1962 start_monitor_and_boot or $failed = 1;
5f9b6ced
SR
1963
1964 if ($type ne "boot") {
c23dca7c
SR
1965 if ($failed && $bisect_skip) {
1966 end_monitor;
1967 bisect_reboot;
1968 $in_bisect = 0;
1969 return -1;
1970 }
7faafbd6 1971 dodie "Failed on boot" if $failed;
5a391fbf 1972
2b7d9b21 1973 do_run_test or $failed = 1;
5f9b6ced 1974 }
7faafbd6 1975 end_monitor;
5f9b6ced
SR
1976 }
1977
1978 if ($failed) {
0a05c769 1979 $result = 0;
5f9b6ced 1980 } else {
0a05c769
SR
1981 $result = 1;
1982 }
4025bc62
SR
1983
1984 # reboot the box to a kernel we can ssh to
1985 if ($type ne "build") {
1986 bisect_reboot;
1987 }
0a05c769
SR
1988 $in_bisect = 0;
1989
1990 return $result;
1991}
1992
1993sub run_bisect {
1994 my ($type) = @_;
1995 my $buildtype = "oldconfig";
1996
1997 # We should have a minconfig to use?
1998 if (defined($minconfig)) {
1999 $buildtype = "useconfig:$minconfig";
5f9b6ced
SR
2000 }
2001
0a05c769
SR
2002 my $ret = run_bisect_test $type, $buildtype;
2003
c960bb9f
SR
2004 if ($bisect_manual) {
2005 $ret = answer_bisect;
2006 }
0a05c769 2007
d6ce2a0b
SR
2008 # Are we looking for where it worked, not failed?
2009 if ($reverse_bisect) {
0a05c769 2010 $ret = !$ret;
d6ce2a0b
SR
2011 }
2012
c23dca7c 2013 if ($ret > 0) {
0a05c769 2014 return "good";
c23dca7c 2015 } elsif ($ret == 0) {
0a05c769 2016 return "bad";
c23dca7c
SR
2017 } elsif ($bisect_skip) {
2018 doprint "HIT A BAD COMMIT ... SKIPPING\n";
2019 return "skip";
0a05c769 2020 }
5f9b6ced
SR
2021}
2022
dad98754
SR
2023sub update_bisect_replay {
2024 my $tmp_log = "$tmpdir/ktest_bisect_log";
2025 run_command "git bisect log > $tmp_log" or
2026 die "can't create bisect log";
2027 return $tmp_log;
2028}
2029
5f9b6ced
SR
2030sub bisect {
2031 my ($i) = @_;
2032
2033 my $result;
2034
2035 die "BISECT_GOOD[$i] not defined\n" if (!defined($opt{"BISECT_GOOD[$i]"}));
2036 die "BISECT_BAD[$i] not defined\n" if (!defined($opt{"BISECT_BAD[$i]"}));
2037 die "BISECT_TYPE[$i] not defined\n" if (!defined($opt{"BISECT_TYPE[$i]"}));
2038
2039 my $good = $opt{"BISECT_GOOD[$i]"};
2040 my $bad = $opt{"BISECT_BAD[$i]"};
2041 my $type = $opt{"BISECT_TYPE[$i]"};
a75fecec
SR
2042 my $start = $opt{"BISECT_START[$i]"};
2043 my $replay = $opt{"BISECT_REPLAY[$i]"};
3410f6fd
SR
2044 my $start_files = $opt{"BISECT_FILES[$i]"};
2045
2046 if (defined($start_files)) {
2047 $start_files = " -- " . $start_files;
2048 } else {
2049 $start_files = "";
2050 }
5f9b6ced 2051
a57419b3
SR
2052 # convert to true sha1's
2053 $good = get_sha1($good);
2054 $bad = get_sha1($bad);
2055
d6ce2a0b
SR
2056 if (defined($opt{"BISECT_REVERSE[$i]"}) &&
2057 $opt{"BISECT_REVERSE[$i]"} == 1) {
2058 doprint "Performing a reverse bisect (bad is good, good is bad!)\n";
2059 $reverse_bisect = 1;
2060 } else {
2061 $reverse_bisect = 0;
2062 }
2063
a75fecec
SR
2064 # Can't have a test without having a test to run
2065 if ($type eq "test" && !defined($run_test)) {
2066 $type = "boot";
2067 }
2068
dad98754
SR
2069 # Check if a bisect was running
2070 my $bisect_start_file = "$builddir/.git/BISECT_START";
2071
a75fecec 2072 my $check = $opt{"BISECT_CHECK[$i]"};
dad98754
SR
2073 my $do_check = defined($check) && $check ne "0";
2074
2075 if ( -f $bisect_start_file ) {
2076 print "Bisect in progress found\n";
2077 if ($do_check) {
2078 print " If you say yes, then no checks of good or bad will be done\n";
2079 }
2080 if (defined($replay)) {
2081 print "** BISECT_REPLAY is defined in config file **";
2082 print " Ignore config option and perform new git bisect log?\n";
2083 if (read_ync " (yes, no, or cancel) ") {
2084 $replay = update_bisect_replay;
2085 $do_check = 0;
2086 }
2087 } elsif (read_yn "read git log and continue?") {
2088 $replay = update_bisect_replay;
2089 $do_check = 0;
2090 }
2091 }
2092
2093 if ($do_check) {
a75fecec
SR
2094
2095 # get current HEAD
a57419b3 2096 my $head = get_sha1("HEAD");
a75fecec
SR
2097
2098 if ($check ne "good") {
2099 doprint "TESTING BISECT BAD [$bad]\n";
2100 run_command "git checkout $bad" or
2101 die "Failed to checkout $bad";
2102
2103 $result = run_bisect $type;
2104
2105 if ($result ne "bad") {
2106 fail "Tested BISECT_BAD [$bad] and it succeeded" and return 0;
2107 }
2108 }
2109
2110 if ($check ne "bad") {
2111 doprint "TESTING BISECT GOOD [$good]\n";
2112 run_command "git checkout $good" or
2113 die "Failed to checkout $good";
2114
2115 $result = run_bisect $type;
2116
2117 if ($result ne "good") {
2118 fail "Tested BISECT_GOOD [$good] and it failed" and return 0;
2119 }
2120 }
2121
2122 # checkout where we started
2123 run_command "git checkout $head" or
2124 die "Failed to checkout $head";
2125 }
2126
3410f6fd 2127 run_command "git bisect start$start_files" or
a75fecec 2128 dodie "could not start bisect";
5f9b6ced
SR
2129
2130 run_command "git bisect good $good" or
a75fecec 2131 dodie "could not set bisect good to $good";
5f9b6ced 2132
a75fecec
SR
2133 run_git_bisect "git bisect bad $bad" or
2134 dodie "could not set bisect bad to $bad";
5f9b6ced 2135
a75fecec
SR
2136 if (defined($replay)) {
2137 run_command "git bisect replay $replay" or
2138 dodie "failed to run replay";
5a391fbf
SR
2139 }
2140
a75fecec
SR
2141 if (defined($start)) {
2142 run_command "git checkout $start" or
2143 dodie "failed to checkout $start";
2144 }
2145
2146 my $test;
5f9b6ced
SR
2147 do {
2148 $result = run_bisect $type;
a75fecec
SR
2149 $test = run_git_bisect "git bisect $result";
2150 } while ($test);
5f9b6ced
SR
2151
2152 run_command "git bisect log" or
2153 dodie "could not capture git bisect log";
2154
2155 run_command "git bisect reset" or
2156 dodie "could not reset git bisect";
2157
2158 doprint "Bad commit was [$bisect_bad]\n";
2159
0a05c769
SR
2160 success $i;
2161}
2162
2163my %config_ignore;
2164my %config_set;
2165
2166my %config_list;
2167my %null_config;
2168
2169my %dependency;
2170
4c4ab120
SR
2171sub assign_configs {
2172 my ($hash, $config) = @_;
0a05c769
SR
2173
2174 open (IN, $config)
2175 or dodie "Failed to read $config";
2176
2177 while (<IN>) {
9bf71749 2178 if (/^((CONFIG\S*)=.*)/) {
4c4ab120 2179 ${$hash}{$2} = $1;
0a05c769
SR
2180 }
2181 }
2182
2183 close(IN);
2184}
2185
4c4ab120
SR
2186sub process_config_ignore {
2187 my ($config) = @_;
2188
2189 assign_configs \%config_ignore, $config;
2190}
2191
0a05c769
SR
2192sub read_current_config {
2193 my ($config_ref) = @_;
2194
2195 %{$config_ref} = ();
2196 undef %{$config_ref};
2197
2198 my @key = keys %{$config_ref};
2199 if ($#key >= 0) {
2200 print "did not delete!\n";
2201 exit;
2202 }
2203 open (IN, "$output_config");
2204
2205 while (<IN>) {
2206 if (/^(CONFIG\S+)=(.*)/) {
2207 ${$config_ref}{$1} = $2;
2208 }
2209 }
2210 close(IN);
2211}
2212
2213sub get_dependencies {
2214 my ($config) = @_;
2215
2216 my $arr = $dependency{$config};
2217 if (!defined($arr)) {
2218 return ();
2219 }
2220
2221 my @deps = @{$arr};
2222
2223 foreach my $dep (@{$arr}) {
2224 print "ADD DEP $dep\n";
2225 @deps = (@deps, get_dependencies $dep);
2226 }
2227
2228 return @deps;
2229}
2230
2231sub create_config {
2232 my @configs = @_;
2233
2234 open(OUT, ">$output_config") or dodie "Can not write to $output_config";
2235
2236 foreach my $config (@configs) {
2237 print OUT "$config_set{$config}\n";
2238 my @deps = get_dependencies $config;
2239 foreach my $dep (@deps) {
2240 print OUT "$config_set{$dep}\n";
2241 }
2242 }
2243
2244 foreach my $config (keys %config_ignore) {
2245 print OUT "$config_ignore{$config}\n";
2246 }
2247 close(OUT);
2248
2249# exit;
fcb3f16a 2250 make_oldconfig;
0a05c769
SR
2251}
2252
2253sub compare_configs {
2254 my (%a, %b) = @_;
2255
2256 foreach my $item (keys %a) {
2257 if (!defined($b{$item})) {
2258 print "diff $item\n";
2259 return 1;
2260 }
2261 delete $b{$item};
2262 }
2263
2264 my @keys = keys %b;
2265 if ($#keys) {
2266 print "diff2 $keys[0]\n";
2267 }
2268 return -1 if ($#keys >= 0);
2269
2270 return 0;
2271}
2272
2273sub run_config_bisect_test {
2274 my ($type) = @_;
2275
2276 return run_bisect_test $type, "oldconfig";
2277}
2278
2279sub process_passed {
2280 my (%configs) = @_;
2281
2282 doprint "These configs had no failure: (Enabling them for further compiles)\n";
2283 # Passed! All these configs are part of a good compile.
2284 # Add them to the min options.
2285 foreach my $config (keys %configs) {
2286 if (defined($config_list{$config})) {
2287 doprint " removing $config\n";
2288 $config_ignore{$config} = $config_list{$config};
2289 delete $config_list{$config};
2290 }
2291 }
f1a27850
SR
2292 doprint "config copied to $outputdir/config_good\n";
2293 run_command "cp -f $output_config $outputdir/config_good";
0a05c769
SR
2294}
2295
2296sub process_failed {
2297 my ($config) = @_;
2298
2299 doprint "\n\n***************************************\n";
2300 doprint "Found bad config: $config\n";
2301 doprint "***************************************\n\n";
2302}
2303
2304sub run_config_bisect {
2305
2306 my @start_list = keys %config_list;
2307
2308 if ($#start_list < 0) {
2309 doprint "No more configs to test!!!\n";
2310 return -1;
2311 }
2312
2313 doprint "***** RUN TEST ***\n";
2314 my $type = $opt{"CONFIG_BISECT_TYPE[$iteration]"};
2315 my $ret;
2316 my %current_config;
2317
2318 my $count = $#start_list + 1;
2319 doprint " $count configs to test\n";
2320
2321 my $half = int($#start_list / 2);
2322
2323 do {
2324 my @tophalf = @start_list[0 .. $half];
2325
2326 create_config @tophalf;
2327 read_current_config \%current_config;
2328
2329 $count = $#tophalf + 1;
2330 doprint "Testing $count configs\n";
2331 my $found = 0;
2332 # make sure we test something
2333 foreach my $config (@tophalf) {
2334 if (defined($current_config{$config})) {
2335 logit " $config\n";
2336 $found = 1;
2337 }
2338 }
2339 if (!$found) {
2340 # try the other half
2341 doprint "Top half produced no set configs, trying bottom half\n";
4c8cc55b 2342 @tophalf = @start_list[$half + 1 .. $#start_list];
0a05c769
SR
2343 create_config @tophalf;
2344 read_current_config \%current_config;
2345 foreach my $config (@tophalf) {
2346 if (defined($current_config{$config})) {
2347 logit " $config\n";
2348 $found = 1;
2349 }
2350 }
2351 if (!$found) {
2352 doprint "Failed: Can't make new config with current configs\n";
2353 foreach my $config (@start_list) {
2354 doprint " CONFIG: $config\n";
2355 }
2356 return -1;
2357 }
2358 $count = $#tophalf + 1;
2359 doprint "Testing $count configs\n";
2360 }
2361
2362 $ret = run_config_bisect_test $type;
c960bb9f
SR
2363 if ($bisect_manual) {
2364 $ret = answer_bisect;
2365 }
0a05c769
SR
2366 if ($ret) {
2367 process_passed %current_config;
2368 return 0;
2369 }
2370
2371 doprint "This config had a failure.\n";
2372 doprint "Removing these configs that were not set in this config:\n";
f1a27850
SR
2373 doprint "config copied to $outputdir/config_bad\n";
2374 run_command "cp -f $output_config $outputdir/config_bad";
0a05c769
SR
2375
2376 # A config exists in this group that was bad.
2377 foreach my $config (keys %config_list) {
2378 if (!defined($current_config{$config})) {
2379 doprint " removing $config\n";
2380 delete $config_list{$config};
2381 }
2382 }
2383
2384 @start_list = @tophalf;
2385
2386 if ($#start_list == 0) {
2387 process_failed $start_list[0];
2388 return 1;
2389 }
2390
2391 # remove half the configs we are looking at and see if
2392 # they are good.
2393 $half = int($#start_list / 2);
4c8cc55b 2394 } while ($#start_list > 0);
0a05c769 2395
c960bb9f
SR
2396 # we found a single config, try it again unless we are running manually
2397
2398 if ($bisect_manual) {
2399 process_failed $start_list[0];
2400 return 1;
2401 }
2402
0a05c769
SR
2403 my @tophalf = @start_list[0 .. 0];
2404
2405 $ret = run_config_bisect_test $type;
2406 if ($ret) {
2407 process_passed %current_config;
2408 return 0;
2409 }
2410
2411 process_failed $start_list[0];
2412 return 1;
2413}
2414
2415sub config_bisect {
2416 my ($i) = @_;
2417
2418 my $start_config = $opt{"CONFIG_BISECT[$i]"};
2419
2420 my $tmpconfig = "$tmpdir/use_config";
2421
30f75da5
SR
2422 if (defined($config_bisect_good)) {
2423 process_config_ignore $config_bisect_good;
2424 }
2425
0a05c769
SR
2426 # Make the file with the bad config and the min config
2427 if (defined($minconfig)) {
2428 # read the min config for things to ignore
2429 run_command "cp $minconfig $tmpconfig" or
2430 dodie "failed to copy $minconfig to $tmpconfig";
2431 } else {
2432 unlink $tmpconfig;
2433 }
2434
0a05c769 2435 if (-f $tmpconfig) {
fcb3f16a 2436 load_force_config($tmpconfig);
0a05c769
SR
2437 process_config_ignore $tmpconfig;
2438 }
2439
2440 # now process the start config
2441 run_command "cp $start_config $output_config" or
2442 dodie "failed to copy $start_config to $output_config";
2443
2444 # read directly what we want to check
2445 my %config_check;
2446 open (IN, $output_config)
2447 or dodie "faied to open $output_config";
2448
2449 while (<IN>) {
2450 if (/^((CONFIG\S*)=.*)/) {
2451 $config_check{$2} = $1;
2452 }
2453 }
2454 close(IN);
2455
250bae8b 2456 # Now run oldconfig with the minconfig
fcb3f16a 2457 make_oldconfig;
0a05c769
SR
2458
2459 # check to see what we lost (or gained)
2460 open (IN, $output_config)
2461 or dodie "Failed to read $start_config";
2462
2463 my %removed_configs;
2464 my %added_configs;
2465
2466 while (<IN>) {
2467 if (/^((CONFIG\S*)=.*)/) {
2468 # save off all options
2469 $config_set{$2} = $1;
2470 if (defined($config_check{$2})) {
2471 if (defined($config_ignore{$2})) {
2472 $removed_configs{$2} = $1;
2473 } else {
2474 $config_list{$2} = $1;
2475 }
2476 } elsif (!defined($config_ignore{$2})) {
2477 $added_configs{$2} = $1;
2478 $config_list{$2} = $1;
2479 }
2480 }
2481 }
2482 close(IN);
2483
2484 my @confs = keys %removed_configs;
2485 if ($#confs >= 0) {
2486 doprint "Configs overridden by default configs and removed from check:\n";
2487 foreach my $config (@confs) {
2488 doprint " $config\n";
2489 }
2490 }
2491 @confs = keys %added_configs;
2492 if ($#confs >= 0) {
2493 doprint "Configs appearing in make oldconfig and added:\n";
2494 foreach my $config (@confs) {
2495 doprint " $config\n";
2496 }
2497 }
2498
2499 my %config_test;
2500 my $once = 0;
2501
2502 # Sometimes kconfig does weird things. We must make sure
2503 # that the config we autocreate has everything we need
2504 # to test, otherwise we may miss testing configs, or
2505 # may not be able to create a new config.
2506 # Here we create a config with everything set.
2507 create_config (keys %config_list);
2508 read_current_config \%config_test;
2509 foreach my $config (keys %config_list) {
2510 if (!defined($config_test{$config})) {
2511 if (!$once) {
2512 $once = 1;
2513 doprint "Configs not produced by kconfig (will not be checked):\n";
2514 }
2515 doprint " $config\n";
2516 delete $config_list{$config};
2517 }
2518 }
2519 my $ret;
2520 do {
2521 $ret = run_config_bisect;
2522 } while (!$ret);
2523
2524 return $ret if ($ret < 0);
5f9b6ced
SR
2525
2526 success $i;
2527}
2528
27d934b2
SR
2529sub patchcheck_reboot {
2530 doprint "Reboot and sleep $patchcheck_sleep_time seconds\n";
2728be41 2531 reboot $patchcheck_sleep_time;
27d934b2
SR
2532}
2533
6c5ee0be
SR
2534sub patchcheck {
2535 my ($i) = @_;
2536
2537 die "PATCHCHECK_START[$i] not defined\n"
2538 if (!defined($opt{"PATCHCHECK_START[$i]"}));
2539 die "PATCHCHECK_TYPE[$i] not defined\n"
2540 if (!defined($opt{"PATCHCHECK_TYPE[$i]"}));
2541
2542 my $start = $opt{"PATCHCHECK_START[$i]"};
2543
2544 my $end = "HEAD";
2545 if (defined($opt{"PATCHCHECK_END[$i]"})) {
2546 $end = $opt{"PATCHCHECK_END[$i]"};
2547 }
2548
a57419b3
SR
2549 # Get the true sha1's since we can use things like HEAD~3
2550 $start = get_sha1($start);
2551 $end = get_sha1($end);
2552
6c5ee0be
SR
2553 my $type = $opt{"PATCHCHECK_TYPE[$i]"};
2554
2555 # Can't have a test without having a test to run
2556 if ($type eq "test" && !defined($run_test)) {
2557 $type = "boot";
2558 }
2559
2560 open (IN, "git log --pretty=oneline $end|") or
2561 dodie "could not get git list";
2562
2563 my @list;
2564
2565 while (<IN>) {
2566 chomp;
2567 $list[$#list+1] = $_;
2568 last if (/^$start/);
2569 }
2570 close(IN);
2571
2572 if ($list[$#list] !~ /^$start/) {
2b7d9b21 2573 fail "SHA1 $start not found";
6c5ee0be
SR
2574 }
2575
2576 # go backwards in the list
2577 @list = reverse @list;
2578
2579 my $save_clean = $noclean;
1990207d
SR
2580 my %ignored_warnings;
2581
2582 if (defined($ignore_warnings)) {
2583 foreach my $sha1 (split /\s+/, $ignore_warnings) {
2584 $ignored_warnings{$sha1} = 1;
2585 }
2586 }
6c5ee0be
SR
2587
2588 $in_patchcheck = 1;
2589 foreach my $item (@list) {
2590 my $sha1 = $item;
2591 $sha1 =~ s/^([[:xdigit:]]+).*/$1/;
2592
2593 doprint "\nProcessing commit $item\n\n";
2594
2595 run_command "git checkout $sha1" or
2596 die "Failed to checkout $sha1";
2597
2598 # only clean on the first and last patch
2599 if ($item eq $list[0] ||
2600 $item eq $list[$#list]) {
2601 $noclean = $save_clean;
2602 } else {
2603 $noclean = 1;
2604 }
2605
2606 if (defined($minconfig)) {
2b7d9b21 2607 build "useconfig:$minconfig" or return 0;
6c5ee0be
SR
2608 } else {
2609 # ?? no config to use?
2b7d9b21 2610 build "oldconfig" or return 0;
6c5ee0be
SR
2611 }
2612
1990207d
SR
2613
2614 if (!defined($ignored_warnings{$sha1})) {
2615 check_buildlog $sha1 or return 0;
2616 }
6c5ee0be
SR
2617
2618 next if ($type eq "build");
2619
7faafbd6
SR
2620 my $failed = 0;
2621
ddf607e5 2622 start_monitor_and_boot or $failed = 1;
7faafbd6
SR
2623
2624 if (!$failed && $type ne "boot"){
2625 do_run_test or $failed = 1;
2626 }
2627 end_monitor;
2628 return 0 if ($failed);
2629
27d934b2
SR
2630 patchcheck_reboot;
2631
6c5ee0be
SR
2632 }
2633 $in_patchcheck = 0;
2634 success $i;
2b7d9b21
SR
2635
2636 return 1;
6c5ee0be
SR
2637}
2638
b9066f6c 2639my %depends;
ac6974c7 2640my %depcount;
b9066f6c
SR
2641my $iflevel = 0;
2642my @ifdeps;
2643
2644# prevent recursion
2645my %read_kconfigs;
2646
ac6974c7
SR
2647sub add_dep {
2648 # $config depends on $dep
2649 my ($config, $dep) = @_;
2650
2651 if (defined($depends{$config})) {
2652 $depends{$config} .= " " . $dep;
2653 } else {
2654 $depends{$config} = $dep;
2655 }
2656
2657 # record the number of configs depending on $dep
2658 if (defined $depcount{$dep}) {
2659 $depcount{$dep}++;
2660 } else {
2661 $depcount{$dep} = 1;
2662 }
2663}
2664
b9066f6c
SR
2665# taken from streamline_config.pl
2666sub read_kconfig {
2667 my ($kconfig) = @_;
2668
2669 my $state = "NONE";
2670 my $config;
2671 my @kconfigs;
2672
2673 my $cont = 0;
2674 my $line;
2675
2676
2677 if (! -f $kconfig) {
2678 doprint "file $kconfig does not exist, skipping\n";
2679 return;
2680 }
2681
2682 open(KIN, "$kconfig")
2683 or die "Can't open $kconfig";
2684 while (<KIN>) {
2685 chomp;
2686
2687 # Make sure that lines ending with \ continue
2688 if ($cont) {
2689 $_ = $line . " " . $_;
2690 }
2691
2692 if (s/\\$//) {
2693 $cont = 1;
2694 $line = $_;
2695 next;
2696 }
2697
2698 $cont = 0;
2699
2700 # collect any Kconfig sources
2701 if (/^source\s*"(.*)"/) {
2702 $kconfigs[$#kconfigs+1] = $1;
2703 }
2704
2705 # configs found
2706 if (/^\s*(menu)?config\s+(\S+)\s*$/) {
2707 $state = "NEW";
2708 $config = $2;
2709
2710 for (my $i = 0; $i < $iflevel; $i++) {
ac6974c7 2711 add_dep $config, $ifdeps[$i];
b9066f6c
SR
2712 }
2713
2714 # collect the depends for the config
2715 } elsif ($state eq "NEW" && /^\s*depends\s+on\s+(.*)$/) {
2716
ac6974c7 2717 add_dep $config, $1;
b9066f6c
SR
2718
2719 # Get the configs that select this config
ac6974c7
SR
2720 } elsif ($state eq "NEW" && /^\s*select\s+(\S+)/) {
2721
2722 # selected by depends on config
2723 add_dep $1, $config;
b9066f6c
SR
2724
2725 # Check for if statements
2726 } elsif (/^if\s+(.*\S)\s*$/) {
2727 my $deps = $1;
2728 # remove beginning and ending non text
2729 $deps =~ s/^[^a-zA-Z0-9_]*//;
2730 $deps =~ s/[^a-zA-Z0-9_]*$//;
2731
2732 my @deps = split /[^a-zA-Z0-9_]+/, $deps;
2733
2734 $ifdeps[$iflevel++] = join ':', @deps;
2735
2736 } elsif (/^endif/) {
2737
2738 $iflevel-- if ($iflevel);
2739
2740 # stop on "help"
2741 } elsif (/^\s*help\s*$/) {
2742 $state = "NONE";
2743 }
2744 }
2745 close(KIN);
2746
2747 # read in any configs that were found.
2748 foreach $kconfig (@kconfigs) {
2749 if (!defined($read_kconfigs{$kconfig})) {
2750 $read_kconfigs{$kconfig} = 1;
2751 read_kconfig("$builddir/$kconfig");
2752 }
2753 }
2754}
2755
2756sub read_depends {
2757 # find out which arch this is by the kconfig file
2758 open (IN, $output_config)
2759 or dodie "Failed to read $output_config";
2760 my $arch;
2761 while (<IN>) {
2762 if (m,Linux/(\S+)\s+\S+\s+Kernel Configuration,) {
2763 $arch = $1;
2764 last;
2765 }
2766 }
2767 close IN;
2768
2769 if (!defined($arch)) {
2770 doprint "Could not find arch from config file\n";
2771 doprint "no dependencies used\n";
2772 return;
2773 }
2774
2775 # arch is really the subarch, we need to know
2776 # what directory to look at.
2777 if ($arch eq "i386" || $arch eq "x86_64") {
2778 $arch = "x86";
2779 } elsif ($arch =~ /^tile/) {
2780 $arch = "tile";
2781 }
2782
2783 my $kconfig = "$builddir/arch/$arch/Kconfig";
2784
2785 if (! -f $kconfig && $arch =~ /\d$/) {
2786 my $orig = $arch;
2787 # some subarchs have numbers, truncate them
2788 $arch =~ s/\d*$//;
2789 $kconfig = "$builddir/arch/$arch/Kconfig";
2790 if (! -f $kconfig) {
2791 doprint "No idea what arch dir $orig is for\n";
2792 doprint "no dependencies used\n";
2793 return;
2794 }
2795 }
2796
2797 read_kconfig($kconfig);
2798}
2799
4c4ab120
SR
2800sub read_config_list {
2801 my ($config) = @_;
2802
2803 open (IN, $config)
2804 or dodie "Failed to read $config";
2805
2806 while (<IN>) {
2807 if (/^((CONFIG\S*)=.*)/) {
2808 if (!defined($config_ignore{$2})) {
2809 $config_list{$2} = $1;
2810 }
2811 }
2812 }
2813
2814 close(IN);
2815}
2816
2817sub read_output_config {
2818 my ($config) = @_;
2819
2820 assign_configs \%config_ignore, $config;
2821}
2822
2823sub make_new_config {
2824 my @configs = @_;
2825
2826 open (OUT, ">$output_config")
2827 or dodie "Failed to write $output_config";
2828
2829 foreach my $config (@configs) {
2830 print OUT "$config\n";
2831 }
2832 close OUT;
2833}
2834
ac6974c7
SR
2835sub chomp_config {
2836 my ($config) = @_;
2837
2838 $config =~ s/CONFIG_//;
2839
2840 return $config;
2841}
2842
b9066f6c
SR
2843sub get_depends {
2844 my ($dep) = @_;
2845
ac6974c7 2846 my $kconfig = chomp_config $dep;
b9066f6c
SR
2847
2848 $dep = $depends{"$kconfig"};
2849
2850 # the dep string we have saves the dependencies as they
2851 # were found, including expressions like ! && ||. We
2852 # want to split this out into just an array of configs.
2853
2854 my $valid = "A-Za-z_0-9";
2855
2856 my @configs;
2857
2858 while ($dep =~ /[$valid]/) {
2859
2860 if ($dep =~ /^[^$valid]*([$valid]+)/) {
2861 my $conf = "CONFIG_" . $1;
2862
2863 $configs[$#configs + 1] = $conf;
2864
2865 $dep =~ s/^[^$valid]*[$valid]+//;
2866 } else {
2867 die "this should never happen";
2868 }
2869 }
2870
2871 return @configs;
2872}
2873
2874my %min_configs;
2875my %keep_configs;
43d1b651 2876my %save_configs;
b9066f6c
SR
2877my %processed_configs;
2878my %nochange_config;
2879
2880sub test_this_config {
2881 my ($config) = @_;
2882
2883 my $found;
2884
2885 # if we already processed this config, skip it
2886 if (defined($processed_configs{$config})) {
2887 return undef;
2888 }
2889 $processed_configs{$config} = 1;
2890
2891 # if this config failed during this round, skip it
2892 if (defined($nochange_config{$config})) {
2893 return undef;
2894 }
2895
ac6974c7 2896 my $kconfig = chomp_config $config;
b9066f6c
SR
2897
2898 # Test dependencies first
2899 if (defined($depends{"$kconfig"})) {
2900 my @parents = get_depends $config;
2901 foreach my $parent (@parents) {
2902 # if the parent is in the min config, check it first
2903 next if (!defined($min_configs{$parent}));
2904 $found = test_this_config($parent);
2905 if (defined($found)) {
2906 return $found;
2907 }
2908 }
2909 }
2910
2911 # Remove this config from the list of configs
2912 # do a make oldnoconfig and then read the resulting
2913 # .config to make sure it is missing the config that
2914 # we had before
2915 my %configs = %min_configs;
2916 delete $configs{$config};
2917 make_new_config ((values %configs), (values %keep_configs));
2918 make_oldconfig;
2919 undef %configs;
2920 assign_configs \%configs, $output_config;
2921
2922 return $config if (!defined($configs{$config}));
2923
2924 doprint "disabling config $config did not change .config\n";
2925
2926 $nochange_config{$config} = 1;
2927
2928 return undef;
2929}
2930
4c4ab120
SR
2931sub make_min_config {
2932 my ($i) = @_;
2933
2934 if (!defined($output_minconfig)) {
2935 fail "OUTPUT_MIN_CONFIG not defined" and return;
2936 }
35ce5952
SR
2937
2938 # If output_minconfig exists, and the start_minconfig
2939 # came from min_config, than ask if we should use
2940 # that instead.
2941 if (-f $output_minconfig && !$start_minconfig_defined) {
2942 print "$output_minconfig exists\n";
2943 if (read_yn " Use it as minconfig?") {
2944 $start_minconfig = $output_minconfig;
2945 }
2946 }
2947
4c4ab120
SR
2948 if (!defined($start_minconfig)) {
2949 fail "START_MIN_CONFIG or MIN_CONFIG not defined" and return;
2950 }
2951
35ce5952
SR
2952 my $temp_config = "$tmpdir/temp_config";
2953
4c4ab120
SR
2954 # First things first. We build an allnoconfig to find
2955 # out what the defaults are that we can't touch.
2956 # Some are selections, but we really can't handle selections.
2957
2958 my $save_minconfig = $minconfig;
2959 undef $minconfig;
2960
2961 run_command "$make allnoconfig" or return 0;
2962
b9066f6c
SR
2963 read_depends;
2964
4c4ab120 2965 process_config_ignore $output_config;
b9066f6c 2966
43d1b651 2967 undef %save_configs;
b9066f6c 2968 undef %min_configs;
4c4ab120
SR
2969
2970 if (defined($ignore_config)) {
2971 # make sure the file exists
2972 `touch $ignore_config`;
43d1b651 2973 assign_configs \%save_configs, $ignore_config;
4c4ab120
SR
2974 }
2975
43d1b651
SR
2976 %keep_configs = %save_configs;
2977
4c4ab120
SR
2978 doprint "Load initial configs from $start_minconfig\n";
2979
2980 # Look at the current min configs, and save off all the
2981 # ones that were set via the allnoconfig
4c4ab120
SR
2982 assign_configs \%min_configs, $start_minconfig;
2983
2984 my @config_keys = keys %min_configs;
2985
ac6974c7
SR
2986 # All configs need a depcount
2987 foreach my $config (@config_keys) {
2988 my $kconfig = chomp_config $config;
2989 if (!defined $depcount{$kconfig}) {
2990 $depcount{$kconfig} = 0;
2991 }
2992 }
2993
4c4ab120
SR
2994 # Remove anything that was set by the make allnoconfig
2995 # we shouldn't need them as they get set for us anyway.
2996 foreach my $config (@config_keys) {
2997 # Remove anything in the ignore_config
2998 if (defined($keep_configs{$config})) {
2999 my $file = $ignore_config;
3000 $file =~ s,.*/(.*?)$,$1,;
3001 doprint "$config set by $file ... ignored\n";
3002 delete $min_configs{$config};
3003 next;
3004 }
3005 # But make sure the settings are the same. If a min config
3006 # sets a selection, we do not want to get rid of it if
3007 # it is not the same as what we have. Just move it into
3008 # the keep configs.
3009 if (defined($config_ignore{$config})) {
3010 if ($config_ignore{$config} ne $min_configs{$config}) {
3011 doprint "$config is in allnoconfig as '$config_ignore{$config}'";
3012 doprint " but it is '$min_configs{$config}' in minconfig .. keeping\n";
3013 $keep_configs{$config} = $min_configs{$config};
3014 } else {
3015 doprint "$config set by allnoconfig ... ignored\n";
3016 }
3017 delete $min_configs{$config};
3018 }
3019 }
3020
4c4ab120 3021 my $done = 0;
b9066f6c 3022 my $take_two = 0;
4c4ab120
SR
3023
3024 while (!$done) {
3025
3026 my $config;
3027 my $found;
3028
3029 # Now disable each config one by one and do a make oldconfig
3030 # till we find a config that changes our list.
3031
4c4ab120 3032 my @test_configs = keys %min_configs;
ac6974c7
SR
3033
3034 # Sort keys by who is most dependent on
3035 @test_configs = sort { $depcount{chomp_config($b)} <=> $depcount{chomp_config($a)} }
3036 @test_configs ;
3037
3038 # Put configs that did not modify the config at the end.
4c4ab120
SR
3039 my $reset = 1;
3040 for (my $i = 0; $i < $#test_configs; $i++) {
3041 if (!defined($nochange_config{$test_configs[0]})) {
3042 $reset = 0;
3043 last;
3044 }
3045 # This config didn't change the .config last time.
3046 # Place it at the end
3047 my $config = shift @test_configs;
3048 push @test_configs, $config;
3049 }
3050
3051 # if every test config has failed to modify the .config file
3052 # in the past, then reset and start over.
3053 if ($reset) {
3054 undef %nochange_config;
3055 }
3056
b9066f6c
SR
3057 undef %processed_configs;
3058
4c4ab120
SR
3059 foreach my $config (@test_configs) {
3060
b9066f6c 3061 $found = test_this_config $config;
4c4ab120 3062
b9066f6c 3063 last if (defined($found));
4c4ab120
SR
3064
3065 # oh well, try another config
4c4ab120
SR
3066 }
3067
3068 if (!defined($found)) {
b9066f6c
SR
3069 # we could have failed due to the nochange_config hash
3070 # reset and try again
3071 if (!$take_two) {
3072 undef %nochange_config;
3073 $take_two = 1;
3074 next;
3075 }
4c4ab120
SR
3076 doprint "No more configs found that we can disable\n";
3077 $done = 1;
3078 last;
3079 }
b9066f6c 3080 $take_two = 0;
4c4ab120
SR
3081
3082 $config = $found;
3083
3084 doprint "Test with $config disabled\n";
3085
3086 # set in_bisect to keep build and monitor from dieing
3087 $in_bisect = 1;
3088
3089 my $failed = 0;
3090 build "oldconfig";
3091 start_monitor_and_boot or $failed = 1;
3092 end_monitor;
3093
3094 $in_bisect = 0;
3095
3096 if ($failed) {
b9066f6c 3097 doprint "$min_configs{$config} is needed to boot the box... keeping\n";
4c4ab120
SR
3098 # this config is needed, add it to the ignore list.
3099 $keep_configs{$config} = $min_configs{$config};
43d1b651 3100 $save_configs{$config} = $min_configs{$config};
4c4ab120 3101 delete $min_configs{$config};
35ce5952
SR
3102
3103 # update new ignore configs
3104 if (defined($ignore_config)) {
3105 open (OUT, ">$temp_config")
3106 or die "Can't write to $temp_config";
43d1b651
SR
3107 foreach my $config (keys %save_configs) {
3108 print OUT "$save_configs{$config}\n";
35ce5952
SR
3109 }
3110 close OUT;
3111 run_command "mv $temp_config $ignore_config" or
3112 dodie "failed to copy update to $ignore_config";
3113 }
3114
4c4ab120
SR
3115 } else {
3116 # We booted without this config, remove it from the minconfigs.
3117 doprint "$config is not needed, disabling\n";
3118
3119 delete $min_configs{$config};
3120
3121 # Also disable anything that is not enabled in this config
3122 my %configs;
3123 assign_configs \%configs, $output_config;
3124 my @config_keys = keys %min_configs;
3125 foreach my $config (@config_keys) {
3126 if (!defined($configs{$config})) {
3127 doprint "$config is not set, disabling\n";
3128 delete $min_configs{$config};
3129 }
3130 }
3131
3132 # Save off all the current mandidory configs
35ce5952
SR
3133 open (OUT, ">$temp_config")
3134 or die "Can't write to $temp_config";
4c4ab120
SR
3135 foreach my $config (keys %keep_configs) {
3136 print OUT "$keep_configs{$config}\n";
3137 }
3138 foreach my $config (keys %min_configs) {
3139 print OUT "$min_configs{$config}\n";
3140 }
3141 close OUT;
35ce5952
SR
3142
3143 run_command "mv $temp_config $output_minconfig" or
3144 dodie "failed to copy update to $output_minconfig";
4c4ab120
SR
3145 }
3146
3147 doprint "Reboot and wait $sleep_time seconds\n";
2728be41 3148 reboot $sleep_time;
4c4ab120
SR
3149 }
3150
3151 success $i;
3152 return 1;
3153}
3154
8d1491ba
SR
3155$#ARGV < 1 or die "ktest.pl version: $VERSION\n usage: ktest.pl config-file\n";
3156
3157if ($#ARGV == 0) {
3158 $ktest_config = $ARGV[0];
3159 if (! -f $ktest_config) {
3160 print "$ktest_config does not exist.\n";
35ce5952 3161 if (!read_yn "Create it?") {
8d1491ba
SR
3162 exit 0;
3163 }
3164 }
3165} else {
3166 $ktest_config = "ktest.conf";
3167}
3168
3169if (! -f $ktest_config) {
dbd3783b 3170 $newconfig = 1;
c4261d0f 3171 get_test_case;
8d1491ba
SR
3172 open(OUT, ">$ktest_config") or die "Can not create $ktest_config";
3173 print OUT << "EOF"
3174# Generated by ktest.pl
3175#
0e7a22de
SR
3176
3177# PWD is a ktest.pl variable that will result in the process working
3178# directory that ktest.pl is executed in.
3179
3180# THIS_DIR is automatically assigned the PWD of the path that generated
3181# the config file. It is best to use this variable when assigning other
3182# directory paths within this directory. This allows you to easily
3183# move the test cases to other locations or to other machines.
3184#
3185THIS_DIR := $variable{"PWD"}
3186
8d1491ba
SR
3187# Define each test with TEST_START
3188# The config options below it will override the defaults
3189TEST_START
c4261d0f 3190TEST_TYPE = $default{"TEST_TYPE"}
8d1491ba
SR
3191
3192DEFAULTS
3193EOF
3194;
3195 close(OUT);
3196}
3197read_config $ktest_config;
3198
23715c3c
SR
3199if (defined($opt{"LOG_FILE"})) {
3200 $opt{"LOG_FILE"} = eval_option($opt{"LOG_FILE"}, -1);
3201}
3202
8d1491ba
SR
3203# Append any configs entered in manually to the config file.
3204my @new_configs = keys %entered_configs;
3205if ($#new_configs >= 0) {
3206 print "\nAppending entered in configs to $ktest_config\n";
3207 open(OUT, ">>$ktest_config") or die "Can not append to $ktest_config";
3208 foreach my $config (@new_configs) {
3209 print OUT "$config = $entered_configs{$config}\n";
0e7a22de 3210 $opt{$config} = process_variables($entered_configs{$config});
8d1491ba
SR
3211 }
3212}
2545eb61 3213
2b7d9b21
SR
3214if ($opt{"CLEAR_LOG"} && defined($opt{"LOG_FILE"})) {
3215 unlink $opt{"LOG_FILE"};
3216}
2545eb61 3217
2b7d9b21
SR
3218doprint "\n\nSTARTING AUTOMATED TESTS\n\n";
3219
a57419b3
SR
3220for (my $i = 0, my $repeat = 1; $i <= $opt{"NUM_TESTS"}; $i += $repeat) {
3221
3222 if (!$i) {
3223 doprint "DEFAULT OPTIONS:\n";
3224 } else {
3225 doprint "\nTEST $i OPTIONS";
3226 if (defined($repeat_tests{$i})) {
3227 $repeat = $repeat_tests{$i};
3228 doprint " ITERATE $repeat";
3229 }
3230 doprint "\n";
3231 }
3232
3233 foreach my $option (sort keys %opt) {
3234
3235 if ($option =~ /\[(\d+)\]$/) {
3236 next if ($i != $1);
3237 } else {
3238 next if ($i);
3239 }
3240
3241 doprint "$option = $opt{$option}\n";
3242 }
2b7d9b21 3243}
2545eb61 3244
2a62512b 3245sub __set_test_option {
5a391fbf 3246 my ($name, $i) = @_;
2545eb61 3247
5a391fbf 3248 my $option = "$name\[$i\]";
5c42fc5b 3249
5a391fbf
SR
3250 if (defined($opt{$option})) {
3251 return $opt{$option};
5f9b6ced
SR
3252 }
3253
a57419b3
SR
3254 foreach my $test (keys %repeat_tests) {
3255 if ($i >= $test &&
3256 $i < $test + $repeat_tests{$test}) {
3257 $option = "$name\[$test\]";
3258 if (defined($opt{$option})) {
3259 return $opt{$option};
3260 }
3261 }
3262 }
3263
5a391fbf
SR
3264 if (defined($opt{$name})) {
3265 return $opt{$name};
2545eb61
SR
3266 }
3267
5a391fbf
SR
3268 return undef;
3269}
3270
2a62512b
SR
3271sub set_test_option {
3272 my ($name, $i) = @_;
3273
3274 my $option = __set_test_option($name, $i);
3275 return $option if (!defined($option));
3276
23715c3c 3277 return eval_option($option, $i);
2a62512b
SR
3278}
3279
5a391fbf 3280# First we need to do is the builds
a75fecec
SR
3281for (my $i = 1; $i <= $opt{"NUM_TESTS"}; $i++) {
3282
4ab1cce5
SR
3283 # Do not reboot on failing test options
3284 $no_reboot = 1;
3285
576f627c
SR
3286 $iteration = $i;
3287
a75fecec
SR
3288 my $makecmd = set_test_option("MAKE_CMD", $i);
3289
3290 $machine = set_test_option("MACHINE", $i);
e48c5293 3291 $ssh_user = set_test_option("SSH_USER", $i);
a75fecec
SR
3292 $tmpdir = set_test_option("TMP_DIR", $i);
3293 $outputdir = set_test_option("OUTPUT_DIR", $i);
3294 $builddir = set_test_option("BUILD_DIR", $i);
3295 $test_type = set_test_option("TEST_TYPE", $i);
3296 $build_type = set_test_option("BUILD_TYPE", $i);
3297 $build_options = set_test_option("BUILD_OPTIONS", $i);
0bd6c1a3
SR
3298 $pre_build = set_test_option("PRE_BUILD", $i);
3299 $post_build = set_test_option("POST_BUILD", $i);
3300 $pre_build_die = set_test_option("PRE_BUILD_DIE", $i);
3301 $post_build_die = set_test_option("POST_BUILD_DIE", $i);
a75fecec 3302 $power_cycle = set_test_option("POWER_CYCLE", $i);
e48c5293 3303 $reboot = set_test_option("REBOOT", $i);
a75fecec
SR
3304 $noclean = set_test_option("BUILD_NOCLEAN", $i);
3305 $minconfig = set_test_option("MIN_CONFIG", $i);
4c4ab120
SR
3306 $output_minconfig = set_test_option("OUTPUT_MIN_CONFIG", $i);
3307 $start_minconfig = set_test_option("START_MIN_CONFIG", $i);
3308 $ignore_config = set_test_option("IGNORE_CONFIG", $i);
a75fecec
SR
3309 $run_test = set_test_option("TEST", $i);
3310 $addconfig = set_test_option("ADD_CONFIG", $i);
3311 $reboot_type = set_test_option("REBOOT_TYPE", $i);
3312 $grub_menu = set_test_option("GRUB_MENU", $i);
8b37ca8c 3313 $post_install = set_test_option("POST_INSTALL", $i);
e0a8742e 3314 $no_install = set_test_option("NO_INSTALL", $i);
a75fecec
SR
3315 $reboot_script = set_test_option("REBOOT_SCRIPT", $i);
3316 $reboot_on_error = set_test_option("REBOOT_ON_ERROR", $i);
3317 $poweroff_on_error = set_test_option("POWEROFF_ON_ERROR", $i);
3318 $die_on_failure = set_test_option("DIE_ON_FAILURE", $i);
3319 $power_off = set_test_option("POWER_OFF", $i);
576f627c
SR
3320 $powercycle_after_reboot = set_test_option("POWERCYCLE_AFTER_REBOOT", $i);
3321 $poweroff_after_halt = set_test_option("POWEROFF_AFTER_HALT", $i);
a75fecec
SR
3322 $sleep_time = set_test_option("SLEEP_TIME", $i);
3323 $bisect_sleep_time = set_test_option("BISECT_SLEEP_TIME", $i);
27d934b2 3324 $patchcheck_sleep_time = set_test_option("PATCHCHECK_SLEEP_TIME", $i);
1990207d 3325 $ignore_warnings = set_test_option("IGNORE_WARNINGS", $i);
c960bb9f 3326 $bisect_manual = set_test_option("BISECT_MANUAL", $i);
c23dca7c 3327 $bisect_skip = set_test_option("BISECT_SKIP", $i);
30f75da5 3328 $config_bisect_good = set_test_option("CONFIG_BISECT_GOOD", $i);
c5dacb88
SR
3329 $bisect_ret_good = set_test_option("BISECT_RET_GOOD", $i);
3330 $bisect_ret_bad = set_test_option("BISECT_RET_BAD", $i);
3331 $bisect_ret_skip = set_test_option("BISECT_RET_SKIP", $i);
3332 $bisect_ret_abort = set_test_option("BISECT_RET_ABORT", $i);
3333 $bisect_ret_default = set_test_option("BISECT_RET_DEFAULT", $i);
a75fecec 3334 $store_failures = set_test_option("STORE_FAILURES", $i);
de5b6e3b 3335 $store_successes = set_test_option("STORE_SUCCESSES", $i);
9064af52 3336 $test_name = set_test_option("TEST_NAME", $i);
a75fecec
SR
3337 $timeout = set_test_option("TIMEOUT", $i);
3338 $booted_timeout = set_test_option("BOOTED_TIMEOUT", $i);
3339 $console = set_test_option("CONSOLE", $i);
f1a5b962 3340 $detect_triplefault = set_test_option("DETECT_TRIPLE_FAULT", $i);
a75fecec 3341 $success_line = set_test_option("SUCCESS_LINE", $i);
2b803365 3342 $reboot_success_line = set_test_option("REBOOT_SUCCESS_LINE", $i);
1c8a617a
SR
3343 $stop_after_success = set_test_option("STOP_AFTER_SUCCESS", $i);
3344 $stop_after_failure = set_test_option("STOP_AFTER_FAILURE", $i);
2d01b26a 3345 $stop_test_after = set_test_option("STOP_TEST_AFTER", $i);
a75fecec 3346 $build_target = set_test_option("BUILD_TARGET", $i);
e48c5293
SR
3347 $ssh_exec = set_test_option("SSH_EXEC", $i);
3348 $scp_to_target = set_test_option("SCP_TO_TARGET", $i);
a75fecec
SR
3349 $target_image = set_test_option("TARGET_IMAGE", $i);
3350 $localversion = set_test_option("LOCALVERSION", $i);
3351
35ce5952
SR
3352 $start_minconfig_defined = 1;
3353
4c4ab120 3354 if (!defined($start_minconfig)) {
35ce5952 3355 $start_minconfig_defined = 0;
4c4ab120
SR
3356 $start_minconfig = $minconfig;
3357 }
3358
a75fecec
SR
3359 chdir $builddir || die "can't change directory to $builddir";
3360
a908a665
AJ
3361 foreach my $dir ($tmpdir, $outputdir) {
3362 if (!-d $dir) {
3363 mkpath($dir) or
3364 die "can't create $dir";
3365 }
a75fecec 3366 }
1a5cfce3 3367
e48c5293
SR
3368 $ENV{"SSH_USER"} = $ssh_user;
3369 $ENV{"MACHINE"} = $machine;
3370
a75fecec 3371 $buildlog = "$tmpdir/buildlog-$machine";
a9dd5d63 3372 $testlog = "$tmpdir/testlog-$machine";
a75fecec
SR
3373 $dmesg = "$tmpdir/dmesg-$machine";
3374 $make = "$makecmd O=$outputdir";
51ad1dd1 3375 $output_config = "$outputdir/.config";
a75fecec 3376
bb8474b1
SR
3377 if (!$buildonly) {
3378 $target = "$ssh_user\@$machine";
3379 if ($reboot_type eq "grub") {
3380 dodie "GRUB_MENU not defined" if (!defined($grub_menu));
3381 } elsif (!defined($reboot_script)) {
3382 dodie "REBOOT_SCRIPT not defined"
3383 }
a75fecec
SR
3384 }
3385
3386 my $run_type = $build_type;
3387 if ($test_type eq "patchcheck") {
3388 $run_type = $opt{"PATCHCHECK_TYPE[$i]"};
3389 } elsif ($test_type eq "bisect") {
3390 $run_type = $opt{"BISECT_TYPE[$i]"};
0a05c769
SR
3391 } elsif ($test_type eq "config_bisect") {
3392 $run_type = $opt{"CONFIG_BISECT_TYPE[$i]"};
a75fecec
SR
3393 }
3394
4c4ab120
SR
3395 if ($test_type eq "make_min_config") {
3396 $run_type = "";
3397 }
3398
a75fecec
SR
3399 # mistake in config file?
3400 if (!defined($run_type)) {
3401 $run_type = "ERROR";
3402 }
5a391fbf 3403
e0a8742e
SR
3404 my $installme = "";
3405 $installme = " no_install" if ($no_install);
3406
2545eb61 3407 doprint "\n\n";
e0a8742e 3408 doprint "RUNNING TEST $i of $opt{NUM_TESTS} with option $test_type $run_type$installme\n\n";
7faafbd6
SR
3409
3410 unlink $dmesg;
3411 unlink $buildlog;
a9dd5d63 3412 unlink $testlog;
2545eb61 3413
250bae8b
SR
3414 if (defined($addconfig)) {
3415 my $min = $minconfig;
3416 if (!defined($minconfig)) {
3417 $min = "";
3418 }
3419 run_command "cat $addconfig $min > $tmpdir/add_config" or
2b7d9b21 3420 dodie "Failed to create temp config";
9be2e6b5 3421 $minconfig = "$tmpdir/add_config";
2b7d9b21
SR
3422 }
3423
6c5ee0be
SR
3424 my $checkout = $opt{"CHECKOUT[$i]"};
3425 if (defined($checkout)) {
3426 run_command "git checkout $checkout" or
3427 die "failed to checkout $checkout";
3428 }
3429
4ab1cce5
SR
3430 $no_reboot = 0;
3431
3432
a75fecec 3433 if ($test_type eq "bisect") {
5f9b6ced
SR
3434 bisect $i;
3435 next;
0a05c769
SR
3436 } elsif ($test_type eq "config_bisect") {
3437 config_bisect $i;
3438 next;
a75fecec 3439 } elsif ($test_type eq "patchcheck") {
6c5ee0be
SR
3440 patchcheck $i;
3441 next;
4c4ab120
SR
3442 } elsif ($test_type eq "make_min_config") {
3443 make_min_config $i;
3444 next;
2545eb61 3445 }
2545eb61 3446
7faafbd6
SR
3447 if ($build_type ne "nobuild") {
3448 build $build_type or next;
2545eb61
SR
3449 }
3450
cd8e368f
SR
3451 if ($test_type eq "install") {
3452 get_version;
3453 install;
3454 success $i;
3455 next;
3456 }
3457
a75fecec 3458 if ($test_type ne "build") {
a75fecec 3459 my $failed = 0;
ddf607e5 3460 start_monitor_and_boot or $failed = 1;
a75fecec
SR
3461
3462 if (!$failed && $test_type ne "boot" && defined($run_test)) {
3463 do_run_test or $failed = 1;
3464 }
3465 end_monitor;
3466 next if ($failed);
5a391fbf
SR
3467 }
3468
5f9b6ced 3469 success $i;
2545eb61
SR
3470}
3471
5c42fc5b 3472if ($opt{"POWEROFF_ON_SUCCESS"}) {
75c3fda7 3473 halt;
576f627c 3474} elsif ($opt{"REBOOT_ON_SUCCESS"} && !do_not_reboot) {
75c3fda7 3475 reboot;
5c42fc5b 3476}
75c3fda7 3477
e48c5293
SR
3478doprint "\n $successes of $opt{NUM_TESTS} tests were successful\n\n";
3479
2545eb61 3480exit 0;