Re: [RFC PATCH] can: gw: fix RCU/BH usage in cgw_create_job()

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 2024-01-11 13:14, Sebastian Andrzej Siewior wrote:

Why are you afraid of doing
	mod = kmalloc(sizeof(*mod), GFP_KERNEL);

before invoking cgw_parse_attr()?

The update of the modification content should be performed instantly and without any potential scheduling from kmalloc().

As you pointed out one of the problems may arise from changing the modification functions but not from changing the modification content.

So what about the below patch then?

Would a spin_lock() or spin_lock_bh() be an alternative to lock this update against the modification execution in can_can_gw_rcv()?

Best regards,
Oliver

diff --git a/net/can/gw.c b/net/can/gw.c
index 37528826935e..79aeb380b66a 100644
--- a/net/can/gw.c
+++ b/net/can/gw.c
@@ -1085,21 +1085,27 @@ static int cgw_create_job(struct sk_buff *skb, struct nlmsghdr *nlh,
 	if (mod.uid) {
 		ASSERT_RTNL();

 		/* check for updating an existing job with identical uid */
 		hlist_for_each_entry(gwj, &net->can.cgw_list, list) {
+			int mi;
+
 			if (gwj->mod.uid != mod.uid)
 				continue;

 			/* interfaces & filters must be identical */
 			if (memcmp(&gwj->ccgw, &ccgw, sizeof(ccgw)))
 				return -EINVAL;

-			/* update modifications with disabled softirq & quit */
-			local_bh_disable();
+			/* modification functions must be identical */
+			for (mi = 0; mi < MAX_MODFUNCTIONS; mi++) {
+				if (gwj->mod.modfunc[mi] != mod.modfunc[mi])
+					return -EINVAL;
+			}
+
+			/* update only the modification content & quit */
 			memcpy(&gwj->mod, &mod, sizeof(mod));
-			local_bh_enable();
 			return 0;
 		}
 	}

 	/* ifindex == 0 is not allowed for job creation */





[Index of Archives]     [Automotive Discussions]     [Linux ARM Kernel]     [Linux ARM]     [Linux Omap]     [Fedora ARM]     [IETF Annouce]     [Security]     [Bugtraq]     [Linux]     [Linux OMAP]     [Linux MIPS]     [eCos]     [Asterisk Internet PBX]     [Linux API]     [CAN Bus]

  Powered by Linux