Add a testcase explicitly triggering the newly introduce
MPTCP_FULL_INFO getsockopt.
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 76 ++++++++++++++++++-
1 file changed, 74 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index 869c041c34f3..598e0f2c592c 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -86,9 +86,25 @@ struct mptcp_subflow_addrs {
#define MPTCP_SUBFLOW_ADDRS 3
#endif
+#ifndef MPTCP_FULL_INFO
+struct mptcp_subflow_info {
+ __u32 id;
+ struct mptcp_subflow_addrs addrs;
+};
+
+struct mptcp_subflow_full_info {
+ struct mptcp_subflow_info subflow_info;
+ struct tcp_info tcp_info;
+};
+
+#define MPTCP_FULL_INFO 4
+#endif
+
struct so_state {
struct mptcp_info mi;
struct mptcp_info last_sample;
+ struct tcp_info tcp_info;
+ struct mptcp_subflow_addrs addrs;
uint64_t mptcpi_rcv_delta;
uint64_t tcpi_rcv_delta;
bool pkt_stats_avail;
@@ -367,6 +383,8 @@ static void do_getsockopt_tcp_info(struct so_state *s, int fd, size_t r, size_t
olen -= sizeof(struct mptcp_subflow_data);
assert(olen == sizeof(struct tcp_info));
+ s->tcp_info = ti.ti[0];
+
if (ti.ti[0].tcpi_bytes_sent == w &&
ti.ti[0].tcpi_bytes_received == r)
goto done;
@@ -388,7 +406,7 @@ static void do_getsockopt_tcp_info(struct so_state *s, int fd, size_t r, size_t
do_getsockopt_bogus_sf_data(fd, MPTCP_TCPINFO);
}
-static void do_getsockopt_subflow_addrs(int fd)
+static void do_getsockopt_subflow_addrs(struct so_state *s, int fd)
{
struct sockaddr_storage remote, local;
socklen_t olen, rlen, llen;
@@ -435,6 +453,7 @@ static void do_getsockopt_subflow_addrs(int fd)
assert(memcmp(&local, &addrs.addr[0].ss_local, sizeof(local)) == 0);
assert(memcmp(&remote, &addrs.addr[0].ss_remote, sizeof(remote)) == 0);
+ s->addrs = addrs.addr[0];
memset(&addrs, 0, sizeof(addrs));
@@ -455,13 +474,66 @@ static void do_getsockopt_subflow_addrs(int fd)
do_getsockopt_bogus_sf_data(fd, MPTCP_SUBFLOW_ADDRS);
}
+static void do_getsockopt_mptcp_full_info(struct so_state *s, int fd)
+{
+ size_t data_size = 2 * sizeof(struct mptcp_subflow_full_info) +
+ sizeof(struct mptcp_subflow_data) +
+ sizeof(struct mptcp_info);
+ struct mptcp_subflow_full_info *sfi;
+ struct mptcp_subflow_data *sfd;
+ void *data = alloca(data_size);
+ struct mptcp_info *mi;
+ socklen_t olen;
+ int ret;
+
+ sfd = data;
+ memset(data, 0, data_size);
+
+ sfd->size_subflow_data = sizeof(struct mptcp_subflow_data);
+ sfd->size_user = sizeof(struct mptcp_subflow_full_info);
+ olen = data_size;
+
+ ret = getsockopt(fd, SOL_MPTCP, MPTCP_FULL_INFO, data, &olen);
+ if (ret < 0) {
+ if (errno == EOPNOTSUPP) {
+ fprintf(stderr, "\tMPTCP_FULL_INFO test skipped due to lack of kernel support\n");
+ return;
+ }
+ xerror("getsockopt MPTCP_FULL_INFO");
+ }
+
+ assert(olen <= data_size);
+ assert(sfd->size_user == sfd->size_kernel);
+ assert(sfd->size_user == sizeof(struct mptcp_subflow_full_info));
+ assert(sfd->num_subflows == 1);
+
+ assert(olen > (socklen_t)sizeof(struct mptcp_subflow_data));
+ olen -= sizeof(struct mptcp_subflow_data);
+ assert(olen > (socklen_t)sizeof(struct mptcp_info));
+ mi = data + sizeof(struct mptcp_subflow_data);
+ assert(mi->mptcpi_subflows == 0);
+ assert(mi->mptcpi_bytes_sent == s->last_sample.mptcpi_bytes_sent);
+ assert(mi->mptcpi_bytes_received == s->last_sample.mptcpi_bytes_received);
+
+ olen -= sizeof(struct mptcp_info);
+ assert(olen == sizeof(struct mptcp_subflow_full_info));
+ sfi = data + sizeof(struct mptcp_subflow_data) + sizeof(struct mptcp_info);
+ assert(sfi->subflow_info.id == 1);
+ assert(sfi->tcp_info.tcpi_bytes_sent == s->tcp_info.tcpi_bytes_sent);
+ assert(sfi->tcp_info.tcpi_bytes_received == s->tcp_info.tcpi_bytes_received);
+ assert(!memcmp(&sfi->subflow_info.addrs, &s->addrs, sizeof(struct mptcp_subflow_addrs)));
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
do_getsockopt_tcp_info(s, fd, r, w);
- do_getsockopt_subflow_addrs(fd);
+ do_getsockopt_subflow_addrs(s, fd);
+
+ if (r)
+ do_getsockopt_mptcp_full_info(s, fd);
}
static void connect_one_server(int fd, int pipefd)
--
2.40.1