* [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options
@ 2025-08-21 8:54 Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 01/10] selftests: mptcp: sockopt: improve test output clarity Geliang Tang
` (11 more replies)
0 siblings, 12 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
v2:
- IP_FREEBIND/IPV6_FREEBIND are set in do_getsockopt_transparent, fix
it.
- Use "for" loops in mptcp_sockopt.sh.
- Move "add IP_TOS socket option test" out of this set.
- some cleanups.
This series significantly expands MPTCP socket option test coverage
by adding validation for 10 more socket options:
1. SO_REUSEADDR/SO_REUSEPORT - Test socket reuse capabilities
2. SO_BINDTODEVICE/SO_BINDTOIFINDEX - Validate interface binding
3. IP_TOS - Verify Type of Service handling
4. IP_FREEBIND - Test free address binding
5. IP_TRANSPARENT - Validate transparent proxying
6. IP_BIND_ADDRESS_NO_PORT - Test deferred port binding
7. IP_LOCAL_PORT_RANGE - Check local port range restriction
8. IPV6_V6ONLY - Verify IPv6-only sockets
Each commit systematically adds:
- Setsockopt/getsockopt operations in mptcp_sockopt.c
- Dedicated test cases in mptcp_sockopt.sh
- IPv4 and IPv6 coverage
- Error handling and edge case validation
The new tests verify that MPTCP correctly propagates socket options to
subflows and maintains consistent behavior across address families.
Link: https://github.com/multipath-tcp/mptcp_net-next/issues/525
Geliang Tang (10):
selftests: mptcp: sockopt: improve test output clarity
selftests: mptcp: sockopt: add SO_REUSEADDR test helper
selftests: mptcp: sockopt: add SO_REUSEPORT test
selftests: mptcp: sockopt: add SO_BINDTODEVICE test
selftests: mptcp: sockopt: add SO_BINDTOIFINDEX test
selftests: mptcp: sockopt: add IP_FREEBIND tests
selftests: mptcp: sockopt: add IP_TRANSPARENT tests
selftests: mptcp: sockopt: add IP_BIND_ADDRESS_NO_PORT test
selftests: mptcp: sockopt: add IP_LOCAL_PORT_RANGE test
selftests: mptcp: sockopt: add IPV6_V6ONLY test
.../selftests/net/mptcp/mptcp_sockopt.c | 257 +++++++++++++++++-
.../selftests/net/mptcp/mptcp_sockopt.sh | 37 ++-
2 files changed, 282 insertions(+), 12 deletions(-)
--
2.48.1
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 01/10] selftests: mptcp: sockopt: improve test output clarity
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 02/10] selftests: mptcp: sockopt: add SO_REUSEADDR test helper Geliang Tang
` (10 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Refine test output to print detailed titles for SOL_MPTCP socket option
tests in both IPv4 and IPv6 contexts. This enhances readability and
distinctly separates v4/v6 results. The output now explicitly labels
each test phase and result, making failures easier to identify.
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.sh | 27 +++++++++++++------
1 file changed, 19 insertions(+), 8 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 418a903c3a4d..003d218defa8 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -261,28 +261,37 @@ do_mptcp_sockopt_tests()
ip netns exec "$ns_sbox" ./mptcp_sockopt
lret=$?
- print_title "SOL_MPTCP sockopt v4"
+ mptcp_lib_print_info "sockopt v4"
if [ $lret -ne 0 ]; then
- mptcp_lib_pr_fail
+ mptcp_lib_pr_fail "sockopt v4"
mptcp_lib_result_fail "sockopt v4"
ret=$lret
return
fi
- mptcp_lib_pr_ok
- mptcp_lib_result_pass "sockopt v4"
+
+ for opt in "SOL_MPTCP"; do
+ print_title "$opt sockopt v4"
+ mptcp_lib_pr_ok
+ mptcp_lib_result_pass "$opt sockopt v4"
+ done
ip netns exec "$ns_sbox" ./mptcp_sockopt -6
lret=$?
- print_title "SOL_MPTCP sockopt v6"
+ mptcp_lib_print_info "sockopt v6"
if [ $lret -ne 0 ]; then
- mptcp_lib_pr_fail
+ mptcp_lib_pr_fail "sockopt v6"
mptcp_lib_result_fail "sockopt v6"
ret=$lret
return
fi
- mptcp_lib_pr_ok
- mptcp_lib_result_pass "sockopt v6"
+
+ for opt in "SOL_MPTCP"; do
+ print_title "$opt sockopt v6"
+ mptcp_lib_pr_ok
+ mptcp_lib_result_pass "$opt sockopt v6"
+ done
+
}
run_tests()
@@ -329,6 +338,8 @@ do_tcpinq_tests()
return
fi
+ mptcp_lib_print_info "sockopt TCP_INQ"
+
local args
for args in "-t tcp" "-r tcp"; do
do_tcpinq_test $args
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 02/10] selftests: mptcp: sockopt: add SO_REUSEADDR test helper
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 01/10] selftests: mptcp: sockopt: improve test output clarity Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 03/10] selftests: mptcp: sockopt: add SO_REUSEPORT test Geliang Tang
` (9 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Introduce helper functions to set and verify the SO_REUSEADDR socket
option. This includes:
- do_setsockopt_reuseaddr() to set the option
- do_getsockopt_reuseaddr() to validate the value
- Integration into IPv4/IPv6 test flows
- Explicit result reporting in the test script
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 34 ++++++++++++++++---
.../selftests/net/mptcp/mptcp_sockopt.sh | 7 ++--
2 files changed, 34 insertions(+), 7 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index e934dd26a59d..a91709aeca06 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -182,6 +182,19 @@ static void xgetaddrinfo(const char *node, const char *service,
}
}
+static void do_setsockopt_reuseaddr(int fd)
+{
+ int one = 1;
+
+ if (setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &one, sizeof(one)))
+ perror("setsockopt(SO_REUSEADDR)");
+}
+
+static void do_setsockopts(int fd)
+{
+ do_setsockopt_reuseaddr(fd);
+}
+
static int sock_listen_mptcp(const char * const listenaddr,
const char * const port)
{
@@ -195,7 +208,6 @@ static int sock_listen_mptcp(const char * const listenaddr,
hints.ai_family = pf;
struct addrinfo *a, *addr;
- int one = 1;
xgetaddrinfo(listenaddr, port, &hints, &addr);
hints.ai_family = pf;
@@ -205,9 +217,7 @@ static int sock_listen_mptcp(const char * const listenaddr,
if (sock < 0)
continue;
- if (-1 == setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &one,
- sizeof(one)))
- perror("setsockopt");
+ do_setsockopts(sock);
if (bind(sock, a->ai_addr, a->ai_addrlen) == 0)
break; /* success */
@@ -246,6 +256,8 @@ static int sock_connect_mptcp(const char * const remoteaddr,
if (sock < 0)
continue;
+ do_setsockopts(sock);
+
if (connect(sock, a->ai_addr, a->ai_addrlen) == 0)
break; /* success */
@@ -554,6 +566,18 @@ static void do_getsockopt_mptcp_full_info(struct so_state *s, int fd)
assert(!memcmp(&sfinfo->addrs, &s->addrs, sizeof(struct mptcp_subflow_addrs)));
}
+static void do_getsockopt_reuseaddr(int fd)
+{
+ socklen_t len;
+ int reuse;
+
+ len = sizeof(reuse);
+ if (getsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &reuse, &len))
+ perror("getsockopt(SO_REUSEADDR)");
+
+ assert(reuse == 1);
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -564,6 +588,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
if (r)
do_getsockopt_mptcp_full_info(s, fd);
+
+ do_getsockopt_reuseaddr(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 003d218defa8..da6c261275ec 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -269,7 +269,8 @@ do_mptcp_sockopt_tests()
return
fi
- for opt in "SOL_MPTCP"; do
+ for opt in "SOL_MPTCP" \
+ "SO_REUSEADDR"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -286,12 +287,12 @@ do_mptcp_sockopt_tests()
return
fi
- for opt in "SOL_MPTCP"; do
+ for opt in "SOL_MPTCP" \
+ "SO_REUSEADDR"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
done
-
}
run_tests()
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 03/10] selftests: mptcp: sockopt: add SO_REUSEPORT test
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 01/10] selftests: mptcp: sockopt: improve test output clarity Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 02/10] selftests: mptcp: sockopt: add SO_REUSEADDR test helper Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 04/10] selftests: mptcp: sockopt: add SO_BINDTODEVICE test Geliang Tang
` (8 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Implement comprehensive testing for the SO_REUSEPORT socket option:
- Setsockopt and getsockopt helpers for SO_REUSEPORT
- Verification of the set value
- Integration into both client/server workflows
- IPv4 and IPv6 test coverage
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 23 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 4 ++--
2 files changed, 25 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index a91709aeca06..816d71706f7d 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -190,9 +190,18 @@ static void do_setsockopt_reuseaddr(int fd)
perror("setsockopt(SO_REUSEADDR)");
}
+static void do_setsockopt_reuseport(int fd)
+{
+ int one = 1;
+
+ if (setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &one, sizeof(one)))
+ perror("setsockopt(SO_REUSEPORT)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
+ do_setsockopt_reuseport(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -578,6 +587,18 @@ static void do_getsockopt_reuseaddr(int fd)
assert(reuse == 1);
}
+static void do_getsockopt_reuseport(int fd)
+{
+ socklen_t len;
+ int reuse;
+
+ len = sizeof(reuse);
+ if (getsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &reuse, &len))
+ perror("getsockopt(SO_REUSEPORT)");
+
+ assert(reuse == 1);
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -590,6 +611,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_mptcp_full_info(s, fd);
do_getsockopt_reuseaddr(fd);
+
+ do_getsockopt_reuseport(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index da6c261275ec..1c357ed757d6 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -270,7 +270,7 @@ do_mptcp_sockopt_tests()
fi
for opt in "SOL_MPTCP" \
- "SO_REUSEADDR"; do
+ "SO_REUSEADDR" "SO_REUSEPORT"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -288,7 +288,7 @@ do_mptcp_sockopt_tests()
fi
for opt in "SOL_MPTCP" \
- "SO_REUSEADDR"; do
+ "SO_REUSEADDR" "SO_REUSEPORT"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 04/10] selftests: mptcp: sockopt: add SO_BINDTODEVICE test
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (2 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 03/10] selftests: mptcp: sockopt: add SO_REUSEPORT test Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 05/10] selftests: mptcp: sockopt: add SO_BINDTOIFINDEX test Geliang Tang
` (7 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Add tests for the SO_BINDTODEVICE socket option:
- Binds sockets to the loopback device ("lo")
- Verifies the binding via getsockopt
- Includes IPv4 and IPv6 test cases
- Reports results explicitly in the test script
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 25 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 6 +++--
2 files changed, 29 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index 816d71706f7d..df4f85f129f7 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -23,6 +23,7 @@
#include <netdb.h>
#include <netinet/in.h>
+#include <net/if.h>
#include <linux/tcp.h>
@@ -198,10 +199,20 @@ static void do_setsockopt_reuseport(int fd)
perror("setsockopt(SO_REUSEPORT)");
}
+static void do_setsockopt_bindtodevice(int fd)
+{
+ const char *interface = "lo";
+
+ if (setsockopt(fd, SOL_SOCKET, SO_BINDTODEVICE,
+ interface, strlen(interface)))
+ perror("setsockopt(SO_BINDTODEVICE)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
do_setsockopt_reuseport(fd);
+ do_setsockopt_bindtodevice(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -599,6 +610,18 @@ static void do_getsockopt_reuseport(int fd)
assert(reuse == 1);
}
+static void do_getsockopt_bindtodevice(int fd)
+{
+ char ifname[IFNAMSIZ] = { 0 };
+ socklen_t len;
+
+ len = sizeof(ifname);
+ if (getsockopt(fd, SOL_SOCKET, SO_BINDTODEVICE, ifname, &len))
+ die_perror("getsockopt(SO_BINDTODEVICE)");
+
+ assert(!memcmp(ifname, "lo", len));
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -613,6 +636,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_reuseaddr(fd);
do_getsockopt_reuseport(fd);
+
+ do_getsockopt_bindtodevice(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 1c357ed757d6..44342ce6fd16 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -270,7 +270,8 @@ do_mptcp_sockopt_tests()
fi
for opt in "SOL_MPTCP" \
- "SO_REUSEADDR" "SO_REUSEPORT"; do
+ "SO_REUSEADDR" "SO_REUSEPORT" \
+ "SO_BINDTODEVICE"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -288,7 +289,8 @@ do_mptcp_sockopt_tests()
fi
for opt in "SOL_MPTCP" \
- "SO_REUSEADDR" "SO_REUSEPORT"; do
+ "SO_REUSEADDR" "SO_REUSEPORT" \
+ "SO_BINDTODEVICE"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 05/10] selftests: mptcp: sockopt: add SO_BINDTOIFINDEX test
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (3 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 04/10] selftests: mptcp: sockopt: add SO_BINDTODEVICE test Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 06/10] selftests: mptcp: sockopt: add IP_FREEBIND tests Geliang Tang
` (6 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Implement tests for the SO_BINDTOIFINDEX socket option:
- Uses ioctl to get the loopback interface index
- Sets the option to bind to "lo"
- Validates the bound index via getsockopt
- Supports both IPv4 and IPv6
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 41 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 4 +-
2 files changed, 43 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index df4f85f129f7..25456e540cad 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -20,6 +20,7 @@
#include <sys/socket.h>
#include <sys/types.h>
#include <sys/wait.h>
+#include <sys/ioctl.h>
#include <netdb.h>
#include <netinet/in.h>
@@ -208,11 +209,36 @@ static void do_setsockopt_bindtodevice(int fd)
perror("setsockopt(SO_BINDTODEVICE)");
}
+static int get_ifindex(int fd, const char *ifname)
+{
+ struct ifreq ifr;
+
+ memset(&ifr, 0, sizeof(ifr));
+ strncpy(ifr.ifr_name, ifname, IFNAMSIZ);
+
+ if (ioctl(fd, SIOCGIFINDEX, &ifr) < 0) {
+ perror("ioctl");
+ return -1;
+ }
+
+ return ifr.ifr_ifindex;
+}
+
+static void do_setsockopt_bindtoifindex(int fd)
+{
+ int ifindex = get_ifindex(fd, "lo");
+
+ if (setsockopt(fd, SOL_SOCKET, SO_BINDTOIFINDEX,
+ &ifindex, sizeof(ifindex)))
+ perror("setsockopt(SO_BINDTOIFINDEX)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
do_setsockopt_reuseport(fd);
do_setsockopt_bindtodevice(fd);
+ do_setsockopt_bindtoifindex(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -622,6 +648,19 @@ static void do_getsockopt_bindtodevice(int fd)
assert(!memcmp(ifname, "lo", len));
}
+static void do_getsockopt_bindtoifindex(int fd)
+{
+ socklen_t len;
+ int ifindex;
+
+ len = sizeof(ifindex);
+ if (getsockopt(fd, SOL_SOCKET, SO_BINDTOIFINDEX,
+ &ifindex, &len))
+ die_perror("getsockopt(SO_BINDTOIFINDEX)");
+
+ assert(ifindex == get_ifindex(fd, "lo"));
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -638,6 +677,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_reuseport(fd);
do_getsockopt_bindtodevice(fd);
+
+ do_getsockopt_bindtoifindex(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 44342ce6fd16..7f2effd82af8 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -271,7 +271,7 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
- "SO_BINDTODEVICE"; do
+ "SO_BINDTODEVICE" "SO_BINDTOIFINDEX"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -290,7 +290,7 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
- "SO_BINDTODEVICE"; do
+ "SO_BINDTODEVICE" "SO_BINDTOIFINDEX"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 06/10] selftests: mptcp: sockopt: add IP_FREEBIND tests
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (4 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 05/10] selftests: mptcp: sockopt: add SO_BINDTOIFINDEX test Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 07/10] selftests: mptcp: sockopt: add IP_TRANSPARENT tests Geliang Tang
` (5 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Add tests for IP_FREEBIND (IPv4) and IPV6_FREEBIND (IPv6):
- Setsockopt helpers to enable FREEBIND
- Getsockopt validation of the enabled state
- Test integration for both address families
- Script result reporting
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 27 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 6 +++--
2 files changed, 31 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index 25456e540cad..e9ef908dc270 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -233,12 +233,23 @@ static void do_setsockopt_bindtoifindex(int fd)
perror("setsockopt(SO_BINDTOIFINDEX)");
}
+static void do_setsockopt_freebind(int fd)
+{
+ int optname = (pf == AF_INET ? IP_FREEBIND : IPV6_FREEBIND);
+ int level = (pf == AF_INET ? SOL_IP : SOL_IPV6);
+ int enable = 1;
+
+ if (setsockopt(fd, level, optname, &enable, sizeof(enable)))
+ perror("setsockopt(IP(V6)_FREEBIND)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
do_setsockopt_reuseport(fd);
do_setsockopt_bindtodevice(fd);
do_setsockopt_bindtoifindex(fd);
+ do_setsockopt_freebind(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -661,6 +672,20 @@ static void do_getsockopt_bindtoifindex(int fd)
assert(ifindex == get_ifindex(fd, "lo"));
}
+static void do_getsockopt_freebind(int fd)
+{
+ int optname = (pf == AF_INET ? IP_FREEBIND : IPV6_FREEBIND);
+ int level = (pf == AF_INET ? SOL_IP : SOL_IPV6);
+ socklen_t len;
+ int enable;
+
+ len = sizeof(enable);
+ if (getsockopt(fd, level, optname, &enable, &len))
+ die_perror("getsockopt(IP(V6)_FREEBIND)");
+
+ assert(enable == 1);
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -679,6 +704,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_bindtodevice(fd);
do_getsockopt_bindtoifindex(fd);
+
+ do_getsockopt_freebind(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 7f2effd82af8..193f4d4dc41a 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -271,7 +271,8 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
- "SO_BINDTODEVICE" "SO_BINDTOIFINDEX"; do
+ "SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
+ "IP_FREEBIND"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -290,7 +291,8 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
- "SO_BINDTODEVICE" "SO_BINDTOIFINDEX"; do
+ "SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
+ "IPV6_FREEBIND"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 07/10] selftests: mptcp: sockopt: add IP_TRANSPARENT tests
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (5 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 06/10] selftests: mptcp: sockopt: add IP_FREEBIND tests Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 08/10] selftests: mptcp: sockopt: add IP_BIND_ADDRESS_NO_PORT test Geliang Tang
` (4 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Implement tests for transparent socket options:
- IP_TRANSPARENT (IPv4) and IPV6_TRANSPARENT (IPv6)
- Setsockopt and getsockopt helpers
- State verification after setting
- IPv4/IPv6 coverage in test script
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 27 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 4 +--
2 files changed, 29 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index e9ef908dc270..ccc072005118 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -243,6 +243,16 @@ static void do_setsockopt_freebind(int fd)
perror("setsockopt(IP(V6)_FREEBIND)");
}
+static void do_setsockopt_transparent(int fd)
+{
+ int optname = (pf == AF_INET ? IP_TRANSPARENT : IPV6_TRANSPARENT);
+ int level = (pf == AF_INET ? SOL_IP : SOL_IPV6);
+ int enable = 1;
+
+ if (setsockopt(fd, level, optname, &enable, sizeof(enable)))
+ perror("setsockopt(IP(V6)_TRANSPARENT)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
@@ -250,6 +260,7 @@ static void do_setsockopts(int fd)
do_setsockopt_bindtodevice(fd);
do_setsockopt_bindtoifindex(fd);
do_setsockopt_freebind(fd);
+ do_setsockopt_transparent(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -686,6 +697,20 @@ static void do_getsockopt_freebind(int fd)
assert(enable == 1);
}
+static void do_getsockopt_transparent(int fd)
+{
+ int optname = (pf == AF_INET ? IP_TRANSPARENT : IPV6_TRANSPARENT);
+ int level = (pf == AF_INET ? SOL_IP : SOL_IPV6);
+ socklen_t len;
+ int enable;
+
+ len = sizeof(enable);
+ if (getsockopt(fd, level, optname, &enable, &len))
+ die_perror("getsockopt(IP(V6)_TRANSPARENT)");
+
+ assert(enable == 1);
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -706,6 +731,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_bindtoifindex(fd);
do_getsockopt_freebind(fd);
+
+ do_getsockopt_transparent(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 193f4d4dc41a..da02769fbb2b 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -272,7 +272,7 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
"SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
- "IP_FREEBIND"; do
+ "IP_FREEBIND" "IP_TRANSPARENT"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -292,7 +292,7 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
"SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
- "IPV6_FREEBIND"; do
+ "IPV6_FREEBIND" "IPV6_TRANSPARENT"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 08/10] selftests: mptcp: sockopt: add IP_BIND_ADDRESS_NO_PORT test
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (6 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 07/10] selftests: mptcp: sockopt: add IP_TRANSPARENT tests Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 09/10] selftests: mptcp: sockopt: add IP_LOCAL_PORT_RANGE test Geliang Tang
` (3 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Add tests for the IP_BIND_ADDRESS_NO_PORT socket option:
- Enables the option via setsockopt
- Verifies the enabled state via getsockopt
- Includes tests for both IPv4 and IPv6
- Updates test script output
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 25 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 6 +++--
2 files changed, 29 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index ccc072005118..ca1a40492aa4 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -253,6 +253,15 @@ static void do_setsockopt_transparent(int fd)
perror("setsockopt(IP(V6)_TRANSPARENT)");
}
+static void do_setsockopt_bind_address_no_port(int fd)
+{
+ int enable = 1;
+
+ if (setsockopt(fd, SOL_IP, IP_BIND_ADDRESS_NO_PORT, &enable,
+ sizeof(enable)))
+ perror("setsockopt(IP_BIND_ADDRESS_NO_PORT)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
@@ -261,6 +270,7 @@ static void do_setsockopts(int fd)
do_setsockopt_bindtoifindex(fd);
do_setsockopt_freebind(fd);
do_setsockopt_transparent(fd);
+ do_setsockopt_bind_address_no_port(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -711,6 +721,19 @@ static void do_getsockopt_transparent(int fd)
assert(enable == 1);
}
+static void do_getsockopt_bind_address_no_port(int fd)
+{
+ socklen_t len;
+ int enable;
+
+ len = sizeof(enable);
+ if (getsockopt(fd, SOL_IP, IP_BIND_ADDRESS_NO_PORT,
+ &enable, &len))
+ die_perror("getsockopt(IP_TRANSPARENT)");
+
+ assert(enable == 1);
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -733,6 +756,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_freebind(fd);
do_getsockopt_transparent(fd);
+
+ do_getsockopt_bind_address_no_port(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index da02769fbb2b..3756b537e2a6 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -272,7 +272,8 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
"SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
- "IP_FREEBIND" "IP_TRANSPARENT"; do
+ "IP_FREEBIND" "IP_TRANSPARENT" \
+ "IP_BIND_ADDRESS_NO_PORT"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -292,7 +293,8 @@ do_mptcp_sockopt_tests()
for opt in "SOL_MPTCP" \
"SO_REUSEADDR" "SO_REUSEPORT" \
"SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
- "IPV6_FREEBIND" "IPV6_TRANSPARENT"; do
+ "IPV6_FREEBIND" "IPV6_TRANSPARENT" \
+ "IP_BIND_ADDRESS_NO_PORT"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 09/10] selftests: mptcp: sockopt: add IP_LOCAL_PORT_RANGE test
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (7 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 08/10] selftests: mptcp: sockopt: add IP_BIND_ADDRESS_NO_PORT test Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 10/10] selftests: mptcp: sockopt: add IPV6_V6ONLY test Geliang Tang
` (2 subsequent siblings)
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Add tests for IP_LOCAL_PORT_RANGE:
- Sets port range to 30000-31000
- Verifies the range via getsockopt
- Covers both IPv4 and IPv6
- Reports results in test script
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 25 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 6 +++--
2 files changed, 29 insertions(+), 2 deletions(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index ca1a40492aa4..25074e5b4eaa 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -262,6 +262,15 @@ static void do_setsockopt_bind_address_no_port(int fd)
perror("setsockopt(IP_BIND_ADDRESS_NO_PORT)");
}
+static void do_setsockopt_local_port_range(int fd)
+{
+ uint32_t port_range = (31000 << 16 | 30000); // [30000 - 31000]
+
+ if (setsockopt(fd, SOL_IP, IP_LOCAL_PORT_RANGE, &port_range,
+ sizeof(port_range)))
+ perror("setsockopt(IP_LOCAL_PORT_RANGE)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
@@ -271,6 +280,7 @@ static void do_setsockopts(int fd)
do_setsockopt_freebind(fd);
do_setsockopt_transparent(fd);
do_setsockopt_bind_address_no_port(fd);
+ do_setsockopt_local_port_range(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -734,6 +744,19 @@ static void do_getsockopt_bind_address_no_port(int fd)
assert(enable == 1);
}
+static void do_getsockopt_local_port_range(int fd)
+{
+ uint32_t port_range;
+ socklen_t len;
+
+ len = sizeof(port_range);
+ if (getsockopt(fd, SOL_IP, IP_LOCAL_PORT_RANGE,
+ &port_range, &len))
+ die_perror("getsockopt(IP_LOCAL_PORT_RANGE)");
+
+ assert(port_range == (31000 << 16 | 30000));
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -758,6 +781,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_transparent(fd);
do_getsockopt_bind_address_no_port(fd);
+
+ do_getsockopt_local_port_range(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 3756b537e2a6..2016adde1553 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -273,7 +273,8 @@ do_mptcp_sockopt_tests()
"SO_REUSEADDR" "SO_REUSEPORT" \
"SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
"IP_FREEBIND" "IP_TRANSPARENT" \
- "IP_BIND_ADDRESS_NO_PORT"; do
+ "IP_BIND_ADDRESS_NO_PORT" \
+ "IP_LOCAL_PORT_RANGE"; do
print_title "$opt sockopt v4"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v4"
@@ -294,7 +295,8 @@ do_mptcp_sockopt_tests()
"SO_REUSEADDR" "SO_REUSEPORT" \
"SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
"IPV6_FREEBIND" "IPV6_TRANSPARENT" \
- "IP_BIND_ADDRESS_NO_PORT"; do
+ "IP_BIND_ADDRESS_NO_PORT" \
+ "IP_LOCAL_PORT_RANGE"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH mptcp-next v2 10/10] selftests: mptcp: sockopt: add IPV6_V6ONLY test
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (8 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 09/10] selftests: mptcp: sockopt: add IP_LOCAL_PORT_RANGE test Geliang Tang
@ 2025-08-21 8:54 ` Geliang Tang
2025-08-21 9:57 ` [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Matthieu Baerts
2025-08-21 11:21 ` MPTCP CI
11 siblings, 0 replies; 13+ messages in thread
From: Geliang Tang @ 2025-08-21 8:54 UTC (permalink / raw)
To: mptcp; +Cc: Geliang Tang
From: Geliang Tang <tanggeliang@kylinos.cn>
Add IPv6-specific testing for IPV6_V6ONLY:
- Enables the option and verifies its state
- Restricted to IPv6 sockets
- Reports results in the test script
Signed-off-by: Geliang Tang <tanggeliang@kylinos.cn>
---
.../selftests/net/mptcp/mptcp_sockopt.c | 30 +++++++++++++++++++
.../selftests/net/mptcp/mptcp_sockopt.sh | 3 +-
2 files changed, 32 insertions(+), 1 deletion(-)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
index 25074e5b4eaa..9bbe2e56351f 100644
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.c
@@ -271,6 +271,18 @@ static void do_setsockopt_local_port_range(int fd)
perror("setsockopt(IP_LOCAL_PORT_RANGE)");
}
+static void do_setsockopt_v6only(int fd)
+{
+ int v6only = 1;
+
+ if (pf != AF_INET6)
+ return;
+
+ if (setsockopt(fd, SOL_IPV6, IPV6_V6ONLY, &v6only,
+ sizeof(v6only)))
+ perror("setsockopt(IPV6_V6ONLY)");
+}
+
static void do_setsockopts(int fd)
{
do_setsockopt_reuseaddr(fd);
@@ -281,6 +293,7 @@ static void do_setsockopts(int fd)
do_setsockopt_transparent(fd);
do_setsockopt_bind_address_no_port(fd);
do_setsockopt_local_port_range(fd);
+ do_setsockopt_v6only(fd);
}
static int sock_listen_mptcp(const char * const listenaddr,
@@ -757,6 +770,21 @@ static void do_getsockopt_local_port_range(int fd)
assert(port_range == (31000 << 16 | 30000));
}
+static void do_getsockopt_v6only(int fd)
+{
+ socklen_t len;
+ int v6only;
+
+ if (pf != AF_INET6)
+ return;
+
+ len = sizeof(v6only);
+ if (getsockopt(fd, SOL_IPV6, IPV6_V6ONLY, &v6only, &len))
+ die_perror("getsockopt(IPV6_V6ONLY)");
+
+ assert(v6only == 1);
+}
+
static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
{
do_getsockopt_mptcp_info(s, fd, w);
@@ -783,6 +811,8 @@ static void do_getsockopts(struct so_state *s, int fd, size_t r, size_t w)
do_getsockopt_bind_address_no_port(fd);
do_getsockopt_local_port_range(fd);
+
+ do_getsockopt_v6only(fd);
}
static void connect_one_server(int fd, int pipefd)
diff --git a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
index 2016adde1553..356911077451 100755
--- a/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
+++ b/tools/testing/selftests/net/mptcp/mptcp_sockopt.sh
@@ -296,7 +296,8 @@ do_mptcp_sockopt_tests()
"SO_BINDTODEVICE" "SO_BINDTOIFINDEX" \
"IPV6_FREEBIND" "IPV6_TRANSPARENT" \
"IP_BIND_ADDRESS_NO_PORT" \
- "IP_LOCAL_PORT_RANGE"; do
+ "IP_LOCAL_PORT_RANGE" \
+ "IPV6_V6ONLY"; do
print_title "$opt sockopt v6"
mptcp_lib_pr_ok
mptcp_lib_result_pass "$opt sockopt v6"
--
2.48.1
^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (9 preceding siblings ...)
2025-08-21 8:54 ` [PATCH mptcp-next v2 10/10] selftests: mptcp: sockopt: add IPV6_V6ONLY test Geliang Tang
@ 2025-08-21 9:57 ` Matthieu Baerts
2025-08-21 11:21 ` MPTCP CI
11 siblings, 0 replies; 13+ messages in thread
From: Matthieu Baerts @ 2025-08-21 9:57 UTC (permalink / raw)
To: Geliang Tang, mptcp; +Cc: Geliang Tang
Hi Geliang,
Thank you for looking at that!
On 21/08/2025 10:54, Geliang Tang wrote:
> From: Geliang Tang <tanggeliang@kylinos.cn>
>
> v2:
> - IP_FREEBIND/IPV6_FREEBIND are set in do_getsockopt_transparent, fix
> it.
> - Use "for" loops in mptcp_sockopt.sh.
> - Move "add IP_TOS socket option test" out of this set.
> - some cleanups.
>
> This series significantly expands MPTCP socket option test coverage
> by adding validation for 10 more socket options:
>
> 1. SO_REUSEADDR/SO_REUSEPORT - Test socket reuse capabilities
> 2. SO_BINDTODEVICE/SO_BINDTOIFINDEX - Validate interface binding
> 3. IP_TOS - Verify Type of Service handling
> 4. IP_FREEBIND - Test free address binding
> 5. IP_TRANSPARENT - Validate transparent proxying
> 6. IP_BIND_ADDRESS_NO_PORT - Test deferred port binding
> 7. IP_LOCAL_PORT_RANGE - Check local port range restriction
> 8. IPV6_V6ONLY - Verify IPv6-only sockets
>
> Each commit systematically adds:
> - Setsockopt/getsockopt operations in mptcp_sockopt.c
> - Dedicated test cases in mptcp_sockopt.sh
> - IPv4 and IPv6 coverage
> - Error handling and edge case validation
>
> The new tests verify that MPTCP correctly propagates socket options to
> subflows and maintains consistent behavior across address families.
I don't know if the last sentence is correct: if I'm not mistaken, it
looks like the new code "only" set and get some socket options, no?
If yes, that's not enough to me to verify a socket option is doing the
expected job. I think it might even be better not to include such code
giving a false sentiment of "it's fully tested" (+ more code to
maintain). All these options are supposed to affect the behaviour
somehow: a test should then mainly validate that, and check this
behaviour is similar to TCP.
In other words, such tests should be similar to what you did with
TCP_MAXSEG in Packetdrill:
https://github.com/multipath-tcp/packetdrill/pull/161
I think that when validating a new socket options, the following should
be checked:
- Comparison with TCP: the behaviour should be as closed as possible
- set/get before and after the connection
- behaviour on the client and server side
- important: checking the new expected behaviour
Checking all this should probably be easier with Packetdrill, especially
to validate a behavioural change. But it might not be always possible,
or best suited, like with IP_BIND_ADDRESS_NO_PORT and
IP_LOCAL_PORT_RANGE which are "properly" tested in:
tools/testing/selftests/net/mptcp/ip_local_port_range.c
What do you think?
Cheers,
Matt
--
Sponsored by the NGI0 Core fund.
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
` (10 preceding siblings ...)
2025-08-21 9:57 ` [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Matthieu Baerts
@ 2025-08-21 11:21 ` MPTCP CI
11 siblings, 0 replies; 13+ messages in thread
From: MPTCP CI @ 2025-08-21 11:21 UTC (permalink / raw)
To: Geliang Tang; +Cc: mptcp
Hi Geliang,
Thank you for your modifications, that's great!
Our CI did some validations and here is its report:
- KVM Validation: normal: Success! ✅
- KVM Validation: debug: Unstable: 3 failed test(s): packetdrill_syscalls selftest_mptcp_connect_checksum selftest_mptcp_join 🔴
- KVM Validation: btf-normal (only bpftest_all): Success! ✅
- KVM Validation: btf-debug (only bpftest_all): Success! ✅
- Task: https://github.com/multipath-tcp/mptcp_net-next/actions/runs/17122626757
Initiator: Patchew Applier
Commits: https://github.com/multipath-tcp/mptcp_net-next/commits/bda4263505d6
Patchwork: https://patchwork.kernel.org/project/mptcp/list/?series=993905
If there are some issues, you can reproduce them using the same environment as
the one used by the CI thanks to a docker image, e.g.:
$ cd [kernel source code]
$ docker run -v "${PWD}:${PWD}:rw" -w "${PWD}" --privileged --rm -it \
--pull always mptcp/mptcp-upstream-virtme-docker:latest \
auto-normal
For more details:
https://github.com/multipath-tcp/mptcp-upstream-virtme-docker
Please note that despite all the efforts that have been already done to have a
stable tests suite when executed on a public CI like here, it is possible some
reported issues are not due to your modifications. Still, do not hesitate to
help us improve that ;-)
Cheers,
MPTCP GH Action bot
Bot operated by Matthieu Baerts (NGI0 Core)
^ permalink raw reply [flat|nested] 13+ messages in thread
end of thread, other threads:[~2025-08-21 11:22 UTC | newest]
Thread overview: 13+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-08-21 8:54 [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 01/10] selftests: mptcp: sockopt: improve test output clarity Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 02/10] selftests: mptcp: sockopt: add SO_REUSEADDR test helper Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 03/10] selftests: mptcp: sockopt: add SO_REUSEPORT test Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 04/10] selftests: mptcp: sockopt: add SO_BINDTODEVICE test Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 05/10] selftests: mptcp: sockopt: add SO_BINDTOIFINDEX test Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 06/10] selftests: mptcp: sockopt: add IP_FREEBIND tests Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 07/10] selftests: mptcp: sockopt: add IP_TRANSPARENT tests Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 08/10] selftests: mptcp: sockopt: add IP_BIND_ADDRESS_NO_PORT test Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 09/10] selftests: mptcp: sockopt: add IP_LOCAL_PORT_RANGE test Geliang Tang
2025-08-21 8:54 ` [PATCH mptcp-next v2 10/10] selftests: mptcp: sockopt: add IPV6_V6ONLY test Geliang Tang
2025-08-21 9:57 ` [PATCH mptcp-next v2 00/10] selftests: cover more MPTCP socket options Matthieu Baerts
2025-08-21 11:21 ` MPTCP CI
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).