blob: c76e18f00c4479528c51d1ab489ec5d4f86e9648 [file] [log] [blame]
Steven Rostedt2545eb62010-11-02 15:01:32 -04001#!/usr/bin/perl -w
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04002#
Uwe Kleine-Königcce1dac2011-01-24 21:12:01 +01003# Copyright 2010 - Steven Rostedt <srostedt@redhat.com>, Red Hat Inc.
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04004# Licensed under the terms of the GNU GPL License version 2
5#
Steven Rostedt2545eb62010-11-02 15:01:32 -04006
7use strict;
8use IPC::Open2;
9use Fcntl qw(F_GETFL F_SETFL O_NONBLOCK);
Steven Rostedt7faafbd2010-11-02 14:58:22 -040010use File::Path qw(mkpath);
11use File::Copy qw(cp);
Steven Rostedt2545eb62010-11-02 15:01:32 -040012use FileHandle;
13
Steven Rostedte48c5292010-11-02 14:35:37 -040014my $VERSION = "0.2";
15
Steven Rostedt2545eb62010-11-02 15:01:32 -040016$| = 1;
17
18my %opt;
Steven Rostedta57419b2010-11-02 15:13:54 -040019my %repeat_tests;
20my %repeats;
Steven Rostedta75fece2010-11-02 14:58:27 -040021my %default;
Steven Rostedt2545eb62010-11-02 15:01:32 -040022
23#default opts
Steven Rostedta57419b2010-11-02 15:13:54 -040024$default{"NUM_TESTS"} = 1;
Steven Rostedta75fece2010-11-02 14:58:27 -040025$default{"REBOOT_TYPE"} = "grub";
26$default{"TEST_TYPE"} = "test";
27$default{"BUILD_TYPE"} = "randconfig";
28$default{"MAKE_CMD"} = "make";
29$default{"TIMEOUT"} = 120;
Steven Rostedt48920632011-06-14 20:42:19 -040030$default{"TMP_DIR"} = "/tmp/ktest/\${MACHINE}";
Steven Rostedta75fece2010-11-02 14:58:27 -040031$default{"SLEEP_TIME"} = 60; # sleep time between tests
32$default{"BUILD_NOCLEAN"} = 0;
33$default{"REBOOT_ON_ERROR"} = 0;
34$default{"POWEROFF_ON_ERROR"} = 0;
35$default{"REBOOT_ON_SUCCESS"} = 1;
36$default{"POWEROFF_ON_SUCCESS"} = 0;
37$default{"BUILD_OPTIONS"} = "";
38$default{"BISECT_SLEEP_TIME"} = 60; # sleep time between bisects
Steven Rostedt27d934b2011-05-20 09:18:18 -040039$default{"PATCHCHECK_SLEEP_TIME"} = 60; # sleep time between patch checks
Steven Rostedta75fece2010-11-02 14:58:27 -040040$default{"CLEAR_LOG"} = 0;
Steven Rostedtc960bb92011-03-08 09:22:39 -050041$default{"BISECT_MANUAL"} = 0;
Steven Rostedtc23dca72011-03-08 09:26:31 -050042$default{"BISECT_SKIP"} = 1;
Steven Rostedta75fece2010-11-02 14:58:27 -040043$default{"SUCCESS_LINE"} = "login:";
Steven Rostedtf1a5b962011-06-13 10:30:00 -040044$default{"DETECT_TRIPLE_FAULT"} = 1;
Steven Rostedte0a87422011-09-30 17:50:48 -040045$default{"NO_INSTALL"} = 0;
Steven Rostedta75fece2010-11-02 14:58:27 -040046$default{"BOOTED_TIMEOUT"} = 1;
47$default{"DIE_ON_FAILURE"} = 1;
Steven Rostedte48c5292010-11-02 14:35:37 -040048$default{"SSH_EXEC"} = "ssh \$SSH_USER\@\$MACHINE \$SSH_COMMAND";
49$default{"SCP_TO_TARGET"} = "scp \$SRC_FILE \$SSH_USER\@\$MACHINE:\$DST_FILE";
50$default{"REBOOT"} = "ssh \$SSH_USER\@\$MACHINE reboot";
Steven Rostedt1c8a6172010-11-09 12:55:40 -050051$default{"STOP_AFTER_SUCCESS"} = 10;
52$default{"STOP_AFTER_FAILURE"} = 60;
Steven Rostedt2d01b262011-03-08 09:47:54 -050053$default{"STOP_TEST_AFTER"} = 600;
Steven Rostedt8d1491b2010-11-18 15:39:48 -050054$default{"LOCALVERSION"} = "-test";
Steven Rostedt2545eb62010-11-02 15:01:32 -040055
Steven Rostedt8d1491b2010-11-18 15:39:48 -050056my $ktest_config;
Steven Rostedt2545eb62010-11-02 15:01:32 -040057my $version;
Steven Rostedta75fece2010-11-02 14:58:27 -040058my $machine;
Steven Rostedte48c5292010-11-02 14:35:37 -040059my $ssh_user;
Steven Rostedta75fece2010-11-02 14:58:27 -040060my $tmpdir;
61my $builddir;
62my $outputdir;
Steven Rostedt51ad1dd2010-11-08 16:43:21 -050063my $output_config;
Steven Rostedta75fece2010-11-02 14:58:27 -040064my $test_type;
Steven Rostedt7faafbd2010-11-02 14:58:22 -040065my $build_type;
Steven Rostedta75fece2010-11-02 14:58:27 -040066my $build_options;
Steven Rostedt0bd6c1a2011-06-14 20:39:31 -040067my $pre_build;
68my $post_build;
69my $pre_build_die;
70my $post_build_die;
Steven Rostedta75fece2010-11-02 14:58:27 -040071my $reboot_type;
72my $reboot_script;
73my $power_cycle;
Steven Rostedte48c5292010-11-02 14:35:37 -040074my $reboot;
Steven Rostedta75fece2010-11-02 14:58:27 -040075my $reboot_on_error;
76my $poweroff_on_error;
77my $die_on_failure;
Steven Rostedt576f6272010-11-02 14:58:38 -040078my $powercycle_after_reboot;
79my $poweroff_after_halt;
Steven Rostedte48c5292010-11-02 14:35:37 -040080my $ssh_exec;
81my $scp_to_target;
Steven Rostedta75fece2010-11-02 14:58:27 -040082my $power_off;
83my $grub_menu;
Steven Rostedt2545eb62010-11-02 15:01:32 -040084my $grub_number;
85my $target;
86my $make;
Steven Rostedt8b37ca82010-11-02 14:58:33 -040087my $post_install;
Steven Rostedte0a87422011-09-30 17:50:48 -040088my $no_install;
Steven Rostedt5c42fc52010-11-02 14:57:01 -040089my $noclean;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -040090my $minconfig;
Steven Rostedt4c4ab122011-07-15 21:16:17 -040091my $start_minconfig;
Steven Rostedt35ce5952011-07-15 21:57:25 -040092my $start_minconfig_defined;
Steven Rostedt4c4ab122011-07-15 21:16:17 -040093my $output_minconfig;
94my $ignore_config;
Steven Rostedt2b7d9b22010-11-02 14:58:15 -040095my $addconfig;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -040096my $in_bisect = 0;
97my $bisect_bad = "";
Steven Rostedtd6ce2a02010-11-02 14:58:05 -040098my $reverse_bisect;
Steven Rostedtc960bb92011-03-08 09:22:39 -050099my $bisect_manual;
Steven Rostedtc23dca72011-03-08 09:26:31 -0500100my $bisect_skip;
Steven Rostedt30f75da2011-06-13 10:35:35 -0400101my $config_bisect_good;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -0400102my $in_patchcheck = 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -0400103my $run_test;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -0400104my $redirect;
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400105my $buildlog;
106my $dmesg;
107my $monitor_fp;
108my $monitor_pid;
109my $monitor_cnt = 0;
Steven Rostedta75fece2010-11-02 14:58:27 -0400110my $sleep_time;
111my $bisect_sleep_time;
Steven Rostedt27d934b2011-05-20 09:18:18 -0400112my $patchcheck_sleep_time;
Steven Rostedt19902072011-06-14 20:46:25 -0400113my $ignore_warnings;
Steven Rostedta75fece2010-11-02 14:58:27 -0400114my $store_failures;
Steven Rostedt9064af52011-06-13 10:38:48 -0400115my $test_name;
Steven Rostedta75fece2010-11-02 14:58:27 -0400116my $timeout;
117my $booted_timeout;
Steven Rostedtf1a5b962011-06-13 10:30:00 -0400118my $detect_triplefault;
Steven Rostedta75fece2010-11-02 14:58:27 -0400119my $console;
Steven Rostedt2b803362011-09-30 18:00:23 -0400120my $reboot_success_line;
Steven Rostedta75fece2010-11-02 14:58:27 -0400121my $success_line;
Steven Rostedt1c8a6172010-11-09 12:55:40 -0500122my $stop_after_success;
123my $stop_after_failure;
Steven Rostedt2d01b262011-03-08 09:47:54 -0500124my $stop_test_after;
Steven Rostedta75fece2010-11-02 14:58:27 -0400125my $build_target;
126my $target_image;
127my $localversion;
Steven Rostedt576f6272010-11-02 14:58:38 -0400128my $iteration = 0;
Steven Rostedte48c5292010-11-02 14:35:37 -0400129my $successes = 0;
Steven Rostedt2545eb62010-11-02 15:01:32 -0400130
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500131my %entered_configs;
132my %config_help;
Steven Rostedt77d942c2011-05-20 13:36:58 -0400133my %variable;
Steven Rostedtfcb3f162011-06-13 10:40:58 -0400134my %force_config;
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500135
Steven Rostedt4ab1cce2011-09-30 18:12:20 -0400136# do not force reboots on config problems
137my $no_reboot = 1;
138
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500139$config_help{"MACHINE"} = << "EOF"
140 The machine hostname that you will test.
141EOF
142 ;
143$config_help{"SSH_USER"} = << "EOF"
144 The box is expected to have ssh on normal bootup, provide the user
145 (most likely root, since you need privileged operations)
146EOF
147 ;
148$config_help{"BUILD_DIR"} = << "EOF"
149 The directory that contains the Linux source code (full path).
150EOF
151 ;
152$config_help{"OUTPUT_DIR"} = << "EOF"
153 The directory that the objects will be built (full path).
154 (can not be same as BUILD_DIR)
155EOF
156 ;
157$config_help{"BUILD_TARGET"} = << "EOF"
158 The location of the compiled file to copy to the target.
159 (relative to OUTPUT_DIR)
160EOF
161 ;
162$config_help{"TARGET_IMAGE"} = << "EOF"
163 The place to put your image on the test machine.
164EOF
165 ;
166$config_help{"POWER_CYCLE"} = << "EOF"
167 A script or command to reboot the box.
168
169 Here is a digital loggers power switch example
170 POWER_CYCLE = wget --no-proxy -O /dev/null -q --auth-no-challenge 'http://admin:admin\@power/outlet?5=CCL'
171
172 Here is an example to reboot a virtual box on the current host
173 with the name "Guest".
174 POWER_CYCLE = virsh destroy Guest; sleep 5; virsh start Guest
175EOF
176 ;
177$config_help{"CONSOLE"} = << "EOF"
178 The script or command that reads the console
179
180 If you use ttywatch server, something like the following would work.
181CONSOLE = nc -d localhost 3001
182
183 For a virtual machine with guest name "Guest".
184CONSOLE = virsh console Guest
185EOF
186 ;
187$config_help{"LOCALVERSION"} = << "EOF"
188 Required version ending to differentiate the test
189 from other linux builds on the system.
190EOF
191 ;
192$config_help{"REBOOT_TYPE"} = << "EOF"
193 Way to reboot the box to the test kernel.
194 Only valid options so far are "grub" and "script".
195
196 If you specify grub, it will assume grub version 1
197 and will search in /boot/grub/menu.lst for the title \$GRUB_MENU
198 and select that target to reboot to the kernel. If this is not
199 your setup, then specify "script" and have a command or script
200 specified in REBOOT_SCRIPT to boot to the target.
201
202 The entry in /boot/grub/menu.lst must be entered in manually.
203 The test will not modify that file.
204EOF
205 ;
206$config_help{"GRUB_MENU"} = << "EOF"
207 The grub title name for the test kernel to boot
208 (Only mandatory if REBOOT_TYPE = grub)
209
210 Note, ktest.pl will not update the grub menu.lst, you need to
211 manually add an option for the test. ktest.pl will search
212 the grub menu.lst for this option to find what kernel to
213 reboot into.
214
215 For example, if in the /boot/grub/menu.lst the test kernel title has:
216 title Test Kernel
217 kernel vmlinuz-test
218 GRUB_MENU = Test Kernel
219EOF
220 ;
221$config_help{"REBOOT_SCRIPT"} = << "EOF"
222 A script to reboot the target into the test kernel
223 (Only mandatory if REBOOT_TYPE = script)
224EOF
225 ;
226
Steven Rostedt35ce5952011-07-15 21:57:25 -0400227sub read_yn {
228 my ($prompt) = @_;
229
230 my $ans;
231
232 for (;;) {
233 print "$prompt [Y/n] ";
234 $ans = <STDIN>;
235 chomp $ans;
236 if ($ans =~ /^\s*$/) {
237 $ans = "y";
238 }
239 last if ($ans =~ /^y$/i || $ans =~ /^n$/i);
240 print "Please answer either 'y' or 'n'.\n";
241 }
242 if ($ans !~ /^y$/i) {
243 return 0;
244 }
245 return 1;
246}
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500247
248sub get_ktest_config {
249 my ($config) = @_;
250
251 return if (defined($opt{$config}));
252
253 if (defined($config_help{$config})) {
254 print "\n";
255 print $config_help{$config};
256 }
257
258 for (;;) {
259 print "$config = ";
260 if (defined($default{$config})) {
261 print "\[$default{$config}\] ";
262 }
263 $entered_configs{$config} = <STDIN>;
264 $entered_configs{$config} =~ s/^\s*(.*\S)\s*$/$1/;
265 if ($entered_configs{$config} =~ /^\s*$/) {
266 if ($default{$config}) {
267 $entered_configs{$config} = $default{$config};
268 } else {
269 print "Your answer can not be blank\n";
270 next;
271 }
272 }
273 last;
274 }
275}
276
277sub get_ktest_configs {
278 get_ktest_config("MACHINE");
279 get_ktest_config("SSH_USER");
280 get_ktest_config("BUILD_DIR");
281 get_ktest_config("OUTPUT_DIR");
282 get_ktest_config("BUILD_TARGET");
283 get_ktest_config("TARGET_IMAGE");
284 get_ktest_config("POWER_CYCLE");
285 get_ktest_config("CONSOLE");
286 get_ktest_config("LOCALVERSION");
287
288 my $rtype = $opt{"REBOOT_TYPE"};
289
290 if (!defined($rtype)) {
291 if (!defined($opt{"GRUB_MENU"})) {
292 get_ktest_config("REBOOT_TYPE");
293 $rtype = $entered_configs{"REBOOT_TYPE"};
294 } else {
295 $rtype = "grub";
296 }
297 }
298
299 if ($rtype eq "grub") {
300 get_ktest_config("GRUB_MENU");
301 } else {
302 get_ktest_config("REBOOT_SCRIPT");
303 }
304}
305
Steven Rostedt77d942c2011-05-20 13:36:58 -0400306sub process_variables {
307 my ($value) = @_;
308 my $retval = "";
309
310 # We want to check for '\', and it is just easier
311 # to check the previous characet of '$' and not need
312 # to worry if '$' is the first character. By adding
313 # a space to $value, we can just check [^\\]\$ and
314 # it will still work.
315 $value = " $value";
316
317 while ($value =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
318 my $begin = $1;
319 my $var = $2;
320 my $end = $3;
321 # append beginning of value to retval
322 $retval = "$retval$begin";
323 if (defined($variable{$var})) {
324 $retval = "$retval$variable{$var}";
325 } else {
326 # put back the origin piece.
327 $retval = "$retval\$\{$var\}";
328 }
329 $value = $end;
330 }
331 $retval = "$retval$value";
332
333 # remove the space added in the beginning
334 $retval =~ s/ //;
335
336 return "$retval"
337}
338
Steven Rostedta57419b2010-11-02 15:13:54 -0400339sub set_value {
340 my ($lvalue, $rvalue) = @_;
341
342 if (defined($opt{$lvalue})) {
343 die "Error: Option $lvalue defined more than once!\n";
344 }
Steven Rostedt21a96792010-11-08 16:45:50 -0500345 if ($rvalue =~ /^\s*$/) {
346 delete $opt{$lvalue};
347 } else {
Steven Rostedt77d942c2011-05-20 13:36:58 -0400348 $rvalue = process_variables($rvalue);
Steven Rostedt21a96792010-11-08 16:45:50 -0500349 $opt{$lvalue} = $rvalue;
350 }
Steven Rostedta57419b2010-11-02 15:13:54 -0400351}
352
Steven Rostedt77d942c2011-05-20 13:36:58 -0400353sub set_variable {
354 my ($lvalue, $rvalue) = @_;
355
356 if ($rvalue =~ /^\s*$/) {
357 delete $variable{$lvalue};
358 } else {
359 $rvalue = process_variables($rvalue);
360 $variable{$lvalue} = $rvalue;
361 }
362}
363
Steven Rostedt45d73a52011-09-30 19:44:53 -0400364sub process_if {
365 my ($name, $value) = @_;
366
367 my $val = process_variables($value);
368
369 if ($val =~ /^\s*0\s*$/) {
370 return 0;
371 } elsif ($val =~ /^\s*\d+\s*$/) {
372 return 1;
373 }
374
375 die ("$name: $.: Undefined variable $val in if statement\n");
376 return 1;
377}
378
Steven Rostedt2545eb62010-11-02 15:01:32 -0400379sub read_config {
380 my ($config) = @_;
381
382 open(IN, $config) || die "can't read file $config";
383
Steven Rostedta57419b2010-11-02 15:13:54 -0400384 my $name = $config;
385 $name =~ s,.*/(.*),$1,;
386
387 my $test_num = 0;
388 my $default = 1;
389 my $repeat = 1;
390 my $num_tests_set = 0;
391 my $skip = 0;
392 my $rest;
Steven Rostedt0df213c2011-06-14 20:51:37 -0400393 my $test_case = 0;
Steven Rostedt45d73a52011-09-30 19:44:53 -0400394 my $if = 0;
395 my $if_set = 0;
Steven Rostedta57419b2010-11-02 15:13:54 -0400396
Steven Rostedt2545eb62010-11-02 15:01:32 -0400397 while (<IN>) {
398
399 # ignore blank lines and comments
400 next if (/^\s*$/ || /\s*\#/);
401
Steven Rostedta57419b2010-11-02 15:13:54 -0400402 if (/^\s*TEST_START(.*)/) {
403
404 $rest = $1;
405
406 if ($num_tests_set) {
407 die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
408 }
409
410 my $old_test_num = $test_num;
Steven Rostedte48c5292010-11-02 14:35:37 -0400411 my $old_repeat = $repeat;
Steven Rostedta57419b2010-11-02 15:13:54 -0400412
413 $test_num += $repeat;
414 $default = 0;
415 $repeat = 1;
416
Steven Rostedt45d73a52011-09-30 19:44:53 -0400417 if ($rest =~ /\s+SKIP\b(.*)/) {
Steven Rostedta57419b2010-11-02 15:13:54 -0400418 $rest = $1;
419 $skip = 1;
420 } else {
Steven Rostedt0df213c2011-06-14 20:51:37 -0400421 $test_case = 1;
Steven Rostedta57419b2010-11-02 15:13:54 -0400422 $skip = 0;
423 }
424
425 if ($rest =~ /\s+ITERATE\s+(\d+)(.*)$/) {
426 $repeat = $1;
427 $rest = $2;
428 $repeat_tests{"$test_num"} = $repeat;
429 }
430
Steven Rostedt45d73a52011-09-30 19:44:53 -0400431 if ($rest =~ /\sIF\s+(\S*)(.*)/) {
432 $rest = $2;
433 if (process_if($name, $1)) {
434 $if_set = 1;
435 } else {
436 $skip = 1;
437 }
438 $if = 1;
439 } else {
440 $if = 0;
Steven Rostedta57419b2010-11-02 15:13:54 -0400441 }
442
443 if ($rest !~ /^\s*$/) {
444 die "$name: $.: Gargbage found after TEST_START\n$_";
445 }
446
447 if ($skip) {
448 $test_num = $old_test_num;
Steven Rostedte48c5292010-11-02 14:35:37 -0400449 $repeat = $old_repeat;
Steven Rostedta57419b2010-11-02 15:13:54 -0400450 }
451
452 } elsif (/^\s*DEFAULTS(.*)$/) {
453 $default = 1;
454
455 $rest = $1;
456
457 if ($rest =~ /\s+SKIP(.*)/) {
458 $rest = $1;
459 $skip = 1;
460 } else {
461 $skip = 0;
462 }
463
Steven Rostedt45d73a52011-09-30 19:44:53 -0400464 if ($rest =~ /\sIF\s+(\S*)(.*)/) {
465 $if = 1;
466 $rest = $2;
467 if (process_if($name, $1)) {
468 $if_set = 1;
469 } else {
470 $skip = 1;
471 }
472 } else {
473 $if = 0;
474 }
475
Steven Rostedta57419b2010-11-02 15:13:54 -0400476 if ($rest !~ /^\s*$/) {
477 die "$name: $.: Gargbage found after DEFAULTS\n$_";
478 }
479
Steven Rostedt45d73a52011-09-30 19:44:53 -0400480 } elsif (/^\s*ELSE(.*)$/) {
481 if (!$if) {
482 die "$name: $.: ELSE found with out matching IF section\n$_";
483 }
484 $rest = $1;
485 if ($if_set) {
486 $skip = 1;
487 } else {
488 $skip = 0;
489
490 if ($rest =~ /\sIF\s+(\S*)(.*)/) {
491 # May be a ELSE IF section.
492 if (!process_if($name, $1)) {
493 $skip = 1;
494 }
495 } else {
496 $if = 0;
497 }
498 }
499
Steven Rostedta57419b2010-11-02 15:13:54 -0400500 } elsif (/^\s*([A-Z_\[\]\d]+)\s*=\s*(.*?)\s*$/) {
501
502 next if ($skip);
503
Steven Rostedt2545eb62010-11-02 15:01:32 -0400504 my $lvalue = $1;
505 my $rvalue = $2;
506
Steven Rostedta57419b2010-11-02 15:13:54 -0400507 if (!$default &&
508 ($lvalue eq "NUM_TESTS" ||
509 $lvalue eq "LOG_FILE" ||
510 $lvalue eq "CLEAR_LOG")) {
511 die "$name: $.: $lvalue must be set in DEFAULTS section\n";
Steven Rostedta75fece2010-11-02 14:58:27 -0400512 }
Steven Rostedta57419b2010-11-02 15:13:54 -0400513
514 if ($lvalue eq "NUM_TESTS") {
515 if ($test_num) {
516 die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
517 }
518 if (!$default) {
519 die "$name: $.: NUM_TESTS must be set in default section\n";
520 }
521 $num_tests_set = 1;
522 }
523
524 if ($default || $lvalue =~ /\[\d+\]$/) {
525 set_value($lvalue, $rvalue);
526 } else {
527 my $val = "$lvalue\[$test_num\]";
528 set_value($val, $rvalue);
529
530 if ($repeat > 1) {
531 $repeats{$val} = $repeat;
532 }
533 }
Steven Rostedt77d942c2011-05-20 13:36:58 -0400534 } elsif (/^\s*([A-Z_\[\]\d]+)\s*:=\s*(.*?)\s*$/) {
535 next if ($skip);
536
537 my $lvalue = $1;
538 my $rvalue = $2;
539
540 # process config variables.
541 # Config variables are only active while reading the
542 # config and can be defined anywhere. They also ignore
543 # TEST_START and DEFAULTS, but are skipped if they are in
544 # on of these sections that have SKIP defined.
545 # The save variable can be
546 # defined multiple times and the new one simply overrides
547 # the prevous one.
548 set_variable($lvalue, $rvalue);
549
Steven Rostedta57419b2010-11-02 15:13:54 -0400550 } else {
551 die "$name: $.: Garbage found in config\n$_";
Steven Rostedt2545eb62010-11-02 15:01:32 -0400552 }
553 }
554
555 close(IN);
Steven Rostedta75fece2010-11-02 14:58:27 -0400556
Steven Rostedta57419b2010-11-02 15:13:54 -0400557 if ($test_num) {
558 $test_num += $repeat - 1;
559 $opt{"NUM_TESTS"} = $test_num;
560 }
561
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500562 # make sure we have all mandatory configs
563 get_ktest_configs;
564
Steven Rostedt0df213c2011-06-14 20:51:37 -0400565 # was a test specified?
566 if (!$test_case) {
567 print "No test case specified.\n";
568 print "What test case would you like to run?\n";
569 my $ans = <STDIN>;
570 chomp $ans;
571 $default{"TEST_TYPE"} = $ans;
572 }
573
Steven Rostedta75fece2010-11-02 14:58:27 -0400574 # set any defaults
575
576 foreach my $default (keys %default) {
577 if (!defined($opt{$default})) {
578 $opt{$default} = $default{$default};
579 }
580 }
Steven Rostedt2545eb62010-11-02 15:01:32 -0400581}
582
Steven Rostedt23715c3c2011-06-13 11:03:34 -0400583sub __eval_option {
584 my ($option, $i) = @_;
585
586 # Add space to evaluate the character before $
587 $option = " $option";
588 my $retval = "";
589
590 while ($option =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
591 my $start = $1;
592 my $var = $2;
593 my $end = $3;
594
595 # Append beginning of line
596 $retval = "$retval$start";
597
598 # If the iteration option OPT[$i] exists, then use that.
599 # otherwise see if the default OPT (without [$i]) exists.
600
601 my $o = "$var\[$i\]";
602
603 if (defined($opt{$o})) {
604 $o = $opt{$o};
605 $retval = "$retval$o";
606 } elsif (defined($opt{$var})) {
607 $o = $opt{$var};
608 $retval = "$retval$o";
609 } else {
610 $retval = "$retval\$\{$var\}";
611 }
612
613 $option = $end;
614 }
615
616 $retval = "$retval$option";
617
618 $retval =~ s/^ //;
619
620 return $retval;
621}
622
623sub eval_option {
624 my ($option, $i) = @_;
625
626 my $prev = "";
627
628 # Since an option can evaluate to another option,
629 # keep iterating until we do not evaluate any more
630 # options.
631 my $r = 0;
632 while ($prev ne $option) {
633 # Check for recursive evaluations.
634 # 100 deep should be more than enough.
635 if ($r++ > 100) {
636 die "Over 100 evaluations accurred with $option\n" .
637 "Check for recursive variables\n";
638 }
639 $prev = $option;
640 $option = __eval_option($option, $i);
641 }
642
643 return $option;
644}
645
Steven Rostedtd1e2f222010-11-08 16:39:57 -0500646sub _logit {
Steven Rostedt2545eb62010-11-02 15:01:32 -0400647 if (defined($opt{"LOG_FILE"})) {
648 open(OUT, ">> $opt{LOG_FILE}") or die "Can't write to $opt{LOG_FILE}";
649 print OUT @_;
650 close(OUT);
651 }
652}
653
Steven Rostedtd1e2f222010-11-08 16:39:57 -0500654sub logit {
655 if (defined($opt{"LOG_FILE"})) {
656 _logit @_;
657 } else {
658 print @_;
659 }
660}
661
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400662sub doprint {
663 print @_;
Steven Rostedtd1e2f222010-11-08 16:39:57 -0500664 _logit @_;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400665}
666
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400667sub run_command;
Andrew Jones2728be42011-08-12 15:32:05 +0200668sub start_monitor;
669sub end_monitor;
670sub wait_for_monitor;
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400671
672sub reboot {
Andrew Jones2728be42011-08-12 15:32:05 +0200673 my ($time) = @_;
674
Steven Rostedt2b803362011-09-30 18:00:23 -0400675 if (defined($time)) {
676 start_monitor;
677 # flush out current monitor
678 # May contain the reboot success line
679 wait_for_monitor 1;
680 }
681
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400682 # try to reboot normally
Steven Rostedte48c5292010-11-02 14:35:37 -0400683 if (run_command $reboot) {
Steven Rostedt576f6272010-11-02 14:58:38 -0400684 if (defined($powercycle_after_reboot)) {
685 sleep $powercycle_after_reboot;
686 run_command "$power_cycle";
687 }
688 } else {
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400689 # nope? power cycle it.
Steven Rostedta75fece2010-11-02 14:58:27 -0400690 run_command "$power_cycle";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400691 }
Andrew Jones2728be42011-08-12 15:32:05 +0200692
693 if (defined($time)) {
Steven Rostedt2b803362011-09-30 18:00:23 -0400694 wait_for_monitor($time, $reboot_success_line);
Andrew Jones2728be42011-08-12 15:32:05 +0200695 end_monitor;
696 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400697}
698
Steven Rostedt576f6272010-11-02 14:58:38 -0400699sub do_not_reboot {
700 my $i = $iteration;
701
Steven Rostedt4ab1cce2011-09-30 18:12:20 -0400702 return $test_type eq "build" || $no_reboot ||
Steven Rostedt576f6272010-11-02 14:58:38 -0400703 ($test_type eq "patchcheck" && $opt{"PATCHCHECK_TYPE[$i]"} eq "build") ||
704 ($test_type eq "bisect" && $opt{"BISECT_TYPE[$i]"} eq "build");
705}
706
Steven Rostedt5c42fc52010-11-02 14:57:01 -0400707sub dodie {
Steven Rostedt5a391fb2010-11-02 14:57:43 -0400708 doprint "CRITICAL FAILURE... ", @_, "\n";
Steven Rostedt5c42fc52010-11-02 14:57:01 -0400709
Steven Rostedt576f6272010-11-02 14:58:38 -0400710 my $i = $iteration;
711
712 if ($reboot_on_error && !do_not_reboot) {
713
Steven Rostedt75c3fda72010-11-02 14:57:21 -0400714 doprint "REBOOTING\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400715 reboot;
Steven Rostedt75c3fda72010-11-02 14:57:21 -0400716
Steven Rostedta75fece2010-11-02 14:58:27 -0400717 } elsif ($poweroff_on_error && defined($power_off)) {
Steven Rostedt5c42fc52010-11-02 14:57:01 -0400718 doprint "POWERING OFF\n";
Steven Rostedta75fece2010-11-02 14:58:27 -0400719 `$power_off`;
Steven Rostedt5c42fc52010-11-02 14:57:01 -0400720 }
Steven Rostedt75c3fda72010-11-02 14:57:21 -0400721
Steven Rostedtf80802c2011-03-07 13:18:47 -0500722 if (defined($opt{"LOG_FILE"})) {
723 print " See $opt{LOG_FILE} for more info.\n";
724 }
725
Steven Rostedt576f6272010-11-02 14:58:38 -0400726 die @_, "\n";
Steven Rostedt5c42fc52010-11-02 14:57:01 -0400727}
728
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400729sub open_console {
730 my ($fp) = @_;
731
732 my $flags;
733
Steven Rostedta75fece2010-11-02 14:58:27 -0400734 my $pid = open($fp, "$console|") or
735 dodie "Can't open console $console";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400736
737 $flags = fcntl($fp, F_GETFL, 0) or
Steven Rostedt576f6272010-11-02 14:58:38 -0400738 dodie "Can't get flags for the socket: $!";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400739 $flags = fcntl($fp, F_SETFL, $flags | O_NONBLOCK) or
Steven Rostedt576f6272010-11-02 14:58:38 -0400740 dodie "Can't set flags for the socket: $!";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400741
742 return $pid;
743}
744
745sub close_console {
746 my ($fp, $pid) = @_;
747
748 doprint "kill child process $pid\n";
749 kill 2, $pid;
750
751 print "closing!\n";
752 close($fp);
753}
754
755sub start_monitor {
756 if ($monitor_cnt++) {
757 return;
758 }
759 $monitor_fp = \*MONFD;
760 $monitor_pid = open_console $monitor_fp;
Steven Rostedta75fece2010-11-02 14:58:27 -0400761
762 return;
763
764 open(MONFD, "Stop perl from warning about single use of MONFD");
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400765}
766
767sub end_monitor {
768 if (--$monitor_cnt) {
769 return;
770 }
771 close_console($monitor_fp, $monitor_pid);
772}
773
774sub wait_for_monitor {
Steven Rostedt2b803362011-09-30 18:00:23 -0400775 my ($time, $stop) = @_;
776 my $full_line = "";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400777 my $line;
Steven Rostedt2b803362011-09-30 18:00:23 -0400778 my $booted = 0;
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400779
Steven Rostedta75fece2010-11-02 14:58:27 -0400780 doprint "** Wait for monitor to settle down **\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400781
782 # read the monitor and wait for the system to calm down
Steven Rostedt2b803362011-09-30 18:00:23 -0400783 while (!$booted) {
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400784 $line = wait_for_input($monitor_fp, $time);
Steven Rostedt2b803362011-09-30 18:00:23 -0400785 last if (!defined($line));
786 print "$line";
787 $full_line .= $line;
788
789 if (defined($stop) && $full_line =~ /$stop/) {
790 doprint "wait for monitor detected $stop\n";
791 $booted = 1;
792 }
793
794 if ($line =~ /\n/) {
795 $full_line = "";
796 }
797 }
Steven Rostedta75fece2010-11-02 14:58:27 -0400798 print "** Monitor flushed **\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400799}
800
Steven Rostedt2b7d9b22010-11-02 14:58:15 -0400801sub fail {
802
Steven Rostedta75fece2010-11-02 14:58:27 -0400803 if ($die_on_failure) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -0400804 dodie @_;
805 }
806
Steven Rostedta75fece2010-11-02 14:58:27 -0400807 doprint "FAILED\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400808
Steven Rostedt576f6272010-11-02 14:58:38 -0400809 my $i = $iteration;
810
Steven Rostedta75fece2010-11-02 14:58:27 -0400811 # no need to reboot for just building.
Steven Rostedt576f6272010-11-02 14:58:38 -0400812 if (!do_not_reboot) {
Steven Rostedta75fece2010-11-02 14:58:27 -0400813 doprint "REBOOTING\n";
Andrew Jones2728be42011-08-12 15:32:05 +0200814 reboot $sleep_time;
Steven Rostedta75fece2010-11-02 14:58:27 -0400815 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400816
Steven Rostedt9064af52011-06-13 10:38:48 -0400817 my $name = "";
818
819 if (defined($test_name)) {
820 $name = " ($test_name)";
821 }
822
Steven Rostedt576f6272010-11-02 14:58:38 -0400823 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
824 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
Steven Rostedt9064af52011-06-13 10:38:48 -0400825 doprint "KTEST RESULT: TEST $i$name Failed: ", @_, "\n";
Steven Rostedt576f6272010-11-02 14:58:38 -0400826 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
827 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
Steven Rostedta75fece2010-11-02 14:58:27 -0400828
829 return 1 if (!defined($store_failures));
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400830
831 my @t = localtime;
832 my $date = sprintf "%04d%02d%02d%02d%02d%02d",
833 1900+$t[5],$t[4],$t[3],$t[2],$t[1],$t[0];
834
Steven Rostedtcccae1a2010-11-09 12:21:32 -0500835 my $type = $build_type;
836 if ($type =~ /useconfig/) {
837 $type = "useconfig";
838 }
839
840 my $dir = "$machine-$test_type-$type-fail-$date";
Steven Rostedta75fece2010-11-02 14:58:27 -0400841 my $faildir = "$store_failures/$dir";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400842
843 if (!-d $faildir) {
844 mkpath($faildir) or
Steven Rostedta75fece2010-11-02 14:58:27 -0400845 die "can't create $faildir";
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400846 }
Steven Rostedt51ad1dd2010-11-08 16:43:21 -0500847 if (-f "$output_config") {
848 cp "$output_config", "$faildir/config" or
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400849 die "failed to copy .config";
850 }
851 if (-f $buildlog) {
852 cp $buildlog, "$faildir/buildlog" or
853 die "failed to move $buildlog";
854 }
855 if (-f $dmesg) {
856 cp $dmesg, "$faildir/dmesg" or
857 die "failed to move $dmesg";
858 }
859
860 doprint "*** Saved info to $faildir ***\n";
861
Steven Rostedt2b7d9b22010-11-02 14:58:15 -0400862 return 1;
863}
864
Steven Rostedt2545eb62010-11-02 15:01:32 -0400865sub run_command {
866 my ($command) = @_;
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400867 my $dolog = 0;
868 my $dord = 0;
869 my $pid;
870
Steven Rostedte48c5292010-11-02 14:35:37 -0400871 $command =~ s/\$SSH_USER/$ssh_user/g;
872 $command =~ s/\$MACHINE/$machine/g;
873
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400874 doprint("$command ... ");
875
876 $pid = open(CMD, "$command 2>&1 |") or
Steven Rostedt2b7d9b22010-11-02 14:58:15 -0400877 (fail "unable to exec $command" and return 0);
Steven Rostedt2545eb62010-11-02 15:01:32 -0400878
879 if (defined($opt{"LOG_FILE"})) {
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400880 open(LOG, ">>$opt{LOG_FILE}") or
881 dodie "failed to write to log";
882 $dolog = 1;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -0400883 }
884
885 if (defined($redirect)) {
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400886 open (RD, ">$redirect") or
887 dodie "failed to write to redirect $redirect";
888 $dord = 1;
Steven Rostedt2545eb62010-11-02 15:01:32 -0400889 }
890
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400891 while (<CMD>) {
892 print LOG if ($dolog);
893 print RD if ($dord);
894 }
Steven Rostedt2545eb62010-11-02 15:01:32 -0400895
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400896 waitpid($pid, 0);
Steven Rostedt2545eb62010-11-02 15:01:32 -0400897 my $failed = $?;
898
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400899 close(CMD);
900 close(LOG) if ($dolog);
901 close(RD) if ($dord);
902
Steven Rostedt2545eb62010-11-02 15:01:32 -0400903 if ($failed) {
904 doprint "FAILED!\n";
905 } else {
906 doprint "SUCCESS\n";
907 }
908
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400909 return !$failed;
910}
911
Steven Rostedte48c5292010-11-02 14:35:37 -0400912sub run_ssh {
913 my ($cmd) = @_;
914 my $cp_exec = $ssh_exec;
915
916 $cp_exec =~ s/\$SSH_COMMAND/$cmd/g;
917 return run_command "$cp_exec";
918}
919
920sub run_scp {
921 my ($src, $dst) = @_;
922 my $cp_scp = $scp_to_target;
923
924 $cp_scp =~ s/\$SRC_FILE/$src/g;
925 $cp_scp =~ s/\$DST_FILE/$dst/g;
926
927 return run_command "$cp_scp";
928}
929
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400930sub get_grub_index {
931
Steven Rostedta75fece2010-11-02 14:58:27 -0400932 if ($reboot_type ne "grub") {
933 return;
934 }
Steven Rostedt5a391fb2010-11-02 14:57:43 -0400935 return if (defined($grub_number));
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400936
937 doprint "Find grub menu ... ";
938 $grub_number = -1;
Steven Rostedte48c5292010-11-02 14:35:37 -0400939
940 my $ssh_grub = $ssh_exec;
941 $ssh_grub =~ s,\$SSH_COMMAND,cat /boot/grub/menu.lst,g;
942
943 open(IN, "$ssh_grub |")
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400944 or die "unable to get menu.lst";
Steven Rostedte48c5292010-11-02 14:35:37 -0400945
Steven Rostedteaa1fe22011-09-14 17:20:39 -0400946 my $found = 0;
947
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400948 while (<IN>) {
Steven Rostedta75fece2010-11-02 14:58:27 -0400949 if (/^\s*title\s+$grub_menu\s*$/) {
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400950 $grub_number++;
Steven Rostedteaa1fe22011-09-14 17:20:39 -0400951 $found = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400952 last;
953 } elsif (/^\s*title\s/) {
954 $grub_number++;
955 }
956 }
957 close(IN);
958
Steven Rostedta75fece2010-11-02 14:58:27 -0400959 die "Could not find '$grub_menu' in /boot/grub/menu on $machine"
Steven Rostedteaa1fe22011-09-14 17:20:39 -0400960 if (!$found);
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400961 doprint "$grub_number\n";
Steven Rostedt2545eb62010-11-02 15:01:32 -0400962}
963
Steven Rostedt2545eb62010-11-02 15:01:32 -0400964sub wait_for_input
965{
966 my ($fp, $time) = @_;
967 my $rin;
968 my $ready;
969 my $line;
970 my $ch;
971
972 if (!defined($time)) {
973 $time = $timeout;
974 }
975
976 $rin = '';
977 vec($rin, fileno($fp), 1) = 1;
978 $ready = select($rin, undef, undef, $time);
979
980 $line = "";
981
982 # try to read one char at a time
983 while (sysread $fp, $ch, 1) {
984 $line .= $ch;
985 last if ($ch eq "\n");
986 }
987
988 if (!length($line)) {
989 return undef;
990 }
991
992 return $line;
993}
994
Steven Rostedt75c3fda72010-11-02 14:57:21 -0400995sub reboot_to {
Steven Rostedta75fece2010-11-02 14:58:27 -0400996 if ($reboot_type eq "grub") {
Steven Rostedt4da46da2011-06-01 23:25:13 -0400997 run_ssh "'(echo \"savedefault --default=$grub_number --once\" | grub --batch && reboot)'";
Steven Rostedta75fece2010-11-02 14:58:27 -0400998 return;
999 }
1000
1001 run_command "$reboot_script";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001002}
1003
Steven Rostedta57419b2010-11-02 15:13:54 -04001004sub get_sha1 {
1005 my ($commit) = @_;
1006
1007 doprint "git rev-list --max-count=1 $commit ... ";
1008 my $sha1 = `git rev-list --max-count=1 $commit`;
1009 my $ret = $?;
1010
1011 logit $sha1;
1012
1013 if ($ret) {
1014 doprint "FAILED\n";
1015 dodie "Failed to get git $commit";
1016 }
1017
1018 print "SUCCESS\n";
1019
1020 chomp $sha1;
1021
1022 return $sha1;
1023}
1024
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001025sub monitor {
Steven Rostedt2545eb62010-11-02 15:01:32 -04001026 my $booted = 0;
1027 my $bug = 0;
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001028 my $skip_call_trace = 0;
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001029 my $loops;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001030
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001031 wait_for_monitor 5;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001032
1033 my $line;
1034 my $full_line = "";
1035
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001036 open(DMESG, "> $dmesg") or
1037 die "unable to write to $dmesg";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001038
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001039 reboot_to;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001040
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001041 my $success_start;
1042 my $failure_start;
Steven Rostedt2d01b262011-03-08 09:47:54 -05001043 my $monitor_start = time;
1044 my $done = 0;
Steven Rostedtf1a5b962011-06-13 10:30:00 -04001045 my $version_found = 0;
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001046
Steven Rostedt2d01b262011-03-08 09:47:54 -05001047 while (!$done) {
Steven Rostedt2545eb62010-11-02 15:01:32 -04001048
Steven Rostedtecaf8e52011-06-13 10:48:10 -04001049 if ($bug && defined($stop_after_failure) &&
1050 $stop_after_failure >= 0) {
1051 my $time = $stop_after_failure - (time - $failure_start);
1052 $line = wait_for_input($monitor_fp, $time);
1053 if (!defined($line)) {
1054 doprint "bug timed out after $booted_timeout seconds\n";
1055 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
1056 last;
1057 }
1058 } elsif ($booted) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001059 $line = wait_for_input($monitor_fp, $booted_timeout);
Steven Rostedtcd4f1d52011-06-13 10:26:27 -04001060 if (!defined($line)) {
1061 my $s = $booted_timeout == 1 ? "" : "s";
1062 doprint "Successful boot found: break after $booted_timeout second$s\n";
1063 last;
1064 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001065 } else {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001066 $line = wait_for_input($monitor_fp);
Steven Rostedtcd4f1d52011-06-13 10:26:27 -04001067 if (!defined($line)) {
1068 my $s = $timeout == 1 ? "" : "s";
1069 doprint "Timed out after $timeout second$s\n";
1070 last;
1071 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001072 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001073
Steven Rostedt2545eb62010-11-02 15:01:32 -04001074 doprint $line;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001075 print DMESG $line;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001076
1077 # we are not guaranteed to get a full line
1078 $full_line .= $line;
1079
Steven Rostedta75fece2010-11-02 14:58:27 -04001080 if ($full_line =~ /$success_line/) {
Steven Rostedt2545eb62010-11-02 15:01:32 -04001081 $booted = 1;
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001082 $success_start = time;
1083 }
1084
1085 if ($booted && defined($stop_after_success) &&
1086 $stop_after_success >= 0) {
1087 my $now = time;
1088 if ($now - $success_start >= $stop_after_success) {
1089 doprint "Test forced to stop after $stop_after_success seconds after success\n";
1090 last;
1091 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001092 }
1093
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001094 if ($full_line =~ /\[ backtrace testing \]/) {
1095 $skip_call_trace = 1;
1096 }
1097
Steven Rostedt2545eb62010-11-02 15:01:32 -04001098 if ($full_line =~ /call trace:/i) {
Steven Rostedt46519202011-03-08 09:40:31 -05001099 if (!$bug && !$skip_call_trace) {
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001100 $bug = 1;
1101 $failure_start = time;
1102 }
1103 }
1104
1105 if ($bug && defined($stop_after_failure) &&
1106 $stop_after_failure >= 0) {
1107 my $now = time;
1108 if ($now - $failure_start >= $stop_after_failure) {
1109 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
1110 last;
1111 }
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001112 }
1113
1114 if ($full_line =~ /\[ end of backtrace testing \]/) {
1115 $skip_call_trace = 0;
1116 }
1117
1118 if ($full_line =~ /Kernel panic -/) {
Steven Rostedt10abf112011-03-07 13:21:00 -05001119 $failure_start = time;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001120 $bug = 1;
1121 }
1122
Steven Rostedtf1a5b962011-06-13 10:30:00 -04001123 # Detect triple faults by testing the banner
1124 if ($full_line =~ /\bLinux version (\S+).*\n/) {
1125 if ($1 eq $version) {
1126 $version_found = 1;
1127 } elsif ($version_found && $detect_triplefault) {
1128 # We already booted into the kernel we are testing,
1129 # but now we booted into another kernel?
1130 # Consider this a triple fault.
1131 doprint "Aleady booted in Linux kernel $version, but now\n";
1132 doprint "we booted into Linux kernel $1.\n";
1133 doprint "Assuming that this is a triple fault.\n";
1134 doprint "To disable this: set DETECT_TRIPLE_FAULT to 0\n";
1135 last;
1136 }
1137 }
1138
Steven Rostedt2545eb62010-11-02 15:01:32 -04001139 if ($line =~ /\n/) {
1140 $full_line = "";
1141 }
Steven Rostedt2d01b262011-03-08 09:47:54 -05001142
1143 if ($stop_test_after > 0 && !$booted && !$bug) {
1144 if (time - $monitor_start > $stop_test_after) {
Steven Rostedt4d62bf52011-05-20 09:14:35 -04001145 doprint "STOP_TEST_AFTER ($stop_test_after seconds) timed out\n";
Steven Rostedt2d01b262011-03-08 09:47:54 -05001146 $done = 1;
1147 }
1148 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001149 }
1150
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001151 close(DMESG);
Steven Rostedt2545eb62010-11-02 15:01:32 -04001152
Steven Rostedt2545eb62010-11-02 15:01:32 -04001153 if ($bug) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001154 return 0 if ($in_bisect);
Steven Rostedt576f6272010-11-02 14:58:38 -04001155 fail "failed - got a bug report" and return 0;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001156 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001157
Steven Rostedta75fece2010-11-02 14:58:27 -04001158 if (!$booted) {
1159 return 0 if ($in_bisect);
Steven Rostedt576f6272010-11-02 14:58:38 -04001160 fail "failed - never got a boot prompt." and return 0;
Steven Rostedta75fece2010-11-02 14:58:27 -04001161 }
1162
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001163 return 1;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001164}
1165
Steven Rostedtdb05cfe2011-06-13 11:09:22 -04001166sub do_post_install {
1167
1168 return if (!defined($post_install));
1169
1170 my $cp_post_install = $post_install;
1171 $cp_post_install =~ s/\$KERNEL_VERSION/$version/g;
1172 run_command "$cp_post_install" or
1173 dodie "Failed to run post install";
1174}
1175
Steven Rostedt2545eb62010-11-02 15:01:32 -04001176sub install {
1177
Steven Rostedte0a87422011-09-30 17:50:48 -04001178 return if ($no_install);
1179
Steven Rostedte48c5292010-11-02 14:35:37 -04001180 run_scp "$outputdir/$build_target", "$target_image" or
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001181 dodie "failed to copy image";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001182
1183 my $install_mods = 0;
1184
1185 # should we process modules?
1186 $install_mods = 0;
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001187 open(IN, "$output_config") or dodie("Can't read config file");
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001188 while (<IN>) {
1189 if (/CONFIG_MODULES(=y)?/) {
1190 $install_mods = 1 if (defined($1));
1191 last;
1192 }
1193 }
1194 close(IN);
1195
1196 if (!$install_mods) {
Steven Rostedtdb05cfe2011-06-13 11:09:22 -04001197 do_post_install;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001198 doprint "No modules needed\n";
1199 return;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001200 }
1201
Steven Rostedta75fece2010-11-02 14:58:27 -04001202 run_command "$make INSTALL_MOD_PATH=$tmpdir modules_install" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001203 dodie "Failed to install modules";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001204
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001205 my $modlib = "/lib/modules/$version";
Steven Rostedta57419b2010-11-02 15:13:54 -04001206 my $modtar = "ktest-mods.tar.bz2";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001207
Steven Rostedte48c5292010-11-02 14:35:37 -04001208 run_ssh "rm -rf $modlib" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001209 dodie "failed to remove old mods: $modlib";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001210
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001211 # would be nice if scp -r did not follow symbolic links
Steven Rostedta75fece2010-11-02 14:58:27 -04001212 run_command "cd $tmpdir && tar -cjf $modtar lib/modules/$version" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001213 dodie "making tarball";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001214
Steven Rostedte48c5292010-11-02 14:35:37 -04001215 run_scp "$tmpdir/$modtar", "/tmp" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001216 dodie "failed to copy modules";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001217
Steven Rostedta75fece2010-11-02 14:58:27 -04001218 unlink "$tmpdir/$modtar";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001219
Steven Rostedte7b13442011-06-14 20:44:36 -04001220 run_ssh "'(cd / && tar xjf /tmp/$modtar)'" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001221 dodie "failed to tar modules";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001222
Steven Rostedte48c5292010-11-02 14:35:37 -04001223 run_ssh "rm -f /tmp/$modtar";
Steven Rostedt8b37ca82010-11-02 14:58:33 -04001224
Steven Rostedtdb05cfe2011-06-13 11:09:22 -04001225 do_post_install;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001226}
1227
Steven Rostedtddf607e2011-06-14 20:49:13 -04001228sub get_version {
1229 # get the release name
1230 doprint "$make kernelrelease ... ";
1231 $version = `$make kernelrelease | tail -1`;
1232 chomp($version);
1233 doprint "$version\n";
1234}
1235
1236sub start_monitor_and_boot {
1237 get_grub_index;
1238 get_version;
1239 install;
1240
1241 start_monitor;
1242 return monitor;
1243}
1244
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001245sub check_buildlog {
1246 my ($patch) = @_;
1247
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001248 my @files = `git show $patch | diffstat -l`;
1249
1250 open(IN, "git show $patch |") or
1251 dodie "failed to show $patch";
1252 while (<IN>) {
1253 if (m,^--- a/(.*),) {
1254 chomp $1;
1255 $files[$#files] = $1;
1256 }
1257 }
1258 close(IN);
1259
1260 open(IN, $buildlog) or dodie "Can't open $buildlog";
1261 while (<IN>) {
1262 if (/^\s*(.*?):.*(warning|error)/) {
1263 my $err = $1;
1264 foreach my $file (@files) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001265 my $fullpath = "$builddir/$file";
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001266 if ($file eq $err || $fullpath eq $err) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001267 fail "$file built with warnings" and return 0;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001268 }
1269 }
1270 }
1271 }
1272 close(IN);
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001273
1274 return 1;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001275}
1276
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001277sub apply_min_config {
1278 my $outconfig = "$output_config.new";
Steven Rostedt612b9e92011-03-07 13:27:43 -05001279
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001280 # Read the config file and remove anything that
1281 # is in the force_config hash (from minconfig and others)
1282 # then add the force config back.
1283
1284 doprint "Applying minimum configurations into $output_config.new\n";
1285
1286 open (OUT, ">$outconfig") or
1287 dodie "Can't create $outconfig";
1288
1289 if (-f $output_config) {
1290 open (IN, $output_config) or
1291 dodie "Failed to open $output_config";
1292 while (<IN>) {
1293 if (/^(# )?(CONFIG_[^\s=]*)/) {
1294 next if (defined($force_config{$2}));
1295 }
1296 print OUT;
1297 }
1298 close IN;
1299 }
1300 foreach my $config (keys %force_config) {
1301 print OUT "$force_config{$config}\n";
1302 }
1303 close OUT;
1304
1305 run_command "mv $outconfig $output_config";
1306}
1307
1308sub make_oldconfig {
1309
Steven Rostedt4c4ab122011-07-15 21:16:17 -04001310 my @force_list = keys %force_config;
1311
1312 if ($#force_list >= 0) {
1313 apply_min_config;
1314 }
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001315
1316 if (!run_command "$make oldnoconfig") {
Steven Rostedt612b9e92011-03-07 13:27:43 -05001317 # Perhaps oldnoconfig doesn't exist in this version of the kernel
1318 # try a yes '' | oldconfig
1319 doprint "oldnoconfig failed, trying yes '' | make oldconfig\n";
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001320 run_command "yes '' | $make oldconfig" or
Steven Rostedt612b9e92011-03-07 13:27:43 -05001321 dodie "failed make config oldconfig";
1322 }
1323}
1324
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001325# read a config file and use this to force new configs.
1326sub load_force_config {
1327 my ($config) = @_;
1328
1329 open(IN, $config) or
1330 dodie "failed to read $config";
1331 while (<IN>) {
1332 chomp;
1333 if (/^(CONFIG[^\s=]*)(\s*=.*)/) {
1334 $force_config{$1} = $_;
1335 } elsif (/^# (CONFIG_\S*) is not set/) {
1336 $force_config{$1} = $_;
1337 }
1338 }
1339 close IN;
1340}
1341
Steven Rostedt2545eb62010-11-02 15:01:32 -04001342sub build {
1343 my ($type) = @_;
1344
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001345 unlink $buildlog;
1346
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04001347 # Failed builds should not reboot the target
1348 my $save_no_reboot = $no_reboot;
1349 $no_reboot = 1;
1350
Steven Rostedt0bd6c1a2011-06-14 20:39:31 -04001351 if (defined($pre_build)) {
1352 my $ret = run_command $pre_build;
1353 if (!$ret && defined($pre_build_die) &&
1354 $pre_build_die) {
1355 dodie "failed to pre_build\n";
1356 }
1357 }
1358
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001359 if ($type =~ /^useconfig:(.*)/) {
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001360 run_command "cp $1 $output_config" or
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001361 dodie "could not copy $1 to .config";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001362
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001363 $type = "oldconfig";
1364 }
1365
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001366 # old config can ask questions
1367 if ($type eq "oldconfig") {
Steven Rostedt9386c6a2010-11-08 16:35:48 -05001368 $type = "oldnoconfig";
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001369
1370 # allow for empty configs
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001371 run_command "touch $output_config";
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001372
Andrew Jones13488232011-08-12 15:32:04 +02001373 if (!$noclean) {
1374 run_command "mv $output_config $outputdir/config_temp" or
1375 dodie "moving .config";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001376
Andrew Jones13488232011-08-12 15:32:04 +02001377 run_command "$make mrproper" or dodie "make mrproper";
1378
1379 run_command "mv $outputdir/config_temp $output_config" or
1380 dodie "moving config_temp";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001381 }
1382
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001383 } elsif (!$noclean) {
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001384 unlink "$output_config";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001385 run_command "$make mrproper" or
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001386 dodie "make mrproper";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001387 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001388
1389 # add something to distinguish this build
Steven Rostedta75fece2010-11-02 14:58:27 -04001390 open(OUT, "> $outputdir/localversion") or dodie("Can't make localversion file");
1391 print OUT "$localversion\n";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001392 close(OUT);
1393
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001394 if (defined($minconfig)) {
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001395 load_force_config($minconfig);
Steven Rostedt2545eb62010-11-02 15:01:32 -04001396 }
1397
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001398 if ($type ne "oldnoconfig") {
1399 run_command "$make $type" or
Steven Rostedt612b9e92011-03-07 13:27:43 -05001400 dodie "failed make config";
1401 }
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001402 # Run old config regardless, to enforce min configurations
1403 make_oldconfig;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001404
Steven Rostedta75fece2010-11-02 14:58:27 -04001405 $redirect = "$buildlog";
Steven Rostedt0bd6c1a2011-06-14 20:39:31 -04001406 my $build_ret = run_command "$make $build_options";
1407 undef $redirect;
1408
1409 if (defined($post_build)) {
1410 my $ret = run_command $post_build;
1411 if (!$ret && defined($post_build_die) &&
1412 $post_build_die) {
1413 dodie "failed to post_build\n";
1414 }
1415 }
1416
1417 if (!$build_ret) {
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001418 # bisect may need this to pass
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04001419 if ($in_bisect) {
1420 $no_reboot = $save_no_reboot;
1421 return 0;
1422 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001423 fail "failed build" and return 0;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001424 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001425
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04001426 $no_reboot = $save_no_reboot;
1427
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001428 return 1;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001429}
1430
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001431sub halt {
Steven Rostedte48c5292010-11-02 14:35:37 -04001432 if (!run_ssh "halt" or defined($power_off)) {
Steven Rostedt576f6272010-11-02 14:58:38 -04001433 if (defined($poweroff_after_halt)) {
1434 sleep $poweroff_after_halt;
1435 run_command "$power_off";
1436 }
1437 } else {
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001438 # nope? the zap it!
Steven Rostedta75fece2010-11-02 14:58:27 -04001439 run_command "$power_off";
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001440 }
1441}
1442
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001443sub success {
1444 my ($i) = @_;
1445
Steven Rostedte48c5292010-11-02 14:35:37 -04001446 $successes++;
1447
Steven Rostedt9064af52011-06-13 10:38:48 -04001448 my $name = "";
1449
1450 if (defined($test_name)) {
1451 $name = " ($test_name)";
1452 }
1453
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001454 doprint "\n\n*******************************************\n";
1455 doprint "*******************************************\n";
Steven Rostedt9064af52011-06-13 10:38:48 -04001456 doprint "KTEST RESULT: TEST $i$name SUCCESS!!!! **\n";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001457 doprint "*******************************************\n";
1458 doprint "*******************************************\n";
1459
Steven Rostedt576f6272010-11-02 14:58:38 -04001460 if ($i != $opt{"NUM_TESTS"} && !do_not_reboot) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001461 doprint "Reboot and wait $sleep_time seconds\n";
Andrew Jones2728be42011-08-12 15:32:05 +02001462 reboot $sleep_time;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001463 }
1464}
1465
Steven Rostedtc960bb92011-03-08 09:22:39 -05001466sub answer_bisect {
1467 for (;;) {
1468 doprint "Pass or fail? [p/f]";
1469 my $ans = <STDIN>;
1470 chomp $ans;
1471 if ($ans eq "p" || $ans eq "P") {
1472 return 1;
1473 } elsif ($ans eq "f" || $ans eq "F") {
1474 return 0;
1475 } else {
1476 print "Please answer 'P' or 'F'\n";
1477 }
1478 }
1479}
1480
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001481sub child_run_test {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001482 my $failed = 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001483
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001484 # child should have no power
Steven Rostedta75fece2010-11-02 14:58:27 -04001485 $reboot_on_error = 0;
1486 $poweroff_on_error = 0;
1487 $die_on_failure = 1;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001488
1489 run_command $run_test or $failed = 1;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001490 exit $failed;
1491}
1492
1493my $child_done;
1494
1495sub child_finished {
1496 $child_done = 1;
1497}
1498
1499sub do_run_test {
1500 my $child_pid;
1501 my $child_exit;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001502 my $line;
1503 my $full_line;
1504 my $bug = 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001505
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001506 wait_for_monitor 1;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001507
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001508 doprint "run test $run_test\n";
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001509
1510 $child_done = 0;
1511
1512 $SIG{CHLD} = qw(child_finished);
1513
1514 $child_pid = fork;
1515
1516 child_run_test if (!$child_pid);
1517
1518 $full_line = "";
1519
1520 do {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001521 $line = wait_for_input($monitor_fp, 1);
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001522 if (defined($line)) {
1523
1524 # we are not guaranteed to get a full line
1525 $full_line .= $line;
Steven Rostedt8ea0e062011-03-08 09:44:35 -05001526 doprint $line;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001527
1528 if ($full_line =~ /call trace:/i) {
1529 $bug = 1;
1530 }
1531
1532 if ($full_line =~ /Kernel panic -/) {
1533 $bug = 1;
1534 }
1535
1536 if ($line =~ /\n/) {
1537 $full_line = "";
1538 }
1539 }
1540 } while (!$child_done && !$bug);
1541
1542 if ($bug) {
Steven Rostedt8ea0e062011-03-08 09:44:35 -05001543 my $failure_start = time;
1544 my $now;
1545 do {
1546 $line = wait_for_input($monitor_fp, 1);
1547 if (defined($line)) {
1548 doprint $line;
1549 }
1550 $now = time;
1551 if ($now - $failure_start >= $stop_after_failure) {
1552 last;
1553 }
1554 } while (defined($line));
1555
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001556 doprint "Detected kernel crash!\n";
1557 # kill the child with extreme prejudice
1558 kill 9, $child_pid;
1559 }
1560
1561 waitpid $child_pid, 0;
1562 $child_exit = $?;
1563
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001564 if ($bug || $child_exit) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001565 return 0 if $in_bisect;
1566 fail "test failed" and return 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001567 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001568 return 1;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001569}
1570
Steven Rostedta75fece2010-11-02 14:58:27 -04001571sub run_git_bisect {
1572 my ($command) = @_;
1573
1574 doprint "$command ... ";
1575
1576 my $output = `$command 2>&1`;
1577 my $ret = $?;
1578
1579 logit $output;
1580
1581 if ($ret) {
1582 doprint "FAILED\n";
1583 dodie "Failed to git bisect";
1584 }
1585
1586 doprint "SUCCESS\n";
1587 if ($output =~ m/^(Bisecting: .*\(roughly \d+ steps?\))\s+\[([[:xdigit:]]+)\]/) {
1588 doprint "$1 [$2]\n";
1589 } elsif ($output =~ m/^([[:xdigit:]]+) is the first bad commit/) {
1590 $bisect_bad = $1;
1591 doprint "Found bad commit... $1\n";
1592 return 0;
1593 } else {
1594 # we already logged it, just print it now.
1595 print $output;
1596 }
1597
1598 return 1;
1599}
1600
Steven Rostedtc23dca72011-03-08 09:26:31 -05001601sub bisect_reboot {
1602 doprint "Reboot and sleep $bisect_sleep_time seconds\n";
Andrew Jones2728be42011-08-12 15:32:05 +02001603 reboot $bisect_sleep_time;
Steven Rostedtc23dca72011-03-08 09:26:31 -05001604}
1605
1606# returns 1 on success, 0 on failure, -1 on skip
Steven Rostedt0a05c762010-11-08 11:14:10 -05001607sub run_bisect_test {
1608 my ($type, $buildtype) = @_;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001609
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001610 my $failed = 0;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001611 my $result;
1612 my $output;
1613 my $ret;
1614
Steven Rostedt0a05c762010-11-08 11:14:10 -05001615 $in_bisect = 1;
1616
1617 build $buildtype or $failed = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001618
1619 if ($type ne "build") {
Steven Rostedtc23dca72011-03-08 09:26:31 -05001620 if ($failed && $bisect_skip) {
1621 $in_bisect = 0;
1622 return -1;
1623 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001624 dodie "Failed on build" if $failed;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001625
1626 # Now boot the box
Steven Rostedtddf607e2011-06-14 20:49:13 -04001627 start_monitor_and_boot or $failed = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001628
1629 if ($type ne "boot") {
Steven Rostedtc23dca72011-03-08 09:26:31 -05001630 if ($failed && $bisect_skip) {
1631 end_monitor;
1632 bisect_reboot;
1633 $in_bisect = 0;
1634 return -1;
1635 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001636 dodie "Failed on boot" if $failed;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001637
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001638 do_run_test or $failed = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001639 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001640 end_monitor;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001641 }
1642
1643 if ($failed) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05001644 $result = 0;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001645 } else {
Steven Rostedt0a05c762010-11-08 11:14:10 -05001646 $result = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001647 }
Steven Rostedt4025bc62011-05-20 09:16:29 -04001648
1649 # reboot the box to a kernel we can ssh to
1650 if ($type ne "build") {
1651 bisect_reboot;
1652 }
Steven Rostedt0a05c762010-11-08 11:14:10 -05001653 $in_bisect = 0;
1654
1655 return $result;
1656}
1657
1658sub run_bisect {
1659 my ($type) = @_;
1660 my $buildtype = "oldconfig";
1661
1662 # We should have a minconfig to use?
1663 if (defined($minconfig)) {
1664 $buildtype = "useconfig:$minconfig";
1665 }
1666
1667 my $ret = run_bisect_test $type, $buildtype;
1668
Steven Rostedtc960bb92011-03-08 09:22:39 -05001669 if ($bisect_manual) {
1670 $ret = answer_bisect;
1671 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001672
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001673 # Are we looking for where it worked, not failed?
1674 if ($reverse_bisect) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05001675 $ret = !$ret;
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001676 }
1677
Steven Rostedtc23dca72011-03-08 09:26:31 -05001678 if ($ret > 0) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05001679 return "good";
Steven Rostedtc23dca72011-03-08 09:26:31 -05001680 } elsif ($ret == 0) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05001681 return "bad";
Steven Rostedtc23dca72011-03-08 09:26:31 -05001682 } elsif ($bisect_skip) {
1683 doprint "HIT A BAD COMMIT ... SKIPPING\n";
1684 return "skip";
Steven Rostedt0a05c762010-11-08 11:14:10 -05001685 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001686}
1687
1688sub bisect {
1689 my ($i) = @_;
1690
1691 my $result;
1692
1693 die "BISECT_GOOD[$i] not defined\n" if (!defined($opt{"BISECT_GOOD[$i]"}));
1694 die "BISECT_BAD[$i] not defined\n" if (!defined($opt{"BISECT_BAD[$i]"}));
1695 die "BISECT_TYPE[$i] not defined\n" if (!defined($opt{"BISECT_TYPE[$i]"}));
1696
1697 my $good = $opt{"BISECT_GOOD[$i]"};
1698 my $bad = $opt{"BISECT_BAD[$i]"};
1699 my $type = $opt{"BISECT_TYPE[$i]"};
Steven Rostedta75fece2010-11-02 14:58:27 -04001700 my $start = $opt{"BISECT_START[$i]"};
1701 my $replay = $opt{"BISECT_REPLAY[$i]"};
Steven Rostedt3410f6f2011-03-08 09:38:12 -05001702 my $start_files = $opt{"BISECT_FILES[$i]"};
1703
1704 if (defined($start_files)) {
1705 $start_files = " -- " . $start_files;
1706 } else {
1707 $start_files = "";
1708 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001709
Steven Rostedta57419b2010-11-02 15:13:54 -04001710 # convert to true sha1's
1711 $good = get_sha1($good);
1712 $bad = get_sha1($bad);
1713
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001714 if (defined($opt{"BISECT_REVERSE[$i]"}) &&
1715 $opt{"BISECT_REVERSE[$i]"} == 1) {
1716 doprint "Performing a reverse bisect (bad is good, good is bad!)\n";
1717 $reverse_bisect = 1;
1718 } else {
1719 $reverse_bisect = 0;
1720 }
1721
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001722 # Can't have a test without having a test to run
1723 if ($type eq "test" && !defined($run_test)) {
1724 $type = "boot";
1725 }
1726
Steven Rostedta75fece2010-11-02 14:58:27 -04001727 my $check = $opt{"BISECT_CHECK[$i]"};
1728 if (defined($check) && $check ne "0") {
1729
1730 # get current HEAD
Steven Rostedta57419b2010-11-02 15:13:54 -04001731 my $head = get_sha1("HEAD");
Steven Rostedta75fece2010-11-02 14:58:27 -04001732
1733 if ($check ne "good") {
1734 doprint "TESTING BISECT BAD [$bad]\n";
1735 run_command "git checkout $bad" or
1736 die "Failed to checkout $bad";
1737
1738 $result = run_bisect $type;
1739
1740 if ($result ne "bad") {
1741 fail "Tested BISECT_BAD [$bad] and it succeeded" and return 0;
1742 }
1743 }
1744
1745 if ($check ne "bad") {
1746 doprint "TESTING BISECT GOOD [$good]\n";
1747 run_command "git checkout $good" or
1748 die "Failed to checkout $good";
1749
1750 $result = run_bisect $type;
1751
1752 if ($result ne "good") {
1753 fail "Tested BISECT_GOOD [$good] and it failed" and return 0;
1754 }
1755 }
1756
1757 # checkout where we started
1758 run_command "git checkout $head" or
1759 die "Failed to checkout $head";
1760 }
1761
Steven Rostedt3410f6f2011-03-08 09:38:12 -05001762 run_command "git bisect start$start_files" or
Steven Rostedta75fece2010-11-02 14:58:27 -04001763 dodie "could not start bisect";
1764
1765 run_command "git bisect good $good" or
1766 dodie "could not set bisect good to $good";
1767
1768 run_git_bisect "git bisect bad $bad" or
1769 dodie "could not set bisect bad to $bad";
1770
1771 if (defined($replay)) {
1772 run_command "git bisect replay $replay" or
1773 dodie "failed to run replay";
1774 }
1775
1776 if (defined($start)) {
1777 run_command "git checkout $start" or
1778 dodie "failed to checkout $start";
1779 }
1780
1781 my $test;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001782 do {
1783 $result = run_bisect $type;
Steven Rostedta75fece2010-11-02 14:58:27 -04001784 $test = run_git_bisect "git bisect $result";
1785 } while ($test);
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001786
1787 run_command "git bisect log" or
1788 dodie "could not capture git bisect log";
1789
1790 run_command "git bisect reset" or
1791 dodie "could not reset git bisect";
1792
1793 doprint "Bad commit was [$bisect_bad]\n";
1794
Steven Rostedt0a05c762010-11-08 11:14:10 -05001795 success $i;
1796}
1797
1798my %config_ignore;
1799my %config_set;
1800
1801my %config_list;
1802my %null_config;
1803
1804my %dependency;
1805
Steven Rostedt4c4ab122011-07-15 21:16:17 -04001806sub assign_configs {
1807 my ($hash, $config) = @_;
Steven Rostedt0a05c762010-11-08 11:14:10 -05001808
1809 open (IN, $config)
1810 or dodie "Failed to read $config";
1811
1812 while (<IN>) {
Steven Rostedt9bf71742011-06-01 23:27:19 -04001813 if (/^((CONFIG\S*)=.*)/) {
Steven Rostedt4c4ab122011-07-15 21:16:17 -04001814 ${$hash}{$2} = $1;
Steven Rostedt0a05c762010-11-08 11:14:10 -05001815 }
1816 }
1817
1818 close(IN);
1819}
1820
Steven Rostedt4c4ab122011-07-15 21:16:17 -04001821sub process_config_ignore {
1822 my ($config) = @_;
1823
1824 assign_configs \%config_ignore, $config;
1825}
1826
Steven Rostedt0a05c762010-11-08 11:14:10 -05001827sub read_current_config {
1828 my ($config_ref) = @_;
1829
1830 %{$config_ref} = ();
1831 undef %{$config_ref};
1832
1833 my @key = keys %{$config_ref};
1834 if ($#key >= 0) {
1835 print "did not delete!\n";
1836 exit;
1837 }
1838 open (IN, "$output_config");
1839
1840 while (<IN>) {
1841 if (/^(CONFIG\S+)=(.*)/) {
1842 ${$config_ref}{$1} = $2;
1843 }
1844 }
1845 close(IN);
1846}
1847
1848sub get_dependencies {
1849 my ($config) = @_;
1850
1851 my $arr = $dependency{$config};
1852 if (!defined($arr)) {
1853 return ();
1854 }
1855
1856 my @deps = @{$arr};
1857
1858 foreach my $dep (@{$arr}) {
1859 print "ADD DEP $dep\n";
1860 @deps = (@deps, get_dependencies $dep);
1861 }
1862
1863 return @deps;
1864}
1865
1866sub create_config {
1867 my @configs = @_;
1868
1869 open(OUT, ">$output_config") or dodie "Can not write to $output_config";
1870
1871 foreach my $config (@configs) {
1872 print OUT "$config_set{$config}\n";
1873 my @deps = get_dependencies $config;
1874 foreach my $dep (@deps) {
1875 print OUT "$config_set{$dep}\n";
1876 }
1877 }
1878
1879 foreach my $config (keys %config_ignore) {
1880 print OUT "$config_ignore{$config}\n";
1881 }
1882 close(OUT);
1883
1884# exit;
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001885 make_oldconfig;
Steven Rostedt0a05c762010-11-08 11:14:10 -05001886}
1887
1888sub compare_configs {
1889 my (%a, %b) = @_;
1890
1891 foreach my $item (keys %a) {
1892 if (!defined($b{$item})) {
1893 print "diff $item\n";
1894 return 1;
1895 }
1896 delete $b{$item};
1897 }
1898
1899 my @keys = keys %b;
1900 if ($#keys) {
1901 print "diff2 $keys[0]\n";
1902 }
1903 return -1 if ($#keys >= 0);
1904
1905 return 0;
1906}
1907
1908sub run_config_bisect_test {
1909 my ($type) = @_;
1910
1911 return run_bisect_test $type, "oldconfig";
1912}
1913
1914sub process_passed {
1915 my (%configs) = @_;
1916
1917 doprint "These configs had no failure: (Enabling them for further compiles)\n";
1918 # Passed! All these configs are part of a good compile.
1919 # Add them to the min options.
1920 foreach my $config (keys %configs) {
1921 if (defined($config_list{$config})) {
1922 doprint " removing $config\n";
1923 $config_ignore{$config} = $config_list{$config};
1924 delete $config_list{$config};
1925 }
1926 }
Steven Rostedtf1a27852010-11-11 11:34:38 -05001927 doprint "config copied to $outputdir/config_good\n";
1928 run_command "cp -f $output_config $outputdir/config_good";
Steven Rostedt0a05c762010-11-08 11:14:10 -05001929}
1930
1931sub process_failed {
1932 my ($config) = @_;
1933
1934 doprint "\n\n***************************************\n";
1935 doprint "Found bad config: $config\n";
1936 doprint "***************************************\n\n";
1937}
1938
1939sub run_config_bisect {
1940
1941 my @start_list = keys %config_list;
1942
1943 if ($#start_list < 0) {
1944 doprint "No more configs to test!!!\n";
1945 return -1;
1946 }
1947
1948 doprint "***** RUN TEST ***\n";
1949 my $type = $opt{"CONFIG_BISECT_TYPE[$iteration]"};
1950 my $ret;
1951 my %current_config;
1952
1953 my $count = $#start_list + 1;
1954 doprint " $count configs to test\n";
1955
1956 my $half = int($#start_list / 2);
1957
1958 do {
1959 my @tophalf = @start_list[0 .. $half];
1960
1961 create_config @tophalf;
1962 read_current_config \%current_config;
1963
1964 $count = $#tophalf + 1;
1965 doprint "Testing $count configs\n";
1966 my $found = 0;
1967 # make sure we test something
1968 foreach my $config (@tophalf) {
1969 if (defined($current_config{$config})) {
1970 logit " $config\n";
1971 $found = 1;
1972 }
1973 }
1974 if (!$found) {
1975 # try the other half
1976 doprint "Top half produced no set configs, trying bottom half\n";
Steven Rostedt4c8cc552011-06-01 23:22:30 -04001977 @tophalf = @start_list[$half + 1 .. $#start_list];
Steven Rostedt0a05c762010-11-08 11:14:10 -05001978 create_config @tophalf;
1979 read_current_config \%current_config;
1980 foreach my $config (@tophalf) {
1981 if (defined($current_config{$config})) {
1982 logit " $config\n";
1983 $found = 1;
1984 }
1985 }
1986 if (!$found) {
1987 doprint "Failed: Can't make new config with current configs\n";
1988 foreach my $config (@start_list) {
1989 doprint " CONFIG: $config\n";
1990 }
1991 return -1;
1992 }
1993 $count = $#tophalf + 1;
1994 doprint "Testing $count configs\n";
1995 }
1996
1997 $ret = run_config_bisect_test $type;
Steven Rostedtc960bb92011-03-08 09:22:39 -05001998 if ($bisect_manual) {
1999 $ret = answer_bisect;
2000 }
Steven Rostedt0a05c762010-11-08 11:14:10 -05002001 if ($ret) {
2002 process_passed %current_config;
2003 return 0;
2004 }
2005
2006 doprint "This config had a failure.\n";
2007 doprint "Removing these configs that were not set in this config:\n";
Steven Rostedtf1a27852010-11-11 11:34:38 -05002008 doprint "config copied to $outputdir/config_bad\n";
2009 run_command "cp -f $output_config $outputdir/config_bad";
Steven Rostedt0a05c762010-11-08 11:14:10 -05002010
2011 # A config exists in this group that was bad.
2012 foreach my $config (keys %config_list) {
2013 if (!defined($current_config{$config})) {
2014 doprint " removing $config\n";
2015 delete $config_list{$config};
2016 }
2017 }
2018
2019 @start_list = @tophalf;
2020
2021 if ($#start_list == 0) {
2022 process_failed $start_list[0];
2023 return 1;
2024 }
2025
2026 # remove half the configs we are looking at and see if
2027 # they are good.
2028 $half = int($#start_list / 2);
Steven Rostedt4c8cc552011-06-01 23:22:30 -04002029 } while ($#start_list > 0);
Steven Rostedt0a05c762010-11-08 11:14:10 -05002030
Steven Rostedtc960bb92011-03-08 09:22:39 -05002031 # we found a single config, try it again unless we are running manually
2032
2033 if ($bisect_manual) {
2034 process_failed $start_list[0];
2035 return 1;
2036 }
2037
Steven Rostedt0a05c762010-11-08 11:14:10 -05002038 my @tophalf = @start_list[0 .. 0];
2039
2040 $ret = run_config_bisect_test $type;
2041 if ($ret) {
2042 process_passed %current_config;
2043 return 0;
2044 }
2045
2046 process_failed $start_list[0];
2047 return 1;
2048}
2049
2050sub config_bisect {
2051 my ($i) = @_;
2052
2053 my $start_config = $opt{"CONFIG_BISECT[$i]"};
2054
2055 my $tmpconfig = "$tmpdir/use_config";
2056
Steven Rostedt30f75da2011-06-13 10:35:35 -04002057 if (defined($config_bisect_good)) {
2058 process_config_ignore $config_bisect_good;
2059 }
2060
Steven Rostedt0a05c762010-11-08 11:14:10 -05002061 # Make the file with the bad config and the min config
2062 if (defined($minconfig)) {
2063 # read the min config for things to ignore
2064 run_command "cp $minconfig $tmpconfig" or
2065 dodie "failed to copy $minconfig to $tmpconfig";
2066 } else {
2067 unlink $tmpconfig;
2068 }
2069
Steven Rostedt0a05c762010-11-08 11:14:10 -05002070 if (-f $tmpconfig) {
Steven Rostedtfcb3f162011-06-13 10:40:58 -04002071 load_force_config($tmpconfig);
Steven Rostedt0a05c762010-11-08 11:14:10 -05002072 process_config_ignore $tmpconfig;
2073 }
2074
2075 # now process the start config
2076 run_command "cp $start_config $output_config" or
2077 dodie "failed to copy $start_config to $output_config";
2078
2079 # read directly what we want to check
2080 my %config_check;
2081 open (IN, $output_config)
2082 or dodie "faied to open $output_config";
2083
2084 while (<IN>) {
2085 if (/^((CONFIG\S*)=.*)/) {
2086 $config_check{$2} = $1;
2087 }
2088 }
2089 close(IN);
2090
Steven Rostedt250bae82011-07-15 22:05:59 -04002091 # Now run oldconfig with the minconfig
Steven Rostedtfcb3f162011-06-13 10:40:58 -04002092 make_oldconfig;
Steven Rostedt0a05c762010-11-08 11:14:10 -05002093
2094 # check to see what we lost (or gained)
2095 open (IN, $output_config)
2096 or dodie "Failed to read $start_config";
2097
2098 my %removed_configs;
2099 my %added_configs;
2100
2101 while (<IN>) {
2102 if (/^((CONFIG\S*)=.*)/) {
2103 # save off all options
2104 $config_set{$2} = $1;
2105 if (defined($config_check{$2})) {
2106 if (defined($config_ignore{$2})) {
2107 $removed_configs{$2} = $1;
2108 } else {
2109 $config_list{$2} = $1;
2110 }
2111 } elsif (!defined($config_ignore{$2})) {
2112 $added_configs{$2} = $1;
2113 $config_list{$2} = $1;
2114 }
2115 }
2116 }
2117 close(IN);
2118
2119 my @confs = keys %removed_configs;
2120 if ($#confs >= 0) {
2121 doprint "Configs overridden by default configs and removed from check:\n";
2122 foreach my $config (@confs) {
2123 doprint " $config\n";
2124 }
2125 }
2126 @confs = keys %added_configs;
2127 if ($#confs >= 0) {
2128 doprint "Configs appearing in make oldconfig and added:\n";
2129 foreach my $config (@confs) {
2130 doprint " $config\n";
2131 }
2132 }
2133
2134 my %config_test;
2135 my $once = 0;
2136
2137 # Sometimes kconfig does weird things. We must make sure
2138 # that the config we autocreate has everything we need
2139 # to test, otherwise we may miss testing configs, or
2140 # may not be able to create a new config.
2141 # Here we create a config with everything set.
2142 create_config (keys %config_list);
2143 read_current_config \%config_test;
2144 foreach my $config (keys %config_list) {
2145 if (!defined($config_test{$config})) {
2146 if (!$once) {
2147 $once = 1;
2148 doprint "Configs not produced by kconfig (will not be checked):\n";
2149 }
2150 doprint " $config\n";
2151 delete $config_list{$config};
2152 }
2153 }
2154 my $ret;
2155 do {
2156 $ret = run_config_bisect;
2157 } while (!$ret);
2158
2159 return $ret if ($ret < 0);
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002160
2161 success $i;
2162}
2163
Steven Rostedt27d934b2011-05-20 09:18:18 -04002164sub patchcheck_reboot {
2165 doprint "Reboot and sleep $patchcheck_sleep_time seconds\n";
Andrew Jones2728be42011-08-12 15:32:05 +02002166 reboot $patchcheck_sleep_time;
Steven Rostedt27d934b2011-05-20 09:18:18 -04002167}
2168
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002169sub patchcheck {
2170 my ($i) = @_;
2171
2172 die "PATCHCHECK_START[$i] not defined\n"
2173 if (!defined($opt{"PATCHCHECK_START[$i]"}));
2174 die "PATCHCHECK_TYPE[$i] not defined\n"
2175 if (!defined($opt{"PATCHCHECK_TYPE[$i]"}));
2176
2177 my $start = $opt{"PATCHCHECK_START[$i]"};
2178
2179 my $end = "HEAD";
2180 if (defined($opt{"PATCHCHECK_END[$i]"})) {
2181 $end = $opt{"PATCHCHECK_END[$i]"};
2182 }
2183
Steven Rostedta57419b2010-11-02 15:13:54 -04002184 # Get the true sha1's since we can use things like HEAD~3
2185 $start = get_sha1($start);
2186 $end = get_sha1($end);
2187
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002188 my $type = $opt{"PATCHCHECK_TYPE[$i]"};
2189
2190 # Can't have a test without having a test to run
2191 if ($type eq "test" && !defined($run_test)) {
2192 $type = "boot";
2193 }
2194
2195 open (IN, "git log --pretty=oneline $end|") or
2196 dodie "could not get git list";
2197
2198 my @list;
2199
2200 while (<IN>) {
2201 chomp;
2202 $list[$#list+1] = $_;
2203 last if (/^$start/);
2204 }
2205 close(IN);
2206
2207 if ($list[$#list] !~ /^$start/) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002208 fail "SHA1 $start not found";
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002209 }
2210
2211 # go backwards in the list
2212 @list = reverse @list;
2213
2214 my $save_clean = $noclean;
Steven Rostedt19902072011-06-14 20:46:25 -04002215 my %ignored_warnings;
2216
2217 if (defined($ignore_warnings)) {
2218 foreach my $sha1 (split /\s+/, $ignore_warnings) {
2219 $ignored_warnings{$sha1} = 1;
2220 }
2221 }
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002222
2223 $in_patchcheck = 1;
2224 foreach my $item (@list) {
2225 my $sha1 = $item;
2226 $sha1 =~ s/^([[:xdigit:]]+).*/$1/;
2227
2228 doprint "\nProcessing commit $item\n\n";
2229
2230 run_command "git checkout $sha1" or
2231 die "Failed to checkout $sha1";
2232
2233 # only clean on the first and last patch
2234 if ($item eq $list[0] ||
2235 $item eq $list[$#list]) {
2236 $noclean = $save_clean;
2237 } else {
2238 $noclean = 1;
2239 }
2240
2241 if (defined($minconfig)) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002242 build "useconfig:$minconfig" or return 0;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002243 } else {
2244 # ?? no config to use?
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002245 build "oldconfig" or return 0;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002246 }
2247
Steven Rostedt19902072011-06-14 20:46:25 -04002248
2249 if (!defined($ignored_warnings{$sha1})) {
2250 check_buildlog $sha1 or return 0;
2251 }
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002252
2253 next if ($type eq "build");
2254
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002255 my $failed = 0;
2256
Steven Rostedtddf607e2011-06-14 20:49:13 -04002257 start_monitor_and_boot or $failed = 1;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002258
2259 if (!$failed && $type ne "boot"){
2260 do_run_test or $failed = 1;
2261 }
2262 end_monitor;
2263 return 0 if ($failed);
2264
Steven Rostedt27d934b2011-05-20 09:18:18 -04002265 patchcheck_reboot;
2266
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002267 }
2268 $in_patchcheck = 0;
2269 success $i;
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002270
2271 return 1;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002272}
2273
Steven Rostedtb9066f62011-07-15 21:25:24 -04002274my %depends;
2275my $iflevel = 0;
2276my @ifdeps;
2277
2278# prevent recursion
2279my %read_kconfigs;
2280
2281# taken from streamline_config.pl
2282sub read_kconfig {
2283 my ($kconfig) = @_;
2284
2285 my $state = "NONE";
2286 my $config;
2287 my @kconfigs;
2288
2289 my $cont = 0;
2290 my $line;
2291
2292
2293 if (! -f $kconfig) {
2294 doprint "file $kconfig does not exist, skipping\n";
2295 return;
2296 }
2297
2298 open(KIN, "$kconfig")
2299 or die "Can't open $kconfig";
2300 while (<KIN>) {
2301 chomp;
2302
2303 # Make sure that lines ending with \ continue
2304 if ($cont) {
2305 $_ = $line . " " . $_;
2306 }
2307
2308 if (s/\\$//) {
2309 $cont = 1;
2310 $line = $_;
2311 next;
2312 }
2313
2314 $cont = 0;
2315
2316 # collect any Kconfig sources
2317 if (/^source\s*"(.*)"/) {
2318 $kconfigs[$#kconfigs+1] = $1;
2319 }
2320
2321 # configs found
2322 if (/^\s*(menu)?config\s+(\S+)\s*$/) {
2323 $state = "NEW";
2324 $config = $2;
2325
2326 for (my $i = 0; $i < $iflevel; $i++) {
2327 if ($i) {
2328 $depends{$config} .= " " . $ifdeps[$i];
2329 } else {
2330 $depends{$config} = $ifdeps[$i];
2331 }
2332 $state = "DEP";
2333 }
2334
2335 # collect the depends for the config
2336 } elsif ($state eq "NEW" && /^\s*depends\s+on\s+(.*)$/) {
2337
2338 if (defined($depends{$1})) {
2339 $depends{$config} .= " " . $1;
2340 } else {
2341 $depends{$config} = $1;
2342 }
2343
2344 # Get the configs that select this config
2345 } elsif ($state ne "NONE" && /^\s*select\s+(\S+)/) {
2346 if (defined($depends{$1})) {
2347 $depends{$1} .= " " . $config;
2348 } else {
2349 $depends{$1} = $config;
2350 }
2351
2352 # Check for if statements
2353 } elsif (/^if\s+(.*\S)\s*$/) {
2354 my $deps = $1;
2355 # remove beginning and ending non text
2356 $deps =~ s/^[^a-zA-Z0-9_]*//;
2357 $deps =~ s/[^a-zA-Z0-9_]*$//;
2358
2359 my @deps = split /[^a-zA-Z0-9_]+/, $deps;
2360
2361 $ifdeps[$iflevel++] = join ':', @deps;
2362
2363 } elsif (/^endif/) {
2364
2365 $iflevel-- if ($iflevel);
2366
2367 # stop on "help"
2368 } elsif (/^\s*help\s*$/) {
2369 $state = "NONE";
2370 }
2371 }
2372 close(KIN);
2373
2374 # read in any configs that were found.
2375 foreach $kconfig (@kconfigs) {
2376 if (!defined($read_kconfigs{$kconfig})) {
2377 $read_kconfigs{$kconfig} = 1;
2378 read_kconfig("$builddir/$kconfig");
2379 }
2380 }
2381}
2382
2383sub read_depends {
2384 # find out which arch this is by the kconfig file
2385 open (IN, $output_config)
2386 or dodie "Failed to read $output_config";
2387 my $arch;
2388 while (<IN>) {
2389 if (m,Linux/(\S+)\s+\S+\s+Kernel Configuration,) {
2390 $arch = $1;
2391 last;
2392 }
2393 }
2394 close IN;
2395
2396 if (!defined($arch)) {
2397 doprint "Could not find arch from config file\n";
2398 doprint "no dependencies used\n";
2399 return;
2400 }
2401
2402 # arch is really the subarch, we need to know
2403 # what directory to look at.
2404 if ($arch eq "i386" || $arch eq "x86_64") {
2405 $arch = "x86";
2406 } elsif ($arch =~ /^tile/) {
2407 $arch = "tile";
2408 }
2409
2410 my $kconfig = "$builddir/arch/$arch/Kconfig";
2411
2412 if (! -f $kconfig && $arch =~ /\d$/) {
2413 my $orig = $arch;
2414 # some subarchs have numbers, truncate them
2415 $arch =~ s/\d*$//;
2416 $kconfig = "$builddir/arch/$arch/Kconfig";
2417 if (! -f $kconfig) {
2418 doprint "No idea what arch dir $orig is for\n";
2419 doprint "no dependencies used\n";
2420 return;
2421 }
2422 }
2423
2424 read_kconfig($kconfig);
2425}
2426
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002427sub read_config_list {
2428 my ($config) = @_;
2429
2430 open (IN, $config)
2431 or dodie "Failed to read $config";
2432
2433 while (<IN>) {
2434 if (/^((CONFIG\S*)=.*)/) {
2435 if (!defined($config_ignore{$2})) {
2436 $config_list{$2} = $1;
2437 }
2438 }
2439 }
2440
2441 close(IN);
2442}
2443
2444sub read_output_config {
2445 my ($config) = @_;
2446
2447 assign_configs \%config_ignore, $config;
2448}
2449
2450sub make_new_config {
2451 my @configs = @_;
2452
2453 open (OUT, ">$output_config")
2454 or dodie "Failed to write $output_config";
2455
2456 foreach my $config (@configs) {
2457 print OUT "$config\n";
2458 }
2459 close OUT;
2460}
2461
Steven Rostedtb9066f62011-07-15 21:25:24 -04002462sub get_depends {
2463 my ($dep) = @_;
2464
2465 my $kconfig = $dep;
2466 $kconfig =~ s/CONFIG_//;
2467
2468 $dep = $depends{"$kconfig"};
2469
2470 # the dep string we have saves the dependencies as they
2471 # were found, including expressions like ! && ||. We
2472 # want to split this out into just an array of configs.
2473
2474 my $valid = "A-Za-z_0-9";
2475
2476 my @configs;
2477
2478 while ($dep =~ /[$valid]/) {
2479
2480 if ($dep =~ /^[^$valid]*([$valid]+)/) {
2481 my $conf = "CONFIG_" . $1;
2482
2483 $configs[$#configs + 1] = $conf;
2484
2485 $dep =~ s/^[^$valid]*[$valid]+//;
2486 } else {
2487 die "this should never happen";
2488 }
2489 }
2490
2491 return @configs;
2492}
2493
2494my %min_configs;
2495my %keep_configs;
Steven Rostedt43d1b652011-07-15 22:01:56 -04002496my %save_configs;
Steven Rostedtb9066f62011-07-15 21:25:24 -04002497my %processed_configs;
2498my %nochange_config;
2499
2500sub test_this_config {
2501 my ($config) = @_;
2502
2503 my $found;
2504
2505 # if we already processed this config, skip it
2506 if (defined($processed_configs{$config})) {
2507 return undef;
2508 }
2509 $processed_configs{$config} = 1;
2510
2511 # if this config failed during this round, skip it
2512 if (defined($nochange_config{$config})) {
2513 return undef;
2514 }
2515
2516 my $kconfig = $config;
2517 $kconfig =~ s/CONFIG_//;
2518
2519 # Test dependencies first
2520 if (defined($depends{"$kconfig"})) {
2521 my @parents = get_depends $config;
2522 foreach my $parent (@parents) {
2523 # if the parent is in the min config, check it first
2524 next if (!defined($min_configs{$parent}));
2525 $found = test_this_config($parent);
2526 if (defined($found)) {
2527 return $found;
2528 }
2529 }
2530 }
2531
2532 # Remove this config from the list of configs
2533 # do a make oldnoconfig and then read the resulting
2534 # .config to make sure it is missing the config that
2535 # we had before
2536 my %configs = %min_configs;
2537 delete $configs{$config};
2538 make_new_config ((values %configs), (values %keep_configs));
2539 make_oldconfig;
2540 undef %configs;
2541 assign_configs \%configs, $output_config;
2542
2543 return $config if (!defined($configs{$config}));
2544
2545 doprint "disabling config $config did not change .config\n";
2546
2547 $nochange_config{$config} = 1;
2548
2549 return undef;
2550}
2551
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002552sub make_min_config {
2553 my ($i) = @_;
2554
2555 if (!defined($output_minconfig)) {
2556 fail "OUTPUT_MIN_CONFIG not defined" and return;
2557 }
Steven Rostedt35ce5952011-07-15 21:57:25 -04002558
2559 # If output_minconfig exists, and the start_minconfig
2560 # came from min_config, than ask if we should use
2561 # that instead.
2562 if (-f $output_minconfig && !$start_minconfig_defined) {
2563 print "$output_minconfig exists\n";
2564 if (read_yn " Use it as minconfig?") {
2565 $start_minconfig = $output_minconfig;
2566 }
2567 }
2568
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002569 if (!defined($start_minconfig)) {
2570 fail "START_MIN_CONFIG or MIN_CONFIG not defined" and return;
2571 }
2572
Steven Rostedt35ce5952011-07-15 21:57:25 -04002573 my $temp_config = "$tmpdir/temp_config";
2574
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002575 # First things first. We build an allnoconfig to find
2576 # out what the defaults are that we can't touch.
2577 # Some are selections, but we really can't handle selections.
2578
2579 my $save_minconfig = $minconfig;
2580 undef $minconfig;
2581
2582 run_command "$make allnoconfig" or return 0;
2583
Steven Rostedtb9066f62011-07-15 21:25:24 -04002584 read_depends;
2585
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002586 process_config_ignore $output_config;
Steven Rostedtb9066f62011-07-15 21:25:24 -04002587
Steven Rostedt43d1b652011-07-15 22:01:56 -04002588 undef %save_configs;
Steven Rostedtb9066f62011-07-15 21:25:24 -04002589 undef %min_configs;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002590
2591 if (defined($ignore_config)) {
2592 # make sure the file exists
2593 `touch $ignore_config`;
Steven Rostedt43d1b652011-07-15 22:01:56 -04002594 assign_configs \%save_configs, $ignore_config;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002595 }
2596
Steven Rostedt43d1b652011-07-15 22:01:56 -04002597 %keep_configs = %save_configs;
2598
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002599 doprint "Load initial configs from $start_minconfig\n";
2600
2601 # Look at the current min configs, and save off all the
2602 # ones that were set via the allnoconfig
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002603 assign_configs \%min_configs, $start_minconfig;
2604
2605 my @config_keys = keys %min_configs;
2606
2607 # Remove anything that was set by the make allnoconfig
2608 # we shouldn't need them as they get set for us anyway.
2609 foreach my $config (@config_keys) {
2610 # Remove anything in the ignore_config
2611 if (defined($keep_configs{$config})) {
2612 my $file = $ignore_config;
2613 $file =~ s,.*/(.*?)$,$1,;
2614 doprint "$config set by $file ... ignored\n";
2615 delete $min_configs{$config};
2616 next;
2617 }
2618 # But make sure the settings are the same. If a min config
2619 # sets a selection, we do not want to get rid of it if
2620 # it is not the same as what we have. Just move it into
2621 # the keep configs.
2622 if (defined($config_ignore{$config})) {
2623 if ($config_ignore{$config} ne $min_configs{$config}) {
2624 doprint "$config is in allnoconfig as '$config_ignore{$config}'";
2625 doprint " but it is '$min_configs{$config}' in minconfig .. keeping\n";
2626 $keep_configs{$config} = $min_configs{$config};
2627 } else {
2628 doprint "$config set by allnoconfig ... ignored\n";
2629 }
2630 delete $min_configs{$config};
2631 }
2632 }
2633
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002634 my $done = 0;
Steven Rostedtb9066f62011-07-15 21:25:24 -04002635 my $take_two = 0;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002636
2637 while (!$done) {
2638
2639 my $config;
2640 my $found;
2641
2642 # Now disable each config one by one and do a make oldconfig
2643 # till we find a config that changes our list.
2644
2645 # Put configs that did not modify the config at the end.
2646 my @test_configs = keys %min_configs;
2647 my $reset = 1;
2648 for (my $i = 0; $i < $#test_configs; $i++) {
2649 if (!defined($nochange_config{$test_configs[0]})) {
2650 $reset = 0;
2651 last;
2652 }
2653 # This config didn't change the .config last time.
2654 # Place it at the end
2655 my $config = shift @test_configs;
2656 push @test_configs, $config;
2657 }
2658
2659 # if every test config has failed to modify the .config file
2660 # in the past, then reset and start over.
2661 if ($reset) {
2662 undef %nochange_config;
2663 }
2664
Steven Rostedtb9066f62011-07-15 21:25:24 -04002665 undef %processed_configs;
2666
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002667 foreach my $config (@test_configs) {
2668
Steven Rostedtb9066f62011-07-15 21:25:24 -04002669 $found = test_this_config $config;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002670
Steven Rostedtb9066f62011-07-15 21:25:24 -04002671 last if (defined($found));
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002672
2673 # oh well, try another config
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002674 }
2675
2676 if (!defined($found)) {
Steven Rostedtb9066f62011-07-15 21:25:24 -04002677 # we could have failed due to the nochange_config hash
2678 # reset and try again
2679 if (!$take_two) {
2680 undef %nochange_config;
2681 $take_two = 1;
2682 next;
2683 }
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002684 doprint "No more configs found that we can disable\n";
2685 $done = 1;
2686 last;
2687 }
Steven Rostedtb9066f62011-07-15 21:25:24 -04002688 $take_two = 0;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002689
2690 $config = $found;
2691
2692 doprint "Test with $config disabled\n";
2693
2694 # set in_bisect to keep build and monitor from dieing
2695 $in_bisect = 1;
2696
2697 my $failed = 0;
2698 build "oldconfig";
2699 start_monitor_and_boot or $failed = 1;
2700 end_monitor;
2701
2702 $in_bisect = 0;
2703
2704 if ($failed) {
Steven Rostedtb9066f62011-07-15 21:25:24 -04002705 doprint "$min_configs{$config} is needed to boot the box... keeping\n";
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002706 # this config is needed, add it to the ignore list.
2707 $keep_configs{$config} = $min_configs{$config};
Steven Rostedt43d1b652011-07-15 22:01:56 -04002708 $save_configs{$config} = $min_configs{$config};
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002709 delete $min_configs{$config};
Steven Rostedt35ce5952011-07-15 21:57:25 -04002710
2711 # update new ignore configs
2712 if (defined($ignore_config)) {
2713 open (OUT, ">$temp_config")
2714 or die "Can't write to $temp_config";
Steven Rostedt43d1b652011-07-15 22:01:56 -04002715 foreach my $config (keys %save_configs) {
2716 print OUT "$save_configs{$config}\n";
Steven Rostedt35ce5952011-07-15 21:57:25 -04002717 }
2718 close OUT;
2719 run_command "mv $temp_config $ignore_config" or
2720 dodie "failed to copy update to $ignore_config";
2721 }
2722
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002723 } else {
2724 # We booted without this config, remove it from the minconfigs.
2725 doprint "$config is not needed, disabling\n";
2726
2727 delete $min_configs{$config};
2728
2729 # Also disable anything that is not enabled in this config
2730 my %configs;
2731 assign_configs \%configs, $output_config;
2732 my @config_keys = keys %min_configs;
2733 foreach my $config (@config_keys) {
2734 if (!defined($configs{$config})) {
2735 doprint "$config is not set, disabling\n";
2736 delete $min_configs{$config};
2737 }
2738 }
2739
2740 # Save off all the current mandidory configs
Steven Rostedt35ce5952011-07-15 21:57:25 -04002741 open (OUT, ">$temp_config")
2742 or die "Can't write to $temp_config";
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002743 foreach my $config (keys %keep_configs) {
2744 print OUT "$keep_configs{$config}\n";
2745 }
2746 foreach my $config (keys %min_configs) {
2747 print OUT "$min_configs{$config}\n";
2748 }
2749 close OUT;
Steven Rostedt35ce5952011-07-15 21:57:25 -04002750
2751 run_command "mv $temp_config $output_minconfig" or
2752 dodie "failed to copy update to $output_minconfig";
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002753 }
2754
2755 doprint "Reboot and wait $sleep_time seconds\n";
Andrew Jones2728be42011-08-12 15:32:05 +02002756 reboot $sleep_time;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002757 }
2758
2759 success $i;
2760 return 1;
2761}
2762
Steven Rostedt8d1491b2010-11-18 15:39:48 -05002763$#ARGV < 1 or die "ktest.pl version: $VERSION\n usage: ktest.pl config-file\n";
Steven Rostedt2545eb62010-11-02 15:01:32 -04002764
Steven Rostedt8d1491b2010-11-18 15:39:48 -05002765if ($#ARGV == 0) {
2766 $ktest_config = $ARGV[0];
2767 if (! -f $ktest_config) {
2768 print "$ktest_config does not exist.\n";
Steven Rostedt35ce5952011-07-15 21:57:25 -04002769 if (!read_yn "Create it?") {
Steven Rostedt8d1491b2010-11-18 15:39:48 -05002770 exit 0;
2771 }
2772 }
2773} else {
2774 $ktest_config = "ktest.conf";
2775}
2776
2777if (! -f $ktest_config) {
2778 open(OUT, ">$ktest_config") or die "Can not create $ktest_config";
2779 print OUT << "EOF"
2780# Generated by ktest.pl
2781#
2782# Define each test with TEST_START
2783# The config options below it will override the defaults
2784TEST_START
2785
2786DEFAULTS
2787EOF
2788;
2789 close(OUT);
2790}
2791read_config $ktest_config;
2792
Steven Rostedt23715c3c2011-06-13 11:03:34 -04002793if (defined($opt{"LOG_FILE"})) {
2794 $opt{"LOG_FILE"} = eval_option($opt{"LOG_FILE"}, -1);
2795}
2796
Steven Rostedt8d1491b2010-11-18 15:39:48 -05002797# Append any configs entered in manually to the config file.
2798my @new_configs = keys %entered_configs;
2799if ($#new_configs >= 0) {
2800 print "\nAppending entered in configs to $ktest_config\n";
2801 open(OUT, ">>$ktest_config") or die "Can not append to $ktest_config";
2802 foreach my $config (@new_configs) {
2803 print OUT "$config = $entered_configs{$config}\n";
2804 $opt{$config} = $entered_configs{$config};
2805 }
2806}
Steven Rostedt2545eb62010-11-02 15:01:32 -04002807
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002808if ($opt{"CLEAR_LOG"} && defined($opt{"LOG_FILE"})) {
2809 unlink $opt{"LOG_FILE"};
2810}
Steven Rostedt2545eb62010-11-02 15:01:32 -04002811
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002812doprint "\n\nSTARTING AUTOMATED TESTS\n\n";
2813
Steven Rostedta57419b2010-11-02 15:13:54 -04002814for (my $i = 0, my $repeat = 1; $i <= $opt{"NUM_TESTS"}; $i += $repeat) {
2815
2816 if (!$i) {
2817 doprint "DEFAULT OPTIONS:\n";
2818 } else {
2819 doprint "\nTEST $i OPTIONS";
2820 if (defined($repeat_tests{$i})) {
2821 $repeat = $repeat_tests{$i};
2822 doprint " ITERATE $repeat";
2823 }
2824 doprint "\n";
2825 }
2826
2827 foreach my $option (sort keys %opt) {
2828
2829 if ($option =~ /\[(\d+)\]$/) {
2830 next if ($i != $1);
2831 } else {
2832 next if ($i);
2833 }
2834
2835 doprint "$option = $opt{$option}\n";
2836 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002837}
Steven Rostedt2545eb62010-11-02 15:01:32 -04002838
Steven Rostedt2a625122011-05-20 15:48:59 -04002839sub __set_test_option {
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002840 my ($name, $i) = @_;
2841
2842 my $option = "$name\[$i\]";
2843
2844 if (defined($opt{$option})) {
2845 return $opt{$option};
2846 }
2847
Steven Rostedta57419b2010-11-02 15:13:54 -04002848 foreach my $test (keys %repeat_tests) {
2849 if ($i >= $test &&
2850 $i < $test + $repeat_tests{$test}) {
2851 $option = "$name\[$test\]";
2852 if (defined($opt{$option})) {
2853 return $opt{$option};
2854 }
2855 }
2856 }
2857
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002858 if (defined($opt{$name})) {
2859 return $opt{$name};
2860 }
2861
2862 return undef;
2863}
2864
Steven Rostedt2a625122011-05-20 15:48:59 -04002865sub set_test_option {
2866 my ($name, $i) = @_;
2867
2868 my $option = __set_test_option($name, $i);
2869 return $option if (!defined($option));
2870
Steven Rostedt23715c3c2011-06-13 11:03:34 -04002871 return eval_option($option, $i);
Steven Rostedt2a625122011-05-20 15:48:59 -04002872}
2873
Steven Rostedt2545eb62010-11-02 15:01:32 -04002874# First we need to do is the builds
Steven Rostedta75fece2010-11-02 14:58:27 -04002875for (my $i = 1; $i <= $opt{"NUM_TESTS"}; $i++) {
Steven Rostedt2545eb62010-11-02 15:01:32 -04002876
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04002877 # Do not reboot on failing test options
2878 $no_reboot = 1;
2879
Steven Rostedt576f6272010-11-02 14:58:38 -04002880 $iteration = $i;
2881
Steven Rostedta75fece2010-11-02 14:58:27 -04002882 my $makecmd = set_test_option("MAKE_CMD", $i);
2883
2884 $machine = set_test_option("MACHINE", $i);
Steven Rostedte48c5292010-11-02 14:35:37 -04002885 $ssh_user = set_test_option("SSH_USER", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002886 $tmpdir = set_test_option("TMP_DIR", $i);
2887 $outputdir = set_test_option("OUTPUT_DIR", $i);
2888 $builddir = set_test_option("BUILD_DIR", $i);
2889 $test_type = set_test_option("TEST_TYPE", $i);
2890 $build_type = set_test_option("BUILD_TYPE", $i);
2891 $build_options = set_test_option("BUILD_OPTIONS", $i);
Steven Rostedt0bd6c1a2011-06-14 20:39:31 -04002892 $pre_build = set_test_option("PRE_BUILD", $i);
2893 $post_build = set_test_option("POST_BUILD", $i);
2894 $pre_build_die = set_test_option("PRE_BUILD_DIE", $i);
2895 $post_build_die = set_test_option("POST_BUILD_DIE", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002896 $power_cycle = set_test_option("POWER_CYCLE", $i);
Steven Rostedte48c5292010-11-02 14:35:37 -04002897 $reboot = set_test_option("REBOOT", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002898 $noclean = set_test_option("BUILD_NOCLEAN", $i);
2899 $minconfig = set_test_option("MIN_CONFIG", $i);
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002900 $output_minconfig = set_test_option("OUTPUT_MIN_CONFIG", $i);
2901 $start_minconfig = set_test_option("START_MIN_CONFIG", $i);
2902 $ignore_config = set_test_option("IGNORE_CONFIG", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002903 $run_test = set_test_option("TEST", $i);
2904 $addconfig = set_test_option("ADD_CONFIG", $i);
2905 $reboot_type = set_test_option("REBOOT_TYPE", $i);
2906 $grub_menu = set_test_option("GRUB_MENU", $i);
Steven Rostedt8b37ca82010-11-02 14:58:33 -04002907 $post_install = set_test_option("POST_INSTALL", $i);
Steven Rostedte0a87422011-09-30 17:50:48 -04002908 $no_install = set_test_option("NO_INSTALL", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002909 $reboot_script = set_test_option("REBOOT_SCRIPT", $i);
2910 $reboot_on_error = set_test_option("REBOOT_ON_ERROR", $i);
2911 $poweroff_on_error = set_test_option("POWEROFF_ON_ERROR", $i);
2912 $die_on_failure = set_test_option("DIE_ON_FAILURE", $i);
2913 $power_off = set_test_option("POWER_OFF", $i);
Steven Rostedt576f6272010-11-02 14:58:38 -04002914 $powercycle_after_reboot = set_test_option("POWERCYCLE_AFTER_REBOOT", $i);
2915 $poweroff_after_halt = set_test_option("POWEROFF_AFTER_HALT", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002916 $sleep_time = set_test_option("SLEEP_TIME", $i);
2917 $bisect_sleep_time = set_test_option("BISECT_SLEEP_TIME", $i);
Steven Rostedt27d934b2011-05-20 09:18:18 -04002918 $patchcheck_sleep_time = set_test_option("PATCHCHECK_SLEEP_TIME", $i);
Steven Rostedt19902072011-06-14 20:46:25 -04002919 $ignore_warnings = set_test_option("IGNORE_WARNINGS", $i);
Steven Rostedtc960bb92011-03-08 09:22:39 -05002920 $bisect_manual = set_test_option("BISECT_MANUAL", $i);
Steven Rostedtc23dca72011-03-08 09:26:31 -05002921 $bisect_skip = set_test_option("BISECT_SKIP", $i);
Steven Rostedt30f75da2011-06-13 10:35:35 -04002922 $config_bisect_good = set_test_option("CONFIG_BISECT_GOOD", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002923 $store_failures = set_test_option("STORE_FAILURES", $i);
Steven Rostedt9064af52011-06-13 10:38:48 -04002924 $test_name = set_test_option("TEST_NAME", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002925 $timeout = set_test_option("TIMEOUT", $i);
2926 $booted_timeout = set_test_option("BOOTED_TIMEOUT", $i);
2927 $console = set_test_option("CONSOLE", $i);
Steven Rostedtf1a5b962011-06-13 10:30:00 -04002928 $detect_triplefault = set_test_option("DETECT_TRIPLE_FAULT", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002929 $success_line = set_test_option("SUCCESS_LINE", $i);
Steven Rostedt2b803362011-09-30 18:00:23 -04002930 $reboot_success_line = set_test_option("REBOOT_SUCCESS_LINE", $i);
Steven Rostedt1c8a6172010-11-09 12:55:40 -05002931 $stop_after_success = set_test_option("STOP_AFTER_SUCCESS", $i);
2932 $stop_after_failure = set_test_option("STOP_AFTER_FAILURE", $i);
Steven Rostedt2d01b262011-03-08 09:47:54 -05002933 $stop_test_after = set_test_option("STOP_TEST_AFTER", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002934 $build_target = set_test_option("BUILD_TARGET", $i);
Steven Rostedte48c5292010-11-02 14:35:37 -04002935 $ssh_exec = set_test_option("SSH_EXEC", $i);
2936 $scp_to_target = set_test_option("SCP_TO_TARGET", $i);
Steven Rostedta75fece2010-11-02 14:58:27 -04002937 $target_image = set_test_option("TARGET_IMAGE", $i);
2938 $localversion = set_test_option("LOCALVERSION", $i);
2939
Steven Rostedt35ce5952011-07-15 21:57:25 -04002940 $start_minconfig_defined = 1;
2941
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002942 if (!defined($start_minconfig)) {
Steven Rostedt35ce5952011-07-15 21:57:25 -04002943 $start_minconfig_defined = 0;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002944 $start_minconfig = $minconfig;
2945 }
2946
Steven Rostedta75fece2010-11-02 14:58:27 -04002947 chdir $builddir || die "can't change directory to $builddir";
2948
Andrew Jonesa908a662011-08-12 15:32:03 +02002949 foreach my $dir ($tmpdir, $outputdir) {
2950 if (!-d $dir) {
2951 mkpath($dir) or
2952 die "can't create $dir";
2953 }
Steven Rostedta75fece2010-11-02 14:58:27 -04002954 }
2955
Steven Rostedte48c5292010-11-02 14:35:37 -04002956 $ENV{"SSH_USER"} = $ssh_user;
2957 $ENV{"MACHINE"} = $machine;
2958
Steven Rostedta75fece2010-11-02 14:58:27 -04002959 $target = "$ssh_user\@$machine";
2960
2961 $buildlog = "$tmpdir/buildlog-$machine";
2962 $dmesg = "$tmpdir/dmesg-$machine";
2963 $make = "$makecmd O=$outputdir";
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05002964 $output_config = "$outputdir/.config";
Steven Rostedta75fece2010-11-02 14:58:27 -04002965
2966 if ($reboot_type eq "grub") {
Steven Rostedt576f6272010-11-02 14:58:38 -04002967 dodie "GRUB_MENU not defined" if (!defined($grub_menu));
Steven Rostedta75fece2010-11-02 14:58:27 -04002968 } elsif (!defined($reboot_script)) {
Steven Rostedt576f6272010-11-02 14:58:38 -04002969 dodie "REBOOT_SCRIPT not defined"
Steven Rostedta75fece2010-11-02 14:58:27 -04002970 }
2971
2972 my $run_type = $build_type;
2973 if ($test_type eq "patchcheck") {
2974 $run_type = $opt{"PATCHCHECK_TYPE[$i]"};
2975 } elsif ($test_type eq "bisect") {
2976 $run_type = $opt{"BISECT_TYPE[$i]"};
Steven Rostedt0a05c762010-11-08 11:14:10 -05002977 } elsif ($test_type eq "config_bisect") {
2978 $run_type = $opt{"CONFIG_BISECT_TYPE[$i]"};
Steven Rostedta75fece2010-11-02 14:58:27 -04002979 }
2980
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002981 if ($test_type eq "make_min_config") {
2982 $run_type = "";
2983 }
2984
Steven Rostedta75fece2010-11-02 14:58:27 -04002985 # mistake in config file?
2986 if (!defined($run_type)) {
2987 $run_type = "ERROR";
2988 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04002989
Steven Rostedte0a87422011-09-30 17:50:48 -04002990 my $installme = "";
2991 $installme = " no_install" if ($no_install);
2992
Steven Rostedt2545eb62010-11-02 15:01:32 -04002993 doprint "\n\n";
Steven Rostedte0a87422011-09-30 17:50:48 -04002994 doprint "RUNNING TEST $i of $opt{NUM_TESTS} with option $test_type $run_type$installme\n\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002995
2996 unlink $dmesg;
2997 unlink $buildlog;
Steven Rostedt2545eb62010-11-02 15:01:32 -04002998
Steven Rostedt250bae82011-07-15 22:05:59 -04002999 if (defined($addconfig)) {
3000 my $min = $minconfig;
3001 if (!defined($minconfig)) {
3002 $min = "";
3003 }
3004 run_command "cat $addconfig $min > $tmpdir/add_config" or
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04003005 dodie "Failed to create temp config";
Steven Rostedt9be2e6b2010-11-09 12:20:21 -05003006 $minconfig = "$tmpdir/add_config";
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04003007 }
3008
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04003009 my $checkout = $opt{"CHECKOUT[$i]"};
3010 if (defined($checkout)) {
3011 run_command "git checkout $checkout" or
3012 die "failed to checkout $checkout";
3013 }
3014
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04003015 $no_reboot = 0;
3016
3017
Steven Rostedta75fece2010-11-02 14:58:27 -04003018 if ($test_type eq "bisect") {
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04003019 bisect $i;
3020 next;
Steven Rostedt0a05c762010-11-08 11:14:10 -05003021 } elsif ($test_type eq "config_bisect") {
3022 config_bisect $i;
3023 next;
Steven Rostedta75fece2010-11-02 14:58:27 -04003024 } elsif ($test_type eq "patchcheck") {
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04003025 patchcheck $i;
3026 next;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003027 } elsif ($test_type eq "make_min_config") {
3028 make_min_config $i;
3029 next;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04003030 }
3031
Steven Rostedt7faafbd2010-11-02 14:58:22 -04003032 if ($build_type ne "nobuild") {
3033 build $build_type or next;
Steven Rostedt2545eb62010-11-02 15:01:32 -04003034 }
3035
Steven Rostedtcd8e3682011-08-18 16:35:44 -04003036 if ($test_type eq "install") {
3037 get_version;
3038 install;
3039 success $i;
3040 next;
3041 }
3042
Steven Rostedta75fece2010-11-02 14:58:27 -04003043 if ($test_type ne "build") {
Steven Rostedta75fece2010-11-02 14:58:27 -04003044 my $failed = 0;
Steven Rostedtddf607e2011-06-14 20:49:13 -04003045 start_monitor_and_boot or $failed = 1;
Steven Rostedta75fece2010-11-02 14:58:27 -04003046
3047 if (!$failed && $test_type ne "boot" && defined($run_test)) {
3048 do_run_test or $failed = 1;
3049 }
3050 end_monitor;
3051 next if ($failed);
Steven Rostedt5a391fb2010-11-02 14:57:43 -04003052 }
3053
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04003054 success $i;
Steven Rostedt2545eb62010-11-02 15:01:32 -04003055}
3056
Steven Rostedt5c42fc52010-11-02 14:57:01 -04003057if ($opt{"POWEROFF_ON_SUCCESS"}) {
Steven Rostedt75c3fda72010-11-02 14:57:21 -04003058 halt;
Steven Rostedt576f6272010-11-02 14:58:38 -04003059} elsif ($opt{"REBOOT_ON_SUCCESS"} && !do_not_reboot) {
Steven Rostedt75c3fda72010-11-02 14:57:21 -04003060 reboot;
Steven Rostedt5c42fc52010-11-02 14:57:01 -04003061}
Steven Rostedt75c3fda72010-11-02 14:57:21 -04003062
Steven Rostedte48c5292010-11-02 14:35:37 -04003063doprint "\n $successes of $opt{NUM_TESTS} tests were successful\n\n";
3064
Steven Rostedt2545eb62010-11-02 15:01:32 -04003065exit 0;