Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit aed972fb authored by Andrei Gherzan's avatar Andrei Gherzan Committed by Greg Kroah-Hartman
Browse files

selftests: net: udpgso_bench_tx: Cater for pending datagrams zerocopy benchmarking



[ Upstream commit 329c9cd769c2e306957df031efff656c40922c76 ]

The test tool can check that the zerocopy number of completions value is
valid taking into consideration the number of datagram send calls. This can
catch the system into a state where the datagrams are still in the system
(for example in a qdisk, waiting for the network interface to return a
completion notification, etc).

This change adds a retry logic of computing the number of completions up to
a configurable (via CLI) timeout (default: 2 seconds).

Fixes: 79ebc3c2 ("net/udpgso_bench_tx: options to exercise TX CMSG")
Signed-off-by: default avatarAndrei Gherzan <andrei.gherzan@canonical.com>
Cc: Willem de Bruijn <willemb@google.com>
Cc: Paolo Abeni <pabeni@redhat.com>
Reviewed-by: default avatarWillem de Bruijn <willemb@google.com>
Link: https://lore.kernel.org/r/20230201001612.515730-4-andrei.gherzan@canonical.com


Signed-off-by: default avatarPaolo Abeni <pabeni@redhat.com>
Signed-off-by: default avatarSasha Levin <sashal@kernel.org>
parent df1213a2
Loading
Loading
Loading
Loading
+27 −7
Original line number Diff line number Diff line
@@ -62,6 +62,7 @@ static int cfg_payload_len = (1472 * 42);
static int	cfg_port	= 8000;
static int	cfg_runtime_ms	= -1;
static bool	cfg_poll;
static int	cfg_poll_loop_timeout_ms = 2000;
static bool	cfg_segment;
static bool	cfg_sendmmsg;
static bool	cfg_tcp;
@@ -235,16 +236,17 @@ static void flush_errqueue_recv(int fd)
	}
}

static void flush_errqueue(int fd, const bool do_poll)
static void flush_errqueue(int fd, const bool do_poll,
			   unsigned long poll_timeout, const bool poll_err)
{
	if (do_poll) {
		struct pollfd fds = {0};
		int ret;

		fds.fd = fd;
		ret = poll(&fds, 1, 500);
		ret = poll(&fds, 1, poll_timeout);
		if (ret == 0) {
			if (cfg_verbose)
			if ((cfg_verbose) && (poll_err))
				fprintf(stderr, "poll timeout\n");
		} else if (ret < 0) {
			error(1, errno, "poll");
@@ -254,6 +256,20 @@ static void flush_errqueue(int fd, const bool do_poll)
	flush_errqueue_recv(fd);
}

static void flush_errqueue_retry(int fd, unsigned long num_sends)
{
	unsigned long tnow, tstop;
	bool first_try = true;

	tnow = gettimeofday_ms();
	tstop = tnow + cfg_poll_loop_timeout_ms;
	do {
		flush_errqueue(fd, true, tstop - tnow, first_try);
		first_try = false;
		tnow = gettimeofday_ms();
	} while ((stat_zcopies != num_sends) && (tnow < tstop));
}

static int send_tcp(int fd, char *data)
{
	int ret, done = 0, count = 0;
@@ -413,7 +429,8 @@ static int send_udp_segment(int fd, char *data)

static void usage(const char *filepath)
{
	error(1, 0, "Usage: %s [-46acmHPtTuvz] [-C cpu] [-D dst ip] [-l secs] [-M messagenr] [-p port] [-s sendsize] [-S gsosize]",
	error(1, 0, "Usage: %s [-46acmHPtTuvz] [-C cpu] [-D dst ip] [-l secs] "
		    "[-L secs] [-M messagenr] [-p port] [-s sendsize] [-S gsosize]",
		    filepath);
}

@@ -423,7 +440,7 @@ static void parse_opts(int argc, char **argv)
	int max_len, hdrlen;
	int c;

	while ((c = getopt(argc, argv, "46acC:D:Hl:mM:p:s:PS:tTuvz")) != -1) {
	while ((c = getopt(argc, argv, "46acC:D:Hl:L:mM:p:s:PS:tTuvz")) != -1) {
		switch (c) {
		case '4':
			if (cfg_family != PF_UNSPEC)
@@ -452,6 +469,9 @@ static void parse_opts(int argc, char **argv)
		case 'l':
			cfg_runtime_ms = strtoul(optarg, NULL, 10) * 1000;
			break;
		case 'L':
			cfg_poll_loop_timeout_ms = strtoul(optarg, NULL, 10) * 1000;
			break;
		case 'm':
			cfg_sendmmsg = true;
			break;
@@ -679,7 +699,7 @@ int main(int argc, char **argv)
			num_sends += send_udp(fd, buf[i]);
		num_msgs++;
		if ((cfg_zerocopy && ((num_msgs & 0xF) == 0)) || cfg_tx_tstamp)
			flush_errqueue(fd, cfg_poll);
			flush_errqueue(fd, cfg_poll, 500, true);

		if (cfg_msg_nr && num_msgs >= cfg_msg_nr)
			break;
@@ -698,7 +718,7 @@ int main(int argc, char **argv)
	} while (!interrupted && (cfg_runtime_ms == -1 || tnow < tstop));

	if (cfg_zerocopy || cfg_tx_tstamp)
		flush_errqueue(fd, true);
		flush_errqueue_retry(fd, num_sends);

	if (close(fd))
		error(1, errno, "close");