#!/usr/bin/env bash # # Test wrapper run inside the VM set -o nounset set -o errexit set -o errtrace export PS4='+`basename ${BASH_SOURCE[0]}`:${LINENO}:${FUNCNAME[0]:+${FUNCNAME[0]}()}+ ' KERNEL_ARCH="" . /host/$ktest_env ktest_dir="/host/$ktest_dir" ktest_tmp="/host/$ktest_tmp" ktest_out="/host/$ktest_out" ln -sf $ktest_dir /ktest ln -sf $ktest_out /ktest-out # Some home directories are in weird places: mkdir -p $(dirname $home) ln -sf /host/$home $home ktest_no_cleanup_tmpdir=1 log_verbose "Testrunner starting" mkdir -p /root/.ssh cat $home/.ssh/id*.pub > /root/.ssh/authorized_keys chmod 600 /root/.ssh/authorized_keys ln -sf "/host/$ktest_kernel_binary/lib/modules" /lib/modules dmesg --console-on dmesg --console-level 8 echo 1 > /proc/sys/kernel/sysrq ulimit -c unlimited # Log file system visible to host # Core dump settings echo 1 > /proc/sys/fs/suid_dumpable echo "|/bin/cp --sparse=always /dev/stdin $ktest_out/core.%e.PID%p.SIG%s.TIME%t" > /proc/sys/kernel/core_pattern ulimit -c unlimited # Virtual block device tweaks echo none | tee /sys/block/sd*/queue/scheduler >/dev/null 2>&1 || true # Check if we are running the crashdump kernel if [[ -s /proc/vmcore ]]; then echo "Collecting crash dump..." cp --sparse=always /proc/vmcore "$ktest_out/vmcore" || true sync poweroff fi # If debugging crash dumps, add "console=hvc0" to the append line # below: if [[ $ktest_crashdump = 1 ]]; then kexec -p /host/$ktest_kernel_binary/vmlinuz --append="root=/dev/sda rw maxcpus=1" || true fi NR_REBOOTS=0 EXPECTED_REBOOT=0 [[ -e /NR_REBOOTS ]] && NR_REBOOTS=$( /dev/null if compgen -G "$ktest_tmp/*.deb" > /dev/null; then if ! output=$(dpkg -i $ktest_tmp/*.deb); then echo $output exit 1 fi fi for i in "${ktest_make_install[@]}"; do pushd "/host/$i" > /dev/null if [[ -f autogen.sh && ! -f configure ]]; then run_quiet "autogen $(basename $i)" ./autogen.sh fi if [[ -f configure && ! -f Makefile ]]; then run_quiet "configure $(basename $i)" ./configure fi run_quiet "building $(basename $i)" make -j $ktest_cpus run_quiet "installing $(basename $i)" make -j $ktest_cpus install popd > /dev/null done get_stratch_devs() { echo sfdisk -X gpt /dev/sdb } copy_to_host() { cat /sys/kernel/debug/tracing/trace > $ktest_out/trace.txt # Code coverage local gcov_dir=/sys/kernel/debug/gcov if [[ -d $gcov_dir ]]; then # find a destination dir that doesn't exist, so we can copy multiple # sets of gcov data from different tests/reboots and merge them later for i in {0..99}; do dst=$ktest_out/gcov.$i if [[ ! -d $dst ]]; then cp -dR $gcov_dir "$dst" break fi done fi sync } check_taint() { read taint < /proc/sys/kernel/tainted if [[ $taint != 0 ]]; then echo "Failure because kernel tainted - check log for warnings" echo "TEST FAILED" exit 0 fi } do_reboot() { copy_to_host check_taint echo $((NR_REBOOTS + 1)) | dd of=/EXPECTED_REBOOT oflag=direct 2> /dev/null echo b > /proc/sysrq-trigger } echo -n "Kernel version: " uname -r if [[ -z $ktest_tests ]]; then echo "No tests found" echo "TEST FAILED" exit 1 fi ktest_tests=$(echo $ktest_tests) if [[ $ktest_tests = "none" ]]; then echo "No tests to run" echo "TEST FAILED" exit 0 fi trap 'pkill -P $$ >/dev/null' EXIT cd /root export ktest_failfast export ktest_out set +e ret=0 iterations=0 while [[ $ret = 0 ]]; do /host/$ktest_test run-tests $ktest_tests ret=$? pkill -P $$ >/dev/null || true [[ $ret != 0 ]] && break [[ $ktest_loop = 1 ]] || break iterations=$((iterations + 1)) echo "SUCCESSFUL ITERATIONS $iterations" done copy_to_host check_taint echo -n "Kernel version: " uname -r if [[ $ret = 0 ]]; then echo "TEST SUCCESS" else echo "TEST FAILED" fi