Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

selftests: mptcp: refactor NLMSG handling with 'proto'

This patch introduces the '__u32 proto' variable to the 'send_query' and
'recv_nlmsg' functions for further extending function.

In the 'send_query' function, the inclusion of this variable makes the
structure clearer and more readable.

In the 'recv_nlmsg' function, the '__u32 proto' variable ensures that
the 'diag_info' field remains unmodified when processing IPPROTO_TCP data,
thereby preventing unintended transformation into 'mptcp_info' format.

While at it, increment iovlen directly when an item is added to simplify
this portion of the code and improve its readaility.

Co-developed-by: Geliang Tang <geliang@kernel.org>
Signed-off-by: Geliang Tang <geliang@kernel.org>
Signed-off-by: Gang Yan <yangang@kylinos.cn>
Reviewed-by: Matthieu Baerts (NGI0) <matttbe@kernel.org>
Signed-off-by: Matthieu Baerts (NGI0) <matttbe@kernel.org>
Link: https://patch.msgid.link/20250502-net-next-mptcp-sft-inc-cover-v1-5-68eec95898fb@kernel.org
Signed-off-by: Jakub Kicinski <kuba@kernel.org>

authored by

Gang Yan and committed by
Jakub Kicinski
caa6811c 3fea468d

+20 -18
+20 -18
tools/testing/selftests/net/mptcp/mptcp_diag.c
··· 62 62 exit(r); 63 63 } 64 64 65 - static void send_query(int fd, struct inet_diag_req_v2 *r) 65 + static void send_query(int fd, struct inet_diag_req_v2 *r, __u32 proto) 66 66 { 67 67 struct sockaddr_nl nladdr = { 68 68 .nl_family = AF_NETLINK ··· 80 80 }; 81 81 struct rtattr rta_proto; 82 82 struct iovec iov[6]; 83 - int iovlen = 1; 84 - __u32 proto; 83 + int iovlen = 0; 85 84 86 - proto = IPPROTO_MPTCP; 87 - rta_proto.rta_type = INET_DIAG_REQ_PROTOCOL; 88 - rta_proto.rta_len = RTA_LENGTH(sizeof(proto)); 89 - 90 - iov[0] = (struct iovec) { 85 + iov[iovlen++] = (struct iovec) { 91 86 .iov_base = &req, 92 87 .iov_len = sizeof(req) 93 88 }; 94 - iov[iovlen] = (struct iovec){ &rta_proto, sizeof(rta_proto)}; 95 - iov[iovlen + 1] = (struct iovec){ &proto, sizeof(proto)}; 96 - req.nlh.nlmsg_len += RTA_LENGTH(sizeof(proto)); 97 - iovlen += 2; 89 + 90 + if (proto == IPPROTO_MPTCP) { 91 + rta_proto.rta_type = INET_DIAG_REQ_PROTOCOL; 92 + rta_proto.rta_len = RTA_LENGTH(sizeof(proto)); 93 + 94 + iov[iovlen++] = (struct iovec){ &rta_proto, sizeof(rta_proto)}; 95 + iov[iovlen++] = (struct iovec){ &proto, sizeof(proto)}; 96 + req.nlh.nlmsg_len += RTA_LENGTH(sizeof(proto)); 97 + } 98 + 98 99 struct msghdr msg = { 99 100 .msg_name = &nladdr, 100 101 .msg_namelen = sizeof(nladdr), ··· 159 158 printf("bytes_acked: %llu\n", info->mptcpi_bytes_acked); 160 159 } 161 160 162 - static void parse_nlmsg(struct nlmsghdr *nlh) 161 + static void parse_nlmsg(struct nlmsghdr *nlh, __u32 proto) 163 162 { 164 163 struct inet_diag_msg *r = NLMSG_DATA(nlh); 165 164 struct rtattr *tb[INET_DIAG_MAX + 1]; ··· 168 167 nlh->nlmsg_len - NLMSG_LENGTH(sizeof(*r)), 169 168 NLA_F_NESTED); 170 169 171 - if (tb[INET_DIAG_INFO]) { 170 + if (proto == IPPROTO_MPTCP && tb[INET_DIAG_INFO]) { 172 171 int len = RTA_PAYLOAD(tb[INET_DIAG_INFO]); 173 172 struct mptcp_info *info; 174 173 ··· 184 183 } 185 184 } 186 185 187 - static void recv_nlmsg(int fd) 186 + static void recv_nlmsg(int fd, __u32 proto) 188 187 { 189 188 char rcv_buff[8192]; 190 189 struct nlmsghdr *nlh = (struct nlmsghdr *)rcv_buff; ··· 217 216 -(err->error), strerror(-(err->error))); 218 217 break; 219 218 } 220 - parse_nlmsg(nlh); 219 + parse_nlmsg(nlh, proto); 221 220 nlh = NLMSG_NEXT(nlh, len); 222 221 } 223 222 } ··· 231 230 .idiag_ext = 1 << (INET_DIAG_INFO - 1), 232 231 .id.idiag_cookie[0] = token, 233 232 }; 233 + __u32 proto = IPPROTO_MPTCP; 234 234 int fd; 235 235 236 236 fd = socket(AF_NETLINK, SOCK_RAW, NETLINK_SOCK_DIAG); 237 237 if (fd < 0) 238 238 die_perror("Netlink socket"); 239 239 240 - send_query(fd, &r); 241 - recv_nlmsg(fd); 240 + send_query(fd, &r, proto); 241 + recv_nlmsg(fd, proto); 242 242 243 243 close(fd); 244 244 }