12545eb61SSteven Rostedt#!/usr/bin/perl -w 2d6ce2a0bSSteven Rostedt# 3cce1dac8SUwe Kleine-König# Copyright 2010 - Steven Rostedt <srostedt@redhat.com>, Red Hat Inc. 4d6ce2a0bSSteven Rostedt# Licensed under the terms of the GNU GPL License version 2 5d6ce2a0bSSteven Rostedt# 62545eb61SSteven Rostedt 72545eb61SSteven Rostedtuse strict; 82545eb61SSteven Rostedtuse IPC::Open2; 92545eb61SSteven Rostedtuse Fcntl qw(F_GETFL F_SETFL O_NONBLOCK); 107faafbd6SSteven Rostedtuse File::Path qw(mkpath); 117faafbd6SSteven Rostedtuse File::Copy qw(cp); 122545eb61SSteven Rostedtuse FileHandle; 132545eb61SSteven Rostedt 14e48c5293SSteven Rostedtmy $VERSION = "0.2"; 15e48c5293SSteven Rostedt 162545eb61SSteven Rostedt$| = 1; 172545eb61SSteven Rostedt 182545eb61SSteven Rostedtmy %opt; 19a57419b3SSteven Rostedtmy %repeat_tests; 20a57419b3SSteven Rostedtmy %repeats; 212545eb61SSteven Rostedt 222545eb61SSteven Rostedt#default opts 234f43e0dcSSteven Rostedtmy %default = ( 244f43e0dcSSteven Rostedt "NUM_TESTS" => 1, 254f43e0dcSSteven Rostedt "TEST_TYPE" => "build", 264f43e0dcSSteven Rostedt "BUILD_TYPE" => "randconfig", 274f43e0dcSSteven Rostedt "MAKE_CMD" => "make", 284f43e0dcSSteven Rostedt "TIMEOUT" => 120, 294f43e0dcSSteven Rostedt "TMP_DIR" => "/tmp/ktest/\${MACHINE}", 304f43e0dcSSteven Rostedt "SLEEP_TIME" => 60, # sleep time between tests 314f43e0dcSSteven Rostedt "BUILD_NOCLEAN" => 0, 324f43e0dcSSteven Rostedt "REBOOT_ON_ERROR" => 0, 334f43e0dcSSteven Rostedt "POWEROFF_ON_ERROR" => 0, 344f43e0dcSSteven Rostedt "REBOOT_ON_SUCCESS" => 1, 354f43e0dcSSteven Rostedt "POWEROFF_ON_SUCCESS" => 0, 364f43e0dcSSteven Rostedt "BUILD_OPTIONS" => "", 374f43e0dcSSteven Rostedt "BISECT_SLEEP_TIME" => 60, # sleep time between bisects 384f43e0dcSSteven Rostedt "PATCHCHECK_SLEEP_TIME" => 60, # sleep time between patch checks 394f43e0dcSSteven Rostedt "CLEAR_LOG" => 0, 404f43e0dcSSteven Rostedt "BISECT_MANUAL" => 0, 414f43e0dcSSteven Rostedt "BISECT_SKIP" => 1, 42ccc513b6SSteven Rostedt "MIN_CONFIG_TYPE" => "boot", 434f43e0dcSSteven Rostedt "SUCCESS_LINE" => "login:", 444f43e0dcSSteven Rostedt "DETECT_TRIPLE_FAULT" => 1, 454f43e0dcSSteven Rostedt "NO_INSTALL" => 0, 464f43e0dcSSteven Rostedt "BOOTED_TIMEOUT" => 1, 474f43e0dcSSteven Rostedt "DIE_ON_FAILURE" => 1, 484f43e0dcSSteven Rostedt "SSH_EXEC" => "ssh \$SSH_USER\@\$MACHINE \$SSH_COMMAND", 494f43e0dcSSteven Rostedt "SCP_TO_TARGET" => "scp \$SRC_FILE \$SSH_USER\@\$MACHINE:\$DST_FILE", 5002ad2617SSteven Rostedt "SCP_TO_TARGET_INSTALL" => "\${SCP_TO_TARGET}", 514f43e0dcSSteven Rostedt "REBOOT" => "ssh \$SSH_USER\@\$MACHINE reboot", 524f43e0dcSSteven Rostedt "STOP_AFTER_SUCCESS" => 10, 534f43e0dcSSteven Rostedt "STOP_AFTER_FAILURE" => 60, 544f43e0dcSSteven Rostedt "STOP_TEST_AFTER" => 600, 55407b95b7SSteven Rostedt "MAX_MONITOR_WAIT" => 1800, 56a15ba913SSteven Rostedt "GRUB_REBOOT" => "grub2-reboot", 577786954cSSteven Rostedt "SYSLINUX" => "extlinux", 587786954cSSteven Rostedt "SYSLINUX_PATH" => "/boot/extlinux", 59600bbf0aSSteven Rostedt 60600bbf0aSSteven Rostedt# required, and we will ask users if they don't have them but we keep the default 61600bbf0aSSteven Rostedt# value something that is common. 624f43e0dcSSteven Rostedt "REBOOT_TYPE" => "grub", 634f43e0dcSSteven Rostedt "LOCALVERSION" => "-test", 644f43e0dcSSteven Rostedt "SSH_USER" => "root", 654f43e0dcSSteven Rostedt "BUILD_TARGET" => "arch/x86/boot/bzImage", 664f43e0dcSSteven Rostedt "TARGET_IMAGE" => "/boot/vmlinuz-test", 679cc9e091SSteven Rostedt 689cc9e091SSteven Rostedt "LOG_FILE" => undef, 699cc9e091SSteven Rostedt "IGNORE_UNUSED" => 0, 704f43e0dcSSteven Rostedt); 712545eb61SSteven Rostedt 728d1491baSSteven Rostedtmy $ktest_config; 732545eb61SSteven Rostedtmy $version; 74683a3e64SSteven Rostedtmy $have_version = 0; 75a75fececSSteven Rostedtmy $machine; 76e48c5293SSteven Rostedtmy $ssh_user; 77a75fececSSteven Rostedtmy $tmpdir; 78a75fececSSteven Rostedtmy $builddir; 79a75fececSSteven Rostedtmy $outputdir; 8051ad1dd1SSteven Rostedtmy $output_config; 81a75fececSSteven Rostedtmy $test_type; 827faafbd6SSteven Rostedtmy $build_type; 83a75fececSSteven Rostedtmy $build_options; 84921ed4c7SSteven Rostedtmy $final_post_ktest; 85921ed4c7SSteven Rostedtmy $pre_ktest; 86921ed4c7SSteven Rostedtmy $post_ktest; 87921ed4c7SSteven Rostedtmy $pre_test; 88921ed4c7SSteven Rostedtmy $post_test; 890bd6c1a3SSteven Rostedtmy $pre_build; 900bd6c1a3SSteven Rostedtmy $post_build; 910bd6c1a3SSteven Rostedtmy $pre_build_die; 920bd6c1a3SSteven Rostedtmy $post_build_die; 93a75fececSSteven Rostedtmy $reboot_type; 94a75fececSSteven Rostedtmy $reboot_script; 95a75fececSSteven Rostedtmy $power_cycle; 96e48c5293SSteven Rostedtmy $reboot; 97a75fececSSteven Rostedtmy $reboot_on_error; 98bc7c5803SSteven Rostedtmy $switch_to_good; 99bc7c5803SSteven Rostedtmy $switch_to_test; 100a75fececSSteven Rostedtmy $poweroff_on_error; 101648a182cSSteven Rostedtmy $reboot_on_success; 102a75fececSSteven Rostedtmy $die_on_failure; 103576f627cSSteven Rostedtmy $powercycle_after_reboot; 104576f627cSSteven Rostedtmy $poweroff_after_halt; 105407b95b7SSteven Rostedtmy $max_monitor_wait; 106e48c5293SSteven Rostedtmy $ssh_exec; 107e48c5293SSteven Rostedtmy $scp_to_target; 10802ad2617SSteven Rostedtmy $scp_to_target_install; 109a75fececSSteven Rostedtmy $power_off; 110a75fececSSteven Rostedtmy $grub_menu; 111a15ba913SSteven Rostedtmy $grub_file; 1122545eb61SSteven Rostedtmy $grub_number; 113a15ba913SSteven Rostedtmy $grub_reboot; 1147786954cSSteven Rostedtmy $syslinux; 1157786954cSSteven Rostedtmy $syslinux_path; 1167786954cSSteven Rostedtmy $syslinux_label; 1172545eb61SSteven Rostedtmy $target; 1182545eb61SSteven Rostedtmy $make; 119e5c2ec11SSteven Rostedtmy $pre_install; 1208b37ca8cSSteven Rostedtmy $post_install; 121e0a8742eSSteven Rostedtmy $no_install; 1225c42fc5bSSteven Rostedtmy $noclean; 1235f9b6cedSSteven Rostedtmy $minconfig; 1244c4ab120SSteven Rostedtmy $start_minconfig; 12535ce5952SSteven Rostedtmy $start_minconfig_defined; 1264c4ab120SSteven Rostedtmy $output_minconfig; 127ccc513b6SSteven Rostedtmy $minconfig_type; 12843de3316SSteven Rostedtmy $use_output_minconfig; 1294283b169SSteven Rostedt (Red Hat)my $warnings_file; 1304c4ab120SSteven Rostedtmy $ignore_config; 131be405f95SSteven Rostedtmy $ignore_errors; 1322b7d9b21SSteven Rostedtmy $addconfig; 1335f9b6cedSSteven Rostedtmy $in_bisect = 0; 134b5f4aea6SSteven Rostedtmy $bisect_bad_commit = ""; 135d6ce2a0bSSteven Rostedtmy $reverse_bisect; 136c960bb9fSSteven Rostedtmy $bisect_manual; 137c23dca7cSSteven Rostedtmy $bisect_skip; 13830f75da5SSteven Rostedtmy $config_bisect_good; 139c5dacb88SSteven Rostedtmy $bisect_ret_good; 140c5dacb88SSteven Rostedtmy $bisect_ret_bad; 141c5dacb88SSteven Rostedtmy $bisect_ret_skip; 142c5dacb88SSteven Rostedtmy $bisect_ret_abort; 143c5dacb88SSteven Rostedtmy $bisect_ret_default; 1446c5ee0beSSteven Rostedtmy $in_patchcheck = 0; 1455a391fbfSSteven Rostedtmy $run_test; 1466c5ee0beSSteven Rostedtmy $redirect; 1477faafbd6SSteven Rostedtmy $buildlog; 148a9dd5d63SRabin Vincentmy $testlog; 1497faafbd6SSteven Rostedtmy $dmesg; 1507faafbd6SSteven Rostedtmy $monitor_fp; 1517faafbd6SSteven Rostedtmy $monitor_pid; 1527faafbd6SSteven Rostedtmy $monitor_cnt = 0; 153a75fececSSteven Rostedtmy $sleep_time; 154a75fececSSteven Rostedtmy $bisect_sleep_time; 15527d934b2SSteven Rostedtmy $patchcheck_sleep_time; 1561990207dSSteven Rostedtmy $ignore_warnings; 157a75fececSSteven Rostedtmy $store_failures; 158de5b6e3bSRabin Vincentmy $store_successes; 1599064af52SSteven Rostedtmy $test_name; 160a75fececSSteven Rostedtmy $timeout; 161a75fececSSteven Rostedtmy $booted_timeout; 162f1a5b962SSteven Rostedtmy $detect_triplefault; 163a75fececSSteven Rostedtmy $console; 1642b803365SSteven Rostedtmy $reboot_success_line; 165a75fececSSteven Rostedtmy $success_line; 1661c8a617aSSteven Rostedtmy $stop_after_success; 1671c8a617aSSteven Rostedtmy $stop_after_failure; 1682d01b26aSSteven Rostedtmy $stop_test_after; 169a75fececSSteven Rostedtmy $build_target; 170a75fececSSteven Rostedtmy $target_image; 171b5f4aea6SSteven Rostedtmy $checkout; 172a75fececSSteven Rostedtmy $localversion; 173576f627cSSteven Rostedtmy $iteration = 0; 174e48c5293SSteven Rostedtmy $successes = 0; 1752545eb61SSteven Rostedt 176b5f4aea6SSteven Rostedtmy $bisect_good; 177b5f4aea6SSteven Rostedtmy $bisect_bad; 178b5f4aea6SSteven Rostedtmy $bisect_type; 179b5f4aea6SSteven Rostedtmy $bisect_start; 180b5f4aea6SSteven Rostedtmy $bisect_replay; 181b5f4aea6SSteven Rostedtmy $bisect_files; 182b5f4aea6SSteven Rostedtmy $bisect_reverse; 183b5f4aea6SSteven Rostedtmy $bisect_check; 184b5f4aea6SSteven Rostedt 185b5f4aea6SSteven Rostedtmy $config_bisect; 186b5f4aea6SSteven Rostedtmy $config_bisect_type; 187b0918612SSteven Rostedtmy $config_bisect_check; 188b5f4aea6SSteven Rostedt 189b5f4aea6SSteven Rostedtmy $patchcheck_type; 190b5f4aea6SSteven Rostedtmy $patchcheck_start; 191b5f4aea6SSteven Rostedtmy $patchcheck_end; 192b5f4aea6SSteven Rostedt 193165708b2SSteven Rostedt# set when a test is something other that just building or install 194bb8474b1SSteven Rostedt# which would require more options. 195bb8474b1SSteven Rostedtmy $buildonly = 1; 196bb8474b1SSteven Rostedt 1974283b169SSteven Rostedt (Red Hat)# tell build not to worry about warnings, even when WARNINGS_FILE is set 1984283b169SSteven Rostedt (Red Hat)my $warnings_ok = 0; 1994283b169SSteven Rostedt (Red Hat) 200dbd3783bSSteven Rostedt# set when creating a new config 201dbd3783bSSteven Rostedtmy $newconfig = 0; 202dbd3783bSSteven Rostedt 2038d1491baSSteven Rostedtmy %entered_configs; 2048d1491baSSteven Rostedtmy %config_help; 20577d942ceSSteven Rostedtmy %variable; 206cf79fab6SSteven Rostedt 207cf79fab6SSteven Rostedt# force_config is the list of configs that we force enabled (or disabled) 208cf79fab6SSteven Rostedt# in a .config file. The MIN_CONFIG and ADD_CONFIG configs. 209fcb3f16aSSteven Rostedtmy %force_config; 2108d1491baSSteven Rostedt 2114ab1cce5SSteven Rostedt# do not force reboots on config problems 2124ab1cce5SSteven Rostedtmy $no_reboot = 1; 2134ab1cce5SSteven Rostedt 214759a3cc6SSteven Rostedt# reboot on success 215759a3cc6SSteven Rostedtmy $reboot_success = 0; 216759a3cc6SSteven Rostedt 2179cc9e091SSteven Rostedtmy %option_map = ( 2189cc9e091SSteven Rostedt "MACHINE" => \$machine, 2199cc9e091SSteven Rostedt "SSH_USER" => \$ssh_user, 2209cc9e091SSteven Rostedt "TMP_DIR" => \$tmpdir, 2219cc9e091SSteven Rostedt "OUTPUT_DIR" => \$outputdir, 2229cc9e091SSteven Rostedt "BUILD_DIR" => \$builddir, 2239cc9e091SSteven Rostedt "TEST_TYPE" => \$test_type, 224921ed4c7SSteven Rostedt "PRE_KTEST" => \$pre_ktest, 225921ed4c7SSteven Rostedt "POST_KTEST" => \$post_ktest, 226921ed4c7SSteven Rostedt "PRE_TEST" => \$pre_test, 227921ed4c7SSteven Rostedt "POST_TEST" => \$post_test, 2289cc9e091SSteven Rostedt "BUILD_TYPE" => \$build_type, 2299cc9e091SSteven Rostedt "BUILD_OPTIONS" => \$build_options, 2309cc9e091SSteven Rostedt "PRE_BUILD" => \$pre_build, 2319cc9e091SSteven Rostedt "POST_BUILD" => \$post_build, 2329cc9e091SSteven Rostedt "PRE_BUILD_DIE" => \$pre_build_die, 2339cc9e091SSteven Rostedt "POST_BUILD_DIE" => \$post_build_die, 2349cc9e091SSteven Rostedt "POWER_CYCLE" => \$power_cycle, 2359cc9e091SSteven Rostedt "REBOOT" => \$reboot, 2369cc9e091SSteven Rostedt "BUILD_NOCLEAN" => \$noclean, 2379cc9e091SSteven Rostedt "MIN_CONFIG" => \$minconfig, 2389cc9e091SSteven Rostedt "OUTPUT_MIN_CONFIG" => \$output_minconfig, 2399cc9e091SSteven Rostedt "START_MIN_CONFIG" => \$start_minconfig, 240ccc513b6SSteven Rostedt "MIN_CONFIG_TYPE" => \$minconfig_type, 24143de3316SSteven Rostedt "USE_OUTPUT_MIN_CONFIG" => \$use_output_minconfig, 2424283b169SSteven Rostedt (Red Hat) "WARNINGS_FILE" => \$warnings_file, 2439cc9e091SSteven Rostedt "IGNORE_CONFIG" => \$ignore_config, 2449cc9e091SSteven Rostedt "TEST" => \$run_test, 2459cc9e091SSteven Rostedt "ADD_CONFIG" => \$addconfig, 2469cc9e091SSteven Rostedt "REBOOT_TYPE" => \$reboot_type, 2479cc9e091SSteven Rostedt "GRUB_MENU" => \$grub_menu, 248a15ba913SSteven Rostedt "GRUB_FILE" => \$grub_file, 249a15ba913SSteven Rostedt "GRUB_REBOOT" => \$grub_reboot, 2507786954cSSteven Rostedt "SYSLINUX" => \$syslinux, 2517786954cSSteven Rostedt "SYSLINUX_PATH" => \$syslinux_path, 2527786954cSSteven Rostedt "SYSLINUX_LABEL" => \$syslinux_label, 253e5c2ec11SSteven Rostedt "PRE_INSTALL" => \$pre_install, 2549cc9e091SSteven Rostedt "POST_INSTALL" => \$post_install, 2559cc9e091SSteven Rostedt "NO_INSTALL" => \$no_install, 2569cc9e091SSteven Rostedt "REBOOT_SCRIPT" => \$reboot_script, 2579cc9e091SSteven Rostedt "REBOOT_ON_ERROR" => \$reboot_on_error, 2589cc9e091SSteven Rostedt "SWITCH_TO_GOOD" => \$switch_to_good, 2599cc9e091SSteven Rostedt "SWITCH_TO_TEST" => \$switch_to_test, 2609cc9e091SSteven Rostedt "POWEROFF_ON_ERROR" => \$poweroff_on_error, 261648a182cSSteven Rostedt "REBOOT_ON_SUCCESS" => \$reboot_on_success, 2629cc9e091SSteven Rostedt "DIE_ON_FAILURE" => \$die_on_failure, 2639cc9e091SSteven Rostedt "POWER_OFF" => \$power_off, 2649cc9e091SSteven Rostedt "POWERCYCLE_AFTER_REBOOT" => \$powercycle_after_reboot, 2659cc9e091SSteven Rostedt "POWEROFF_AFTER_HALT" => \$poweroff_after_halt, 266407b95b7SSteven Rostedt "MAX_MONITOR_WAIT" => \$max_monitor_wait, 2679cc9e091SSteven Rostedt "SLEEP_TIME" => \$sleep_time, 2689cc9e091SSteven Rostedt "BISECT_SLEEP_TIME" => \$bisect_sleep_time, 2699cc9e091SSteven Rostedt "PATCHCHECK_SLEEP_TIME" => \$patchcheck_sleep_time, 2709cc9e091SSteven Rostedt "IGNORE_WARNINGS" => \$ignore_warnings, 271be405f95SSteven Rostedt "IGNORE_ERRORS" => \$ignore_errors, 2729cc9e091SSteven Rostedt "BISECT_MANUAL" => \$bisect_manual, 2739cc9e091SSteven Rostedt "BISECT_SKIP" => \$bisect_skip, 2749cc9e091SSteven Rostedt "CONFIG_BISECT_GOOD" => \$config_bisect_good, 2759cc9e091SSteven Rostedt "BISECT_RET_GOOD" => \$bisect_ret_good, 2769cc9e091SSteven Rostedt "BISECT_RET_BAD" => \$bisect_ret_bad, 2779cc9e091SSteven Rostedt "BISECT_RET_SKIP" => \$bisect_ret_skip, 2789cc9e091SSteven Rostedt "BISECT_RET_ABORT" => \$bisect_ret_abort, 2799cc9e091SSteven Rostedt "BISECT_RET_DEFAULT" => \$bisect_ret_default, 2809cc9e091SSteven Rostedt "STORE_FAILURES" => \$store_failures, 2819cc9e091SSteven Rostedt "STORE_SUCCESSES" => \$store_successes, 2829cc9e091SSteven Rostedt "TEST_NAME" => \$test_name, 2839cc9e091SSteven Rostedt "TIMEOUT" => \$timeout, 2849cc9e091SSteven Rostedt "BOOTED_TIMEOUT" => \$booted_timeout, 2859cc9e091SSteven Rostedt "CONSOLE" => \$console, 2869cc9e091SSteven Rostedt "DETECT_TRIPLE_FAULT" => \$detect_triplefault, 2879cc9e091SSteven Rostedt "SUCCESS_LINE" => \$success_line, 2889cc9e091SSteven Rostedt "REBOOT_SUCCESS_LINE" => \$reboot_success_line, 2899cc9e091SSteven Rostedt "STOP_AFTER_SUCCESS" => \$stop_after_success, 2909cc9e091SSteven Rostedt "STOP_AFTER_FAILURE" => \$stop_after_failure, 2919cc9e091SSteven Rostedt "STOP_TEST_AFTER" => \$stop_test_after, 2929cc9e091SSteven Rostedt "BUILD_TARGET" => \$build_target, 2939cc9e091SSteven Rostedt "SSH_EXEC" => \$ssh_exec, 2949cc9e091SSteven Rostedt "SCP_TO_TARGET" => \$scp_to_target, 29502ad2617SSteven Rostedt "SCP_TO_TARGET_INSTALL" => \$scp_to_target_install, 2969cc9e091SSteven Rostedt "CHECKOUT" => \$checkout, 2979cc9e091SSteven Rostedt "TARGET_IMAGE" => \$target_image, 2989cc9e091SSteven Rostedt "LOCALVERSION" => \$localversion, 2999cc9e091SSteven Rostedt 3009cc9e091SSteven Rostedt "BISECT_GOOD" => \$bisect_good, 3019cc9e091SSteven Rostedt "BISECT_BAD" => \$bisect_bad, 3029cc9e091SSteven Rostedt "BISECT_TYPE" => \$bisect_type, 3039cc9e091SSteven Rostedt "BISECT_START" => \$bisect_start, 3049cc9e091SSteven Rostedt "BISECT_REPLAY" => \$bisect_replay, 3059cc9e091SSteven Rostedt "BISECT_FILES" => \$bisect_files, 3069cc9e091SSteven Rostedt "BISECT_REVERSE" => \$bisect_reverse, 3079cc9e091SSteven Rostedt "BISECT_CHECK" => \$bisect_check, 3089cc9e091SSteven Rostedt 3099cc9e091SSteven Rostedt "CONFIG_BISECT" => \$config_bisect, 3109cc9e091SSteven Rostedt "CONFIG_BISECT_TYPE" => \$config_bisect_type, 311b0918612SSteven Rostedt "CONFIG_BISECT_CHECK" => \$config_bisect_check, 3129cc9e091SSteven Rostedt 3139cc9e091SSteven Rostedt "PATCHCHECK_TYPE" => \$patchcheck_type, 3149cc9e091SSteven Rostedt "PATCHCHECK_START" => \$patchcheck_start, 3159cc9e091SSteven Rostedt "PATCHCHECK_END" => \$patchcheck_end, 3169cc9e091SSteven Rostedt); 3179cc9e091SSteven Rostedt 3189cc9e091SSteven Rostedt# Options may be used by other options, record them. 3199cc9e091SSteven Rostedtmy %used_options; 3209cc9e091SSteven Rostedt 3217bf51073SSteven Rostedt# default variables that can be used 3227bf51073SSteven Rostedtchomp ($variable{"PWD"} = `pwd`); 3237bf51073SSteven Rostedt 3248d1491baSSteven Rostedt$config_help{"MACHINE"} = << "EOF" 3258d1491baSSteven Rostedt The machine hostname that you will test. 326bb8474b1SSteven Rostedt For build only tests, it is still needed to differentiate log files. 3278d1491baSSteven RostedtEOF 3288d1491baSSteven Rostedt ; 3298d1491baSSteven Rostedt$config_help{"SSH_USER"} = << "EOF" 3308d1491baSSteven Rostedt The box is expected to have ssh on normal bootup, provide the user 3318d1491baSSteven Rostedt (most likely root, since you need privileged operations) 3328d1491baSSteven RostedtEOF 3338d1491baSSteven Rostedt ; 3348d1491baSSteven Rostedt$config_help{"BUILD_DIR"} = << "EOF" 3358d1491baSSteven Rostedt The directory that contains the Linux source code (full path). 3360e7a22deSSteven Rostedt You can use \${PWD} that will be the path where ktest.pl is run, or use 3370e7a22deSSteven Rostedt \${THIS_DIR} which is assigned \${PWD} but may be changed later. 3388d1491baSSteven RostedtEOF 3398d1491baSSteven Rostedt ; 3408d1491baSSteven Rostedt$config_help{"OUTPUT_DIR"} = << "EOF" 3418d1491baSSteven Rostedt The directory that the objects will be built (full path). 3428d1491baSSteven Rostedt (can not be same as BUILD_DIR) 3430e7a22deSSteven Rostedt You can use \${PWD} that will be the path where ktest.pl is run, or use 3440e7a22deSSteven Rostedt \${THIS_DIR} which is assigned \${PWD} but may be changed later. 3458d1491baSSteven RostedtEOF 3468d1491baSSteven Rostedt ; 3478d1491baSSteven Rostedt$config_help{"BUILD_TARGET"} = << "EOF" 3488d1491baSSteven Rostedt The location of the compiled file to copy to the target. 3498d1491baSSteven Rostedt (relative to OUTPUT_DIR) 3508d1491baSSteven RostedtEOF 3518d1491baSSteven Rostedt ; 352dbd3783bSSteven Rostedt$config_help{"BUILD_OPTIONS"} = << "EOF" 353dbd3783bSSteven Rostedt Options to add to \"make\" when building. 354dbd3783bSSteven Rostedt i.e. -j20 355dbd3783bSSteven RostedtEOF 356dbd3783bSSteven Rostedt ; 3578d1491baSSteven Rostedt$config_help{"TARGET_IMAGE"} = << "EOF" 3588d1491baSSteven Rostedt The place to put your image on the test machine. 3598d1491baSSteven RostedtEOF 3608d1491baSSteven Rostedt ; 3618d1491baSSteven Rostedt$config_help{"POWER_CYCLE"} = << "EOF" 3628d1491baSSteven Rostedt A script or command to reboot the box. 3638d1491baSSteven Rostedt 3648d1491baSSteven Rostedt Here is a digital loggers power switch example 3658d1491baSSteven Rostedt POWER_CYCLE = wget --no-proxy -O /dev/null -q --auth-no-challenge 'http://admin:admin\@power/outlet?5=CCL' 3668d1491baSSteven Rostedt 3678d1491baSSteven Rostedt Here is an example to reboot a virtual box on the current host 3688d1491baSSteven Rostedt with the name "Guest". 3698d1491baSSteven Rostedt POWER_CYCLE = virsh destroy Guest; sleep 5; virsh start Guest 3708d1491baSSteven RostedtEOF 3718d1491baSSteven Rostedt ; 3728d1491baSSteven Rostedt$config_help{"CONSOLE"} = << "EOF" 3738d1491baSSteven Rostedt The script or command that reads the console 3748d1491baSSteven Rostedt 3758d1491baSSteven Rostedt If you use ttywatch server, something like the following would work. 3768d1491baSSteven RostedtCONSOLE = nc -d localhost 3001 3778d1491baSSteven Rostedt 3788d1491baSSteven Rostedt For a virtual machine with guest name "Guest". 3798d1491baSSteven RostedtCONSOLE = virsh console Guest 3808d1491baSSteven RostedtEOF 3818d1491baSSteven Rostedt ; 3828d1491baSSteven Rostedt$config_help{"LOCALVERSION"} = << "EOF" 3838d1491baSSteven Rostedt Required version ending to differentiate the test 3848d1491baSSteven Rostedt from other linux builds on the system. 3858d1491baSSteven RostedtEOF 3868d1491baSSteven Rostedt ; 3878d1491baSSteven Rostedt$config_help{"REBOOT_TYPE"} = << "EOF" 3888d1491baSSteven Rostedt Way to reboot the box to the test kernel. 3897786954cSSteven Rostedt Only valid options so far are "grub", "grub2", "syslinux", and "script". 3908d1491baSSteven Rostedt 3918d1491baSSteven Rostedt If you specify grub, it will assume grub version 1 3928d1491baSSteven Rostedt and will search in /boot/grub/menu.lst for the title \$GRUB_MENU 3938d1491baSSteven Rostedt and select that target to reboot to the kernel. If this is not 3948d1491baSSteven Rostedt your setup, then specify "script" and have a command or script 3958d1491baSSteven Rostedt specified in REBOOT_SCRIPT to boot to the target. 3968d1491baSSteven Rostedt 3978d1491baSSteven Rostedt The entry in /boot/grub/menu.lst must be entered in manually. 3988d1491baSSteven Rostedt The test will not modify that file. 399a15ba913SSteven Rostedt 400a15ba913SSteven Rostedt If you specify grub2, then you also need to specify both \$GRUB_MENU 401a15ba913SSteven Rostedt and \$GRUB_FILE. 4027786954cSSteven Rostedt 4037786954cSSteven Rostedt If you specify syslinux, then you may use SYSLINUX to define the syslinux 4047786954cSSteven Rostedt command (defaults to extlinux), and SYSLINUX_PATH to specify the path to 4057786954cSSteven Rostedt the syslinux install (defaults to /boot/extlinux). But you have to specify 4067786954cSSteven Rostedt SYSLINUX_LABEL to define the label to boot to for the test kernel. 4078d1491baSSteven RostedtEOF 4088d1491baSSteven Rostedt ; 4098d1491baSSteven Rostedt$config_help{"GRUB_MENU"} = << "EOF" 4108d1491baSSteven Rostedt The grub title name for the test kernel to boot 411a15ba913SSteven Rostedt (Only mandatory if REBOOT_TYPE = grub or grub2) 4128d1491baSSteven Rostedt 4138d1491baSSteven Rostedt Note, ktest.pl will not update the grub menu.lst, you need to 4148d1491baSSteven Rostedt manually add an option for the test. ktest.pl will search 4158d1491baSSteven Rostedt the grub menu.lst for this option to find what kernel to 4168d1491baSSteven Rostedt reboot into. 4178d1491baSSteven Rostedt 4188d1491baSSteven Rostedt For example, if in the /boot/grub/menu.lst the test kernel title has: 4198d1491baSSteven Rostedt title Test Kernel 4208d1491baSSteven Rostedt kernel vmlinuz-test 4218d1491baSSteven Rostedt GRUB_MENU = Test Kernel 422a15ba913SSteven Rostedt 423a15ba913SSteven Rostedt For grub2, a search of \$GRUB_FILE is performed for the lines 424a15ba913SSteven Rostedt that begin with "menuentry". It will not detect submenus. The 425a15ba913SSteven Rostedt menu must be a non-nested menu. Add the quotes used in the menu 426a15ba913SSteven Rostedt to guarantee your selection, as the first menuentry with the content 427a15ba913SSteven Rostedt of \$GRUB_MENU that is found will be used. 428a15ba913SSteven RostedtEOF 429a15ba913SSteven Rostedt ; 430a15ba913SSteven Rostedt$config_help{"GRUB_FILE"} = << "EOF" 431a15ba913SSteven Rostedt If grub2 is used, the full path for the grub.cfg file is placed 432a15ba913SSteven Rostedt here. Use something like /boot/grub2/grub.cfg to search. 4338d1491baSSteven RostedtEOF 4348d1491baSSteven Rostedt ; 4357786954cSSteven Rostedt$config_help{"SYSLINUX_LABEL"} = << "EOF" 4367786954cSSteven Rostedt If syslinux is used, the label that boots the target kernel must 4377786954cSSteven Rostedt be specified with SYSLINUX_LABEL. 4387786954cSSteven RostedtEOF 4397786954cSSteven Rostedt ; 4408d1491baSSteven Rostedt$config_help{"REBOOT_SCRIPT"} = << "EOF" 4418d1491baSSteven Rostedt A script to reboot the target into the test kernel 4428d1491baSSteven Rostedt (Only mandatory if REBOOT_TYPE = script) 4438d1491baSSteven RostedtEOF 4448d1491baSSteven Rostedt ; 4458d1491baSSteven Rostedt 446dad98754SSteven Rostedtsub read_prompt { 447dad98754SSteven Rostedt my ($cancel, $prompt) = @_; 44835ce5952SSteven Rostedt 44935ce5952SSteven Rostedt my $ans; 45035ce5952SSteven Rostedt 45135ce5952SSteven Rostedt for (;;) { 452dad98754SSteven Rostedt if ($cancel) { 453dad98754SSteven Rostedt print "$prompt [y/n/C] "; 454dad98754SSteven Rostedt } else { 45535ce5952SSteven Rostedt print "$prompt [Y/n] "; 456dad98754SSteven Rostedt } 45735ce5952SSteven Rostedt $ans = <STDIN>; 45835ce5952SSteven Rostedt chomp $ans; 45935ce5952SSteven Rostedt if ($ans =~ /^\s*$/) { 460dad98754SSteven Rostedt if ($cancel) { 461dad98754SSteven Rostedt $ans = "c"; 462dad98754SSteven Rostedt } else { 46335ce5952SSteven Rostedt $ans = "y"; 46435ce5952SSteven Rostedt } 465dad98754SSteven Rostedt } 46635ce5952SSteven Rostedt last if ($ans =~ /^y$/i || $ans =~ /^n$/i); 467dad98754SSteven Rostedt if ($cancel) { 468dad98754SSteven Rostedt last if ($ans =~ /^c$/i); 469dad98754SSteven Rostedt print "Please answer either 'y', 'n' or 'c'.\n"; 470dad98754SSteven Rostedt } else { 47135ce5952SSteven Rostedt print "Please answer either 'y' or 'n'.\n"; 47235ce5952SSteven Rostedt } 473dad98754SSteven Rostedt } 474dad98754SSteven Rostedt if ($ans =~ /^c/i) { 475dad98754SSteven Rostedt exit; 476dad98754SSteven Rostedt } 47735ce5952SSteven Rostedt if ($ans !~ /^y$/i) { 47835ce5952SSteven Rostedt return 0; 47935ce5952SSteven Rostedt } 48035ce5952SSteven Rostedt return 1; 48135ce5952SSteven Rostedt} 4828d1491baSSteven Rostedt 483dad98754SSteven Rostedtsub read_yn { 484dad98754SSteven Rostedt my ($prompt) = @_; 485dad98754SSteven Rostedt 486dad98754SSteven Rostedt return read_prompt 0, $prompt; 487dad98754SSteven Rostedt} 488dad98754SSteven Rostedt 489dad98754SSteven Rostedtsub read_ync { 490dad98754SSteven Rostedt my ($prompt) = @_; 491dad98754SSteven Rostedt 492dad98754SSteven Rostedt return read_prompt 1, $prompt; 493dad98754SSteven Rostedt} 494dad98754SSteven Rostedt 4958d1491baSSteven Rostedtsub get_ktest_config { 4968d1491baSSteven Rostedt my ($config) = @_; 497815e2bd7SSteven Rostedt my $ans; 4988d1491baSSteven Rostedt 4998d1491baSSteven Rostedt return if (defined($opt{$config})); 5008d1491baSSteven Rostedt 5018d1491baSSteven Rostedt if (defined($config_help{$config})) { 5028d1491baSSteven Rostedt print "\n"; 5038d1491baSSteven Rostedt print $config_help{$config}; 5048d1491baSSteven Rostedt } 5058d1491baSSteven Rostedt 5068d1491baSSteven Rostedt for (;;) { 5078d1491baSSteven Rostedt print "$config = "; 508dbd3783bSSteven Rostedt if (defined($default{$config}) && length($default{$config})) { 5098d1491baSSteven Rostedt print "\[$default{$config}\] "; 5108d1491baSSteven Rostedt } 511815e2bd7SSteven Rostedt $ans = <STDIN>; 512815e2bd7SSteven Rostedt $ans =~ s/^\s*(.*\S)\s*$/$1/; 513815e2bd7SSteven Rostedt if ($ans =~ /^\s*$/) { 5148d1491baSSteven Rostedt if ($default{$config}) { 515815e2bd7SSteven Rostedt $ans = $default{$config}; 5168d1491baSSteven Rostedt } else { 5178d1491baSSteven Rostedt print "Your answer can not be blank\n"; 5188d1491baSSteven Rostedt next; 5198d1491baSSteven Rostedt } 5208d1491baSSteven Rostedt } 5210e7a22deSSteven Rostedt $entered_configs{$config} = ${ans}; 5228d1491baSSteven Rostedt last; 5238d1491baSSteven Rostedt } 5248d1491baSSteven Rostedt} 5258d1491baSSteven Rostedt 5268d1491baSSteven Rostedtsub get_ktest_configs { 5278d1491baSSteven Rostedt get_ktest_config("MACHINE"); 5288d1491baSSteven Rostedt get_ktest_config("BUILD_DIR"); 5298d1491baSSteven Rostedt get_ktest_config("OUTPUT_DIR"); 530bb8474b1SSteven Rostedt 531dbd3783bSSteven Rostedt if ($newconfig) { 532dbd3783bSSteven Rostedt get_ktest_config("BUILD_OPTIONS"); 533dbd3783bSSteven Rostedt } 534dbd3783bSSteven Rostedt 535bb8474b1SSteven Rostedt # options required for other than just building a kernel 536bb8474b1SSteven Rostedt if (!$buildonly) { 537165708b2SSteven Rostedt get_ktest_config("POWER_CYCLE"); 538165708b2SSteven Rostedt get_ktest_config("CONSOLE"); 539165708b2SSteven Rostedt } 540165708b2SSteven Rostedt 541165708b2SSteven Rostedt # options required for install and more 542165708b2SSteven Rostedt if ($buildonly != 1) { 543bb8474b1SSteven Rostedt get_ktest_config("SSH_USER"); 5448d1491baSSteven Rostedt get_ktest_config("BUILD_TARGET"); 5458d1491baSSteven Rostedt get_ktest_config("TARGET_IMAGE"); 546bb8474b1SSteven Rostedt } 547bb8474b1SSteven Rostedt 5488d1491baSSteven Rostedt get_ktest_config("LOCALVERSION"); 5498d1491baSSteven Rostedt 550bb8474b1SSteven Rostedt return if ($buildonly); 551bb8474b1SSteven Rostedt 5528d1491baSSteven Rostedt my $rtype = $opt{"REBOOT_TYPE"}; 5538d1491baSSteven Rostedt 5548d1491baSSteven Rostedt if (!defined($rtype)) { 5558d1491baSSteven Rostedt if (!defined($opt{"GRUB_MENU"})) { 5568d1491baSSteven Rostedt get_ktest_config("REBOOT_TYPE"); 5578d1491baSSteven Rostedt $rtype = $entered_configs{"REBOOT_TYPE"}; 5588d1491baSSteven Rostedt } else { 5598d1491baSSteven Rostedt $rtype = "grub"; 5608d1491baSSteven Rostedt } 5618d1491baSSteven Rostedt } 5628d1491baSSteven Rostedt 5638d1491baSSteven Rostedt if ($rtype eq "grub") { 5648d1491baSSteven Rostedt get_ktest_config("GRUB_MENU"); 5658d1491baSSteven Rostedt } 566a15ba913SSteven Rostedt 567a15ba913SSteven Rostedt if ($rtype eq "grub2") { 568a15ba913SSteven Rostedt get_ktest_config("GRUB_MENU"); 569a15ba913SSteven Rostedt get_ktest_config("GRUB_FILE"); 570a15ba913SSteven Rostedt } 5717786954cSSteven Rostedt 5727786954cSSteven Rostedt if ($rtype eq "syslinux") { 5737786954cSSteven Rostedt get_ktest_config("SYSLINUX_LABEL"); 5747786954cSSteven Rostedt } 5758d1491baSSteven Rostedt} 5768d1491baSSteven Rostedt 57777d942ceSSteven Rostedtsub process_variables { 5788d735212SSteven Rostedt my ($value, $remove_undef) = @_; 57977d942ceSSteven Rostedt my $retval = ""; 58077d942ceSSteven Rostedt 58177d942ceSSteven Rostedt # We want to check for '\', and it is just easier 58277d942ceSSteven Rostedt # to check the previous characet of '$' and not need 58377d942ceSSteven Rostedt # to worry if '$' is the first character. By adding 58477d942ceSSteven Rostedt # a space to $value, we can just check [^\\]\$ and 58577d942ceSSteven Rostedt # it will still work. 58677d942ceSSteven Rostedt $value = " $value"; 58777d942ceSSteven Rostedt 58877d942ceSSteven Rostedt while ($value =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) { 58977d942ceSSteven Rostedt my $begin = $1; 59077d942ceSSteven Rostedt my $var = $2; 59177d942ceSSteven Rostedt my $end = $3; 59277d942ceSSteven Rostedt # append beginning of value to retval 59377d942ceSSteven Rostedt $retval = "$retval$begin"; 59477d942ceSSteven Rostedt if (defined($variable{$var})) { 59577d942ceSSteven Rostedt $retval = "$retval$variable{$var}"; 5968d735212SSteven Rostedt } elsif (defined($remove_undef) && $remove_undef) { 5978d735212SSteven Rostedt # for if statements, any variable that is not defined, 5988d735212SSteven Rostedt # we simple convert to 0 5998d735212SSteven Rostedt $retval = "${retval}0"; 60077d942ceSSteven Rostedt } else { 60177d942ceSSteven Rostedt # put back the origin piece. 60277d942ceSSteven Rostedt $retval = "$retval\$\{$var\}"; 6039cc9e091SSteven Rostedt # This could be an option that is used later, save 6049cc9e091SSteven Rostedt # it so we don't warn if this option is not one of 6059cc9e091SSteven Rostedt # ktests options. 6069cc9e091SSteven Rostedt $used_options{$var} = 1; 60777d942ceSSteven Rostedt } 60877d942ceSSteven Rostedt $value = $end; 60977d942ceSSteven Rostedt } 61077d942ceSSteven Rostedt $retval = "$retval$value"; 61177d942ceSSteven Rostedt 61277d942ceSSteven Rostedt # remove the space added in the beginning 61377d942ceSSteven Rostedt $retval =~ s/ //; 61477d942ceSSteven Rostedt 61577d942ceSSteven Rostedt return "$retval" 61677d942ceSSteven Rostedt} 61777d942ceSSteven Rostedt 618a57419b3SSteven Rostedtsub set_value { 6193d1cc414SSteven Rostedt my ($lvalue, $rvalue, $override, $overrides, $name) = @_; 6202545eb61SSteven Rostedt 621cad96669SSteven Rostedt my $prvalue = process_variables($rvalue); 622cad96669SSteven Rostedt 623cad96669SSteven Rostedt if ($buildonly && $lvalue =~ /^TEST_TYPE(\[.*\])?$/ && $prvalue ne "build") { 624bb8474b1SSteven Rostedt # Note if a test is something other than build, then we 625bb8474b1SSteven Rostedt # will need other manditory options. 626cad96669SSteven Rostedt if ($prvalue ne "install") { 627319ab14fSSteven Rostedt (Red Hat) # for bisect, we need to check BISECT_TYPE 628319ab14fSSteven Rostedt (Red Hat) if ($prvalue ne "bisect") { 629319ab14fSSteven Rostedt (Red Hat) $buildonly = 0; 630319ab14fSSteven Rostedt (Red Hat) } 631319ab14fSSteven Rostedt (Red Hat) } else { 632319ab14fSSteven Rostedt (Red Hat) # install still limits some manditory options. 633319ab14fSSteven Rostedt (Red Hat) $buildonly = 2; 634319ab14fSSteven Rostedt (Red Hat) } 635319ab14fSSteven Rostedt (Red Hat) } 636319ab14fSSteven Rostedt (Red Hat) 637319ab14fSSteven Rostedt (Red Hat) if ($buildonly && $lvalue =~ /^BISECT_TYPE(\[.*\])?$/ && $prvalue ne "build") { 638319ab14fSSteven Rostedt (Red Hat) if ($prvalue ne "install") { 639bb8474b1SSteven Rostedt $buildonly = 0; 640165708b2SSteven Rostedt } else { 641165708b2SSteven Rostedt # install still limits some manditory options. 642165708b2SSteven Rostedt $buildonly = 2; 643165708b2SSteven Rostedt } 644bb8474b1SSteven Rostedt } 645bb8474b1SSteven Rostedt 646a75fececSSteven Rostedt if (defined($opt{$lvalue})) { 6473d1cc414SSteven Rostedt if (!$override || defined(${$overrides}{$lvalue})) { 6483d1cc414SSteven Rostedt my $extra = ""; 6493d1cc414SSteven Rostedt if ($override) { 6503d1cc414SSteven Rostedt $extra = "In the same override section!\n"; 6513d1cc414SSteven Rostedt } 6523d1cc414SSteven Rostedt die "$name: $.: Option $lvalue defined more than once!\n$extra"; 6533d1cc414SSteven Rostedt } 654cad96669SSteven Rostedt ${$overrides}{$lvalue} = $prvalue; 655a75fececSSteven Rostedt } 65621a9679fSSteven Rostedt if ($rvalue =~ /^\s*$/) { 65721a9679fSSteven Rostedt delete $opt{$lvalue}; 65821a9679fSSteven Rostedt } else { 659cad96669SSteven Rostedt $opt{$lvalue} = $prvalue; 66021a9679fSSteven Rostedt } 6612545eb61SSteven Rostedt} 662a57419b3SSteven Rostedt 66377d942ceSSteven Rostedtsub set_variable { 66477d942ceSSteven Rostedt my ($lvalue, $rvalue) = @_; 66577d942ceSSteven Rostedt 66677d942ceSSteven Rostedt if ($rvalue =~ /^\s*$/) { 66777d942ceSSteven Rostedt delete $variable{$lvalue}; 66877d942ceSSteven Rostedt } else { 66977d942ceSSteven Rostedt $rvalue = process_variables($rvalue); 67077d942ceSSteven Rostedt $variable{$lvalue} = $rvalue; 67177d942ceSSteven Rostedt } 67277d942ceSSteven Rostedt} 67377d942ceSSteven Rostedt 674ab7a3f52SSteven Rostedtsub process_compare { 675ab7a3f52SSteven Rostedt my ($lval, $cmp, $rval) = @_; 676ab7a3f52SSteven Rostedt 677ab7a3f52SSteven Rostedt # remove whitespace 678ab7a3f52SSteven Rostedt 679ab7a3f52SSteven Rostedt $lval =~ s/^\s*//; 680ab7a3f52SSteven Rostedt $lval =~ s/\s*$//; 681ab7a3f52SSteven Rostedt 682ab7a3f52SSteven Rostedt $rval =~ s/^\s*//; 683ab7a3f52SSteven Rostedt $rval =~ s/\s*$//; 684ab7a3f52SSteven Rostedt 685ab7a3f52SSteven Rostedt if ($cmp eq "==") { 686ab7a3f52SSteven Rostedt return $lval eq $rval; 687ab7a3f52SSteven Rostedt } elsif ($cmp eq "!=") { 688ab7a3f52SSteven Rostedt return $lval ne $rval; 6898fddbe9bSSteven Rostedt } elsif ($cmp eq "=~") { 6908fddbe9bSSteven Rostedt return $lval =~ m/$rval/; 6918fddbe9bSSteven Rostedt } elsif ($cmp eq "!~") { 6928fddbe9bSSteven Rostedt return $lval !~ m/$rval/; 693ab7a3f52SSteven Rostedt } 694ab7a3f52SSteven Rostedt 695ab7a3f52SSteven Rostedt my $statement = "$lval $cmp $rval"; 696ab7a3f52SSteven Rostedt my $ret = eval $statement; 697ab7a3f52SSteven Rostedt 698ab7a3f52SSteven Rostedt # $@ stores error of eval 699ab7a3f52SSteven Rostedt if ($@) { 700ab7a3f52SSteven Rostedt return -1; 701ab7a3f52SSteven Rostedt } 702ab7a3f52SSteven Rostedt 703ab7a3f52SSteven Rostedt return $ret; 704ab7a3f52SSteven Rostedt} 705ab7a3f52SSteven Rostedt 7069900b5dcSSteven Rostedtsub value_defined { 7079900b5dcSSteven Rostedt my ($val) = @_; 7089900b5dcSSteven Rostedt 7099900b5dcSSteven Rostedt return defined($variable{$2}) || 7109900b5dcSSteven Rostedt defined($opt{$2}); 7119900b5dcSSteven Rostedt} 7129900b5dcSSteven Rostedt 7138d735212SSteven Rostedtmy $d = 0; 7148d735212SSteven Rostedtsub process_expression { 7158d735212SSteven Rostedt my ($name, $val) = @_; 71645d73a5dSSteven Rostedt 7178d735212SSteven Rostedt my $c = $d++; 7188d735212SSteven Rostedt 7198d735212SSteven Rostedt while ($val =~ s/\(([^\(]*?)\)/\&\&\&\&VAL\&\&\&\&/) { 7208d735212SSteven Rostedt my $express = $1; 7218d735212SSteven Rostedt 7228d735212SSteven Rostedt if (process_expression($name, $express)) { 7238d735212SSteven Rostedt $val =~ s/\&\&\&\&VAL\&\&\&\&/ 1 /; 7248d735212SSteven Rostedt } else { 7258d735212SSteven Rostedt $val =~ s/\&\&\&\&VAL\&\&\&\&/ 0 /; 7268d735212SSteven Rostedt } 7278d735212SSteven Rostedt } 7288d735212SSteven Rostedt 7298d735212SSteven Rostedt $d--; 7308d735212SSteven Rostedt my $OR = "\\|\\|"; 7318d735212SSteven Rostedt my $AND = "\\&\\&"; 7328d735212SSteven Rostedt 7338d735212SSteven Rostedt while ($val =~ s/^(.*?)($OR|$AND)//) { 7348d735212SSteven Rostedt my $express = $1; 7358d735212SSteven Rostedt my $op = $2; 7368d735212SSteven Rostedt 7378d735212SSteven Rostedt if (process_expression($name, $express)) { 7388d735212SSteven Rostedt if ($op eq "||") { 7398d735212SSteven Rostedt return 1; 7408d735212SSteven Rostedt } 7418d735212SSteven Rostedt } else { 7428d735212SSteven Rostedt if ($op eq "&&") { 7438d735212SSteven Rostedt return 0; 7448d735212SSteven Rostedt } 7458d735212SSteven Rostedt } 7468d735212SSteven Rostedt } 74745d73a5dSSteven Rostedt 7488fddbe9bSSteven Rostedt if ($val =~ /(.*)(==|\!=|>=|<=|>|<|=~|\!~)(.*)/) { 749ab7a3f52SSteven Rostedt my $ret = process_compare($1, $2, $3); 750ab7a3f52SSteven Rostedt if ($ret < 0) { 751ab7a3f52SSteven Rostedt die "$name: $.: Unable to process comparison\n"; 752ab7a3f52SSteven Rostedt } 753ab7a3f52SSteven Rostedt return $ret; 754ab7a3f52SSteven Rostedt } 755ab7a3f52SSteven Rostedt 7569900b5dcSSteven Rostedt if ($val =~ /^\s*(NOT\s*)?DEFINED\s+(\S+)\s*$/) { 7579900b5dcSSteven Rostedt if (defined $1) { 7589900b5dcSSteven Rostedt return !value_defined($2); 7599900b5dcSSteven Rostedt } else { 7609900b5dcSSteven Rostedt return value_defined($2); 7619900b5dcSSteven Rostedt } 7629900b5dcSSteven Rostedt } 7639900b5dcSSteven Rostedt 76445d73a5dSSteven Rostedt if ($val =~ /^\s*0\s*$/) { 76545d73a5dSSteven Rostedt return 0; 76645d73a5dSSteven Rostedt } elsif ($val =~ /^\s*\d+\s*$/) { 76745d73a5dSSteven Rostedt return 1; 76845d73a5dSSteven Rostedt } 76945d73a5dSSteven Rostedt 7709900b5dcSSteven Rostedt die ("$name: $.: Undefined content $val in if statement\n"); 7718d735212SSteven Rostedt} 7728d735212SSteven Rostedt 7738d735212SSteven Rostedtsub process_if { 7748d735212SSteven Rostedt my ($name, $value) = @_; 7758d735212SSteven Rostedt 7768d735212SSteven Rostedt # Convert variables and replace undefined ones with 0 7778d735212SSteven Rostedt my $val = process_variables($value, 1); 7788d735212SSteven Rostedt my $ret = process_expression $name, $val; 7798d735212SSteven Rostedt 7808d735212SSteven Rostedt return $ret; 78145d73a5dSSteven Rostedt} 78245d73a5dSSteven Rostedt 7832ed3b161SSteven Rostedtsub __read_config { 7842ed3b161SSteven Rostedt my ($config, $current_test_num) = @_; 785a57419b3SSteven Rostedt 7862ed3b161SSteven Rostedt my $in; 7872ed3b161SSteven Rostedt open($in, $config) || die "can't read file $config"; 788a57419b3SSteven Rostedt 789a57419b3SSteven Rostedt my $name = $config; 790a57419b3SSteven Rostedt $name =~ s,.*/(.*),$1,; 791a57419b3SSteven Rostedt 7922ed3b161SSteven Rostedt my $test_num = $$current_test_num; 793a57419b3SSteven Rostedt my $default = 1; 794a57419b3SSteven Rostedt my $repeat = 1; 795a57419b3SSteven Rostedt my $num_tests_set = 0; 796a57419b3SSteven Rostedt my $skip = 0; 797a57419b3SSteven Rostedt my $rest; 798a9f84424SSteven Rostedt my $line; 7990df213caSSteven Rostedt my $test_case = 0; 80045d73a5dSSteven Rostedt my $if = 0; 80145d73a5dSSteven Rostedt my $if_set = 0; 8023d1cc414SSteven Rostedt my $override = 0; 8033d1cc414SSteven Rostedt 8043d1cc414SSteven Rostedt my %overrides; 805a57419b3SSteven Rostedt 8062ed3b161SSteven Rostedt while (<$in>) { 807a57419b3SSteven Rostedt 808a57419b3SSteven Rostedt # ignore blank lines and comments 809a57419b3SSteven Rostedt next if (/^\s*$/ || /\s*\#/); 810a57419b3SSteven Rostedt 8110050b6bbSSteven Rostedt if (/^\s*(TEST_START|DEFAULTS)\b(.*)/) { 812a57419b3SSteven Rostedt 8130050b6bbSSteven Rostedt my $type = $1; 8140050b6bbSSteven Rostedt $rest = $2; 815a9f84424SSteven Rostedt $line = $2; 8160050b6bbSSteven Rostedt 8170050b6bbSSteven Rostedt my $old_test_num; 8180050b6bbSSteven Rostedt my $old_repeat; 8193d1cc414SSteven Rostedt $override = 0; 8200050b6bbSSteven Rostedt 8210050b6bbSSteven Rostedt if ($type eq "TEST_START") { 822a57419b3SSteven Rostedt 823a57419b3SSteven Rostedt if ($num_tests_set) { 824a57419b3SSteven Rostedt die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n"; 825a57419b3SSteven Rostedt } 826a57419b3SSteven Rostedt 8270050b6bbSSteven Rostedt $old_test_num = $test_num; 8280050b6bbSSteven Rostedt $old_repeat = $repeat; 829a57419b3SSteven Rostedt 830a57419b3SSteven Rostedt $test_num += $repeat; 831a57419b3SSteven Rostedt $default = 0; 832a57419b3SSteven Rostedt $repeat = 1; 8330050b6bbSSteven Rostedt } else { 8340050b6bbSSteven Rostedt $default = 1; 8350050b6bbSSteven Rostedt } 836a57419b3SSteven Rostedt 837a9f84424SSteven Rostedt # If SKIP is anywhere in the line, the command will be skipped 838a9f84424SSteven Rostedt if ($rest =~ s/\s+SKIP\b//) { 839a57419b3SSteven Rostedt $skip = 1; 840a57419b3SSteven Rostedt } else { 8410df213caSSteven Rostedt $test_case = 1; 842a57419b3SSteven Rostedt $skip = 0; 843a57419b3SSteven Rostedt } 844a57419b3SSteven Rostedt 845a9f84424SSteven Rostedt if ($rest =~ s/\sELSE\b//) { 846a9f84424SSteven Rostedt if (!$if) { 847a9f84424SSteven Rostedt die "$name: $.: ELSE found with out matching IF section\n$_"; 848a57419b3SSteven Rostedt } 849a9f84424SSteven Rostedt $if = 0; 850a9f84424SSteven Rostedt 851a9f84424SSteven Rostedt if ($if_set) { 852a9f84424SSteven Rostedt $skip = 1; 853a9f84424SSteven Rostedt } else { 854a9f84424SSteven Rostedt $skip = 0; 8553d1cc414SSteven Rostedt } 8563d1cc414SSteven Rostedt } 857a57419b3SSteven Rostedt 858a9f84424SSteven Rostedt if ($rest =~ s/\sIF\s+(.*)//) { 85945d73a5dSSteven Rostedt if (process_if($name, $1)) { 86045d73a5dSSteven Rostedt $if_set = 1; 86145d73a5dSSteven Rostedt } else { 862a57419b3SSteven Rostedt $skip = 1; 863a57419b3SSteven Rostedt } 86445d73a5dSSteven Rostedt $if = 1; 86545d73a5dSSteven Rostedt } else { 86645d73a5dSSteven Rostedt $if = 0; 867a9f84424SSteven Rostedt $if_set = 0; 86845d73a5dSSteven Rostedt } 869a57419b3SSteven Rostedt 870a9f84424SSteven Rostedt if (!$skip) { 871a9f84424SSteven Rostedt if ($type eq "TEST_START") { 872a9f84424SSteven Rostedt if ($rest =~ s/\s+ITERATE\s+(\d+)//) { 873a9f84424SSteven Rostedt $repeat = $1; 874a9f84424SSteven Rostedt $repeat_tests{"$test_num"} = $repeat; 875a9f84424SSteven Rostedt } 876a9f84424SSteven Rostedt } elsif ($rest =~ s/\sOVERRIDE\b//) { 877a9f84424SSteven Rostedt # DEFAULT only 878a9f84424SSteven Rostedt $override = 1; 879a9f84424SSteven Rostedt # Clear previous overrides 880a9f84424SSteven Rostedt %overrides = (); 881a9f84424SSteven Rostedt } 882a9f84424SSteven Rostedt } 883a9f84424SSteven Rostedt 884a9f84424SSteven Rostedt if (!$skip && $rest !~ /^\s*$/) { 8850050b6bbSSteven Rostedt die "$name: $.: Gargbage found after $type\n$_"; 886a57419b3SSteven Rostedt } 887a57419b3SSteven Rostedt 8880050b6bbSSteven Rostedt if ($skip && $type eq "TEST_START") { 889a57419b3SSteven Rostedt $test_num = $old_test_num; 890e48c5293SSteven Rostedt $repeat = $old_repeat; 891a57419b3SSteven Rostedt } 892a57419b3SSteven Rostedt 893ab7a3f52SSteven Rostedt } elsif (/^\s*ELSE\b(.*)$/) { 89445d73a5dSSteven Rostedt if (!$if) { 89545d73a5dSSteven Rostedt die "$name: $.: ELSE found with out matching IF section\n$_"; 89645d73a5dSSteven Rostedt } 89745d73a5dSSteven Rostedt $rest = $1; 89845d73a5dSSteven Rostedt if ($if_set) { 89945d73a5dSSteven Rostedt $skip = 1; 900ab7a3f52SSteven Rostedt $rest = ""; 90145d73a5dSSteven Rostedt } else { 90245d73a5dSSteven Rostedt $skip = 0; 90345d73a5dSSteven Rostedt 904ab7a3f52SSteven Rostedt if ($rest =~ /\sIF\s+(.*)/) { 90545d73a5dSSteven Rostedt # May be a ELSE IF section. 90695f57838SSteven Rostedt if (process_if($name, $1)) { 90795f57838SSteven Rostedt $if_set = 1; 90895f57838SSteven Rostedt } else { 90945d73a5dSSteven Rostedt $skip = 1; 91045d73a5dSSteven Rostedt } 911ab7a3f52SSteven Rostedt $rest = ""; 91245d73a5dSSteven Rostedt } else { 91345d73a5dSSteven Rostedt $if = 0; 91445d73a5dSSteven Rostedt } 91545d73a5dSSteven Rostedt } 91645d73a5dSSteven Rostedt 917ab7a3f52SSteven Rostedt if ($rest !~ /^\s*$/) { 918ab7a3f52SSteven Rostedt die "$name: $.: Gargbage found after DEFAULTS\n$_"; 919ab7a3f52SSteven Rostedt } 920ab7a3f52SSteven Rostedt 9212ed3b161SSteven Rostedt } elsif (/^\s*INCLUDE\s+(\S+)/) { 9222ed3b161SSteven Rostedt 9232ed3b161SSteven Rostedt next if ($skip); 9242ed3b161SSteven Rostedt 9252ed3b161SSteven Rostedt if (!$default) { 9262ed3b161SSteven Rostedt die "$name: $.: INCLUDE can only be done in default sections\n$_"; 9272ed3b161SSteven Rostedt } 9282ed3b161SSteven Rostedt 9292ed3b161SSteven Rostedt my $file = process_variables($1); 9302ed3b161SSteven Rostedt 9312ed3b161SSteven Rostedt if ($file !~ m,^/,) { 9322ed3b161SSteven Rostedt # check the path of the config file first 9332ed3b161SSteven Rostedt if ($config =~ m,(.*)/,) { 9342ed3b161SSteven Rostedt if (-f "$1/$file") { 9352ed3b161SSteven Rostedt $file = "$1/$file"; 9362ed3b161SSteven Rostedt } 9372ed3b161SSteven Rostedt } 9382ed3b161SSteven Rostedt } 9392ed3b161SSteven Rostedt 9402ed3b161SSteven Rostedt if ( ! -r $file ) { 9412ed3b161SSteven Rostedt die "$name: $.: Can't read file $file\n$_"; 9422ed3b161SSteven Rostedt } 9432ed3b161SSteven Rostedt 9442ed3b161SSteven Rostedt if (__read_config($file, \$test_num)) { 9452ed3b161SSteven Rostedt $test_case = 1; 9462ed3b161SSteven Rostedt } 9472ed3b161SSteven Rostedt 948a57419b3SSteven Rostedt } elsif (/^\s*([A-Z_\[\]\d]+)\s*=\s*(.*?)\s*$/) { 949a57419b3SSteven Rostedt 950a57419b3SSteven Rostedt next if ($skip); 951a57419b3SSteven Rostedt 952a57419b3SSteven Rostedt my $lvalue = $1; 953a57419b3SSteven Rostedt my $rvalue = $2; 954a57419b3SSteven Rostedt 955a57419b3SSteven Rostedt if (!$default && 956a57419b3SSteven Rostedt ($lvalue eq "NUM_TESTS" || 957a57419b3SSteven Rostedt $lvalue eq "LOG_FILE" || 958a57419b3SSteven Rostedt $lvalue eq "CLEAR_LOG")) { 959a57419b3SSteven Rostedt die "$name: $.: $lvalue must be set in DEFAULTS section\n"; 960a57419b3SSteven Rostedt } 961a57419b3SSteven Rostedt 962a57419b3SSteven Rostedt if ($lvalue eq "NUM_TESTS") { 963a57419b3SSteven Rostedt if ($test_num) { 964a57419b3SSteven Rostedt die "$name: $.: Can not specify both NUM_TESTS and TEST_START\n"; 965a57419b3SSteven Rostedt } 966a57419b3SSteven Rostedt if (!$default) { 967a57419b3SSteven Rostedt die "$name: $.: NUM_TESTS must be set in default section\n"; 968a57419b3SSteven Rostedt } 969a57419b3SSteven Rostedt $num_tests_set = 1; 970a57419b3SSteven Rostedt } 971a57419b3SSteven Rostedt 972a57419b3SSteven Rostedt if ($default || $lvalue =~ /\[\d+\]$/) { 9733d1cc414SSteven Rostedt set_value($lvalue, $rvalue, $override, \%overrides, $name); 974a57419b3SSteven Rostedt } else { 975a57419b3SSteven Rostedt my $val = "$lvalue\[$test_num\]"; 9763d1cc414SSteven Rostedt set_value($val, $rvalue, $override, \%overrides, $name); 977a57419b3SSteven Rostedt 978a57419b3SSteven Rostedt if ($repeat > 1) { 979a57419b3SSteven Rostedt $repeats{$val} = $repeat; 980a57419b3SSteven Rostedt } 981a57419b3SSteven Rostedt } 98277d942ceSSteven Rostedt } elsif (/^\s*([A-Z_\[\]\d]+)\s*:=\s*(.*?)\s*$/) { 98377d942ceSSteven Rostedt next if ($skip); 98477d942ceSSteven Rostedt 98577d942ceSSteven Rostedt my $lvalue = $1; 98677d942ceSSteven Rostedt my $rvalue = $2; 98777d942ceSSteven Rostedt 98877d942ceSSteven Rostedt # process config variables. 98977d942ceSSteven Rostedt # Config variables are only active while reading the 99077d942ceSSteven Rostedt # config and can be defined anywhere. They also ignore 99177d942ceSSteven Rostedt # TEST_START and DEFAULTS, but are skipped if they are in 99277d942ceSSteven Rostedt # on of these sections that have SKIP defined. 99377d942ceSSteven Rostedt # The save variable can be 99477d942ceSSteven Rostedt # defined multiple times and the new one simply overrides 99577d942ceSSteven Rostedt # the prevous one. 99677d942ceSSteven Rostedt set_variable($lvalue, $rvalue); 99777d942ceSSteven Rostedt 998a57419b3SSteven Rostedt } else { 999a57419b3SSteven Rostedt die "$name: $.: Garbage found in config\n$_"; 1000a57419b3SSteven Rostedt } 10012545eb61SSteven Rostedt } 10022545eb61SSteven Rostedt 1003a57419b3SSteven Rostedt if ($test_num) { 1004a57419b3SSteven Rostedt $test_num += $repeat - 1; 1005a57419b3SSteven Rostedt $opt{"NUM_TESTS"} = $test_num; 1006a57419b3SSteven Rostedt } 1007a57419b3SSteven Rostedt 10082ed3b161SSteven Rostedt close($in); 10092ed3b161SSteven Rostedt 10102ed3b161SSteven Rostedt $$current_test_num = $test_num; 10112ed3b161SSteven Rostedt 10122ed3b161SSteven Rostedt return $test_case; 10132ed3b161SSteven Rostedt} 10142ed3b161SSteven Rostedt 1015c4261d0fSSteven Rostedtsub get_test_case { 1016c4261d0fSSteven Rostedt print "What test case would you like to run?\n"; 1017c4261d0fSSteven Rostedt print " (build, install or boot)\n"; 1018c4261d0fSSteven Rostedt print " Other tests are available but require editing the config file\n"; 1019c4261d0fSSteven Rostedt my $ans = <STDIN>; 1020c4261d0fSSteven Rostedt chomp $ans; 1021c4261d0fSSteven Rostedt $default{"TEST_TYPE"} = $ans; 1022c4261d0fSSteven Rostedt} 1023c4261d0fSSteven Rostedt 10242ed3b161SSteven Rostedtsub read_config { 10252ed3b161SSteven Rostedt my ($config) = @_; 10262ed3b161SSteven Rostedt 10272ed3b161SSteven Rostedt my $test_case; 10282ed3b161SSteven Rostedt my $test_num = 0; 10292ed3b161SSteven Rostedt 10302ed3b161SSteven Rostedt $test_case = __read_config $config, \$test_num; 10312ed3b161SSteven Rostedt 10328d1491baSSteven Rostedt # make sure we have all mandatory configs 10338d1491baSSteven Rostedt get_ktest_configs; 10348d1491baSSteven Rostedt 10350df213caSSteven Rostedt # was a test specified? 10360df213caSSteven Rostedt if (!$test_case) { 10370df213caSSteven Rostedt print "No test case specified.\n"; 1038c4261d0fSSteven Rostedt get_test_case; 10390df213caSSteven Rostedt } 10400df213caSSteven Rostedt 1041a75fececSSteven Rostedt # set any defaults 1042a75fececSSteven Rostedt 1043a75fececSSteven Rostedt foreach my $default (keys %default) { 1044a75fececSSteven Rostedt if (!defined($opt{$default})) { 1045a75fececSSteven Rostedt $opt{$default} = $default{$default}; 1046a75fececSSteven Rostedt } 1047a75fececSSteven Rostedt } 10489cc9e091SSteven Rostedt 10499cc9e091SSteven Rostedt if ($opt{"IGNORE_UNUSED"} == 1) { 10509cc9e091SSteven Rostedt return; 10519cc9e091SSteven Rostedt } 10529cc9e091SSteven Rostedt 10539cc9e091SSteven Rostedt my %not_used; 10549cc9e091SSteven Rostedt 10559cc9e091SSteven Rostedt # check if there are any stragglers (typos?) 10569cc9e091SSteven Rostedt foreach my $option (keys %opt) { 10579cc9e091SSteven Rostedt my $op = $option; 10589cc9e091SSteven Rostedt # remove per test labels. 10599cc9e091SSteven Rostedt $op =~ s/\[.*\]//; 10609cc9e091SSteven Rostedt if (!exists($option_map{$op}) && 10619cc9e091SSteven Rostedt !exists($default{$op}) && 10629cc9e091SSteven Rostedt !exists($used_options{$op})) { 10639cc9e091SSteven Rostedt $not_used{$op} = 1; 10649cc9e091SSteven Rostedt } 10659cc9e091SSteven Rostedt } 10669cc9e091SSteven Rostedt 10679cc9e091SSteven Rostedt if (%not_used) { 10689cc9e091SSteven Rostedt my $s = "s are"; 10699cc9e091SSteven Rostedt $s = " is" if (keys %not_used == 1); 10709cc9e091SSteven Rostedt print "The following option$s not used; could be a typo:\n"; 10719cc9e091SSteven Rostedt foreach my $option (keys %not_used) { 10729cc9e091SSteven Rostedt print "$option\n"; 10739cc9e091SSteven Rostedt } 10749cc9e091SSteven Rostedt print "Set IGRNORE_UNUSED = 1 to have ktest ignore unused variables\n"; 10759cc9e091SSteven Rostedt if (!read_yn "Do you want to continue?") { 10769cc9e091SSteven Rostedt exit -1; 10779cc9e091SSteven Rostedt } 10789cc9e091SSteven Rostedt } 10792545eb61SSteven Rostedt} 10802545eb61SSteven Rostedt 108123715c3cSSteven Rostedtsub __eval_option { 108204262be3SSteven Rostedt (Red Hat) my ($name, $option, $i) = @_; 108323715c3cSSteven Rostedt 108423715c3cSSteven Rostedt # Add space to evaluate the character before $ 108523715c3cSSteven Rostedt $option = " $option"; 108623715c3cSSteven Rostedt my $retval = ""; 1087f9dfb65bSRabin Vincent my $repeated = 0; 1088f9dfb65bSRabin Vincent my $parent = 0; 1089f9dfb65bSRabin Vincent 1090f9dfb65bSRabin Vincent foreach my $test (keys %repeat_tests) { 1091f9dfb65bSRabin Vincent if ($i >= $test && 1092f9dfb65bSRabin Vincent $i < $test + $repeat_tests{$test}) { 1093f9dfb65bSRabin Vincent 1094f9dfb65bSRabin Vincent $repeated = 1; 1095f9dfb65bSRabin Vincent $parent = $test; 1096f9dfb65bSRabin Vincent last; 1097f9dfb65bSRabin Vincent } 1098f9dfb65bSRabin Vincent } 109923715c3cSSteven Rostedt 110023715c3cSSteven Rostedt while ($option =~ /(.*?[^\\])\$\{(.*?)\}(.*)/) { 110123715c3cSSteven Rostedt my $start = $1; 110223715c3cSSteven Rostedt my $var = $2; 110323715c3cSSteven Rostedt my $end = $3; 110423715c3cSSteven Rostedt 110523715c3cSSteven Rostedt # Append beginning of line 110623715c3cSSteven Rostedt $retval = "$retval$start"; 110723715c3cSSteven Rostedt 110823715c3cSSteven Rostedt # If the iteration option OPT[$i] exists, then use that. 110923715c3cSSteven Rostedt # otherwise see if the default OPT (without [$i]) exists. 111023715c3cSSteven Rostedt 111123715c3cSSteven Rostedt my $o = "$var\[$i\]"; 1112f9dfb65bSRabin Vincent my $parento = "$var\[$parent\]"; 111323715c3cSSteven Rostedt 111404262be3SSteven Rostedt (Red Hat) # If a variable contains itself, use the default var 111504262be3SSteven Rostedt (Red Hat) if (($var eq $name) && defined($opt{$var})) { 111604262be3SSteven Rostedt (Red Hat) $o = $opt{$var}; 111704262be3SSteven Rostedt (Red Hat) $retval = "$retval$o"; 111804262be3SSteven Rostedt (Red Hat) } elsif (defined($opt{$o})) { 111923715c3cSSteven Rostedt $o = $opt{$o}; 112023715c3cSSteven Rostedt $retval = "$retval$o"; 1121f9dfb65bSRabin Vincent } elsif ($repeated && defined($opt{$parento})) { 1122f9dfb65bSRabin Vincent $o = $opt{$parento}; 1123f9dfb65bSRabin Vincent $retval = "$retval$o"; 112423715c3cSSteven Rostedt } elsif (defined($opt{$var})) { 112523715c3cSSteven Rostedt $o = $opt{$var}; 112623715c3cSSteven Rostedt $retval = "$retval$o"; 112723715c3cSSteven Rostedt } else { 112823715c3cSSteven Rostedt $retval = "$retval\$\{$var\}"; 112923715c3cSSteven Rostedt } 113023715c3cSSteven Rostedt 113123715c3cSSteven Rostedt $option = $end; 113223715c3cSSteven Rostedt } 113323715c3cSSteven Rostedt 113423715c3cSSteven Rostedt $retval = "$retval$option"; 113523715c3cSSteven Rostedt 113623715c3cSSteven Rostedt $retval =~ s/^ //; 113723715c3cSSteven Rostedt 113823715c3cSSteven Rostedt return $retval; 113923715c3cSSteven Rostedt} 114023715c3cSSteven Rostedt 114123715c3cSSteven Rostedtsub eval_option { 114204262be3SSteven Rostedt (Red Hat) my ($name, $option, $i) = @_; 114323715c3cSSteven Rostedt 114423715c3cSSteven Rostedt my $prev = ""; 114523715c3cSSteven Rostedt 114623715c3cSSteven Rostedt # Since an option can evaluate to another option, 114723715c3cSSteven Rostedt # keep iterating until we do not evaluate any more 114823715c3cSSteven Rostedt # options. 114923715c3cSSteven Rostedt my $r = 0; 115023715c3cSSteven Rostedt while ($prev ne $option) { 115123715c3cSSteven Rostedt # Check for recursive evaluations. 115223715c3cSSteven Rostedt # 100 deep should be more than enough. 115323715c3cSSteven Rostedt if ($r++ > 100) { 115423715c3cSSteven Rostedt die "Over 100 evaluations accurred with $option\n" . 115523715c3cSSteven Rostedt "Check for recursive variables\n"; 115623715c3cSSteven Rostedt } 115723715c3cSSteven Rostedt $prev = $option; 115804262be3SSteven Rostedt (Red Hat) $option = __eval_option($name, $option, $i); 115923715c3cSSteven Rostedt } 116023715c3cSSteven Rostedt 116123715c3cSSteven Rostedt return $option; 116223715c3cSSteven Rostedt} 116323715c3cSSteven Rostedt 1164d1e2f22aSSteven Rostedtsub _logit { 11652545eb61SSteven Rostedt if (defined($opt{"LOG_FILE"})) { 11662545eb61SSteven Rostedt open(OUT, ">> $opt{LOG_FILE}") or die "Can't write to $opt{LOG_FILE}"; 11672545eb61SSteven Rostedt print OUT @_; 11682545eb61SSteven Rostedt close(OUT); 11692545eb61SSteven Rostedt } 11702545eb61SSteven Rostedt} 11712545eb61SSteven Rostedt 1172d1e2f22aSSteven Rostedtsub logit { 1173d1e2f22aSSteven Rostedt if (defined($opt{"LOG_FILE"})) { 1174d1e2f22aSSteven Rostedt _logit @_; 1175d1e2f22aSSteven Rostedt } else { 1176d1e2f22aSSteven Rostedt print @_; 1177d1e2f22aSSteven Rostedt } 1178d1e2f22aSSteven Rostedt} 1179d1e2f22aSSteven Rostedt 11805f9b6cedSSteven Rostedtsub doprint { 11815f9b6cedSSteven Rostedt print @_; 1182d1e2f22aSSteven Rostedt _logit @_; 11835f9b6cedSSteven Rostedt} 11845f9b6cedSSteven Rostedt 11857faafbd6SSteven Rostedtsub run_command; 11862728be41SAndrew Jonessub start_monitor; 11872728be41SAndrew Jonessub end_monitor; 11882728be41SAndrew Jonessub wait_for_monitor; 11897faafbd6SSteven Rostedt 11907faafbd6SSteven Rostedtsub reboot { 11912728be41SAndrew Jones my ($time) = @_; 11922728be41SAndrew Jones 1193a4968722SSteven Rostedt # Make sure everything has been written to disk 1194a4968722SSteven Rostedt run_ssh("sync"); 1195a4968722SSteven Rostedt 11962b803365SSteven Rostedt if (defined($time)) { 11972b803365SSteven Rostedt start_monitor; 11982b803365SSteven Rostedt # flush out current monitor 11992b803365SSteven Rostedt # May contain the reboot success line 12002b803365SSteven Rostedt wait_for_monitor 1; 12012b803365SSteven Rostedt } 12022b803365SSteven Rostedt 12037faafbd6SSteven Rostedt # try to reboot normally 1204e48c5293SSteven Rostedt if (run_command $reboot) { 1205576f627cSSteven Rostedt if (defined($powercycle_after_reboot)) { 1206576f627cSSteven Rostedt sleep $powercycle_after_reboot; 1207576f627cSSteven Rostedt run_command "$power_cycle"; 1208576f627cSSteven Rostedt } 1209576f627cSSteven Rostedt } else { 12107faafbd6SSteven Rostedt # nope? power cycle it. 1211a75fececSSteven Rostedt run_command "$power_cycle"; 12127faafbd6SSteven Rostedt } 12132728be41SAndrew Jones 12142728be41SAndrew Jones if (defined($time)) { 1215*4c0b67a2SSteven Rostedt (Red Hat) 1216*4c0b67a2SSteven Rostedt (Red Hat) # We only want to get to the new kernel, don't fail 1217*4c0b67a2SSteven Rostedt (Red Hat) # if we stumble over a call trace. 1218*4c0b67a2SSteven Rostedt (Red Hat) my $save_ignore_errors = $ignore_errors; 1219*4c0b67a2SSteven Rostedt (Red Hat) $ignore_errors = 1; 1220*4c0b67a2SSteven Rostedt (Red Hat) 1221d6845536SSteven Rostedt (Red Hat) # Look for the good kernel to boot 1222d6845536SSteven Rostedt (Red Hat) if (wait_for_monitor($time, "Linux version")) { 1223407b95b7SSteven Rostedt # reboot got stuck? 12248a80c727SSteven Rostedt doprint "Reboot did not finish. Forcing power cycle\n"; 1225407b95b7SSteven Rostedt run_command "$power_cycle"; 1226407b95b7SSteven Rostedt } 1227d6845536SSteven Rostedt (Red Hat) 1228*4c0b67a2SSteven Rostedt (Red Hat) $ignore_errors = $save_ignore_errors; 1229*4c0b67a2SSteven Rostedt (Red Hat) 1230d6845536SSteven Rostedt (Red Hat) # Still need to wait for the reboot to finish 1231d6845536SSteven Rostedt (Red Hat) wait_for_monitor($time, $reboot_success_line); 1232d6845536SSteven Rostedt (Red Hat) 12332728be41SAndrew Jones end_monitor; 12342728be41SAndrew Jones } 12357faafbd6SSteven Rostedt} 12367faafbd6SSteven Rostedt 1237bc7c5803SSteven Rostedtsub reboot_to_good { 1238bc7c5803SSteven Rostedt my ($time) = @_; 1239bc7c5803SSteven Rostedt 1240bc7c5803SSteven Rostedt if (defined($switch_to_good)) { 1241bc7c5803SSteven Rostedt run_command $switch_to_good; 1242bc7c5803SSteven Rostedt } 1243bc7c5803SSteven Rostedt 1244bc7c5803SSteven Rostedt reboot $time; 1245bc7c5803SSteven Rostedt} 1246bc7c5803SSteven Rostedt 1247576f627cSSteven Rostedtsub do_not_reboot { 1248576f627cSSteven Rostedt my $i = $iteration; 1249576f627cSSteven Rostedt 12504ab1cce5SSteven Rostedt return $test_type eq "build" || $no_reboot || 1251576f627cSSteven Rostedt ($test_type eq "patchcheck" && $opt{"PATCHCHECK_TYPE[$i]"} eq "build") || 1252576f627cSSteven Rostedt ($test_type eq "bisect" && $opt{"BISECT_TYPE[$i]"} eq "build"); 1253576f627cSSteven Rostedt} 1254576f627cSSteven Rostedt 12555c42fc5bSSteven Rostedtsub dodie { 12565a391fbfSSteven Rostedt doprint "CRITICAL FAILURE... ", @_, "\n"; 12575c42fc5bSSteven Rostedt 1258576f627cSSteven Rostedt my $i = $iteration; 1259576f627cSSteven Rostedt 1260576f627cSSteven Rostedt if ($reboot_on_error && !do_not_reboot) { 1261576f627cSSteven Rostedt 126275c3fda7SSteven Rostedt doprint "REBOOTING\n"; 1263bc7c5803SSteven Rostedt reboot_to_good; 126475c3fda7SSteven Rostedt 1265a75fececSSteven Rostedt } elsif ($poweroff_on_error && defined($power_off)) { 12665c42fc5bSSteven Rostedt doprint "POWERING OFF\n"; 1267a75fececSSteven Rostedt `$power_off`; 12685c42fc5bSSteven Rostedt } 126975c3fda7SSteven Rostedt 1270f80802cbSSteven Rostedt if (defined($opt{"LOG_FILE"})) { 1271f80802cbSSteven Rostedt print " See $opt{LOG_FILE} for more info.\n"; 1272f80802cbSSteven Rostedt } 1273f80802cbSSteven Rostedt 1274576f627cSSteven Rostedt die @_, "\n"; 12755c42fc5bSSteven Rostedt} 12765c42fc5bSSteven Rostedt 12777faafbd6SSteven Rostedtsub open_console { 12787faafbd6SSteven Rostedt my ($fp) = @_; 12797faafbd6SSteven Rostedt 12807faafbd6SSteven Rostedt my $flags; 12817faafbd6SSteven Rostedt 1282a75fececSSteven Rostedt my $pid = open($fp, "$console|") or 1283a75fececSSteven Rostedt dodie "Can't open console $console"; 12847faafbd6SSteven Rostedt 12857faafbd6SSteven Rostedt $flags = fcntl($fp, F_GETFL, 0) or 1286576f627cSSteven Rostedt dodie "Can't get flags for the socket: $!"; 12877faafbd6SSteven Rostedt $flags = fcntl($fp, F_SETFL, $flags | O_NONBLOCK) or 1288576f627cSSteven Rostedt dodie "Can't set flags for the socket: $!"; 12897faafbd6SSteven Rostedt 12907faafbd6SSteven Rostedt return $pid; 12917faafbd6SSteven Rostedt} 12927faafbd6SSteven Rostedt 12937faafbd6SSteven Rostedtsub close_console { 12947faafbd6SSteven Rostedt my ($fp, $pid) = @_; 12957faafbd6SSteven Rostedt 12967faafbd6SSteven Rostedt doprint "kill child process $pid\n"; 12977faafbd6SSteven Rostedt kill 2, $pid; 12987faafbd6SSteven Rostedt 12997faafbd6SSteven Rostedt print "closing!\n"; 13007faafbd6SSteven Rostedt close($fp); 13017faafbd6SSteven Rostedt} 13027faafbd6SSteven Rostedt 13037faafbd6SSteven Rostedtsub start_monitor { 13047faafbd6SSteven Rostedt if ($monitor_cnt++) { 13057faafbd6SSteven Rostedt return; 13067faafbd6SSteven Rostedt } 13077faafbd6SSteven Rostedt $monitor_fp = \*MONFD; 13087faafbd6SSteven Rostedt $monitor_pid = open_console $monitor_fp; 1309a75fececSSteven Rostedt 1310a75fececSSteven Rostedt return; 1311a75fececSSteven Rostedt 1312a75fececSSteven Rostedt open(MONFD, "Stop perl from warning about single use of MONFD"); 13137faafbd6SSteven Rostedt} 13147faafbd6SSteven Rostedt 13157faafbd6SSteven Rostedtsub end_monitor { 1316319ab14fSSteven Rostedt (Red Hat) return if (!defined $console); 13177faafbd6SSteven Rostedt if (--$monitor_cnt) { 13187faafbd6SSteven Rostedt return; 13197faafbd6SSteven Rostedt } 13207faafbd6SSteven Rostedt close_console($monitor_fp, $monitor_pid); 13217faafbd6SSteven Rostedt} 13227faafbd6SSteven Rostedt 13237faafbd6SSteven Rostedtsub wait_for_monitor { 13242b803365SSteven Rostedt my ($time, $stop) = @_; 13252b803365SSteven Rostedt my $full_line = ""; 13267faafbd6SSteven Rostedt my $line; 13272b803365SSteven Rostedt my $booted = 0; 1328407b95b7SSteven Rostedt my $start_time = time; 13298a80c727SSteven Rostedt my $skip_call_trace = 0; 13308a80c727SSteven Rostedt my $bug = 0; 13318a80c727SSteven Rostedt my $bug_ignored = 0; 1332407b95b7SSteven Rostedt my $now; 13337faafbd6SSteven Rostedt 1334a75fececSSteven Rostedt doprint "** Wait for monitor to settle down **\n"; 13357faafbd6SSteven Rostedt 13367faafbd6SSteven Rostedt # read the monitor and wait for the system to calm down 13372b803365SSteven Rostedt while (!$booted) { 13387faafbd6SSteven Rostedt $line = wait_for_input($monitor_fp, $time); 13392b803365SSteven Rostedt last if (!defined($line)); 13402b803365SSteven Rostedt print "$line"; 13412b803365SSteven Rostedt $full_line .= $line; 13422b803365SSteven Rostedt 13432b803365SSteven Rostedt if (defined($stop) && $full_line =~ /$stop/) { 13442b803365SSteven Rostedt doprint "wait for monitor detected $stop\n"; 13452b803365SSteven Rostedt $booted = 1; 13462b803365SSteven Rostedt } 13472b803365SSteven Rostedt 13488a80c727SSteven Rostedt if ($full_line =~ /\[ backtrace testing \]/) { 13498a80c727SSteven Rostedt $skip_call_trace = 1; 13508a80c727SSteven Rostedt } 13518a80c727SSteven Rostedt 13528a80c727SSteven Rostedt if ($full_line =~ /call trace:/i) { 13538a80c727SSteven Rostedt if (!$bug && !$skip_call_trace) { 13548a80c727SSteven Rostedt if ($ignore_errors) { 13558a80c727SSteven Rostedt $bug_ignored = 1; 13568a80c727SSteven Rostedt } else { 13578a80c727SSteven Rostedt $bug = 1; 13588a80c727SSteven Rostedt } 13598a80c727SSteven Rostedt } 13608a80c727SSteven Rostedt } 13618a80c727SSteven Rostedt 13628a80c727SSteven Rostedt if ($full_line =~ /\[ end of backtrace testing \]/) { 13638a80c727SSteven Rostedt $skip_call_trace = 0; 13648a80c727SSteven Rostedt } 13658a80c727SSteven Rostedt 13668a80c727SSteven Rostedt if ($full_line =~ /Kernel panic -/) { 13678a80c727SSteven Rostedt $bug = 1; 13688a80c727SSteven Rostedt } 13698a80c727SSteven Rostedt 13702b803365SSteven Rostedt if ($line =~ /\n/) { 13712b803365SSteven Rostedt $full_line = ""; 13722b803365SSteven Rostedt } 1373407b95b7SSteven Rostedt $now = time; 1374407b95b7SSteven Rostedt if ($now - $start_time >= $max_monitor_wait) { 1375407b95b7SSteven Rostedt doprint "Exiting monitor flush due to hitting MAX_MONITOR_WAIT\n"; 1376407b95b7SSteven Rostedt return 1; 1377407b95b7SSteven Rostedt } 13782b803365SSteven Rostedt } 1379a75fececSSteven Rostedt print "** Monitor flushed **\n"; 13808a80c727SSteven Rostedt return $bug; 13817faafbd6SSteven Rostedt} 13827faafbd6SSteven Rostedt 1383de5b6e3bSRabin Vincentsub save_logs { 1384de5b6e3bSRabin Vincent my ($result, $basedir) = @_; 1385de5b6e3bSRabin Vincent my @t = localtime; 1386de5b6e3bSRabin Vincent my $date = sprintf "%04d%02d%02d%02d%02d%02d", 1387de5b6e3bSRabin Vincent 1900+$t[5],$t[4],$t[3],$t[2],$t[1],$t[0]; 1388de5b6e3bSRabin Vincent 1389de5b6e3bSRabin Vincent my $type = $build_type; 1390de5b6e3bSRabin Vincent if ($type =~ /useconfig/) { 1391de5b6e3bSRabin Vincent $type = "useconfig"; 1392de5b6e3bSRabin Vincent } 1393de5b6e3bSRabin Vincent 1394de5b6e3bSRabin Vincent my $dir = "$machine-$test_type-$type-$result-$date"; 1395de5b6e3bSRabin Vincent 1396de5b6e3bSRabin Vincent $dir = "$basedir/$dir"; 1397de5b6e3bSRabin Vincent 1398de5b6e3bSRabin Vincent if (!-d $dir) { 1399de5b6e3bSRabin Vincent mkpath($dir) or 1400de5b6e3bSRabin Vincent die "can't create $dir"; 1401de5b6e3bSRabin Vincent } 1402de5b6e3bSRabin Vincent 1403de5b6e3bSRabin Vincent my %files = ( 1404de5b6e3bSRabin Vincent "config" => $output_config, 1405de5b6e3bSRabin Vincent "buildlog" => $buildlog, 1406de5b6e3bSRabin Vincent "dmesg" => $dmesg, 1407de5b6e3bSRabin Vincent "testlog" => $testlog, 1408de5b6e3bSRabin Vincent ); 1409de5b6e3bSRabin Vincent 1410de5b6e3bSRabin Vincent while (my ($name, $source) = each(%files)) { 1411de5b6e3bSRabin Vincent if (-f "$source") { 1412de5b6e3bSRabin Vincent cp "$source", "$dir/$name" or 1413de5b6e3bSRabin Vincent die "failed to copy $source"; 1414de5b6e3bSRabin Vincent } 1415de5b6e3bSRabin Vincent } 1416de5b6e3bSRabin Vincent 1417de5b6e3bSRabin Vincent doprint "*** Saved info to $dir ***\n"; 1418de5b6e3bSRabin Vincent} 1419de5b6e3bSRabin Vincent 14202b7d9b21SSteven Rostedtsub fail { 14212b7d9b21SSteven Rostedt 1422921ed4c7SSteven Rostedt if (defined($post_test)) { 1423921ed4c7SSteven Rostedt run_command $post_test; 1424921ed4c7SSteven Rostedt } 1425921ed4c7SSteven Rostedt 1426a75fececSSteven Rostedt if ($die_on_failure) { 14272b7d9b21SSteven Rostedt dodie @_; 14282b7d9b21SSteven Rostedt } 14292b7d9b21SSteven Rostedt 1430a75fececSSteven Rostedt doprint "FAILED\n"; 14317faafbd6SSteven Rostedt 1432576f627cSSteven Rostedt my $i = $iteration; 1433576f627cSSteven Rostedt 1434a75fececSSteven Rostedt # no need to reboot for just building. 1435576f627cSSteven Rostedt if (!do_not_reboot) { 14367faafbd6SSteven Rostedt doprint "REBOOTING\n"; 1437bc7c5803SSteven Rostedt reboot_to_good $sleep_time; 1438a75fececSSteven Rostedt } 14397faafbd6SSteven Rostedt 14409064af52SSteven Rostedt my $name = ""; 14419064af52SSteven Rostedt 14429064af52SSteven Rostedt if (defined($test_name)) { 14439064af52SSteven Rostedt $name = " ($test_name)"; 14449064af52SSteven Rostedt } 14459064af52SSteven Rostedt 1446576f627cSSteven Rostedt doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n"; 1447576f627cSSteven Rostedt doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n"; 14489064af52SSteven Rostedt doprint "KTEST RESULT: TEST $i$name Failed: ", @_, "\n"; 1449576f627cSSteven Rostedt doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n"; 1450576f627cSSteven Rostedt doprint "%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n"; 1451a75fececSSteven Rostedt 1452de5b6e3bSRabin Vincent if (defined($store_failures)) { 1453de5b6e3bSRabin Vincent save_logs "fail", $store_failures; 1454cccae1a6SSteven Rostedt } 1455cccae1a6SSteven Rostedt 14562b7d9b21SSteven Rostedt return 1; 14572b7d9b21SSteven Rostedt} 14582b7d9b21SSteven Rostedt 14592545eb61SSteven Rostedtsub run_command { 14602545eb61SSteven Rostedt my ($command) = @_; 1461d6ce2a0bSSteven Rostedt my $dolog = 0; 1462d6ce2a0bSSteven Rostedt my $dord = 0; 1463d6ce2a0bSSteven Rostedt my $pid; 1464d6ce2a0bSSteven Rostedt 1465e48c5293SSteven Rostedt $command =~ s/\$SSH_USER/$ssh_user/g; 1466e48c5293SSteven Rostedt $command =~ s/\$MACHINE/$machine/g; 1467e48c5293SSteven Rostedt 1468d6ce2a0bSSteven Rostedt doprint("$command ... "); 1469d6ce2a0bSSteven Rostedt 1470d6ce2a0bSSteven Rostedt $pid = open(CMD, "$command 2>&1 |") or 14712b7d9b21SSteven Rostedt (fail "unable to exec $command" and return 0); 14722545eb61SSteven Rostedt 14732545eb61SSteven Rostedt if (defined($opt{"LOG_FILE"})) { 1474d6ce2a0bSSteven Rostedt open(LOG, ">>$opt{LOG_FILE}") or 1475d6ce2a0bSSteven Rostedt dodie "failed to write to log"; 1476d6ce2a0bSSteven Rostedt $dolog = 1; 14776c5ee0beSSteven Rostedt } 14786c5ee0beSSteven Rostedt 14796c5ee0beSSteven Rostedt if (defined($redirect)) { 1480d6ce2a0bSSteven Rostedt open (RD, ">$redirect") or 1481d6ce2a0bSSteven Rostedt dodie "failed to write to redirect $redirect"; 1482d6ce2a0bSSteven Rostedt $dord = 1; 14832545eb61SSteven Rostedt } 14842545eb61SSteven Rostedt 1485d6ce2a0bSSteven Rostedt while (<CMD>) { 1486d6ce2a0bSSteven Rostedt print LOG if ($dolog); 1487d6ce2a0bSSteven Rostedt print RD if ($dord); 1488d6ce2a0bSSteven Rostedt } 14892545eb61SSteven Rostedt 1490d6ce2a0bSSteven Rostedt waitpid($pid, 0); 14912545eb61SSteven Rostedt my $failed = $?; 14922545eb61SSteven Rostedt 1493d6ce2a0bSSteven Rostedt close(CMD); 1494d6ce2a0bSSteven Rostedt close(LOG) if ($dolog); 1495d6ce2a0bSSteven Rostedt close(RD) if ($dord); 1496d6ce2a0bSSteven Rostedt 14972545eb61SSteven Rostedt if ($failed) { 14982545eb61SSteven Rostedt doprint "FAILED!\n"; 14992545eb61SSteven Rostedt } else { 15002545eb61SSteven Rostedt doprint "SUCCESS\n"; 15012545eb61SSteven Rostedt } 15022545eb61SSteven Rostedt 15035f9b6cedSSteven Rostedt return !$failed; 15045f9b6cedSSteven Rostedt} 15055f9b6cedSSteven Rostedt 1506e48c5293SSteven Rostedtsub run_ssh { 1507e48c5293SSteven Rostedt my ($cmd) = @_; 1508e48c5293SSteven Rostedt my $cp_exec = $ssh_exec; 1509e48c5293SSteven Rostedt 1510e48c5293SSteven Rostedt $cp_exec =~ s/\$SSH_COMMAND/$cmd/g; 1511e48c5293SSteven Rostedt return run_command "$cp_exec"; 1512e48c5293SSteven Rostedt} 1513e48c5293SSteven Rostedt 1514e48c5293SSteven Rostedtsub run_scp { 151502ad2617SSteven Rostedt my ($src, $dst, $cp_scp) = @_; 1516e48c5293SSteven Rostedt 1517e48c5293SSteven Rostedt $cp_scp =~ s/\$SRC_FILE/$src/g; 1518e48c5293SSteven Rostedt $cp_scp =~ s/\$DST_FILE/$dst/g; 1519e48c5293SSteven Rostedt 1520e48c5293SSteven Rostedt return run_command "$cp_scp"; 1521e48c5293SSteven Rostedt} 1522e48c5293SSteven Rostedt 152302ad2617SSteven Rostedtsub run_scp_install { 152402ad2617SSteven Rostedt my ($src, $dst) = @_; 152502ad2617SSteven Rostedt 152602ad2617SSteven Rostedt my $cp_scp = $scp_to_target_install; 152702ad2617SSteven Rostedt 152802ad2617SSteven Rostedt return run_scp($src, $dst, $cp_scp); 152902ad2617SSteven Rostedt} 153002ad2617SSteven Rostedt 153102ad2617SSteven Rostedtsub run_scp_mod { 153202ad2617SSteven Rostedt my ($src, $dst) = @_; 153302ad2617SSteven Rostedt 153402ad2617SSteven Rostedt my $cp_scp = $scp_to_target; 153502ad2617SSteven Rostedt 153602ad2617SSteven Rostedt return run_scp($src, $dst, $cp_scp); 153702ad2617SSteven Rostedt} 153802ad2617SSteven Rostedt 1539a15ba913SSteven Rostedtsub get_grub2_index { 1540a15ba913SSteven Rostedt 1541a15ba913SSteven Rostedt return if (defined($grub_number)); 1542a15ba913SSteven Rostedt 1543a15ba913SSteven Rostedt doprint "Find grub2 menu ... "; 1544a15ba913SSteven Rostedt $grub_number = -1; 1545a15ba913SSteven Rostedt 1546a15ba913SSteven Rostedt my $ssh_grub = $ssh_exec; 1547a15ba913SSteven Rostedt $ssh_grub =~ s,\$SSH_COMMAND,cat $grub_file,g; 1548a15ba913SSteven Rostedt 1549a15ba913SSteven Rostedt open(IN, "$ssh_grub |") 1550a15ba913SSteven Rostedt or die "unable to get $grub_file"; 1551a15ba913SSteven Rostedt 1552a15ba913SSteven Rostedt my $found = 0; 1553a15ba913SSteven Rostedt 1554a15ba913SSteven Rostedt while (<IN>) { 1555a15ba913SSteven Rostedt if (/^menuentry.*$grub_menu/) { 1556a15ba913SSteven Rostedt $grub_number++; 1557a15ba913SSteven Rostedt $found = 1; 1558a15ba913SSteven Rostedt last; 1559a15ba913SSteven Rostedt } elsif (/^menuentry\s/) { 1560a15ba913SSteven Rostedt $grub_number++; 1561a15ba913SSteven Rostedt } 1562a15ba913SSteven Rostedt } 1563a15ba913SSteven Rostedt close(IN); 1564a15ba913SSteven Rostedt 1565a15ba913SSteven Rostedt die "Could not find '$grub_menu' in $grub_file on $machine" 1566a15ba913SSteven Rostedt if (!$found); 1567a15ba913SSteven Rostedt doprint "$grub_number\n"; 1568a15ba913SSteven Rostedt} 1569a15ba913SSteven Rostedt 15705f9b6cedSSteven Rostedtsub get_grub_index { 15715f9b6cedSSteven Rostedt 1572a15ba913SSteven Rostedt if ($reboot_type eq "grub2") { 1573a15ba913SSteven Rostedt get_grub2_index; 1574a15ba913SSteven Rostedt return; 1575a15ba913SSteven Rostedt } 1576a15ba913SSteven Rostedt 1577a75fececSSteven Rostedt if ($reboot_type ne "grub") { 1578a75fececSSteven Rostedt return; 1579a75fececSSteven Rostedt } 15805a391fbfSSteven Rostedt return if (defined($grub_number)); 15815f9b6cedSSteven Rostedt 15825f9b6cedSSteven Rostedt doprint "Find grub menu ... "; 15835f9b6cedSSteven Rostedt $grub_number = -1; 1584e48c5293SSteven Rostedt 1585e48c5293SSteven Rostedt my $ssh_grub = $ssh_exec; 1586e48c5293SSteven Rostedt $ssh_grub =~ s,\$SSH_COMMAND,cat /boot/grub/menu.lst,g; 1587e48c5293SSteven Rostedt 1588e48c5293SSteven Rostedt open(IN, "$ssh_grub |") 15895f9b6cedSSteven Rostedt or die "unable to get menu.lst"; 1590e48c5293SSteven Rostedt 1591eaa1fe25SSteven Rostedt my $found = 0; 1592eaa1fe25SSteven Rostedt 15935f9b6cedSSteven Rostedt while (<IN>) { 1594a75fececSSteven Rostedt if (/^\s*title\s+$grub_menu\s*$/) { 15955f9b6cedSSteven Rostedt $grub_number++; 1596eaa1fe25SSteven Rostedt $found = 1; 15975f9b6cedSSteven Rostedt last; 15985f9b6cedSSteven Rostedt } elsif (/^\s*title\s/) { 15995f9b6cedSSteven Rostedt $grub_number++; 16005f9b6cedSSteven Rostedt } 16015f9b6cedSSteven Rostedt } 16025f9b6cedSSteven Rostedt close(IN); 16035f9b6cedSSteven Rostedt 1604a75fececSSteven Rostedt die "Could not find '$grub_menu' in /boot/grub/menu on $machine" 1605eaa1fe25SSteven Rostedt if (!$found); 16065f9b6cedSSteven Rostedt doprint "$grub_number\n"; 16072545eb61SSteven Rostedt} 16082545eb61SSteven Rostedt 16092545eb61SSteven Rostedtsub wait_for_input 16102545eb61SSteven Rostedt{ 16112545eb61SSteven Rostedt my ($fp, $time) = @_; 16122545eb61SSteven Rostedt my $rin; 16132545eb61SSteven Rostedt my $ready; 16142545eb61SSteven Rostedt my $line; 16152545eb61SSteven Rostedt my $ch; 16162545eb61SSteven Rostedt 16172545eb61SSteven Rostedt if (!defined($time)) { 16182545eb61SSteven Rostedt $time = $timeout; 16192545eb61SSteven Rostedt } 16202545eb61SSteven Rostedt 16212545eb61SSteven Rostedt $rin = ''; 16222545eb61SSteven Rostedt vec($rin, fileno($fp), 1) = 1; 1623319ab14fSSteven Rostedt (Red Hat) ($ready, $time) = select($rin, undef, undef, $time); 16242545eb61SSteven Rostedt 16252545eb61SSteven Rostedt $line = ""; 16262545eb61SSteven Rostedt 16272545eb61SSteven Rostedt # try to read one char at a time 16282545eb61SSteven Rostedt while (sysread $fp, $ch, 1) { 16292545eb61SSteven Rostedt $line .= $ch; 16302545eb61SSteven Rostedt last if ($ch eq "\n"); 16312545eb61SSteven Rostedt } 16322545eb61SSteven Rostedt 16332545eb61SSteven Rostedt if (!length($line)) { 16342545eb61SSteven Rostedt return undef; 16352545eb61SSteven Rostedt } 16362545eb61SSteven Rostedt 16372545eb61SSteven Rostedt return $line; 16382545eb61SSteven Rostedt} 16392545eb61SSteven Rostedt 164075c3fda7SSteven Rostedtsub reboot_to { 1641bc7c5803SSteven Rostedt if (defined($switch_to_test)) { 1642bc7c5803SSteven Rostedt run_command $switch_to_test; 1643bc7c5803SSteven Rostedt } 1644bc7c5803SSteven Rostedt 1645a75fececSSteven Rostedt if ($reboot_type eq "grub") { 1646c54367f9SSteven Rostedt run_ssh "'(echo \"savedefault --default=$grub_number --once\" | grub --batch)'"; 1647a15ba913SSteven Rostedt } elsif ($reboot_type eq "grub2") { 1648a15ba913SSteven Rostedt run_ssh "$grub_reboot $grub_number"; 16497786954cSSteven Rostedt } elsif ($reboot_type eq "syslinux") { 16507786954cSSteven Rostedt run_ssh "$syslinux --once \\\"$syslinux_label\\\" $syslinux_path"; 165196f6a0dfSSteven Rostedt } elsif (defined $reboot_script) { 1652a75fececSSteven Rostedt run_command "$reboot_script"; 16532545eb61SSteven Rostedt } 165496f6a0dfSSteven Rostedt reboot; 165596f6a0dfSSteven Rostedt} 16562545eb61SSteven Rostedt 1657a57419b3SSteven Rostedtsub get_sha1 { 1658a57419b3SSteven Rostedt my ($commit) = @_; 1659a57419b3SSteven Rostedt 1660a57419b3SSteven Rostedt doprint "git rev-list --max-count=1 $commit ... "; 1661a57419b3SSteven Rostedt my $sha1 = `git rev-list --max-count=1 $commit`; 1662a57419b3SSteven Rostedt my $ret = $?; 1663a57419b3SSteven Rostedt 1664a57419b3SSteven Rostedt logit $sha1; 1665a57419b3SSteven Rostedt 1666a57419b3SSteven Rostedt if ($ret) { 1667a57419b3SSteven Rostedt doprint "FAILED\n"; 1668a57419b3SSteven Rostedt dodie "Failed to get git $commit"; 1669a57419b3SSteven Rostedt } 1670a57419b3SSteven Rostedt 1671a57419b3SSteven Rostedt print "SUCCESS\n"; 1672a57419b3SSteven Rostedt 1673a57419b3SSteven Rostedt chomp $sha1; 1674a57419b3SSteven Rostedt 1675a57419b3SSteven Rostedt return $sha1; 1676a57419b3SSteven Rostedt} 1677a57419b3SSteven Rostedt 16785a391fbfSSteven Rostedtsub monitor { 16792545eb61SSteven Rostedt my $booted = 0; 16802545eb61SSteven Rostedt my $bug = 0; 16816ca996ccSSteven Rostedt my $bug_ignored = 0; 16825c42fc5bSSteven Rostedt my $skip_call_trace = 0; 16832b7d9b21SSteven Rostedt my $loops; 16842545eb61SSteven Rostedt 16857faafbd6SSteven Rostedt wait_for_monitor 5; 16862545eb61SSteven Rostedt 16872545eb61SSteven Rostedt my $line; 16882545eb61SSteven Rostedt my $full_line = ""; 16892545eb61SSteven Rostedt 16907faafbd6SSteven Rostedt open(DMESG, "> $dmesg") or 16917faafbd6SSteven Rostedt die "unable to write to $dmesg"; 16922545eb61SSteven Rostedt 169375c3fda7SSteven Rostedt reboot_to; 16942545eb61SSteven Rostedt 16951c8a617aSSteven Rostedt my $success_start; 16961c8a617aSSteven Rostedt my $failure_start; 16972d01b26aSSteven Rostedt my $monitor_start = time; 16982d01b26aSSteven Rostedt my $done = 0; 1699f1a5b962SSteven Rostedt my $version_found = 0; 17001c8a617aSSteven Rostedt 17012d01b26aSSteven Rostedt while (!$done) { 17022545eb61SSteven Rostedt 1703ecaf8e52SSteven Rostedt if ($bug && defined($stop_after_failure) && 1704ecaf8e52SSteven Rostedt $stop_after_failure >= 0) { 1705ecaf8e52SSteven Rostedt my $time = $stop_after_failure - (time - $failure_start); 1706ecaf8e52SSteven Rostedt $line = wait_for_input($monitor_fp, $time); 1707ecaf8e52SSteven Rostedt if (!defined($line)) { 1708ecaf8e52SSteven Rostedt doprint "bug timed out after $booted_timeout seconds\n"; 1709ecaf8e52SSteven Rostedt doprint "Test forced to stop after $stop_after_failure seconds after failure\n"; 1710ecaf8e52SSteven Rostedt last; 1711ecaf8e52SSteven Rostedt } 1712ecaf8e52SSteven Rostedt } elsif ($booted) { 1713a75fececSSteven Rostedt $line = wait_for_input($monitor_fp, $booted_timeout); 1714cd4f1d53SSteven Rostedt if (!defined($line)) { 1715cd4f1d53SSteven Rostedt my $s = $booted_timeout == 1 ? "" : "s"; 1716cd4f1d53SSteven Rostedt doprint "Successful boot found: break after $booted_timeout second$s\n"; 1717cd4f1d53SSteven Rostedt last; 1718cd4f1d53SSteven Rostedt } 17192b7d9b21SSteven Rostedt } else { 17207faafbd6SSteven Rostedt $line = wait_for_input($monitor_fp); 1721cd4f1d53SSteven Rostedt if (!defined($line)) { 1722cd4f1d53SSteven Rostedt my $s = $timeout == 1 ? "" : "s"; 1723cd4f1d53SSteven Rostedt doprint "Timed out after $timeout second$s\n"; 1724cd4f1d53SSteven Rostedt last; 17252b7d9b21SSteven Rostedt } 1726cd4f1d53SSteven Rostedt } 17272545eb61SSteven Rostedt 17282545eb61SSteven Rostedt doprint $line; 17297faafbd6SSteven Rostedt print DMESG $line; 17302545eb61SSteven Rostedt 17312545eb61SSteven Rostedt # we are not guaranteed to get a full line 17322545eb61SSteven Rostedt $full_line .= $line; 17332545eb61SSteven Rostedt 1734a75fececSSteven Rostedt if ($full_line =~ /$success_line/) { 17352545eb61SSteven Rostedt $booted = 1; 17361c8a617aSSteven Rostedt $success_start = time; 17371c8a617aSSteven Rostedt } 17381c8a617aSSteven Rostedt 17391c8a617aSSteven Rostedt if ($booted && defined($stop_after_success) && 17401c8a617aSSteven Rostedt $stop_after_success >= 0) { 17411c8a617aSSteven Rostedt my $now = time; 17421c8a617aSSteven Rostedt if ($now - $success_start >= $stop_after_success) { 17431c8a617aSSteven Rostedt doprint "Test forced to stop after $stop_after_success seconds after success\n"; 17441c8a617aSSteven Rostedt last; 17451c8a617aSSteven Rostedt } 17462545eb61SSteven Rostedt } 17472545eb61SSteven Rostedt 17485c42fc5bSSteven Rostedt if ($full_line =~ /\[ backtrace testing \]/) { 17495c42fc5bSSteven Rostedt $skip_call_trace = 1; 17505c42fc5bSSteven Rostedt } 17515c42fc5bSSteven Rostedt 17522545eb61SSteven Rostedt if ($full_line =~ /call trace:/i) { 17536ca996ccSSteven Rostedt if (!$bug && !$skip_call_trace) { 17546ca996ccSSteven Rostedt if ($ignore_errors) { 17556ca996ccSSteven Rostedt $bug_ignored = 1; 17566ca996ccSSteven Rostedt } else { 17571c8a617aSSteven Rostedt $bug = 1; 17581c8a617aSSteven Rostedt $failure_start = time; 17591c8a617aSSteven Rostedt } 17601c8a617aSSteven Rostedt } 17616ca996ccSSteven Rostedt } 17621c8a617aSSteven Rostedt 17631c8a617aSSteven Rostedt if ($bug && defined($stop_after_failure) && 17641c8a617aSSteven Rostedt $stop_after_failure >= 0) { 17651c8a617aSSteven Rostedt my $now = time; 17661c8a617aSSteven Rostedt if ($now - $failure_start >= $stop_after_failure) { 17671c8a617aSSteven Rostedt doprint "Test forced to stop after $stop_after_failure seconds after failure\n"; 17681c8a617aSSteven Rostedt last; 17691c8a617aSSteven Rostedt } 17705c42fc5bSSteven Rostedt } 17715c42fc5bSSteven Rostedt 17725c42fc5bSSteven Rostedt if ($full_line =~ /\[ end of backtrace testing \]/) { 17735c42fc5bSSteven Rostedt $skip_call_trace = 0; 17745c42fc5bSSteven Rostedt } 17755c42fc5bSSteven Rostedt 17765c42fc5bSSteven Rostedt if ($full_line =~ /Kernel panic -/) { 177710abf118SSteven Rostedt $failure_start = time; 17782545eb61SSteven Rostedt $bug = 1; 17792545eb61SSteven Rostedt } 17802545eb61SSteven Rostedt 1781f1a5b962SSteven Rostedt # Detect triple faults by testing the banner 1782f1a5b962SSteven Rostedt if ($full_line =~ /\bLinux version (\S+).*\n/) { 1783f1a5b962SSteven Rostedt if ($1 eq $version) { 1784f1a5b962SSteven Rostedt $version_found = 1; 1785f1a5b962SSteven Rostedt } elsif ($version_found && $detect_triplefault) { 1786f1a5b962SSteven Rostedt # We already booted into the kernel we are testing, 1787f1a5b962SSteven Rostedt # but now we booted into another kernel? 1788f1a5b962SSteven Rostedt # Consider this a triple fault. 1789f1a5b962SSteven Rostedt doprint "Aleady booted in Linux kernel $version, but now\n"; 1790f1a5b962SSteven Rostedt doprint "we booted into Linux kernel $1.\n"; 1791f1a5b962SSteven Rostedt doprint "Assuming that this is a triple fault.\n"; 1792f1a5b962SSteven Rostedt doprint "To disable this: set DETECT_TRIPLE_FAULT to 0\n"; 1793f1a5b962SSteven Rostedt last; 1794f1a5b962SSteven Rostedt } 1795f1a5b962SSteven Rostedt } 1796f1a5b962SSteven Rostedt 17972545eb61SSteven Rostedt if ($line =~ /\n/) { 17982545eb61SSteven Rostedt $full_line = ""; 17992545eb61SSteven Rostedt } 18002d01b26aSSteven Rostedt 18012d01b26aSSteven Rostedt if ($stop_test_after > 0 && !$booted && !$bug) { 18022d01b26aSSteven Rostedt if (time - $monitor_start > $stop_test_after) { 18034d62bf51SSteven Rostedt doprint "STOP_TEST_AFTER ($stop_test_after seconds) timed out\n"; 18042d01b26aSSteven Rostedt $done = 1; 18052d01b26aSSteven Rostedt } 18062d01b26aSSteven Rostedt } 18072545eb61SSteven Rostedt } 18082545eb61SSteven Rostedt 18097faafbd6SSteven Rostedt close(DMESG); 18102545eb61SSteven Rostedt 18112545eb61SSteven Rostedt if ($bug) { 18122b7d9b21SSteven Rostedt return 0 if ($in_bisect); 1813576f627cSSteven Rostedt fail "failed - got a bug report" and return 0; 18142545eb61SSteven Rostedt } 18155f9b6cedSSteven Rostedt 1816a75fececSSteven Rostedt if (!$booted) { 1817a75fececSSteven Rostedt return 0 if ($in_bisect); 1818576f627cSSteven Rostedt fail "failed - never got a boot prompt." and return 0; 1819a75fececSSteven Rostedt } 1820a75fececSSteven Rostedt 18216ca996ccSSteven Rostedt if ($bug_ignored) { 18226ca996ccSSteven Rostedt doprint "WARNING: Call Trace detected but ignored due to IGNORE_ERRORS=1\n"; 18236ca996ccSSteven Rostedt } 18246ca996ccSSteven Rostedt 18252b7d9b21SSteven Rostedt return 1; 18262545eb61SSteven Rostedt} 18272545eb61SSteven Rostedt 18282b29b2f8SSteven Rostedtsub eval_kernel_version { 18292b29b2f8SSteven Rostedt my ($option) = @_; 18302b29b2f8SSteven Rostedt 18312b29b2f8SSteven Rostedt $option =~ s/\$KERNEL_VERSION/$version/g; 18322b29b2f8SSteven Rostedt 18332b29b2f8SSteven Rostedt return $option; 18342b29b2f8SSteven Rostedt} 18352b29b2f8SSteven Rostedt 1836db05cfefSSteven Rostedtsub do_post_install { 1837db05cfefSSteven Rostedt 1838db05cfefSSteven Rostedt return if (!defined($post_install)); 1839db05cfefSSteven Rostedt 18402b29b2f8SSteven Rostedt my $cp_post_install = eval_kernel_version $post_install; 1841db05cfefSSteven Rostedt run_command "$cp_post_install" or 1842db05cfefSSteven Rostedt dodie "Failed to run post install"; 1843db05cfefSSteven Rostedt} 1844db05cfefSSteven Rostedt 1845e1a6c3d7SSteven Rostedt# Sometimes the reboot fails, and will hang. We try to ssh to the box 1846e1a6c3d7SSteven Rostedt# and if we fail, we force another reboot, that should powercycle it. 1847e1a6c3d7SSteven Rostedtsub test_booted { 1848e1a6c3d7SSteven Rostedt if (!run_ssh "echo testing connection") { 1849e1a6c3d7SSteven Rostedt reboot $sleep_time; 1850e1a6c3d7SSteven Rostedt } 1851e1a6c3d7SSteven Rostedt} 1852e1a6c3d7SSteven Rostedt 18532545eb61SSteven Rostedtsub install { 18542545eb61SSteven Rostedt 1855e0a8742eSSteven Rostedt return if ($no_install); 1856e0a8742eSSteven Rostedt 1857e5c2ec11SSteven Rostedt if (defined($pre_install)) { 1858e5c2ec11SSteven Rostedt my $cp_pre_install = eval_kernel_version $pre_install; 1859e5c2ec11SSteven Rostedt run_command "$cp_pre_install" or 1860e5c2ec11SSteven Rostedt dodie "Failed to run pre install"; 1861e5c2ec11SSteven Rostedt } 1862e5c2ec11SSteven Rostedt 18632b29b2f8SSteven Rostedt my $cp_target = eval_kernel_version $target_image; 18642b29b2f8SSteven Rostedt 1865e1a6c3d7SSteven Rostedt test_booted; 1866e1a6c3d7SSteven Rostedt 186702ad2617SSteven Rostedt run_scp_install "$outputdir/$build_target", "$cp_target" or 18685c42fc5bSSteven Rostedt dodie "failed to copy image"; 18695f9b6cedSSteven Rostedt 18705f9b6cedSSteven Rostedt my $install_mods = 0; 18715f9b6cedSSteven Rostedt 18725f9b6cedSSteven Rostedt # should we process modules? 18735f9b6cedSSteven Rostedt $install_mods = 0; 187451ad1dd1SSteven Rostedt open(IN, "$output_config") or dodie("Can't read config file"); 18755f9b6cedSSteven Rostedt while (<IN>) { 18765f9b6cedSSteven Rostedt if (/CONFIG_MODULES(=y)?/) { 18778bc5e4eaSSteven Rostedt if (defined($1)) { 18788bc5e4eaSSteven Rostedt $install_mods = 1; 18795f9b6cedSSteven Rostedt last; 18805f9b6cedSSteven Rostedt } 18815f9b6cedSSteven Rostedt } 18828bc5e4eaSSteven Rostedt } 18835f9b6cedSSteven Rostedt close(IN); 18845f9b6cedSSteven Rostedt 18855f9b6cedSSteven Rostedt if (!$install_mods) { 1886db05cfefSSteven Rostedt do_post_install; 18875f9b6cedSSteven Rostedt doprint "No modules needed\n"; 18885f9b6cedSSteven Rostedt return; 18892545eb61SSteven Rostedt } 18902545eb61SSteven Rostedt 1891627977d8SSteven Rostedt run_command "$make INSTALL_MOD_STRIP=1 INSTALL_MOD_PATH=$tmpdir modules_install" or 18925f9b6cedSSteven Rostedt dodie "Failed to install modules"; 18935f9b6cedSSteven Rostedt 18942545eb61SSteven Rostedt my $modlib = "/lib/modules/$version"; 1895a57419b3SSteven Rostedt my $modtar = "ktest-mods.tar.bz2"; 18962545eb61SSteven Rostedt 1897e48c5293SSteven Rostedt run_ssh "rm -rf $modlib" or 18985c42fc5bSSteven Rostedt dodie "failed to remove old mods: $modlib"; 18992545eb61SSteven Rostedt 19005c42fc5bSSteven Rostedt # would be nice if scp -r did not follow symbolic links 1901a75fececSSteven Rostedt run_command "cd $tmpdir && tar -cjf $modtar lib/modules/$version" or 19025c42fc5bSSteven Rostedt dodie "making tarball"; 19035c42fc5bSSteven Rostedt 190402ad2617SSteven Rostedt run_scp_mod "$tmpdir/$modtar", "/tmp" or 19055c42fc5bSSteven Rostedt dodie "failed to copy modules"; 19065c42fc5bSSteven Rostedt 1907a75fececSSteven Rostedt unlink "$tmpdir/$modtar"; 19085c42fc5bSSteven Rostedt 1909e7b13441SSteven Rostedt run_ssh "'(cd / && tar xjf /tmp/$modtar)'" or 19105c42fc5bSSteven Rostedt dodie "failed to tar modules"; 19115c42fc5bSSteven Rostedt 1912e48c5293SSteven Rostedt run_ssh "rm -f /tmp/$modtar"; 19138b37ca8cSSteven Rostedt 1914db05cfefSSteven Rostedt do_post_install; 19152545eb61SSteven Rostedt} 19162545eb61SSteven Rostedt 1917ddf607e5SSteven Rostedtsub get_version { 1918ddf607e5SSteven Rostedt # get the release name 1919683a3e64SSteven Rostedt return if ($have_version); 1920ddf607e5SSteven Rostedt doprint "$make kernelrelease ... "; 1921ddf607e5SSteven Rostedt $version = `$make kernelrelease | tail -1`; 1922ddf607e5SSteven Rostedt chomp($version); 1923ddf607e5SSteven Rostedt doprint "$version\n"; 1924683a3e64SSteven Rostedt $have_version = 1; 1925ddf607e5SSteven Rostedt} 1926ddf607e5SSteven Rostedt 1927ddf607e5SSteven Rostedtsub start_monitor_and_boot { 19289f7424ccSSteven Rostedt # Make sure the stable kernel has finished booting 1929319ab14fSSteven Rostedt (Red Hat) 1930319ab14fSSteven Rostedt (Red Hat) # Install bisects, don't need console 1931319ab14fSSteven Rostedt (Red Hat) if (defined $console) { 19329f7424ccSSteven Rostedt start_monitor; 19339f7424ccSSteven Rostedt wait_for_monitor 5; 19349f7424ccSSteven Rostedt end_monitor; 1935319ab14fSSteven Rostedt (Red Hat) } 19369f7424ccSSteven Rostedt 1937ddf607e5SSteven Rostedt get_grub_index; 1938ddf607e5SSteven Rostedt get_version; 1939ddf607e5SSteven Rostedt install; 1940ddf607e5SSteven Rostedt 1941319ab14fSSteven Rostedt (Red Hat) start_monitor if (defined $console); 1942ddf607e5SSteven Rostedt return monitor; 1943ddf607e5SSteven Rostedt} 1944ddf607e5SSteven Rostedt 19454283b169SSteven Rostedt (Red Hat)my $check_build_re = ".*:.*(warning|error|Error):.*"; 19464283b169SSteven Rostedt (Red Hat)my $utf8_quote = "\\x{e2}\\x{80}(\\x{98}|\\x{99})"; 19474283b169SSteven Rostedt (Red Hat) 19484283b169SSteven Rostedt (Red Hat)# Read buildlog and check against warnings file for any 19494283b169SSteven Rostedt (Red Hat)# new warnings. 19504283b169SSteven Rostedt (Red Hat)# 19514283b169SSteven Rostedt (Red Hat)# Returns 1 if OK 19524283b169SSteven Rostedt (Red Hat)# 0 otherwise 19536c5ee0beSSteven Rostedtsub check_buildlog { 19544283b169SSteven Rostedt (Red Hat) return 1 if (!defined $warnings_file); 19554283b169SSteven Rostedt (Red Hat) 19564283b169SSteven Rostedt (Red Hat) my %warnings_list; 19574283b169SSteven Rostedt (Red Hat) 19584283b169SSteven Rostedt (Red Hat) # Failed builds should not reboot the target 19594283b169SSteven Rostedt (Red Hat) my $save_no_reboot = $no_reboot; 19604283b169SSteven Rostedt (Red Hat) $no_reboot = 1; 19614283b169SSteven Rostedt (Red Hat) 19624283b169SSteven Rostedt (Red Hat) if (-f $warnings_file) { 19634283b169SSteven Rostedt (Red Hat) open(IN, $warnings_file) or 19644283b169SSteven Rostedt (Red Hat) dodie "Error opening $warnings_file"; 19654283b169SSteven Rostedt (Red Hat) 19664283b169SSteven Rostedt (Red Hat) while (<IN>) { 19674283b169SSteven Rostedt (Red Hat) if (/$check_build_re/) { 19684283b169SSteven Rostedt (Red Hat) chomp; 19694283b169SSteven Rostedt (Red Hat) $warnings_list{$_} = 1; 19704283b169SSteven Rostedt (Red Hat) } 19714283b169SSteven Rostedt (Red Hat) } 19724283b169SSteven Rostedt (Red Hat) close(IN); 19734283b169SSteven Rostedt (Red Hat) } 19744283b169SSteven Rostedt (Red Hat) 19754283b169SSteven Rostedt (Red Hat) # If warnings file didn't exist, and WARNINGS_FILE exist, 19764283b169SSteven Rostedt (Red Hat) # then we fail on any warning! 19774283b169SSteven Rostedt (Red Hat) 19784283b169SSteven Rostedt (Red Hat) open(IN, $buildlog) or dodie "Can't open $buildlog"; 19794283b169SSteven Rostedt (Red Hat) while (<IN>) { 19804283b169SSteven Rostedt (Red Hat) if (/$check_build_re/) { 19814283b169SSteven Rostedt (Red Hat) 19824283b169SSteven Rostedt (Red Hat) # Some compilers use UTF-8 extended for quotes 19834283b169SSteven Rostedt (Red Hat) # for distcc heterogeneous systems, this causes issues 19844283b169SSteven Rostedt (Red Hat) s/$utf8_quote/'/g; 19854283b169SSteven Rostedt (Red Hat) 19864283b169SSteven Rostedt (Red Hat) chomp; 19874283b169SSteven Rostedt (Red Hat) if (!defined $warnings_list{$_}) { 19884283b169SSteven Rostedt (Red Hat) fail "New warning found (not in $warnings_file)\n$_\n"; 19894283b169SSteven Rostedt (Red Hat) $no_reboot = $save_no_reboot; 19904283b169SSteven Rostedt (Red Hat) return 0; 19914283b169SSteven Rostedt (Red Hat) } 19924283b169SSteven Rostedt (Red Hat) } 19934283b169SSteven Rostedt (Red Hat) } 19944283b169SSteven Rostedt (Red Hat) $no_reboot = $save_no_reboot; 19954283b169SSteven Rostedt (Red Hat) close(IN); 19964283b169SSteven Rostedt (Red Hat)} 19974283b169SSteven Rostedt (Red Hat) 19984283b169SSteven Rostedt (Red Hat)sub check_patch_buildlog { 19996c5ee0beSSteven Rostedt my ($patch) = @_; 20006c5ee0beSSteven Rostedt 20016c5ee0beSSteven Rostedt my @files = `git show $patch | diffstat -l`; 20026c5ee0beSSteven Rostedt 200335275685SSteven Rostedt (Red Hat) foreach my $file (@files) { 200435275685SSteven Rostedt (Red Hat) chomp $file; 200535275685SSteven Rostedt (Red Hat) } 200635275685SSteven Rostedt (Red Hat) 20076c5ee0beSSteven Rostedt open(IN, "git show $patch |") or 20086c5ee0beSSteven Rostedt dodie "failed to show $patch"; 20096c5ee0beSSteven Rostedt while (<IN>) { 20106c5ee0beSSteven Rostedt if (m,^--- a/(.*),) { 20116c5ee0beSSteven Rostedt chomp $1; 20126c5ee0beSSteven Rostedt $files[$#files] = $1; 20136c5ee0beSSteven Rostedt } 20146c5ee0beSSteven Rostedt } 20156c5ee0beSSteven Rostedt close(IN); 20166c5ee0beSSteven Rostedt 20176c5ee0beSSteven Rostedt open(IN, $buildlog) or dodie "Can't open $buildlog"; 20186c5ee0beSSteven Rostedt while (<IN>) { 20196c5ee0beSSteven Rostedt if (/^\s*(.*?):.*(warning|error)/) { 20206c5ee0beSSteven Rostedt my $err = $1; 20216c5ee0beSSteven Rostedt foreach my $file (@files) { 2022a75fececSSteven Rostedt my $fullpath = "$builddir/$file"; 20236c5ee0beSSteven Rostedt if ($file eq $err || $fullpath eq $err) { 20242b7d9b21SSteven Rostedt fail "$file built with warnings" and return 0; 20256c5ee0beSSteven Rostedt } 20266c5ee0beSSteven Rostedt } 20276c5ee0beSSteven Rostedt } 20286c5ee0beSSteven Rostedt } 20296c5ee0beSSteven Rostedt close(IN); 20302b7d9b21SSteven Rostedt 20312b7d9b21SSteven Rostedt return 1; 20326c5ee0beSSteven Rostedt} 20336c5ee0beSSteven Rostedt 2034fcb3f16aSSteven Rostedtsub apply_min_config { 2035fcb3f16aSSteven Rostedt my $outconfig = "$output_config.new"; 2036612b9e9bSSteven Rostedt 2037fcb3f16aSSteven Rostedt # Read the config file and remove anything that 2038fcb3f16aSSteven Rostedt # is in the force_config hash (from minconfig and others) 2039fcb3f16aSSteven Rostedt # then add the force config back. 2040fcb3f16aSSteven Rostedt 2041fcb3f16aSSteven Rostedt doprint "Applying minimum configurations into $output_config.new\n"; 2042fcb3f16aSSteven Rostedt 2043fcb3f16aSSteven Rostedt open (OUT, ">$outconfig") or 2044fcb3f16aSSteven Rostedt dodie "Can't create $outconfig"; 2045fcb3f16aSSteven Rostedt 2046fcb3f16aSSteven Rostedt if (-f $output_config) { 2047fcb3f16aSSteven Rostedt open (IN, $output_config) or 2048fcb3f16aSSteven Rostedt dodie "Failed to open $output_config"; 2049fcb3f16aSSteven Rostedt while (<IN>) { 2050fcb3f16aSSteven Rostedt if (/^(# )?(CONFIG_[^\s=]*)/) { 2051fcb3f16aSSteven Rostedt next if (defined($force_config{$2})); 2052fcb3f16aSSteven Rostedt } 2053fcb3f16aSSteven Rostedt print OUT; 2054fcb3f16aSSteven Rostedt } 2055fcb3f16aSSteven Rostedt close IN; 2056fcb3f16aSSteven Rostedt } 2057fcb3f16aSSteven Rostedt foreach my $config (keys %force_config) { 2058fcb3f16aSSteven Rostedt print OUT "$force_config{$config}\n"; 2059fcb3f16aSSteven Rostedt } 2060fcb3f16aSSteven Rostedt close OUT; 2061fcb3f16aSSteven Rostedt 2062fcb3f16aSSteven Rostedt run_command "mv $outconfig $output_config"; 2063fcb3f16aSSteven Rostedt} 2064fcb3f16aSSteven Rostedt 2065fcb3f16aSSteven Rostedtsub make_oldconfig { 2066fcb3f16aSSteven Rostedt 20674c4ab120SSteven Rostedt my @force_list = keys %force_config; 20684c4ab120SSteven Rostedt 20694c4ab120SSteven Rostedt if ($#force_list >= 0) { 2070fcb3f16aSSteven Rostedt apply_min_config; 20714c4ab120SSteven Rostedt } 2072fcb3f16aSSteven Rostedt 2073fb16d891SAdam Lee if (!run_command "$make olddefconfig") { 2074fb16d891SAdam Lee # Perhaps olddefconfig doesn't exist in this version of the kernel 207518925170SSteven Rostedt # try oldnoconfig 207618925170SSteven Rostedt doprint "olddefconfig failed, trying make oldnoconfig\n"; 207718925170SSteven Rostedt if (!run_command "$make oldnoconfig") { 207818925170SSteven Rostedt doprint "oldnoconfig failed, trying yes '' | make oldconfig\n"; 2079612b9e9bSSteven Rostedt # try a yes '' | oldconfig 2080fcb3f16aSSteven Rostedt run_command "yes '' | $make oldconfig" or 2081612b9e9bSSteven Rostedt dodie "failed make config oldconfig"; 2082612b9e9bSSteven Rostedt } 2083612b9e9bSSteven Rostedt } 208418925170SSteven Rostedt} 2085612b9e9bSSteven Rostedt 2086fcb3f16aSSteven Rostedt# read a config file and use this to force new configs. 2087fcb3f16aSSteven Rostedtsub load_force_config { 2088fcb3f16aSSteven Rostedt my ($config) = @_; 2089fcb3f16aSSteven Rostedt 2090cf79fab6SSteven Rostedt doprint "Loading force configs from $config\n"; 2091fcb3f16aSSteven Rostedt open(IN, $config) or 2092fcb3f16aSSteven Rostedt dodie "failed to read $config"; 2093fcb3f16aSSteven Rostedt while (<IN>) { 2094fcb3f16aSSteven Rostedt chomp; 2095fcb3f16aSSteven Rostedt if (/^(CONFIG[^\s=]*)(\s*=.*)/) { 2096fcb3f16aSSteven Rostedt $force_config{$1} = $_; 2097fcb3f16aSSteven Rostedt } elsif (/^# (CONFIG_\S*) is not set/) { 2098fcb3f16aSSteven Rostedt $force_config{$1} = $_; 2099fcb3f16aSSteven Rostedt } 2100fcb3f16aSSteven Rostedt } 2101fcb3f16aSSteven Rostedt close IN; 2102fcb3f16aSSteven Rostedt} 2103fcb3f16aSSteven Rostedt 21042545eb61SSteven Rostedtsub build { 21052545eb61SSteven Rostedt my ($type) = @_; 21062545eb61SSteven Rostedt 21077faafbd6SSteven Rostedt unlink $buildlog; 21087faafbd6SSteven Rostedt 21094ab1cce5SSteven Rostedt # Failed builds should not reboot the target 21104ab1cce5SSteven Rostedt my $save_no_reboot = $no_reboot; 21114ab1cce5SSteven Rostedt $no_reboot = 1; 21124ab1cce5SSteven Rostedt 2113683a3e64SSteven Rostedt # Calculate a new version from here. 2114683a3e64SSteven Rostedt $have_version = 0; 2115683a3e64SSteven Rostedt 21160bd6c1a3SSteven Rostedt if (defined($pre_build)) { 21170bd6c1a3SSteven Rostedt my $ret = run_command $pre_build; 21180bd6c1a3SSteven Rostedt if (!$ret && defined($pre_build_die) && 21190bd6c1a3SSteven Rostedt $pre_build_die) { 21200bd6c1a3SSteven Rostedt dodie "failed to pre_build\n"; 21210bd6c1a3SSteven Rostedt } 21220bd6c1a3SSteven Rostedt } 21230bd6c1a3SSteven Rostedt 212475c3fda7SSteven Rostedt if ($type =~ /^useconfig:(.*)/) { 212551ad1dd1SSteven Rostedt run_command "cp $1 $output_config" or 212675c3fda7SSteven Rostedt dodie "could not copy $1 to .config"; 21275f9b6cedSSteven Rostedt 212875c3fda7SSteven Rostedt $type = "oldconfig"; 212975c3fda7SSteven Rostedt } 213075c3fda7SSteven Rostedt 21315c42fc5bSSteven Rostedt # old config can ask questions 21325c42fc5bSSteven Rostedt if ($type eq "oldconfig") { 2133fb16d891SAdam Lee $type = "olddefconfig"; 213475c3fda7SSteven Rostedt 213575c3fda7SSteven Rostedt # allow for empty configs 213651ad1dd1SSteven Rostedt run_command "touch $output_config"; 213775c3fda7SSteven Rostedt 213813488231SAndrew Jones if (!$noclean) { 213951ad1dd1SSteven Rostedt run_command "mv $output_config $outputdir/config_temp" or 21405c42fc5bSSteven Rostedt dodie "moving .config"; 21415c42fc5bSSteven Rostedt 214213488231SAndrew Jones run_command "$make mrproper" or dodie "make mrproper"; 21435c42fc5bSSteven Rostedt 214451ad1dd1SSteven Rostedt run_command "mv $outputdir/config_temp $output_config" or 21455c42fc5bSSteven Rostedt dodie "moving config_temp"; 214613488231SAndrew Jones } 21475c42fc5bSSteven Rostedt 21485c42fc5bSSteven Rostedt } elsif (!$noclean) { 214951ad1dd1SSteven Rostedt unlink "$output_config"; 21505f9b6cedSSteven Rostedt run_command "$make mrproper" or 21515c42fc5bSSteven Rostedt dodie "make mrproper"; 21525c42fc5bSSteven Rostedt } 21532545eb61SSteven Rostedt 21542545eb61SSteven Rostedt # add something to distinguish this build 2155a75fececSSteven Rostedt open(OUT, "> $outputdir/localversion") or dodie("Can't make localversion file"); 2156a75fececSSteven Rostedt print OUT "$localversion\n"; 21572545eb61SSteven Rostedt close(OUT); 21582545eb61SSteven Rostedt 21595f9b6cedSSteven Rostedt if (defined($minconfig)) { 2160fcb3f16aSSteven Rostedt load_force_config($minconfig); 21612545eb61SSteven Rostedt } 21622545eb61SSteven Rostedt 2163fb16d891SAdam Lee if ($type ne "olddefconfig") { 2164fcb3f16aSSteven Rostedt run_command "$make $type" or 21655c42fc5bSSteven Rostedt dodie "failed make config"; 2166612b9e9bSSteven Rostedt } 2167fcb3f16aSSteven Rostedt # Run old config regardless, to enforce min configurations 2168fcb3f16aSSteven Rostedt make_oldconfig; 21692545eb61SSteven Rostedt 2170a75fececSSteven Rostedt $redirect = "$buildlog"; 21710bd6c1a3SSteven Rostedt my $build_ret = run_command "$make $build_options"; 21726c5ee0beSSteven Rostedt undef $redirect; 21730bd6c1a3SSteven Rostedt 21740bd6c1a3SSteven Rostedt if (defined($post_build)) { 2175683a3e64SSteven Rostedt # Because a post build may change the kernel version 2176683a3e64SSteven Rostedt # do it now. 2177683a3e64SSteven Rostedt get_version; 21780bd6c1a3SSteven Rostedt my $ret = run_command $post_build; 21790bd6c1a3SSteven Rostedt if (!$ret && defined($post_build_die) && 21800bd6c1a3SSteven Rostedt $post_build_die) { 21810bd6c1a3SSteven Rostedt dodie "failed to post_build\n"; 21820bd6c1a3SSteven Rostedt } 21830bd6c1a3SSteven Rostedt } 21840bd6c1a3SSteven Rostedt 21850bd6c1a3SSteven Rostedt if (!$build_ret) { 21865f9b6cedSSteven Rostedt # bisect may need this to pass 21874ab1cce5SSteven Rostedt if ($in_bisect) { 21884ab1cce5SSteven Rostedt $no_reboot = $save_no_reboot; 21894ab1cce5SSteven Rostedt return 0; 21904ab1cce5SSteven Rostedt } 21912b7d9b21SSteven Rostedt fail "failed build" and return 0; 21922545eb61SSteven Rostedt } 21935f9b6cedSSteven Rostedt 21944ab1cce5SSteven Rostedt $no_reboot = $save_no_reboot; 21954ab1cce5SSteven Rostedt 21962b7d9b21SSteven Rostedt return 1; 21972545eb61SSteven Rostedt} 21982545eb61SSteven Rostedt 219975c3fda7SSteven Rostedtsub halt { 2200e48c5293SSteven Rostedt if (!run_ssh "halt" or defined($power_off)) { 2201576f627cSSteven Rostedt if (defined($poweroff_after_halt)) { 2202576f627cSSteven Rostedt sleep $poweroff_after_halt; 2203576f627cSSteven Rostedt run_command "$power_off"; 2204576f627cSSteven Rostedt } 2205576f627cSSteven Rostedt } else { 220675c3fda7SSteven Rostedt # nope? the zap it! 2207a75fececSSteven Rostedt run_command "$power_off"; 220875c3fda7SSteven Rostedt } 220975c3fda7SSteven Rostedt} 221075c3fda7SSteven Rostedt 22115f9b6cedSSteven Rostedtsub success { 22125f9b6cedSSteven Rostedt my ($i) = @_; 22135f9b6cedSSteven Rostedt 2214921ed4c7SSteven Rostedt if (defined($post_test)) { 2215921ed4c7SSteven Rostedt run_command $post_test; 2216921ed4c7SSteven Rostedt } 2217921ed4c7SSteven Rostedt 2218e48c5293SSteven Rostedt $successes++; 2219e48c5293SSteven Rostedt 22209064af52SSteven Rostedt my $name = ""; 22219064af52SSteven Rostedt 22229064af52SSteven Rostedt if (defined($test_name)) { 22239064af52SSteven Rostedt $name = " ($test_name)"; 22249064af52SSteven Rostedt } 22259064af52SSteven Rostedt 22265f9b6cedSSteven Rostedt doprint "\n\n*******************************************\n"; 22275f9b6cedSSteven Rostedt doprint "*******************************************\n"; 22289064af52SSteven Rostedt doprint "KTEST RESULT: TEST $i$name SUCCESS!!!! **\n"; 22295f9b6cedSSteven Rostedt doprint "*******************************************\n"; 22305f9b6cedSSteven Rostedt doprint "*******************************************\n"; 22315f9b6cedSSteven Rostedt 2232de5b6e3bSRabin Vincent if (defined($store_successes)) { 2233de5b6e3bSRabin Vincent save_logs "success", $store_successes; 2234de5b6e3bSRabin Vincent } 2235de5b6e3bSRabin Vincent 2236576f627cSSteven Rostedt if ($i != $opt{"NUM_TESTS"} && !do_not_reboot) { 2237a75fececSSteven Rostedt doprint "Reboot and wait $sleep_time seconds\n"; 2238bc7c5803SSteven Rostedt reboot_to_good $sleep_time; 22395f9b6cedSSteven Rostedt } 22405f9b6cedSSteven Rostedt} 22415f9b6cedSSteven Rostedt 2242c960bb9fSSteven Rostedtsub answer_bisect { 2243c960bb9fSSteven Rostedt for (;;) { 2244c960bb9fSSteven Rostedt doprint "Pass or fail? [p/f]"; 2245c960bb9fSSteven Rostedt my $ans = <STDIN>; 2246c960bb9fSSteven Rostedt chomp $ans; 2247c960bb9fSSteven Rostedt if ($ans eq "p" || $ans eq "P") { 2248c960bb9fSSteven Rostedt return 1; 2249c960bb9fSSteven Rostedt } elsif ($ans eq "f" || $ans eq "F") { 2250c960bb9fSSteven Rostedt return 0; 2251c960bb9fSSteven Rostedt } else { 2252c960bb9fSSteven Rostedt print "Please answer 'P' or 'F'\n"; 2253c960bb9fSSteven Rostedt } 2254c960bb9fSSteven Rostedt } 2255c960bb9fSSteven Rostedt} 2256c960bb9fSSteven Rostedt 22575a391fbfSSteven Rostedtsub child_run_test { 22587faafbd6SSteven Rostedt my $failed = 0; 22595a391fbfSSteven Rostedt 22607faafbd6SSteven Rostedt # child should have no power 2261a75fececSSteven Rostedt $reboot_on_error = 0; 2262a75fececSSteven Rostedt $poweroff_on_error = 0; 2263a75fececSSteven Rostedt $die_on_failure = 1; 22647faafbd6SSteven Rostedt 2265a9dd5d63SRabin Vincent $redirect = "$testlog"; 22667faafbd6SSteven Rostedt run_command $run_test or $failed = 1; 2267a9dd5d63SRabin Vincent undef $redirect; 2268a9dd5d63SRabin Vincent 22695a391fbfSSteven Rostedt exit $failed; 22705a391fbfSSteven Rostedt} 22715a391fbfSSteven Rostedt 22725a391fbfSSteven Rostedtmy $child_done; 22735a391fbfSSteven Rostedt 22745a391fbfSSteven Rostedtsub child_finished { 22755a391fbfSSteven Rostedt $child_done = 1; 22765a391fbfSSteven Rostedt} 22775a391fbfSSteven Rostedt 22785a391fbfSSteven Rostedtsub do_run_test { 22795a391fbfSSteven Rostedt my $child_pid; 22805a391fbfSSteven Rostedt my $child_exit; 22815a391fbfSSteven Rostedt my $line; 22825a391fbfSSteven Rostedt my $full_line; 22835a391fbfSSteven Rostedt my $bug = 0; 22849b1d367dSSteven Rostedt my $bug_ignored = 0; 22855a391fbfSSteven Rostedt 22867faafbd6SSteven Rostedt wait_for_monitor 1; 22875a391fbfSSteven Rostedt 22887faafbd6SSteven Rostedt doprint "run test $run_test\n"; 22895a391fbfSSteven Rostedt 22905a391fbfSSteven Rostedt $child_done = 0; 22915a391fbfSSteven Rostedt 22925a391fbfSSteven Rostedt $SIG{CHLD} = qw(child_finished); 22935a391fbfSSteven Rostedt 22945a391fbfSSteven Rostedt $child_pid = fork; 22955a391fbfSSteven Rostedt 22965a391fbfSSteven Rostedt child_run_test if (!$child_pid); 22975a391fbfSSteven Rostedt 22985a391fbfSSteven Rostedt $full_line = ""; 22995a391fbfSSteven Rostedt 23005a391fbfSSteven Rostedt do { 23017faafbd6SSteven Rostedt $line = wait_for_input($monitor_fp, 1); 23025a391fbfSSteven Rostedt if (defined($line)) { 23035a391fbfSSteven Rostedt 23045a391fbfSSteven Rostedt # we are not guaranteed to get a full line 23055a391fbfSSteven Rostedt $full_line .= $line; 23068ea0e063SSteven Rostedt doprint $line; 23075a391fbfSSteven Rostedt 23085a391fbfSSteven Rostedt if ($full_line =~ /call trace:/i) { 23099b1d367dSSteven Rostedt if ($ignore_errors) { 23109b1d367dSSteven Rostedt $bug_ignored = 1; 23119b1d367dSSteven Rostedt } else { 23125a391fbfSSteven Rostedt $bug = 1; 23135a391fbfSSteven Rostedt } 23149b1d367dSSteven Rostedt } 23155a391fbfSSteven Rostedt 23165a391fbfSSteven Rostedt if ($full_line =~ /Kernel panic -/) { 23175a391fbfSSteven Rostedt $bug = 1; 23185a391fbfSSteven Rostedt } 23195a391fbfSSteven Rostedt 23205a391fbfSSteven Rostedt if ($line =~ /\n/) { 23215a391fbfSSteven Rostedt $full_line = ""; 23225a391fbfSSteven Rostedt } 23235a391fbfSSteven Rostedt } 23245a391fbfSSteven Rostedt } while (!$child_done && !$bug); 23255a391fbfSSteven Rostedt 23269b1d367dSSteven Rostedt if (!$bug && $bug_ignored) { 23279b1d367dSSteven Rostedt doprint "WARNING: Call Trace detected but ignored due to IGNORE_ERRORS=1\n"; 23289b1d367dSSteven Rostedt } 23299b1d367dSSteven Rostedt 23305a391fbfSSteven Rostedt if ($bug) { 23318ea0e063SSteven Rostedt my $failure_start = time; 23328ea0e063SSteven Rostedt my $now; 23338ea0e063SSteven Rostedt do { 23348ea0e063SSteven Rostedt $line = wait_for_input($monitor_fp, 1); 23358ea0e063SSteven Rostedt if (defined($line)) { 23368ea0e063SSteven Rostedt doprint $line; 23378ea0e063SSteven Rostedt } 23388ea0e063SSteven Rostedt $now = time; 23398ea0e063SSteven Rostedt if ($now - $failure_start >= $stop_after_failure) { 23408ea0e063SSteven Rostedt last; 23418ea0e063SSteven Rostedt } 23428ea0e063SSteven Rostedt } while (defined($line)); 23438ea0e063SSteven Rostedt 23445a391fbfSSteven Rostedt doprint "Detected kernel crash!\n"; 23455a391fbfSSteven Rostedt # kill the child with extreme prejudice 23465a391fbfSSteven Rostedt kill 9, $child_pid; 23475a391fbfSSteven Rostedt } 23485a391fbfSSteven Rostedt 23495a391fbfSSteven Rostedt waitpid $child_pid, 0; 23505a391fbfSSteven Rostedt $child_exit = $?; 23515a391fbfSSteven Rostedt 2352c5dacb88SSteven Rostedt if (!$bug && $in_bisect) { 2353c5dacb88SSteven Rostedt if (defined($bisect_ret_good)) { 2354c5dacb88SSteven Rostedt if ($child_exit == $bisect_ret_good) { 2355c5dacb88SSteven Rostedt return 1; 2356c5dacb88SSteven Rostedt } 2357c5dacb88SSteven Rostedt } 2358c5dacb88SSteven Rostedt if (defined($bisect_ret_skip)) { 2359c5dacb88SSteven Rostedt if ($child_exit == $bisect_ret_skip) { 2360c5dacb88SSteven Rostedt return -1; 2361c5dacb88SSteven Rostedt } 2362c5dacb88SSteven Rostedt } 2363c5dacb88SSteven Rostedt if (defined($bisect_ret_abort)) { 2364c5dacb88SSteven Rostedt if ($child_exit == $bisect_ret_abort) { 2365c5dacb88SSteven Rostedt fail "test abort" and return -2; 2366c5dacb88SSteven Rostedt } 2367c5dacb88SSteven Rostedt } 2368c5dacb88SSteven Rostedt if (defined($bisect_ret_bad)) { 2369c5dacb88SSteven Rostedt if ($child_exit == $bisect_ret_skip) { 2370c5dacb88SSteven Rostedt return 0; 2371c5dacb88SSteven Rostedt } 2372c5dacb88SSteven Rostedt } 2373c5dacb88SSteven Rostedt if (defined($bisect_ret_default)) { 2374c5dacb88SSteven Rostedt if ($bisect_ret_default eq "good") { 2375c5dacb88SSteven Rostedt return 1; 2376c5dacb88SSteven Rostedt } elsif ($bisect_ret_default eq "bad") { 2377c5dacb88SSteven Rostedt return 0; 2378c5dacb88SSteven Rostedt } elsif ($bisect_ret_default eq "skip") { 2379c5dacb88SSteven Rostedt return -1; 2380c5dacb88SSteven Rostedt } elsif ($bisect_ret_default eq "abort") { 2381c5dacb88SSteven Rostedt return -2; 2382c5dacb88SSteven Rostedt } else { 2383c5dacb88SSteven Rostedt fail "unknown default action: $bisect_ret_default" 2384c5dacb88SSteven Rostedt and return -2; 2385c5dacb88SSteven Rostedt } 2386c5dacb88SSteven Rostedt } 2387c5dacb88SSteven Rostedt } 2388c5dacb88SSteven Rostedt 23895a391fbfSSteven Rostedt if ($bug || $child_exit) { 23902b7d9b21SSteven Rostedt return 0 if $in_bisect; 23912b7d9b21SSteven Rostedt fail "test failed" and return 0; 23925a391fbfSSteven Rostedt } 23932b7d9b21SSteven Rostedt return 1; 23945a391fbfSSteven Rostedt} 23955a391fbfSSteven Rostedt 2396a75fececSSteven Rostedtsub run_git_bisect { 2397a75fececSSteven Rostedt my ($command) = @_; 2398a75fececSSteven Rostedt 2399a75fececSSteven Rostedt doprint "$command ... "; 2400a75fececSSteven Rostedt 2401a75fececSSteven Rostedt my $output = `$command 2>&1`; 2402a75fececSSteven Rostedt my $ret = $?; 2403a75fececSSteven Rostedt 2404a75fececSSteven Rostedt logit $output; 2405a75fececSSteven Rostedt 2406a75fececSSteven Rostedt if ($ret) { 2407a75fececSSteven Rostedt doprint "FAILED\n"; 2408a75fececSSteven Rostedt dodie "Failed to git bisect"; 2409a75fececSSteven Rostedt } 2410a75fececSSteven Rostedt 2411a75fececSSteven Rostedt doprint "SUCCESS\n"; 2412a75fececSSteven Rostedt if ($output =~ m/^(Bisecting: .*\(roughly \d+ steps?\))\s+\[([[:xdigit:]]+)\]/) { 2413a75fececSSteven Rostedt doprint "$1 [$2]\n"; 2414a75fececSSteven Rostedt } elsif ($output =~ m/^([[:xdigit:]]+) is the first bad commit/) { 2415b5f4aea6SSteven Rostedt $bisect_bad_commit = $1; 2416a75fececSSteven Rostedt doprint "Found bad commit... $1\n"; 2417a75fececSSteven Rostedt return 0; 2418a75fececSSteven Rostedt } else { 2419a75fececSSteven Rostedt # we already logged it, just print it now. 2420a75fececSSteven Rostedt print $output; 2421a75fececSSteven Rostedt } 2422a75fececSSteven Rostedt 2423a75fececSSteven Rostedt return 1; 2424a75fececSSteven Rostedt} 2425a75fececSSteven Rostedt 2426c23dca7cSSteven Rostedtsub bisect_reboot { 2427c23dca7cSSteven Rostedt doprint "Reboot and sleep $bisect_sleep_time seconds\n"; 2428bc7c5803SSteven Rostedt reboot_to_good $bisect_sleep_time; 2429c23dca7cSSteven Rostedt} 2430c23dca7cSSteven Rostedt 2431c23dca7cSSteven Rostedt# returns 1 on success, 0 on failure, -1 on skip 24320a05c769SSteven Rostedtsub run_bisect_test { 24330a05c769SSteven Rostedt my ($type, $buildtype) = @_; 24345f9b6cedSSteven Rostedt 24352b7d9b21SSteven Rostedt my $failed = 0; 24365f9b6cedSSteven Rostedt my $result; 24375f9b6cedSSteven Rostedt my $output; 24385f9b6cedSSteven Rostedt my $ret; 24395f9b6cedSSteven Rostedt 24400a05c769SSteven Rostedt $in_bisect = 1; 24410a05c769SSteven Rostedt 24420a05c769SSteven Rostedt build $buildtype or $failed = 1; 24435f9b6cedSSteven Rostedt 24445f9b6cedSSteven Rostedt if ($type ne "build") { 2445c23dca7cSSteven Rostedt if ($failed && $bisect_skip) { 2446c23dca7cSSteven Rostedt $in_bisect = 0; 2447c23dca7cSSteven Rostedt return -1; 2448c23dca7cSSteven Rostedt } 24497faafbd6SSteven Rostedt dodie "Failed on build" if $failed; 24505f9b6cedSSteven Rostedt 24515f9b6cedSSteven Rostedt # Now boot the box 2452ddf607e5SSteven Rostedt start_monitor_and_boot or $failed = 1; 24535f9b6cedSSteven Rostedt 24545f9b6cedSSteven Rostedt if ($type ne "boot") { 2455c23dca7cSSteven Rostedt if ($failed && $bisect_skip) { 2456c23dca7cSSteven Rostedt end_monitor; 2457c23dca7cSSteven Rostedt bisect_reboot; 2458c23dca7cSSteven Rostedt $in_bisect = 0; 2459c23dca7cSSteven Rostedt return -1; 2460c23dca7cSSteven Rostedt } 24617faafbd6SSteven Rostedt dodie "Failed on boot" if $failed; 24625a391fbfSSteven Rostedt 24632b7d9b21SSteven Rostedt do_run_test or $failed = 1; 24645f9b6cedSSteven Rostedt } 24657faafbd6SSteven Rostedt end_monitor; 24665f9b6cedSSteven Rostedt } 24675f9b6cedSSteven Rostedt 24685f9b6cedSSteven Rostedt if ($failed) { 24690a05c769SSteven Rostedt $result = 0; 24705f9b6cedSSteven Rostedt } else { 24710a05c769SSteven Rostedt $result = 1; 24725f9b6cedSSteven Rostedt } 24734025bc62SSteven Rostedt 24744025bc62SSteven Rostedt # reboot the box to a kernel we can ssh to 24754025bc62SSteven Rostedt if ($type ne "build") { 24764025bc62SSteven Rostedt bisect_reboot; 24774025bc62SSteven Rostedt } 24780a05c769SSteven Rostedt $in_bisect = 0; 24790a05c769SSteven Rostedt 24800a05c769SSteven Rostedt return $result; 24810a05c769SSteven Rostedt} 24820a05c769SSteven Rostedt 24830a05c769SSteven Rostedtsub run_bisect { 24840a05c769SSteven Rostedt my ($type) = @_; 24850a05c769SSteven Rostedt my $buildtype = "oldconfig"; 24860a05c769SSteven Rostedt 24870a05c769SSteven Rostedt # We should have a minconfig to use? 24880a05c769SSteven Rostedt if (defined($minconfig)) { 24890a05c769SSteven Rostedt $buildtype = "useconfig:$minconfig"; 24900a05c769SSteven Rostedt } 24910a05c769SSteven Rostedt 24920a05c769SSteven Rostedt my $ret = run_bisect_test $type, $buildtype; 24930a05c769SSteven Rostedt 2494c960bb9fSSteven Rostedt if ($bisect_manual) { 2495c960bb9fSSteven Rostedt $ret = answer_bisect; 2496c960bb9fSSteven Rostedt } 24975f9b6cedSSteven Rostedt 2498d6ce2a0bSSteven Rostedt # Are we looking for where it worked, not failed? 24995158ba3eSRuss Dill if ($reverse_bisect && $ret >= 0) { 25000a05c769SSteven Rostedt $ret = !$ret; 2501d6ce2a0bSSteven Rostedt } 2502d6ce2a0bSSteven Rostedt 2503c23dca7cSSteven Rostedt if ($ret > 0) { 25040a05c769SSteven Rostedt return "good"; 2505c23dca7cSSteven Rostedt } elsif ($ret == 0) { 25060a05c769SSteven Rostedt return "bad"; 2507c23dca7cSSteven Rostedt } elsif ($bisect_skip) { 2508c23dca7cSSteven Rostedt doprint "HIT A BAD COMMIT ... SKIPPING\n"; 2509c23dca7cSSteven Rostedt return "skip"; 25100a05c769SSteven Rostedt } 25115f9b6cedSSteven Rostedt} 25125f9b6cedSSteven Rostedt 2513dad98754SSteven Rostedtsub update_bisect_replay { 2514dad98754SSteven Rostedt my $tmp_log = "$tmpdir/ktest_bisect_log"; 2515dad98754SSteven Rostedt run_command "git bisect log > $tmp_log" or 2516dad98754SSteven Rostedt die "can't create bisect log"; 2517dad98754SSteven Rostedt return $tmp_log; 2518dad98754SSteven Rostedt} 2519dad98754SSteven Rostedt 25205f9b6cedSSteven Rostedtsub bisect { 25215f9b6cedSSteven Rostedt my ($i) = @_; 25225f9b6cedSSteven Rostedt 25235f9b6cedSSteven Rostedt my $result; 25245f9b6cedSSteven Rostedt 2525b5f4aea6SSteven Rostedt die "BISECT_GOOD[$i] not defined\n" if (!defined($bisect_good)); 2526b5f4aea6SSteven Rostedt die "BISECT_BAD[$i] not defined\n" if (!defined($bisect_bad)); 2527b5f4aea6SSteven Rostedt die "BISECT_TYPE[$i] not defined\n" if (!defined($bisect_type)); 25285f9b6cedSSteven Rostedt 2529b5f4aea6SSteven Rostedt my $good = $bisect_good; 2530b5f4aea6SSteven Rostedt my $bad = $bisect_bad; 2531b5f4aea6SSteven Rostedt my $type = $bisect_type; 2532b5f4aea6SSteven Rostedt my $start = $bisect_start; 2533b5f4aea6SSteven Rostedt my $replay = $bisect_replay; 2534b5f4aea6SSteven Rostedt my $start_files = $bisect_files; 25353410f6fdSSteven Rostedt 25363410f6fdSSteven Rostedt if (defined($start_files)) { 25373410f6fdSSteven Rostedt $start_files = " -- " . $start_files; 25383410f6fdSSteven Rostedt } else { 25393410f6fdSSteven Rostedt $start_files = ""; 25403410f6fdSSteven Rostedt } 25415f9b6cedSSteven Rostedt 2542a57419b3SSteven Rostedt # convert to true sha1's 2543a57419b3SSteven Rostedt $good = get_sha1($good); 2544a57419b3SSteven Rostedt $bad = get_sha1($bad); 2545a57419b3SSteven Rostedt 2546b5f4aea6SSteven Rostedt if (defined($bisect_reverse) && $bisect_reverse == 1) { 2547d6ce2a0bSSteven Rostedt doprint "Performing a reverse bisect (bad is good, good is bad!)\n"; 2548d6ce2a0bSSteven Rostedt $reverse_bisect = 1; 2549d6ce2a0bSSteven Rostedt } else { 2550d6ce2a0bSSteven Rostedt $reverse_bisect = 0; 2551d6ce2a0bSSteven Rostedt } 2552d6ce2a0bSSteven Rostedt 25535a391fbfSSteven Rostedt # Can't have a test without having a test to run 25545a391fbfSSteven Rostedt if ($type eq "test" && !defined($run_test)) { 25555a391fbfSSteven Rostedt $type = "boot"; 25565a391fbfSSteven Rostedt } 25575a391fbfSSteven Rostedt 2558dad98754SSteven Rostedt # Check if a bisect was running 2559dad98754SSteven Rostedt my $bisect_start_file = "$builddir/.git/BISECT_START"; 2560dad98754SSteven Rostedt 2561b5f4aea6SSteven Rostedt my $check = $bisect_check; 2562dad98754SSteven Rostedt my $do_check = defined($check) && $check ne "0"; 2563dad98754SSteven Rostedt 2564dad98754SSteven Rostedt if ( -f $bisect_start_file ) { 2565dad98754SSteven Rostedt print "Bisect in progress found\n"; 2566dad98754SSteven Rostedt if ($do_check) { 2567dad98754SSteven Rostedt print " If you say yes, then no checks of good or bad will be done\n"; 2568dad98754SSteven Rostedt } 2569dad98754SSteven Rostedt if (defined($replay)) { 2570dad98754SSteven Rostedt print "** BISECT_REPLAY is defined in config file **"; 2571dad98754SSteven Rostedt print " Ignore config option and perform new git bisect log?\n"; 2572dad98754SSteven Rostedt if (read_ync " (yes, no, or cancel) ") { 2573dad98754SSteven Rostedt $replay = update_bisect_replay; 2574dad98754SSteven Rostedt $do_check = 0; 2575dad98754SSteven Rostedt } 2576dad98754SSteven Rostedt } elsif (read_yn "read git log and continue?") { 2577dad98754SSteven Rostedt $replay = update_bisect_replay; 2578dad98754SSteven Rostedt $do_check = 0; 2579dad98754SSteven Rostedt } 2580dad98754SSteven Rostedt } 2581dad98754SSteven Rostedt 2582dad98754SSteven Rostedt if ($do_check) { 2583a75fececSSteven Rostedt 2584a75fececSSteven Rostedt # get current HEAD 2585a57419b3SSteven Rostedt my $head = get_sha1("HEAD"); 2586a75fececSSteven Rostedt 2587a75fececSSteven Rostedt if ($check ne "good") { 2588a75fececSSteven Rostedt doprint "TESTING BISECT BAD [$bad]\n"; 2589a75fececSSteven Rostedt run_command "git checkout $bad" or 2590a75fececSSteven Rostedt die "Failed to checkout $bad"; 2591a75fececSSteven Rostedt 2592a75fececSSteven Rostedt $result = run_bisect $type; 2593a75fececSSteven Rostedt 2594a75fececSSteven Rostedt if ($result ne "bad") { 2595a75fececSSteven Rostedt fail "Tested BISECT_BAD [$bad] and it succeeded" and return 0; 2596a75fececSSteven Rostedt } 2597a75fececSSteven Rostedt } 2598a75fececSSteven Rostedt 2599a75fececSSteven Rostedt if ($check ne "bad") { 2600a75fececSSteven Rostedt doprint "TESTING BISECT GOOD [$good]\n"; 2601a75fececSSteven Rostedt run_command "git checkout $good" or 2602a75fececSSteven Rostedt die "Failed to checkout $good"; 2603a75fececSSteven Rostedt 2604a75fececSSteven Rostedt $result = run_bisect $type; 2605a75fececSSteven Rostedt 2606a75fececSSteven Rostedt if ($result ne "good") { 2607a75fececSSteven Rostedt fail "Tested BISECT_GOOD [$good] and it failed" and return 0; 2608a75fececSSteven Rostedt } 2609a75fececSSteven Rostedt } 2610a75fececSSteven Rostedt 2611a75fececSSteven Rostedt # checkout where we started 2612a75fececSSteven Rostedt run_command "git checkout $head" or 2613a75fececSSteven Rostedt die "Failed to checkout $head"; 2614a75fececSSteven Rostedt } 2615a75fececSSteven Rostedt 26163410f6fdSSteven Rostedt run_command "git bisect start$start_files" or 2617a75fececSSteven Rostedt dodie "could not start bisect"; 2618a75fececSSteven Rostedt 2619a75fececSSteven Rostedt run_command "git bisect good $good" or 2620a75fececSSteven Rostedt dodie "could not set bisect good to $good"; 2621a75fececSSteven Rostedt 2622a75fececSSteven Rostedt run_git_bisect "git bisect bad $bad" or 2623a75fececSSteven Rostedt dodie "could not set bisect bad to $bad"; 2624a75fececSSteven Rostedt 2625a75fececSSteven Rostedt if (defined($replay)) { 2626a75fececSSteven Rostedt run_command "git bisect replay $replay" or 2627a75fececSSteven Rostedt dodie "failed to run replay"; 2628a75fececSSteven Rostedt } 2629a75fececSSteven Rostedt 2630a75fececSSteven Rostedt if (defined($start)) { 2631a75fececSSteven Rostedt run_command "git checkout $start" or 2632a75fececSSteven Rostedt dodie "failed to checkout $start"; 2633a75fececSSteven Rostedt } 2634a75fececSSteven Rostedt 2635a75fececSSteven Rostedt my $test; 26365f9b6cedSSteven Rostedt do { 26375f9b6cedSSteven Rostedt $result = run_bisect $type; 2638a75fececSSteven Rostedt $test = run_git_bisect "git bisect $result"; 2639a75fececSSteven Rostedt } while ($test); 26405f9b6cedSSteven Rostedt 26415f9b6cedSSteven Rostedt run_command "git bisect log" or 26425f9b6cedSSteven Rostedt dodie "could not capture git bisect log"; 26435f9b6cedSSteven Rostedt 26445f9b6cedSSteven Rostedt run_command "git bisect reset" or 26455f9b6cedSSteven Rostedt dodie "could not reset git bisect"; 26465f9b6cedSSteven Rostedt 2647b5f4aea6SSteven Rostedt doprint "Bad commit was [$bisect_bad_commit]\n"; 26485f9b6cedSSteven Rostedt 26490a05c769SSteven Rostedt success $i; 26500a05c769SSteven Rostedt} 26510a05c769SSteven Rostedt 2652cf79fab6SSteven Rostedt# config_ignore holds the configs that were set (or unset) for 2653cf79fab6SSteven Rostedt# a good config and we will ignore these configs for the rest 2654cf79fab6SSteven Rostedt# of a config bisect. These configs stay as they were. 26550a05c769SSteven Rostedtmy %config_ignore; 2656cf79fab6SSteven Rostedt 2657cf79fab6SSteven Rostedt# config_set holds what all configs were set as. 26580a05c769SSteven Rostedtmy %config_set; 26590a05c769SSteven Rostedt 2660cf79fab6SSteven Rostedt# config_off holds the set of configs that the bad config had disabled. 2661cf79fab6SSteven Rostedt# We need to record them and set them in the .config when running 2662fb16d891SAdam Lee# olddefconfig, because olddefconfig keeps the defaults. 2663cf79fab6SSteven Rostedtmy %config_off; 2664cf79fab6SSteven Rostedt 2665cf79fab6SSteven Rostedt# config_off_tmp holds a set of configs to turn off for now 2666cf79fab6SSteven Rostedtmy @config_off_tmp; 2667cf79fab6SSteven Rostedt 2668cf79fab6SSteven Rostedt# config_list is the set of configs that are being tested 26690a05c769SSteven Rostedtmy %config_list; 26700a05c769SSteven Rostedtmy %null_config; 26710a05c769SSteven Rostedt 26720a05c769SSteven Rostedtmy %dependency; 26730a05c769SSteven Rostedt 26744c4ab120SSteven Rostedtsub assign_configs { 26754c4ab120SSteven Rostedt my ($hash, $config) = @_; 26760a05c769SSteven Rostedt 26770a05c769SSteven Rostedt open (IN, $config) 26780a05c769SSteven Rostedt or dodie "Failed to read $config"; 26790a05c769SSteven Rostedt 26800a05c769SSteven Rostedt while (<IN>) { 26819bf71749SSteven Rostedt if (/^((CONFIG\S*)=.*)/) { 26824c4ab120SSteven Rostedt ${$hash}{$2} = $1; 26830a05c769SSteven Rostedt } 26840a05c769SSteven Rostedt } 26850a05c769SSteven Rostedt 26860a05c769SSteven Rostedt close(IN); 26870a05c769SSteven Rostedt} 26880a05c769SSteven Rostedt 26894c4ab120SSteven Rostedtsub process_config_ignore { 26904c4ab120SSteven Rostedt my ($config) = @_; 26914c4ab120SSteven Rostedt 26924c4ab120SSteven Rostedt assign_configs \%config_ignore, $config; 26934c4ab120SSteven Rostedt} 26944c4ab120SSteven Rostedt 26950a05c769SSteven Rostedtsub read_current_config { 26960a05c769SSteven Rostedt my ($config_ref) = @_; 26970a05c769SSteven Rostedt 26980a05c769SSteven Rostedt %{$config_ref} = (); 26990a05c769SSteven Rostedt undef %{$config_ref}; 27000a05c769SSteven Rostedt 27010a05c769SSteven Rostedt my @key = keys %{$config_ref}; 27020a05c769SSteven Rostedt if ($#key >= 0) { 27030a05c769SSteven Rostedt print "did not delete!\n"; 27040a05c769SSteven Rostedt exit; 27050a05c769SSteven Rostedt } 27060a05c769SSteven Rostedt open (IN, "$output_config"); 27070a05c769SSteven Rostedt 27080a05c769SSteven Rostedt while (<IN>) { 27090a05c769SSteven Rostedt if (/^(CONFIG\S+)=(.*)/) { 27100a05c769SSteven Rostedt ${$config_ref}{$1} = $2; 27110a05c769SSteven Rostedt } 27120a05c769SSteven Rostedt } 27130a05c769SSteven Rostedt close(IN); 27140a05c769SSteven Rostedt} 27150a05c769SSteven Rostedt 27160a05c769SSteven Rostedtsub get_dependencies { 27170a05c769SSteven Rostedt my ($config) = @_; 27180a05c769SSteven Rostedt 27190a05c769SSteven Rostedt my $arr = $dependency{$config}; 27200a05c769SSteven Rostedt if (!defined($arr)) { 27210a05c769SSteven Rostedt return (); 27220a05c769SSteven Rostedt } 27230a05c769SSteven Rostedt 27240a05c769SSteven Rostedt my @deps = @{$arr}; 27250a05c769SSteven Rostedt 27260a05c769SSteven Rostedt foreach my $dep (@{$arr}) { 27270a05c769SSteven Rostedt print "ADD DEP $dep\n"; 27280a05c769SSteven Rostedt @deps = (@deps, get_dependencies $dep); 27290a05c769SSteven Rostedt } 27300a05c769SSteven Rostedt 27310a05c769SSteven Rostedt return @deps; 27320a05c769SSteven Rostedt} 27330a05c769SSteven Rostedt 27340a05c769SSteven Rostedtsub create_config { 27350a05c769SSteven Rostedt my @configs = @_; 27360a05c769SSteven Rostedt 27370a05c769SSteven Rostedt open(OUT, ">$output_config") or dodie "Can not write to $output_config"; 27380a05c769SSteven Rostedt 27390a05c769SSteven Rostedt foreach my $config (@configs) { 27400a05c769SSteven Rostedt print OUT "$config_set{$config}\n"; 27410a05c769SSteven Rostedt my @deps = get_dependencies $config; 27420a05c769SSteven Rostedt foreach my $dep (@deps) { 27430a05c769SSteven Rostedt print OUT "$config_set{$dep}\n"; 27440a05c769SSteven Rostedt } 27450a05c769SSteven Rostedt } 27460a05c769SSteven Rostedt 2747cf79fab6SSteven Rostedt # turn off configs to keep off 2748cf79fab6SSteven Rostedt foreach my $config (keys %config_off) { 2749cf79fab6SSteven Rostedt print OUT "# $config is not set\n"; 2750cf79fab6SSteven Rostedt } 2751cf79fab6SSteven Rostedt 2752cf79fab6SSteven Rostedt # turn off configs that should be off for now 2753cf79fab6SSteven Rostedt foreach my $config (@config_off_tmp) { 2754cf79fab6SSteven Rostedt print OUT "# $config is not set\n"; 2755cf79fab6SSteven Rostedt } 2756cf79fab6SSteven Rostedt 27570a05c769SSteven Rostedt foreach my $config (keys %config_ignore) { 27580a05c769SSteven Rostedt print OUT "$config_ignore{$config}\n"; 27590a05c769SSteven Rostedt } 27600a05c769SSteven Rostedt close(OUT); 27610a05c769SSteven Rostedt 2762fcb3f16aSSteven Rostedt make_oldconfig; 27630a05c769SSteven Rostedt} 27640a05c769SSteven Rostedt 27650a05c769SSteven Rostedtsub compare_configs { 27660a05c769SSteven Rostedt my (%a, %b) = @_; 27670a05c769SSteven Rostedt 27680a05c769SSteven Rostedt foreach my $item (keys %a) { 27690a05c769SSteven Rostedt if (!defined($b{$item})) { 27700a05c769SSteven Rostedt print "diff $item\n"; 27710a05c769SSteven Rostedt return 1; 27720a05c769SSteven Rostedt } 27730a05c769SSteven Rostedt delete $b{$item}; 27740a05c769SSteven Rostedt } 27750a05c769SSteven Rostedt 27760a05c769SSteven Rostedt my @keys = keys %b; 27770a05c769SSteven Rostedt if ($#keys) { 27780a05c769SSteven Rostedt print "diff2 $keys[0]\n"; 27790a05c769SSteven Rostedt } 27800a05c769SSteven Rostedt return -1 if ($#keys >= 0); 27810a05c769SSteven Rostedt 27820a05c769SSteven Rostedt return 0; 27830a05c769SSteven Rostedt} 27840a05c769SSteven Rostedt 27850a05c769SSteven Rostedtsub run_config_bisect_test { 27860a05c769SSteven Rostedt my ($type) = @_; 27870a05c769SSteven Rostedt 27880a05c769SSteven Rostedt return run_bisect_test $type, "oldconfig"; 27890a05c769SSteven Rostedt} 27900a05c769SSteven Rostedt 27910a05c769SSteven Rostedtsub process_passed { 27920a05c769SSteven Rostedt my (%configs) = @_; 27930a05c769SSteven Rostedt 27940a05c769SSteven Rostedt doprint "These configs had no failure: (Enabling them for further compiles)\n"; 27950a05c769SSteven Rostedt # Passed! All these configs are part of a good compile. 27960a05c769SSteven Rostedt # Add them to the min options. 27970a05c769SSteven Rostedt foreach my $config (keys %configs) { 27980a05c769SSteven Rostedt if (defined($config_list{$config})) { 27990a05c769SSteven Rostedt doprint " removing $config\n"; 28000a05c769SSteven Rostedt $config_ignore{$config} = $config_list{$config}; 28010a05c769SSteven Rostedt delete $config_list{$config}; 28020a05c769SSteven Rostedt } 28030a05c769SSteven Rostedt } 2804f1a27850SSteven Rostedt doprint "config copied to $outputdir/config_good\n"; 2805f1a27850SSteven Rostedt run_command "cp -f $output_config $outputdir/config_good"; 28060a05c769SSteven Rostedt} 28070a05c769SSteven Rostedt 28080a05c769SSteven Rostedtsub process_failed { 28090a05c769SSteven Rostedt my ($config) = @_; 28100a05c769SSteven Rostedt 28110a05c769SSteven Rostedt doprint "\n\n***************************************\n"; 28120a05c769SSteven Rostedt doprint "Found bad config: $config\n"; 28130a05c769SSteven Rostedt doprint "***************************************\n\n"; 28140a05c769SSteven Rostedt} 28150a05c769SSteven Rostedt 28160a05c769SSteven Rostedtsub run_config_bisect { 28170a05c769SSteven Rostedt 28180a05c769SSteven Rostedt my @start_list = keys %config_list; 28190a05c769SSteven Rostedt 28200a05c769SSteven Rostedt if ($#start_list < 0) { 28210a05c769SSteven Rostedt doprint "No more configs to test!!!\n"; 28220a05c769SSteven Rostedt return -1; 28230a05c769SSteven Rostedt } 28240a05c769SSteven Rostedt 28250a05c769SSteven Rostedt doprint "***** RUN TEST ***\n"; 2826b5f4aea6SSteven Rostedt my $type = $config_bisect_type; 28270a05c769SSteven Rostedt my $ret; 28280a05c769SSteven Rostedt my %current_config; 28290a05c769SSteven Rostedt 28300a05c769SSteven Rostedt my $count = $#start_list + 1; 28310a05c769SSteven Rostedt doprint " $count configs to test\n"; 28320a05c769SSteven Rostedt 28330a05c769SSteven Rostedt my $half = int($#start_list / 2); 28340a05c769SSteven Rostedt 28350a05c769SSteven Rostedt do { 28360a05c769SSteven Rostedt my @tophalf = @start_list[0 .. $half]; 28370a05c769SSteven Rostedt 2838cf79fab6SSteven Rostedt # keep the bottom half off 2839cf79fab6SSteven Rostedt if ($half < $#start_list) { 2840cf79fab6SSteven Rostedt @config_off_tmp = @start_list[$half + 1 .. $#start_list]; 2841cf79fab6SSteven Rostedt } else { 2842cf79fab6SSteven Rostedt @config_off_tmp = (); 2843cf79fab6SSteven Rostedt } 2844cf79fab6SSteven Rostedt 28450a05c769SSteven Rostedt create_config @tophalf; 28460a05c769SSteven Rostedt read_current_config \%current_config; 28470a05c769SSteven Rostedt 28480a05c769SSteven Rostedt $count = $#tophalf + 1; 28490a05c769SSteven Rostedt doprint "Testing $count configs\n"; 28500a05c769SSteven Rostedt my $found = 0; 28510a05c769SSteven Rostedt # make sure we test something 28520a05c769SSteven Rostedt foreach my $config (@tophalf) { 28530a05c769SSteven Rostedt if (defined($current_config{$config})) { 28540a05c769SSteven Rostedt logit " $config\n"; 28550a05c769SSteven Rostedt $found = 1; 28560a05c769SSteven Rostedt } 28570a05c769SSteven Rostedt } 28580a05c769SSteven Rostedt if (!$found) { 28590a05c769SSteven Rostedt # try the other half 28600a05c769SSteven Rostedt doprint "Top half produced no set configs, trying bottom half\n"; 2861cf79fab6SSteven Rostedt 2862cf79fab6SSteven Rostedt # keep the top half off 2863cf79fab6SSteven Rostedt @config_off_tmp = @tophalf; 28644c8cc55bSSteven Rostedt @tophalf = @start_list[$half + 1 .. $#start_list]; 2865cf79fab6SSteven Rostedt 28660a05c769SSteven Rostedt create_config @tophalf; 28670a05c769SSteven Rostedt read_current_config \%current_config; 28680a05c769SSteven Rostedt foreach my $config (@tophalf) { 28690a05c769SSteven Rostedt if (defined($current_config{$config})) { 28700a05c769SSteven Rostedt logit " $config\n"; 28710a05c769SSteven Rostedt $found = 1; 28720a05c769SSteven Rostedt } 28730a05c769SSteven Rostedt } 28740a05c769SSteven Rostedt if (!$found) { 28750a05c769SSteven Rostedt doprint "Failed: Can't make new config with current configs\n"; 28760a05c769SSteven Rostedt foreach my $config (@start_list) { 28770a05c769SSteven Rostedt doprint " CONFIG: $config\n"; 28780a05c769SSteven Rostedt } 28790a05c769SSteven Rostedt return -1; 28800a05c769SSteven Rostedt } 28810a05c769SSteven Rostedt $count = $#tophalf + 1; 28820a05c769SSteven Rostedt doprint "Testing $count configs\n"; 28830a05c769SSteven Rostedt } 28840a05c769SSteven Rostedt 28850a05c769SSteven Rostedt $ret = run_config_bisect_test $type; 2886c960bb9fSSteven Rostedt if ($bisect_manual) { 2887c960bb9fSSteven Rostedt $ret = answer_bisect; 2888c960bb9fSSteven Rostedt } 28890a05c769SSteven Rostedt if ($ret) { 28900a05c769SSteven Rostedt process_passed %current_config; 28910a05c769SSteven Rostedt return 0; 28920a05c769SSteven Rostedt } 28930a05c769SSteven Rostedt 28940a05c769SSteven Rostedt doprint "This config had a failure.\n"; 28950a05c769SSteven Rostedt doprint "Removing these configs that were not set in this config:\n"; 2896f1a27850SSteven Rostedt doprint "config copied to $outputdir/config_bad\n"; 2897f1a27850SSteven Rostedt run_command "cp -f $output_config $outputdir/config_bad"; 28980a05c769SSteven Rostedt 28990a05c769SSteven Rostedt # A config exists in this group that was bad. 29000a05c769SSteven Rostedt foreach my $config (keys %config_list) { 29010a05c769SSteven Rostedt if (!defined($current_config{$config})) { 29020a05c769SSteven Rostedt doprint " removing $config\n"; 29030a05c769SSteven Rostedt delete $config_list{$config}; 29040a05c769SSteven Rostedt } 29050a05c769SSteven Rostedt } 29060a05c769SSteven Rostedt 29070a05c769SSteven Rostedt @start_list = @tophalf; 29080a05c769SSteven Rostedt 29090a05c769SSteven Rostedt if ($#start_list == 0) { 29100a05c769SSteven Rostedt process_failed $start_list[0]; 29110a05c769SSteven Rostedt return 1; 29120a05c769SSteven Rostedt } 29130a05c769SSteven Rostedt 29140a05c769SSteven Rostedt # remove half the configs we are looking at and see if 29150a05c769SSteven Rostedt # they are good. 29160a05c769SSteven Rostedt $half = int($#start_list / 2); 29174c8cc55bSSteven Rostedt } while ($#start_list > 0); 29180a05c769SSteven Rostedt 2919c960bb9fSSteven Rostedt # we found a single config, try it again unless we are running manually 2920c960bb9fSSteven Rostedt 2921c960bb9fSSteven Rostedt if ($bisect_manual) { 2922c960bb9fSSteven Rostedt process_failed $start_list[0]; 2923c960bb9fSSteven Rostedt return 1; 2924c960bb9fSSteven Rostedt } 2925c960bb9fSSteven Rostedt 29260a05c769SSteven Rostedt my @tophalf = @start_list[0 .. 0]; 29270a05c769SSteven Rostedt 29280a05c769SSteven Rostedt $ret = run_config_bisect_test $type; 29290a05c769SSteven Rostedt if ($ret) { 29300a05c769SSteven Rostedt process_passed %current_config; 29310a05c769SSteven Rostedt return 0; 29320a05c769SSteven Rostedt } 29330a05c769SSteven Rostedt 29340a05c769SSteven Rostedt process_failed $start_list[0]; 29350a05c769SSteven Rostedt return 1; 29360a05c769SSteven Rostedt} 29370a05c769SSteven Rostedt 29380a05c769SSteven Rostedtsub config_bisect { 29390a05c769SSteven Rostedt my ($i) = @_; 29400a05c769SSteven Rostedt 2941b5f4aea6SSteven Rostedt my $start_config = $config_bisect; 29420a05c769SSteven Rostedt 29430a05c769SSteven Rostedt my $tmpconfig = "$tmpdir/use_config"; 29440a05c769SSteven Rostedt 294530f75da5SSteven Rostedt if (defined($config_bisect_good)) { 294630f75da5SSteven Rostedt process_config_ignore $config_bisect_good; 294730f75da5SSteven Rostedt } 294830f75da5SSteven Rostedt 29490a05c769SSteven Rostedt # Make the file with the bad config and the min config 29500a05c769SSteven Rostedt if (defined($minconfig)) { 29510a05c769SSteven Rostedt # read the min config for things to ignore 29520a05c769SSteven Rostedt run_command "cp $minconfig $tmpconfig" or 29530a05c769SSteven Rostedt dodie "failed to copy $minconfig to $tmpconfig"; 29540a05c769SSteven Rostedt } else { 29550a05c769SSteven Rostedt unlink $tmpconfig; 29560a05c769SSteven Rostedt } 29570a05c769SSteven Rostedt 29580a05c769SSteven Rostedt if (-f $tmpconfig) { 2959fcb3f16aSSteven Rostedt load_force_config($tmpconfig); 29600a05c769SSteven Rostedt process_config_ignore $tmpconfig; 29610a05c769SSteven Rostedt } 29620a05c769SSteven Rostedt 29630a05c769SSteven Rostedt # now process the start config 29640a05c769SSteven Rostedt run_command "cp $start_config $output_config" or 29650a05c769SSteven Rostedt dodie "failed to copy $start_config to $output_config"; 29660a05c769SSteven Rostedt 29670a05c769SSteven Rostedt # read directly what we want to check 29680a05c769SSteven Rostedt my %config_check; 29690a05c769SSteven Rostedt open (IN, $output_config) 2970f9dee311SMasanari Iida or dodie "failed to open $output_config"; 29710a05c769SSteven Rostedt 29720a05c769SSteven Rostedt while (<IN>) { 29730a05c769SSteven Rostedt if (/^((CONFIG\S*)=.*)/) { 29740a05c769SSteven Rostedt $config_check{$2} = $1; 29750a05c769SSteven Rostedt } 29760a05c769SSteven Rostedt } 29770a05c769SSteven Rostedt close(IN); 29780a05c769SSteven Rostedt 2979250bae8bSSteven Rostedt # Now run oldconfig with the minconfig 2980fcb3f16aSSteven Rostedt make_oldconfig; 29810a05c769SSteven Rostedt 29820a05c769SSteven Rostedt # check to see what we lost (or gained) 29830a05c769SSteven Rostedt open (IN, $output_config) 29840a05c769SSteven Rostedt or dodie "Failed to read $start_config"; 29850a05c769SSteven Rostedt 29860a05c769SSteven Rostedt my %removed_configs; 29870a05c769SSteven Rostedt my %added_configs; 29880a05c769SSteven Rostedt 29890a05c769SSteven Rostedt while (<IN>) { 29900a05c769SSteven Rostedt if (/^((CONFIG\S*)=.*)/) { 29910a05c769SSteven Rostedt # save off all options 29920a05c769SSteven Rostedt $config_set{$2} = $1; 29930a05c769SSteven Rostedt if (defined($config_check{$2})) { 29940a05c769SSteven Rostedt if (defined($config_ignore{$2})) { 29950a05c769SSteven Rostedt $removed_configs{$2} = $1; 29960a05c769SSteven Rostedt } else { 29970a05c769SSteven Rostedt $config_list{$2} = $1; 29980a05c769SSteven Rostedt } 29990a05c769SSteven Rostedt } elsif (!defined($config_ignore{$2})) { 30000a05c769SSteven Rostedt $added_configs{$2} = $1; 30010a05c769SSteven Rostedt $config_list{$2} = $1; 30020a05c769SSteven Rostedt } 3003cf79fab6SSteven Rostedt } elsif (/^# ((CONFIG\S*).*)/) { 3004cf79fab6SSteven Rostedt # Keep these configs disabled 3005cf79fab6SSteven Rostedt $config_set{$2} = $1; 3006cf79fab6SSteven Rostedt $config_off{$2} = $1; 30070a05c769SSteven Rostedt } 30080a05c769SSteven Rostedt } 30090a05c769SSteven Rostedt close(IN); 30100a05c769SSteven Rostedt 30110a05c769SSteven Rostedt my @confs = keys %removed_configs; 30120a05c769SSteven Rostedt if ($#confs >= 0) { 30130a05c769SSteven Rostedt doprint "Configs overridden by default configs and removed from check:\n"; 30140a05c769SSteven Rostedt foreach my $config (@confs) { 30150a05c769SSteven Rostedt doprint " $config\n"; 30160a05c769SSteven Rostedt } 30170a05c769SSteven Rostedt } 30180a05c769SSteven Rostedt @confs = keys %added_configs; 30190a05c769SSteven Rostedt if ($#confs >= 0) { 30200a05c769SSteven Rostedt doprint "Configs appearing in make oldconfig and added:\n"; 30210a05c769SSteven Rostedt foreach my $config (@confs) { 30220a05c769SSteven Rostedt doprint " $config\n"; 30230a05c769SSteven Rostedt } 30240a05c769SSteven Rostedt } 30250a05c769SSteven Rostedt 30260a05c769SSteven Rostedt my %config_test; 30270a05c769SSteven Rostedt my $once = 0; 30280a05c769SSteven Rostedt 3029cf79fab6SSteven Rostedt @config_off_tmp = (); 3030cf79fab6SSteven Rostedt 30310a05c769SSteven Rostedt # Sometimes kconfig does weird things. We must make sure 30320a05c769SSteven Rostedt # that the config we autocreate has everything we need 30330a05c769SSteven Rostedt # to test, otherwise we may miss testing configs, or 30340a05c769SSteven Rostedt # may not be able to create a new config. 30350a05c769SSteven Rostedt # Here we create a config with everything set. 30360a05c769SSteven Rostedt create_config (keys %config_list); 30370a05c769SSteven Rostedt read_current_config \%config_test; 30380a05c769SSteven Rostedt foreach my $config (keys %config_list) { 30390a05c769SSteven Rostedt if (!defined($config_test{$config})) { 30400a05c769SSteven Rostedt if (!$once) { 30410a05c769SSteven Rostedt $once = 1; 30420a05c769SSteven Rostedt doprint "Configs not produced by kconfig (will not be checked):\n"; 30430a05c769SSteven Rostedt } 30440a05c769SSteven Rostedt doprint " $config\n"; 30450a05c769SSteven Rostedt delete $config_list{$config}; 30460a05c769SSteven Rostedt } 30470a05c769SSteven Rostedt } 30480a05c769SSteven Rostedt my $ret; 3049b0918612SSteven Rostedt 3050b0918612SSteven Rostedt if (defined($config_bisect_check) && $config_bisect_check) { 3051b0918612SSteven Rostedt doprint " Checking to make sure bad config with min config fails\n"; 3052b0918612SSteven Rostedt create_config keys %config_list; 3053b0918612SSteven Rostedt $ret = run_config_bisect_test $config_bisect_type; 3054b0918612SSteven Rostedt if ($ret) { 3055b0918612SSteven Rostedt doprint " FAILED! Bad config with min config boots fine\n"; 3056b0918612SSteven Rostedt return -1; 3057b0918612SSteven Rostedt } 3058b0918612SSteven Rostedt doprint " Bad config with min config fails as expected\n"; 3059b0918612SSteven Rostedt } 3060b0918612SSteven Rostedt 30610a05c769SSteven Rostedt do { 30620a05c769SSteven Rostedt $ret = run_config_bisect; 30630a05c769SSteven Rostedt } while (!$ret); 30640a05c769SSteven Rostedt 30650a05c769SSteven Rostedt return $ret if ($ret < 0); 30665f9b6cedSSteven Rostedt 30675f9b6cedSSteven Rostedt success $i; 30685f9b6cedSSteven Rostedt} 30695f9b6cedSSteven Rostedt 307027d934b2SSteven Rostedtsub patchcheck_reboot { 307127d934b2SSteven Rostedt doprint "Reboot and sleep $patchcheck_sleep_time seconds\n"; 3072bc7c5803SSteven Rostedt reboot_to_good $patchcheck_sleep_time; 307327d934b2SSteven Rostedt} 307427d934b2SSteven Rostedt 30756c5ee0beSSteven Rostedtsub patchcheck { 30766c5ee0beSSteven Rostedt my ($i) = @_; 30776c5ee0beSSteven Rostedt 30786c5ee0beSSteven Rostedt die "PATCHCHECK_START[$i] not defined\n" 3079b5f4aea6SSteven Rostedt if (!defined($patchcheck_start)); 30806c5ee0beSSteven Rostedt die "PATCHCHECK_TYPE[$i] not defined\n" 3081b5f4aea6SSteven Rostedt if (!defined($patchcheck_type)); 30826c5ee0beSSteven Rostedt 3083b5f4aea6SSteven Rostedt my $start = $patchcheck_start; 30846c5ee0beSSteven Rostedt 30856c5ee0beSSteven Rostedt my $end = "HEAD"; 3086b5f4aea6SSteven Rostedt if (defined($patchcheck_end)) { 3087b5f4aea6SSteven Rostedt $end = $patchcheck_end; 30886c5ee0beSSteven Rostedt } 30896c5ee0beSSteven Rostedt 3090a57419b3SSteven Rostedt # Get the true sha1's since we can use things like HEAD~3 3091a57419b3SSteven Rostedt $start = get_sha1($start); 3092a57419b3SSteven Rostedt $end = get_sha1($end); 3093a57419b3SSteven Rostedt 3094b5f4aea6SSteven Rostedt my $type = $patchcheck_type; 30956c5ee0beSSteven Rostedt 30966c5ee0beSSteven Rostedt # Can't have a test without having a test to run 30976c5ee0beSSteven Rostedt if ($type eq "test" && !defined($run_test)) { 30986c5ee0beSSteven Rostedt $type = "boot"; 30996c5ee0beSSteven Rostedt } 31006c5ee0beSSteven Rostedt 31016c5ee0beSSteven Rostedt open (IN, "git log --pretty=oneline $end|") or 31026c5ee0beSSteven Rostedt dodie "could not get git list"; 31036c5ee0beSSteven Rostedt 31046c5ee0beSSteven Rostedt my @list; 31056c5ee0beSSteven Rostedt 31066c5ee0beSSteven Rostedt while (<IN>) { 31076c5ee0beSSteven Rostedt chomp; 31086c5ee0beSSteven Rostedt $list[$#list+1] = $_; 31096c5ee0beSSteven Rostedt last if (/^$start/); 31106c5ee0beSSteven Rostedt } 31116c5ee0beSSteven Rostedt close(IN); 31126c5ee0beSSteven Rostedt 31136c5ee0beSSteven Rostedt if ($list[$#list] !~ /^$start/) { 31142b7d9b21SSteven Rostedt fail "SHA1 $start not found"; 31156c5ee0beSSteven Rostedt } 31166c5ee0beSSteven Rostedt 31176c5ee0beSSteven Rostedt # go backwards in the list 31186c5ee0beSSteven Rostedt @list = reverse @list; 31196c5ee0beSSteven Rostedt 31206c5ee0beSSteven Rostedt my $save_clean = $noclean; 31211990207dSSteven Rostedt my %ignored_warnings; 31221990207dSSteven Rostedt 31231990207dSSteven Rostedt if (defined($ignore_warnings)) { 31241990207dSSteven Rostedt foreach my $sha1 (split /\s+/, $ignore_warnings) { 31251990207dSSteven Rostedt $ignored_warnings{$sha1} = 1; 31261990207dSSteven Rostedt } 31271990207dSSteven Rostedt } 31286c5ee0beSSteven Rostedt 31296c5ee0beSSteven Rostedt $in_patchcheck = 1; 31306c5ee0beSSteven Rostedt foreach my $item (@list) { 31316c5ee0beSSteven Rostedt my $sha1 = $item; 31326c5ee0beSSteven Rostedt $sha1 =~ s/^([[:xdigit:]]+).*/$1/; 31336c5ee0beSSteven Rostedt 31346c5ee0beSSteven Rostedt doprint "\nProcessing commit $item\n\n"; 31356c5ee0beSSteven Rostedt 31366c5ee0beSSteven Rostedt run_command "git checkout $sha1" or 31376c5ee0beSSteven Rostedt die "Failed to checkout $sha1"; 31386c5ee0beSSteven Rostedt 31396c5ee0beSSteven Rostedt # only clean on the first and last patch 31406c5ee0beSSteven Rostedt if ($item eq $list[0] || 31416c5ee0beSSteven Rostedt $item eq $list[$#list]) { 31426c5ee0beSSteven Rostedt $noclean = $save_clean; 31436c5ee0beSSteven Rostedt } else { 31446c5ee0beSSteven Rostedt $noclean = 1; 31456c5ee0beSSteven Rostedt } 31466c5ee0beSSteven Rostedt 31476c5ee0beSSteven Rostedt if (defined($minconfig)) { 31482b7d9b21SSteven Rostedt build "useconfig:$minconfig" or return 0; 31496c5ee0beSSteven Rostedt } else { 31506c5ee0beSSteven Rostedt # ?? no config to use? 31512b7d9b21SSteven Rostedt build "oldconfig" or return 0; 31526c5ee0beSSteven Rostedt } 31536c5ee0beSSteven Rostedt 31544283b169SSteven Rostedt (Red Hat) # No need to do per patch checking if warnings file exists 31554283b169SSteven Rostedt (Red Hat) if (!defined($warnings_file) && !defined($ignored_warnings{$sha1})) { 31564283b169SSteven Rostedt (Red Hat) check_patch_buildlog $sha1 or return 0; 31571990207dSSteven Rostedt } 31586c5ee0beSSteven Rostedt 31594283b169SSteven Rostedt (Red Hat) check_buildlog or return 0; 31604283b169SSteven Rostedt (Red Hat) 31616c5ee0beSSteven Rostedt next if ($type eq "build"); 31626c5ee0beSSteven Rostedt 31637faafbd6SSteven Rostedt my $failed = 0; 31647faafbd6SSteven Rostedt 3165ddf607e5SSteven Rostedt start_monitor_and_boot or $failed = 1; 31667faafbd6SSteven Rostedt 31677faafbd6SSteven Rostedt if (!$failed && $type ne "boot"){ 31687faafbd6SSteven Rostedt do_run_test or $failed = 1; 31697faafbd6SSteven Rostedt } 31707faafbd6SSteven Rostedt end_monitor; 31717faafbd6SSteven Rostedt return 0 if ($failed); 31727faafbd6SSteven Rostedt 317327d934b2SSteven Rostedt patchcheck_reboot; 317427d934b2SSteven Rostedt 31756c5ee0beSSteven Rostedt } 31766c5ee0beSSteven Rostedt $in_patchcheck = 0; 31776c5ee0beSSteven Rostedt success $i; 31782b7d9b21SSteven Rostedt 31792b7d9b21SSteven Rostedt return 1; 31806c5ee0beSSteven Rostedt} 31816c5ee0beSSteven Rostedt 3182b9066f6cSSteven Rostedtmy %depends; 3183ac6974c7SSteven Rostedtmy %depcount; 3184b9066f6cSSteven Rostedtmy $iflevel = 0; 3185b9066f6cSSteven Rostedtmy @ifdeps; 3186b9066f6cSSteven Rostedt 3187b9066f6cSSteven Rostedt# prevent recursion 3188b9066f6cSSteven Rostedtmy %read_kconfigs; 3189b9066f6cSSteven Rostedt 3190ac6974c7SSteven Rostedtsub add_dep { 3191ac6974c7SSteven Rostedt # $config depends on $dep 3192ac6974c7SSteven Rostedt my ($config, $dep) = @_; 3193ac6974c7SSteven Rostedt 3194ac6974c7SSteven Rostedt if (defined($depends{$config})) { 3195ac6974c7SSteven Rostedt $depends{$config} .= " " . $dep; 3196ac6974c7SSteven Rostedt } else { 3197ac6974c7SSteven Rostedt $depends{$config} = $dep; 3198ac6974c7SSteven Rostedt } 3199ac6974c7SSteven Rostedt 3200ac6974c7SSteven Rostedt # record the number of configs depending on $dep 3201ac6974c7SSteven Rostedt if (defined $depcount{$dep}) { 3202ac6974c7SSteven Rostedt $depcount{$dep}++; 3203ac6974c7SSteven Rostedt } else { 3204ac6974c7SSteven Rostedt $depcount{$dep} = 1; 3205ac6974c7SSteven Rostedt } 3206ac6974c7SSteven Rostedt} 3207ac6974c7SSteven Rostedt 3208b9066f6cSSteven Rostedt# taken from streamline_config.pl 3209b9066f6cSSteven Rostedtsub read_kconfig { 3210b9066f6cSSteven Rostedt my ($kconfig) = @_; 3211b9066f6cSSteven Rostedt 3212b9066f6cSSteven Rostedt my $state = "NONE"; 3213b9066f6cSSteven Rostedt my $config; 3214b9066f6cSSteven Rostedt my @kconfigs; 3215b9066f6cSSteven Rostedt 3216b9066f6cSSteven Rostedt my $cont = 0; 3217b9066f6cSSteven Rostedt my $line; 3218b9066f6cSSteven Rostedt 3219b9066f6cSSteven Rostedt 3220b9066f6cSSteven Rostedt if (! -f $kconfig) { 3221b9066f6cSSteven Rostedt doprint "file $kconfig does not exist, skipping\n"; 3222b9066f6cSSteven Rostedt return; 3223b9066f6cSSteven Rostedt } 3224b9066f6cSSteven Rostedt 3225b9066f6cSSteven Rostedt open(KIN, "$kconfig") 3226b9066f6cSSteven Rostedt or die "Can't open $kconfig"; 3227b9066f6cSSteven Rostedt while (<KIN>) { 3228b9066f6cSSteven Rostedt chomp; 3229b9066f6cSSteven Rostedt 3230b9066f6cSSteven Rostedt # Make sure that lines ending with \ continue 3231b9066f6cSSteven Rostedt if ($cont) { 3232b9066f6cSSteven Rostedt $_ = $line . " " . $_; 3233b9066f6cSSteven Rostedt } 3234b9066f6cSSteven Rostedt 3235b9066f6cSSteven Rostedt if (s/\\$//) { 3236b9066f6cSSteven Rostedt $cont = 1; 3237b9066f6cSSteven Rostedt $line = $_; 3238b9066f6cSSteven Rostedt next; 3239b9066f6cSSteven Rostedt } 3240b9066f6cSSteven Rostedt 3241b9066f6cSSteven Rostedt $cont = 0; 3242b9066f6cSSteven Rostedt 3243b9066f6cSSteven Rostedt # collect any Kconfig sources 3244b9066f6cSSteven Rostedt if (/^source\s*"(.*)"/) { 3245b9066f6cSSteven Rostedt $kconfigs[$#kconfigs+1] = $1; 3246b9066f6cSSteven Rostedt } 3247b9066f6cSSteven Rostedt 3248b9066f6cSSteven Rostedt # configs found 3249b9066f6cSSteven Rostedt if (/^\s*(menu)?config\s+(\S+)\s*$/) { 3250b9066f6cSSteven Rostedt $state = "NEW"; 3251b9066f6cSSteven Rostedt $config = $2; 3252b9066f6cSSteven Rostedt 3253b9066f6cSSteven Rostedt for (my $i = 0; $i < $iflevel; $i++) { 3254ac6974c7SSteven Rostedt add_dep $config, $ifdeps[$i]; 3255b9066f6cSSteven Rostedt } 3256b9066f6cSSteven Rostedt 3257b9066f6cSSteven Rostedt # collect the depends for the config 3258b9066f6cSSteven Rostedt } elsif ($state eq "NEW" && /^\s*depends\s+on\s+(.*)$/) { 3259b9066f6cSSteven Rostedt 3260ac6974c7SSteven Rostedt add_dep $config, $1; 3261b9066f6cSSteven Rostedt 3262b9066f6cSSteven Rostedt # Get the configs that select this config 3263ac6974c7SSteven Rostedt } elsif ($state eq "NEW" && /^\s*select\s+(\S+)/) { 3264ac6974c7SSteven Rostedt 3265ac6974c7SSteven Rostedt # selected by depends on config 3266ac6974c7SSteven Rostedt add_dep $1, $config; 3267b9066f6cSSteven Rostedt 3268b9066f6cSSteven Rostedt # Check for if statements 3269b9066f6cSSteven Rostedt } elsif (/^if\s+(.*\S)\s*$/) { 3270b9066f6cSSteven Rostedt my $deps = $1; 3271b9066f6cSSteven Rostedt # remove beginning and ending non text 3272b9066f6cSSteven Rostedt $deps =~ s/^[^a-zA-Z0-9_]*//; 3273b9066f6cSSteven Rostedt $deps =~ s/[^a-zA-Z0-9_]*$//; 3274b9066f6cSSteven Rostedt 3275b9066f6cSSteven Rostedt my @deps = split /[^a-zA-Z0-9_]+/, $deps; 3276b9066f6cSSteven Rostedt 3277b9066f6cSSteven Rostedt $ifdeps[$iflevel++] = join ':', @deps; 3278b9066f6cSSteven Rostedt 3279b9066f6cSSteven Rostedt } elsif (/^endif/) { 3280b9066f6cSSteven Rostedt 3281b9066f6cSSteven Rostedt $iflevel-- if ($iflevel); 3282b9066f6cSSteven Rostedt 3283b9066f6cSSteven Rostedt # stop on "help" 3284b9066f6cSSteven Rostedt } elsif (/^\s*help\s*$/) { 3285b9066f6cSSteven Rostedt $state = "NONE"; 3286b9066f6cSSteven Rostedt } 3287b9066f6cSSteven Rostedt } 3288b9066f6cSSteven Rostedt close(KIN); 3289b9066f6cSSteven Rostedt 3290b9066f6cSSteven Rostedt # read in any configs that were found. 3291b9066f6cSSteven Rostedt foreach $kconfig (@kconfigs) { 3292b9066f6cSSteven Rostedt if (!defined($read_kconfigs{$kconfig})) { 3293b9066f6cSSteven Rostedt $read_kconfigs{$kconfig} = 1; 3294b9066f6cSSteven Rostedt read_kconfig("$builddir/$kconfig"); 3295b9066f6cSSteven Rostedt } 3296b9066f6cSSteven Rostedt } 3297b9066f6cSSteven Rostedt} 3298b9066f6cSSteven Rostedt 3299b9066f6cSSteven Rostedtsub read_depends { 3300b9066f6cSSteven Rostedt # find out which arch this is by the kconfig file 3301b9066f6cSSteven Rostedt open (IN, $output_config) 3302b9066f6cSSteven Rostedt or dodie "Failed to read $output_config"; 3303b9066f6cSSteven Rostedt my $arch; 3304b9066f6cSSteven Rostedt while (<IN>) { 3305b9066f6cSSteven Rostedt if (m,Linux/(\S+)\s+\S+\s+Kernel Configuration,) { 3306b9066f6cSSteven Rostedt $arch = $1; 3307b9066f6cSSteven Rostedt last; 3308b9066f6cSSteven Rostedt } 3309b9066f6cSSteven Rostedt } 3310b9066f6cSSteven Rostedt close IN; 3311b9066f6cSSteven Rostedt 3312b9066f6cSSteven Rostedt if (!defined($arch)) { 3313b9066f6cSSteven Rostedt doprint "Could not find arch from config file\n"; 3314b9066f6cSSteven Rostedt doprint "no dependencies used\n"; 3315b9066f6cSSteven Rostedt return; 3316b9066f6cSSteven Rostedt } 3317b9066f6cSSteven Rostedt 3318b9066f6cSSteven Rostedt # arch is really the subarch, we need to know 3319b9066f6cSSteven Rostedt # what directory to look at. 3320b9066f6cSSteven Rostedt if ($arch eq "i386" || $arch eq "x86_64") { 3321b9066f6cSSteven Rostedt $arch = "x86"; 3322b9066f6cSSteven Rostedt } elsif ($arch =~ /^tile/) { 3323b9066f6cSSteven Rostedt $arch = "tile"; 3324b9066f6cSSteven Rostedt } 3325b9066f6cSSteven Rostedt 3326b9066f6cSSteven Rostedt my $kconfig = "$builddir/arch/$arch/Kconfig"; 3327b9066f6cSSteven Rostedt 3328b9066f6cSSteven Rostedt if (! -f $kconfig && $arch =~ /\d$/) { 3329b9066f6cSSteven Rostedt my $orig = $arch; 3330b9066f6cSSteven Rostedt # some subarchs have numbers, truncate them 3331b9066f6cSSteven Rostedt $arch =~ s/\d*$//; 3332b9066f6cSSteven Rostedt $kconfig = "$builddir/arch/$arch/Kconfig"; 3333b9066f6cSSteven Rostedt if (! -f $kconfig) { 3334b9066f6cSSteven Rostedt doprint "No idea what arch dir $orig is for\n"; 3335b9066f6cSSteven Rostedt doprint "no dependencies used\n"; 3336b9066f6cSSteven Rostedt return; 3337b9066f6cSSteven Rostedt } 3338b9066f6cSSteven Rostedt } 3339b9066f6cSSteven Rostedt 3340b9066f6cSSteven Rostedt read_kconfig($kconfig); 3341b9066f6cSSteven Rostedt} 3342b9066f6cSSteven Rostedt 33434c4ab120SSteven Rostedtsub read_config_list { 33444c4ab120SSteven Rostedt my ($config) = @_; 33454c4ab120SSteven Rostedt 33464c4ab120SSteven Rostedt open (IN, $config) 33474c4ab120SSteven Rostedt or dodie "Failed to read $config"; 33484c4ab120SSteven Rostedt 33494c4ab120SSteven Rostedt while (<IN>) { 33504c4ab120SSteven Rostedt if (/^((CONFIG\S*)=.*)/) { 33514c4ab120SSteven Rostedt if (!defined($config_ignore{$2})) { 33524c4ab120SSteven Rostedt $config_list{$2} = $1; 33534c4ab120SSteven Rostedt } 33544c4ab120SSteven Rostedt } 33554c4ab120SSteven Rostedt } 33564c4ab120SSteven Rostedt 33574c4ab120SSteven Rostedt close(IN); 33584c4ab120SSteven Rostedt} 33594c4ab120SSteven Rostedt 33604c4ab120SSteven Rostedtsub read_output_config { 33614c4ab120SSteven Rostedt my ($config) = @_; 33624c4ab120SSteven Rostedt 33634c4ab120SSteven Rostedt assign_configs \%config_ignore, $config; 33644c4ab120SSteven Rostedt} 33654c4ab120SSteven Rostedt 33664c4ab120SSteven Rostedtsub make_new_config { 33674c4ab120SSteven Rostedt my @configs = @_; 33684c4ab120SSteven Rostedt 33694c4ab120SSteven Rostedt open (OUT, ">$output_config") 33704c4ab120SSteven Rostedt or dodie "Failed to write $output_config"; 33714c4ab120SSteven Rostedt 33724c4ab120SSteven Rostedt foreach my $config (@configs) { 33734c4ab120SSteven Rostedt print OUT "$config\n"; 33744c4ab120SSteven Rostedt } 33754c4ab120SSteven Rostedt close OUT; 33764c4ab120SSteven Rostedt} 33774c4ab120SSteven Rostedt 3378ac6974c7SSteven Rostedtsub chomp_config { 3379ac6974c7SSteven Rostedt my ($config) = @_; 3380ac6974c7SSteven Rostedt 3381ac6974c7SSteven Rostedt $config =~ s/CONFIG_//; 3382ac6974c7SSteven Rostedt 3383ac6974c7SSteven Rostedt return $config; 3384ac6974c7SSteven Rostedt} 3385ac6974c7SSteven Rostedt 3386b9066f6cSSteven Rostedtsub get_depends { 3387b9066f6cSSteven Rostedt my ($dep) = @_; 3388b9066f6cSSteven Rostedt 3389ac6974c7SSteven Rostedt my $kconfig = chomp_config $dep; 3390b9066f6cSSteven Rostedt 3391b9066f6cSSteven Rostedt $dep = $depends{"$kconfig"}; 3392b9066f6cSSteven Rostedt 3393b9066f6cSSteven Rostedt # the dep string we have saves the dependencies as they 3394b9066f6cSSteven Rostedt # were found, including expressions like ! && ||. We 3395b9066f6cSSteven Rostedt # want to split this out into just an array of configs. 3396b9066f6cSSteven Rostedt 3397b9066f6cSSteven Rostedt my $valid = "A-Za-z_0-9"; 3398b9066f6cSSteven Rostedt 3399b9066f6cSSteven Rostedt my @configs; 3400b9066f6cSSteven Rostedt 3401b9066f6cSSteven Rostedt while ($dep =~ /[$valid]/) { 3402b9066f6cSSteven Rostedt 3403b9066f6cSSteven Rostedt if ($dep =~ /^[^$valid]*([$valid]+)/) { 3404b9066f6cSSteven Rostedt my $conf = "CONFIG_" . $1; 3405b9066f6cSSteven Rostedt 3406b9066f6cSSteven Rostedt $configs[$#configs + 1] = $conf; 3407b9066f6cSSteven Rostedt 3408b9066f6cSSteven Rostedt $dep =~ s/^[^$valid]*[$valid]+//; 3409b9066f6cSSteven Rostedt } else { 3410b9066f6cSSteven Rostedt die "this should never happen"; 3411b9066f6cSSteven Rostedt } 3412b9066f6cSSteven Rostedt } 3413b9066f6cSSteven Rostedt 3414b9066f6cSSteven Rostedt return @configs; 3415b9066f6cSSteven Rostedt} 3416b9066f6cSSteven Rostedt 3417b9066f6cSSteven Rostedtmy %min_configs; 3418b9066f6cSSteven Rostedtmy %keep_configs; 341943d1b651SSteven Rostedtmy %save_configs; 3420b9066f6cSSteven Rostedtmy %processed_configs; 3421b9066f6cSSteven Rostedtmy %nochange_config; 3422b9066f6cSSteven Rostedt 3423b9066f6cSSteven Rostedtsub test_this_config { 3424b9066f6cSSteven Rostedt my ($config) = @_; 3425b9066f6cSSteven Rostedt 3426b9066f6cSSteven Rostedt my $found; 3427b9066f6cSSteven Rostedt 3428b9066f6cSSteven Rostedt # if we already processed this config, skip it 3429b9066f6cSSteven Rostedt if (defined($processed_configs{$config})) { 3430b9066f6cSSteven Rostedt return undef; 3431b9066f6cSSteven Rostedt } 3432b9066f6cSSteven Rostedt $processed_configs{$config} = 1; 3433b9066f6cSSteven Rostedt 3434b9066f6cSSteven Rostedt # if this config failed during this round, skip it 3435b9066f6cSSteven Rostedt if (defined($nochange_config{$config})) { 3436b9066f6cSSteven Rostedt return undef; 3437b9066f6cSSteven Rostedt } 3438b9066f6cSSteven Rostedt 3439ac6974c7SSteven Rostedt my $kconfig = chomp_config $config; 3440b9066f6cSSteven Rostedt 3441b9066f6cSSteven Rostedt # Test dependencies first 3442b9066f6cSSteven Rostedt if (defined($depends{"$kconfig"})) { 3443b9066f6cSSteven Rostedt my @parents = get_depends $config; 3444b9066f6cSSteven Rostedt foreach my $parent (@parents) { 3445b9066f6cSSteven Rostedt # if the parent is in the min config, check it first 3446b9066f6cSSteven Rostedt next if (!defined($min_configs{$parent})); 3447b9066f6cSSteven Rostedt $found = test_this_config($parent); 3448b9066f6cSSteven Rostedt if (defined($found)) { 3449b9066f6cSSteven Rostedt return $found; 3450b9066f6cSSteven Rostedt } 3451b9066f6cSSteven Rostedt } 3452b9066f6cSSteven Rostedt } 3453b9066f6cSSteven Rostedt 3454b9066f6cSSteven Rostedt # Remove this config from the list of configs 3455fb16d891SAdam Lee # do a make olddefconfig and then read the resulting 3456b9066f6cSSteven Rostedt # .config to make sure it is missing the config that 3457b9066f6cSSteven Rostedt # we had before 3458b9066f6cSSteven Rostedt my %configs = %min_configs; 3459b9066f6cSSteven Rostedt delete $configs{$config}; 3460b9066f6cSSteven Rostedt make_new_config ((values %configs), (values %keep_configs)); 3461b9066f6cSSteven Rostedt make_oldconfig; 3462b9066f6cSSteven Rostedt undef %configs; 3463b9066f6cSSteven Rostedt assign_configs \%configs, $output_config; 3464b9066f6cSSteven Rostedt 3465b9066f6cSSteven Rostedt return $config if (!defined($configs{$config})); 3466b9066f6cSSteven Rostedt 3467b9066f6cSSteven Rostedt doprint "disabling config $config did not change .config\n"; 3468b9066f6cSSteven Rostedt 3469b9066f6cSSteven Rostedt $nochange_config{$config} = 1; 3470b9066f6cSSteven Rostedt 3471b9066f6cSSteven Rostedt return undef; 3472b9066f6cSSteven Rostedt} 3473b9066f6cSSteven Rostedt 34744c4ab120SSteven Rostedtsub make_min_config { 34754c4ab120SSteven Rostedt my ($i) = @_; 34764c4ab120SSteven Rostedt 3477ccc513b6SSteven Rostedt my $type = $minconfig_type; 3478ccc513b6SSteven Rostedt if ($type ne "boot" && $type ne "test") { 3479ccc513b6SSteven Rostedt fail "Invalid MIN_CONFIG_TYPE '$minconfig_type'\n" . 3480ccc513b6SSteven Rostedt " make_min_config works only with 'boot' and 'test'\n" and return; 3481ccc513b6SSteven Rostedt } 3482ccc513b6SSteven Rostedt 34834c4ab120SSteven Rostedt if (!defined($output_minconfig)) { 34844c4ab120SSteven Rostedt fail "OUTPUT_MIN_CONFIG not defined" and return; 34854c4ab120SSteven Rostedt } 348635ce5952SSteven Rostedt 348735ce5952SSteven Rostedt # If output_minconfig exists, and the start_minconfig 348835ce5952SSteven Rostedt # came from min_config, than ask if we should use 348935ce5952SSteven Rostedt # that instead. 349035ce5952SSteven Rostedt if (-f $output_minconfig && !$start_minconfig_defined) { 349135ce5952SSteven Rostedt print "$output_minconfig exists\n"; 349243de3316SSteven Rostedt if (!defined($use_output_minconfig)) { 349335ce5952SSteven Rostedt if (read_yn " Use it as minconfig?") { 349435ce5952SSteven Rostedt $start_minconfig = $output_minconfig; 349535ce5952SSteven Rostedt } 349643de3316SSteven Rostedt } elsif ($use_output_minconfig > 0) { 349743de3316SSteven Rostedt doprint "Using $output_minconfig as MIN_CONFIG\n"; 349843de3316SSteven Rostedt $start_minconfig = $output_minconfig; 349943de3316SSteven Rostedt } else { 350043de3316SSteven Rostedt doprint "Set to still use MIN_CONFIG as starting point\n"; 350143de3316SSteven Rostedt } 350235ce5952SSteven Rostedt } 350335ce5952SSteven Rostedt 35044c4ab120SSteven Rostedt if (!defined($start_minconfig)) { 35054c4ab120SSteven Rostedt fail "START_MIN_CONFIG or MIN_CONFIG not defined" and return; 35064c4ab120SSteven Rostedt } 35074c4ab120SSteven Rostedt 350835ce5952SSteven Rostedt my $temp_config = "$tmpdir/temp_config"; 350935ce5952SSteven Rostedt 35104c4ab120SSteven Rostedt # First things first. We build an allnoconfig to find 35114c4ab120SSteven Rostedt # out what the defaults are that we can't touch. 35124c4ab120SSteven Rostedt # Some are selections, but we really can't handle selections. 35134c4ab120SSteven Rostedt 35144c4ab120SSteven Rostedt my $save_minconfig = $minconfig; 35154c4ab120SSteven Rostedt undef $minconfig; 35164c4ab120SSteven Rostedt 35174c4ab120SSteven Rostedt run_command "$make allnoconfig" or return 0; 35184c4ab120SSteven Rostedt 3519b9066f6cSSteven Rostedt read_depends; 3520b9066f6cSSteven Rostedt 35214c4ab120SSteven Rostedt process_config_ignore $output_config; 3522b9066f6cSSteven Rostedt 352343d1b651SSteven Rostedt undef %save_configs; 3524b9066f6cSSteven Rostedt undef %min_configs; 35254c4ab120SSteven Rostedt 35264c4ab120SSteven Rostedt if (defined($ignore_config)) { 35274c4ab120SSteven Rostedt # make sure the file exists 35284c4ab120SSteven Rostedt `touch $ignore_config`; 352943d1b651SSteven Rostedt assign_configs \%save_configs, $ignore_config; 35304c4ab120SSteven Rostedt } 35314c4ab120SSteven Rostedt 353243d1b651SSteven Rostedt %keep_configs = %save_configs; 353343d1b651SSteven Rostedt 35344c4ab120SSteven Rostedt doprint "Load initial configs from $start_minconfig\n"; 35354c4ab120SSteven Rostedt 35364c4ab120SSteven Rostedt # Look at the current min configs, and save off all the 35374c4ab120SSteven Rostedt # ones that were set via the allnoconfig 35384c4ab120SSteven Rostedt assign_configs \%min_configs, $start_minconfig; 35394c4ab120SSteven Rostedt 35404c4ab120SSteven Rostedt my @config_keys = keys %min_configs; 35414c4ab120SSteven Rostedt 3542ac6974c7SSteven Rostedt # All configs need a depcount 3543ac6974c7SSteven Rostedt foreach my $config (@config_keys) { 3544ac6974c7SSteven Rostedt my $kconfig = chomp_config $config; 3545ac6974c7SSteven Rostedt if (!defined $depcount{$kconfig}) { 3546ac6974c7SSteven Rostedt $depcount{$kconfig} = 0; 3547ac6974c7SSteven Rostedt } 3548ac6974c7SSteven Rostedt } 3549ac6974c7SSteven Rostedt 35504c4ab120SSteven Rostedt # Remove anything that was set by the make allnoconfig 35514c4ab120SSteven Rostedt # we shouldn't need them as they get set for us anyway. 35524c4ab120SSteven Rostedt foreach my $config (@config_keys) { 35534c4ab120SSteven Rostedt # Remove anything in the ignore_config 35544c4ab120SSteven Rostedt if (defined($keep_configs{$config})) { 35554c4ab120SSteven Rostedt my $file = $ignore_config; 35564c4ab120SSteven Rostedt $file =~ s,.*/(.*?)$,$1,; 35574c4ab120SSteven Rostedt doprint "$config set by $file ... ignored\n"; 35584c4ab120SSteven Rostedt delete $min_configs{$config}; 35594c4ab120SSteven Rostedt next; 35604c4ab120SSteven Rostedt } 35614c4ab120SSteven Rostedt # But make sure the settings are the same. If a min config 35624c4ab120SSteven Rostedt # sets a selection, we do not want to get rid of it if 35634c4ab120SSteven Rostedt # it is not the same as what we have. Just move it into 35644c4ab120SSteven Rostedt # the keep configs. 35654c4ab120SSteven Rostedt if (defined($config_ignore{$config})) { 35664c4ab120SSteven Rostedt if ($config_ignore{$config} ne $min_configs{$config}) { 35674c4ab120SSteven Rostedt doprint "$config is in allnoconfig as '$config_ignore{$config}'"; 35684c4ab120SSteven Rostedt doprint " but it is '$min_configs{$config}' in minconfig .. keeping\n"; 35694c4ab120SSteven Rostedt $keep_configs{$config} = $min_configs{$config}; 35704c4ab120SSteven Rostedt } else { 35714c4ab120SSteven Rostedt doprint "$config set by allnoconfig ... ignored\n"; 35724c4ab120SSteven Rostedt } 35734c4ab120SSteven Rostedt delete $min_configs{$config}; 35744c4ab120SSteven Rostedt } 35754c4ab120SSteven Rostedt } 35764c4ab120SSteven Rostedt 35774c4ab120SSteven Rostedt my $done = 0; 3578b9066f6cSSteven Rostedt my $take_two = 0; 35794c4ab120SSteven Rostedt 35804c4ab120SSteven Rostedt while (!$done) { 35814c4ab120SSteven Rostedt 35824c4ab120SSteven Rostedt my $config; 35834c4ab120SSteven Rostedt my $found; 35844c4ab120SSteven Rostedt 35854c4ab120SSteven Rostedt # Now disable each config one by one and do a make oldconfig 35864c4ab120SSteven Rostedt # till we find a config that changes our list. 35874c4ab120SSteven Rostedt 35884c4ab120SSteven Rostedt my @test_configs = keys %min_configs; 3589ac6974c7SSteven Rostedt 3590ac6974c7SSteven Rostedt # Sort keys by who is most dependent on 3591ac6974c7SSteven Rostedt @test_configs = sort { $depcount{chomp_config($b)} <=> $depcount{chomp_config($a)} } 3592ac6974c7SSteven Rostedt @test_configs ; 3593ac6974c7SSteven Rostedt 3594ac6974c7SSteven Rostedt # Put configs that did not modify the config at the end. 35954c4ab120SSteven Rostedt my $reset = 1; 35964c4ab120SSteven Rostedt for (my $i = 0; $i < $#test_configs; $i++) { 35974c4ab120SSteven Rostedt if (!defined($nochange_config{$test_configs[0]})) { 35984c4ab120SSteven Rostedt $reset = 0; 35994c4ab120SSteven Rostedt last; 36004c4ab120SSteven Rostedt } 36014c4ab120SSteven Rostedt # This config didn't change the .config last time. 36024c4ab120SSteven Rostedt # Place it at the end 36034c4ab120SSteven Rostedt my $config = shift @test_configs; 36044c4ab120SSteven Rostedt push @test_configs, $config; 36054c4ab120SSteven Rostedt } 36064c4ab120SSteven Rostedt 36074c4ab120SSteven Rostedt # if every test config has failed to modify the .config file 36084c4ab120SSteven Rostedt # in the past, then reset and start over. 36094c4ab120SSteven Rostedt if ($reset) { 36104c4ab120SSteven Rostedt undef %nochange_config; 36114c4ab120SSteven Rostedt } 36124c4ab120SSteven Rostedt 3613b9066f6cSSteven Rostedt undef %processed_configs; 3614b9066f6cSSteven Rostedt 36154c4ab120SSteven Rostedt foreach my $config (@test_configs) { 36164c4ab120SSteven Rostedt 3617b9066f6cSSteven Rostedt $found = test_this_config $config; 36184c4ab120SSteven Rostedt 3619b9066f6cSSteven Rostedt last if (defined($found)); 36204c4ab120SSteven Rostedt 36214c4ab120SSteven Rostedt # oh well, try another config 36224c4ab120SSteven Rostedt } 36234c4ab120SSteven Rostedt 36244c4ab120SSteven Rostedt if (!defined($found)) { 3625b9066f6cSSteven Rostedt # we could have failed due to the nochange_config hash 3626b9066f6cSSteven Rostedt # reset and try again 3627b9066f6cSSteven Rostedt if (!$take_two) { 3628b9066f6cSSteven Rostedt undef %nochange_config; 3629b9066f6cSSteven Rostedt $take_two = 1; 3630b9066f6cSSteven Rostedt next; 3631b9066f6cSSteven Rostedt } 36324c4ab120SSteven Rostedt doprint "No more configs found that we can disable\n"; 36334c4ab120SSteven Rostedt $done = 1; 36344c4ab120SSteven Rostedt last; 36354c4ab120SSteven Rostedt } 3636b9066f6cSSteven Rostedt $take_two = 0; 36374c4ab120SSteven Rostedt 36384c4ab120SSteven Rostedt $config = $found; 36394c4ab120SSteven Rostedt 36404c4ab120SSteven Rostedt doprint "Test with $config disabled\n"; 36414c4ab120SSteven Rostedt 36424c4ab120SSteven Rostedt # set in_bisect to keep build and monitor from dieing 36434c4ab120SSteven Rostedt $in_bisect = 1; 36444c4ab120SSteven Rostedt 36454c4ab120SSteven Rostedt my $failed = 0; 3646bf1c95abSSteven Rostedt build "oldconfig" or $failed = 1; 3647bf1c95abSSteven Rostedt if (!$failed) { 36484c4ab120SSteven Rostedt start_monitor_and_boot or $failed = 1; 3649ccc513b6SSteven Rostedt 3650ccc513b6SSteven Rostedt if ($type eq "test" && !$failed) { 3651ccc513b6SSteven Rostedt do_run_test or $failed = 1; 3652ccc513b6SSteven Rostedt } 3653ccc513b6SSteven Rostedt 36544c4ab120SSteven Rostedt end_monitor; 3655bf1c95abSSteven Rostedt } 36564c4ab120SSteven Rostedt 36574c4ab120SSteven Rostedt $in_bisect = 0; 36584c4ab120SSteven Rostedt 36594c4ab120SSteven Rostedt if ($failed) { 3660b9066f6cSSteven Rostedt doprint "$min_configs{$config} is needed to boot the box... keeping\n"; 36614c4ab120SSteven Rostedt # this config is needed, add it to the ignore list. 36624c4ab120SSteven Rostedt $keep_configs{$config} = $min_configs{$config}; 366343d1b651SSteven Rostedt $save_configs{$config} = $min_configs{$config}; 36644c4ab120SSteven Rostedt delete $min_configs{$config}; 366535ce5952SSteven Rostedt 366635ce5952SSteven Rostedt # update new ignore configs 366735ce5952SSteven Rostedt if (defined($ignore_config)) { 366835ce5952SSteven Rostedt open (OUT, ">$temp_config") 366935ce5952SSteven Rostedt or die "Can't write to $temp_config"; 367043d1b651SSteven Rostedt foreach my $config (keys %save_configs) { 367143d1b651SSteven Rostedt print OUT "$save_configs{$config}\n"; 367235ce5952SSteven Rostedt } 367335ce5952SSteven Rostedt close OUT; 367435ce5952SSteven Rostedt run_command "mv $temp_config $ignore_config" or 367535ce5952SSteven Rostedt dodie "failed to copy update to $ignore_config"; 367635ce5952SSteven Rostedt } 367735ce5952SSteven Rostedt 36784c4ab120SSteven Rostedt } else { 36794c4ab120SSteven Rostedt # We booted without this config, remove it from the minconfigs. 36804c4ab120SSteven Rostedt doprint "$config is not needed, disabling\n"; 36814c4ab120SSteven Rostedt 36824c4ab120SSteven Rostedt delete $min_configs{$config}; 36834c4ab120SSteven Rostedt 36844c4ab120SSteven Rostedt # Also disable anything that is not enabled in this config 36854c4ab120SSteven Rostedt my %configs; 36864c4ab120SSteven Rostedt assign_configs \%configs, $output_config; 36874c4ab120SSteven Rostedt my @config_keys = keys %min_configs; 36884c4ab120SSteven Rostedt foreach my $config (@config_keys) { 36894c4ab120SSteven Rostedt if (!defined($configs{$config})) { 36904c4ab120SSteven Rostedt doprint "$config is not set, disabling\n"; 36914c4ab120SSteven Rostedt delete $min_configs{$config}; 36924c4ab120SSteven Rostedt } 36934c4ab120SSteven Rostedt } 36944c4ab120SSteven Rostedt 36954c4ab120SSteven Rostedt # Save off all the current mandidory configs 369635ce5952SSteven Rostedt open (OUT, ">$temp_config") 369735ce5952SSteven Rostedt or die "Can't write to $temp_config"; 36984c4ab120SSteven Rostedt foreach my $config (keys %keep_configs) { 36994c4ab120SSteven Rostedt print OUT "$keep_configs{$config}\n"; 37004c4ab120SSteven Rostedt } 37014c4ab120SSteven Rostedt foreach my $config (keys %min_configs) { 37024c4ab120SSteven Rostedt print OUT "$min_configs{$config}\n"; 37034c4ab120SSteven Rostedt } 37044c4ab120SSteven Rostedt close OUT; 370535ce5952SSteven Rostedt 370635ce5952SSteven Rostedt run_command "mv $temp_config $output_minconfig" or 370735ce5952SSteven Rostedt dodie "failed to copy update to $output_minconfig"; 37084c4ab120SSteven Rostedt } 37094c4ab120SSteven Rostedt 37104c4ab120SSteven Rostedt doprint "Reboot and wait $sleep_time seconds\n"; 3711bc7c5803SSteven Rostedt reboot_to_good $sleep_time; 37124c4ab120SSteven Rostedt } 37134c4ab120SSteven Rostedt 37144c4ab120SSteven Rostedt success $i; 37154c4ab120SSteven Rostedt return 1; 37164c4ab120SSteven Rostedt} 37174c4ab120SSteven Rostedt 37184283b169SSteven Rostedt (Red Hat)sub make_warnings_file { 37194283b169SSteven Rostedt (Red Hat) my ($i) = @_; 37204283b169SSteven Rostedt (Red Hat) 37214283b169SSteven Rostedt (Red Hat) if (!defined($warnings_file)) { 37224283b169SSteven Rostedt (Red Hat) dodie "Must define WARNINGS_FILE for make_warnings_file test"; 37234283b169SSteven Rostedt (Red Hat) } 37244283b169SSteven Rostedt (Red Hat) 37254283b169SSteven Rostedt (Red Hat) if ($build_type eq "nobuild") { 37264283b169SSteven Rostedt (Red Hat) dodie "BUILD_TYPE can not be 'nobuild' for make_warnings_file test"; 37274283b169SSteven Rostedt (Red Hat) } 37284283b169SSteven Rostedt (Red Hat) 37294283b169SSteven Rostedt (Red Hat) build $build_type or dodie "Failed to build"; 37304283b169SSteven Rostedt (Red Hat) 37314283b169SSteven Rostedt (Red Hat) open(OUT, ">$warnings_file") or dodie "Can't create $warnings_file"; 37324283b169SSteven Rostedt (Red Hat) 37334283b169SSteven Rostedt (Red Hat) open(IN, $buildlog) or dodie "Can't open $buildlog"; 37344283b169SSteven Rostedt (Red Hat) while (<IN>) { 37354283b169SSteven Rostedt (Red Hat) 37364283b169SSteven Rostedt (Red Hat) # Some compilers use UTF-8 extended for quotes 37374283b169SSteven Rostedt (Red Hat) # for distcc heterogeneous systems, this causes issues 37384283b169SSteven Rostedt (Red Hat) s/$utf8_quote/'/g; 37394283b169SSteven Rostedt (Red Hat) 37404283b169SSteven Rostedt (Red Hat) if (/$check_build_re/) { 37414283b169SSteven Rostedt (Red Hat) print OUT; 37424283b169SSteven Rostedt (Red Hat) } 37434283b169SSteven Rostedt (Red Hat) } 37444283b169SSteven Rostedt (Red Hat) close(IN); 37454283b169SSteven Rostedt (Red Hat) 37464283b169SSteven Rostedt (Red Hat) close(OUT); 37474283b169SSteven Rostedt (Red Hat) 37484283b169SSteven Rostedt (Red Hat) success $i; 37494283b169SSteven Rostedt (Red Hat)} 37504283b169SSteven Rostedt (Red Hat) 37518d1491baSSteven Rostedt$#ARGV < 1 or die "ktest.pl version: $VERSION\n usage: ktest.pl config-file\n"; 37522545eb61SSteven Rostedt 37538d1491baSSteven Rostedtif ($#ARGV == 0) { 37548d1491baSSteven Rostedt $ktest_config = $ARGV[0]; 37558d1491baSSteven Rostedt if (! -f $ktest_config) { 37568d1491baSSteven Rostedt print "$ktest_config does not exist.\n"; 375735ce5952SSteven Rostedt if (!read_yn "Create it?") { 37588d1491baSSteven Rostedt exit 0; 37598d1491baSSteven Rostedt } 37608d1491baSSteven Rostedt } 37618d1491baSSteven Rostedt} else { 37628d1491baSSteven Rostedt $ktest_config = "ktest.conf"; 37638d1491baSSteven Rostedt} 37648d1491baSSteven Rostedt 37658d1491baSSteven Rostedtif (! -f $ktest_config) { 3766dbd3783bSSteven Rostedt $newconfig = 1; 3767c4261d0fSSteven Rostedt get_test_case; 37688d1491baSSteven Rostedt open(OUT, ">$ktest_config") or die "Can not create $ktest_config"; 37698d1491baSSteven Rostedt print OUT << "EOF" 37708d1491baSSteven Rostedt# Generated by ktest.pl 37718d1491baSSteven Rostedt# 37720e7a22deSSteven Rostedt 37730e7a22deSSteven Rostedt# PWD is a ktest.pl variable that will result in the process working 37740e7a22deSSteven Rostedt# directory that ktest.pl is executed in. 37750e7a22deSSteven Rostedt 37760e7a22deSSteven Rostedt# THIS_DIR is automatically assigned the PWD of the path that generated 37770e7a22deSSteven Rostedt# the config file. It is best to use this variable when assigning other 37780e7a22deSSteven Rostedt# directory paths within this directory. This allows you to easily 37790e7a22deSSteven Rostedt# move the test cases to other locations or to other machines. 37800e7a22deSSteven Rostedt# 37810e7a22deSSteven RostedtTHIS_DIR := $variable{"PWD"} 37820e7a22deSSteven Rostedt 37838d1491baSSteven Rostedt# Define each test with TEST_START 37848d1491baSSteven Rostedt# The config options below it will override the defaults 37858d1491baSSteven RostedtTEST_START 3786c4261d0fSSteven RostedtTEST_TYPE = $default{"TEST_TYPE"} 37878d1491baSSteven Rostedt 37888d1491baSSteven RostedtDEFAULTS 37898d1491baSSteven RostedtEOF 37908d1491baSSteven Rostedt; 37918d1491baSSteven Rostedt close(OUT); 37928d1491baSSteven Rostedt} 37938d1491baSSteven Rostedtread_config $ktest_config; 37948d1491baSSteven Rostedt 379523715c3cSSteven Rostedtif (defined($opt{"LOG_FILE"})) { 379604262be3SSteven Rostedt (Red Hat) $opt{"LOG_FILE"} = eval_option("LOG_FILE", $opt{"LOG_FILE"}, -1); 379723715c3cSSteven Rostedt} 379823715c3cSSteven Rostedt 37998d1491baSSteven Rostedt# Append any configs entered in manually to the config file. 38008d1491baSSteven Rostedtmy @new_configs = keys %entered_configs; 38018d1491baSSteven Rostedtif ($#new_configs >= 0) { 38028d1491baSSteven Rostedt print "\nAppending entered in configs to $ktest_config\n"; 38038d1491baSSteven Rostedt open(OUT, ">>$ktest_config") or die "Can not append to $ktest_config"; 38048d1491baSSteven Rostedt foreach my $config (@new_configs) { 38058d1491baSSteven Rostedt print OUT "$config = $entered_configs{$config}\n"; 38060e7a22deSSteven Rostedt $opt{$config} = process_variables($entered_configs{$config}); 38078d1491baSSteven Rostedt } 38088d1491baSSteven Rostedt} 38092545eb61SSteven Rostedt 38102b7d9b21SSteven Rostedtif ($opt{"CLEAR_LOG"} && defined($opt{"LOG_FILE"})) { 38112b7d9b21SSteven Rostedt unlink $opt{"LOG_FILE"}; 38122b7d9b21SSteven Rostedt} 38132545eb61SSteven Rostedt 38142b7d9b21SSteven Rostedtdoprint "\n\nSTARTING AUTOMATED TESTS\n\n"; 38152b7d9b21SSteven Rostedt 3816a57419b3SSteven Rostedtfor (my $i = 0, my $repeat = 1; $i <= $opt{"NUM_TESTS"}; $i += $repeat) { 3817a57419b3SSteven Rostedt 3818a57419b3SSteven Rostedt if (!$i) { 3819a57419b3SSteven Rostedt doprint "DEFAULT OPTIONS:\n"; 3820a57419b3SSteven Rostedt } else { 3821a57419b3SSteven Rostedt doprint "\nTEST $i OPTIONS"; 3822a57419b3SSteven Rostedt if (defined($repeat_tests{$i})) { 3823a57419b3SSteven Rostedt $repeat = $repeat_tests{$i}; 3824a57419b3SSteven Rostedt doprint " ITERATE $repeat"; 3825a57419b3SSteven Rostedt } 3826a57419b3SSteven Rostedt doprint "\n"; 3827a57419b3SSteven Rostedt } 3828a57419b3SSteven Rostedt 38292b7d9b21SSteven Rostedt foreach my $option (sort keys %opt) { 3830a57419b3SSteven Rostedt 3831a57419b3SSteven Rostedt if ($option =~ /\[(\d+)\]$/) { 3832a57419b3SSteven Rostedt next if ($i != $1); 3833a57419b3SSteven Rostedt } else { 3834a57419b3SSteven Rostedt next if ($i); 3835a57419b3SSteven Rostedt } 3836a57419b3SSteven Rostedt 38372b7d9b21SSteven Rostedt doprint "$option = $opt{$option}\n"; 38382b7d9b21SSteven Rostedt } 3839a57419b3SSteven Rostedt} 38402545eb61SSteven Rostedt 38412a62512bSSteven Rostedtsub __set_test_option { 38425a391fbfSSteven Rostedt my ($name, $i) = @_; 38435a391fbfSSteven Rostedt 38445a391fbfSSteven Rostedt my $option = "$name\[$i\]"; 38455a391fbfSSteven Rostedt 38465a391fbfSSteven Rostedt if (defined($opt{$option})) { 38475a391fbfSSteven Rostedt return $opt{$option}; 38485a391fbfSSteven Rostedt } 38495a391fbfSSteven Rostedt 3850a57419b3SSteven Rostedt foreach my $test (keys %repeat_tests) { 3851a57419b3SSteven Rostedt if ($i >= $test && 3852a57419b3SSteven Rostedt $i < $test + $repeat_tests{$test}) { 3853a57419b3SSteven Rostedt $option = "$name\[$test\]"; 3854a57419b3SSteven Rostedt if (defined($opt{$option})) { 3855a57419b3SSteven Rostedt return $opt{$option}; 3856a57419b3SSteven Rostedt } 3857a57419b3SSteven Rostedt } 3858a57419b3SSteven Rostedt } 3859a57419b3SSteven Rostedt 38605a391fbfSSteven Rostedt if (defined($opt{$name})) { 38615a391fbfSSteven Rostedt return $opt{$name}; 38625a391fbfSSteven Rostedt } 38635a391fbfSSteven Rostedt 38645a391fbfSSteven Rostedt return undef; 38655a391fbfSSteven Rostedt} 38665a391fbfSSteven Rostedt 38672a62512bSSteven Rostedtsub set_test_option { 38682a62512bSSteven Rostedt my ($name, $i) = @_; 38692a62512bSSteven Rostedt 38702a62512bSSteven Rostedt my $option = __set_test_option($name, $i); 38712a62512bSSteven Rostedt return $option if (!defined($option)); 38722a62512bSSteven Rostedt 387304262be3SSteven Rostedt (Red Hat) return eval_option($name, $option, $i); 38742a62512bSSteven Rostedt} 38752a62512bSSteven Rostedt 38762545eb61SSteven Rostedt# First we need to do is the builds 3877a75fececSSteven Rostedtfor (my $i = 1; $i <= $opt{"NUM_TESTS"}; $i++) { 38782545eb61SSteven Rostedt 38794ab1cce5SSteven Rostedt # Do not reboot on failing test options 38804ab1cce5SSteven Rostedt $no_reboot = 1; 3881759a3cc6SSteven Rostedt $reboot_success = 0; 38824ab1cce5SSteven Rostedt 3883683a3e64SSteven Rostedt $have_version = 0; 3884683a3e64SSteven Rostedt 3885576f627cSSteven Rostedt $iteration = $i; 3886576f627cSSteven Rostedt 3887c1434dccSSteven Rostedt undef %force_config; 3888c1434dccSSteven Rostedt 3889a75fececSSteven Rostedt my $makecmd = set_test_option("MAKE_CMD", $i); 3890a75fececSSteven Rostedt 38919cc9e091SSteven Rostedt # Load all the options into their mapped variable names 38929cc9e091SSteven Rostedt foreach my $opt (keys %option_map) { 38939cc9e091SSteven Rostedt ${$option_map{$opt}} = set_test_option($opt, $i); 38949cc9e091SSteven Rostedt } 3895b5f4aea6SSteven Rostedt 389635ce5952SSteven Rostedt $start_minconfig_defined = 1; 389735ce5952SSteven Rostedt 3898921ed4c7SSteven Rostedt # The first test may override the PRE_KTEST option 3899921ed4c7SSteven Rostedt if (defined($pre_ktest) && $i == 1) { 3900921ed4c7SSteven Rostedt doprint "\n"; 3901921ed4c7SSteven Rostedt run_command $pre_ktest; 3902921ed4c7SSteven Rostedt } 3903921ed4c7SSteven Rostedt 3904921ed4c7SSteven Rostedt # Any test can override the POST_KTEST option 3905921ed4c7SSteven Rostedt # The last test takes precedence. 3906921ed4c7SSteven Rostedt if (defined($post_ktest)) { 3907921ed4c7SSteven Rostedt $final_post_ktest = $post_ktest; 3908921ed4c7SSteven Rostedt } 3909921ed4c7SSteven Rostedt 39104c4ab120SSteven Rostedt if (!defined($start_minconfig)) { 391135ce5952SSteven Rostedt $start_minconfig_defined = 0; 39124c4ab120SSteven Rostedt $start_minconfig = $minconfig; 39134c4ab120SSteven Rostedt } 39144c4ab120SSteven Rostedt 3915a75fececSSteven Rostedt chdir $builddir || die "can't change directory to $builddir"; 3916a75fececSSteven Rostedt 3917a908a665SAndrew Jones foreach my $dir ($tmpdir, $outputdir) { 3918a908a665SAndrew Jones if (!-d $dir) { 3919a908a665SAndrew Jones mkpath($dir) or 3920a908a665SAndrew Jones die "can't create $dir"; 3921a908a665SAndrew Jones } 3922a75fececSSteven Rostedt } 3923a75fececSSteven Rostedt 3924e48c5293SSteven Rostedt $ENV{"SSH_USER"} = $ssh_user; 3925e48c5293SSteven Rostedt $ENV{"MACHINE"} = $machine; 3926e48c5293SSteven Rostedt 3927a75fececSSteven Rostedt $buildlog = "$tmpdir/buildlog-$machine"; 3928a9dd5d63SRabin Vincent $testlog = "$tmpdir/testlog-$machine"; 3929a75fececSSteven Rostedt $dmesg = "$tmpdir/dmesg-$machine"; 3930a75fececSSteven Rostedt $make = "$makecmd O=$outputdir"; 393151ad1dd1SSteven Rostedt $output_config = "$outputdir/.config"; 3932a75fececSSteven Rostedt 3933bb8474b1SSteven Rostedt if (!$buildonly) { 3934bb8474b1SSteven Rostedt $target = "$ssh_user\@$machine"; 3935a75fececSSteven Rostedt if ($reboot_type eq "grub") { 3936576f627cSSteven Rostedt dodie "GRUB_MENU not defined" if (!defined($grub_menu)); 3937a15ba913SSteven Rostedt } elsif ($reboot_type eq "grub2") { 3938a15ba913SSteven Rostedt dodie "GRUB_MENU not defined" if (!defined($grub_menu)); 3939a15ba913SSteven Rostedt dodie "GRUB_FILE not defined" if (!defined($grub_file)); 39407786954cSSteven Rostedt } elsif ($reboot_type eq "syslinux") { 39417786954cSSteven Rostedt dodie "SYSLINUX_LABEL not defined" if (!defined($syslinux_label)); 3942a75fececSSteven Rostedt } 3943bb8474b1SSteven Rostedt } 3944a75fececSSteven Rostedt 3945a75fececSSteven Rostedt my $run_type = $build_type; 3946a75fececSSteven Rostedt if ($test_type eq "patchcheck") { 3947b5f4aea6SSteven Rostedt $run_type = $patchcheck_type; 3948a75fececSSteven Rostedt } elsif ($test_type eq "bisect") { 3949b5f4aea6SSteven Rostedt $run_type = $bisect_type; 39500a05c769SSteven Rostedt } elsif ($test_type eq "config_bisect") { 3951b5f4aea6SSteven Rostedt $run_type = $config_bisect_type; 39524283b169SSteven Rostedt (Red Hat) } elsif ($test_type eq "make_min_config") { 39534283b169SSteven Rostedt (Red Hat) $run_type = ""; 39544283b169SSteven Rostedt (Red Hat) } elsif ($test_type eq "make_warnings_file") { 39554c4ab120SSteven Rostedt $run_type = ""; 39564c4ab120SSteven Rostedt } 39574c4ab120SSteven Rostedt 3958a75fececSSteven Rostedt # mistake in config file? 3959a75fececSSteven Rostedt if (!defined($run_type)) { 3960a75fececSSteven Rostedt $run_type = "ERROR"; 3961a75fececSSteven Rostedt } 39622545eb61SSteven Rostedt 3963e0a8742eSSteven Rostedt my $installme = ""; 3964e0a8742eSSteven Rostedt $installme = " no_install" if ($no_install); 3965e0a8742eSSteven Rostedt 39662545eb61SSteven Rostedt doprint "\n\n"; 3967e0a8742eSSteven Rostedt doprint "RUNNING TEST $i of $opt{NUM_TESTS} with option $test_type $run_type$installme\n\n"; 39687faafbd6SSteven Rostedt 3969921ed4c7SSteven Rostedt if (defined($pre_test)) { 3970921ed4c7SSteven Rostedt run_command $pre_test; 3971921ed4c7SSteven Rostedt } 3972921ed4c7SSteven Rostedt 39737faafbd6SSteven Rostedt unlink $dmesg; 39747faafbd6SSteven Rostedt unlink $buildlog; 3975a9dd5d63SRabin Vincent unlink $testlog; 39762545eb61SSteven Rostedt 3977250bae8bSSteven Rostedt if (defined($addconfig)) { 3978250bae8bSSteven Rostedt my $min = $minconfig; 39792b7d9b21SSteven Rostedt if (!defined($minconfig)) { 3980250bae8bSSteven Rostedt $min = ""; 3981250bae8bSSteven Rostedt } 3982250bae8bSSteven Rostedt run_command "cat $addconfig $min > $tmpdir/add_config" or 39832b7d9b21SSteven Rostedt dodie "Failed to create temp config"; 39849be2e6b5SSteven Rostedt $minconfig = "$tmpdir/add_config"; 39852b7d9b21SSteven Rostedt } 39862b7d9b21SSteven Rostedt 39876c5ee0beSSteven Rostedt if (defined($checkout)) { 39886c5ee0beSSteven Rostedt run_command "git checkout $checkout" or 39896c5ee0beSSteven Rostedt die "failed to checkout $checkout"; 39906c5ee0beSSteven Rostedt } 39916c5ee0beSSteven Rostedt 3992759a3cc6SSteven Rostedt $no_reboot = 0; 3993759a3cc6SSteven Rostedt 3994648a182cSSteven Rostedt # A test may opt to not reboot the box 3995648a182cSSteven Rostedt if ($reboot_on_success) { 3996759a3cc6SSteven Rostedt $reboot_success = 1; 3997648a182cSSteven Rostedt } 39984ab1cce5SSteven Rostedt 3999a75fececSSteven Rostedt if ($test_type eq "bisect") { 40005f9b6cedSSteven Rostedt bisect $i; 40015f9b6cedSSteven Rostedt next; 40020a05c769SSteven Rostedt } elsif ($test_type eq "config_bisect") { 40030a05c769SSteven Rostedt config_bisect $i; 40040a05c769SSteven Rostedt next; 4005a75fececSSteven Rostedt } elsif ($test_type eq "patchcheck") { 40066c5ee0beSSteven Rostedt patchcheck $i; 40076c5ee0beSSteven Rostedt next; 40084c4ab120SSteven Rostedt } elsif ($test_type eq "make_min_config") { 40094c4ab120SSteven Rostedt make_min_config $i; 40104c4ab120SSteven Rostedt next; 40114283b169SSteven Rostedt (Red Hat) } elsif ($test_type eq "make_warnings_file") { 40124283b169SSteven Rostedt (Red Hat) $no_reboot = 1; 40134283b169SSteven Rostedt (Red Hat) make_warnings_file $i; 40144283b169SSteven Rostedt (Red Hat) next; 40155f9b6cedSSteven Rostedt } 40165f9b6cedSSteven Rostedt 40177faafbd6SSteven Rostedt if ($build_type ne "nobuild") { 40187faafbd6SSteven Rostedt build $build_type or next; 40194283b169SSteven Rostedt (Red Hat) check_buildlog or next; 40202545eb61SSteven Rostedt } 40212545eb61SSteven Rostedt 4022cd8e368fSSteven Rostedt if ($test_type eq "install") { 4023cd8e368fSSteven Rostedt get_version; 4024cd8e368fSSteven Rostedt install; 4025cd8e368fSSteven Rostedt success $i; 4026cd8e368fSSteven Rostedt next; 4027cd8e368fSSteven Rostedt } 4028cd8e368fSSteven Rostedt 4029a75fececSSteven Rostedt if ($test_type ne "build") { 40307faafbd6SSteven Rostedt my $failed = 0; 4031ddf607e5SSteven Rostedt start_monitor_and_boot or $failed = 1; 4032a75fececSSteven Rostedt 4033a75fececSSteven Rostedt if (!$failed && $test_type ne "boot" && defined($run_test)) { 40347faafbd6SSteven Rostedt do_run_test or $failed = 1; 40355a391fbfSSteven Rostedt } 40367faafbd6SSteven Rostedt end_monitor; 40377faafbd6SSteven Rostedt next if ($failed); 4038a75fececSSteven Rostedt } 40395a391fbfSSteven Rostedt 40405f9b6cedSSteven Rostedt success $i; 404175c3fda7SSteven Rostedt} 40422545eb61SSteven Rostedt 4043921ed4c7SSteven Rostedtif (defined($final_post_ktest)) { 4044921ed4c7SSteven Rostedt run_command $final_post_ktest; 4045921ed4c7SSteven Rostedt} 4046921ed4c7SSteven Rostedt 40475c42fc5bSSteven Rostedtif ($opt{"POWEROFF_ON_SUCCESS"}) { 404875c3fda7SSteven Rostedt halt; 4049759a3cc6SSteven Rostedt} elsif ($opt{"REBOOT_ON_SUCCESS"} && !do_not_reboot && $reboot_success) { 4050bc7c5803SSteven Rostedt reboot_to_good; 4051648a182cSSteven Rostedt} elsif (defined($switch_to_good)) { 4052648a182cSSteven Rostedt # still need to get to the good kernel 4053648a182cSSteven Rostedt run_command $switch_to_good; 40545c42fc5bSSteven Rostedt} 405575c3fda7SSteven Rostedt 4056648a182cSSteven Rostedt 4057e48c5293SSteven Rostedtdoprint "\n $successes of $opt{NUM_TESTS} tests were successful\n\n"; 4058e48c5293SSteven Rostedt 40592545eb61SSteven Rostedtexit 0; 4060