summaryrefslogtreecommitdiff
path: root/tools/testing/selftests/drivers/net/netcons_torture.sh
blob: 2ce9ee3719d1aa221d1b6f99454c813321c71065 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
#!/usr/bin/env bash
# SPDX-License-Identifier: GPL-2.0

# Repeatedly send kernel messages, toggles netconsole targets on and off,
# creates and deletes targets in parallel, and toggles the source interface to
# simulate stress conditions.
#
# This test aims to verify the robustness of netconsole under dynamic
# configurations and concurrent operations.
#
# The major goal is to run this test with LOCKDEP, Kmemleak and KASAN to make
# sure no issues is reported.
#
# Author: Breno Leitao <leitao@debian.org>

set -euo pipefail

SCRIPTDIR=$(dirname "$(readlink -e "${BASH_SOURCE[0]}")")

source "${SCRIPTDIR}"/lib/sh/lib_netcons.sh

# Number of times the main loop run
ITERATIONS=${1:-150}

# Only test extended format
FORMAT="extended"
# And ipv6 only
IP_VERSION="ipv6"

# Create, enable and delete some targets.
create_and_delete_random_target() {
	COUNT=2
	RND_PREFIX=$(mktemp -u netcons_rnd_XXXX_)

	if [ -d "${NETCONS_CONFIGFS}/${RND_PREFIX}${COUNT}"  ] || \
	   [ -d "${NETCONS_CONFIGFS}/${RND_PREFIX}0" ]; then
		echo "Function didn't finish yet, skipping it." >&2
		return
	fi

	# enable COUNT targets
	for i in $(seq ${COUNT})
	do
		RND_TARGET="${RND_PREFIX}"${i}
		RND_TARGET_PATH="${NETCONS_CONFIGFS}"/"${RND_TARGET}"

		# Basic population so the target can come up
		_create_dynamic_target "${FORMAT}" "${RND_TARGET_PATH}"
	done

	echo "netconsole selftest: ${COUNT} additional targets were created" > /dev/kmsg
	# disable them all
	for i in $(seq ${COUNT})
	do
		RND_TARGET="${RND_PREFIX}"${i}
		RND_TARGET_PATH="${NETCONS_CONFIGFS}"/"${RND_TARGET}"
		if [[ $(cat "${RND_TARGET_PATH}/enabled") -eq 1 ]]
		then
			echo 0 > "${RND_TARGET_PATH}"/enabled
		fi
		rmdir "${RND_TARGET_PATH}"
	done
}

# Disable and enable the target mid-air, while messages
# are being transmitted.
toggle_netcons_target() {
	for i in $(seq 2)
	do
		if [ ! -d "${NETCONS_PATH}" ]
		then
			break
		fi
		echo 0 > "${NETCONS_PATH}"/enabled 2> /dev/null || true
		# Try to enable a bit harder, given it might fail to enable
		# Write to `enabled` might fail depending on the lock, which is
		# highly contentious here
		for _ in $(seq 5)
		do
			echo 1 > "${NETCONS_PATH}"/enabled 2> /dev/null || true
		done
	done
}

toggle_iface(){
	ip link set "${SRCIF}" down
	ip link set "${SRCIF}" up
}

# Start here

modprobe netdevsim 2> /dev/null || true
modprobe netconsole 2> /dev/null || true

# Check for basic system dependency and exit if not found
check_for_dependencies
# Set current loglevel to KERN_INFO(6), and default to KERN_NOTICE(5)
echo "6 5" > /proc/sys/kernel/printk
# Remove the namespace, interfaces and netconsole target on exit
trap cleanup EXIT
# Create one namespace and two interfaces
set_network "${IP_VERSION}"
# Create a dynamic target for netconsole
create_dynamic_target "${FORMAT}"

for i in $(seq "$ITERATIONS")
do
	for _ in $(seq 10)
	do
		echo "${MSG}: ${TARGET} ${i}" > /dev/kmsg
	done
	wait

	if (( i % 30 == 0 )); then
		toggle_netcons_target &
	fi

	if (( i % 50 == 0 )); then
		# create some targets, enable them, send msg and disable
		# all in a parallel thread
		create_and_delete_random_target &
	fi

	if (( i % 70 == 0 )); then
		toggle_iface &
	fi
done
wait

exit "${EXIT_STATUS}"