GNU Linux-libre 6.8.9-gnu
[releases.git] / tools / testing / ktest / ktest.pl
1 #!/usr/bin/perl -w
2 # SPDX-License-Identifier: GPL-2.0-only
3 #
4 # Copyright 2010 - Steven Rostedt <srostedt@redhat.com>, Red Hat Inc.
5 #
6
7 use strict;
8 use IPC::Open2;
9 use Fcntl qw(F_GETFL F_SETFL O_NONBLOCK);
10 use File::Path qw(mkpath);
11 use File::Copy qw(cp);
12 use FileHandle;
13 use FindBin;
14 use IO::Handle;
15
16 my $VERSION = "0.2";
17
18 $| = 1;
19
20 my %opt;
21 my %repeat_tests;
22 my %repeats;
23 my %evals;
24
25 #default opts
26 my %default = (
27     "MAILER"                    => "sendmail",  # default mailer
28     "EMAIL_ON_ERROR"            => 1,
29     "EMAIL_WHEN_FINISHED"       => 1,
30     "EMAIL_WHEN_CANCELED"       => 0,
31     "EMAIL_WHEN_STARTED"        => 0,
32     "NUM_TESTS"                 => 1,
33     "TEST_TYPE"                 => "build",
34     "BUILD_TYPE"                => "oldconfig",
35     "MAKE_CMD"                  => "make",
36     "CLOSE_CONSOLE_SIGNAL"      => "INT",
37     "TIMEOUT"                   => 120,
38     "TMP_DIR"                   => "/tmp/ktest/\${MACHINE}",
39     "SLEEP_TIME"                => 60,          # sleep time between tests
40     "BUILD_NOCLEAN"             => 0,
41     "REBOOT_ON_ERROR"           => 0,
42     "POWEROFF_ON_ERROR"         => 0,
43     "REBOOT_ON_SUCCESS"         => 1,
44     "POWEROFF_ON_SUCCESS"       => 0,
45     "BUILD_OPTIONS"             => "",
46     "BISECT_SLEEP_TIME"         => 60,          # sleep time between bisects
47     "PATCHCHECK_SLEEP_TIME"     => 60,          # sleep time between patch checks
48     "CLEAR_LOG"                 => 0,
49     "BISECT_MANUAL"             => 0,
50     "BISECT_SKIP"               => 1,
51     "BISECT_TRIES"              => 1,
52     "MIN_CONFIG_TYPE"           => "boot",
53     "SUCCESS_LINE"              => "login:",
54     "DETECT_TRIPLE_FAULT"       => 1,
55     "NO_INSTALL"                => 0,
56     "BOOTED_TIMEOUT"            => 1,
57     "DIE_ON_FAILURE"            => 1,
58     "SSH_EXEC"                  => "ssh \$SSH_USER\@\$MACHINE \$SSH_COMMAND",
59     "SCP_TO_TARGET"             => "scp \$SRC_FILE \$SSH_USER\@\$MACHINE:\$DST_FILE",
60     "SCP_TO_TARGET_INSTALL"     => "\${SCP_TO_TARGET}",
61     "REBOOT"                    => "ssh \$SSH_USER\@\$MACHINE reboot",
62     "REBOOT_RETURN_CODE"        => 255,
63     "STOP_AFTER_SUCCESS"        => 10,
64     "STOP_AFTER_FAILURE"        => 60,
65     "STOP_TEST_AFTER"           => 600,
66     "MAX_MONITOR_WAIT"          => 1800,
67     "GRUB_REBOOT"               => "grub2-reboot",
68     "GRUB_BLS_GET"              => "grubby --info=ALL",
69     "SYSLINUX"                  => "extlinux",
70     "SYSLINUX_PATH"             => "/boot/extlinux",
71     "CONNECT_TIMEOUT"           => 25,
72
73 # required, and we will ask users if they don't have them but we keep the default
74 # value something that is common.
75     "REBOOT_TYPE"               => "grub",
76     "LOCALVERSION"              => "-test",
77     "SSH_USER"                  => "root",
78     "BUILD_TARGET"              => "arch/x86/boot/bzImage",
79     "TARGET_IMAGE"              => "/boot/vmlinuz-test",
80
81     "LOG_FILE"                  => undef,
82     "IGNORE_UNUSED"             => 0,
83 );
84
85 my $test_log_start = 0;
86
87 my $ktest_config = "ktest.conf";
88 my $version;
89 my $have_version = 0;
90 my $machine;
91 my $last_machine;
92 my $ssh_user;
93 my $tmpdir;
94 my $builddir;
95 my $outputdir;
96 my $output_config;
97 my $test_type;
98 my $build_type;
99 my $build_options;
100 my $final_post_ktest;
101 my $pre_ktest;
102 my $post_ktest;
103 my $pre_test;
104 my $pre_test_die;
105 my $post_test;
106 my $pre_build;
107 my $post_build;
108 my $pre_build_die;
109 my $post_build_die;
110 my $reboot_type;
111 my $reboot_script;
112 my $power_cycle;
113 my $reboot;
114 my $reboot_return_code;
115 my $reboot_on_error;
116 my $switch_to_good;
117 my $switch_to_test;
118 my $poweroff_on_error;
119 my $reboot_on_success;
120 my $die_on_failure;
121 my $powercycle_after_reboot;
122 my $poweroff_after_halt;
123 my $max_monitor_wait;
124 my $ssh_exec;
125 my $scp_to_target;
126 my $scp_to_target_install;
127 my $power_off;
128 my $grub_menu;
129 my $last_grub_menu;
130 my $grub_file;
131 my $grub_number;
132 my $grub_reboot;
133 my $grub_bls_get;
134 my $syslinux;
135 my $syslinux_path;
136 my $syslinux_label;
137 my $target;
138 my $make;
139 my $pre_install;
140 my $post_install;
141 my $no_install;
142 my $noclean;
143 my $minconfig;
144 my $start_minconfig;
145 my $start_minconfig_defined;
146 my $output_minconfig;
147 my $minconfig_type;
148 my $use_output_minconfig;
149 my $warnings_file;
150 my $ignore_config;
151 my $ignore_errors;
152 my $addconfig;
153 my $in_bisect = 0;
154 my $bisect_bad_commit = "";
155 my $reverse_bisect;
156 my $bisect_manual;
157 my $bisect_skip;
158 my $bisect_tries;
159 my $config_bisect_good;
160 my $bisect_ret_good;
161 my $bisect_ret_bad;
162 my $bisect_ret_skip;
163 my $bisect_ret_abort;
164 my $bisect_ret_default;
165 my $in_patchcheck = 0;
166 my $run_test;
167 my $buildlog;
168 my $testlog;
169 my $dmesg;
170 my $monitor_fp;
171 my $monitor_pid;
172 my $monitor_cnt = 0;
173 my $sleep_time;
174 my $bisect_sleep_time;
175 my $patchcheck_sleep_time;
176 my $ignore_warnings;
177 my $store_failures;
178 my $store_successes;
179 my $test_name;
180 my $timeout;
181 my $run_timeout;
182 my $connect_timeout;
183 my $config_bisect_exec;
184 my $booted_timeout;
185 my $detect_triplefault;
186 my $console;
187 my $close_console_signal;
188 my $reboot_success_line;
189 my $success_line;
190 my $stop_after_success;
191 my $stop_after_failure;
192 my $stop_test_after;
193 my $build_target;
194 my $target_image;
195 my $checkout;
196 my $localversion;
197 my $iteration = 0;
198 my $successes = 0;
199 my $stty_orig;
200 my $run_command_status = 0;
201
202 my $bisect_good;
203 my $bisect_bad;
204 my $bisect_type;
205 my $bisect_start;
206 my $bisect_replay;
207 my $bisect_files;
208 my $bisect_reverse;
209 my $bisect_check;
210
211 my $config_bisect;
212 my $config_bisect_type;
213 my $config_bisect_check;
214
215 my $patchcheck_type;
216 my $patchcheck_start;
217 my $patchcheck_cherry;
218 my $patchcheck_end;
219
220 my $build_time;
221 my $install_time;
222 my $reboot_time;
223 my $test_time;
224
225 my $pwd;
226 my $dirname = $FindBin::Bin;
227
228 my $mailto;
229 my $mailer;
230 my $mail_path;
231 my $mail_max_size;
232 my $mail_command;
233 my $email_on_error;
234 my $email_when_finished;
235 my $email_when_started;
236 my $email_when_canceled;
237
238 my $script_start_time = localtime();
239
240 # set when a test is something other that just building or install
241 # which would require more options.
242 my $buildonly = 1;
243
244 # tell build not to worry about warnings, even when WARNINGS_FILE is set
245 my $warnings_ok = 0;
246
247 # set when creating a new config
248 my $newconfig = 0;
249
250 my %entered_configs;
251 my %config_help;
252 my %variable;
253
254 # force_config is the list of configs that we force enabled (or disabled)
255 # in a .config file. The MIN_CONFIG and ADD_CONFIG configs.
256 my %force_config;
257
258 # do not force reboots on config problems
259 my $no_reboot = 1;
260
261 # reboot on success
262 my $reboot_success = 0;
263
264 my %option_map = (
265     "MAILTO"                    => \$mailto,
266     "MAILER"                    => \$mailer,
267     "MAIL_PATH"                 => \$mail_path,
268     "MAIL_MAX_SIZE"             => \$mail_max_size,
269     "MAIL_COMMAND"              => \$mail_command,
270     "EMAIL_ON_ERROR"            => \$email_on_error,
271     "EMAIL_WHEN_FINISHED"       => \$email_when_finished,
272     "EMAIL_WHEN_STARTED"        => \$email_when_started,
273     "EMAIL_WHEN_CANCELED"       => \$email_when_canceled,
274     "MACHINE"                   => \$machine,
275     "SSH_USER"                  => \$ssh_user,
276     "TMP_DIR"                   => \$tmpdir,
277     "OUTPUT_DIR"                => \$outputdir,
278     "BUILD_DIR"                 => \$builddir,
279     "TEST_TYPE"                 => \$test_type,
280     "PRE_KTEST"                 => \$pre_ktest,
281     "POST_KTEST"                => \$post_ktest,
282     "PRE_TEST"                  => \$pre_test,
283     "PRE_TEST_DIE"              => \$pre_test_die,
284     "POST_TEST"                 => \$post_test,
285     "BUILD_TYPE"                => \$build_type,
286     "BUILD_OPTIONS"             => \$build_options,
287     "PRE_BUILD"                 => \$pre_build,
288     "POST_BUILD"                => \$post_build,
289     "PRE_BUILD_DIE"             => \$pre_build_die,
290     "POST_BUILD_DIE"            => \$post_build_die,
291     "POWER_CYCLE"               => \$power_cycle,
292     "REBOOT"                    => \$reboot,
293     "REBOOT_RETURN_CODE"        => \$reboot_return_code,
294     "BUILD_NOCLEAN"             => \$noclean,
295     "MIN_CONFIG"                => \$minconfig,
296     "OUTPUT_MIN_CONFIG"         => \$output_minconfig,
297     "START_MIN_CONFIG"          => \$start_minconfig,
298     "MIN_CONFIG_TYPE"           => \$minconfig_type,
299     "USE_OUTPUT_MIN_CONFIG"     => \$use_output_minconfig,
300     "WARNINGS_FILE"             => \$warnings_file,
301     "IGNORE_CONFIG"             => \$ignore_config,
302     "TEST"                      => \$run_test,
303     "ADD_CONFIG"                => \$addconfig,
304     "REBOOT_TYPE"               => \$reboot_type,
305     "GRUB_MENU"                 => \$grub_menu,
306     "GRUB_FILE"                 => \$grub_file,
307     "GRUB_REBOOT"               => \$grub_reboot,
308     "GRUB_BLS_GET"              => \$grub_bls_get,
309     "SYSLINUX"                  => \$syslinux,
310     "SYSLINUX_PATH"             => \$syslinux_path,
311     "SYSLINUX_LABEL"            => \$syslinux_label,
312     "PRE_INSTALL"               => \$pre_install,
313     "POST_INSTALL"              => \$post_install,
314     "NO_INSTALL"                => \$no_install,
315     "REBOOT_SCRIPT"             => \$reboot_script,
316     "REBOOT_ON_ERROR"           => \$reboot_on_error,
317     "SWITCH_TO_GOOD"            => \$switch_to_good,
318     "SWITCH_TO_TEST"            => \$switch_to_test,
319     "POWEROFF_ON_ERROR"         => \$poweroff_on_error,
320     "REBOOT_ON_SUCCESS"         => \$reboot_on_success,
321     "DIE_ON_FAILURE"            => \$die_on_failure,
322     "POWER_OFF"                 => \$power_off,
323     "POWERCYCLE_AFTER_REBOOT"   => \$powercycle_after_reboot,
324     "POWEROFF_AFTER_HALT"       => \$poweroff_after_halt,
325     "MAX_MONITOR_WAIT"          => \$max_monitor_wait,
326     "SLEEP_TIME"                => \$sleep_time,
327     "BISECT_SLEEP_TIME"         => \$bisect_sleep_time,
328     "PATCHCHECK_SLEEP_TIME"     => \$patchcheck_sleep_time,
329     "IGNORE_WARNINGS"           => \$ignore_warnings,
330     "IGNORE_ERRORS"             => \$ignore_errors,
331     "BISECT_MANUAL"             => \$bisect_manual,
332     "BISECT_SKIP"               => \$bisect_skip,
333     "BISECT_TRIES"              => \$bisect_tries,
334     "CONFIG_BISECT_GOOD"        => \$config_bisect_good,
335     "BISECT_RET_GOOD"           => \$bisect_ret_good,
336     "BISECT_RET_BAD"            => \$bisect_ret_bad,
337     "BISECT_RET_SKIP"           => \$bisect_ret_skip,
338     "BISECT_RET_ABORT"          => \$bisect_ret_abort,
339     "BISECT_RET_DEFAULT"        => \$bisect_ret_default,
340     "STORE_FAILURES"            => \$store_failures,
341     "STORE_SUCCESSES"           => \$store_successes,
342     "TEST_NAME"                 => \$test_name,
343     "TIMEOUT"                   => \$timeout,
344     "RUN_TIMEOUT"               => \$run_timeout,
345     "CONNECT_TIMEOUT"           => \$connect_timeout,
346     "CONFIG_BISECT_EXEC"        => \$config_bisect_exec,
347     "BOOTED_TIMEOUT"            => \$booted_timeout,
348     "CONSOLE"                   => \$console,
349     "CLOSE_CONSOLE_SIGNAL"      => \$close_console_signal,
350     "DETECT_TRIPLE_FAULT"       => \$detect_triplefault,
351     "SUCCESS_LINE"              => \$success_line,
352     "REBOOT_SUCCESS_LINE"       => \$reboot_success_line,
353     "STOP_AFTER_SUCCESS"        => \$stop_after_success,
354     "STOP_AFTER_FAILURE"        => \$stop_after_failure,
355     "STOP_TEST_AFTER"           => \$stop_test_after,
356     "BUILD_TARGET"              => \$build_target,
357     "SSH_EXEC"                  => \$ssh_exec,
358     "SCP_TO_TARGET"             => \$scp_to_target,
359     "SCP_TO_TARGET_INSTALL"     => \$scp_to_target_install,
360     "CHECKOUT"                  => \$checkout,
361     "TARGET_IMAGE"              => \$target_image,
362     "LOCALVERSION"              => \$localversion,
363
364     "BISECT_GOOD"               => \$bisect_good,
365     "BISECT_BAD"                => \$bisect_bad,
366     "BISECT_TYPE"               => \$bisect_type,
367     "BISECT_START"              => \$bisect_start,
368     "BISECT_REPLAY"             => \$bisect_replay,
369     "BISECT_FILES"              => \$bisect_files,
370     "BISECT_REVERSE"            => \$bisect_reverse,
371     "BISECT_CHECK"              => \$bisect_check,
372
373     "CONFIG_BISECT"             => \$config_bisect,
374     "CONFIG_BISECT_TYPE"        => \$config_bisect_type,
375     "CONFIG_BISECT_CHECK"       => \$config_bisect_check,
376
377     "PATCHCHECK_TYPE"           => \$patchcheck_type,
378     "PATCHCHECK_START"          => \$patchcheck_start,
379     "PATCHCHECK_CHERRY"         => \$patchcheck_cherry,
380     "PATCHCHECK_END"            => \$patchcheck_end,
381 );
382
383 # Options may be used by other options, record them.
384 my %used_options;
385
386 # default variables that can be used
387 chomp ($variable{"PWD"} = `pwd`);
388 $pwd = $variable{"PWD"};
389
390 $config_help{"MACHINE"} = << "EOF"
391  The machine hostname that you will test.
392  For build only tests, it is still needed to differentiate log files.
393 EOF
394     ;
395 $config_help{"SSH_USER"} = << "EOF"
396  The box is expected to have ssh on normal bootup, provide the user
397   (most likely root, since you need privileged operations)
398 EOF
399     ;
400 $config_help{"BUILD_DIR"} = << "EOF"
401  The directory that contains the Linux source code (full path).
402  You can use \${PWD} that will be the path where ktest.pl is run, or use
403  \${THIS_DIR} which is assigned \${PWD} but may be changed later.
404 EOF
405     ;
406 $config_help{"OUTPUT_DIR"} = << "EOF"
407  The directory that the objects will be built (full path).
408  (can not be same as BUILD_DIR)
409  You can use \${PWD} that will be the path where ktest.pl is run, or use
410  \${THIS_DIR} which is assigned \${PWD} but may be changed later.
411 EOF
412     ;
413 $config_help{"BUILD_TARGET"} = << "EOF"
414  The location of the compiled file to copy to the target.
415  (relative to OUTPUT_DIR)
416 EOF
417     ;
418 $config_help{"BUILD_OPTIONS"} = << "EOF"
419  Options to add to \"make\" when building.
420  i.e.  -j20
421 EOF
422     ;
423 $config_help{"TARGET_IMAGE"} = << "EOF"
424  The place to put your image on the test machine.
425 EOF
426     ;
427 $config_help{"POWER_CYCLE"} = << "EOF"
428  A script or command to reboot the box.
429
430  Here is a digital loggers power switch example
431  POWER_CYCLE = wget --no-proxy -O /dev/null -q  --auth-no-challenge 'http://admin:admin\@power/outlet?5=CCL'
432
433  Here is an example to reboot a virtual box on the current host
434  with the name "Guest".
435  POWER_CYCLE = virsh destroy Guest; sleep 5; virsh start Guest
436 EOF
437     ;
438 $config_help{"CONSOLE"} = << "EOF"
439  The script or command that reads the console
440
441   If you use ttywatch server, something like the following would work.
442 CONSOLE = nc -d localhost 3001
443
444  For a virtual machine with guest name "Guest".
445 CONSOLE =  virsh console Guest
446 EOF
447     ;
448 $config_help{"LOCALVERSION"} = << "EOF"
449  Required version ending to differentiate the test
450  from other linux builds on the system.
451 EOF
452     ;
453 $config_help{"REBOOT_TYPE"} = << "EOF"
454  Way to reboot the box to the test kernel.
455  Only valid options so far are "grub", "grub2", "grub2bls", "syslinux", and "script".
456
457  If you specify grub, it will assume grub version 1
458  and will search in /boot/grub/menu.lst for the title \$GRUB_MENU
459  and select that target to reboot to the kernel. If this is not
460  your setup, then specify "script" and have a command or script
461  specified in REBOOT_SCRIPT to boot to the target.
462
463  The entry in /boot/grub/menu.lst must be entered in manually.
464  The test will not modify that file.
465
466  If you specify grub2, then you also need to specify both \$GRUB_MENU
467  and \$GRUB_FILE.
468
469  If you specify grub2bls, then you also need to specify \$GRUB_MENU.
470
471  If you specify syslinux, then you may use SYSLINUX to define the syslinux
472  command (defaults to extlinux), and SYSLINUX_PATH to specify the path to
473  the syslinux install (defaults to /boot/extlinux). But you have to specify
474  SYSLINUX_LABEL to define the label to boot to for the test kernel.
475 EOF
476     ;
477 $config_help{"GRUB_MENU"} = << "EOF"
478  The grub title name for the test kernel to boot
479  (Only mandatory if REBOOT_TYPE = grub or grub2)
480
481  Note, ktest.pl will not update the grub menu.lst, you need to
482  manually add an option for the test. ktest.pl will search
483  the grub menu.lst for this option to find what kernel to
484  reboot into.
485
486  For example, if in the /boot/grub/menu.lst the test kernel title has:
487  title Test Kernel
488  kernel vmlinuz-test
489  GRUB_MENU = Test Kernel
490
491  For grub2, a search of \$GRUB_FILE is performed for the lines
492  that begin with "menuentry". It will not detect submenus. The
493  menu must be a non-nested menu. Add the quotes used in the menu
494  to guarantee your selection, as the first menuentry with the content
495  of \$GRUB_MENU that is found will be used.
496
497  For grub2bls, \$GRUB_MENU is searched on the result of \$GRUB_BLS_GET
498  command for the lines that begin with "title".
499 EOF
500     ;
501 $config_help{"GRUB_FILE"} = << "EOF"
502  If grub2 is used, the full path for the grub.cfg file is placed
503  here. Use something like /boot/grub2/grub.cfg to search.
504 EOF
505     ;
506 $config_help{"SYSLINUX_LABEL"} = << "EOF"
507  If syslinux is used, the label that boots the target kernel must
508  be specified with SYSLINUX_LABEL.
509 EOF
510     ;
511 $config_help{"REBOOT_SCRIPT"} = << "EOF"
512  A script to reboot the target into the test kernel
513  (Only mandatory if REBOOT_TYPE = script)
514 EOF
515     ;
516
517 # used with process_expression()
518 my $d = 0;
519
520 # defined before get_test_name()
521 my $in_die = 0;
522
523 # defined before process_warning_line()
524 my $check_build_re = ".*:.*(warning|error|Error):.*";
525 my $utf8_quote = "\\x{e2}\\x{80}(\\x{98}|\\x{99})";
526
527 # defined before child_finished()
528 my $child_done;
529
530 # config_ignore holds the configs that were set (or unset) for
531 # a good config and we will ignore these configs for the rest
532 # of a config bisect. These configs stay as they were.
533 my %config_ignore;
534
535 # config_set holds what all configs were set as.
536 my %config_set;
537
538 # config_off holds the set of configs that the bad config had disabled.
539 # We need to record them and set them in the .config when running
540 # olddefconfig, because olddefconfig keeps the defaults.
541 my %config_off;
542
543 # config_off_tmp holds a set of configs to turn off for now
544 my @config_off_tmp;
545
546 # config_list is the set of configs that are being tested
547 my %config_list;
548 my %null_config;
549
550 my %dependency;
551
552 # found above run_config_bisect()
553 my $pass = 1;
554
555 # found above add_dep()
556
557 my %depends;
558 my %depcount;
559 my $iflevel = 0;
560 my @ifdeps;
561
562 # prevent recursion
563 my %read_kconfigs;
564
565 # found above test_this_config()
566 my %min_configs;
567 my %keep_configs;
568 my %save_configs;
569 my %processed_configs;
570 my %nochange_config;
571
572 #
573 # These are first defined here, main function later on
574 #
575 sub run_command;
576 sub start_monitor;
577 sub end_monitor;
578 sub wait_for_monitor;
579
580 sub _logit {
581     if (defined($opt{"LOG_FILE"})) {
582         print LOG @_;
583     }
584 }
585
586 sub logit {
587     if (defined($opt{"LOG_FILE"})) {
588         _logit @_;
589     } else {
590         print @_;
591     }
592 }
593
594 sub doprint {
595     print @_;
596     _logit @_;
597 }
598
599 sub read_prompt {
600     my ($cancel, $prompt) = @_;
601
602     my $ans;
603
604     for (;;) {
605         if ($cancel) {
606             print "$prompt [y/n/C] ";
607         } else {
608             print "$prompt [Y/n] ";
609         }
610         $ans = <STDIN>;
611         chomp $ans;
612         if ($ans =~ /^\s*$/) {
613             if ($cancel) {
614                 $ans = "c";
615             } else {
616                 $ans = "y";
617             }
618         }
619         last if ($ans =~ /^y$/i || $ans =~ /^n$/i);
620         if ($cancel) {
621             last if ($ans =~ /^c$/i);
622             print "Please answer either 'y', 'n' or 'c'.\n";
623         } else {
624             print "Please answer either 'y' or 'n'.\n";
625         }
626     }
627     if ($ans =~ /^c/i) {
628         exit;
629     }
630     if ($ans !~ /^y$/i) {
631         return 0;
632     }
633     return 1;
634 }
635
636 sub read_yn {
637     my ($prompt) = @_;
638
639     return read_prompt 0, $prompt;
640 }
641
642 sub read_ync {
643     my ($prompt) = @_;
644
645     return read_prompt 1, $prompt;
646 }
647
648 sub get_mandatory_config {
649     my ($config) = @_;
650     my $ans;
651
652     return if (defined($opt{$config}));
653
654     if (defined($config_help{$config})) {
655         print "\n";
656         print $config_help{$config};
657     }
658
659     for (;;) {
660         print "$config = ";
661         if (defined($default{$config}) && length($default{$config})) {
662             print "\[$default{$config}\] ";
663         }
664         $ans = <STDIN>;
665         $ans =~ s/^\s*(.*\S)\s*$/$1/;
666         if ($ans =~ /^\s*$/) {
667             if ($default{$config}) {
668                 $ans = $default{$config};
669             } else {
670                 print "Your answer can not be blank\n";
671                 next;
672             }
673         }
674         $entered_configs{$config} = ${ans};
675         last;
676     }
677 }
678
679 sub show_time {
680     my ($time) = @_;
681
682     my $hours = 0;
683     my $minutes = 0;
684
685     if ($time > 3600) {
686         $hours = int($time / 3600);
687         $time -= $hours * 3600;
688     }
689     if ($time > 60) {
690         $minutes = int($time / 60);
691         $time -= $minutes * 60;
692     }
693
694     if ($hours > 0) {
695         doprint "$hours hour";
696         doprint "s" if ($hours > 1);
697         doprint " ";
698     }
699
700     if ($minutes > 0) {
701         doprint "$minutes minute";
702         doprint "s" if ($minutes > 1);
703         doprint " ";
704     }
705
706     doprint "$time second";
707     doprint "s" if ($time != 1);
708 }
709
710 sub print_times {
711     doprint "\n";
712     if ($build_time) {
713         doprint "Build time:   ";
714         show_time($build_time);
715         doprint "\n";
716     }
717     if ($install_time) {
718         doprint "Install time: ";
719         show_time($install_time);
720         doprint "\n";
721     }
722     if ($reboot_time) {
723         doprint "Reboot time:  ";
724         show_time($reboot_time);
725         doprint "\n";
726     }
727     if ($test_time) {
728         doprint "Test time:    ";
729         show_time($test_time);
730         doprint "\n";
731     }
732     # reset for iterations like bisect
733     $build_time = 0;
734     $install_time = 0;
735     $reboot_time = 0;
736     $test_time = 0;
737 }
738
739 sub get_mandatory_configs {
740     get_mandatory_config("MACHINE");
741     get_mandatory_config("BUILD_DIR");
742     get_mandatory_config("OUTPUT_DIR");
743
744     if ($newconfig) {
745         get_mandatory_config("BUILD_OPTIONS");
746     }
747
748     # options required for other than just building a kernel
749     if (!$buildonly) {
750         get_mandatory_config("POWER_CYCLE");
751         get_mandatory_config("CONSOLE");
752     }
753
754     # options required for install and more
755     if ($buildonly != 1) {
756         get_mandatory_config("SSH_USER");
757         get_mandatory_config("BUILD_TARGET");
758         get_mandatory_config("TARGET_IMAGE");
759     }
760
761     get_mandatory_config("LOCALVERSION");
762
763     return if ($buildonly);
764
765     my $rtype = $opt{"REBOOT_TYPE"};
766
767     if (!defined($rtype)) {
768         if (!defined($opt{"GRUB_MENU"})) {
769             get_mandatory_config("REBOOT_TYPE");
770             $rtype = $entered_configs{"REBOOT_TYPE"};
771         } else {
772             $rtype = "grub";
773         }
774     }
775
776     if (($rtype eq "grub") or ($rtype eq "grub2bls")) {
777         get_mandatory_config("GRUB_MENU");
778     }
779
780     if ($rtype eq "grub2") {
781         get_mandatory_config("GRUB_MENU");
782         get_mandatory_config("GRUB_FILE");
783     }
784
785     if ($rtype eq "syslinux") {
786         get_mandatory_config("SYSLINUX_LABEL");
787     }
788 }
789
790 sub process_variables {
791     my ($value, $remove_undef) = @_;
792     my $retval = "";
793
794     # We want to check for '\', and it is just easier
795     # to check the previous characet of '$' and not need
796     # to worry if '$' is the first character. By adding
797     # a space to $value, we can just check [^\\]\$ and
798     # it will still work.
799     $value = " $value";
800
801     while ($value =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
802         my $begin = $1;
803         my $var = $2;
804         my $end = $3;
805         # append beginning of value to retval
806         $retval = "$retval$begin";
807         if ($var =~ s/^shell\s+//) {
808             $retval = `$var`;
809             if ($?) {
810                 doprint "WARNING: $var returned an error\n";
811             } else {
812                 chomp $retval;
813             }
814         } elsif (defined($variable{$var})) {
815             $retval = "$retval$variable{$var}";
816         } elsif (defined($remove_undef) && $remove_undef) {
817             # for if statements, any variable that is not defined,
818             # we simple convert to 0
819             $retval = "${retval}0";
820         } else {
821             # put back the origin piece.
822             $retval = "$retval\$\{$var\}";
823             # This could be an option that is used later, save
824             # it so we don't warn if this option is not one of
825             # ktests options.
826             $used_options{$var} = 1;
827         }
828         $value = $end;
829     }
830     $retval = "$retval$value";
831
832     # remove the space added in the beginning
833     $retval =~ s/ //;
834
835     return "$retval";
836 }
837
838 sub set_value {
839     my ($lvalue, $rvalue, $override, $overrides, $name) = @_;
840
841     my $prvalue = process_variables($rvalue);
842
843     if ($lvalue =~ /^(TEST|BISECT|CONFIG_BISECT)_TYPE(\[.*\])?$/ &&
844         $prvalue !~ /^(config_|)bisect$/ &&
845         $prvalue !~ /^build$/ &&
846         $prvalue !~ /^make_warnings_file$/ &&
847         $buildonly) {
848
849         # Note if a test is something other than build, then we
850         # will need other mandatory options.
851         if ($prvalue ne "install") {
852             $buildonly = 0;
853         } else {
854             # install still limits some mandatory options.
855             $buildonly = 2;
856         }
857     }
858
859     if (defined($opt{$lvalue})) {
860         if (!$override || defined(${$overrides}{$lvalue})) {
861             my $extra = "";
862             if ($override) {
863                 $extra = "In the same override section!\n";
864             }
865             die "$name: $.: Option $lvalue defined more than once!\n$extra";
866         }
867         ${$overrides}{$lvalue} = $prvalue;
868     }
869
870     $opt{$lvalue} = $prvalue;
871 }
872
873 sub set_eval {
874     my ($lvalue, $rvalue, $name) = @_;
875
876     my $prvalue = process_variables($rvalue);
877     my $arr;
878
879     if (defined($evals{$lvalue})) {
880         $arr = $evals{$lvalue};
881     } else {
882         $arr = [];
883         $evals{$lvalue} = $arr;
884     }
885
886     push @{$arr}, $rvalue;
887 }
888
889 sub set_variable {
890     my ($lvalue, $rvalue) = @_;
891
892     if ($rvalue =~ /^\s*$/) {
893         delete $variable{$lvalue};
894     } else {
895         $rvalue = process_variables($rvalue);
896         $variable{$lvalue} = $rvalue;
897     }
898 }
899
900 sub process_compare {
901     my ($lval, $cmp, $rval) = @_;
902
903     # remove whitespace
904
905     $lval =~ s/^\s*//;
906     $lval =~ s/\s*$//;
907
908     $rval =~ s/^\s*//;
909     $rval =~ s/\s*$//;
910
911     if ($cmp eq "==") {
912         return $lval eq $rval;
913     } elsif ($cmp eq "!=") {
914         return $lval ne $rval;
915     } elsif ($cmp eq "=~") {
916         return $lval =~ m/$rval/;
917     } elsif ($cmp eq "!~") {
918         return $lval !~ m/$rval/;
919     }
920
921     my $statement = "$lval $cmp $rval";
922     my $ret = eval $statement;
923
924     # $@ stores error of eval
925     if ($@) {
926         return -1;
927     }
928
929     return $ret;
930 }
931
932 sub value_defined {
933     my ($val) = @_;
934
935     return defined($variable{$2}) ||
936         defined($opt{$2});
937 }
938
939 sub process_expression {
940     my ($name, $val) = @_;
941
942     my $c = $d++;
943
944     while ($val =~ s/\(([^\(]*?)\)/\&\&\&\&VAL\&\&\&\&/) {
945         my $express = $1;
946
947         if (process_expression($name, $express)) {
948             $val =~ s/\&\&\&\&VAL\&\&\&\&/ 1 /;
949         } else {
950             $val =~ s/\&\&\&\&VAL\&\&\&\&/ 0 /;
951         }
952     }
953
954     $d--;
955     my $OR = "\\|\\|";
956     my $AND = "\\&\\&";
957
958     while ($val =~ s/^(.*?)($OR|$AND)//) {
959         my $express = $1;
960         my $op = $2;
961
962         if (process_expression($name, $express)) {
963             if ($op eq "||") {
964                 return 1;
965             }
966         } else {
967             if ($op eq "&&") {
968                 return 0;
969             }
970         }
971     }
972
973     if ($val =~ /(.*)(==|\!=|>=|<=|>|<|=~|\!~)(.*)/) {
974         my $ret = process_compare($1, $2, $3);
975         if ($ret < 0) {
976             die "$name: $.: Unable to process comparison\n";
977         }
978         return $ret;
979     }
980
981     if ($val =~ /^\s*(NOT\s*)?DEFINED\s+(\S+)\s*$/) {
982         if (defined $1) {
983             return !value_defined($2);
984         } else {
985             return value_defined($2);
986         }
987     }
988
989     if ($val =~ s/^\s*NOT\s+(.*)//) {
990         my $express = $1;
991         my $ret = process_expression($name, $express);
992         return !$ret;
993     }
994
995     if ($val =~ /^\s*0\s*$/) {
996         return 0;
997     } elsif ($val =~ /^\s*\d+\s*$/) {
998         return 1;
999     }
1000
1001     die ("$name: $.: Undefined content $val in if statement\n");
1002 }
1003
1004 sub process_if {
1005     my ($name, $value) = @_;
1006
1007     # Convert variables and replace undefined ones with 0
1008     my $val = process_variables($value, 1);
1009     my $ret = process_expression $name, $val;
1010
1011     return $ret;
1012 }
1013
1014 sub __read_config {
1015     my ($config, $current_test_num) = @_;
1016
1017     my $in;
1018     open($in, $config) || die "can't read file $config";
1019
1020     my $name = $config;
1021     $name =~ s,.*/(.*),$1,;
1022
1023     my $test_num = $$current_test_num;
1024     my $default = 1;
1025     my $repeat = 1;
1026     my $num_tests_set = 0;
1027     my $skip = 0;
1028     my $rest;
1029     my $line;
1030     my $test_case = 0;
1031     my $if = 0;
1032     my $if_set = 0;
1033     my $override = 0;
1034
1035     my %overrides;
1036
1037     while (<$in>) {
1038
1039         # ignore blank lines and comments
1040         next if (/^\s*$/ || /\s*\#/);
1041
1042         if (/^\s*(TEST_START|DEFAULTS)\b(.*)/) {
1043
1044             my $type = $1;
1045             $rest = $2;
1046             $line = $2;
1047
1048             my $old_test_num;
1049             my $old_repeat;
1050             $override = 0;
1051
1052             if ($type eq "TEST_START") {
1053                 if ($num_tests_set) {
1054                     die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
1055                 }
1056
1057                 $old_test_num = $test_num;
1058                 $old_repeat = $repeat;
1059
1060                 $test_num += $repeat;
1061                 $default = 0;
1062                 $repeat = 1;
1063             } else {
1064                 $default = 1;
1065             }
1066
1067             # If SKIP is anywhere in the line, the command will be skipped
1068             if ($rest =~ s/\s+SKIP\b//) {
1069                 $skip = 1;
1070             } else {
1071                 $test_case = 1;
1072                 $skip = 0;
1073             }
1074
1075             if ($rest =~ s/\sELSE\b//) {
1076                 if (!$if) {
1077                     die "$name: $.: ELSE found with out matching IF section\n$_";
1078                 }
1079                 $if = 0;
1080
1081                 if ($if_set) {
1082                     $skip = 1;
1083                 } else {
1084                     $skip = 0;
1085                 }
1086             }
1087
1088             if ($rest =~ s/\sIF\s+(.*)//) {
1089                 if (process_if($name, $1)) {
1090                     $if_set = 1;
1091                 } else {
1092                     $skip = 1;
1093                 }
1094                 $if = 1;
1095             } else {
1096                 $if = 0;
1097                 $if_set = 0;
1098             }
1099
1100             if (!$skip) {
1101                 if ($type eq "TEST_START") {
1102                     if ($rest =~ s/\s+ITERATE\s+(\d+)//) {
1103                         $repeat = $1;
1104                         $repeat_tests{"$test_num"} = $repeat;
1105                     }
1106                 } elsif ($rest =~ s/\sOVERRIDE\b//) {
1107                     # DEFAULT only
1108                     $override = 1;
1109                     # Clear previous overrides
1110                     %overrides = ();
1111                 }
1112             }
1113
1114             if (!$skip && $rest !~ /^\s*$/) {
1115                 die "$name: $.: Garbage found after $type\n$_";
1116             }
1117
1118             if ($skip && $type eq "TEST_START") {
1119                 $test_num = $old_test_num;
1120                 $repeat = $old_repeat;
1121             }
1122         } elsif (/^\s*ELSE\b(.*)$/) {
1123             if (!$if) {
1124                 die "$name: $.: ELSE found with out matching IF section\n$_";
1125             }
1126             $rest = $1;
1127             if ($if_set) {
1128                 $skip = 1;
1129                 $rest = "";
1130             } else {
1131                 $skip = 0;
1132
1133                 if ($rest =~ /\sIF\s+(.*)/) {
1134                     # May be a ELSE IF section.
1135                     if (process_if($name, $1)) {
1136                         $if_set = 1;
1137                     } else {
1138                         $skip = 1;
1139                     }
1140                     $rest = "";
1141                 } else {
1142                     $if = 0;
1143                 }
1144             }
1145
1146             if ($rest !~ /^\s*$/) {
1147                 die "$name: $.: Garbage found after DEFAULTS\n$_";
1148             }
1149
1150         } elsif (/^\s*INCLUDE\s+(\S+)/) {
1151
1152             next if ($skip);
1153
1154             if (!$default) {
1155                 die "$name: $.: INCLUDE can only be done in default sections\n$_";
1156             }
1157
1158             my $file = process_variables($1);
1159
1160             if ($file !~ m,^/,) {
1161                 # check the path of the config file first
1162                 if ($config =~ m,(.*)/,) {
1163                     if (-f "$1/$file") {
1164                         $file = "$1/$file";
1165                     }
1166                 }
1167             }
1168
1169             if ( ! -r $file ) {
1170                 die "$name: $.: Can't read file $file\n$_";
1171             }
1172
1173             if (__read_config($file, \$test_num)) {
1174                 $test_case = 1;
1175             }
1176
1177         } elsif (/^\s*([A-Z_\[\]\d]+)\s*=~\s*(.*?)\s*$/) {
1178
1179             next if ($skip);
1180
1181             my $lvalue = $1;
1182             my $rvalue = $2;
1183
1184             if ($default || $lvalue =~ /\[\d+\]$/) {
1185                 set_eval($lvalue, $rvalue, $name);
1186             } else {
1187                 my $val = "$lvalue\[$test_num\]";
1188                 set_eval($val, $rvalue, $name);
1189             }
1190
1191         } elsif (/^\s*([A-Z_\[\]\d]+)\s*=\s*(.*?)\s*$/) {
1192
1193             next if ($skip);
1194
1195             my $lvalue = $1;
1196             my $rvalue = $2;
1197
1198             if (!$default &&
1199                 ($lvalue eq "NUM_TESTS" ||
1200                  $lvalue eq "LOG_FILE" ||
1201                  $lvalue eq "CLEAR_LOG")) {
1202                 die "$name: $.: $lvalue must be set in DEFAULTS section\n";
1203             }
1204
1205             if ($lvalue eq "NUM_TESTS") {
1206                 if ($test_num) {
1207                     die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
1208                 }
1209                 if (!$default) {
1210                     die "$name: $.: NUM_TESTS must be set in default section\n";
1211                 }
1212                 $num_tests_set = 1;
1213             }
1214
1215             if ($default || $lvalue =~ /\[\d+\]$/) {
1216                 set_value($lvalue, $rvalue, $override, \%overrides, $name);
1217             } else {
1218                 my $val = "$lvalue\[$test_num\]";
1219                 set_value($val, $rvalue, $override, \%overrides, $name);
1220
1221                 if ($repeat > 1) {
1222                     $repeats{$val} = $repeat;
1223                 }
1224             }
1225         } elsif (/^\s*([A-Z_\[\]\d]+)\s*:=\s*(.*?)\s*$/) {
1226             next if ($skip);
1227
1228             my $lvalue = $1;
1229             my $rvalue = $2;
1230
1231             # process config variables.
1232             # Config variables are only active while reading the
1233             # config and can be defined anywhere. They also ignore
1234             # TEST_START and DEFAULTS, but are skipped if they are in
1235             # on of these sections that have SKIP defined.
1236             # The save variable can be
1237             # defined multiple times and the new one simply overrides
1238             # the previous one.
1239             set_variable($lvalue, $rvalue);
1240
1241         } else {
1242             die "$name: $.: Garbage found in config\n$_";
1243         }
1244     }
1245
1246     if ($test_num) {
1247         $test_num += $repeat - 1;
1248         $opt{"NUM_TESTS"} = $test_num;
1249     }
1250
1251     close($in);
1252
1253     $$current_test_num = $test_num;
1254
1255     return $test_case;
1256 }
1257
1258 sub get_test_case {
1259     print "What test case would you like to run?\n";
1260     print " (build, install or boot)\n";
1261     print " Other tests are available but require editing ktest.conf\n";
1262     print " (see tools/testing/ktest/sample.conf)\n";
1263     my $ans = <STDIN>;
1264     chomp $ans;
1265     $default{"TEST_TYPE"} = $ans;
1266 }
1267
1268 sub read_config {
1269     my ($config) = @_;
1270
1271     my $test_case;
1272     my $test_num = 0;
1273
1274     $test_case = __read_config $config, \$test_num;
1275
1276     # make sure we have all mandatory configs
1277     get_mandatory_configs;
1278
1279     # was a test specified?
1280     if (!$test_case) {
1281         print "No test case specified.\n";
1282         get_test_case;
1283     }
1284
1285     # set any defaults
1286
1287     foreach my $default (keys %default) {
1288         if (!defined($opt{$default})) {
1289             $opt{$default} = $default{$default};
1290         }
1291     }
1292
1293     if ($opt{"IGNORE_UNUSED"} == 1) {
1294         return;
1295     }
1296
1297     my %not_used;
1298
1299     # check if there are any stragglers (typos?)
1300     foreach my $option (keys %opt) {
1301         my $op = $option;
1302         # remove per test labels.
1303         $op =~ s/\[.*\]//;
1304         if (!exists($option_map{$op}) &&
1305             !exists($default{$op}) &&
1306             !exists($used_options{$op})) {
1307             $not_used{$op} = 1;
1308         }
1309     }
1310
1311     if (%not_used) {
1312         my $s = "s are";
1313         $s = " is" if (keys %not_used == 1);
1314         print "The following option$s not used; could be a typo:\n";
1315         foreach my $option (keys %not_used) {
1316             print "$option\n";
1317         }
1318         print "Set IGNORE_UNUSED = 1 to have ktest ignore unused variables\n";
1319         if (!read_yn "Do you want to continue?") {
1320             exit -1;
1321         }
1322     }
1323 }
1324
1325 sub __eval_option {
1326     my ($name, $option, $i) = @_;
1327
1328     # Add space to evaluate the character before $
1329     $option = " $option";
1330     my $retval = "";
1331     my $repeated = 0;
1332     my $parent = 0;
1333
1334     foreach my $test (keys %repeat_tests) {
1335         if ($i >= $test &&
1336             $i < $test + $repeat_tests{$test}) {
1337
1338             $repeated = 1;
1339             $parent = $test;
1340             last;
1341         }
1342     }
1343
1344     while ($option =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
1345         my $start = $1;
1346         my $var = $2;
1347         my $end = $3;
1348
1349         # Append beginning of line
1350         $retval = "$retval$start";
1351
1352         # If the iteration option OPT[$i] exists, then use that.
1353         # otherwise see if the default OPT (without [$i]) exists.
1354
1355         my $o = "$var\[$i\]";
1356         my $parento = "$var\[$parent\]";
1357
1358         # If a variable contains itself, use the default var
1359         if (($var eq $name) && defined($opt{$var})) {
1360             $o = $opt{$var};
1361             $retval = "$retval$o";
1362         } elsif (defined($opt{$o})) {
1363             $o = $opt{$o};
1364             $retval = "$retval$o";
1365         } elsif ($repeated && defined($opt{$parento})) {
1366             $o = $opt{$parento};
1367             $retval = "$retval$o";
1368         } elsif (defined($opt{$var})) {
1369             $o = $opt{$var};
1370             $retval = "$retval$o";
1371         } elsif ($var eq "KERNEL_VERSION" && defined($make)) {
1372             # special option KERNEL_VERSION uses kernel version
1373             get_version();
1374             $retval = "$retval$version";
1375         } else {
1376             $retval = "$retval\$\{$var\}";
1377         }
1378
1379         $option = $end;
1380     }
1381
1382     $retval = "$retval$option";
1383
1384     $retval =~ s/^ //;
1385
1386     return $retval;
1387 }
1388
1389 sub process_evals {
1390     my ($name, $option, $i) = @_;
1391
1392     my $option_name = "$name\[$i\]";
1393     my $ev;
1394
1395     my $old_option = $option;
1396
1397     if (defined($evals{$option_name})) {
1398         $ev = $evals{$option_name};
1399     } elsif (defined($evals{$name})) {
1400         $ev = $evals{$name};
1401     } else {
1402         return $option;
1403     }
1404
1405     for my $e (@{$ev}) {
1406         eval "\$option =~ $e";
1407     }
1408
1409     if ($option ne $old_option) {
1410         doprint("$name changed from '$old_option' to '$option'\n");
1411     }
1412
1413     return $option;
1414 }
1415
1416 sub eval_option {
1417     my ($name, $option, $i) = @_;
1418
1419     my $prev = "";
1420
1421     # Since an option can evaluate to another option,
1422     # keep iterating until we do not evaluate any more
1423     # options.
1424     my $r = 0;
1425     while ($prev ne $option) {
1426         # Check for recursive evaluations.
1427         # 100 deep should be more than enough.
1428         if ($r++ > 100) {
1429             die "Over 100 evaluations occurred with $option\n" .
1430                 "Check for recursive variables\n";
1431         }
1432         $prev = $option;
1433         $option = __eval_option($name, $option, $i);
1434     }
1435
1436     $option = process_evals($name, $option, $i);
1437
1438     return $option;
1439 }
1440
1441 sub reboot {
1442     my ($time) = @_;
1443     my $powercycle = 0;
1444
1445     # test if the machine can be connected to within a few seconds
1446     my $stat = run_ssh("echo check machine status", $connect_timeout);
1447     if (!$stat) {
1448         doprint("power cycle\n");
1449         $powercycle = 1;
1450     }
1451
1452     if ($powercycle) {
1453         run_command "$power_cycle";
1454
1455         start_monitor;
1456         # flush out current monitor
1457         # May contain the reboot success line
1458         wait_for_monitor 1;
1459
1460     } else {
1461         # Make sure everything has been written to disk
1462         run_ssh("sync", 10);
1463
1464         if (defined($time)) {
1465             start_monitor;
1466             # flush out current monitor
1467             # May contain the reboot success line
1468             wait_for_monitor 1;
1469         }
1470
1471         # try to reboot normally
1472         if (run_command $reboot) {
1473             if (defined($powercycle_after_reboot)) {
1474                 sleep $powercycle_after_reboot;
1475                 run_command "$power_cycle";
1476             }
1477         } else {
1478             # nope? power cycle it.
1479             run_command "$power_cycle";
1480         }
1481     }
1482
1483     if (defined($time)) {
1484
1485         # We only want to get to the new kernel, don't fail
1486         # if we stumble over a call trace.
1487         my $save_ignore_errors = $ignore_errors;
1488         $ignore_errors = 1;
1489
1490         # Look for the good kernel to boot
1491         if (wait_for_monitor($time, "Linux version")) {
1492             # reboot got stuck?
1493             doprint "Reboot did not finish. Forcing power cycle\n";
1494             run_command "$power_cycle";
1495         }
1496
1497         $ignore_errors = $save_ignore_errors;
1498
1499         # Still need to wait for the reboot to finish
1500         wait_for_monitor($time, $reboot_success_line);
1501     }
1502     if ($powercycle || $time) {
1503         end_monitor;
1504     }
1505 }
1506
1507 sub reboot_to_good {
1508     my ($time) = @_;
1509
1510     if (defined($switch_to_good)) {
1511         run_command $switch_to_good;
1512     }
1513
1514     reboot $time;
1515 }
1516
1517 sub do_not_reboot {
1518     my $i = $iteration;
1519
1520     return $test_type eq "build" || $no_reboot ||
1521         ($test_type eq "patchcheck" && $opt{"PATCHCHECK_TYPE[$i]"} eq "build") ||
1522         ($test_type eq "bisect" && $opt{"BISECT_TYPE[$i]"} eq "build") ||
1523         ($test_type eq "config_bisect" && $opt{"CONFIG_BISECT_TYPE[$i]"} eq "build");
1524 }
1525
1526 sub get_test_name() {
1527     my $name;
1528
1529     if (defined($test_name)) {
1530         $name = "$test_name:$test_type";
1531     } else {
1532         $name = $test_type;
1533     }
1534     return $name;
1535 }
1536
1537 sub dodie {
1538     # avoid recursion
1539     return if ($in_die);
1540     $in_die = 1;
1541
1542     if ($monitor_cnt) {
1543         # restore terminal settings
1544         system("stty $stty_orig");
1545     }
1546
1547     my $i = $iteration;
1548
1549     doprint "CRITICAL FAILURE... [TEST $i] ", @_, "\n";
1550
1551     if ($reboot_on_error && !do_not_reboot) {
1552         doprint "REBOOTING\n";
1553         reboot_to_good;
1554     } elsif ($poweroff_on_error && defined($power_off)) {
1555         doprint "POWERING OFF\n";
1556         `$power_off`;
1557     }
1558
1559     if (defined($opt{"LOG_FILE"})) {
1560         print " See $opt{LOG_FILE} for more info.\n";
1561     }
1562
1563     if ($email_on_error) {
1564         my $name = get_test_name;
1565         my $log_file;
1566
1567         if (defined($opt{"LOG_FILE"})) {
1568             my $whence = 2; # End of file
1569             my $log_size = tell LOG;
1570             my $size = $log_size - $test_log_start;
1571
1572             if (defined($mail_max_size)) {
1573                 if ($size > $mail_max_size) {
1574                     $size = $mail_max_size;
1575                 }
1576             }
1577             my $pos = - $size;
1578             $log_file = "$tmpdir/log";
1579             open (L, "$opt{LOG_FILE}") or die "Can't open $opt{LOG_FILE} to read)";
1580             open (O, "> $tmpdir/log") or die "Can't open $tmpdir/log\n";
1581             seek(L, $pos, $whence);
1582             while (<L>) {
1583                 print O;
1584             }
1585             close O;
1586             close L;
1587         }
1588
1589         send_email("KTEST: critical failure for test $i [$name]",
1590                 "Your test started at $script_start_time has failed with:\n@_\n", $log_file);
1591     }
1592
1593     if (defined($post_test)) {
1594         run_command $post_test;
1595     }
1596
1597     die @_, "\n";
1598 }
1599
1600 sub create_pty {
1601     my ($ptm, $pts) = @_;
1602     my $tmp;
1603     my $TIOCSPTLCK = 0x40045431;
1604     my $TIOCGPTN = 0x80045430;
1605
1606     sysopen($ptm, "/dev/ptmx", O_RDWR | O_NONBLOCK) or
1607         dodie "Can't open /dev/ptmx";
1608
1609     # unlockpt()
1610     $tmp = pack("i", 0);
1611     ioctl($ptm, $TIOCSPTLCK, $tmp) or
1612         dodie "ioctl TIOCSPTLCK for /dev/ptmx failed";
1613
1614     # ptsname()
1615     ioctl($ptm, $TIOCGPTN, $tmp) or
1616         dodie "ioctl TIOCGPTN for /dev/ptmx failed";
1617     $tmp = unpack("i", $tmp);
1618
1619     sysopen($pts, "/dev/pts/$tmp", O_RDWR | O_NONBLOCK) or
1620         dodie "Can't open /dev/pts/$tmp";
1621 }
1622
1623 sub exec_console {
1624     my ($ptm, $pts) = @_;
1625
1626     close($ptm);
1627
1628     close(\*STDIN);
1629     close(\*STDOUT);
1630     close(\*STDERR);
1631
1632     open(\*STDIN, '<&', $pts);
1633     open(\*STDOUT, '>&', $pts);
1634     open(\*STDERR, '>&', $pts);
1635
1636     close($pts);
1637
1638     exec $console or
1639         dodie "Can't open console $console";
1640 }
1641
1642 sub open_console {
1643     my ($ptm) = @_;
1644     my $pts = \*PTSFD;
1645     my $pid;
1646
1647     # save terminal settings
1648     $stty_orig = `stty -g`;
1649
1650     # place terminal in cbreak mode so that stdin can be read one character at
1651     # a time without having to wait for a newline
1652     system("stty -icanon -echo -icrnl");
1653
1654     create_pty($ptm, $pts);
1655
1656     $pid = fork;
1657
1658     if (!$pid) {
1659         # child
1660         exec_console($ptm, $pts)
1661     }
1662
1663     # parent
1664     close($pts);
1665
1666     return $pid;
1667
1668     open(PTSFD, "Stop perl from warning about single use of PTSFD");
1669 }
1670
1671 sub close_console {
1672     my ($fp, $pid) = @_;
1673
1674     doprint "kill child process $pid\n";
1675     kill $close_console_signal, $pid;
1676
1677     doprint "wait for child process $pid to exit\n";
1678     waitpid($pid, 0);
1679
1680     print "closing!\n";
1681     close($fp);
1682
1683     # restore terminal settings
1684     system("stty $stty_orig");
1685 }
1686
1687 sub start_monitor {
1688     if ($monitor_cnt++) {
1689         return;
1690     }
1691     $monitor_fp = \*MONFD;
1692     $monitor_pid = open_console $monitor_fp;
1693
1694     return;
1695
1696     open(MONFD, "Stop perl from warning about single use of MONFD");
1697 }
1698
1699 sub end_monitor {
1700     return if (!defined $console);
1701     if (--$monitor_cnt) {
1702         return;
1703     }
1704     close_console($monitor_fp, $monitor_pid);
1705 }
1706
1707 sub wait_for_monitor {
1708     my ($time, $stop) = @_;
1709     my $full_line = "";
1710     my $line;
1711     my $booted = 0;
1712     my $start_time = time;
1713     my $skip_call_trace = 0;
1714     my $bug = 0;
1715     my $bug_ignored = 0;
1716     my $now;
1717
1718     doprint "** Wait for monitor to settle down **\n";
1719
1720     # read the monitor and wait for the system to calm down
1721     while (!$booted) {
1722         $line = wait_for_input($monitor_fp, $time);
1723         last if (!defined($line));
1724         print "$line";
1725         $full_line .= $line;
1726
1727         if (defined($stop) && $full_line =~ /$stop/) {
1728             doprint "wait for monitor detected $stop\n";
1729             $booted = 1;
1730         }
1731
1732         if ($full_line =~ /\[ backtrace testing \]/) {
1733             $skip_call_trace = 1;
1734         }
1735
1736         if ($full_line =~ /call trace:/i) {
1737             if (!$bug && !$skip_call_trace) {
1738                 if ($ignore_errors) {
1739                     $bug_ignored = 1;
1740                 } else {
1741                     $bug = 1;
1742                 }
1743             }
1744         }
1745
1746         if ($full_line =~ /\[ end of backtrace testing \]/) {
1747             $skip_call_trace = 0;
1748         }
1749
1750         if ($full_line =~ /Kernel panic -/) {
1751             $bug = 1;
1752         }
1753
1754         if ($line =~ /\n/) {
1755             $full_line = "";
1756         }
1757         $now = time;
1758         if ($now - $start_time >= $max_monitor_wait) {
1759             doprint "Exiting monitor flush due to hitting MAX_MONITOR_WAIT\n";
1760             return 1;
1761         }
1762     }
1763     print "** Monitor flushed **\n";
1764
1765     # if stop is defined but wasn't hit, return error
1766     # used by reboot (which wants to see a reboot)
1767     if (defined($stop) && !$booted) {
1768         $bug = 1;
1769     }
1770     return $bug;
1771 }
1772
1773 sub save_logs {
1774     my ($result, $basedir) = @_;
1775     my @t = localtime;
1776     my $date = sprintf "%04d%02d%02d%02d%02d%02d",
1777         1900+$t[5],$t[4],$t[3],$t[2],$t[1],$t[0];
1778
1779     my $type = $build_type;
1780     if ($type =~ /useconfig/) {
1781         $type = "useconfig";
1782     }
1783
1784     my $dir = "$machine-$test_type-$type-$result-$date";
1785
1786     $dir = "$basedir/$dir";
1787
1788     if (!-d $dir) {
1789         mkpath($dir) or
1790             dodie "can't create $dir";
1791     }
1792
1793     my %files = (
1794         "config" => $output_config,
1795         "buildlog" => $buildlog,
1796         "dmesg" => $dmesg,
1797         "testlog" => $testlog,
1798     );
1799
1800     while (my ($name, $source) = each(%files)) {
1801         if (-f "$source") {
1802             cp "$source", "$dir/$name" or
1803                 dodie "failed to copy $source";
1804         }
1805     }
1806
1807     doprint "*** Saved info to $dir ***\n";
1808 }
1809
1810 sub fail {
1811
1812     if ($die_on_failure) {
1813         dodie @_;
1814     }
1815
1816     doprint "FAILED\n";
1817
1818     my $i = $iteration;
1819
1820     # no need to reboot for just building.
1821     if (!do_not_reboot) {
1822         doprint "REBOOTING\n";
1823         reboot_to_good $sleep_time;
1824     }
1825
1826     my $name = "";
1827
1828     if (defined($test_name)) {
1829         $name = " ($test_name)";
1830     }
1831
1832     print_times;
1833
1834     doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1835     doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1836     doprint "KTEST RESULT: TEST $i$name Failed: ", @_, "\n";
1837     doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1838     doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1839
1840     if (defined($store_failures)) {
1841         save_logs "fail", $store_failures;
1842     }
1843
1844     if (defined($post_test)) {
1845         run_command $post_test;
1846     }
1847
1848     return 1;
1849 }
1850
1851 sub run_command {
1852     my ($command, $redirect, $timeout) = @_;
1853     my $start_time;
1854     my $end_time;
1855     my $dolog = 0;
1856     my $dord = 0;
1857     my $dostdout = 0;
1858     my $pid;
1859     my $command_orig = $command;
1860
1861     $command =~ s/\$SSH_USER/$ssh_user/g;
1862     $command =~ s/\$MACHINE/$machine/g;
1863
1864     if (!defined($timeout)) {
1865         $timeout = $run_timeout;
1866     }
1867
1868     if (!defined($timeout)) {
1869         $timeout = -1; # tell wait_for_input to wait indefinitely
1870     }
1871
1872     doprint("$command ... ");
1873     $start_time = time;
1874
1875     $pid = open(CMD, "$command 2>&1 |") or
1876         (fail "unable to exec $command" and return 0);
1877
1878     if (defined($opt{"LOG_FILE"})) {
1879         $dolog = 1;
1880     }
1881
1882     if (defined($redirect)) {
1883         if ($redirect eq 1) {
1884             $dostdout = 1;
1885             # Have the output of the command on its own line
1886             doprint "\n";
1887         } else {
1888             open (RD, ">$redirect") or
1889                 dodie "failed to write to redirect $redirect";
1890             $dord = 1;
1891         }
1892     }
1893
1894     my $hit_timeout = 0;
1895
1896     while (1) {
1897         my $fp = \*CMD;
1898         my $line = wait_for_input($fp, $timeout);
1899         if (!defined($line)) {
1900             my $now = time;
1901             if ($timeout >= 0 && (($now - $start_time) >= $timeout)) {
1902                 doprint "Hit timeout of $timeout, killing process\n";
1903                 $hit_timeout = 1;
1904                 kill 9, $pid;
1905             }
1906             last;
1907         }
1908         print LOG $line if ($dolog);
1909         print RD $line if ($dord);
1910         print $line if ($dostdout);
1911     }
1912
1913     waitpid($pid, 0);
1914     # shift 8 for real exit status
1915     $run_command_status = $? >> 8;
1916
1917     if ($command_orig eq $default{REBOOT} &&
1918         $run_command_status == $reboot_return_code) {
1919         $run_command_status = 0;
1920     }
1921
1922     close(CMD);
1923     close(RD)  if ($dord);
1924
1925     $end_time = time;
1926     my $delta = $end_time - $start_time;
1927
1928     if ($delta == 1) {
1929         doprint "[1 second] ";
1930     } else {
1931         doprint "[$delta seconds] ";
1932     }
1933
1934     if ($hit_timeout) {
1935         $run_command_status = 1;
1936     }
1937
1938     if ($run_command_status) {
1939         doprint "FAILED!\n";
1940     } else {
1941         doprint "SUCCESS\n";
1942     }
1943
1944     return !$run_command_status;
1945 }
1946
1947 sub run_ssh {
1948     my ($cmd, $timeout) = @_;
1949     my $cp_exec = $ssh_exec;
1950
1951     $cp_exec =~ s/\$SSH_COMMAND/$cmd/g;
1952     return run_command "$cp_exec", undef , $timeout;
1953 }
1954
1955 sub run_scp {
1956     my ($src, $dst, $cp_scp) = @_;
1957
1958     $cp_scp =~ s/\$SRC_FILE/$src/g;
1959     $cp_scp =~ s/\$DST_FILE/$dst/g;
1960
1961     return run_command "$cp_scp";
1962 }
1963
1964 sub run_scp_install {
1965     my ($src, $dst) = @_;
1966
1967     my $cp_scp = $scp_to_target_install;
1968
1969     return run_scp($src, $dst, $cp_scp);
1970 }
1971
1972 sub run_scp_mod {
1973     my ($src, $dst) = @_;
1974
1975     my $cp_scp = $scp_to_target;
1976
1977     return run_scp($src, $dst, $cp_scp);
1978 }
1979
1980 sub _get_grub_index {
1981
1982     my ($command, $target, $skip, $submenu) = @_;
1983
1984     return if (defined($grub_number) && defined($last_grub_menu) &&
1985         $last_grub_menu eq $grub_menu && defined($last_machine) &&
1986         $last_machine eq $machine);
1987
1988     doprint "Find $reboot_type menu ... ";
1989     $grub_number = -1;
1990
1991     my $ssh_grub = $ssh_exec;
1992     $ssh_grub =~ s,\$SSH_COMMAND,$command,g;
1993
1994     open(IN, "$ssh_grub |") or
1995         dodie "unable to execute $command";
1996
1997     my $found = 0;
1998
1999     my $submenu_number = 0;
2000
2001     while (<IN>) {
2002         if (/$target/) {
2003             $grub_number++;
2004             $found = 1;
2005             last;
2006         } elsif (defined($submenu) && /$submenu/) {
2007                 $submenu_number++;
2008                 $grub_number = -1;
2009         } elsif (/$skip/) {
2010             $grub_number++;
2011         }
2012     }
2013     close(IN);
2014
2015     dodie "Could not find '$grub_menu' through $command on $machine"
2016         if (!$found);
2017     if ($submenu_number > 0) {
2018         $grub_number = "$submenu_number>$grub_number";
2019     }
2020     doprint "$grub_number\n";
2021     $last_grub_menu = $grub_menu;
2022     $last_machine = $machine;
2023 }
2024
2025 sub get_grub_index {
2026
2027     my $command;
2028     my $target;
2029     my $skip;
2030     my $submenu;
2031     my $grub_menu_qt;
2032
2033     if ($reboot_type !~ /^grub/) {
2034         return;
2035     }
2036
2037     $grub_menu_qt = quotemeta($grub_menu);
2038
2039     if ($reboot_type eq "grub") {
2040         $command = "cat /boot/grub/menu.lst";
2041         $target = '^\s*title\s+' . $grub_menu_qt . '\s*$';
2042         $skip = '^\s*title\s';
2043     } elsif ($reboot_type eq "grub2") {
2044         $command = "cat $grub_file";
2045         $target = '^\s*menuentry.*' . $grub_menu_qt;
2046         $skip = '^\s*menuentry';
2047         $submenu = '^\s*submenu\s';
2048     } elsif ($reboot_type eq "grub2bls") {
2049         $command = $grub_bls_get;
2050         $target = '^title=.*' . $grub_menu_qt;
2051         $skip = '^title=';
2052     } else {
2053         return;
2054     }
2055
2056     _get_grub_index($command, $target, $skip, $submenu);
2057 }
2058
2059 sub wait_for_input {
2060     my ($fp, $time) = @_;
2061     my $start_time;
2062     my $rin;
2063     my $rout;
2064     my $nr;
2065     my $buf;
2066     my $line;
2067     my $ch;
2068
2069     if (!defined($time)) {
2070         $time = $timeout;
2071     }
2072
2073     if ($time < 0) {
2074         # Negative number means wait indefinitely
2075         undef $time;
2076     }
2077
2078     $rin = '';
2079     vec($rin, fileno($fp), 1) = 1;
2080     vec($rin, fileno(\*STDIN), 1) = 1;
2081
2082     $start_time = time;
2083
2084     while (1) {
2085         $nr = select($rout=$rin, undef, undef, $time);
2086
2087         last if ($nr <= 0);
2088
2089         # copy data from stdin to the console
2090         if (vec($rout, fileno(\*STDIN), 1) == 1) {
2091             $nr = sysread(\*STDIN, $buf, 1000);
2092             syswrite($fp, $buf, $nr) if ($nr > 0);
2093         }
2094
2095         # The timeout is based on time waiting for the fp data
2096         if (vec($rout, fileno($fp), 1) != 1) {
2097             last if (defined($time) && (time - $start_time > $time));
2098             next;
2099         }
2100
2101         $line = "";
2102
2103         # try to read one char at a time
2104         while (sysread $fp, $ch, 1) {
2105             $line .= $ch;
2106             last if ($ch eq "\n");
2107         }
2108
2109         last if (!length($line));
2110
2111         return $line;
2112     }
2113     return undef;
2114 }
2115
2116 sub reboot_to {
2117     if (defined($switch_to_test)) {
2118         run_command $switch_to_test;
2119     }
2120
2121     if ($reboot_type eq "grub") {
2122         run_ssh "'(echo \"savedefault --default=$grub_number --once\" | grub --batch)'";
2123     } elsif (($reboot_type eq "grub2") or ($reboot_type eq "grub2bls")) {
2124         run_ssh "$grub_reboot \"'$grub_number'\"";
2125     } elsif ($reboot_type eq "syslinux") {
2126         run_ssh "$syslinux --once \\\"$syslinux_label\\\" $syslinux_path";
2127     } elsif (defined $reboot_script) {
2128         run_command "$reboot_script";
2129     }
2130     reboot;
2131 }
2132
2133 sub get_sha1 {
2134     my ($commit) = @_;
2135
2136     doprint "git rev-list --max-count=1 $commit ... ";
2137     my $sha1 = `git rev-list --max-count=1 $commit`;
2138     my $ret = $?;
2139
2140     logit $sha1;
2141
2142     if ($ret) {
2143         doprint "FAILED\n";
2144         dodie "Failed to get git $commit";
2145     }
2146
2147     print "SUCCESS\n";
2148
2149     chomp $sha1;
2150
2151     return $sha1;
2152 }
2153
2154 sub monitor {
2155     my $booted = 0;
2156     my $bug = 0;
2157     my $bug_ignored = 0;
2158     my $skip_call_trace = 0;
2159     my $loops;
2160
2161     my $start_time = time;
2162
2163     wait_for_monitor 5;
2164
2165     my $line;
2166     my $full_line = "";
2167
2168     open(DMESG, "> $dmesg") or
2169         dodie "unable to write to $dmesg";
2170
2171     reboot_to;
2172
2173     my $success_start;
2174     my $failure_start;
2175     my $monitor_start = time;
2176     my $done = 0;
2177     my $version_found = 0;
2178
2179     while (!$done) {
2180         if ($bug && defined($stop_after_failure) &&
2181             $stop_after_failure >= 0) {
2182             my $time = $stop_after_failure - (time - $failure_start);
2183             $line = wait_for_input($monitor_fp, $time);
2184             if (!defined($line)) {
2185                 doprint "bug timed out after $booted_timeout seconds\n";
2186                 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
2187                 last;
2188             }
2189         } elsif ($booted) {
2190             $line = wait_for_input($monitor_fp, $booted_timeout);
2191             if (!defined($line)) {
2192                 my $s = $booted_timeout == 1 ? "" : "s";
2193                 doprint "Successful boot found: break after $booted_timeout second$s\n";
2194                 last;
2195             }
2196         } else {
2197             $line = wait_for_input($monitor_fp);
2198             if (!defined($line)) {
2199                 my $s = $timeout == 1 ? "" : "s";
2200                 doprint "Timed out after $timeout second$s\n";
2201                 last;
2202             }
2203         }
2204
2205         doprint $line;
2206         print DMESG $line;
2207
2208         # we are not guaranteed to get a full line
2209         $full_line .= $line;
2210
2211         if ($full_line =~ /$success_line/) {
2212             $booted = 1;
2213             $success_start = time;
2214         }
2215
2216         if ($booted && defined($stop_after_success) &&
2217             $stop_after_success >= 0) {
2218             my $now = time;
2219             if ($now - $success_start >= $stop_after_success) {
2220                 doprint "Test forced to stop after $stop_after_success seconds after success\n";
2221                 last;
2222             }
2223         }
2224
2225         if ($full_line =~ /\[ backtrace testing \]/) {
2226             $skip_call_trace = 1;
2227         }
2228
2229         if ($full_line =~ /call trace:/i) {
2230             if (!$bug && !$skip_call_trace) {
2231                 if ($ignore_errors) {
2232                     $bug_ignored = 1;
2233                 } else {
2234                     $bug = 1;
2235                     $failure_start = time;
2236                 }
2237             }
2238         }
2239
2240         if ($bug && defined($stop_after_failure) &&
2241             $stop_after_failure >= 0) {
2242             my $now = time;
2243             if ($now - $failure_start >= $stop_after_failure) {
2244                 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
2245                 last;
2246             }
2247         }
2248
2249         if ($full_line =~ /\[ end of backtrace testing \]/) {
2250             $skip_call_trace = 0;
2251         }
2252
2253         if ($full_line =~ /Kernel panic -/) {
2254             $failure_start = time;
2255             $bug = 1;
2256         }
2257
2258         # Detect triple faults by testing the banner
2259         if ($full_line =~ /\bLinux version (\S+).*\n/) {
2260             if ($1 eq $version) {
2261                 $version_found = 1;
2262             } elsif ($version_found && $detect_triplefault) {
2263                 # We already booted into the kernel we are testing,
2264                 # but now we booted into another kernel?
2265                 # Consider this a triple fault.
2266                 doprint "Already booted in Linux kernel $version, but now\n";
2267                 doprint "we booted into Linux kernel $1.\n";
2268                 doprint "Assuming that this is a triple fault.\n";
2269                 doprint "To disable this: set DETECT_TRIPLE_FAULT to 0\n";
2270                 last;
2271             }
2272         }
2273
2274         if ($line =~ /\n/) {
2275             $full_line = "";
2276         }
2277
2278         if ($stop_test_after > 0 && !$booted && !$bug) {
2279             if (time - $monitor_start > $stop_test_after) {
2280                 doprint "STOP_TEST_AFTER ($stop_test_after seconds) timed out\n";
2281                 $done = 1;
2282             }
2283         }
2284     }
2285
2286     my $end_time = time;
2287     $reboot_time = $end_time - $start_time;
2288
2289     close(DMESG);
2290
2291     if ($bug) {
2292         return 0 if ($in_bisect);
2293         fail "failed - got a bug report" and return 0;
2294     }
2295
2296     if (!$booted) {
2297         return 0 if ($in_bisect);
2298         fail "failed - never got a boot prompt." and return 0;
2299     }
2300
2301     if ($bug_ignored) {
2302         doprint "WARNING: Call Trace detected but ignored due to IGNORE_ERRORS=1\n";
2303     }
2304
2305     return 1;
2306 }
2307
2308 sub eval_kernel_version {
2309     my ($option) = @_;
2310
2311     $option =~ s/\$KERNEL_VERSION/$version/g;
2312
2313     return $option;
2314 }
2315
2316 sub do_post_install {
2317
2318     return if (!defined($post_install));
2319
2320     my $cp_post_install = eval_kernel_version $post_install;
2321     run_command "$cp_post_install" or
2322         dodie "Failed to run post install";
2323 }
2324
2325 # Sometimes the reboot fails, and will hang. We try to ssh to the box
2326 # and if we fail, we force another reboot, that should powercycle it.
2327 sub test_booted {
2328     if (!run_ssh "echo testing connection") {
2329         reboot $sleep_time;
2330     }
2331 }
2332
2333 sub install {
2334
2335     return if ($no_install);
2336
2337     my $start_time = time;
2338
2339     if (defined($pre_install)) {
2340         my $cp_pre_install = eval_kernel_version $pre_install;
2341         run_command "$cp_pre_install" or
2342             dodie "Failed to run pre install";
2343     }
2344
2345     my $cp_target = eval_kernel_version $target_image;
2346
2347     test_booted;
2348
2349     run_scp_install "$outputdir/$build_target", "$cp_target" or
2350         dodie "failed to copy image";
2351
2352     my $install_mods = 0;
2353
2354     # should we process modules?
2355     $install_mods = 0;
2356     open(IN, "$output_config") or dodie("Can't read config file");
2357     while (<IN>) {
2358         if (/CONFIG_MODULES(=y)?/) {
2359             if (defined($1)) {
2360                 $install_mods = 1;
2361                 last;
2362             }
2363         }
2364     }
2365     close(IN);
2366
2367     if (!$install_mods) {
2368         do_post_install;
2369         doprint "No modules needed\n";
2370         my $end_time = time;
2371         $install_time = $end_time - $start_time;
2372         return;
2373     }
2374
2375     run_command "$make INSTALL_MOD_STRIP=1 INSTALL_MOD_PATH=$tmpdir modules_install" or
2376         dodie "Failed to install modules";
2377
2378     my $modlib = "/lib/modules/$version";
2379     my $modtar = "ktest-mods.tar.bz2";
2380
2381     run_ssh "rm -rf $modlib" or
2382         dodie "failed to remove old mods: $modlib";
2383
2384     # would be nice if scp -r did not follow symbolic links
2385     run_command "cd $tmpdir && tar -cjf $modtar lib/modules/$version" or
2386         dodie "making tarball";
2387
2388     run_scp_mod "$tmpdir/$modtar", "/tmp" or
2389         dodie "failed to copy modules";
2390
2391     unlink "$tmpdir/$modtar";
2392
2393     run_ssh "'(cd / && tar xjf /tmp/$modtar)'" or
2394         dodie "failed to tar modules";
2395
2396     run_ssh "rm -f /tmp/$modtar";
2397
2398     do_post_install;
2399
2400     my $end_time = time;
2401     $install_time = $end_time - $start_time;
2402 }
2403
2404 sub get_version {
2405     # get the release name
2406     return if ($have_version);
2407     doprint "$make kernelrelease ... ";
2408     $version = `$make -s kernelrelease | tail -1`;
2409     chomp($version);
2410     doprint "$version\n";
2411     $have_version = 1;
2412 }
2413
2414 sub start_monitor_and_install {
2415     # Make sure the stable kernel has finished booting
2416
2417     # Install bisects, don't need console
2418     if (defined $console) {
2419         start_monitor;
2420         wait_for_monitor 5;
2421         end_monitor;
2422     }
2423
2424     get_grub_index;
2425     get_version;
2426     install;
2427
2428     start_monitor if (defined $console);
2429     return monitor;
2430 }
2431
2432 sub process_warning_line {
2433     my ($line) = @_;
2434
2435     chomp $line;
2436
2437     # for distcc heterogeneous systems, some compilers
2438     # do things differently causing warning lines
2439     # to be slightly different. This makes an attempt
2440     # to fixe those issues.
2441
2442     # chop off the index into the line
2443     # using distcc, some compilers give different indexes
2444     # depending on white space
2445     $line =~ s/^(\s*\S+:\d+:)\d+/$1/;
2446
2447     # Some compilers use UTF-8 extended for quotes and some don't.
2448     $line =~ s/$utf8_quote/'/g;
2449
2450     return $line;
2451 }
2452
2453 # Read buildlog and check against warnings file for any
2454 # new warnings.
2455 #
2456 # Returns 1 if OK
2457 #         0 otherwise
2458 sub check_buildlog {
2459     return 1 if (!defined $warnings_file);
2460
2461     my %warnings_list;
2462
2463     # Failed builds should not reboot the target
2464     my $save_no_reboot = $no_reboot;
2465     $no_reboot = 1;
2466
2467     if (-f $warnings_file) {
2468         open(IN, $warnings_file) or
2469             dodie "Error opening $warnings_file";
2470
2471         while (<IN>) {
2472             if (/$check_build_re/) {
2473                 my $warning = process_warning_line $_;
2474
2475                 $warnings_list{$warning} = 1;
2476             }
2477         }
2478         close(IN);
2479     }
2480
2481     # If warnings file didn't exist, and WARNINGS_FILE exist,
2482     # then we fail on any warning!
2483
2484     open(IN, $buildlog) or dodie "Can't open $buildlog";
2485     while (<IN>) {
2486         if (/$check_build_re/) {
2487             my $warning = process_warning_line $_;
2488
2489             if (!defined $warnings_list{$warning}) {
2490                 fail "New warning found (not in $warnings_file)\n$_\n";
2491                 $no_reboot = $save_no_reboot;
2492                 return 0;
2493             }
2494         }
2495     }
2496     $no_reboot = $save_no_reboot;
2497     close(IN);
2498 }
2499
2500 sub check_patch_buildlog {
2501     my ($patch) = @_;
2502
2503     my @files = `git show $patch | diffstat -l`;
2504
2505     foreach my $file (@files) {
2506         chomp $file;
2507     }
2508
2509     open(IN, "git show $patch |") or
2510         dodie "failed to show $patch";
2511     while (<IN>) {
2512         if (m,^--- a/(.*),) {
2513             chomp $1;
2514             $files[$#files] = $1;
2515         }
2516     }
2517     close(IN);
2518
2519     open(IN, $buildlog) or dodie "Can't open $buildlog";
2520     while (<IN>) {
2521         if (/^\s*(.*?):.*(warning|error)/) {
2522             my $err = $1;
2523             foreach my $file (@files) {
2524                 my $fullpath = "$builddir/$file";
2525                 if ($file eq $err || $fullpath eq $err) {
2526                     fail "$file built with warnings" and return 0;
2527                 }
2528             }
2529         }
2530     }
2531     close(IN);
2532
2533     return 1;
2534 }
2535
2536 sub apply_min_config {
2537     my $outconfig = "$output_config.new";
2538
2539     # Read the config file and remove anything that
2540     # is in the force_config hash (from minconfig and others)
2541     # then add the force config back.
2542
2543     doprint "Applying minimum configurations into $output_config.new\n";
2544
2545     open (OUT, ">$outconfig") or
2546         dodie "Can't create $outconfig";
2547
2548     if (-f $output_config) {
2549         open (IN, $output_config) or
2550             dodie "Failed to open $output_config";
2551         while (<IN>) {
2552             if (/^(# )?(CONFIG_[^\s=]*)/) {
2553                 next if (defined($force_config{$2}));
2554             }
2555             print OUT;
2556         }
2557         close IN;
2558     }
2559     foreach my $config (keys %force_config) {
2560         print OUT "$force_config{$config}\n";
2561     }
2562     close OUT;
2563
2564     run_command "mv $outconfig $output_config";
2565 }
2566
2567 sub make_oldconfig {
2568
2569     my @force_list = keys %force_config;
2570
2571     if ($#force_list >= 0) {
2572         apply_min_config;
2573     }
2574
2575     if (!run_command "$make olddefconfig") {
2576         # Perhaps olddefconfig doesn't exist in this version of the kernel
2577         # try oldnoconfig
2578         doprint "olddefconfig failed, trying make oldnoconfig\n";
2579         if (!run_command "$make oldnoconfig") {
2580             doprint "oldnoconfig failed, trying yes '' | make oldconfig\n";
2581             # try a yes '' | oldconfig
2582             run_command "yes '' | $make oldconfig" or
2583                 dodie "failed make config oldconfig";
2584         }
2585     }
2586 }
2587
2588 # read a config file and use this to force new configs.
2589 sub load_force_config {
2590     my ($config) = @_;
2591
2592     doprint "Loading force configs from $config\n";
2593     open(IN, $config) or
2594         dodie "failed to read $config";
2595     while (<IN>) {
2596         chomp;
2597         if (/^(CONFIG[^\s=]*)(\s*=.*)/) {
2598             $force_config{$1} = $_;
2599         } elsif (/^# (CONFIG_\S*) is not set/) {
2600             $force_config{$1} = $_;
2601         }
2602     }
2603     close IN;
2604 }
2605
2606 sub build {
2607     my ($type) = @_;
2608
2609     unlink $buildlog;
2610
2611     my $start_time = time;
2612
2613     # Failed builds should not reboot the target
2614     my $save_no_reboot = $no_reboot;
2615     $no_reboot = 1;
2616
2617     # Calculate a new version from here.
2618     $have_version = 0;
2619
2620     if (defined($pre_build)) {
2621         my $ret = run_command $pre_build;
2622         if (!$ret && defined($pre_build_die) &&
2623             $pre_build_die) {
2624             dodie "failed to pre_build\n";
2625         }
2626     }
2627
2628     if ($type =~ /^useconfig:(.*)/) {
2629         run_command "cp $1 $output_config" or
2630             dodie "could not copy $1 to .config";
2631
2632         $type = "oldconfig";
2633     }
2634
2635     # old config can ask questions
2636     if ($type eq "oldconfig") {
2637         $type = "olddefconfig";
2638
2639         # allow for empty configs
2640         run_command "touch $output_config";
2641
2642         if (!$noclean) {
2643             run_command "mv $output_config $outputdir/config_temp" or
2644                 dodie "moving .config";
2645
2646             run_command "$make mrproper" or dodie "make mrproper";
2647
2648             run_command "mv $outputdir/config_temp $output_config" or
2649                 dodie "moving config_temp";
2650         }
2651     } elsif (!$noclean) {
2652         unlink "$output_config";
2653         run_command "$make mrproper" or
2654             dodie "make mrproper";
2655     }
2656
2657     # add something to distinguish this build
2658     open(OUT, "> $outputdir/localversion") or dodie("Can't make localversion file");
2659     print OUT "$localversion\n";
2660     close(OUT);
2661
2662     if (defined($minconfig)) {
2663         load_force_config($minconfig);
2664     }
2665
2666     if ($type ne "olddefconfig") {
2667         run_command "$make $type" or
2668             dodie "failed make config";
2669     }
2670     # Run old config regardless, to enforce min configurations
2671     make_oldconfig;
2672
2673     if (not defined($build_options)){
2674         $build_options = "";
2675     }
2676     my $build_ret = run_command "$make $build_options", $buildlog;
2677
2678     if (defined($post_build)) {
2679         # Because a post build may change the kernel version
2680         # do it now.
2681         get_version;
2682         my $ret = run_command $post_build;
2683         if (!$ret && defined($post_build_die) &&
2684             $post_build_die) {
2685             dodie "failed to post_build\n";
2686         }
2687     }
2688
2689     if (!$build_ret) {
2690         # bisect may need this to pass
2691         if ($in_bisect) {
2692             $no_reboot = $save_no_reboot;
2693             return 0;
2694         }
2695         fail "failed build" and return 0;
2696     }
2697
2698     $no_reboot = $save_no_reboot;
2699
2700     my $end_time = time;
2701     $build_time = $end_time - $start_time;
2702
2703     return 1;
2704 }
2705
2706 sub halt {
2707     if (!run_ssh "halt" or defined($power_off)) {
2708         if (defined($poweroff_after_halt)) {
2709             sleep $poweroff_after_halt;
2710             run_command "$power_off";
2711         }
2712     } else {
2713         # nope? the zap it!
2714         run_command "$power_off";
2715     }
2716 }
2717
2718 sub success {
2719     my ($i) = @_;
2720
2721     $successes++;
2722
2723     my $name = "";
2724
2725     if (defined($test_name)) {
2726         $name = " ($test_name)";
2727     }
2728
2729     print_times;
2730
2731     doprint "\n\n";
2732     doprint "*******************************************\n";
2733     doprint "*******************************************\n";
2734     doprint "KTEST RESULT: TEST $i$name SUCCESS!!!!   **\n";
2735     doprint "*******************************************\n";
2736     doprint "*******************************************\n";
2737
2738     if (defined($store_successes)) {
2739         save_logs "success", $store_successes;
2740     }
2741
2742     if ($i != $opt{"NUM_TESTS"} && !do_not_reboot) {
2743         doprint "Reboot and wait $sleep_time seconds\n";
2744         reboot_to_good $sleep_time;
2745     }
2746
2747     if (defined($post_test)) {
2748         run_command $post_test;
2749     }
2750 }
2751
2752 sub answer_bisect {
2753     for (;;) {
2754         doprint "Pass, fail, or skip? [p/f/s]";
2755         my $ans = <STDIN>;
2756         chomp $ans;
2757         if ($ans eq "p" || $ans eq "P") {
2758             return 1;
2759         } elsif ($ans eq "f" || $ans eq "F") {
2760             return 0;
2761         } elsif ($ans eq "s" || $ans eq "S") {
2762             return -1;
2763         } else {
2764             print "Please answer 'p', 'f', or 's'\n";
2765         }
2766     }
2767 }
2768
2769 sub child_run_test {
2770
2771     # child should have no power
2772     $reboot_on_error = 0;
2773     $poweroff_on_error = 0;
2774     $die_on_failure = 1;
2775
2776     run_command $run_test, $testlog;
2777
2778     exit $run_command_status;
2779 }
2780
2781 sub child_finished {
2782     $child_done = 1;
2783 }
2784
2785 sub do_run_test {
2786     my $child_pid;
2787     my $child_exit;
2788     my $line;
2789     my $full_line;
2790     my $bug = 0;
2791     my $bug_ignored = 0;
2792
2793     my $start_time = time;
2794
2795     wait_for_monitor 1;
2796
2797     doprint "run test $run_test\n";
2798
2799     $child_done = 0;
2800
2801     $SIG{CHLD} = qw(child_finished);
2802
2803     $child_pid = fork;
2804
2805     child_run_test if (!$child_pid);
2806
2807     $full_line = "";
2808
2809     do {
2810         $line = wait_for_input($monitor_fp, 1);
2811         if (defined($line)) {
2812
2813             # we are not guaranteed to get a full line
2814             $full_line .= $line;
2815             doprint $line;
2816
2817             if ($full_line =~ /call trace:/i) {
2818                 if ($ignore_errors) {
2819                     $bug_ignored = 1;
2820                 } else {
2821                     $bug = 1;
2822                 }
2823             }
2824
2825             if ($full_line =~ /Kernel panic -/) {
2826                 $bug = 1;
2827             }
2828
2829             if ($line =~ /\n/) {
2830                 $full_line = "";
2831             }
2832         }
2833     } while (!$child_done && !$bug);
2834
2835     if (!$bug && $bug_ignored) {
2836         doprint "WARNING: Call Trace detected but ignored due to IGNORE_ERRORS=1\n";
2837     }
2838
2839     if ($bug) {
2840         my $failure_start = time;
2841         my $now;
2842         do {
2843             $line = wait_for_input($monitor_fp, 1);
2844             if (defined($line)) {
2845                 doprint $line;
2846             }
2847             $now = time;
2848             if ($now - $failure_start >= $stop_after_failure) {
2849                 last;
2850             }
2851         } while (defined($line));
2852
2853         doprint "Detected kernel crash!\n";
2854         # kill the child with extreme prejudice
2855         kill 9, $child_pid;
2856     }
2857
2858     waitpid $child_pid, 0;
2859     $child_exit = $? >> 8;
2860
2861     my $end_time = time;
2862     $test_time = $end_time - $start_time;
2863
2864     if (!$bug && $in_bisect) {
2865         if (defined($bisect_ret_good)) {
2866             if ($child_exit == $bisect_ret_good) {
2867                 return 1;
2868             }
2869         }
2870         if (defined($bisect_ret_skip)) {
2871             if ($child_exit == $bisect_ret_skip) {
2872                 return -1;
2873             }
2874         }
2875         if (defined($bisect_ret_abort)) {
2876             if ($child_exit == $bisect_ret_abort) {
2877                 fail "test abort" and return -2;
2878             }
2879         }
2880         if (defined($bisect_ret_bad)) {
2881             if ($child_exit == $bisect_ret_skip) {
2882                 return 0;
2883             }
2884         }
2885         if (defined($bisect_ret_default)) {
2886             if ($bisect_ret_default eq "good") {
2887                 return 1;
2888             } elsif ($bisect_ret_default eq "bad") {
2889                 return 0;
2890             } elsif ($bisect_ret_default eq "skip") {
2891                 return -1;
2892             } elsif ($bisect_ret_default eq "abort") {
2893                 return -2;
2894             } else {
2895                 fail "unknown default action: $bisect_ret_default"
2896                     and return -2;
2897             }
2898         }
2899     }
2900
2901     if ($bug || $child_exit) {
2902         return 0 if $in_bisect;
2903         fail "test failed" and return 0;
2904     }
2905     return 1;
2906 }
2907
2908 sub run_git_bisect {
2909     my ($command) = @_;
2910
2911     doprint "$command ... ";
2912
2913     my $output = `$command 2>&1`;
2914     my $ret = $?;
2915
2916     logit $output;
2917
2918     if ($ret) {
2919         doprint "FAILED\n";
2920         dodie "Failed to git bisect";
2921     }
2922
2923     doprint "SUCCESS\n";
2924     if ($output =~ m/^(Bisecting: .*\(roughly \d+ steps?\))\s+\[([[:xdigit:]]+)\]/) {
2925         doprint "$1 [$2]\n";
2926     } elsif ($output =~ m/^([[:xdigit:]]+) is the first bad commit/) {
2927         $bisect_bad_commit = $1;
2928         doprint "Found bad commit... $1\n";
2929         return 0;
2930     } else {
2931         # we already logged it, just print it now.
2932         print $output;
2933     }
2934
2935     return 1;
2936 }
2937
2938 sub bisect_reboot {
2939     doprint "Reboot and sleep $bisect_sleep_time seconds\n";
2940     reboot_to_good $bisect_sleep_time;
2941 }
2942
2943 # returns 1 on success, 0 on failure, -1 on skip
2944 sub run_bisect_test {
2945     my ($type, $buildtype) = @_;
2946
2947     my $failed = 0;
2948     my $result;
2949     my $output;
2950     my $ret;
2951
2952     $in_bisect = 1;
2953
2954     build $buildtype or $failed = 1;
2955
2956     if ($type ne "build") {
2957         if ($failed && $bisect_skip) {
2958             $in_bisect = 0;
2959             return -1;
2960         }
2961         dodie "Failed on build" if $failed;
2962
2963         # Now boot the box
2964         start_monitor_and_install or $failed = 1;
2965
2966         if ($type ne "boot") {
2967             if ($failed && $bisect_skip) {
2968                 end_monitor;
2969                 bisect_reboot;
2970                 $in_bisect = 0;
2971                 return -1;
2972             }
2973             dodie "Failed on boot" if $failed;
2974
2975             do_run_test or $failed = 1;
2976         }
2977         end_monitor;
2978     }
2979
2980     if ($failed) {
2981         $result = 0;
2982     } else {
2983         $result = 1;
2984     }
2985
2986     # reboot the box to a kernel we can ssh to
2987     if ($type ne "build") {
2988         bisect_reboot;
2989     }
2990     $in_bisect = 0;
2991
2992     return $result;
2993 }
2994
2995 sub run_bisect {
2996     my ($type) = @_;
2997     my $buildtype = "oldconfig";
2998
2999     # We should have a minconfig to use?
3000     if (defined($minconfig)) {
3001         $buildtype = "useconfig:$minconfig";
3002     }
3003
3004     # If the user sets bisect_tries to less than 1, then no tries
3005     # is a success.
3006     my $ret = 1;
3007
3008     # Still let the user manually decide that though.
3009     if ($bisect_tries < 1 && $bisect_manual) {
3010         $ret = answer_bisect;
3011     }
3012
3013     for (my $i = 0; $i < $bisect_tries; $i++) {
3014         if ($bisect_tries > 1) {
3015             my $t = $i + 1;
3016             doprint("Running bisect trial $t of $bisect_tries:\n");
3017         }
3018         $ret = run_bisect_test $type, $buildtype;
3019
3020         if ($bisect_manual) {
3021             $ret = answer_bisect;
3022         }
3023
3024         last if (!$ret);
3025     }
3026
3027     # Are we looking for where it worked, not failed?
3028     if ($reverse_bisect && $ret >= 0) {
3029         $ret = !$ret;
3030     }
3031
3032     if ($ret > 0) {
3033         return "good";
3034     } elsif ($ret == 0) {
3035         return  "bad";
3036     } elsif ($bisect_skip) {
3037         doprint "HIT A BAD COMMIT ... SKIPPING\n";
3038         return "skip";
3039     }
3040 }
3041
3042 sub update_bisect_replay {
3043     my $tmp_log = "$tmpdir/ktest_bisect_log";
3044     run_command "git bisect log > $tmp_log" or
3045         dodie "can't create bisect log";
3046     return $tmp_log;
3047 }
3048
3049 sub bisect {
3050     my ($i) = @_;
3051
3052     my $result;
3053
3054     dodie "BISECT_GOOD[$i] not defined\n"       if (!defined($bisect_good));
3055     dodie "BISECT_BAD[$i] not defined\n"        if (!defined($bisect_bad));
3056     dodie "BISECT_TYPE[$i] not defined\n"       if (!defined($bisect_type));
3057
3058     my $good = $bisect_good;
3059     my $bad = $bisect_bad;
3060     my $type = $bisect_type;
3061     my $start = $bisect_start;
3062     my $replay = $bisect_replay;
3063     my $start_files = $bisect_files;
3064
3065     if (defined($start_files)) {
3066         $start_files = " -- " . $start_files;
3067     } else {
3068         $start_files = "";
3069     }
3070
3071     # convert to true sha1's
3072     $good = get_sha1($good);
3073     $bad = get_sha1($bad);
3074
3075     if (defined($bisect_reverse) && $bisect_reverse == 1) {
3076         doprint "Performing a reverse bisect (bad is good, good is bad!)\n";
3077         $reverse_bisect = 1;
3078     } else {
3079         $reverse_bisect = 0;
3080     }
3081
3082     # Can't have a test without having a test to run
3083     if ($type eq "test" && !defined($run_test)) {
3084         $type = "boot";
3085     }
3086
3087     # Check if a bisect was running
3088     my $bisect_start_file = "$builddir/.git/BISECT_START";
3089
3090     my $check = $bisect_check;
3091     my $do_check = defined($check) && $check ne "0";
3092
3093     if ( -f $bisect_start_file ) {
3094         print "Bisect in progress found\n";
3095         if ($do_check) {
3096             print " If you say yes, then no checks of good or bad will be done\n";
3097         }
3098         if (defined($replay)) {
3099             print "** BISECT_REPLAY is defined in config file **";
3100             print " Ignore config option and perform new git bisect log?\n";
3101             if (read_ync " (yes, no, or cancel) ") {
3102                 $replay = update_bisect_replay;
3103                 $do_check = 0;
3104             }
3105         } elsif (read_yn "read git log and continue?") {
3106             $replay = update_bisect_replay;
3107             $do_check = 0;
3108         }
3109     }
3110
3111     if ($do_check) {
3112         # get current HEAD
3113         my $head = get_sha1("HEAD");
3114
3115         if ($check ne "good") {
3116             doprint "TESTING BISECT BAD [$bad]\n";
3117             run_command "git checkout $bad" or
3118                 dodie "Failed to checkout $bad";
3119
3120             $result = run_bisect $type;
3121
3122             if ($result ne "bad") {
3123                 fail "Tested BISECT_BAD [$bad] and it succeeded" and return 0;
3124             }
3125         }
3126
3127         if ($check ne "bad") {
3128             doprint "TESTING BISECT GOOD [$good]\n";
3129             run_command "git checkout $good" or
3130                 dodie "Failed to checkout $good";
3131
3132             $result = run_bisect $type;
3133
3134             if ($result ne "good") {
3135                 fail "Tested BISECT_GOOD [$good] and it failed" and return 0;
3136             }
3137         }
3138
3139         # checkout where we started
3140         run_command "git checkout $head" or
3141             dodie "Failed to checkout $head";
3142     }
3143
3144     run_command "git bisect start$start_files" or
3145         dodie "could not start bisect";
3146
3147     if (defined($replay)) {
3148         run_command "git bisect replay $replay" or
3149             dodie "failed to run replay";
3150     } else {
3151         run_command "git bisect good $good" or
3152             dodie "could not set bisect good to $good";
3153
3154         run_git_bisect "git bisect bad $bad" or
3155             dodie "could not set bisect bad to $bad";
3156     }
3157
3158     if (defined($start)) {
3159         run_command "git checkout $start" or
3160             dodie "failed to checkout $start";
3161     }
3162
3163     my $test;
3164     do {
3165         $result = run_bisect $type;
3166         $test = run_git_bisect "git bisect $result";
3167         print_times;
3168     } while ($test);
3169
3170     run_command "git bisect log" or
3171         dodie "could not capture git bisect log";
3172
3173     run_command "git bisect reset" or
3174         dodie "could not reset git bisect";
3175
3176     doprint "Bad commit was [$bisect_bad_commit]\n";
3177
3178     success $i;
3179 }
3180
3181 sub assign_configs {
3182     my ($hash, $config) = @_;
3183
3184     doprint "Reading configs from $config\n";
3185
3186     open (IN, $config) or
3187         dodie "Failed to read $config";
3188
3189     while (<IN>) {
3190         chomp;
3191         if (/^((CONFIG\S*)=.*)/) {
3192             ${$hash}{$2} = $1;
3193         } elsif (/^(# (CONFIG\S*) is not set)/) {
3194             ${$hash}{$2} = $1;
3195         }
3196     }
3197
3198     close(IN);
3199 }
3200
3201 sub process_config_ignore {
3202     my ($config) = @_;
3203
3204     assign_configs \%config_ignore, $config;
3205 }
3206
3207 sub get_dependencies {
3208     my ($config) = @_;
3209
3210     my $arr = $dependency{$config};
3211     if (!defined($arr)) {
3212         return ();
3213     }
3214
3215     my @deps = @{$arr};
3216
3217     foreach my $dep (@{$arr}) {
3218         print "ADD DEP $dep\n";
3219         @deps = (@deps, get_dependencies $dep);
3220     }
3221
3222     return @deps;
3223 }
3224
3225 sub save_config {
3226     my ($pc, $file) = @_;
3227
3228     my %configs = %{$pc};
3229
3230     doprint "Saving configs into $file\n";
3231
3232     open(OUT, ">$file") or dodie "Can not write to $file";
3233
3234     foreach my $config (keys %configs) {
3235         print OUT "$configs{$config}\n";
3236     }
3237     close(OUT);
3238 }
3239
3240 sub create_config {
3241     my ($name, $pc) = @_;
3242
3243     doprint "Creating old config from $name configs\n";
3244
3245     save_config $pc, $output_config;
3246
3247     make_oldconfig;
3248 }
3249
3250 sub run_config_bisect_test {
3251     my ($type) = @_;
3252
3253     my $ret = run_bisect_test $type, "oldconfig";
3254
3255     if ($bisect_manual) {
3256         $ret = answer_bisect;
3257     }
3258
3259     return $ret;
3260 }
3261
3262 sub config_bisect_end {
3263     my ($good, $bad) = @_;
3264     my $diffexec = "diff -u";
3265
3266     if (-f "$builddir/scripts/diffconfig") {
3267         $diffexec = "$builddir/scripts/diffconfig";
3268     }
3269     doprint "\n\n***************************************\n";
3270     doprint "No more config bisecting possible.\n";
3271     run_command "$diffexec $good $bad", 1;
3272     doprint "***************************************\n\n";
3273 }
3274
3275 sub run_config_bisect {
3276     my ($good, $bad, $last_result) = @_;
3277     my $reset = "";
3278     my $cmd;
3279     my $ret;
3280
3281     if (!length($last_result)) {
3282         $reset = "-r";
3283     }
3284     run_command "$config_bisect_exec $reset -b $outputdir $good $bad $last_result", 1;
3285
3286     # config-bisect returns:
3287     #   0 if there is more to bisect
3288     #   1 for finding a good config
3289     #   2 if it can not find any more configs
3290     #  -1 (255) on error
3291     if ($run_command_status) {
3292         return $run_command_status;
3293     }
3294
3295     $ret = run_config_bisect_test $config_bisect_type;
3296     if ($ret) {
3297         doprint "NEW GOOD CONFIG ($pass)\n";
3298         system("cp $output_config $tmpdir/good_config.tmp.$pass");
3299         $pass++;
3300         # Return 3 for good config
3301         return 3;
3302     } else {
3303         doprint "NEW BAD CONFIG ($pass)\n";
3304         system("cp $output_config $tmpdir/bad_config.tmp.$pass");
3305         $pass++;
3306         # Return 4 for bad config
3307         return 4;
3308     }
3309 }
3310
3311 sub config_bisect {
3312     my ($i) = @_;
3313
3314     my $good_config;
3315     my $bad_config;
3316
3317     my $type = $config_bisect_type;
3318     my $ret;
3319
3320     $bad_config = $config_bisect;
3321
3322     if (defined($config_bisect_good)) {
3323         $good_config = $config_bisect_good;
3324     } elsif (defined($minconfig)) {
3325         $good_config = $minconfig;
3326     } else {
3327         doprint "No config specified, checking if defconfig works";
3328         $ret = run_bisect_test $type, "defconfig";
3329         if (!$ret) {
3330             fail "Have no good config to compare with, please set CONFIG_BISECT_GOOD";
3331             return 1;
3332         }
3333         $good_config = $output_config;
3334     }
3335
3336     if (!defined($config_bisect_exec)) {
3337         # First check the location that ktest.pl ran
3338         my @locations = (
3339                 "$pwd/config-bisect.pl",
3340                 "$dirname/config-bisect.pl",
3341                 "$builddir/tools/testing/ktest/config-bisect.pl",
3342                 undef );
3343         foreach my $loc (@locations) {
3344             doprint "loc = $loc\n";
3345             $config_bisect_exec = $loc;
3346             last if (defined($config_bisect_exec && -x $config_bisect_exec));
3347         }
3348         if (!defined($config_bisect_exec)) {
3349             fail "Could not find an executable config-bisect.pl\n",
3350                 "  Set CONFIG_BISECT_EXEC to point to config-bisect.pl";
3351             return 1;
3352         }
3353     }
3354
3355     # we don't want min configs to cause issues here.
3356     doprint "Disabling 'MIN_CONFIG' for this test\n";
3357     undef $minconfig;
3358
3359     my %good_configs;
3360     my %bad_configs;
3361     my %tmp_configs;
3362
3363     if (-f "$tmpdir/good_config.tmp" || -f "$tmpdir/bad_config.tmp") {
3364         if (read_yn "Interrupted config-bisect. Continue (n - will start new)?") {
3365             if (-f "$tmpdir/good_config.tmp") {
3366                 $good_config = "$tmpdir/good_config.tmp";
3367             } else {
3368                 $good_config = "$tmpdir/good_config";
3369             }
3370             if (-f "$tmpdir/bad_config.tmp") {
3371                 $bad_config = "$tmpdir/bad_config.tmp";
3372             } else {
3373                 $bad_config = "$tmpdir/bad_config";
3374             }
3375         }
3376     }
3377     doprint "Run good configs through make oldconfig\n";
3378     assign_configs \%tmp_configs, $good_config;
3379     create_config "$good_config", \%tmp_configs;
3380     $good_config = "$tmpdir/good_config";
3381     system("cp $output_config $good_config") == 0 or dodie "cp good config";
3382
3383     doprint "Run bad configs through make oldconfig\n";
3384     assign_configs \%tmp_configs, $bad_config;
3385     create_config "$bad_config", \%tmp_configs;
3386     $bad_config = "$tmpdir/bad_config";
3387     system("cp $output_config $bad_config") == 0 or dodie "cp bad config";
3388
3389     if (defined($config_bisect_check) && $config_bisect_check ne "0") {
3390         if ($config_bisect_check ne "good") {
3391             doprint "Testing bad config\n";
3392
3393             $ret = run_bisect_test $type, "useconfig:$bad_config";
3394             if ($ret) {
3395                 fail "Bad config succeeded when expected to fail!";
3396                 return 0;
3397             }
3398         }
3399         if ($config_bisect_check ne "bad") {
3400             doprint "Testing good config\n";
3401
3402             $ret = run_bisect_test $type, "useconfig:$good_config";
3403             if (!$ret) {
3404                 fail "Good config failed when expected to succeed!";
3405                 return 0;
3406             }
3407         }
3408     }
3409
3410     my $last_run = "";
3411
3412     do {
3413         $ret = run_config_bisect $good_config, $bad_config, $last_run;
3414         if ($ret == 3) {
3415             $last_run = "good";
3416         } elsif ($ret == 4) {
3417             $last_run = "bad";
3418         }
3419         print_times;
3420     } while ($ret == 3 || $ret == 4);
3421
3422     if ($ret == 2) {
3423         config_bisect_end "$good_config.tmp", "$bad_config.tmp";
3424     }
3425
3426     return $ret if ($ret < 0);
3427
3428     success $i;
3429 }
3430
3431 sub patchcheck_reboot {
3432     doprint "Reboot and sleep $patchcheck_sleep_time seconds\n";
3433     reboot_to_good $patchcheck_sleep_time;
3434 }
3435
3436 sub patchcheck {
3437     my ($i) = @_;
3438
3439     dodie "PATCHCHECK_START[$i] not defined\n"
3440         if (!defined($patchcheck_start));
3441     dodie "PATCHCHECK_TYPE[$i] not defined\n"
3442         if (!defined($patchcheck_type));
3443
3444     my $start = $patchcheck_start;
3445
3446     my $cherry = $patchcheck_cherry;
3447     if (!defined($cherry)) {
3448         $cherry = 0;
3449     }
3450
3451     my $end = "HEAD";
3452     if (defined($patchcheck_end)) {
3453         $end = $patchcheck_end;
3454     } elsif ($cherry) {
3455         dodie "PATCHCHECK_END must be defined with PATCHCHECK_CHERRY\n";
3456     }
3457
3458     # Get the true sha1's since we can use things like HEAD~3
3459     $start = get_sha1($start);
3460     $end = get_sha1($end);
3461
3462     my $type = $patchcheck_type;
3463
3464     # Can't have a test without having a test to run
3465     if ($type eq "test" && !defined($run_test)) {
3466         $type = "boot";
3467     }
3468
3469     if ($cherry) {
3470         open (IN, "git cherry -v $start $end|") or
3471             dodie "could not get git list";
3472     } else {
3473         open (IN, "git log --pretty=oneline $end|") or
3474             dodie "could not get git list";
3475     }
3476
3477     my @list;
3478
3479     while (<IN>) {
3480         chomp;
3481         # git cherry adds a '+' we want to remove
3482         s/^\+ //;
3483         $list[$#list+1] = $_;
3484         last if (/^$start/);
3485     }
3486     close(IN);
3487
3488     if (!$cherry) {
3489         if ($list[$#list] !~ /^$start/) {
3490             fail "SHA1 $start not found";
3491         }
3492
3493         # go backwards in the list
3494         @list = reverse @list;
3495     }
3496
3497     doprint("Going to test the following commits:\n");
3498     foreach my $l (@list) {
3499         doprint "$l\n";
3500     }
3501
3502     my $save_clean = $noclean;
3503     my %ignored_warnings;
3504
3505     if (defined($ignore_warnings)) {
3506         foreach my $sha1 (split /\s+/, $ignore_warnings) {
3507             $ignored_warnings{$sha1} = 1;
3508         }
3509     }
3510
3511     $in_patchcheck = 1;
3512     foreach my $item (@list) {
3513         my $sha1 = $item;
3514         $sha1 =~ s/^([[:xdigit:]]+).*/$1/;
3515
3516         doprint "\nProcessing commit \"$item\"\n\n";
3517
3518         run_command "git checkout $sha1" or
3519             dodie "Failed to checkout $sha1";
3520
3521         # only clean on the first and last patch
3522         if ($item eq $list[0] ||
3523             $item eq $list[$#list]) {
3524             $noclean = $save_clean;
3525         } else {
3526             $noclean = 1;
3527         }
3528
3529         if (defined($minconfig)) {
3530             build "useconfig:$minconfig" or return 0;
3531         } else {
3532             # ?? no config to use?
3533             build "oldconfig" or return 0;
3534         }
3535
3536         # No need to do per patch checking if warnings file exists
3537         if (!defined($warnings_file) && !defined($ignored_warnings{$sha1})) {
3538             check_patch_buildlog $sha1 or return 0;
3539         }
3540
3541         check_buildlog or return 0;
3542
3543         next if ($type eq "build");
3544
3545         my $failed = 0;
3546
3547         start_monitor_and_install or $failed = 1;
3548
3549         if (!$failed && $type ne "boot"){
3550             do_run_test or $failed = 1;
3551         }
3552         end_monitor;
3553         if ($failed) {
3554             print_times;
3555             return 0;
3556         }
3557         patchcheck_reboot;
3558         print_times;
3559     }
3560     $in_patchcheck = 0;
3561     success $i;
3562
3563     return 1;
3564 }
3565
3566 sub add_dep {
3567     # $config depends on $dep
3568     my ($config, $dep) = @_;
3569
3570     if (defined($depends{$config})) {
3571         $depends{$config} .= " " . $dep;
3572     } else {
3573         $depends{$config} = $dep;
3574     }
3575
3576     # record the number of configs depending on $dep
3577     if (defined $depcount{$dep}) {
3578         $depcount{$dep}++;
3579     } else {
3580         $depcount{$dep} = 1;
3581     } 
3582 }
3583
3584 # taken from streamline_config.pl
3585 sub read_kconfig {
3586     my ($kconfig) = @_;
3587
3588     my $state = "NONE";
3589     my $config;
3590     my @kconfigs;
3591
3592     my $cont = 0;
3593     my $line;
3594
3595     if (! -f $kconfig) {
3596         doprint "file $kconfig does not exist, skipping\n";
3597         return;
3598     }
3599
3600     open(KIN, "$kconfig")
3601         or dodie "Can't open $kconfig";
3602     while (<KIN>) {
3603         chomp;
3604
3605         # Make sure that lines ending with \ continue
3606         if ($cont) {
3607             $_ = $line . " " . $_;
3608         }
3609
3610         if (s/\\$//) {
3611             $cont = 1;
3612             $line = $_;
3613             next;
3614         }
3615
3616         $cont = 0;
3617
3618         # collect any Kconfig sources
3619         if (/^source\s*"(.*)"/) {
3620             $kconfigs[$#kconfigs+1] = $1;
3621         }
3622
3623         # configs found
3624         if (/^\s*(menu)?config\s+(\S+)\s*$/) {
3625             $state = "NEW";
3626             $config = $2;
3627
3628             for (my $i = 0; $i < $iflevel; $i++) {
3629                 add_dep $config, $ifdeps[$i];
3630             }
3631
3632         # collect the depends for the config
3633         } elsif ($state eq "NEW" && /^\s*depends\s+on\s+(.*)$/) {
3634
3635             add_dep $config, $1;
3636
3637         # Get the configs that select this config
3638         } elsif ($state eq "NEW" && /^\s*select\s+(\S+)/) {
3639
3640             # selected by depends on config
3641             add_dep $1, $config;
3642
3643         # Check for if statements
3644         } elsif (/^if\s+(.*\S)\s*$/) {
3645             my $deps = $1;
3646             # remove beginning and ending non text
3647             $deps =~ s/^[^a-zA-Z0-9_]*//;
3648             $deps =~ s/[^a-zA-Z0-9_]*$//;
3649
3650             my @deps = split /[^a-zA-Z0-9_]+/, $deps;
3651
3652             $ifdeps[$iflevel++] = join ':', @deps;
3653
3654         } elsif (/^endif/) {
3655
3656             $iflevel-- if ($iflevel);
3657
3658         # stop on "help"
3659         } elsif (/^\s*help\s*$/) {
3660             $state = "NONE";
3661         }
3662     }
3663     close(KIN);
3664
3665     # read in any configs that were found.
3666     foreach $kconfig (@kconfigs) {
3667         if (!defined($read_kconfigs{$kconfig})) {
3668             $read_kconfigs{$kconfig} = 1;
3669             read_kconfig("$builddir/$kconfig");
3670         }
3671     }
3672 }
3673
3674 sub read_depends {
3675     # find out which arch this is by the kconfig file
3676     open (IN, $output_config) or
3677         dodie "Failed to read $output_config";
3678     my $arch;
3679     while (<IN>) {
3680         if (m,Linux/(\S+)\s+\S+\s+Kernel Configuration,) {
3681             $arch = $1;
3682             last;
3683         }
3684     }
3685     close IN;
3686
3687     if (!defined($arch)) {
3688         doprint "Could not find arch from config file\n";
3689         doprint "no dependencies used\n";
3690         return;
3691     }
3692
3693     # arch is really the subarch, we need to know
3694     # what directory to look at.
3695     if ($arch eq "i386" || $arch eq "x86_64") {
3696         $arch = "x86";
3697     }
3698
3699     my $kconfig = "$builddir/arch/$arch/Kconfig";
3700
3701     if (! -f $kconfig && $arch =~ /\d$/) {
3702         my $orig = $arch;
3703         # some subarchs have numbers, truncate them
3704         $arch =~ s/\d*$//;
3705         $kconfig = "$builddir/arch/$arch/Kconfig";
3706         if (! -f $kconfig) {
3707             doprint "No idea what arch dir $orig is for\n";
3708             doprint "no dependencies used\n";
3709             return;
3710         }
3711     }
3712
3713     read_kconfig($kconfig);
3714 }
3715
3716 sub make_new_config {
3717     my @configs = @_;
3718
3719     open (OUT, ">$output_config")
3720         or dodie "Failed to write $output_config";
3721
3722     foreach my $config (@configs) {
3723         print OUT "$config\n";
3724     }
3725     close OUT;
3726 }
3727
3728 sub chomp_config {
3729     my ($config) = @_;
3730
3731     $config =~ s/CONFIG_//;
3732
3733     return $config;
3734 }
3735
3736 sub get_depends {
3737     my ($dep) = @_;
3738
3739     my $kconfig = chomp_config $dep;
3740
3741     $dep = $depends{"$kconfig"};
3742
3743     # the dep string we have saves the dependencies as they
3744     # were found, including expressions like ! && ||. We
3745     # want to split this out into just an array of configs.
3746
3747     my $valid = "A-Za-z_0-9";
3748
3749     my @configs;
3750
3751     while ($dep =~ /[$valid]/) {
3752         if ($dep =~ /^[^$valid]*([$valid]+)/) {
3753             my $conf = "CONFIG_" . $1;
3754
3755             $configs[$#configs + 1] = $conf;
3756
3757             $dep =~ s/^[^$valid]*[$valid]+//;
3758         } else {
3759             dodie "this should never happen";
3760         }
3761     }
3762
3763     return @configs;
3764 }
3765
3766 sub test_this_config {
3767     my ($config) = @_;
3768
3769     my $found;
3770
3771     # if we already processed this config, skip it
3772     if (defined($processed_configs{$config})) {
3773         return undef;
3774     }
3775     $processed_configs{$config} = 1;
3776
3777     # if this config failed during this round, skip it
3778     if (defined($nochange_config{$config})) {
3779         return undef;
3780     }
3781
3782     my $kconfig = chomp_config $config;
3783
3784     # Test dependencies first
3785     if (defined($depends{"$kconfig"})) {
3786         my @parents = get_depends $config;
3787         foreach my $parent (@parents) {
3788             # if the parent is in the min config, check it first
3789             next if (!defined($min_configs{$parent}));
3790             $found = test_this_config($parent);
3791             if (defined($found)) {
3792                 return $found;
3793             }
3794         }
3795     }
3796
3797     # Remove this config from the list of configs
3798     # do a make olddefconfig and then read the resulting
3799     # .config to make sure it is missing the config that
3800     # we had before
3801     my %configs = %min_configs;
3802     $configs{$config} = "# $config is not set";
3803     make_new_config ((values %configs), (values %keep_configs));
3804     make_oldconfig;
3805     delete $configs{$config};
3806     undef %configs;
3807     assign_configs \%configs, $output_config;
3808
3809     if (!defined($configs{$config}) || $configs{$config} =~ /^#/) {
3810         return $config;
3811     }
3812
3813     doprint "disabling config $config did not change .config\n";
3814
3815     $nochange_config{$config} = 1;
3816
3817     return undef;
3818 }
3819
3820 sub make_min_config {
3821     my ($i) = @_;
3822
3823     my $type = $minconfig_type;
3824     if ($type ne "boot" && $type ne "test") {
3825         fail "Invalid MIN_CONFIG_TYPE '$minconfig_type'\n" .
3826             " make_min_config works only with 'boot' and 'test'\n" and return;
3827     }
3828
3829     if (!defined($output_minconfig)) {
3830         fail "OUTPUT_MIN_CONFIG not defined" and return;
3831     }
3832
3833     # If output_minconfig exists, and the start_minconfig
3834     # came from min_config, than ask if we should use
3835     # that instead.
3836     if (-f $output_minconfig && !$start_minconfig_defined) {
3837         print "$output_minconfig exists\n";
3838         if (!defined($use_output_minconfig)) {
3839             if (read_yn " Use it as minconfig?") {
3840                 $start_minconfig = $output_minconfig;
3841             }
3842         } elsif ($use_output_minconfig > 0) {
3843             doprint "Using $output_minconfig as MIN_CONFIG\n";
3844             $start_minconfig = $output_minconfig;
3845         } else {
3846             doprint "Set to still use MIN_CONFIG as starting point\n";
3847         }
3848     }
3849
3850     if (!defined($start_minconfig)) {
3851         fail "START_MIN_CONFIG or MIN_CONFIG not defined" and return;
3852     }
3853
3854     my $temp_config = "$tmpdir/temp_config";
3855
3856     # First things first. We build an allnoconfig to find
3857     # out what the defaults are that we can't touch.
3858     # Some are selections, but we really can't handle selections.
3859
3860     my $save_minconfig = $minconfig;
3861     undef $minconfig;
3862
3863     run_command "$make allnoconfig" or return 0;
3864
3865     read_depends;
3866
3867     process_config_ignore $output_config;
3868
3869     undef %save_configs;
3870     undef %min_configs;
3871
3872     if (defined($ignore_config)) {
3873         # make sure the file exists
3874         `touch $ignore_config`;
3875         assign_configs \%save_configs, $ignore_config;
3876     }
3877
3878     %keep_configs = %save_configs;
3879
3880     doprint "Load initial configs from $start_minconfig\n";
3881
3882     # Look at the current min configs, and save off all the
3883     # ones that were set via the allnoconfig
3884     assign_configs \%min_configs, $start_minconfig;
3885
3886     my @config_keys = keys %min_configs;
3887
3888     # All configs need a depcount
3889     foreach my $config (@config_keys) {
3890         my $kconfig = chomp_config $config;
3891         if (!defined $depcount{$kconfig}) {
3892             $depcount{$kconfig} = 0;
3893         }
3894     }
3895
3896     # Remove anything that was set by the make allnoconfig
3897     # we shouldn't need them as they get set for us anyway.
3898     foreach my $config (@config_keys) {
3899         # Remove anything in the ignore_config
3900         if (defined($keep_configs{$config})) {
3901             my $file = $ignore_config;
3902             $file =~ s,.*/(.*?)$,$1,;
3903             doprint "$config set by $file ... ignored\n";
3904             delete $min_configs{$config};
3905             next;
3906         }
3907         # But make sure the settings are the same. If a min config
3908         # sets a selection, we do not want to get rid of it if
3909         # it is not the same as what we have. Just move it into
3910         # the keep configs.
3911         if (defined($config_ignore{$config})) {
3912             if ($config_ignore{$config} ne $min_configs{$config}) {
3913                 doprint "$config is in allnoconfig as '$config_ignore{$config}'";
3914                 doprint " but it is '$min_configs{$config}' in minconfig .. keeping\n";
3915                 $keep_configs{$config} = $min_configs{$config};
3916             } else {
3917                 doprint "$config set by allnoconfig ... ignored\n";
3918             }
3919             delete $min_configs{$config};
3920         }
3921     }
3922
3923     my $done = 0;
3924     my $take_two = 0;
3925
3926     while (!$done) {
3927         my $config;
3928         my $found;
3929
3930         # Now disable each config one by one and do a make oldconfig
3931         # till we find a config that changes our list.
3932
3933         my @test_configs = keys %min_configs;
3934
3935         # Sort keys by who is most dependent on
3936         @test_configs = sort  { $depcount{chomp_config($b)} <=> $depcount{chomp_config($a)} }
3937             @test_configs ;
3938
3939         # Put configs that did not modify the config at the end.
3940         my $reset = 1;
3941         for (my $i = 0; $i < $#test_configs; $i++) {
3942             if (!defined($nochange_config{$test_configs[0]})) {
3943                 $reset = 0;
3944                 last;
3945             }
3946             # This config didn't change the .config last time.
3947             # Place it at the end
3948             my $config = shift @test_configs;
3949             push @test_configs, $config;
3950         }
3951
3952         # if every test config has failed to modify the .config file
3953         # in the past, then reset and start over.
3954         if ($reset) {
3955             undef %nochange_config;
3956         }
3957
3958         undef %processed_configs;
3959
3960         foreach my $config (@test_configs) {
3961
3962             $found = test_this_config $config;
3963
3964             last if (defined($found));
3965
3966             # oh well, try another config
3967         }
3968
3969         if (!defined($found)) {
3970             # we could have failed due to the nochange_config hash
3971             # reset and try again
3972             if (!$take_two) {
3973                 undef %nochange_config;
3974                 $take_two = 1;
3975                 next;
3976             }
3977             doprint "No more configs found that we can disable\n";
3978             $done = 1;
3979             last;
3980         }
3981         $take_two = 0;
3982
3983         $config = $found;
3984
3985         doprint "Test with $config disabled\n";
3986
3987         # set in_bisect to keep build and monitor from dieing
3988         $in_bisect = 1;
3989
3990         my $failed = 0;
3991         build "oldconfig" or $failed = 1;
3992         if (!$failed) {
3993             start_monitor_and_install or $failed = 1;
3994
3995             if ($type eq "test" && !$failed) {
3996                 do_run_test or $failed = 1;
3997             }
3998
3999             end_monitor;
4000         }
4001
4002         $in_bisect = 0;
4003
4004         if ($failed) {
4005             doprint "$min_configs{$config} is needed to boot the box... keeping\n";
4006             # this config is needed, add it to the ignore list.
4007             $keep_configs{$config} = $min_configs{$config};
4008             $save_configs{$config} = $min_configs{$config};
4009             delete $min_configs{$config};
4010
4011             # update new ignore configs
4012             if (defined($ignore_config)) {
4013                 open (OUT, ">$temp_config") or
4014                     dodie "Can't write to $temp_config";
4015                 foreach my $config (keys %save_configs) {
4016                     print OUT "$save_configs{$config}\n";
4017                 }
4018                 close OUT;
4019                 run_command "mv $temp_config $ignore_config" or
4020                     dodie "failed to copy update to $ignore_config";
4021             }
4022
4023         } else {
4024             # We booted without this config, remove it from the minconfigs.
4025             doprint "$config is not needed, disabling\n";
4026
4027             delete $min_configs{$config};
4028
4029             # Also disable anything that is not enabled in this config
4030             my %configs;
4031             assign_configs \%configs, $output_config;
4032             my @config_keys = keys %min_configs;
4033             foreach my $config (@config_keys) {
4034                 if (!defined($configs{$config})) {
4035                     doprint "$config is not set, disabling\n";
4036                     delete $min_configs{$config};
4037                 }
4038             }
4039
4040             # Save off all the current mandatory configs
4041             open (OUT, ">$temp_config") or
4042                 dodie "Can't write to $temp_config";
4043             foreach my $config (keys %keep_configs) {
4044                 print OUT "$keep_configs{$config}\n";
4045             }
4046             foreach my $config (keys %min_configs) {
4047                 print OUT "$min_configs{$config}\n";
4048             }
4049             close OUT;
4050
4051             run_command "mv $temp_config $output_minconfig" or
4052                 dodie "failed to copy update to $output_minconfig";
4053         }
4054
4055         doprint "Reboot and wait $sleep_time seconds\n";
4056         reboot_to_good $sleep_time;
4057     }
4058
4059     success $i;
4060     return 1;
4061 }
4062
4063 sub make_warnings_file {
4064     my ($i) = @_;
4065
4066     if (!defined($warnings_file)) {
4067         dodie "Must define WARNINGS_FILE for make_warnings_file test";
4068     }
4069
4070     if ($build_type eq "nobuild") {
4071         dodie "BUILD_TYPE can not be 'nobuild' for make_warnings_file test";
4072     }
4073
4074     build $build_type or dodie "Failed to build";
4075
4076     open(OUT, ">$warnings_file") or dodie "Can't create $warnings_file";
4077
4078     open(IN, $buildlog) or dodie "Can't open $buildlog";
4079     while (<IN>) {
4080         # Some compilers use UTF-8 extended for quotes
4081         # for distcc heterogeneous systems, this causes issues
4082         s/$utf8_quote/'/g;
4083
4084         if (/$check_build_re/) {
4085             print OUT;
4086         }
4087     }
4088     close(IN);
4089
4090     close(OUT);
4091
4092     success $i;
4093 }
4094
4095 sub option_defined {
4096     my ($option) = @_;
4097
4098     if (defined($opt{$option}) && $opt{$option} !~ /^\s*$/) {
4099         return 1;
4100     }
4101
4102     return 0;
4103 }
4104
4105 sub __set_test_option {
4106     my ($name, $i) = @_;
4107
4108     my $option = "$name\[$i\]";
4109
4110     if (option_defined($option)) {
4111         return $opt{$option};
4112     }
4113
4114     foreach my $test (keys %repeat_tests) {
4115         if ($i >= $test &&
4116             $i < $test + $repeat_tests{$test}) {
4117             $option = "$name\[$test\]";
4118             if (option_defined($option)) {
4119                 return $opt{$option};
4120             }
4121         }
4122     }
4123
4124     if (option_defined($name)) {
4125         return $opt{$name};
4126     }
4127
4128     return undef;
4129 }
4130
4131 sub set_test_option {
4132     my ($name, $i) = @_;
4133
4134     my $option = __set_test_option($name, $i);
4135     return $option if (!defined($option));
4136
4137     return eval_option($name, $option, $i);
4138 }
4139
4140 sub find_mailer {
4141     my ($mailer) = @_;
4142
4143     my @paths = split /:/, $ENV{PATH};
4144
4145     # sendmail is usually in /usr/sbin
4146     $paths[$#paths + 1] = "/usr/sbin";
4147
4148     foreach my $path (@paths) {
4149         if (-x "$path/$mailer") {
4150             return $path;
4151         }
4152     }
4153
4154     return undef;
4155 }
4156
4157 sub do_send_mail {
4158     my ($subject, $message, $file) = @_;
4159
4160     if (!defined($mail_path)) {
4161         # find the mailer
4162         $mail_path = find_mailer $mailer;
4163         if (!defined($mail_path)) {
4164             die "\nCan not find $mailer in PATH\n";
4165         }
4166     }
4167
4168     my $header_file = "$tmpdir/header";
4169     open (HEAD, ">$header_file") or die "Can not create $header_file\n";
4170     print HEAD "To: $mailto\n";
4171     print HEAD "Subject: $subject\n\n";
4172     print HEAD "$message\n";
4173     close HEAD;
4174
4175     if (!defined($mail_command)) {
4176         if ($mailer eq "mail" || $mailer eq "mailx") {
4177             $mail_command = "cat \$HEADER_FILE \$BODY_FILE | \$MAIL_PATH/\$MAILER -s \'\$SUBJECT\' \$MAILTO";
4178         } elsif ($mailer eq "sendmail" ) {
4179             $mail_command =  "cat \$HEADER_FILE \$BODY_FILE | \$MAIL_PATH/\$MAILER -t \$MAILTO";
4180         } else {
4181             die "\nYour mailer: $mailer is not supported.\n";
4182         }
4183     }
4184
4185     if (defined($file)) {
4186         $mail_command =~ s/\$BODY_FILE/$file/g;
4187     } else {
4188         $mail_command =~ s/\$BODY_FILE//g;
4189     }
4190
4191     $mail_command =~ s/\$HEADER_FILE/$header_file/g;
4192     $mail_command =~ s/\$MAILER/$mailer/g;
4193     $mail_command =~ s/\$MAIL_PATH/$mail_path/g;
4194     $mail_command =~ s/\$MAILTO/$mailto/g;
4195     $mail_command =~ s/\$SUBJECT/$subject/g;
4196     $mail_command =~ s/\$MESSAGE/$message/g;
4197
4198     my $ret = run_command $mail_command;
4199     if (!$ret && defined($file)) {
4200         # try again without the file
4201         $message .= "\n\n*** FAILED TO SEND LOG ***\n\n";
4202         do_send_email($subject, $message);
4203     }
4204 }
4205
4206 sub send_email {
4207     if (defined($mailto)) {
4208         if (!defined($mailer)) {
4209             doprint "No email sent: email or mailer not specified in config.\n";
4210             return;
4211         }
4212         do_send_mail @_;
4213     }
4214 }
4215
4216 sub cancel_test {
4217     if ($monitor_cnt) {
4218         end_monitor;
4219     }
4220     if ($email_when_canceled) {
4221         my $name = get_test_name;
4222         send_email("KTEST: Your [$name] test was cancelled",
4223             "Your test started at $script_start_time was cancelled: sig int");
4224     }
4225     die "\nCaught Sig Int, test interrupted: $!\n"
4226 }
4227
4228 $#ARGV < 1 or die "ktest.pl version: $VERSION\n   usage: ktest.pl [config-file]\n";
4229
4230 if ($#ARGV == 0) {
4231     $ktest_config = $ARGV[0];
4232     if (! -f $ktest_config) {
4233         print "$ktest_config does not exist.\n";
4234         if (!read_yn "Create it?") {
4235             exit 0;
4236         }
4237     }
4238 }
4239
4240 if (! -f $ktest_config) {
4241     $newconfig = 1;
4242     get_test_case;
4243     open(OUT, ">$ktest_config") or die "Can not create $ktest_config";
4244     print OUT << "EOF"
4245 # Generated by ktest.pl
4246 #
4247
4248 # PWD is a ktest.pl variable that will result in the process working
4249 # directory that ktest.pl is executed in.
4250
4251 # THIS_DIR is automatically assigned the PWD of the path that generated
4252 # the config file. It is best to use this variable when assigning other
4253 # directory paths within this directory. This allows you to easily
4254 # move the test cases to other locations or to other machines.
4255 #
4256 THIS_DIR := $variable{"PWD"}
4257
4258 # Define each test with TEST_START
4259 # The config options below it will override the defaults
4260 TEST_START
4261 TEST_TYPE = $default{"TEST_TYPE"}
4262
4263 DEFAULTS
4264 EOF
4265 ;
4266     close(OUT);
4267 }
4268 read_config $ktest_config;
4269
4270 if (defined($opt{"LOG_FILE"})) {
4271     $opt{"LOG_FILE"} = eval_option("LOG_FILE", $opt{"LOG_FILE"}, -1);
4272 }
4273
4274 # Append any configs entered in manually to the config file.
4275 my @new_configs = keys %entered_configs;
4276 if ($#new_configs >= 0) {
4277     print "\nAppending entered in configs to $ktest_config\n";
4278     open(OUT, ">>$ktest_config") or die "Can not append to $ktest_config";
4279     foreach my $config (@new_configs) {
4280         print OUT "$config = $entered_configs{$config}\n";
4281         $opt{$config} = process_variables($entered_configs{$config});
4282     }
4283 }
4284
4285 if (defined($opt{"LOG_FILE"})) {
4286     if ($opt{"CLEAR_LOG"}) {
4287         unlink $opt{"LOG_FILE"};
4288     }
4289     open(LOG, ">> $opt{LOG_FILE}") or die "Can't write to $opt{LOG_FILE}";
4290     LOG->autoflush(1);
4291 }
4292
4293 doprint "\n\nSTARTING AUTOMATED TESTS\n\n";
4294
4295 for (my $i = 0, my $repeat = 1; $i <= $opt{"NUM_TESTS"}; $i += $repeat) {
4296
4297     if (!$i) {
4298         doprint "DEFAULT OPTIONS:\n";
4299     } else {
4300         doprint "\nTEST $i OPTIONS";
4301         if (defined($repeat_tests{$i})) {
4302             $repeat = $repeat_tests{$i};
4303             doprint " ITERATE $repeat";
4304         }
4305         doprint "\n";
4306     }
4307
4308     foreach my $option (sort keys %opt) {
4309         if ($option =~ /\[(\d+)\]$/) {
4310             next if ($i != $1);
4311         } else {
4312             next if ($i);
4313         }
4314
4315         doprint "$option = $opt{$option}\n";
4316     }
4317 }
4318
4319 $SIG{INT} = qw(cancel_test);
4320
4321 # First we need to do is the builds
4322 for (my $i = 1; $i <= $opt{"NUM_TESTS"}; $i++) {
4323
4324     # Do not reboot on failing test options
4325     $no_reboot = 1;
4326     $reboot_success = 0;
4327
4328     $have_version = 0;
4329
4330     $iteration = $i;
4331
4332     $build_time = 0;
4333     $install_time = 0;
4334     $reboot_time = 0;
4335     $test_time = 0;
4336
4337     undef %force_config;
4338
4339     my $makecmd = set_test_option("MAKE_CMD", $i);
4340
4341     $outputdir = set_test_option("OUTPUT_DIR", $i);
4342     $builddir = set_test_option("BUILD_DIR", $i);
4343
4344     chdir $builddir || dodie "can't change directory to $builddir";
4345
4346     if (!-d $outputdir) {
4347         mkpath($outputdir) or
4348             dodie "can't create $outputdir";
4349     }
4350
4351     $make = "$makecmd O=$outputdir";
4352
4353     # Load all the options into their mapped variable names
4354     foreach my $opt (keys %option_map) {
4355         ${$option_map{$opt}} = set_test_option($opt, $i);
4356     }
4357
4358     $start_minconfig_defined = 1;
4359
4360     # The first test may override the PRE_KTEST option
4361     if ($i == 1) {
4362         if (defined($pre_ktest)) {
4363             doprint "\n";
4364             run_command $pre_ktest;
4365         }
4366         if ($email_when_started) {
4367             my $name = get_test_name;
4368             send_email("KTEST: Your [$name] test was started",
4369                 "Your test was started on $script_start_time");
4370         }
4371     }
4372
4373     # Any test can override the POST_KTEST option
4374     # The last test takes precedence.
4375     if (defined($post_ktest)) {
4376         $final_post_ktest = $post_ktest;
4377     }
4378
4379     if (!defined($start_minconfig)) {
4380         $start_minconfig_defined = 0;
4381         $start_minconfig = $minconfig;
4382     }
4383
4384     if (!-d $tmpdir) {
4385         mkpath($tmpdir) or
4386             dodie "can't create $tmpdir";
4387     }
4388
4389     $ENV{"SSH_USER"} = $ssh_user;
4390     $ENV{"MACHINE"} = $machine;
4391
4392     $buildlog = "$tmpdir/buildlog-$machine";
4393     $testlog = "$tmpdir/testlog-$machine";
4394     $dmesg = "$tmpdir/dmesg-$machine";
4395     $output_config = "$outputdir/.config";
4396
4397     if (!$buildonly) {
4398         $target = "$ssh_user\@$machine";
4399         if (($reboot_type eq "grub") or ($reboot_type eq "grub2bls")) {
4400             dodie "GRUB_MENU not defined" if (!defined($grub_menu));
4401         } elsif ($reboot_type eq "grub2") {
4402             dodie "GRUB_MENU not defined" if (!defined($grub_menu));
4403             dodie "GRUB_FILE not defined" if (!defined($grub_file));
4404         } elsif ($reboot_type eq "syslinux") {
4405             dodie "SYSLINUX_LABEL not defined" if (!defined($syslinux_label));
4406         }
4407     }
4408
4409     my $run_type = $build_type;
4410     if ($test_type eq "patchcheck") {
4411         $run_type = $patchcheck_type;
4412     } elsif ($test_type eq "bisect") {
4413         $run_type = $bisect_type;
4414     } elsif ($test_type eq "config_bisect") {
4415         $run_type = $config_bisect_type;
4416     } elsif ($test_type eq "make_min_config") {
4417         $run_type = "";
4418     } elsif ($test_type eq "make_warnings_file") {
4419         $run_type = "";
4420     }
4421
4422     # mistake in config file?
4423     if (!defined($run_type)) {
4424         $run_type = "ERROR";
4425     }
4426
4427     my $installme = "";
4428     $installme = " no_install" if ($no_install);
4429
4430     my $name = "";
4431
4432     if (defined($test_name)) {
4433         $name = " ($test_name)";
4434     }
4435
4436     doprint "\n\n";
4437
4438     if (defined($opt{"LOG_FILE"})) {
4439         $test_log_start = tell(LOG);
4440     }
4441
4442     doprint "RUNNING TEST $i of $opt{NUM_TESTS}$name with option $test_type $run_type$installme\n\n";
4443
4444     if (defined($pre_test)) {
4445         my $ret = run_command $pre_test;
4446         if (!$ret && defined($pre_test_die) &&
4447             $pre_test_die) {
4448                 dodie "failed to pre_test\n";
4449         }
4450     }
4451
4452     unlink $dmesg;
4453     unlink $buildlog;
4454     unlink $testlog;
4455
4456     if (defined($addconfig)) {
4457         my $min = $minconfig;
4458         if (!defined($minconfig)) {
4459             $min = "";
4460         }
4461         run_command "cat $addconfig $min > $tmpdir/add_config" or
4462             dodie "Failed to create temp config";
4463         $minconfig = "$tmpdir/add_config";
4464     }
4465
4466     if (defined($checkout)) {
4467         run_command "git checkout $checkout" or
4468             dodie "failed to checkout $checkout";
4469     }
4470
4471     $no_reboot = 0;
4472
4473     # A test may opt to not reboot the box
4474     if ($reboot_on_success) {
4475         $reboot_success = 1;
4476     }
4477
4478     if ($test_type eq "bisect") {
4479         bisect $i;
4480         next;
4481     } elsif ($test_type eq "config_bisect") {
4482         config_bisect $i;
4483         next;
4484     } elsif ($test_type eq "patchcheck") {
4485         patchcheck $i;
4486         next;
4487     } elsif ($test_type eq "make_min_config") {
4488         make_min_config $i;
4489         next;
4490     } elsif ($test_type eq "make_warnings_file") {
4491         $no_reboot = 1;
4492         make_warnings_file $i;
4493         next;
4494     }
4495
4496     if ($build_type ne "nobuild") {
4497         build $build_type or next;
4498         check_buildlog or next;
4499     }
4500
4501     if ($test_type eq "install") {
4502         get_version;
4503         install;
4504         success $i;
4505         next;
4506     }
4507
4508     if ($test_type ne "build") {
4509         my $failed = 0;
4510         start_monitor_and_install or $failed = 1;
4511
4512         if (!$failed && $test_type ne "boot" && defined($run_test)) {
4513             do_run_test or $failed = 1;
4514         }
4515         end_monitor;
4516         if ($failed) {
4517             print_times;
4518             next;
4519         }
4520     }
4521
4522     print_times;
4523
4524     success $i;
4525 }
4526
4527 if (defined($final_post_ktest)) {
4528
4529     my $cp_final_post_ktest = eval_kernel_version $final_post_ktest;
4530     run_command $cp_final_post_ktest;
4531 }
4532
4533 if ($opt{"POWEROFF_ON_SUCCESS"}) {
4534     halt;
4535 } elsif ($opt{"REBOOT_ON_SUCCESS"} && !do_not_reboot && $reboot_success) {
4536     reboot_to_good;
4537 } elsif (defined($switch_to_good)) {
4538     # still need to get to the good kernel
4539     run_command $switch_to_good;
4540 }
4541
4542 doprint "\n    $successes of $opt{NUM_TESTS} tests were successful\n\n";
4543
4544 if ($email_when_finished) {
4545     send_email("KTEST: Your test has finished!",
4546         "$successes of $opt{NUM_TESTS} tests started at $script_start_time were successful!");
4547 }
4548
4549 if (defined($opt{"LOG_FILE"})) {
4550     print "\n See $opt{LOG_FILE} for the record of results.\n\n";
4551     close LOG;
4552 }
4553
4554 exit 0;
4555
4556 ##
4557 # The following are here to standardize tabs/spaces/etc across the most likely editors
4558 ###
4559
4560 # Local Variables:
4561 # mode: perl
4562 # End:
4563 # vim: softtabstop=4