[PATCH net-next 2/2] selftests: drv-net: let ethtool stats settle before reading

Jakub Kicinski <[email protected]>
Newsgroups org.kernel.vger.linux-kselftest,org.kernel.vger.netdev
Message-ID <[email protected]>
Some devices refresh the statistics exposed via ethtool only
periodically, every stats-block-usecs (as reported by ethtool -c).
ethtool_std_stats and ethtool_rmon sample the counters immediately
after generating traffic, so on such devices they can read stale
values and fail with a delta short of the packets just sent.

Add a hw_stats_settle() helper which sleeps for 1.25x the configured
stats-block-usecs (defaulting to 20ms when the device reports no, or
a zero, period). Use it for ethtool std stats and RMON.
The 1.25x/20msec heuristic matches what the Python tests do.

Signed-off-by: Jakub Kicinski <[email protected]>
---
CC: [email protected]
CC: [email protected]
CC: [email protected]
CC: [email protected]
CC: [email protected]
CC: [email protected]
CC: [email protected]
---
 .../selftests/drivers/net/hw/ethtool_rmon.sh      |  2 ++
 .../selftests/drivers/net/hw/ethtool_std_stats.sh |  2 ++
 tools/testing/selftests/net/forwarding/lib.sh     | 15 +++++++++++++++
 3 files changed, 19 insertions(+)

diff --git a/tools/testing/selftests/drivers/net/hw/ethtool_rmon.sh b/tools/testing/selftests/drivers/net/hw/ethtool_rmon.sh
index 2ec19edddfaa..a074834cbe59 100755
--- a/tools/testing/selftests/drivers/net/hw/ethtool_rmon.sh
+++ b/tools/testing/selftests/drivers/net/hw/ethtool_rmon.sh
@@ -65,6 +65,8 @@ bucket_test()
 	run_on "$iface" \
 		"$MZ" "$iface" -q -c "$num_tx" -p "$len" -a own -b bcast -d 10us
 
+	hw_stats_settle "$iface"
+
 	after=$(run_on "$iface" ethtool --json -S "$iface" --groups rmon | \
 		jq -r ".[0].rmon[\"${set}-pktsNtoM\"][$bucket].val")
 
diff --git a/tools/testing/selftests/drivers/net/hw/ethtool_std_stats.sh b/tools/testing/selftests/drivers/net/hw/ethtool_std_stats.sh
index 1b329b3f60c2..09f8128c51f3 100755
--- a/tools/testing/selftests/drivers/net/hw/ethtool_std_stats.sh
+++ b/tools/testing/selftests/drivers/net/hw/ethtool_std_stats.sh
@@ -48,6 +48,8 @@ traffic_test()
 	# shellcheck disable=SC2086 # needs split options
 	run_on "$neigh" "$MZ" "$neigh" -q -d 10usec -c "$num_rx" $pkt_format
 
+	hw_stats_settle "$int"
+
 	for i in "${!counters[@]}"; do
 		read -r int grp cnt target exact_check xfail_message \
 			<<< "${counters[$i]}"
diff --git a/tools/testing/selftests/net/forwarding/lib.sh b/tools/testing/selftests/net/forwarding/lib.sh
index ac8358bcb22c..05acd4011456 100644
--- a/tools/testing/selftests/net/forwarding/lib.sh
+++ b/tools/testing/selftests/net/forwarding/lib.sh
@@ -406,6 +406,21 @@ get_ifname_by_ip()
 	__run_on "$target" ip -j addr show to "$ip_addr" | jq -r '.[].ifname'
 }
 
+# Wait for the device to refresh its HW statistics. Devices latch the stats
+# reported via ethtool only every stats-block-usecs, so sample after that.
+hw_stats_settle()
+{
+	local iface=$1; shift
+	local usecs
+
+	# Match only a non-zero integer; 0 or "n/a" use default (20msec)
+	usecs=$(run_on "$iface" ethtool -c "$iface" 2>/dev/null | \
+		sed -n 's/^stats-block-usecs:[[:space:]]*\([1-9][0-9]*\)$/\1/p')
+	usecs=${usecs:-20000}
+
+	sleep "$(echo "$usecs * 1.25 / 1000 / 1000" | bc -l)"
+}
+
 # Whether the test is conforming to the requirements and usage described in
 # drivers/net/README.rst.
 : "${DRIVER_TEST_CONFORMANT:=no}"
-- 
2.55.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.