[PATCH] inet: fix flags used when deleting routes

Steve Schrock <[email protected]>
Newsgroups dev.linux.lists.connman
Message-ID <[email protected]>
When using PreferredTechnologies, default routes may be added and
deleted multiple times as interfaces of different priorities appear.
Unfortunately on kernel 6.11 connman is successfully adding routes, but
it is receiving "Operation not supported (95)" errors when it tries to
delete those same routes.

strace shows that connman is passing unexpected flags for RTM_DELROUTE:
  nlmsg_flags=NLM_F_REQUEST|NLM_F_ACK|NLM_F_BULK|0x400

connman is actually passing RTM_NEWROUTE's NLM_F_EXCL (0x200) and
NLM_F_CREATE (0x400) which are interpreted as RTM_DELROUTE's NLM_F_BULK
(0x200) and "nothing", respectively.

The NLM_F_BULK flag was added to the kernel in commit
545528d788556c724eeb5400757f828ef27782a8 ("net: netlink: add NLM_F_BULK
delete request modifier") which is included in the 5.19 and 6.0
kernels. This flag was likely ignored in prior kernel versions which
was why route deletions succeeded in the past.

The fix is to ensure these flags are not set for RTM_DELROUTE.
---
 src/inet.c | 10 ++++++++--
 1 file changed, 8 insertions(+), 2 deletions(-)

diff --git a/src/inet.c b/src/inet.c
index 5032cf25d396..542e5a851306 100644
--- a/src/inet.c
+++ b/src/inet.c
@@ -829,7 +829,7 @@ static int inet_modify_host_or_network_route(int cmd,
 	memset(&rth, 0, sizeof(rth));
 
 	rth.req.n.nlmsg_len   = NLMSG_LENGTH(sizeof(struct rtmsg));
-	rth.req.n.nlmsg_flags = NLM_F_REQUEST | NLM_F_CREATE | NLM_F_EXCL;
+	rth.req.n.nlmsg_flags = NLM_F_REQUEST;
 	rth.req.n.nlmsg_type  = cmd;
 
 	rth.req.u.r.rt.rtm_family   = family;
@@ -841,6 +841,9 @@ static int inet_modify_host_or_network_route(int cmd,
 	rth.req.u.r.rt.rtm_type     = RTN_UNICAST;
 	rth.req.u.r.rt.rtm_dst_len  = prefixlen;
 
+	if (cmd == RTM_NEWROUTE)
+		rth.req.n.nlmsg_flags |= NLM_F_CREATE | NLM_F_EXCL;
+
 	__connman_inet_rtnl_addattr_l(&rth.req.n, sizeof(rth.req),
 				RTA_DST, host_or_network_buf, addr_len);
 
@@ -4717,7 +4720,7 @@ static int iproute_default_modify(int cmd, uint32_t table_id, uint32_t metric,
 	memset(&rth, 0, sizeof(rth));
 
 	rth.req.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct rtmsg));
-	rth.req.n.nlmsg_flags = NLM_F_REQUEST | NLM_F_CREATE | NLM_F_EXCL;
+	rth.req.n.nlmsg_flags = NLM_F_REQUEST;
 	rth.req.n.nlmsg_type = cmd;
 	rth.req.u.r.rt.rtm_family = family;
 	rth.req.u.r.rt.rtm_table = RT_TABLE_MAIN;
@@ -4726,6 +4729,9 @@ static int iproute_default_modify(int cmd, uint32_t table_id, uint32_t metric,
 	rth.req.u.r.rt.rtm_type = RTN_UNICAST;
 	rth.req.u.r.rt.rtm_dst_len = prefixlen;
 
+	if (cmd == RTM_NEWROUTE)
+		rth.req.n.nlmsg_flags |= NLM_F_CREATE | NLM_F_EXCL;
+
 	__connman_inet_rtnl_addattr_l(&rth.req.n, sizeof(rth.req),
 		prefixlen > 0 ? RTA_DST : RTA_GATEWAY, buf, len);
 
-- 
2.43.0


-- 


*Confidentiality Note:* We care about protecting our proprietary 
information, confidential material, and trade secrets. This message may 
contain some or all of those things. Cruise will suffer material harm if 
anyone other than the intended recipient disseminates or takes any action 
based on this message. If you have received this message (including any 
attachments) in error, please delete it immediately and notify the sender 
promptly.
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.