1*053f45beSAndroid Build Coastguard Worker#!/bin/sh 2*053f45beSAndroid Build Coastguard Worker# SPDX-License-Identifier: GPL-2.0 3*053f45beSAndroid Build Coastguard Worker# 4*053f45beSAndroid Build Coastguard Worker# This reads tests.txt for the list of LKDTM tests to invoke. Any marked 5*053f45beSAndroid Build Coastguard Worker# with a leading "#" are skipped. The rest of the line after the 6*053f45beSAndroid Build Coastguard Worker# test name is either the text to look for in dmesg for a "success", 7*053f45beSAndroid Build Coastguard Worker# or the rationale for why a test is marked to be skipped. 8*053f45beSAndroid Build Coastguard Worker# 9*053f45beSAndroid Build Coastguard Workerset -e 10*053f45beSAndroid Build Coastguard WorkerTRIGGER=/sys/kernel/debug/provoke-crash/DIRECT 11*053f45beSAndroid Build Coastguard WorkerCLEAR_ONCE=/sys/kernel/debug/clear_warn_once 12*053f45beSAndroid Build Coastguard WorkerKSELFTEST_SKIP_TEST=4 13*053f45beSAndroid Build Coastguard Worker 14*053f45beSAndroid Build Coastguard Worker# Verify we have LKDTM available in the kernel. 15*053f45beSAndroid Build Coastguard Workerif [ ! -r $TRIGGER ] ; then 16*053f45beSAndroid Build Coastguard Worker /sbin/modprobe -q lkdtm || true 17*053f45beSAndroid Build Coastguard Worker if [ ! -r $TRIGGER ] ; then 18*053f45beSAndroid Build Coastguard Worker echo "Cannot find $TRIGGER (missing CONFIG_LKDTM?)" 19*053f45beSAndroid Build Coastguard Worker else 20*053f45beSAndroid Build Coastguard Worker echo "Cannot write $TRIGGER (need to run as root?)" 21*053f45beSAndroid Build Coastguard Worker fi 22*053f45beSAndroid Build Coastguard Worker # Skip this test 23*053f45beSAndroid Build Coastguard Worker exit $KSELFTEST_SKIP_TEST 24*053f45beSAndroid Build Coastguard Workerfi 25*053f45beSAndroid Build Coastguard Worker 26*053f45beSAndroid Build Coastguard Worker# Figure out which test to run from our script name. 27*053f45beSAndroid Build Coastguard Workertest=$(basename $0 .sh) 28*053f45beSAndroid Build Coastguard Worker# Look up details about the test from master list of LKDTM tests. 29*053f45beSAndroid Build Coastguard Workerline=$(grep -E '^#?'"$test"'\b' tests.txt) 30*053f45beSAndroid Build Coastguard Workerif [ -z "$line" ]; then 31*053f45beSAndroid Build Coastguard Worker echo "Skipped: missing test '$test' in tests.txt" 32*053f45beSAndroid Build Coastguard Worker exit $KSELFTEST_SKIP_TEST 33*053f45beSAndroid Build Coastguard Workerfi 34*053f45beSAndroid Build Coastguard Worker# Check that the test is known to LKDTM. 35*053f45beSAndroid Build Coastguard Workerif ! grep -E -q '^'"$test"'$' "$TRIGGER" ; then 36*053f45beSAndroid Build Coastguard Worker echo "Skipped: test '$test' missing in $TRIGGER!" 37*053f45beSAndroid Build Coastguard Worker exit $KSELFTEST_SKIP_TEST 38*053f45beSAndroid Build Coastguard Workerfi 39*053f45beSAndroid Build Coastguard Worker 40*053f45beSAndroid Build Coastguard Worker# Extract notes/expected output from test list. 41*053f45beSAndroid Build Coastguard Workertest=$(echo "$line" | cut -d" " -f1) 42*053f45beSAndroid Build Coastguard Workerif echo "$line" | grep -q ' ' ; then 43*053f45beSAndroid Build Coastguard Worker expect=$(echo "$line" | cut -d" " -f2-) 44*053f45beSAndroid Build Coastguard Workerelse 45*053f45beSAndroid Build Coastguard Worker expect="" 46*053f45beSAndroid Build Coastguard Workerfi 47*053f45beSAndroid Build Coastguard Worker 48*053f45beSAndroid Build Coastguard Worker# If the test is commented out, report a skip 49*053f45beSAndroid Build Coastguard Workerif echo "$test" | grep -q '^#' ; then 50*053f45beSAndroid Build Coastguard Worker test=$(echo "$test" | cut -c2-) 51*053f45beSAndroid Build Coastguard Worker if [ -z "$expect" ]; then 52*053f45beSAndroid Build Coastguard Worker expect="crashes entire system" 53*053f45beSAndroid Build Coastguard Worker fi 54*053f45beSAndroid Build Coastguard Worker echo "Skipping $test: $expect" 55*053f45beSAndroid Build Coastguard Worker exit $KSELFTEST_SKIP_TEST 56*053f45beSAndroid Build Coastguard Workerfi 57*053f45beSAndroid Build Coastguard Worker 58*053f45beSAndroid Build Coastguard Worker# If no expected output given, assume an Oops with back trace is success. 59*053f45beSAndroid Build Coastguard Workerrepeat=1 60*053f45beSAndroid Build Coastguard Workerif [ -z "$expect" ]; then 61*053f45beSAndroid Build Coastguard Worker expect="call trace:" 62*053f45beSAndroid Build Coastguard Workerelse 63*053f45beSAndroid Build Coastguard Worker if echo "$expect" | grep -q '^repeat:' ; then 64*053f45beSAndroid Build Coastguard Worker repeat=$(echo "$expect" | cut -d' ' -f1 | cut -d: -f2) 65*053f45beSAndroid Build Coastguard Worker expect=$(echo "$expect" | cut -d' ' -f2-) 66*053f45beSAndroid Build Coastguard Worker fi 67*053f45beSAndroid Build Coastguard Workerfi 68*053f45beSAndroid Build Coastguard Worker 69*053f45beSAndroid Build Coastguard Worker# Prepare log for report checking 70*053f45beSAndroid Build Coastguard WorkerLOG=$(mktemp --tmpdir -t lkdtm-log-XXXXXX) 71*053f45beSAndroid Build Coastguard WorkerDMESG=$(mktemp --tmpdir -t lkdtm-dmesg-XXXXXX) 72*053f45beSAndroid Build Coastguard Workercleanup() { 73*053f45beSAndroid Build Coastguard Worker rm -f "$LOG" "$DMESG" 74*053f45beSAndroid Build Coastguard Worker} 75*053f45beSAndroid Build Coastguard Workertrap cleanup EXIT 76*053f45beSAndroid Build Coastguard Worker 77*053f45beSAndroid Build Coastguard Worker# Reset WARN_ONCE counters so we trip it each time this runs. 78*053f45beSAndroid Build Coastguard Workerif [ -w $CLEAR_ONCE ] ; then 79*053f45beSAndroid Build Coastguard Worker echo 1 > $CLEAR_ONCE 80*053f45beSAndroid Build Coastguard Workerfi 81*053f45beSAndroid Build Coastguard Worker 82*053f45beSAndroid Build Coastguard Worker# Save existing dmesg so we can detect new content below 83*053f45beSAndroid Build Coastguard Workerdmesg > "$DMESG" 84*053f45beSAndroid Build Coastguard Worker 85*053f45beSAndroid Build Coastguard Worker# Since the kernel is likely killing the process writing to the trigger 86*053f45beSAndroid Build Coastguard Worker# file, it must not be the script's shell itself. i.e. we cannot do: 87*053f45beSAndroid Build Coastguard Worker# echo "$test" >"$TRIGGER" 88*053f45beSAndroid Build Coastguard Worker# Instead, use "cat" to take the signal. Since the shell will yell about 89*053f45beSAndroid Build Coastguard Worker# the signal that killed the subprocess, we must ignore the failure and 90*053f45beSAndroid Build Coastguard Worker# continue. However we don't silence stderr since there might be other 91*053f45beSAndroid Build Coastguard Worker# useful details reported there in the case of other unexpected conditions. 92*053f45beSAndroid Build Coastguard Workerfor i in $(seq 1 $repeat); do 93*053f45beSAndroid Build Coastguard Worker echo "$test" | cat >"$TRIGGER" || true 94*053f45beSAndroid Build Coastguard Workerdone 95*053f45beSAndroid Build Coastguard Worker 96*053f45beSAndroid Build Coastguard Worker# Record and dump the results 97*053f45beSAndroid Build Coastguard Workerdmesg | comm --nocheck-order -13 "$DMESG" - > "$LOG" || true 98*053f45beSAndroid Build Coastguard Worker 99*053f45beSAndroid Build Coastguard Workercat "$LOG" 100*053f45beSAndroid Build Coastguard Worker# Check for expected output 101*053f45beSAndroid Build Coastguard Workerif grep -E -qi "$expect" "$LOG" ; then 102*053f45beSAndroid Build Coastguard Worker echo "$test: saw '$expect': ok" 103*053f45beSAndroid Build Coastguard Worker exit 0 104*053f45beSAndroid Build Coastguard Workerelse 105*053f45beSAndroid Build Coastguard Worker if grep -E -qi XFAIL: "$LOG" ; then 106*053f45beSAndroid Build Coastguard Worker echo "$test: saw 'XFAIL': [SKIP]" 107*053f45beSAndroid Build Coastguard Worker exit $KSELFTEST_SKIP_TEST 108*053f45beSAndroid Build Coastguard Worker else 109*053f45beSAndroid Build Coastguard Worker echo "$test: missing '$expect': [FAIL]" 110*053f45beSAndroid Build Coastguard Worker exit 1 111*053f45beSAndroid Build Coastguard Worker fi 112*053f45beSAndroid Build Coastguard Workerfi 113