blob: 2b63190c9f64da458ea28111a642d6a7204591be [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 Rostedt2545eb62010-11-02 15:01:32 -040021
22#default opts
Steven Rostedt4f43e0d2011-12-22 21:32:05 -050023my %default = (
24 "NUM_TESTS" => 1,
25 "TEST_TYPE" => "build",
26 "BUILD_TYPE" => "randconfig",
27 "MAKE_CMD" => "make",
28 "TIMEOUT" => 120,
29 "TMP_DIR" => "/tmp/ktest/\${MACHINE}",
30 "SLEEP_TIME" => 60, # sleep time between tests
31 "BUILD_NOCLEAN" => 0,
32 "REBOOT_ON_ERROR" => 0,
33 "POWEROFF_ON_ERROR" => 0,
34 "REBOOT_ON_SUCCESS" => 1,
35 "POWEROFF_ON_SUCCESS" => 0,
36 "BUILD_OPTIONS" => "",
37 "BISECT_SLEEP_TIME" => 60, # sleep time between bisects
38 "PATCHCHECK_SLEEP_TIME" => 60, # sleep time between patch checks
39 "CLEAR_LOG" => 0,
40 "BISECT_MANUAL" => 0,
41 "BISECT_SKIP" => 1,
42 "SUCCESS_LINE" => "login:",
43 "DETECT_TRIPLE_FAULT" => 1,
44 "NO_INSTALL" => 0,
45 "BOOTED_TIMEOUT" => 1,
46 "DIE_ON_FAILURE" => 1,
47 "SSH_EXEC" => "ssh \$SSH_USER\@\$MACHINE \$SSH_COMMAND",
48 "SCP_TO_TARGET" => "scp \$SRC_FILE \$SSH_USER\@\$MACHINE:\$DST_FILE",
49 "REBOOT" => "ssh \$SSH_USER\@\$MACHINE reboot",
50 "STOP_AFTER_SUCCESS" => 10,
51 "STOP_AFTER_FAILURE" => 60,
52 "STOP_TEST_AFTER" => 600,
Steven Rostedt600bbf02011-11-21 20:12:04 -050053
54# required, and we will ask users if they don't have them but we keep the default
55# value something that is common.
Steven Rostedt4f43e0d2011-12-22 21:32:05 -050056 "REBOOT_TYPE" => "grub",
57 "LOCALVERSION" => "-test",
58 "SSH_USER" => "root",
59 "BUILD_TARGET" => "arch/x86/boot/bzImage",
60 "TARGET_IMAGE" => "/boot/vmlinuz-test",
Steven Rostedt9cc9e092011-12-22 21:37:22 -050061
62 "LOG_FILE" => undef,
63 "IGNORE_UNUSED" => 0,
Steven Rostedt4f43e0d2011-12-22 21:32:05 -050064);
Steven Rostedt2545eb62010-11-02 15:01:32 -040065
Steven Rostedt8d1491b2010-11-18 15:39:48 -050066my $ktest_config;
Steven Rostedt2545eb62010-11-02 15:01:32 -040067my $version;
Steven Rostedta75fece2010-11-02 14:58:27 -040068my $machine;
Steven Rostedte48c5292010-11-02 14:35:37 -040069my $ssh_user;
Steven Rostedta75fece2010-11-02 14:58:27 -040070my $tmpdir;
71my $builddir;
72my $outputdir;
Steven Rostedt51ad1dd2010-11-08 16:43:21 -050073my $output_config;
Steven Rostedta75fece2010-11-02 14:58:27 -040074my $test_type;
Steven Rostedt7faafbd2010-11-02 14:58:22 -040075my $build_type;
Steven Rostedta75fece2010-11-02 14:58:27 -040076my $build_options;
Steven Rostedt0bd6c1a2011-06-14 20:39:31 -040077my $pre_build;
78my $post_build;
79my $pre_build_die;
80my $post_build_die;
Steven Rostedta75fece2010-11-02 14:58:27 -040081my $reboot_type;
82my $reboot_script;
83my $power_cycle;
Steven Rostedte48c5292010-11-02 14:35:37 -040084my $reboot;
Steven Rostedta75fece2010-11-02 14:58:27 -040085my $reboot_on_error;
Steven Rostedtbc7c5802011-12-22 16:29:10 -050086my $switch_to_good;
87my $switch_to_test;
Steven Rostedta75fece2010-11-02 14:58:27 -040088my $poweroff_on_error;
89my $die_on_failure;
Steven Rostedt576f6272010-11-02 14:58:38 -040090my $powercycle_after_reboot;
91my $poweroff_after_halt;
Steven Rostedte48c5292010-11-02 14:35:37 -040092my $ssh_exec;
93my $scp_to_target;
Steven Rostedta75fece2010-11-02 14:58:27 -040094my $power_off;
95my $grub_menu;
Steven Rostedt2545eb62010-11-02 15:01:32 -040096my $grub_number;
97my $target;
98my $make;
Steven Rostedt8b37ca82010-11-02 14:58:33 -040099my $post_install;
Steven Rostedte0a87422011-09-30 17:50:48 -0400100my $no_install;
Steven Rostedt5c42fc52010-11-02 14:57:01 -0400101my $noclean;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400102my $minconfig;
Steven Rostedt4c4ab122011-07-15 21:16:17 -0400103my $start_minconfig;
Steven Rostedt35ce5952011-07-15 21:57:25 -0400104my $start_minconfig_defined;
Steven Rostedt4c4ab122011-07-15 21:16:17 -0400105my $output_minconfig;
106my $ignore_config;
Steven Rostedtbe405f92012-01-04 21:51:59 -0500107my $ignore_errors;
Steven Rostedt2b7d9b22010-11-02 14:58:15 -0400108my $addconfig;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -0400109my $in_bisect = 0;
Steven Rostedtb5f4aea2011-12-22 21:33:55 -0500110my $bisect_bad_commit = "";
Steven Rostedtd6ce2a02010-11-02 14:58:05 -0400111my $reverse_bisect;
Steven Rostedtc960bb92011-03-08 09:22:39 -0500112my $bisect_manual;
Steven Rostedtc23dca72011-03-08 09:26:31 -0500113my $bisect_skip;
Steven Rostedt30f75da2011-06-13 10:35:35 -0400114my $config_bisect_good;
Steven Rostedtc5dacb82011-12-22 12:43:57 -0500115my $bisect_ret_good;
116my $bisect_ret_bad;
117my $bisect_ret_skip;
118my $bisect_ret_abort;
119my $bisect_ret_default;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -0400120my $in_patchcheck = 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -0400121my $run_test;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -0400122my $redirect;
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400123my $buildlog;
Rabin Vincenta9dd5d62011-11-18 17:05:29 +0530124my $testlog;
Steven Rostedt7faafbd2010-11-02 14:58:22 -0400125my $dmesg;
126my $monitor_fp;
127my $monitor_pid;
128my $monitor_cnt = 0;
Steven Rostedta75fece2010-11-02 14:58:27 -0400129my $sleep_time;
130my $bisect_sleep_time;
Steven Rostedt27d934b2011-05-20 09:18:18 -0400131my $patchcheck_sleep_time;
Steven Rostedt19902072011-06-14 20:46:25 -0400132my $ignore_warnings;
Steven Rostedta75fece2010-11-02 14:58:27 -0400133my $store_failures;
Rabin Vincentde5b6e32011-11-18 17:05:31 +0530134my $store_successes;
Steven Rostedt9064af52011-06-13 10:38:48 -0400135my $test_name;
Steven Rostedta75fece2010-11-02 14:58:27 -0400136my $timeout;
137my $booted_timeout;
Steven Rostedtf1a5b962011-06-13 10:30:00 -0400138my $detect_triplefault;
Steven Rostedta75fece2010-11-02 14:58:27 -0400139my $console;
Steven Rostedt2b803362011-09-30 18:00:23 -0400140my $reboot_success_line;
Steven Rostedta75fece2010-11-02 14:58:27 -0400141my $success_line;
Steven Rostedt1c8a6172010-11-09 12:55:40 -0500142my $stop_after_success;
143my $stop_after_failure;
Steven Rostedt2d01b262011-03-08 09:47:54 -0500144my $stop_test_after;
Steven Rostedta75fece2010-11-02 14:58:27 -0400145my $build_target;
146my $target_image;
Steven Rostedtb5f4aea2011-12-22 21:33:55 -0500147my $checkout;
Steven Rostedta75fece2010-11-02 14:58:27 -0400148my $localversion;
Steven Rostedt576f6272010-11-02 14:58:38 -0400149my $iteration = 0;
Steven Rostedte48c5292010-11-02 14:35:37 -0400150my $successes = 0;
Steven Rostedt2545eb62010-11-02 15:01:32 -0400151
Steven Rostedtb5f4aea2011-12-22 21:33:55 -0500152my $bisect_good;
153my $bisect_bad;
154my $bisect_type;
155my $bisect_start;
156my $bisect_replay;
157my $bisect_files;
158my $bisect_reverse;
159my $bisect_check;
160
161my $config_bisect;
162my $config_bisect_type;
163
164my $patchcheck_type;
165my $patchcheck_start;
166my $patchcheck_end;
167
Steven Rostedt165708b2011-11-26 20:56:52 -0500168# set when a test is something other that just building or install
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500169# which would require more options.
170my $buildonly = 1;
171
Steven Rostedtdbd37832011-11-23 16:00:48 -0500172# set when creating a new config
173my $newconfig = 0;
174
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500175my %entered_configs;
176my %config_help;
Steven Rostedt77d942c2011-05-20 13:36:58 -0400177my %variable;
Steven Rostedtfcb3f162011-06-13 10:40:58 -0400178my %force_config;
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500179
Steven Rostedt4ab1cce2011-09-30 18:12:20 -0400180# do not force reboots on config problems
181my $no_reboot = 1;
182
Steven Rostedt9cc9e092011-12-22 21:37:22 -0500183my %option_map = (
184 "MACHINE" => \$machine,
185 "SSH_USER" => \$ssh_user,
186 "TMP_DIR" => \$tmpdir,
187 "OUTPUT_DIR" => \$outputdir,
188 "BUILD_DIR" => \$builddir,
189 "TEST_TYPE" => \$test_type,
190 "BUILD_TYPE" => \$build_type,
191 "BUILD_OPTIONS" => \$build_options,
192 "PRE_BUILD" => \$pre_build,
193 "POST_BUILD" => \$post_build,
194 "PRE_BUILD_DIE" => \$pre_build_die,
195 "POST_BUILD_DIE" => \$post_build_die,
196 "POWER_CYCLE" => \$power_cycle,
197 "REBOOT" => \$reboot,
198 "BUILD_NOCLEAN" => \$noclean,
199 "MIN_CONFIG" => \$minconfig,
200 "OUTPUT_MIN_CONFIG" => \$output_minconfig,
201 "START_MIN_CONFIG" => \$start_minconfig,
202 "IGNORE_CONFIG" => \$ignore_config,
203 "TEST" => \$run_test,
204 "ADD_CONFIG" => \$addconfig,
205 "REBOOT_TYPE" => \$reboot_type,
206 "GRUB_MENU" => \$grub_menu,
207 "POST_INSTALL" => \$post_install,
208 "NO_INSTALL" => \$no_install,
209 "REBOOT_SCRIPT" => \$reboot_script,
210 "REBOOT_ON_ERROR" => \$reboot_on_error,
211 "SWITCH_TO_GOOD" => \$switch_to_good,
212 "SWITCH_TO_TEST" => \$switch_to_test,
213 "POWEROFF_ON_ERROR" => \$poweroff_on_error,
214 "DIE_ON_FAILURE" => \$die_on_failure,
215 "POWER_OFF" => \$power_off,
216 "POWERCYCLE_AFTER_REBOOT" => \$powercycle_after_reboot,
217 "POWEROFF_AFTER_HALT" => \$poweroff_after_halt,
218 "SLEEP_TIME" => \$sleep_time,
219 "BISECT_SLEEP_TIME" => \$bisect_sleep_time,
220 "PATCHCHECK_SLEEP_TIME" => \$patchcheck_sleep_time,
221 "IGNORE_WARNINGS" => \$ignore_warnings,
Steven Rostedtbe405f92012-01-04 21:51:59 -0500222 "IGNORE_ERRORS" => \$ignore_errors,
Steven Rostedt9cc9e092011-12-22 21:37:22 -0500223 "BISECT_MANUAL" => \$bisect_manual,
224 "BISECT_SKIP" => \$bisect_skip,
225 "CONFIG_BISECT_GOOD" => \$config_bisect_good,
226 "BISECT_RET_GOOD" => \$bisect_ret_good,
227 "BISECT_RET_BAD" => \$bisect_ret_bad,
228 "BISECT_RET_SKIP" => \$bisect_ret_skip,
229 "BISECT_RET_ABORT" => \$bisect_ret_abort,
230 "BISECT_RET_DEFAULT" => \$bisect_ret_default,
231 "STORE_FAILURES" => \$store_failures,
232 "STORE_SUCCESSES" => \$store_successes,
233 "TEST_NAME" => \$test_name,
234 "TIMEOUT" => \$timeout,
235 "BOOTED_TIMEOUT" => \$booted_timeout,
236 "CONSOLE" => \$console,
237 "DETECT_TRIPLE_FAULT" => \$detect_triplefault,
238 "SUCCESS_LINE" => \$success_line,
239 "REBOOT_SUCCESS_LINE" => \$reboot_success_line,
240 "STOP_AFTER_SUCCESS" => \$stop_after_success,
241 "STOP_AFTER_FAILURE" => \$stop_after_failure,
242 "STOP_TEST_AFTER" => \$stop_test_after,
243 "BUILD_TARGET" => \$build_target,
244 "SSH_EXEC" => \$ssh_exec,
245 "SCP_TO_TARGET" => \$scp_to_target,
246 "CHECKOUT" => \$checkout,
247 "TARGET_IMAGE" => \$target_image,
248 "LOCALVERSION" => \$localversion,
249
250 "BISECT_GOOD" => \$bisect_good,
251 "BISECT_BAD" => \$bisect_bad,
252 "BISECT_TYPE" => \$bisect_type,
253 "BISECT_START" => \$bisect_start,
254 "BISECT_REPLAY" => \$bisect_replay,
255 "BISECT_FILES" => \$bisect_files,
256 "BISECT_REVERSE" => \$bisect_reverse,
257 "BISECT_CHECK" => \$bisect_check,
258
259 "CONFIG_BISECT" => \$config_bisect,
260 "CONFIG_BISECT_TYPE" => \$config_bisect_type,
261
262 "PATCHCHECK_TYPE" => \$patchcheck_type,
263 "PATCHCHECK_START" => \$patchcheck_start,
264 "PATCHCHECK_END" => \$patchcheck_end,
265);
266
267# Options may be used by other options, record them.
268my %used_options;
269
Steven Rostedt7bf51072011-10-22 09:07:03 -0400270# default variables that can be used
271chomp ($variable{"PWD"} = `pwd`);
272
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500273$config_help{"MACHINE"} = << "EOF"
274 The machine hostname that you will test.
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500275 For build only tests, it is still needed to differentiate log files.
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500276EOF
277 ;
278$config_help{"SSH_USER"} = << "EOF"
279 The box is expected to have ssh on normal bootup, provide the user
280 (most likely root, since you need privileged operations)
281EOF
282 ;
283$config_help{"BUILD_DIR"} = << "EOF"
284 The directory that contains the Linux source code (full path).
Steven Rostedt0e7a22d2011-11-21 20:39:33 -0500285 You can use \${PWD} that will be the path where ktest.pl is run, or use
286 \${THIS_DIR} which is assigned \${PWD} but may be changed later.
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500287EOF
288 ;
289$config_help{"OUTPUT_DIR"} = << "EOF"
290 The directory that the objects will be built (full path).
291 (can not be same as BUILD_DIR)
Steven Rostedt0e7a22d2011-11-21 20:39:33 -0500292 You can use \${PWD} that will be the path where ktest.pl is run, or use
293 \${THIS_DIR} which is assigned \${PWD} but may be changed later.
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500294EOF
295 ;
296$config_help{"BUILD_TARGET"} = << "EOF"
297 The location of the compiled file to copy to the target.
298 (relative to OUTPUT_DIR)
299EOF
300 ;
Steven Rostedtdbd37832011-11-23 16:00:48 -0500301$config_help{"BUILD_OPTIONS"} = << "EOF"
302 Options to add to \"make\" when building.
303 i.e. -j20
304EOF
305 ;
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500306$config_help{"TARGET_IMAGE"} = << "EOF"
307 The place to put your image on the test machine.
308EOF
309 ;
310$config_help{"POWER_CYCLE"} = << "EOF"
311 A script or command to reboot the box.
312
313 Here is a digital loggers power switch example
314 POWER_CYCLE = wget --no-proxy -O /dev/null -q --auth-no-challenge 'http://admin:admin\@power/outlet?5=CCL'
315
316 Here is an example to reboot a virtual box on the current host
317 with the name "Guest".
318 POWER_CYCLE = virsh destroy Guest; sleep 5; virsh start Guest
319EOF
320 ;
321$config_help{"CONSOLE"} = << "EOF"
322 The script or command that reads the console
323
324 If you use ttywatch server, something like the following would work.
325CONSOLE = nc -d localhost 3001
326
327 For a virtual machine with guest name "Guest".
328CONSOLE = virsh console Guest
329EOF
330 ;
331$config_help{"LOCALVERSION"} = << "EOF"
332 Required version ending to differentiate the test
333 from other linux builds on the system.
334EOF
335 ;
336$config_help{"REBOOT_TYPE"} = << "EOF"
337 Way to reboot the box to the test kernel.
338 Only valid options so far are "grub" and "script".
339
340 If you specify grub, it will assume grub version 1
341 and will search in /boot/grub/menu.lst for the title \$GRUB_MENU
342 and select that target to reboot to the kernel. If this is not
343 your setup, then specify "script" and have a command or script
344 specified in REBOOT_SCRIPT to boot to the target.
345
346 The entry in /boot/grub/menu.lst must be entered in manually.
347 The test will not modify that file.
348EOF
349 ;
350$config_help{"GRUB_MENU"} = << "EOF"
351 The grub title name for the test kernel to boot
352 (Only mandatory if REBOOT_TYPE = grub)
353
354 Note, ktest.pl will not update the grub menu.lst, you need to
355 manually add an option for the test. ktest.pl will search
356 the grub menu.lst for this option to find what kernel to
357 reboot into.
358
359 For example, if in the /boot/grub/menu.lst the test kernel title has:
360 title Test Kernel
361 kernel vmlinuz-test
362 GRUB_MENU = Test Kernel
363EOF
364 ;
365$config_help{"REBOOT_SCRIPT"} = << "EOF"
366 A script to reboot the target into the test kernel
367 (Only mandatory if REBOOT_TYPE = script)
368EOF
369 ;
370
Steven Rostedtdad98752011-11-22 20:48:57 -0500371sub read_prompt {
372 my ($cancel, $prompt) = @_;
Steven Rostedt35ce5952011-07-15 21:57:25 -0400373
374 my $ans;
375
376 for (;;) {
Steven Rostedtdad98752011-11-22 20:48:57 -0500377 if ($cancel) {
378 print "$prompt [y/n/C] ";
379 } else {
380 print "$prompt [Y/n] ";
381 }
Steven Rostedt35ce5952011-07-15 21:57:25 -0400382 $ans = <STDIN>;
383 chomp $ans;
384 if ($ans =~ /^\s*$/) {
Steven Rostedtdad98752011-11-22 20:48:57 -0500385 if ($cancel) {
386 $ans = "c";
387 } else {
388 $ans = "y";
389 }
Steven Rostedt35ce5952011-07-15 21:57:25 -0400390 }
391 last if ($ans =~ /^y$/i || $ans =~ /^n$/i);
Steven Rostedtdad98752011-11-22 20:48:57 -0500392 if ($cancel) {
393 last if ($ans =~ /^c$/i);
394 print "Please answer either 'y', 'n' or 'c'.\n";
395 } else {
396 print "Please answer either 'y' or 'n'.\n";
397 }
398 }
399 if ($ans =~ /^c/i) {
400 exit;
Steven Rostedt35ce5952011-07-15 21:57:25 -0400401 }
402 if ($ans !~ /^y$/i) {
403 return 0;
404 }
405 return 1;
406}
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500407
Steven Rostedtdad98752011-11-22 20:48:57 -0500408sub read_yn {
409 my ($prompt) = @_;
410
411 return read_prompt 0, $prompt;
412}
413
414sub read_ync {
415 my ($prompt) = @_;
416
417 return read_prompt 1, $prompt;
418}
419
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500420sub get_ktest_config {
421 my ($config) = @_;
Steven Rostedt815e2bd2011-10-28 07:01:40 -0400422 my $ans;
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500423
424 return if (defined($opt{$config}));
425
426 if (defined($config_help{$config})) {
427 print "\n";
428 print $config_help{$config};
429 }
430
431 for (;;) {
432 print "$config = ";
Steven Rostedtdbd37832011-11-23 16:00:48 -0500433 if (defined($default{$config}) && length($default{$config})) {
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500434 print "\[$default{$config}\] ";
435 }
Steven Rostedt815e2bd2011-10-28 07:01:40 -0400436 $ans = <STDIN>;
437 $ans =~ s/^\s*(.*\S)\s*$/$1/;
438 if ($ans =~ /^\s*$/) {
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500439 if ($default{$config}) {
Steven Rostedt815e2bd2011-10-28 07:01:40 -0400440 $ans = $default{$config};
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500441 } else {
442 print "Your answer can not be blank\n";
443 next;
444 }
445 }
Steven Rostedt0e7a22d2011-11-21 20:39:33 -0500446 $entered_configs{$config} = ${ans};
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500447 last;
448 }
449}
450
451sub get_ktest_configs {
452 get_ktest_config("MACHINE");
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500453 get_ktest_config("BUILD_DIR");
454 get_ktest_config("OUTPUT_DIR");
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500455
Steven Rostedtdbd37832011-11-23 16:00:48 -0500456 if ($newconfig) {
457 get_ktest_config("BUILD_OPTIONS");
458 }
459
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500460 # options required for other than just building a kernel
461 if (!$buildonly) {
Steven Rostedt165708b2011-11-26 20:56:52 -0500462 get_ktest_config("POWER_CYCLE");
463 get_ktest_config("CONSOLE");
464 }
465
466 # options required for install and more
467 if ($buildonly != 1) {
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500468 get_ktest_config("SSH_USER");
469 get_ktest_config("BUILD_TARGET");
470 get_ktest_config("TARGET_IMAGE");
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500471 }
472
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500473 get_ktest_config("LOCALVERSION");
474
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500475 return if ($buildonly);
476
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500477 my $rtype = $opt{"REBOOT_TYPE"};
478
479 if (!defined($rtype)) {
480 if (!defined($opt{"GRUB_MENU"})) {
481 get_ktest_config("REBOOT_TYPE");
482 $rtype = $entered_configs{"REBOOT_TYPE"};
483 } else {
484 $rtype = "grub";
485 }
486 }
487
488 if ($rtype eq "grub") {
489 get_ktest_config("GRUB_MENU");
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500490 }
491}
492
Steven Rostedt77d942c2011-05-20 13:36:58 -0400493sub process_variables {
Steven Rostedt8d735212011-10-17 11:36:44 -0400494 my ($value, $remove_undef) = @_;
Steven Rostedt77d942c2011-05-20 13:36:58 -0400495 my $retval = "";
496
497 # We want to check for '\', and it is just easier
498 # to check the previous characet of '$' and not need
499 # to worry if '$' is the first character. By adding
500 # a space to $value, we can just check [^\\]\$ and
501 # it will still work.
502 $value = " $value";
503
504 while ($value =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
505 my $begin = $1;
506 my $var = $2;
507 my $end = $3;
508 # append beginning of value to retval
509 $retval = "$retval$begin";
510 if (defined($variable{$var})) {
511 $retval = "$retval$variable{$var}";
Steven Rostedt8d735212011-10-17 11:36:44 -0400512 } elsif (defined($remove_undef) && $remove_undef) {
513 # for if statements, any variable that is not defined,
514 # we simple convert to 0
515 $retval = "${retval}0";
Steven Rostedt77d942c2011-05-20 13:36:58 -0400516 } else {
517 # put back the origin piece.
518 $retval = "$retval\$\{$var\}";
Steven Rostedt9cc9e092011-12-22 21:37:22 -0500519 # This could be an option that is used later, save
520 # it so we don't warn if this option is not one of
521 # ktests options.
522 $used_options{$var} = 1;
Steven Rostedt77d942c2011-05-20 13:36:58 -0400523 }
524 $value = $end;
525 }
526 $retval = "$retval$value";
527
528 # remove the space added in the beginning
529 $retval =~ s/ //;
530
531 return "$retval"
532}
533
Steven Rostedta57419b2010-11-02 15:13:54 -0400534sub set_value {
Steven Rostedt3d1cc412011-09-30 22:14:21 -0400535 my ($lvalue, $rvalue, $override, $overrides, $name) = @_;
Steven Rostedta57419b2010-11-02 15:13:54 -0400536
Steven Rostedtcad96662011-12-22 11:32:52 -0500537 my $prvalue = process_variables($rvalue);
538
539 if ($buildonly && $lvalue =~ /^TEST_TYPE(\[.*\])?$/ && $prvalue ne "build") {
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500540 # Note if a test is something other than build, then we
541 # will need other manditory options.
Steven Rostedtcad96662011-12-22 11:32:52 -0500542 if ($prvalue ne "install") {
Steven Rostedt165708b2011-11-26 20:56:52 -0500543 $buildonly = 0;
544 } else {
545 # install still limits some manditory options.
546 $buildonly = 2;
547 }
Steven Rostedtbb8474b2011-11-23 15:58:00 -0500548 }
549
Steven Rostedta57419b2010-11-02 15:13:54 -0400550 if (defined($opt{$lvalue})) {
Steven Rostedt3d1cc412011-09-30 22:14:21 -0400551 if (!$override || defined(${$overrides}{$lvalue})) {
552 my $extra = "";
553 if ($override) {
554 $extra = "In the same override section!\n";
555 }
556 die "$name: $.: Option $lvalue defined more than once!\n$extra";
557 }
Steven Rostedtcad96662011-12-22 11:32:52 -0500558 ${$overrides}{$lvalue} = $prvalue;
Steven Rostedta57419b2010-11-02 15:13:54 -0400559 }
Steven Rostedt21a96792010-11-08 16:45:50 -0500560 if ($rvalue =~ /^\s*$/) {
561 delete $opt{$lvalue};
562 } else {
Steven Rostedtcad96662011-12-22 11:32:52 -0500563 $opt{$lvalue} = $prvalue;
Steven Rostedt21a96792010-11-08 16:45:50 -0500564 }
Steven Rostedta57419b2010-11-02 15:13:54 -0400565}
566
Steven Rostedt77d942c2011-05-20 13:36:58 -0400567sub set_variable {
568 my ($lvalue, $rvalue) = @_;
569
570 if ($rvalue =~ /^\s*$/) {
571 delete $variable{$lvalue};
572 } else {
573 $rvalue = process_variables($rvalue);
574 $variable{$lvalue} = $rvalue;
575 }
576}
577
Steven Rostedtab7a3f52011-09-30 20:24:07 -0400578sub process_compare {
579 my ($lval, $cmp, $rval) = @_;
580
581 # remove whitespace
582
583 $lval =~ s/^\s*//;
584 $lval =~ s/\s*$//;
585
586 $rval =~ s/^\s*//;
587 $rval =~ s/\s*$//;
588
589 if ($cmp eq "==") {
590 return $lval eq $rval;
591 } elsif ($cmp eq "!=") {
592 return $lval ne $rval;
593 }
594
595 my $statement = "$lval $cmp $rval";
596 my $ret = eval $statement;
597
598 # $@ stores error of eval
599 if ($@) {
600 return -1;
601 }
602
603 return $ret;
604}
605
Steven Rostedt9900b5d2011-09-30 22:41:14 -0400606sub value_defined {
607 my ($val) = @_;
608
609 return defined($variable{$2}) ||
610 defined($opt{$2});
611}
612
Steven Rostedt8d735212011-10-17 11:36:44 -0400613my $d = 0;
614sub process_expression {
615 my ($name, $val) = @_;
Steven Rostedt45d73a52011-09-30 19:44:53 -0400616
Steven Rostedt8d735212011-10-17 11:36:44 -0400617 my $c = $d++;
618
619 while ($val =~ s/\(([^\(]*?)\)/\&\&\&\&VAL\&\&\&\&/) {
620 my $express = $1;
621
622 if (process_expression($name, $express)) {
623 $val =~ s/\&\&\&\&VAL\&\&\&\&/ 1 /;
624 } else {
625 $val =~ s/\&\&\&\&VAL\&\&\&\&/ 0 /;
626 }
627 }
628
629 $d--;
630 my $OR = "\\|\\|";
631 my $AND = "\\&\\&";
632
633 while ($val =~ s/^(.*?)($OR|$AND)//) {
634 my $express = $1;
635 my $op = $2;
636
637 if (process_expression($name, $express)) {
638 if ($op eq "||") {
639 return 1;
640 }
641 } else {
642 if ($op eq "&&") {
643 return 0;
644 }
645 }
646 }
Steven Rostedt45d73a52011-09-30 19:44:53 -0400647
Steven Rostedtab7a3f52011-09-30 20:24:07 -0400648 if ($val =~ /(.*)(==|\!=|>=|<=|>|<)(.*)/) {
649 my $ret = process_compare($1, $2, $3);
650 if ($ret < 0) {
651 die "$name: $.: Unable to process comparison\n";
652 }
653 return $ret;
654 }
655
Steven Rostedt9900b5d2011-09-30 22:41:14 -0400656 if ($val =~ /^\s*(NOT\s*)?DEFINED\s+(\S+)\s*$/) {
657 if (defined $1) {
658 return !value_defined($2);
659 } else {
660 return value_defined($2);
661 }
662 }
663
Steven Rostedt45d73a52011-09-30 19:44:53 -0400664 if ($val =~ /^\s*0\s*$/) {
665 return 0;
666 } elsif ($val =~ /^\s*\d+\s*$/) {
667 return 1;
668 }
669
Steven Rostedt9900b5d2011-09-30 22:41:14 -0400670 die ("$name: $.: Undefined content $val in if statement\n");
Steven Rostedt8d735212011-10-17 11:36:44 -0400671}
672
673sub process_if {
674 my ($name, $value) = @_;
675
676 # Convert variables and replace undefined ones with 0
677 my $val = process_variables($value, 1);
678 my $ret = process_expression $name, $val;
679
680 return $ret;
Steven Rostedt45d73a52011-09-30 19:44:53 -0400681}
682
Steven Rostedt2ed3b162011-09-30 21:00:00 -0400683sub __read_config {
684 my ($config, $current_test_num) = @_;
Steven Rostedt2545eb62010-11-02 15:01:32 -0400685
Steven Rostedt2ed3b162011-09-30 21:00:00 -0400686 my $in;
687 open($in, $config) || die "can't read file $config";
Steven Rostedt2545eb62010-11-02 15:01:32 -0400688
Steven Rostedta57419b2010-11-02 15:13:54 -0400689 my $name = $config;
690 $name =~ s,.*/(.*),$1,;
691
Steven Rostedt2ed3b162011-09-30 21:00:00 -0400692 my $test_num = $$current_test_num;
Steven Rostedta57419b2010-11-02 15:13:54 -0400693 my $default = 1;
694 my $repeat = 1;
695 my $num_tests_set = 0;
696 my $skip = 0;
697 my $rest;
Steven Rostedta9f84422011-10-17 11:06:29 -0400698 my $line;
Steven Rostedt0df213c2011-06-14 20:51:37 -0400699 my $test_case = 0;
Steven Rostedt45d73a52011-09-30 19:44:53 -0400700 my $if = 0;
701 my $if_set = 0;
Steven Rostedt3d1cc412011-09-30 22:14:21 -0400702 my $override = 0;
703
704 my %overrides;
Steven Rostedta57419b2010-11-02 15:13:54 -0400705
Steven Rostedt2ed3b162011-09-30 21:00:00 -0400706 while (<$in>) {
Steven Rostedt2545eb62010-11-02 15:01:32 -0400707
708 # ignore blank lines and comments
709 next if (/^\s*$/ || /\s*\#/);
710
Steven Rostedt0050b6b2011-09-30 21:10:30 -0400711 if (/^\s*(TEST_START|DEFAULTS)\b(.*)/) {
Steven Rostedta57419b2010-11-02 15:13:54 -0400712
Steven Rostedt0050b6b2011-09-30 21:10:30 -0400713 my $type = $1;
714 $rest = $2;
Steven Rostedta9f84422011-10-17 11:06:29 -0400715 $line = $2;
Steven Rostedta57419b2010-11-02 15:13:54 -0400716
Steven Rostedt0050b6b2011-09-30 21:10:30 -0400717 my $old_test_num;
718 my $old_repeat;
Steven Rostedt3d1cc412011-09-30 22:14:21 -0400719 $override = 0;
Steven Rostedt0050b6b2011-09-30 21:10:30 -0400720
721 if ($type eq "TEST_START") {
722
723 if ($num_tests_set) {
724 die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
725 }
726
727 $old_test_num = $test_num;
728 $old_repeat = $repeat;
729
730 $test_num += $repeat;
731 $default = 0;
732 $repeat = 1;
733 } else {
734 $default = 1;
Steven Rostedta57419b2010-11-02 15:13:54 -0400735 }
736
Steven Rostedta9f84422011-10-17 11:06:29 -0400737 # If SKIP is anywhere in the line, the command will be skipped
738 if ($rest =~ s/\s+SKIP\b//) {
Steven Rostedta57419b2010-11-02 15:13:54 -0400739 $skip = 1;
740 } else {
Steven Rostedt0df213c2011-06-14 20:51:37 -0400741 $test_case = 1;
Steven Rostedta57419b2010-11-02 15:13:54 -0400742 $skip = 0;
743 }
744
Steven Rostedta9f84422011-10-17 11:06:29 -0400745 if ($rest =~ s/\sELSE\b//) {
746 if (!$if) {
747 die "$name: $.: ELSE found with out matching IF section\n$_";
748 }
749 $if = 0;
750
751 if ($if_set) {
752 $skip = 1;
753 } else {
754 $skip = 0;
Steven Rostedt3d1cc412011-09-30 22:14:21 -0400755 }
Steven Rostedta57419b2010-11-02 15:13:54 -0400756 }
757
Steven Rostedta9f84422011-10-17 11:06:29 -0400758 if ($rest =~ s/\sIF\s+(.*)//) {
Steven Rostedt45d73a52011-09-30 19:44:53 -0400759 if (process_if($name, $1)) {
760 $if_set = 1;
761 } else {
762 $skip = 1;
763 }
764 $if = 1;
765 } else {
766 $if = 0;
Steven Rostedta9f84422011-10-17 11:06:29 -0400767 $if_set = 0;
Steven Rostedta57419b2010-11-02 15:13:54 -0400768 }
769
Steven Rostedta9f84422011-10-17 11:06:29 -0400770 if (!$skip) {
771 if ($type eq "TEST_START") {
772 if ($rest =~ s/\s+ITERATE\s+(\d+)//) {
773 $repeat = $1;
774 $repeat_tests{"$test_num"} = $repeat;
775 }
776 } elsif ($rest =~ s/\sOVERRIDE\b//) {
777 # DEFAULT only
778 $override = 1;
779 # Clear previous overrides
780 %overrides = ();
781 }
782 }
783
784 if (!$skip && $rest !~ /^\s*$/) {
Steven Rostedt0050b6b2011-09-30 21:10:30 -0400785 die "$name: $.: Gargbage found after $type\n$_";
Steven Rostedta57419b2010-11-02 15:13:54 -0400786 }
787
Steven Rostedt0050b6b2011-09-30 21:10:30 -0400788 if ($skip && $type eq "TEST_START") {
Steven Rostedta57419b2010-11-02 15:13:54 -0400789 $test_num = $old_test_num;
Steven Rostedte48c5292010-11-02 14:35:37 -0400790 $repeat = $old_repeat;
Steven Rostedta57419b2010-11-02 15:13:54 -0400791 }
792
Steven Rostedtab7a3f52011-09-30 20:24:07 -0400793 } elsif (/^\s*ELSE\b(.*)$/) {
Steven Rostedt45d73a52011-09-30 19:44:53 -0400794 if (!$if) {
795 die "$name: $.: ELSE found with out matching IF section\n$_";
796 }
797 $rest = $1;
798 if ($if_set) {
799 $skip = 1;
Steven Rostedtab7a3f52011-09-30 20:24:07 -0400800 $rest = "";
Steven Rostedt45d73a52011-09-30 19:44:53 -0400801 } else {
802 $skip = 0;
803
Steven Rostedtab7a3f52011-09-30 20:24:07 -0400804 if ($rest =~ /\sIF\s+(.*)/) {
Steven Rostedt45d73a52011-09-30 19:44:53 -0400805 # May be a ELSE IF section.
806 if (!process_if($name, $1)) {
807 $skip = 1;
808 }
Steven Rostedtab7a3f52011-09-30 20:24:07 -0400809 $rest = "";
Steven Rostedt45d73a52011-09-30 19:44:53 -0400810 } else {
811 $if = 0;
812 }
813 }
814
Steven Rostedtab7a3f52011-09-30 20:24:07 -0400815 if ($rest !~ /^\s*$/) {
816 die "$name: $.: Gargbage found after DEFAULTS\n$_";
817 }
818
Steven Rostedt2ed3b162011-09-30 21:00:00 -0400819 } elsif (/^\s*INCLUDE\s+(\S+)/) {
820
821 next if ($skip);
822
823 if (!$default) {
824 die "$name: $.: INCLUDE can only be done in default sections\n$_";
825 }
826
827 my $file = process_variables($1);
828
829 if ($file !~ m,^/,) {
830 # check the path of the config file first
831 if ($config =~ m,(.*)/,) {
832 if (-f "$1/$file") {
833 $file = "$1/$file";
834 }
835 }
836 }
837
838 if ( ! -r $file ) {
839 die "$name: $.: Can't read file $file\n$_";
840 }
841
842 if (__read_config($file, \$test_num)) {
843 $test_case = 1;
844 }
845
Steven Rostedta57419b2010-11-02 15:13:54 -0400846 } elsif (/^\s*([A-Z_\[\]\d]+)\s*=\s*(.*?)\s*$/) {
847
848 next if ($skip);
849
Steven Rostedt2545eb62010-11-02 15:01:32 -0400850 my $lvalue = $1;
851 my $rvalue = $2;
852
Steven Rostedta57419b2010-11-02 15:13:54 -0400853 if (!$default &&
854 ($lvalue eq "NUM_TESTS" ||
855 $lvalue eq "LOG_FILE" ||
856 $lvalue eq "CLEAR_LOG")) {
857 die "$name: $.: $lvalue must be set in DEFAULTS section\n";
Steven Rostedta75fece2010-11-02 14:58:27 -0400858 }
Steven Rostedta57419b2010-11-02 15:13:54 -0400859
860 if ($lvalue eq "NUM_TESTS") {
861 if ($test_num) {
862 die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n";
863 }
864 if (!$default) {
865 die "$name: $.: NUM_TESTS must be set in default section\n";
866 }
867 $num_tests_set = 1;
868 }
869
870 if ($default || $lvalue =~ /\[\d+\]$/) {
Steven Rostedt3d1cc412011-09-30 22:14:21 -0400871 set_value($lvalue, $rvalue, $override, \%overrides, $name);
Steven Rostedta57419b2010-11-02 15:13:54 -0400872 } else {
873 my $val = "$lvalue\[$test_num\]";
Steven Rostedt3d1cc412011-09-30 22:14:21 -0400874 set_value($val, $rvalue, $override, \%overrides, $name);
Steven Rostedta57419b2010-11-02 15:13:54 -0400875
876 if ($repeat > 1) {
877 $repeats{$val} = $repeat;
878 }
879 }
Steven Rostedt77d942c2011-05-20 13:36:58 -0400880 } elsif (/^\s*([A-Z_\[\]\d]+)\s*:=\s*(.*?)\s*$/) {
881 next if ($skip);
882
883 my $lvalue = $1;
884 my $rvalue = $2;
885
886 # process config variables.
887 # Config variables are only active while reading the
888 # config and can be defined anywhere. They also ignore
889 # TEST_START and DEFAULTS, but are skipped if they are in
890 # on of these sections that have SKIP defined.
891 # The save variable can be
892 # defined multiple times and the new one simply overrides
893 # the prevous one.
894 set_variable($lvalue, $rvalue);
895
Steven Rostedta57419b2010-11-02 15:13:54 -0400896 } else {
897 die "$name: $.: Garbage found in config\n$_";
Steven Rostedt2545eb62010-11-02 15:01:32 -0400898 }
899 }
900
Steven Rostedta57419b2010-11-02 15:13:54 -0400901 if ($test_num) {
902 $test_num += $repeat - 1;
903 $opt{"NUM_TESTS"} = $test_num;
904 }
905
Steven Rostedt2ed3b162011-09-30 21:00:00 -0400906 close($in);
907
908 $$current_test_num = $test_num;
909
910 return $test_case;
911}
912
Steven Rostedtc4261d02011-11-23 13:41:18 -0500913sub get_test_case {
914 print "What test case would you like to run?\n";
915 print " (build, install or boot)\n";
916 print " Other tests are available but require editing the config file\n";
917 my $ans = <STDIN>;
918 chomp $ans;
919 $default{"TEST_TYPE"} = $ans;
920}
921
Steven Rostedt2ed3b162011-09-30 21:00:00 -0400922sub read_config {
923 my ($config) = @_;
924
925 my $test_case;
926 my $test_num = 0;
927
928 $test_case = __read_config $config, \$test_num;
929
Steven Rostedt8d1491b2010-11-18 15:39:48 -0500930 # make sure we have all mandatory configs
931 get_ktest_configs;
932
Steven Rostedt0df213c2011-06-14 20:51:37 -0400933 # was a test specified?
934 if (!$test_case) {
935 print "No test case specified.\n";
Steven Rostedtc4261d02011-11-23 13:41:18 -0500936 get_test_case;
Steven Rostedt0df213c2011-06-14 20:51:37 -0400937 }
938
Steven Rostedta75fece2010-11-02 14:58:27 -0400939 # set any defaults
940
941 foreach my $default (keys %default) {
942 if (!defined($opt{$default})) {
943 $opt{$default} = $default{$default};
944 }
945 }
Steven Rostedt9cc9e092011-12-22 21:37:22 -0500946
947 if ($opt{"IGNORE_UNUSED"} == 1) {
948 return;
949 }
950
951 my %not_used;
952
953 # check if there are any stragglers (typos?)
954 foreach my $option (keys %opt) {
955 my $op = $option;
956 # remove per test labels.
957 $op =~ s/\[.*\]//;
958 if (!exists($option_map{$op}) &&
959 !exists($default{$op}) &&
960 !exists($used_options{$op})) {
961 $not_used{$op} = 1;
962 }
963 }
964
965 if (%not_used) {
966 my $s = "s are";
967 $s = " is" if (keys %not_used == 1);
968 print "The following option$s not used; could be a typo:\n";
969 foreach my $option (keys %not_used) {
970 print "$option\n";
971 }
972 print "Set IGRNORE_UNUSED = 1 to have ktest ignore unused variables\n";
973 if (!read_yn "Do you want to continue?") {
974 exit -1;
975 }
976 }
Steven Rostedt2545eb62010-11-02 15:01:32 -0400977}
978
Steven Rostedt23715c3c2011-06-13 11:03:34 -0400979sub __eval_option {
980 my ($option, $i) = @_;
981
982 # Add space to evaluate the character before $
983 $option = " $option";
984 my $retval = "";
Rabin Vincentf9dfb652011-11-18 17:05:30 +0530985 my $repeated = 0;
986 my $parent = 0;
987
988 foreach my $test (keys %repeat_tests) {
989 if ($i >= $test &&
990 $i < $test + $repeat_tests{$test}) {
991
992 $repeated = 1;
993 $parent = $test;
994 last;
995 }
996 }
Steven Rostedt23715c3c2011-06-13 11:03:34 -0400997
998 while ($option =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) {
999 my $start = $1;
1000 my $var = $2;
1001 my $end = $3;
1002
1003 # Append beginning of line
1004 $retval = "$retval$start";
1005
1006 # If the iteration option OPT[$i] exists, then use that.
1007 # otherwise see if the default OPT (without [$i]) exists.
1008
1009 my $o = "$var\[$i\]";
Rabin Vincentf9dfb652011-11-18 17:05:30 +05301010 my $parento = "$var\[$parent\]";
Steven Rostedt23715c3c2011-06-13 11:03:34 -04001011
1012 if (defined($opt{$o})) {
1013 $o = $opt{$o};
1014 $retval = "$retval$o";
Rabin Vincentf9dfb652011-11-18 17:05:30 +05301015 } elsif ($repeated && defined($opt{$parento})) {
1016 $o = $opt{$parento};
1017 $retval = "$retval$o";
Steven Rostedt23715c3c2011-06-13 11:03:34 -04001018 } elsif (defined($opt{$var})) {
1019 $o = $opt{$var};
1020 $retval = "$retval$o";
1021 } else {
1022 $retval = "$retval\$\{$var\}";
1023 }
1024
1025 $option = $end;
1026 }
1027
1028 $retval = "$retval$option";
1029
1030 $retval =~ s/^ //;
1031
1032 return $retval;
1033}
1034
1035sub eval_option {
1036 my ($option, $i) = @_;
1037
1038 my $prev = "";
1039
1040 # Since an option can evaluate to another option,
1041 # keep iterating until we do not evaluate any more
1042 # options.
1043 my $r = 0;
1044 while ($prev ne $option) {
1045 # Check for recursive evaluations.
1046 # 100 deep should be more than enough.
1047 if ($r++ > 100) {
1048 die "Over 100 evaluations accurred with $option\n" .
1049 "Check for recursive variables\n";
1050 }
1051 $prev = $option;
1052 $option = __eval_option($option, $i);
1053 }
1054
1055 return $option;
1056}
1057
Steven Rostedtd1e2f222010-11-08 16:39:57 -05001058sub _logit {
Steven Rostedt2545eb62010-11-02 15:01:32 -04001059 if (defined($opt{"LOG_FILE"})) {
1060 open(OUT, ">> $opt{LOG_FILE}") or die "Can't write to $opt{LOG_FILE}";
1061 print OUT @_;
1062 close(OUT);
1063 }
1064}
1065
Steven Rostedtd1e2f222010-11-08 16:39:57 -05001066sub logit {
1067 if (defined($opt{"LOG_FILE"})) {
1068 _logit @_;
1069 } else {
1070 print @_;
1071 }
1072}
1073
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001074sub doprint {
1075 print @_;
Steven Rostedtd1e2f222010-11-08 16:39:57 -05001076 _logit @_;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001077}
1078
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001079sub run_command;
Andrew Jones2728be42011-08-12 15:32:05 +02001080sub start_monitor;
1081sub end_monitor;
1082sub wait_for_monitor;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001083
1084sub reboot {
Andrew Jones2728be42011-08-12 15:32:05 +02001085 my ($time) = @_;
1086
Steven Rostedt2b803362011-09-30 18:00:23 -04001087 if (defined($time)) {
1088 start_monitor;
1089 # flush out current monitor
1090 # May contain the reboot success line
1091 wait_for_monitor 1;
1092 }
1093
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001094 # try to reboot normally
Steven Rostedte48c5292010-11-02 14:35:37 -04001095 if (run_command $reboot) {
Steven Rostedt576f6272010-11-02 14:58:38 -04001096 if (defined($powercycle_after_reboot)) {
1097 sleep $powercycle_after_reboot;
1098 run_command "$power_cycle";
1099 }
1100 } else {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001101 # nope? power cycle it.
Steven Rostedta75fece2010-11-02 14:58:27 -04001102 run_command "$power_cycle";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001103 }
Andrew Jones2728be42011-08-12 15:32:05 +02001104
1105 if (defined($time)) {
Steven Rostedt2b803362011-09-30 18:00:23 -04001106 wait_for_monitor($time, $reboot_success_line);
Andrew Jones2728be42011-08-12 15:32:05 +02001107 end_monitor;
1108 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001109}
1110
Steven Rostedtbc7c5802011-12-22 16:29:10 -05001111sub reboot_to_good {
1112 my ($time) = @_;
1113
1114 if (defined($switch_to_good)) {
1115 run_command $switch_to_good;
1116 return;
1117 }
1118
1119 reboot $time;
1120}
1121
Steven Rostedt576f6272010-11-02 14:58:38 -04001122sub do_not_reboot {
1123 my $i = $iteration;
1124
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04001125 return $test_type eq "build" || $no_reboot ||
Steven Rostedt576f6272010-11-02 14:58:38 -04001126 ($test_type eq "patchcheck" && $opt{"PATCHCHECK_TYPE[$i]"} eq "build") ||
1127 ($test_type eq "bisect" && $opt{"BISECT_TYPE[$i]"} eq "build");
1128}
1129
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001130sub dodie {
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001131 doprint "CRITICAL FAILURE... ", @_, "\n";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001132
Steven Rostedt576f6272010-11-02 14:58:38 -04001133 my $i = $iteration;
1134
1135 if ($reboot_on_error && !do_not_reboot) {
1136
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001137 doprint "REBOOTING\n";
Steven Rostedtbc7c5802011-12-22 16:29:10 -05001138 reboot_to_good;
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001139
Steven Rostedta75fece2010-11-02 14:58:27 -04001140 } elsif ($poweroff_on_error && defined($power_off)) {
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001141 doprint "POWERING OFF\n";
Steven Rostedta75fece2010-11-02 14:58:27 -04001142 `$power_off`;
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001143 }
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001144
Steven Rostedtf80802c2011-03-07 13:18:47 -05001145 if (defined($opt{"LOG_FILE"})) {
1146 print " See $opt{LOG_FILE} for more info.\n";
1147 }
1148
Steven Rostedt576f6272010-11-02 14:58:38 -04001149 die @_, "\n";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001150}
1151
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001152sub open_console {
1153 my ($fp) = @_;
1154
1155 my $flags;
1156
Steven Rostedta75fece2010-11-02 14:58:27 -04001157 my $pid = open($fp, "$console|") or
1158 dodie "Can't open console $console";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001159
1160 $flags = fcntl($fp, F_GETFL, 0) or
Steven Rostedt576f6272010-11-02 14:58:38 -04001161 dodie "Can't get flags for the socket: $!";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001162 $flags = fcntl($fp, F_SETFL, $flags | O_NONBLOCK) or
Steven Rostedt576f6272010-11-02 14:58:38 -04001163 dodie "Can't set flags for the socket: $!";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001164
1165 return $pid;
1166}
1167
1168sub close_console {
1169 my ($fp, $pid) = @_;
1170
1171 doprint "kill child process $pid\n";
1172 kill 2, $pid;
1173
1174 print "closing!\n";
1175 close($fp);
1176}
1177
1178sub start_monitor {
1179 if ($monitor_cnt++) {
1180 return;
1181 }
1182 $monitor_fp = \*MONFD;
1183 $monitor_pid = open_console $monitor_fp;
Steven Rostedta75fece2010-11-02 14:58:27 -04001184
1185 return;
1186
1187 open(MONFD, "Stop perl from warning about single use of MONFD");
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001188}
1189
1190sub end_monitor {
1191 if (--$monitor_cnt) {
1192 return;
1193 }
1194 close_console($monitor_fp, $monitor_pid);
1195}
1196
1197sub wait_for_monitor {
Steven Rostedt2b803362011-09-30 18:00:23 -04001198 my ($time, $stop) = @_;
1199 my $full_line = "";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001200 my $line;
Steven Rostedt2b803362011-09-30 18:00:23 -04001201 my $booted = 0;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001202
Steven Rostedta75fece2010-11-02 14:58:27 -04001203 doprint "** Wait for monitor to settle down **\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001204
1205 # read the monitor and wait for the system to calm down
Steven Rostedt2b803362011-09-30 18:00:23 -04001206 while (!$booted) {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001207 $line = wait_for_input($monitor_fp, $time);
Steven Rostedt2b803362011-09-30 18:00:23 -04001208 last if (!defined($line));
1209 print "$line";
1210 $full_line .= $line;
1211
1212 if (defined($stop) && $full_line =~ /$stop/) {
1213 doprint "wait for monitor detected $stop\n";
1214 $booted = 1;
1215 }
1216
1217 if ($line =~ /\n/) {
1218 $full_line = "";
1219 }
1220 }
Steven Rostedta75fece2010-11-02 14:58:27 -04001221 print "** Monitor flushed **\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001222}
1223
Rabin Vincentde5b6e32011-11-18 17:05:31 +05301224sub save_logs {
1225 my ($result, $basedir) = @_;
1226 my @t = localtime;
1227 my $date = sprintf "%04d%02d%02d%02d%02d%02d",
1228 1900+$t[5],$t[4],$t[3],$t[2],$t[1],$t[0];
1229
1230 my $type = $build_type;
1231 if ($type =~ /useconfig/) {
1232 $type = "useconfig";
1233 }
1234
1235 my $dir = "$machine-$test_type-$type-$result-$date";
1236
1237 $dir = "$basedir/$dir";
1238
1239 if (!-d $dir) {
1240 mkpath($dir) or
1241 die "can't create $dir";
1242 }
1243
1244 my %files = (
1245 "config" => $output_config,
1246 "buildlog" => $buildlog,
1247 "dmesg" => $dmesg,
1248 "testlog" => $testlog,
1249 );
1250
1251 while (my ($name, $source) = each(%files)) {
1252 if (-f "$source") {
1253 cp "$source", "$dir/$name" or
1254 die "failed to copy $source";
1255 }
1256 }
1257
1258 doprint "*** Saved info to $dir ***\n";
1259}
1260
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001261sub fail {
1262
Steven Rostedta75fece2010-11-02 14:58:27 -04001263 if ($die_on_failure) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001264 dodie @_;
1265 }
1266
Steven Rostedta75fece2010-11-02 14:58:27 -04001267 doprint "FAILED\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001268
Steven Rostedt576f6272010-11-02 14:58:38 -04001269 my $i = $iteration;
1270
Steven Rostedta75fece2010-11-02 14:58:27 -04001271 # no need to reboot for just building.
Steven Rostedt576f6272010-11-02 14:58:38 -04001272 if (!do_not_reboot) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001273 doprint "REBOOTING\n";
Steven Rostedtbc7c5802011-12-22 16:29:10 -05001274 reboot_to_good $sleep_time;
Steven Rostedta75fece2010-11-02 14:58:27 -04001275 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001276
Steven Rostedt9064af52011-06-13 10:38:48 -04001277 my $name = "";
1278
1279 if (defined($test_name)) {
1280 $name = " ($test_name)";
1281 }
1282
Steven Rostedt576f6272010-11-02 14:58:38 -04001283 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1284 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
Steven Rostedt9064af52011-06-13 10:38:48 -04001285 doprint "KTEST RESULT: TEST $i$name Failed: ", @_, "\n";
Steven Rostedt576f6272010-11-02 14:58:38 -04001286 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
1287 doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
Steven Rostedta75fece2010-11-02 14:58:27 -04001288
Rabin Vincentde5b6e32011-11-18 17:05:31 +05301289 if (defined($store_failures)) {
1290 save_logs "fail", $store_failures;
1291 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001292
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001293 return 1;
1294}
1295
Steven Rostedt2545eb62010-11-02 15:01:32 -04001296sub run_command {
1297 my ($command) = @_;
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001298 my $dolog = 0;
1299 my $dord = 0;
1300 my $pid;
1301
Steven Rostedte48c5292010-11-02 14:35:37 -04001302 $command =~ s/\$SSH_USER/$ssh_user/g;
1303 $command =~ s/\$MACHINE/$machine/g;
1304
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001305 doprint("$command ... ");
1306
1307 $pid = open(CMD, "$command 2>&1 |") or
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001308 (fail "unable to exec $command" and return 0);
Steven Rostedt2545eb62010-11-02 15:01:32 -04001309
1310 if (defined($opt{"LOG_FILE"})) {
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001311 open(LOG, ">>$opt{LOG_FILE}") or
1312 dodie "failed to write to log";
1313 $dolog = 1;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001314 }
1315
1316 if (defined($redirect)) {
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001317 open (RD, ">$redirect") or
1318 dodie "failed to write to redirect $redirect";
1319 $dord = 1;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001320 }
1321
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001322 while (<CMD>) {
1323 print LOG if ($dolog);
1324 print RD if ($dord);
1325 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001326
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001327 waitpid($pid, 0);
Steven Rostedt2545eb62010-11-02 15:01:32 -04001328 my $failed = $?;
1329
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04001330 close(CMD);
1331 close(LOG) if ($dolog);
1332 close(RD) if ($dord);
1333
Steven Rostedt2545eb62010-11-02 15:01:32 -04001334 if ($failed) {
1335 doprint "FAILED!\n";
1336 } else {
1337 doprint "SUCCESS\n";
1338 }
1339
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001340 return !$failed;
1341}
1342
Steven Rostedte48c5292010-11-02 14:35:37 -04001343sub run_ssh {
1344 my ($cmd) = @_;
1345 my $cp_exec = $ssh_exec;
1346
1347 $cp_exec =~ s/\$SSH_COMMAND/$cmd/g;
1348 return run_command "$cp_exec";
1349}
1350
1351sub run_scp {
1352 my ($src, $dst) = @_;
1353 my $cp_scp = $scp_to_target;
1354
1355 $cp_scp =~ s/\$SRC_FILE/$src/g;
1356 $cp_scp =~ s/\$DST_FILE/$dst/g;
1357
1358 return run_command "$cp_scp";
1359}
1360
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001361sub get_grub_index {
1362
Steven Rostedta75fece2010-11-02 14:58:27 -04001363 if ($reboot_type ne "grub") {
1364 return;
1365 }
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001366 return if (defined($grub_number));
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001367
1368 doprint "Find grub menu ... ";
1369 $grub_number = -1;
Steven Rostedte48c5292010-11-02 14:35:37 -04001370
1371 my $ssh_grub = $ssh_exec;
1372 $ssh_grub =~ s,\$SSH_COMMAND,cat /boot/grub/menu.lst,g;
1373
1374 open(IN, "$ssh_grub |")
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001375 or die "unable to get menu.lst";
Steven Rostedte48c5292010-11-02 14:35:37 -04001376
Steven Rostedteaa1fe22011-09-14 17:20:39 -04001377 my $found = 0;
1378
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001379 while (<IN>) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001380 if (/^\s*title\s+$grub_menu\s*$/) {
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001381 $grub_number++;
Steven Rostedteaa1fe22011-09-14 17:20:39 -04001382 $found = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001383 last;
1384 } elsif (/^\s*title\s/) {
1385 $grub_number++;
1386 }
1387 }
1388 close(IN);
1389
Steven Rostedta75fece2010-11-02 14:58:27 -04001390 die "Could not find '$grub_menu' in /boot/grub/menu on $machine"
Steven Rostedteaa1fe22011-09-14 17:20:39 -04001391 if (!$found);
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001392 doprint "$grub_number\n";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001393}
1394
Steven Rostedt2545eb62010-11-02 15:01:32 -04001395sub wait_for_input
1396{
1397 my ($fp, $time) = @_;
1398 my $rin;
1399 my $ready;
1400 my $line;
1401 my $ch;
1402
1403 if (!defined($time)) {
1404 $time = $timeout;
1405 }
1406
1407 $rin = '';
1408 vec($rin, fileno($fp), 1) = 1;
1409 $ready = select($rin, undef, undef, $time);
1410
1411 $line = "";
1412
1413 # try to read one char at a time
1414 while (sysread $fp, $ch, 1) {
1415 $line .= $ch;
1416 last if ($ch eq "\n");
1417 }
1418
1419 if (!length($line)) {
1420 return undef;
1421 }
1422
1423 return $line;
1424}
1425
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001426sub reboot_to {
Steven Rostedtbc7c5802011-12-22 16:29:10 -05001427 if (defined($switch_to_test)) {
1428 run_command $switch_to_test;
1429 }
1430
Steven Rostedta75fece2010-11-02 14:58:27 -04001431 if ($reboot_type eq "grub") {
Steven Rostedtc54367f2011-10-20 09:56:41 -04001432 run_ssh "'(echo \"savedefault --default=$grub_number --once\" | grub --batch)'";
Steven Rostedt96f6a0d2011-12-23 00:24:51 -05001433 } elsif (defined $reboot_script) {
1434 run_command "$reboot_script";
Steven Rostedta75fece2010-11-02 14:58:27 -04001435 }
Steven Rostedt96f6a0d2011-12-23 00:24:51 -05001436 reboot;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001437}
1438
Steven Rostedta57419b2010-11-02 15:13:54 -04001439sub get_sha1 {
1440 my ($commit) = @_;
1441
1442 doprint "git rev-list --max-count=1 $commit ... ";
1443 my $sha1 = `git rev-list --max-count=1 $commit`;
1444 my $ret = $?;
1445
1446 logit $sha1;
1447
1448 if ($ret) {
1449 doprint "FAILED\n";
1450 dodie "Failed to get git $commit";
1451 }
1452
1453 print "SUCCESS\n";
1454
1455 chomp $sha1;
1456
1457 return $sha1;
1458}
1459
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001460sub monitor {
Steven Rostedt2545eb62010-11-02 15:01:32 -04001461 my $booted = 0;
1462 my $bug = 0;
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001463 my $skip_call_trace = 0;
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001464 my $loops;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001465
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001466 wait_for_monitor 5;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001467
1468 my $line;
1469 my $full_line = "";
1470
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001471 open(DMESG, "> $dmesg") or
1472 die "unable to write to $dmesg";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001473
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001474 reboot_to;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001475
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001476 my $success_start;
1477 my $failure_start;
Steven Rostedt2d01b262011-03-08 09:47:54 -05001478 my $monitor_start = time;
1479 my $done = 0;
Steven Rostedtf1a5b962011-06-13 10:30:00 -04001480 my $version_found = 0;
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001481
Steven Rostedt2d01b262011-03-08 09:47:54 -05001482 while (!$done) {
Steven Rostedt2545eb62010-11-02 15:01:32 -04001483
Steven Rostedtecaf8e52011-06-13 10:48:10 -04001484 if ($bug && defined($stop_after_failure) &&
1485 $stop_after_failure >= 0) {
1486 my $time = $stop_after_failure - (time - $failure_start);
1487 $line = wait_for_input($monitor_fp, $time);
1488 if (!defined($line)) {
1489 doprint "bug timed out after $booted_timeout seconds\n";
1490 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
1491 last;
1492 }
1493 } elsif ($booted) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001494 $line = wait_for_input($monitor_fp, $booted_timeout);
Steven Rostedtcd4f1d52011-06-13 10:26:27 -04001495 if (!defined($line)) {
1496 my $s = $booted_timeout == 1 ? "" : "s";
1497 doprint "Successful boot found: break after $booted_timeout second$s\n";
1498 last;
1499 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001500 } else {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001501 $line = wait_for_input($monitor_fp);
Steven Rostedtcd4f1d52011-06-13 10:26:27 -04001502 if (!defined($line)) {
1503 my $s = $timeout == 1 ? "" : "s";
1504 doprint "Timed out after $timeout second$s\n";
1505 last;
1506 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001507 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001508
Steven Rostedt2545eb62010-11-02 15:01:32 -04001509 doprint $line;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001510 print DMESG $line;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001511
1512 # we are not guaranteed to get a full line
1513 $full_line .= $line;
1514
Steven Rostedta75fece2010-11-02 14:58:27 -04001515 if ($full_line =~ /$success_line/) {
Steven Rostedt2545eb62010-11-02 15:01:32 -04001516 $booted = 1;
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001517 $success_start = time;
1518 }
1519
1520 if ($booted && defined($stop_after_success) &&
1521 $stop_after_success >= 0) {
1522 my $now = time;
1523 if ($now - $success_start >= $stop_after_success) {
1524 doprint "Test forced to stop after $stop_after_success seconds after success\n";
1525 last;
1526 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001527 }
1528
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001529 if ($full_line =~ /\[ backtrace testing \]/) {
1530 $skip_call_trace = 1;
1531 }
1532
Steven Rostedt2545eb62010-11-02 15:01:32 -04001533 if ($full_line =~ /call trace:/i) {
Steven Rostedtbe405f92012-01-04 21:51:59 -05001534 if (!$ignore_errors && !$bug && !$skip_call_trace) {
Steven Rostedt1c8a6172010-11-09 12:55:40 -05001535 $bug = 1;
1536 $failure_start = time;
1537 }
1538 }
1539
1540 if ($bug && defined($stop_after_failure) &&
1541 $stop_after_failure >= 0) {
1542 my $now = time;
1543 if ($now - $failure_start >= $stop_after_failure) {
1544 doprint "Test forced to stop after $stop_after_failure seconds after failure\n";
1545 last;
1546 }
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001547 }
1548
1549 if ($full_line =~ /\[ end of backtrace testing \]/) {
1550 $skip_call_trace = 0;
1551 }
1552
1553 if ($full_line =~ /Kernel panic -/) {
Steven Rostedt10abf112011-03-07 13:21:00 -05001554 $failure_start = time;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001555 $bug = 1;
1556 }
1557
Steven Rostedtf1a5b962011-06-13 10:30:00 -04001558 # Detect triple faults by testing the banner
1559 if ($full_line =~ /\bLinux version (\S+).*\n/) {
1560 if ($1 eq $version) {
1561 $version_found = 1;
1562 } elsif ($version_found && $detect_triplefault) {
1563 # We already booted into the kernel we are testing,
1564 # but now we booted into another kernel?
1565 # Consider this a triple fault.
1566 doprint "Aleady booted in Linux kernel $version, but now\n";
1567 doprint "we booted into Linux kernel $1.\n";
1568 doprint "Assuming that this is a triple fault.\n";
1569 doprint "To disable this: set DETECT_TRIPLE_FAULT to 0\n";
1570 last;
1571 }
1572 }
1573
Steven Rostedt2545eb62010-11-02 15:01:32 -04001574 if ($line =~ /\n/) {
1575 $full_line = "";
1576 }
Steven Rostedt2d01b262011-03-08 09:47:54 -05001577
1578 if ($stop_test_after > 0 && !$booted && !$bug) {
1579 if (time - $monitor_start > $stop_test_after) {
Steven Rostedt4d62bf52011-05-20 09:14:35 -04001580 doprint "STOP_TEST_AFTER ($stop_test_after seconds) timed out\n";
Steven Rostedt2d01b262011-03-08 09:47:54 -05001581 $done = 1;
1582 }
1583 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001584 }
1585
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001586 close(DMESG);
Steven Rostedt2545eb62010-11-02 15:01:32 -04001587
Steven Rostedt2545eb62010-11-02 15:01:32 -04001588 if ($bug) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001589 return 0 if ($in_bisect);
Steven Rostedt576f6272010-11-02 14:58:38 -04001590 fail "failed - got a bug report" and return 0;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001591 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001592
Steven Rostedta75fece2010-11-02 14:58:27 -04001593 if (!$booted) {
1594 return 0 if ($in_bisect);
Steven Rostedt576f6272010-11-02 14:58:38 -04001595 fail "failed - never got a boot prompt." and return 0;
Steven Rostedta75fece2010-11-02 14:58:27 -04001596 }
1597
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001598 return 1;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001599}
1600
Steven Rostedt2b29b2f2011-12-22 11:25:46 -05001601sub eval_kernel_version {
1602 my ($option) = @_;
1603
1604 $option =~ s/\$KERNEL_VERSION/$version/g;
1605
1606 return $option;
1607}
1608
Steven Rostedtdb05cfe2011-06-13 11:09:22 -04001609sub do_post_install {
1610
1611 return if (!defined($post_install));
1612
Steven Rostedt2b29b2f2011-12-22 11:25:46 -05001613 my $cp_post_install = eval_kernel_version $post_install;
Steven Rostedtdb05cfe2011-06-13 11:09:22 -04001614 run_command "$cp_post_install" or
1615 dodie "Failed to run post install";
1616}
1617
Steven Rostedt2545eb62010-11-02 15:01:32 -04001618sub install {
1619
Steven Rostedte0a87422011-09-30 17:50:48 -04001620 return if ($no_install);
1621
Steven Rostedt2b29b2f2011-12-22 11:25:46 -05001622 my $cp_target = eval_kernel_version $target_image;
1623
1624 run_scp "$outputdir/$build_target", "$cp_target" or
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001625 dodie "failed to copy image";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001626
1627 my $install_mods = 0;
1628
1629 # should we process modules?
1630 $install_mods = 0;
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001631 open(IN, "$output_config") or dodie("Can't read config file");
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001632 while (<IN>) {
1633 if (/CONFIG_MODULES(=y)?/) {
1634 $install_mods = 1 if (defined($1));
1635 last;
1636 }
1637 }
1638 close(IN);
1639
1640 if (!$install_mods) {
Steven Rostedtdb05cfe2011-06-13 11:09:22 -04001641 do_post_install;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001642 doprint "No modules needed\n";
1643 return;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001644 }
1645
Steven Rostedt627977d2012-03-21 08:16:15 -04001646 run_command "$make INSTALL_MOD_STRIP=1 INSTALL_MOD_PATH=$tmpdir modules_install" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001647 dodie "Failed to install modules";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001648
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001649 my $modlib = "/lib/modules/$version";
Steven Rostedta57419b2010-11-02 15:13:54 -04001650 my $modtar = "ktest-mods.tar.bz2";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001651
Steven Rostedte48c5292010-11-02 14:35:37 -04001652 run_ssh "rm -rf $modlib" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001653 dodie "failed to remove old mods: $modlib";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001654
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001655 # would be nice if scp -r did not follow symbolic links
Steven Rostedta75fece2010-11-02 14:58:27 -04001656 run_command "cd $tmpdir && tar -cjf $modtar lib/modules/$version" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001657 dodie "making tarball";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001658
Steven Rostedte48c5292010-11-02 14:35:37 -04001659 run_scp "$tmpdir/$modtar", "/tmp" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001660 dodie "failed to copy modules";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001661
Steven Rostedta75fece2010-11-02 14:58:27 -04001662 unlink "$tmpdir/$modtar";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001663
Steven Rostedte7b13442011-06-14 20:44:36 -04001664 run_ssh "'(cd / && tar xjf /tmp/$modtar)'" or
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001665 dodie "failed to tar modules";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001666
Steven Rostedte48c5292010-11-02 14:35:37 -04001667 run_ssh "rm -f /tmp/$modtar";
Steven Rostedt8b37ca82010-11-02 14:58:33 -04001668
Steven Rostedtdb05cfe2011-06-13 11:09:22 -04001669 do_post_install;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001670}
1671
Steven Rostedtddf607e2011-06-14 20:49:13 -04001672sub get_version {
1673 # get the release name
1674 doprint "$make kernelrelease ... ";
1675 $version = `$make kernelrelease | tail -1`;
1676 chomp($version);
1677 doprint "$version\n";
1678}
1679
1680sub start_monitor_and_boot {
Steven Rostedt9f7424c2011-10-22 08:58:19 -04001681 # Make sure the stable kernel has finished booting
1682 start_monitor;
1683 wait_for_monitor 5;
1684 end_monitor;
1685
Steven Rostedtddf607e2011-06-14 20:49:13 -04001686 get_grub_index;
1687 get_version;
1688 install;
1689
1690 start_monitor;
1691 return monitor;
1692}
1693
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001694sub check_buildlog {
1695 my ($patch) = @_;
1696
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001697 my @files = `git show $patch | diffstat -l`;
1698
1699 open(IN, "git show $patch |") or
1700 dodie "failed to show $patch";
1701 while (<IN>) {
1702 if (m,^--- a/(.*),) {
1703 chomp $1;
1704 $files[$#files] = $1;
1705 }
1706 }
1707 close(IN);
1708
1709 open(IN, $buildlog) or dodie "Can't open $buildlog";
1710 while (<IN>) {
1711 if (/^\s*(.*?):.*(warning|error)/) {
1712 my $err = $1;
1713 foreach my $file (@files) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001714 my $fullpath = "$builddir/$file";
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001715 if ($file eq $err || $fullpath eq $err) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001716 fail "$file built with warnings" and return 0;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001717 }
1718 }
1719 }
1720 }
1721 close(IN);
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001722
1723 return 1;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04001724}
1725
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001726sub apply_min_config {
1727 my $outconfig = "$output_config.new";
Steven Rostedt612b9e92011-03-07 13:27:43 -05001728
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001729 # Read the config file and remove anything that
1730 # is in the force_config hash (from minconfig and others)
1731 # then add the force config back.
1732
1733 doprint "Applying minimum configurations into $output_config.new\n";
1734
1735 open (OUT, ">$outconfig") or
1736 dodie "Can't create $outconfig";
1737
1738 if (-f $output_config) {
1739 open (IN, $output_config) or
1740 dodie "Failed to open $output_config";
1741 while (<IN>) {
1742 if (/^(# )?(CONFIG_[^\s=]*)/) {
1743 next if (defined($force_config{$2}));
1744 }
1745 print OUT;
1746 }
1747 close IN;
1748 }
1749 foreach my $config (keys %force_config) {
1750 print OUT "$force_config{$config}\n";
1751 }
1752 close OUT;
1753
1754 run_command "mv $outconfig $output_config";
1755}
1756
1757sub make_oldconfig {
1758
Steven Rostedt4c4ab122011-07-15 21:16:17 -04001759 my @force_list = keys %force_config;
1760
1761 if ($#force_list >= 0) {
1762 apply_min_config;
1763 }
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001764
1765 if (!run_command "$make oldnoconfig") {
Steven Rostedt612b9e92011-03-07 13:27:43 -05001766 # Perhaps oldnoconfig doesn't exist in this version of the kernel
1767 # try a yes '' | oldconfig
1768 doprint "oldnoconfig failed, trying yes '' | make oldconfig\n";
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001769 run_command "yes '' | $make oldconfig" or
Steven Rostedt612b9e92011-03-07 13:27:43 -05001770 dodie "failed make config oldconfig";
1771 }
1772}
1773
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001774# read a config file and use this to force new configs.
1775sub load_force_config {
1776 my ($config) = @_;
1777
1778 open(IN, $config) or
1779 dodie "failed to read $config";
1780 while (<IN>) {
1781 chomp;
1782 if (/^(CONFIG[^\s=]*)(\s*=.*)/) {
1783 $force_config{$1} = $_;
1784 } elsif (/^# (CONFIG_\S*) is not set/) {
1785 $force_config{$1} = $_;
1786 }
1787 }
1788 close IN;
1789}
1790
Steven Rostedt2545eb62010-11-02 15:01:32 -04001791sub build {
1792 my ($type) = @_;
1793
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001794 unlink $buildlog;
1795
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04001796 # Failed builds should not reboot the target
1797 my $save_no_reboot = $no_reboot;
1798 $no_reboot = 1;
1799
Steven Rostedt0bd6c1a2011-06-14 20:39:31 -04001800 if (defined($pre_build)) {
1801 my $ret = run_command $pre_build;
1802 if (!$ret && defined($pre_build_die) &&
1803 $pre_build_die) {
1804 dodie "failed to pre_build\n";
1805 }
1806 }
1807
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001808 if ($type =~ /^useconfig:(.*)/) {
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001809 run_command "cp $1 $output_config" or
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001810 dodie "could not copy $1 to .config";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001811
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001812 $type = "oldconfig";
1813 }
1814
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001815 # old config can ask questions
1816 if ($type eq "oldconfig") {
Steven Rostedt9386c6a2010-11-08 16:35:48 -05001817 $type = "oldnoconfig";
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001818
1819 # allow for empty configs
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001820 run_command "touch $output_config";
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001821
Andrew Jones13488232011-08-12 15:32:04 +02001822 if (!$noclean) {
1823 run_command "mv $output_config $outputdir/config_temp" or
1824 dodie "moving .config";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001825
Andrew Jones13488232011-08-12 15:32:04 +02001826 run_command "$make mrproper" or dodie "make mrproper";
1827
1828 run_command "mv $outputdir/config_temp $output_config" or
1829 dodie "moving config_temp";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001830 }
1831
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001832 } elsif (!$noclean) {
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05001833 unlink "$output_config";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001834 run_command "$make mrproper" or
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001835 dodie "make mrproper";
Steven Rostedt5c42fc52010-11-02 14:57:01 -04001836 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04001837
1838 # add something to distinguish this build
Steven Rostedta75fece2010-11-02 14:58:27 -04001839 open(OUT, "> $outputdir/localversion") or dodie("Can't make localversion file");
1840 print OUT "$localversion\n";
Steven Rostedt2545eb62010-11-02 15:01:32 -04001841 close(OUT);
1842
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001843 if (defined($minconfig)) {
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001844 load_force_config($minconfig);
Steven Rostedt2545eb62010-11-02 15:01:32 -04001845 }
1846
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001847 if ($type ne "oldnoconfig") {
1848 run_command "$make $type" or
Steven Rostedt612b9e92011-03-07 13:27:43 -05001849 dodie "failed make config";
1850 }
Steven Rostedtfcb3f162011-06-13 10:40:58 -04001851 # Run old config regardless, to enforce min configurations
1852 make_oldconfig;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001853
Steven Rostedta75fece2010-11-02 14:58:27 -04001854 $redirect = "$buildlog";
Steven Rostedt0bd6c1a2011-06-14 20:39:31 -04001855 my $build_ret = run_command "$make $build_options";
1856 undef $redirect;
1857
1858 if (defined($post_build)) {
1859 my $ret = run_command $post_build;
1860 if (!$ret && defined($post_build_die) &&
1861 $post_build_die) {
1862 dodie "failed to post_build\n";
1863 }
1864 }
1865
1866 if (!$build_ret) {
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001867 # bisect may need this to pass
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04001868 if ($in_bisect) {
1869 $no_reboot = $save_no_reboot;
1870 return 0;
1871 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001872 fail "failed build" and return 0;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001873 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001874
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04001875 $no_reboot = $save_no_reboot;
1876
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04001877 return 1;
Steven Rostedt2545eb62010-11-02 15:01:32 -04001878}
1879
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001880sub halt {
Steven Rostedte48c5292010-11-02 14:35:37 -04001881 if (!run_ssh "halt" or defined($power_off)) {
Steven Rostedt576f6272010-11-02 14:58:38 -04001882 if (defined($poweroff_after_halt)) {
1883 sleep $poweroff_after_halt;
1884 run_command "$power_off";
1885 }
1886 } else {
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001887 # nope? the zap it!
Steven Rostedta75fece2010-11-02 14:58:27 -04001888 run_command "$power_off";
Steven Rostedt75c3fda72010-11-02 14:57:21 -04001889 }
1890}
1891
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001892sub success {
1893 my ($i) = @_;
1894
Steven Rostedte48c5292010-11-02 14:35:37 -04001895 $successes++;
1896
Steven Rostedt9064af52011-06-13 10:38:48 -04001897 my $name = "";
1898
1899 if (defined($test_name)) {
1900 $name = " ($test_name)";
1901 }
1902
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001903 doprint "\n\n*******************************************\n";
1904 doprint "*******************************************\n";
Steven Rostedt9064af52011-06-13 10:38:48 -04001905 doprint "KTEST RESULT: TEST $i$name SUCCESS!!!! **\n";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001906 doprint "*******************************************\n";
1907 doprint "*******************************************\n";
1908
Rabin Vincentde5b6e32011-11-18 17:05:31 +05301909 if (defined($store_successes)) {
1910 save_logs "success", $store_successes;
1911 }
1912
Steven Rostedt576f6272010-11-02 14:58:38 -04001913 if ($i != $opt{"NUM_TESTS"} && !do_not_reboot) {
Steven Rostedta75fece2010-11-02 14:58:27 -04001914 doprint "Reboot and wait $sleep_time seconds\n";
Steven Rostedtbc7c5802011-12-22 16:29:10 -05001915 reboot_to_good $sleep_time;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04001916 }
1917}
1918
Steven Rostedtc960bb92011-03-08 09:22:39 -05001919sub answer_bisect {
1920 for (;;) {
1921 doprint "Pass or fail? [p/f]";
1922 my $ans = <STDIN>;
1923 chomp $ans;
1924 if ($ans eq "p" || $ans eq "P") {
1925 return 1;
1926 } elsif ($ans eq "f" || $ans eq "F") {
1927 return 0;
1928 } else {
1929 print "Please answer 'P' or 'F'\n";
1930 }
1931 }
1932}
1933
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001934sub child_run_test {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001935 my $failed = 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001936
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001937 # child should have no power
Steven Rostedta75fece2010-11-02 14:58:27 -04001938 $reboot_on_error = 0;
1939 $poweroff_on_error = 0;
1940 $die_on_failure = 1;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001941
Rabin Vincenta9dd5d62011-11-18 17:05:29 +05301942 $redirect = "$testlog";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001943 run_command $run_test or $failed = 1;
Rabin Vincenta9dd5d62011-11-18 17:05:29 +05301944 undef $redirect;
1945
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001946 exit $failed;
1947}
1948
1949my $child_done;
1950
1951sub child_finished {
1952 $child_done = 1;
1953}
1954
1955sub do_run_test {
1956 my $child_pid;
1957 my $child_exit;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001958 my $line;
1959 my $full_line;
1960 my $bug = 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001961
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001962 wait_for_monitor 1;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001963
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001964 doprint "run test $run_test\n";
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001965
1966 $child_done = 0;
1967
1968 $SIG{CHLD} = qw(child_finished);
1969
1970 $child_pid = fork;
1971
1972 child_run_test if (!$child_pid);
1973
1974 $full_line = "";
1975
1976 do {
Steven Rostedt7faafbd2010-11-02 14:58:22 -04001977 $line = wait_for_input($monitor_fp, 1);
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001978 if (defined($line)) {
1979
1980 # we are not guaranteed to get a full line
1981 $full_line .= $line;
Steven Rostedt8ea0e062011-03-08 09:44:35 -05001982 doprint $line;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04001983
1984 if ($full_line =~ /call trace:/i) {
1985 $bug = 1;
1986 }
1987
1988 if ($full_line =~ /Kernel panic -/) {
1989 $bug = 1;
1990 }
1991
1992 if ($line =~ /\n/) {
1993 $full_line = "";
1994 }
1995 }
1996 } while (!$child_done && !$bug);
1997
1998 if ($bug) {
Steven Rostedt8ea0e062011-03-08 09:44:35 -05001999 my $failure_start = time;
2000 my $now;
2001 do {
2002 $line = wait_for_input($monitor_fp, 1);
2003 if (defined($line)) {
2004 doprint $line;
2005 }
2006 $now = time;
2007 if ($now - $failure_start >= $stop_after_failure) {
2008 last;
2009 }
2010 } while (defined($line));
2011
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002012 doprint "Detected kernel crash!\n";
2013 # kill the child with extreme prejudice
2014 kill 9, $child_pid;
2015 }
2016
2017 waitpid $child_pid, 0;
2018 $child_exit = $?;
2019
Steven Rostedtc5dacb82011-12-22 12:43:57 -05002020 if (!$bug && $in_bisect) {
2021 if (defined($bisect_ret_good)) {
2022 if ($child_exit == $bisect_ret_good) {
2023 return 1;
2024 }
2025 }
2026 if (defined($bisect_ret_skip)) {
2027 if ($child_exit == $bisect_ret_skip) {
2028 return -1;
2029 }
2030 }
2031 if (defined($bisect_ret_abort)) {
2032 if ($child_exit == $bisect_ret_abort) {
2033 fail "test abort" and return -2;
2034 }
2035 }
2036 if (defined($bisect_ret_bad)) {
2037 if ($child_exit == $bisect_ret_skip) {
2038 return 0;
2039 }
2040 }
2041 if (defined($bisect_ret_default)) {
2042 if ($bisect_ret_default eq "good") {
2043 return 1;
2044 } elsif ($bisect_ret_default eq "bad") {
2045 return 0;
2046 } elsif ($bisect_ret_default eq "skip") {
2047 return -1;
2048 } elsif ($bisect_ret_default eq "abort") {
2049 return -2;
2050 } else {
2051 fail "unknown default action: $bisect_ret_default"
2052 and return -2;
2053 }
2054 }
2055 }
2056
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002057 if ($bug || $child_exit) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002058 return 0 if $in_bisect;
2059 fail "test failed" and return 0;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002060 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002061 return 1;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002062}
2063
Steven Rostedta75fece2010-11-02 14:58:27 -04002064sub run_git_bisect {
2065 my ($command) = @_;
2066
2067 doprint "$command ... ";
2068
2069 my $output = `$command 2>&1`;
2070 my $ret = $?;
2071
2072 logit $output;
2073
2074 if ($ret) {
2075 doprint "FAILED\n";
2076 dodie "Failed to git bisect";
2077 }
2078
2079 doprint "SUCCESS\n";
2080 if ($output =~ m/^(Bisecting: .*\(roughly \d+ steps?\))\s+\[([[:xdigit:]]+)\]/) {
2081 doprint "$1 [$2]\n";
2082 } elsif ($output =~ m/^([[:xdigit:]]+) is the first bad commit/) {
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002083 $bisect_bad_commit = $1;
Steven Rostedta75fece2010-11-02 14:58:27 -04002084 doprint "Found bad commit... $1\n";
2085 return 0;
2086 } else {
2087 # we already logged it, just print it now.
2088 print $output;
2089 }
2090
2091 return 1;
2092}
2093
Steven Rostedtc23dca72011-03-08 09:26:31 -05002094sub bisect_reboot {
2095 doprint "Reboot and sleep $bisect_sleep_time seconds\n";
Steven Rostedtbc7c5802011-12-22 16:29:10 -05002096 reboot_to_good $bisect_sleep_time;
Steven Rostedtc23dca72011-03-08 09:26:31 -05002097}
2098
2099# returns 1 on success, 0 on failure, -1 on skip
Steven Rostedt0a05c762010-11-08 11:14:10 -05002100sub run_bisect_test {
2101 my ($type, $buildtype) = @_;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002102
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002103 my $failed = 0;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002104 my $result;
2105 my $output;
2106 my $ret;
2107
Steven Rostedt0a05c762010-11-08 11:14:10 -05002108 $in_bisect = 1;
2109
2110 build $buildtype or $failed = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002111
2112 if ($type ne "build") {
Steven Rostedtc23dca72011-03-08 09:26:31 -05002113 if ($failed && $bisect_skip) {
2114 $in_bisect = 0;
2115 return -1;
2116 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002117 dodie "Failed on build" if $failed;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002118
2119 # Now boot the box
Steven Rostedtddf607e2011-06-14 20:49:13 -04002120 start_monitor_and_boot or $failed = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002121
2122 if ($type ne "boot") {
Steven Rostedtc23dca72011-03-08 09:26:31 -05002123 if ($failed && $bisect_skip) {
2124 end_monitor;
2125 bisect_reboot;
2126 $in_bisect = 0;
2127 return -1;
2128 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002129 dodie "Failed on boot" if $failed;
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002130
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002131 do_run_test or $failed = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002132 }
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002133 end_monitor;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002134 }
2135
2136 if ($failed) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05002137 $result = 0;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002138 } else {
Steven Rostedt0a05c762010-11-08 11:14:10 -05002139 $result = 1;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002140 }
Steven Rostedt4025bc62011-05-20 09:16:29 -04002141
2142 # reboot the box to a kernel we can ssh to
2143 if ($type ne "build") {
2144 bisect_reboot;
2145 }
Steven Rostedt0a05c762010-11-08 11:14:10 -05002146 $in_bisect = 0;
2147
2148 return $result;
2149}
2150
2151sub run_bisect {
2152 my ($type) = @_;
2153 my $buildtype = "oldconfig";
2154
2155 # We should have a minconfig to use?
2156 if (defined($minconfig)) {
2157 $buildtype = "useconfig:$minconfig";
2158 }
2159
2160 my $ret = run_bisect_test $type, $buildtype;
2161
Steven Rostedtc960bb92011-03-08 09:22:39 -05002162 if ($bisect_manual) {
2163 $ret = answer_bisect;
2164 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002165
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04002166 # Are we looking for where it worked, not failed?
2167 if ($reverse_bisect) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05002168 $ret = !$ret;
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04002169 }
2170
Steven Rostedtc23dca72011-03-08 09:26:31 -05002171 if ($ret > 0) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05002172 return "good";
Steven Rostedtc23dca72011-03-08 09:26:31 -05002173 } elsif ($ret == 0) {
Steven Rostedt0a05c762010-11-08 11:14:10 -05002174 return "bad";
Steven Rostedtc23dca72011-03-08 09:26:31 -05002175 } elsif ($bisect_skip) {
2176 doprint "HIT A BAD COMMIT ... SKIPPING\n";
2177 return "skip";
Steven Rostedt0a05c762010-11-08 11:14:10 -05002178 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002179}
2180
Steven Rostedtdad98752011-11-22 20:48:57 -05002181sub update_bisect_replay {
2182 my $tmp_log = "$tmpdir/ktest_bisect_log";
2183 run_command "git bisect log > $tmp_log" or
2184 die "can't create bisect log";
2185 return $tmp_log;
2186}
2187
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002188sub bisect {
2189 my ($i) = @_;
2190
2191 my $result;
2192
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002193 die "BISECT_GOOD[$i] not defined\n" if (!defined($bisect_good));
2194 die "BISECT_BAD[$i] not defined\n" if (!defined($bisect_bad));
2195 die "BISECT_TYPE[$i] not defined\n" if (!defined($bisect_type));
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002196
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002197 my $good = $bisect_good;
2198 my $bad = $bisect_bad;
2199 my $type = $bisect_type;
2200 my $start = $bisect_start;
2201 my $replay = $bisect_replay;
2202 my $start_files = $bisect_files;
Steven Rostedt3410f6f2011-03-08 09:38:12 -05002203
2204 if (defined($start_files)) {
2205 $start_files = " -- " . $start_files;
2206 } else {
2207 $start_files = "";
2208 }
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002209
Steven Rostedta57419b2010-11-02 15:13:54 -04002210 # convert to true sha1's
2211 $good = get_sha1($good);
2212 $bad = get_sha1($bad);
2213
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002214 if (defined($bisect_reverse) && $bisect_reverse == 1) {
Steven Rostedtd6ce2a02010-11-02 14:58:05 -04002215 doprint "Performing a reverse bisect (bad is good, good is bad!)\n";
2216 $reverse_bisect = 1;
2217 } else {
2218 $reverse_bisect = 0;
2219 }
2220
Steven Rostedt5a391fb2010-11-02 14:57:43 -04002221 # Can't have a test without having a test to run
2222 if ($type eq "test" && !defined($run_test)) {
2223 $type = "boot";
2224 }
2225
Steven Rostedtdad98752011-11-22 20:48:57 -05002226 # Check if a bisect was running
2227 my $bisect_start_file = "$builddir/.git/BISECT_START";
2228
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002229 my $check = $bisect_check;
Steven Rostedtdad98752011-11-22 20:48:57 -05002230 my $do_check = defined($check) && $check ne "0";
2231
2232 if ( -f $bisect_start_file ) {
2233 print "Bisect in progress found\n";
2234 if ($do_check) {
2235 print " If you say yes, then no checks of good or bad will be done\n";
2236 }
2237 if (defined($replay)) {
2238 print "** BISECT_REPLAY is defined in config file **";
2239 print " Ignore config option and perform new git bisect log?\n";
2240 if (read_ync " (yes, no, or cancel) ") {
2241 $replay = update_bisect_replay;
2242 $do_check = 0;
2243 }
2244 } elsif (read_yn "read git log and continue?") {
2245 $replay = update_bisect_replay;
2246 $do_check = 0;
2247 }
2248 }
2249
2250 if ($do_check) {
Steven Rostedta75fece2010-11-02 14:58:27 -04002251
2252 # get current HEAD
Steven Rostedta57419b2010-11-02 15:13:54 -04002253 my $head = get_sha1("HEAD");
Steven Rostedta75fece2010-11-02 14:58:27 -04002254
2255 if ($check ne "good") {
2256 doprint "TESTING BISECT BAD [$bad]\n";
2257 run_command "git checkout $bad" or
2258 die "Failed to checkout $bad";
2259
2260 $result = run_bisect $type;
2261
2262 if ($result ne "bad") {
2263 fail "Tested BISECT_BAD [$bad] and it succeeded" and return 0;
2264 }
2265 }
2266
2267 if ($check ne "bad") {
2268 doprint "TESTING BISECT GOOD [$good]\n";
2269 run_command "git checkout $good" or
2270 die "Failed to checkout $good";
2271
2272 $result = run_bisect $type;
2273
2274 if ($result ne "good") {
2275 fail "Tested BISECT_GOOD [$good] and it failed" and return 0;
2276 }
2277 }
2278
2279 # checkout where we started
2280 run_command "git checkout $head" or
2281 die "Failed to checkout $head";
2282 }
2283
Steven Rostedt3410f6f2011-03-08 09:38:12 -05002284 run_command "git bisect start$start_files" or
Steven Rostedta75fece2010-11-02 14:58:27 -04002285 dodie "could not start bisect";
2286
2287 run_command "git bisect good $good" or
2288 dodie "could not set bisect good to $good";
2289
2290 run_git_bisect "git bisect bad $bad" or
2291 dodie "could not set bisect bad to $bad";
2292
2293 if (defined($replay)) {
2294 run_command "git bisect replay $replay" or
2295 dodie "failed to run replay";
2296 }
2297
2298 if (defined($start)) {
2299 run_command "git checkout $start" or
2300 dodie "failed to checkout $start";
2301 }
2302
2303 my $test;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002304 do {
2305 $result = run_bisect $type;
Steven Rostedta75fece2010-11-02 14:58:27 -04002306 $test = run_git_bisect "git bisect $result";
2307 } while ($test);
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002308
2309 run_command "git bisect log" or
2310 dodie "could not capture git bisect log";
2311
2312 run_command "git bisect reset" or
2313 dodie "could not reset git bisect";
2314
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002315 doprint "Bad commit was [$bisect_bad_commit]\n";
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002316
Steven Rostedt0a05c762010-11-08 11:14:10 -05002317 success $i;
2318}
2319
2320my %config_ignore;
2321my %config_set;
2322
2323my %config_list;
2324my %null_config;
2325
2326my %dependency;
2327
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002328sub assign_configs {
2329 my ($hash, $config) = @_;
Steven Rostedt0a05c762010-11-08 11:14:10 -05002330
2331 open (IN, $config)
2332 or dodie "Failed to read $config";
2333
2334 while (<IN>) {
Steven Rostedt9bf71742011-06-01 23:27:19 -04002335 if (/^((CONFIG\S*)=.*)/) {
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002336 ${$hash}{$2} = $1;
Steven Rostedt0a05c762010-11-08 11:14:10 -05002337 }
2338 }
2339
2340 close(IN);
2341}
2342
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002343sub process_config_ignore {
2344 my ($config) = @_;
2345
2346 assign_configs \%config_ignore, $config;
2347}
2348
Steven Rostedt0a05c762010-11-08 11:14:10 -05002349sub read_current_config {
2350 my ($config_ref) = @_;
2351
2352 %{$config_ref} = ();
2353 undef %{$config_ref};
2354
2355 my @key = keys %{$config_ref};
2356 if ($#key >= 0) {
2357 print "did not delete!\n";
2358 exit;
2359 }
2360 open (IN, "$output_config");
2361
2362 while (<IN>) {
2363 if (/^(CONFIG\S+)=(.*)/) {
2364 ${$config_ref}{$1} = $2;
2365 }
2366 }
2367 close(IN);
2368}
2369
2370sub get_dependencies {
2371 my ($config) = @_;
2372
2373 my $arr = $dependency{$config};
2374 if (!defined($arr)) {
2375 return ();
2376 }
2377
2378 my @deps = @{$arr};
2379
2380 foreach my $dep (@{$arr}) {
2381 print "ADD DEP $dep\n";
2382 @deps = (@deps, get_dependencies $dep);
2383 }
2384
2385 return @deps;
2386}
2387
2388sub create_config {
2389 my @configs = @_;
2390
2391 open(OUT, ">$output_config") or dodie "Can not write to $output_config";
2392
2393 foreach my $config (@configs) {
2394 print OUT "$config_set{$config}\n";
2395 my @deps = get_dependencies $config;
2396 foreach my $dep (@deps) {
2397 print OUT "$config_set{$dep}\n";
2398 }
2399 }
2400
2401 foreach my $config (keys %config_ignore) {
2402 print OUT "$config_ignore{$config}\n";
2403 }
2404 close(OUT);
2405
2406# exit;
Steven Rostedtfcb3f162011-06-13 10:40:58 -04002407 make_oldconfig;
Steven Rostedt0a05c762010-11-08 11:14:10 -05002408}
2409
2410sub compare_configs {
2411 my (%a, %b) = @_;
2412
2413 foreach my $item (keys %a) {
2414 if (!defined($b{$item})) {
2415 print "diff $item\n";
2416 return 1;
2417 }
2418 delete $b{$item};
2419 }
2420
2421 my @keys = keys %b;
2422 if ($#keys) {
2423 print "diff2 $keys[0]\n";
2424 }
2425 return -1 if ($#keys >= 0);
2426
2427 return 0;
2428}
2429
2430sub run_config_bisect_test {
2431 my ($type) = @_;
2432
2433 return run_bisect_test $type, "oldconfig";
2434}
2435
2436sub process_passed {
2437 my (%configs) = @_;
2438
2439 doprint "These configs had no failure: (Enabling them for further compiles)\n";
2440 # Passed! All these configs are part of a good compile.
2441 # Add them to the min options.
2442 foreach my $config (keys %configs) {
2443 if (defined($config_list{$config})) {
2444 doprint " removing $config\n";
2445 $config_ignore{$config} = $config_list{$config};
2446 delete $config_list{$config};
2447 }
2448 }
Steven Rostedtf1a27852010-11-11 11:34:38 -05002449 doprint "config copied to $outputdir/config_good\n";
2450 run_command "cp -f $output_config $outputdir/config_good";
Steven Rostedt0a05c762010-11-08 11:14:10 -05002451}
2452
2453sub process_failed {
2454 my ($config) = @_;
2455
2456 doprint "\n\n***************************************\n";
2457 doprint "Found bad config: $config\n";
2458 doprint "***************************************\n\n";
2459}
2460
2461sub run_config_bisect {
2462
2463 my @start_list = keys %config_list;
2464
2465 if ($#start_list < 0) {
2466 doprint "No more configs to test!!!\n";
2467 return -1;
2468 }
2469
2470 doprint "***** RUN TEST ***\n";
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002471 my $type = $config_bisect_type;
Steven Rostedt0a05c762010-11-08 11:14:10 -05002472 my $ret;
2473 my %current_config;
2474
2475 my $count = $#start_list + 1;
2476 doprint " $count configs to test\n";
2477
2478 my $half = int($#start_list / 2);
2479
2480 do {
2481 my @tophalf = @start_list[0 .. $half];
2482
2483 create_config @tophalf;
2484 read_current_config \%current_config;
2485
2486 $count = $#tophalf + 1;
2487 doprint "Testing $count configs\n";
2488 my $found = 0;
2489 # make sure we test something
2490 foreach my $config (@tophalf) {
2491 if (defined($current_config{$config})) {
2492 logit " $config\n";
2493 $found = 1;
2494 }
2495 }
2496 if (!$found) {
2497 # try the other half
2498 doprint "Top half produced no set configs, trying bottom half\n";
Steven Rostedt4c8cc552011-06-01 23:22:30 -04002499 @tophalf = @start_list[$half + 1 .. $#start_list];
Steven Rostedt0a05c762010-11-08 11:14:10 -05002500 create_config @tophalf;
2501 read_current_config \%current_config;
2502 foreach my $config (@tophalf) {
2503 if (defined($current_config{$config})) {
2504 logit " $config\n";
2505 $found = 1;
2506 }
2507 }
2508 if (!$found) {
2509 doprint "Failed: Can't make new config with current configs\n";
2510 foreach my $config (@start_list) {
2511 doprint " CONFIG: $config\n";
2512 }
2513 return -1;
2514 }
2515 $count = $#tophalf + 1;
2516 doprint "Testing $count configs\n";
2517 }
2518
2519 $ret = run_config_bisect_test $type;
Steven Rostedtc960bb92011-03-08 09:22:39 -05002520 if ($bisect_manual) {
2521 $ret = answer_bisect;
2522 }
Steven Rostedt0a05c762010-11-08 11:14:10 -05002523 if ($ret) {
2524 process_passed %current_config;
2525 return 0;
2526 }
2527
2528 doprint "This config had a failure.\n";
2529 doprint "Removing these configs that were not set in this config:\n";
Steven Rostedtf1a27852010-11-11 11:34:38 -05002530 doprint "config copied to $outputdir/config_bad\n";
2531 run_command "cp -f $output_config $outputdir/config_bad";
Steven Rostedt0a05c762010-11-08 11:14:10 -05002532
2533 # A config exists in this group that was bad.
2534 foreach my $config (keys %config_list) {
2535 if (!defined($current_config{$config})) {
2536 doprint " removing $config\n";
2537 delete $config_list{$config};
2538 }
2539 }
2540
2541 @start_list = @tophalf;
2542
2543 if ($#start_list == 0) {
2544 process_failed $start_list[0];
2545 return 1;
2546 }
2547
2548 # remove half the configs we are looking at and see if
2549 # they are good.
2550 $half = int($#start_list / 2);
Steven Rostedt4c8cc552011-06-01 23:22:30 -04002551 } while ($#start_list > 0);
Steven Rostedt0a05c762010-11-08 11:14:10 -05002552
Steven Rostedtc960bb92011-03-08 09:22:39 -05002553 # we found a single config, try it again unless we are running manually
2554
2555 if ($bisect_manual) {
2556 process_failed $start_list[0];
2557 return 1;
2558 }
2559
Steven Rostedt0a05c762010-11-08 11:14:10 -05002560 my @tophalf = @start_list[0 .. 0];
2561
2562 $ret = run_config_bisect_test $type;
2563 if ($ret) {
2564 process_passed %current_config;
2565 return 0;
2566 }
2567
2568 process_failed $start_list[0];
2569 return 1;
2570}
2571
2572sub config_bisect {
2573 my ($i) = @_;
2574
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002575 my $start_config = $config_bisect;
Steven Rostedt0a05c762010-11-08 11:14:10 -05002576
2577 my $tmpconfig = "$tmpdir/use_config";
2578
Steven Rostedt30f75da2011-06-13 10:35:35 -04002579 if (defined($config_bisect_good)) {
2580 process_config_ignore $config_bisect_good;
2581 }
2582
Steven Rostedt0a05c762010-11-08 11:14:10 -05002583 # Make the file with the bad config and the min config
2584 if (defined($minconfig)) {
2585 # read the min config for things to ignore
2586 run_command "cp $minconfig $tmpconfig" or
2587 dodie "failed to copy $minconfig to $tmpconfig";
2588 } else {
2589 unlink $tmpconfig;
2590 }
2591
Steven Rostedt0a05c762010-11-08 11:14:10 -05002592 if (-f $tmpconfig) {
Steven Rostedtfcb3f162011-06-13 10:40:58 -04002593 load_force_config($tmpconfig);
Steven Rostedt0a05c762010-11-08 11:14:10 -05002594 process_config_ignore $tmpconfig;
2595 }
2596
2597 # now process the start config
2598 run_command "cp $start_config $output_config" or
2599 dodie "failed to copy $start_config to $output_config";
2600
2601 # read directly what we want to check
2602 my %config_check;
2603 open (IN, $output_config)
2604 or dodie "faied to open $output_config";
2605
2606 while (<IN>) {
2607 if (/^((CONFIG\S*)=.*)/) {
2608 $config_check{$2} = $1;
2609 }
2610 }
2611 close(IN);
2612
Steven Rostedt250bae82011-07-15 22:05:59 -04002613 # Now run oldconfig with the minconfig
Steven Rostedtfcb3f162011-06-13 10:40:58 -04002614 make_oldconfig;
Steven Rostedt0a05c762010-11-08 11:14:10 -05002615
2616 # check to see what we lost (or gained)
2617 open (IN, $output_config)
2618 or dodie "Failed to read $start_config";
2619
2620 my %removed_configs;
2621 my %added_configs;
2622
2623 while (<IN>) {
2624 if (/^((CONFIG\S*)=.*)/) {
2625 # save off all options
2626 $config_set{$2} = $1;
2627 if (defined($config_check{$2})) {
2628 if (defined($config_ignore{$2})) {
2629 $removed_configs{$2} = $1;
2630 } else {
2631 $config_list{$2} = $1;
2632 }
2633 } elsif (!defined($config_ignore{$2})) {
2634 $added_configs{$2} = $1;
2635 $config_list{$2} = $1;
2636 }
2637 }
2638 }
2639 close(IN);
2640
2641 my @confs = keys %removed_configs;
2642 if ($#confs >= 0) {
2643 doprint "Configs overridden by default configs and removed from check:\n";
2644 foreach my $config (@confs) {
2645 doprint " $config\n";
2646 }
2647 }
2648 @confs = keys %added_configs;
2649 if ($#confs >= 0) {
2650 doprint "Configs appearing in make oldconfig and added:\n";
2651 foreach my $config (@confs) {
2652 doprint " $config\n";
2653 }
2654 }
2655
2656 my %config_test;
2657 my $once = 0;
2658
2659 # Sometimes kconfig does weird things. We must make sure
2660 # that the config we autocreate has everything we need
2661 # to test, otherwise we may miss testing configs, or
2662 # may not be able to create a new config.
2663 # Here we create a config with everything set.
2664 create_config (keys %config_list);
2665 read_current_config \%config_test;
2666 foreach my $config (keys %config_list) {
2667 if (!defined($config_test{$config})) {
2668 if (!$once) {
2669 $once = 1;
2670 doprint "Configs not produced by kconfig (will not be checked):\n";
2671 }
2672 doprint " $config\n";
2673 delete $config_list{$config};
2674 }
2675 }
2676 my $ret;
2677 do {
2678 $ret = run_config_bisect;
2679 } while (!$ret);
2680
2681 return $ret if ($ret < 0);
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04002682
2683 success $i;
2684}
2685
Steven Rostedt27d934b2011-05-20 09:18:18 -04002686sub patchcheck_reboot {
2687 doprint "Reboot and sleep $patchcheck_sleep_time seconds\n";
Steven Rostedtbc7c5802011-12-22 16:29:10 -05002688 reboot_to_good $patchcheck_sleep_time;
Steven Rostedt27d934b2011-05-20 09:18:18 -04002689}
2690
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002691sub patchcheck {
2692 my ($i) = @_;
2693
2694 die "PATCHCHECK_START[$i] not defined\n"
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002695 if (!defined($patchcheck_start));
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002696 die "PATCHCHECK_TYPE[$i] not defined\n"
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002697 if (!defined($patchcheck_type));
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002698
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002699 my $start = $patchcheck_start;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002700
2701 my $end = "HEAD";
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002702 if (defined($patchcheck_end)) {
2703 $end = $patchcheck_end;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002704 }
2705
Steven Rostedta57419b2010-11-02 15:13:54 -04002706 # Get the true sha1's since we can use things like HEAD~3
2707 $start = get_sha1($start);
2708 $end = get_sha1($end);
2709
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05002710 my $type = $patchcheck_type;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002711
2712 # Can't have a test without having a test to run
2713 if ($type eq "test" && !defined($run_test)) {
2714 $type = "boot";
2715 }
2716
2717 open (IN, "git log --pretty=oneline $end|") or
2718 dodie "could not get git list";
2719
2720 my @list;
2721
2722 while (<IN>) {
2723 chomp;
2724 $list[$#list+1] = $_;
2725 last if (/^$start/);
2726 }
2727 close(IN);
2728
2729 if ($list[$#list] !~ /^$start/) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002730 fail "SHA1 $start not found";
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002731 }
2732
2733 # go backwards in the list
2734 @list = reverse @list;
2735
2736 my $save_clean = $noclean;
Steven Rostedt19902072011-06-14 20:46:25 -04002737 my %ignored_warnings;
2738
2739 if (defined($ignore_warnings)) {
2740 foreach my $sha1 (split /\s+/, $ignore_warnings) {
2741 $ignored_warnings{$sha1} = 1;
2742 }
2743 }
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002744
2745 $in_patchcheck = 1;
2746 foreach my $item (@list) {
2747 my $sha1 = $item;
2748 $sha1 =~ s/^([[:xdigit:]]+).*/$1/;
2749
2750 doprint "\nProcessing commit $item\n\n";
2751
2752 run_command "git checkout $sha1" or
2753 die "Failed to checkout $sha1";
2754
2755 # only clean on the first and last patch
2756 if ($item eq $list[0] ||
2757 $item eq $list[$#list]) {
2758 $noclean = $save_clean;
2759 } else {
2760 $noclean = 1;
2761 }
2762
2763 if (defined($minconfig)) {
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002764 build "useconfig:$minconfig" or return 0;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002765 } else {
2766 # ?? no config to use?
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002767 build "oldconfig" or return 0;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002768 }
2769
Steven Rostedt19902072011-06-14 20:46:25 -04002770
2771 if (!defined($ignored_warnings{$sha1})) {
2772 check_buildlog $sha1 or return 0;
2773 }
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002774
2775 next if ($type eq "build");
2776
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002777 my $failed = 0;
2778
Steven Rostedtddf607e2011-06-14 20:49:13 -04002779 start_monitor_and_boot or $failed = 1;
Steven Rostedt7faafbd2010-11-02 14:58:22 -04002780
2781 if (!$failed && $type ne "boot"){
2782 do_run_test or $failed = 1;
2783 }
2784 end_monitor;
2785 return 0 if ($failed);
2786
Steven Rostedt27d934b2011-05-20 09:18:18 -04002787 patchcheck_reboot;
2788
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002789 }
2790 $in_patchcheck = 0;
2791 success $i;
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04002792
2793 return 1;
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04002794}
2795
Steven Rostedtb9066f62011-07-15 21:25:24 -04002796my %depends;
Steven Rostedtac6974c2011-10-04 09:40:17 -04002797my %depcount;
Steven Rostedtb9066f62011-07-15 21:25:24 -04002798my $iflevel = 0;
2799my @ifdeps;
2800
2801# prevent recursion
2802my %read_kconfigs;
2803
Steven Rostedtac6974c2011-10-04 09:40:17 -04002804sub add_dep {
2805 # $config depends on $dep
2806 my ($config, $dep) = @_;
2807
2808 if (defined($depends{$config})) {
2809 $depends{$config} .= " " . $dep;
2810 } else {
2811 $depends{$config} = $dep;
2812 }
2813
2814 # record the number of configs depending on $dep
2815 if (defined $depcount{$dep}) {
2816 $depcount{$dep}++;
2817 } else {
2818 $depcount{$dep} = 1;
2819 }
2820}
2821
Steven Rostedtb9066f62011-07-15 21:25:24 -04002822# taken from streamline_config.pl
2823sub read_kconfig {
2824 my ($kconfig) = @_;
2825
2826 my $state = "NONE";
2827 my $config;
2828 my @kconfigs;
2829
2830 my $cont = 0;
2831 my $line;
2832
2833
2834 if (! -f $kconfig) {
2835 doprint "file $kconfig does not exist, skipping\n";
2836 return;
2837 }
2838
2839 open(KIN, "$kconfig")
2840 or die "Can't open $kconfig";
2841 while (<KIN>) {
2842 chomp;
2843
2844 # Make sure that lines ending with \ continue
2845 if ($cont) {
2846 $_ = $line . " " . $_;
2847 }
2848
2849 if (s/\\$//) {
2850 $cont = 1;
2851 $line = $_;
2852 next;
2853 }
2854
2855 $cont = 0;
2856
2857 # collect any Kconfig sources
2858 if (/^source\s*"(.*)"/) {
2859 $kconfigs[$#kconfigs+1] = $1;
2860 }
2861
2862 # configs found
2863 if (/^\s*(menu)?config\s+(\S+)\s*$/) {
2864 $state = "NEW";
2865 $config = $2;
2866
2867 for (my $i = 0; $i < $iflevel; $i++) {
Steven Rostedtac6974c2011-10-04 09:40:17 -04002868 add_dep $config, $ifdeps[$i];
Steven Rostedtb9066f62011-07-15 21:25:24 -04002869 }
2870
2871 # collect the depends for the config
2872 } elsif ($state eq "NEW" && /^\s*depends\s+on\s+(.*)$/) {
2873
Steven Rostedtac6974c2011-10-04 09:40:17 -04002874 add_dep $config, $1;
Steven Rostedtb9066f62011-07-15 21:25:24 -04002875
2876 # Get the configs that select this config
Steven Rostedtac6974c2011-10-04 09:40:17 -04002877 } elsif ($state eq "NEW" && /^\s*select\s+(\S+)/) {
2878
2879 # selected by depends on config
2880 add_dep $1, $config;
Steven Rostedtb9066f62011-07-15 21:25:24 -04002881
2882 # Check for if statements
2883 } elsif (/^if\s+(.*\S)\s*$/) {
2884 my $deps = $1;
2885 # remove beginning and ending non text
2886 $deps =~ s/^[^a-zA-Z0-9_]*//;
2887 $deps =~ s/[^a-zA-Z0-9_]*$//;
2888
2889 my @deps = split /[^a-zA-Z0-9_]+/, $deps;
2890
2891 $ifdeps[$iflevel++] = join ':', @deps;
2892
2893 } elsif (/^endif/) {
2894
2895 $iflevel-- if ($iflevel);
2896
2897 # stop on "help"
2898 } elsif (/^\s*help\s*$/) {
2899 $state = "NONE";
2900 }
2901 }
2902 close(KIN);
2903
2904 # read in any configs that were found.
2905 foreach $kconfig (@kconfigs) {
2906 if (!defined($read_kconfigs{$kconfig})) {
2907 $read_kconfigs{$kconfig} = 1;
2908 read_kconfig("$builddir/$kconfig");
2909 }
2910 }
2911}
2912
2913sub read_depends {
2914 # find out which arch this is by the kconfig file
2915 open (IN, $output_config)
2916 or dodie "Failed to read $output_config";
2917 my $arch;
2918 while (<IN>) {
2919 if (m,Linux/(\S+)\s+\S+\s+Kernel Configuration,) {
2920 $arch = $1;
2921 last;
2922 }
2923 }
2924 close IN;
2925
2926 if (!defined($arch)) {
2927 doprint "Could not find arch from config file\n";
2928 doprint "no dependencies used\n";
2929 return;
2930 }
2931
2932 # arch is really the subarch, we need to know
2933 # what directory to look at.
2934 if ($arch eq "i386" || $arch eq "x86_64") {
2935 $arch = "x86";
2936 } elsif ($arch =~ /^tile/) {
2937 $arch = "tile";
2938 }
2939
2940 my $kconfig = "$builddir/arch/$arch/Kconfig";
2941
2942 if (! -f $kconfig && $arch =~ /\d$/) {
2943 my $orig = $arch;
2944 # some subarchs have numbers, truncate them
2945 $arch =~ s/\d*$//;
2946 $kconfig = "$builddir/arch/$arch/Kconfig";
2947 if (! -f $kconfig) {
2948 doprint "No idea what arch dir $orig is for\n";
2949 doprint "no dependencies used\n";
2950 return;
2951 }
2952 }
2953
2954 read_kconfig($kconfig);
2955}
2956
Steven Rostedt4c4ab122011-07-15 21:16:17 -04002957sub read_config_list {
2958 my ($config) = @_;
2959
2960 open (IN, $config)
2961 or dodie "Failed to read $config";
2962
2963 while (<IN>) {
2964 if (/^((CONFIG\S*)=.*)/) {
2965 if (!defined($config_ignore{$2})) {
2966 $config_list{$2} = $1;
2967 }
2968 }
2969 }
2970
2971 close(IN);
2972}
2973
2974sub read_output_config {
2975 my ($config) = @_;
2976
2977 assign_configs \%config_ignore, $config;
2978}
2979
2980sub make_new_config {
2981 my @configs = @_;
2982
2983 open (OUT, ">$output_config")
2984 or dodie "Failed to write $output_config";
2985
2986 foreach my $config (@configs) {
2987 print OUT "$config\n";
2988 }
2989 close OUT;
2990}
2991
Steven Rostedtac6974c2011-10-04 09:40:17 -04002992sub chomp_config {
2993 my ($config) = @_;
2994
2995 $config =~ s/CONFIG_//;
2996
2997 return $config;
2998}
2999
Steven Rostedtb9066f62011-07-15 21:25:24 -04003000sub get_depends {
3001 my ($dep) = @_;
3002
Steven Rostedtac6974c2011-10-04 09:40:17 -04003003 my $kconfig = chomp_config $dep;
Steven Rostedtb9066f62011-07-15 21:25:24 -04003004
3005 $dep = $depends{"$kconfig"};
3006
3007 # the dep string we have saves the dependencies as they
3008 # were found, including expressions like ! && ||. We
3009 # want to split this out into just an array of configs.
3010
3011 my $valid = "A-Za-z_0-9";
3012
3013 my @configs;
3014
3015 while ($dep =~ /[$valid]/) {
3016
3017 if ($dep =~ /^[^$valid]*([$valid]+)/) {
3018 my $conf = "CONFIG_" . $1;
3019
3020 $configs[$#configs + 1] = $conf;
3021
3022 $dep =~ s/^[^$valid]*[$valid]+//;
3023 } else {
3024 die "this should never happen";
3025 }
3026 }
3027
3028 return @configs;
3029}
3030
3031my %min_configs;
3032my %keep_configs;
Steven Rostedt43d1b652011-07-15 22:01:56 -04003033my %save_configs;
Steven Rostedtb9066f62011-07-15 21:25:24 -04003034my %processed_configs;
3035my %nochange_config;
3036
3037sub test_this_config {
3038 my ($config) = @_;
3039
3040 my $found;
3041
3042 # if we already processed this config, skip it
3043 if (defined($processed_configs{$config})) {
3044 return undef;
3045 }
3046 $processed_configs{$config} = 1;
3047
3048 # if this config failed during this round, skip it
3049 if (defined($nochange_config{$config})) {
3050 return undef;
3051 }
3052
Steven Rostedtac6974c2011-10-04 09:40:17 -04003053 my $kconfig = chomp_config $config;
Steven Rostedtb9066f62011-07-15 21:25:24 -04003054
3055 # Test dependencies first
3056 if (defined($depends{"$kconfig"})) {
3057 my @parents = get_depends $config;
3058 foreach my $parent (@parents) {
3059 # if the parent is in the min config, check it first
3060 next if (!defined($min_configs{$parent}));
3061 $found = test_this_config($parent);
3062 if (defined($found)) {
3063 return $found;
3064 }
3065 }
3066 }
3067
3068 # Remove this config from the list of configs
3069 # do a make oldnoconfig and then read the resulting
3070 # .config to make sure it is missing the config that
3071 # we had before
3072 my %configs = %min_configs;
3073 delete $configs{$config};
3074 make_new_config ((values %configs), (values %keep_configs));
3075 make_oldconfig;
3076 undef %configs;
3077 assign_configs \%configs, $output_config;
3078
3079 return $config if (!defined($configs{$config}));
3080
3081 doprint "disabling config $config did not change .config\n";
3082
3083 $nochange_config{$config} = 1;
3084
3085 return undef;
3086}
3087
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003088sub make_min_config {
3089 my ($i) = @_;
3090
3091 if (!defined($output_minconfig)) {
3092 fail "OUTPUT_MIN_CONFIG not defined" and return;
3093 }
Steven Rostedt35ce5952011-07-15 21:57:25 -04003094
3095 # If output_minconfig exists, and the start_minconfig
3096 # came from min_config, than ask if we should use
3097 # that instead.
3098 if (-f $output_minconfig && !$start_minconfig_defined) {
3099 print "$output_minconfig exists\n";
3100 if (read_yn " Use it as minconfig?") {
3101 $start_minconfig = $output_minconfig;
3102 }
3103 }
3104
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003105 if (!defined($start_minconfig)) {
3106 fail "START_MIN_CONFIG or MIN_CONFIG not defined" and return;
3107 }
3108
Steven Rostedt35ce5952011-07-15 21:57:25 -04003109 my $temp_config = "$tmpdir/temp_config";
3110
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003111 # First things first. We build an allnoconfig to find
3112 # out what the defaults are that we can't touch.
3113 # Some are selections, but we really can't handle selections.
3114
3115 my $save_minconfig = $minconfig;
3116 undef $minconfig;
3117
3118 run_command "$make allnoconfig" or return 0;
3119
Steven Rostedtb9066f62011-07-15 21:25:24 -04003120 read_depends;
3121
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003122 process_config_ignore $output_config;
Steven Rostedtb9066f62011-07-15 21:25:24 -04003123
Steven Rostedt43d1b652011-07-15 22:01:56 -04003124 undef %save_configs;
Steven Rostedtb9066f62011-07-15 21:25:24 -04003125 undef %min_configs;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003126
3127 if (defined($ignore_config)) {
3128 # make sure the file exists
3129 `touch $ignore_config`;
Steven Rostedt43d1b652011-07-15 22:01:56 -04003130 assign_configs \%save_configs, $ignore_config;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003131 }
3132
Steven Rostedt43d1b652011-07-15 22:01:56 -04003133 %keep_configs = %save_configs;
3134
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003135 doprint "Load initial configs from $start_minconfig\n";
3136
3137 # Look at the current min configs, and save off all the
3138 # ones that were set via the allnoconfig
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003139 assign_configs \%min_configs, $start_minconfig;
3140
3141 my @config_keys = keys %min_configs;
3142
Steven Rostedtac6974c2011-10-04 09:40:17 -04003143 # All configs need a depcount
3144 foreach my $config (@config_keys) {
3145 my $kconfig = chomp_config $config;
3146 if (!defined $depcount{$kconfig}) {
3147 $depcount{$kconfig} = 0;
3148 }
3149 }
3150
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003151 # Remove anything that was set by the make allnoconfig
3152 # we shouldn't need them as they get set for us anyway.
3153 foreach my $config (@config_keys) {
3154 # Remove anything in the ignore_config
3155 if (defined($keep_configs{$config})) {
3156 my $file = $ignore_config;
3157 $file =~ s,.*/(.*?)$,$1,;
3158 doprint "$config set by $file ... ignored\n";
3159 delete $min_configs{$config};
3160 next;
3161 }
3162 # But make sure the settings are the same. If a min config
3163 # sets a selection, we do not want to get rid of it if
3164 # it is not the same as what we have. Just move it into
3165 # the keep configs.
3166 if (defined($config_ignore{$config})) {
3167 if ($config_ignore{$config} ne $min_configs{$config}) {
3168 doprint "$config is in allnoconfig as '$config_ignore{$config}'";
3169 doprint " but it is '$min_configs{$config}' in minconfig .. keeping\n";
3170 $keep_configs{$config} = $min_configs{$config};
3171 } else {
3172 doprint "$config set by allnoconfig ... ignored\n";
3173 }
3174 delete $min_configs{$config};
3175 }
3176 }
3177
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003178 my $done = 0;
Steven Rostedtb9066f62011-07-15 21:25:24 -04003179 my $take_two = 0;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003180
3181 while (!$done) {
3182
3183 my $config;
3184 my $found;
3185
3186 # Now disable each config one by one and do a make oldconfig
3187 # till we find a config that changes our list.
3188
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003189 my @test_configs = keys %min_configs;
Steven Rostedtac6974c2011-10-04 09:40:17 -04003190
3191 # Sort keys by who is most dependent on
3192 @test_configs = sort { $depcount{chomp_config($b)} <=> $depcount{chomp_config($a)} }
3193 @test_configs ;
3194
3195 # Put configs that did not modify the config at the end.
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003196 my $reset = 1;
3197 for (my $i = 0; $i < $#test_configs; $i++) {
3198 if (!defined($nochange_config{$test_configs[0]})) {
3199 $reset = 0;
3200 last;
3201 }
3202 # This config didn't change the .config last time.
3203 # Place it at the end
3204 my $config = shift @test_configs;
3205 push @test_configs, $config;
3206 }
3207
3208 # if every test config has failed to modify the .config file
3209 # in the past, then reset and start over.
3210 if ($reset) {
3211 undef %nochange_config;
3212 }
3213
Steven Rostedtb9066f62011-07-15 21:25:24 -04003214 undef %processed_configs;
3215
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003216 foreach my $config (@test_configs) {
3217
Steven Rostedtb9066f62011-07-15 21:25:24 -04003218 $found = test_this_config $config;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003219
Steven Rostedtb9066f62011-07-15 21:25:24 -04003220 last if (defined($found));
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003221
3222 # oh well, try another config
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003223 }
3224
3225 if (!defined($found)) {
Steven Rostedtb9066f62011-07-15 21:25:24 -04003226 # we could have failed due to the nochange_config hash
3227 # reset and try again
3228 if (!$take_two) {
3229 undef %nochange_config;
3230 $take_two = 1;
3231 next;
3232 }
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003233 doprint "No more configs found that we can disable\n";
3234 $done = 1;
3235 last;
3236 }
Steven Rostedtb9066f62011-07-15 21:25:24 -04003237 $take_two = 0;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003238
3239 $config = $found;
3240
3241 doprint "Test with $config disabled\n";
3242
3243 # set in_bisect to keep build and monitor from dieing
3244 $in_bisect = 1;
3245
3246 my $failed = 0;
Steven Rostedtbf1c95a2012-02-27 13:58:49 -05003247 build "oldconfig" or $failed = 1;
3248 if (!$failed) {
3249 start_monitor_and_boot or $failed = 1;
3250 end_monitor;
3251 }
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003252
3253 $in_bisect = 0;
3254
3255 if ($failed) {
Steven Rostedtb9066f62011-07-15 21:25:24 -04003256 doprint "$min_configs{$config} is needed to boot the box... keeping\n";
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003257 # this config is needed, add it to the ignore list.
3258 $keep_configs{$config} = $min_configs{$config};
Steven Rostedt43d1b652011-07-15 22:01:56 -04003259 $save_configs{$config} = $min_configs{$config};
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003260 delete $min_configs{$config};
Steven Rostedt35ce5952011-07-15 21:57:25 -04003261
3262 # update new ignore configs
3263 if (defined($ignore_config)) {
3264 open (OUT, ">$temp_config")
3265 or die "Can't write to $temp_config";
Steven Rostedt43d1b652011-07-15 22:01:56 -04003266 foreach my $config (keys %save_configs) {
3267 print OUT "$save_configs{$config}\n";
Steven Rostedt35ce5952011-07-15 21:57:25 -04003268 }
3269 close OUT;
3270 run_command "mv $temp_config $ignore_config" or
3271 dodie "failed to copy update to $ignore_config";
3272 }
3273
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003274 } else {
3275 # We booted without this config, remove it from the minconfigs.
3276 doprint "$config is not needed, disabling\n";
3277
3278 delete $min_configs{$config};
3279
3280 # Also disable anything that is not enabled in this config
3281 my %configs;
3282 assign_configs \%configs, $output_config;
3283 my @config_keys = keys %min_configs;
3284 foreach my $config (@config_keys) {
3285 if (!defined($configs{$config})) {
3286 doprint "$config is not set, disabling\n";
3287 delete $min_configs{$config};
3288 }
3289 }
3290
3291 # Save off all the current mandidory configs
Steven Rostedt35ce5952011-07-15 21:57:25 -04003292 open (OUT, ">$temp_config")
3293 or die "Can't write to $temp_config";
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003294 foreach my $config (keys %keep_configs) {
3295 print OUT "$keep_configs{$config}\n";
3296 }
3297 foreach my $config (keys %min_configs) {
3298 print OUT "$min_configs{$config}\n";
3299 }
3300 close OUT;
Steven Rostedt35ce5952011-07-15 21:57:25 -04003301
3302 run_command "mv $temp_config $output_minconfig" or
3303 dodie "failed to copy update to $output_minconfig";
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003304 }
3305
3306 doprint "Reboot and wait $sleep_time seconds\n";
Steven Rostedtbc7c5802011-12-22 16:29:10 -05003307 reboot_to_good $sleep_time;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003308 }
3309
3310 success $i;
3311 return 1;
3312}
3313
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003314$#ARGV < 1 or die "ktest.pl version: $VERSION\n usage: ktest.pl config-file\n";
Steven Rostedt2545eb62010-11-02 15:01:32 -04003315
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003316if ($#ARGV == 0) {
3317 $ktest_config = $ARGV[0];
3318 if (! -f $ktest_config) {
3319 print "$ktest_config does not exist.\n";
Steven Rostedt35ce5952011-07-15 21:57:25 -04003320 if (!read_yn "Create it?") {
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003321 exit 0;
3322 }
3323 }
3324} else {
3325 $ktest_config = "ktest.conf";
3326}
3327
3328if (! -f $ktest_config) {
Steven Rostedtdbd37832011-11-23 16:00:48 -05003329 $newconfig = 1;
Steven Rostedtc4261d02011-11-23 13:41:18 -05003330 get_test_case;
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003331 open(OUT, ">$ktest_config") or die "Can not create $ktest_config";
3332 print OUT << "EOF"
3333# Generated by ktest.pl
3334#
Steven Rostedt0e7a22d2011-11-21 20:39:33 -05003335
3336# PWD is a ktest.pl variable that will result in the process working
3337# directory that ktest.pl is executed in.
3338
3339# THIS_DIR is automatically assigned the PWD of the path that generated
3340# the config file. It is best to use this variable when assigning other
3341# directory paths within this directory. This allows you to easily
3342# move the test cases to other locations or to other machines.
3343#
3344THIS_DIR := $variable{"PWD"}
3345
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003346# Define each test with TEST_START
3347# The config options below it will override the defaults
3348TEST_START
Steven Rostedtc4261d02011-11-23 13:41:18 -05003349TEST_TYPE = $default{"TEST_TYPE"}
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003350
3351DEFAULTS
3352EOF
3353;
3354 close(OUT);
3355}
3356read_config $ktest_config;
3357
Steven Rostedt23715c3c2011-06-13 11:03:34 -04003358if (defined($opt{"LOG_FILE"})) {
3359 $opt{"LOG_FILE"} = eval_option($opt{"LOG_FILE"}, -1);
3360}
3361
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003362# Append any configs entered in manually to the config file.
3363my @new_configs = keys %entered_configs;
3364if ($#new_configs >= 0) {
3365 print "\nAppending entered in configs to $ktest_config\n";
3366 open(OUT, ">>$ktest_config") or die "Can not append to $ktest_config";
3367 foreach my $config (@new_configs) {
3368 print OUT "$config = $entered_configs{$config}\n";
Steven Rostedt0e7a22d2011-11-21 20:39:33 -05003369 $opt{$config} = process_variables($entered_configs{$config});
Steven Rostedt8d1491b2010-11-18 15:39:48 -05003370 }
3371}
Steven Rostedt2545eb62010-11-02 15:01:32 -04003372
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04003373if ($opt{"CLEAR_LOG"} && defined($opt{"LOG_FILE"})) {
3374 unlink $opt{"LOG_FILE"};
3375}
Steven Rostedt2545eb62010-11-02 15:01:32 -04003376
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04003377doprint "\n\nSTARTING AUTOMATED TESTS\n\n";
3378
Steven Rostedta57419b2010-11-02 15:13:54 -04003379for (my $i = 0, my $repeat = 1; $i <= $opt{"NUM_TESTS"}; $i += $repeat) {
3380
3381 if (!$i) {
3382 doprint "DEFAULT OPTIONS:\n";
3383 } else {
3384 doprint "\nTEST $i OPTIONS";
3385 if (defined($repeat_tests{$i})) {
3386 $repeat = $repeat_tests{$i};
3387 doprint " ITERATE $repeat";
3388 }
3389 doprint "\n";
3390 }
3391
3392 foreach my $option (sort keys %opt) {
3393
3394 if ($option =~ /\[(\d+)\]$/) {
3395 next if ($i != $1);
3396 } else {
3397 next if ($i);
3398 }
3399
3400 doprint "$option = $opt{$option}\n";
3401 }
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04003402}
Steven Rostedt2545eb62010-11-02 15:01:32 -04003403
Steven Rostedt2a625122011-05-20 15:48:59 -04003404sub __set_test_option {
Steven Rostedt5a391fb2010-11-02 14:57:43 -04003405 my ($name, $i) = @_;
3406
3407 my $option = "$name\[$i\]";
3408
3409 if (defined($opt{$option})) {
3410 return $opt{$option};
3411 }
3412
Steven Rostedta57419b2010-11-02 15:13:54 -04003413 foreach my $test (keys %repeat_tests) {
3414 if ($i >= $test &&
3415 $i < $test + $repeat_tests{$test}) {
3416 $option = "$name\[$test\]";
3417 if (defined($opt{$option})) {
3418 return $opt{$option};
3419 }
3420 }
3421 }
3422
Steven Rostedt5a391fb2010-11-02 14:57:43 -04003423 if (defined($opt{$name})) {
3424 return $opt{$name};
3425 }
3426
3427 return undef;
3428}
3429
Steven Rostedt2a625122011-05-20 15:48:59 -04003430sub set_test_option {
3431 my ($name, $i) = @_;
3432
3433 my $option = __set_test_option($name, $i);
3434 return $option if (!defined($option));
3435
Steven Rostedt23715c3c2011-06-13 11:03:34 -04003436 return eval_option($option, $i);
Steven Rostedt2a625122011-05-20 15:48:59 -04003437}
3438
Steven Rostedt2545eb62010-11-02 15:01:32 -04003439# First we need to do is the builds
Steven Rostedta75fece2010-11-02 14:58:27 -04003440for (my $i = 1; $i <= $opt{"NUM_TESTS"}; $i++) {
Steven Rostedt2545eb62010-11-02 15:01:32 -04003441
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04003442 # Do not reboot on failing test options
3443 $no_reboot = 1;
3444
Steven Rostedt576f6272010-11-02 14:58:38 -04003445 $iteration = $i;
3446
Steven Rostedta75fece2010-11-02 14:58:27 -04003447 my $makecmd = set_test_option("MAKE_CMD", $i);
3448
Steven Rostedt9cc9e092011-12-22 21:37:22 -05003449 # Load all the options into their mapped variable names
3450 foreach my $opt (keys %option_map) {
3451 ${$option_map{$opt}} = set_test_option($opt, $i);
3452 }
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05003453
Steven Rostedt35ce5952011-07-15 21:57:25 -04003454 $start_minconfig_defined = 1;
3455
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003456 if (!defined($start_minconfig)) {
Steven Rostedt35ce5952011-07-15 21:57:25 -04003457 $start_minconfig_defined = 0;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003458 $start_minconfig = $minconfig;
3459 }
3460
Steven Rostedta75fece2010-11-02 14:58:27 -04003461 chdir $builddir || die "can't change directory to $builddir";
3462
Andrew Jonesa908a662011-08-12 15:32:03 +02003463 foreach my $dir ($tmpdir, $outputdir) {
3464 if (!-d $dir) {
3465 mkpath($dir) or
3466 die "can't create $dir";
3467 }
Steven Rostedta75fece2010-11-02 14:58:27 -04003468 }
3469
Steven Rostedte48c5292010-11-02 14:35:37 -04003470 $ENV{"SSH_USER"} = $ssh_user;
3471 $ENV{"MACHINE"} = $machine;
3472
Steven Rostedta75fece2010-11-02 14:58:27 -04003473 $buildlog = "$tmpdir/buildlog-$machine";
Rabin Vincenta9dd5d62011-11-18 17:05:29 +05303474 $testlog = "$tmpdir/testlog-$machine";
Steven Rostedta75fece2010-11-02 14:58:27 -04003475 $dmesg = "$tmpdir/dmesg-$machine";
3476 $make = "$makecmd O=$outputdir";
Steven Rostedt51ad1dd2010-11-08 16:43:21 -05003477 $output_config = "$outputdir/.config";
Steven Rostedta75fece2010-11-02 14:58:27 -04003478
Steven Rostedtbb8474b2011-11-23 15:58:00 -05003479 if (!$buildonly) {
3480 $target = "$ssh_user\@$machine";
3481 if ($reboot_type eq "grub") {
3482 dodie "GRUB_MENU not defined" if (!defined($grub_menu));
Steven Rostedtbb8474b2011-11-23 15:58:00 -05003483 }
Steven Rostedta75fece2010-11-02 14:58:27 -04003484 }
3485
3486 my $run_type = $build_type;
3487 if ($test_type eq "patchcheck") {
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05003488 $run_type = $patchcheck_type;
Steven Rostedta75fece2010-11-02 14:58:27 -04003489 } elsif ($test_type eq "bisect") {
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05003490 $run_type = $bisect_type;
Steven Rostedt0a05c762010-11-08 11:14:10 -05003491 } elsif ($test_type eq "config_bisect") {
Steven Rostedtb5f4aea2011-12-22 21:33:55 -05003492 $run_type = $config_bisect_type;
Steven Rostedta75fece2010-11-02 14:58:27 -04003493 }
3494
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003495 if ($test_type eq "make_min_config") {
3496 $run_type = "";
3497 }
3498
Steven Rostedta75fece2010-11-02 14:58:27 -04003499 # mistake in config file?
3500 if (!defined($run_type)) {
3501 $run_type = "ERROR";
3502 }
Steven Rostedt2545eb62010-11-02 15:01:32 -04003503
Steven Rostedte0a87422011-09-30 17:50:48 -04003504 my $installme = "";
3505 $installme = " no_install" if ($no_install);
3506
Steven Rostedt2545eb62010-11-02 15:01:32 -04003507 doprint "\n\n";
Steven Rostedte0a87422011-09-30 17:50:48 -04003508 doprint "RUNNING TEST $i of $opt{NUM_TESTS} with option $test_type $run_type$installme\n\n";
Steven Rostedt7faafbd2010-11-02 14:58:22 -04003509
3510 unlink $dmesg;
3511 unlink $buildlog;
Rabin Vincenta9dd5d62011-11-18 17:05:29 +05303512 unlink $testlog;
Steven Rostedt2545eb62010-11-02 15:01:32 -04003513
Steven Rostedt250bae82011-07-15 22:05:59 -04003514 if (defined($addconfig)) {
3515 my $min = $minconfig;
3516 if (!defined($minconfig)) {
3517 $min = "";
3518 }
3519 run_command "cat $addconfig $min > $tmpdir/add_config" or
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04003520 dodie "Failed to create temp config";
Steven Rostedt9be2e6b2010-11-09 12:20:21 -05003521 $minconfig = "$tmpdir/add_config";
Steven Rostedt2b7d9b22010-11-02 14:58:15 -04003522 }
3523
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04003524 if (defined($checkout)) {
3525 run_command "git checkout $checkout" or
3526 die "failed to checkout $checkout";
3527 }
3528
Steven Rostedt4ab1cce2011-09-30 18:12:20 -04003529 $no_reboot = 0;
3530
3531
Steven Rostedta75fece2010-11-02 14:58:27 -04003532 if ($test_type eq "bisect") {
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04003533 bisect $i;
3534 next;
Steven Rostedt0a05c762010-11-08 11:14:10 -05003535 } elsif ($test_type eq "config_bisect") {
3536 config_bisect $i;
3537 next;
Steven Rostedta75fece2010-11-02 14:58:27 -04003538 } elsif ($test_type eq "patchcheck") {
Steven Rostedt6c5ee0b2010-11-02 14:57:58 -04003539 patchcheck $i;
3540 next;
Steven Rostedt4c4ab122011-07-15 21:16:17 -04003541 } elsif ($test_type eq "make_min_config") {
3542 make_min_config $i;
3543 next;
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04003544 }
3545
Steven Rostedt7faafbd2010-11-02 14:58:22 -04003546 if ($build_type ne "nobuild") {
3547 build $build_type or next;
Steven Rostedt2545eb62010-11-02 15:01:32 -04003548 }
3549
Steven Rostedtcd8e3682011-08-18 16:35:44 -04003550 if ($test_type eq "install") {
3551 get_version;
3552 install;
3553 success $i;
3554 next;
3555 }
3556
Steven Rostedta75fece2010-11-02 14:58:27 -04003557 if ($test_type ne "build") {
Steven Rostedta75fece2010-11-02 14:58:27 -04003558 my $failed = 0;
Steven Rostedtddf607e2011-06-14 20:49:13 -04003559 start_monitor_and_boot or $failed = 1;
Steven Rostedta75fece2010-11-02 14:58:27 -04003560
3561 if (!$failed && $test_type ne "boot" && defined($run_test)) {
3562 do_run_test or $failed = 1;
3563 }
3564 end_monitor;
3565 next if ($failed);
Steven Rostedt5a391fb2010-11-02 14:57:43 -04003566 }
3567
Steven Rostedt5f9b6ce2010-11-02 14:57:33 -04003568 success $i;
Steven Rostedt2545eb62010-11-02 15:01:32 -04003569}
3570
Steven Rostedt5c42fc52010-11-02 14:57:01 -04003571if ($opt{"POWEROFF_ON_SUCCESS"}) {
Steven Rostedt75c3fda72010-11-02 14:57:21 -04003572 halt;
Steven Rostedt576f6272010-11-02 14:58:38 -04003573} elsif ($opt{"REBOOT_ON_SUCCESS"} && !do_not_reboot) {
Steven Rostedtbc7c5802011-12-22 16:29:10 -05003574 reboot_to_good;
Steven Rostedt5c42fc52010-11-02 14:57:01 -04003575}
Steven Rostedt75c3fda72010-11-02 14:57:21 -04003576
Steven Rostedte48c5292010-11-02 14:35:37 -04003577doprint "\n $successes of $opt{NUM_TESTS} tests were successful\n\n";
3578
Steven Rostedt2545eb62010-11-02 15:01:32 -04003579exit 0;