* [PATCH net 0/2] pull-request: can 2022-02-09
@ 2022-02-09 8:01 Marc Kleine-Budde
2022-02-09 8:01 ` [PATCH net 1/2] can: isotp: fix potential CAN frame reception race in isotp_rcv() Marc Kleine-Budde
2022-02-09 8:01 ` [PATCH net 2/2] can: isotp: fix error path in isotp_sendmsg() to unlock wait queue Marc Kleine-Budde
0 siblings, 2 replies; 4+ messages in thread
From: Marc Kleine-Budde @ 2022-02-09 8:01 UTC (permalink / raw)
To: netdev; +Cc: davem, kuba, linux-can, kernel
Hello Jakub, hello David,
this is a pull request of 2 patches for net/master.
Oliver Hartkopp contributes 2 fixes for the CAN ISOTP protocol.
regards,
Marc
---
The following changes since commit 7db788ad627aabff2b74d4f1a3b68516d0fee0d7:
nfp: flower: fix ida_idx not being released (2022-02-08 21:06:35 -0800)
are available in the Git repository at:
git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can.git tags/linux-can-fixes-for-5.17-20220209
for you to fetch changes up to 8375dfac4f683e1b2c5956d919d36aeedad46699:
can: isotp: fix error path in isotp_sendmsg() to unlock wait queue (2022-02-09 08:47:47 +0100)
----------------------------------------------------------------
linux-can-fixes-for-5.17-20220209
----------------------------------------------------------------
Oliver Hartkopp (2):
can: isotp: fix potential CAN frame reception race in isotp_rcv()
can: isotp: fix error path in isotp_sendmsg() to unlock wait queue
net/can/isotp.c | 29 ++++++++++++++++++++++-------
1 file changed, 22 insertions(+), 7 deletions(-)
^ permalink raw reply [flat|nested] 4+ messages in thread
* [PATCH net 1/2] can: isotp: fix potential CAN frame reception race in isotp_rcv()
2022-02-09 8:01 [PATCH net 0/2] pull-request: can 2022-02-09 Marc Kleine-Budde
@ 2022-02-09 8:01 ` Marc Kleine-Budde
2022-02-09 12:10 ` patchwork-bot+netdevbpf
2022-02-09 8:01 ` [PATCH net 2/2] can: isotp: fix error path in isotp_sendmsg() to unlock wait queue Marc Kleine-Budde
1 sibling, 1 reply; 4+ messages in thread
From: Marc Kleine-Budde @ 2022-02-09 8:01 UTC (permalink / raw)
To: netdev
Cc: davem, kuba, linux-can, kernel, Oliver Hartkopp, stable,
syzbot+4c63f36709a642f801c5, Ziyang Xuan, Marc Kleine-Budde
From: Oliver Hartkopp <socketcan@hartkopp.net>
When receiving a CAN frame the current code logic does not consider
concurrently receiving processes which do not show up in real world
usage.
Ziyang Xuan writes:
The following syz problem is one of the scenarios. so->rx.len is
changed by isotp_rcv_ff() during isotp_rcv_cf(), so->rx.len equals
0 before alloc_skb() and equals 4096 after alloc_skb(). That will
trigger skb_over_panic() in skb_put().
=======================================================
CPU: 1 PID: 19 Comm: ksoftirqd/1 Not tainted 5.16.0-rc8-syzkaller #0
RIP: 0010:skb_panic+0x16c/0x16e net/core/skbuff.c:113
Call Trace:
<TASK>
skb_over_panic net/core/skbuff.c:118 [inline]
skb_put.cold+0x24/0x24 net/core/skbuff.c:1990
isotp_rcv_cf net/can/isotp.c:570 [inline]
isotp_rcv+0xa38/0x1e30 net/can/isotp.c:668
deliver net/can/af_can.c:574 [inline]
can_rcv_filter+0x445/0x8d0 net/can/af_can.c:635
can_receive+0x31d/0x580 net/can/af_can.c:665
can_rcv+0x120/0x1c0 net/can/af_can.c:696
__netif_receive_skb_one_core+0x114/0x180 net/core/dev.c:5465
__netif_receive_skb+0x24/0x1b0 net/core/dev.c:5579
Therefore we make sure the state changes and data structures stay
consistent at CAN frame reception time by adding a spin_lock in
isotp_rcv(). This fixes the issue reported by syzkaller but does not
affect real world operation.
Fixes: e057dd3fc20f ("can: add ISO 15765-2:2016 transport protocol")
Link: https://lore.kernel.org/linux-can/d7e69278-d741-c706-65e1-e87623d9a8e8@huawei.com/T/
Link: https://lore.kernel.org/all/20220208200026.13783-1-socketcan@hartkopp.net
Cc: stable@vger.kernel.org
Reported-by: syzbot+4c63f36709a642f801c5@syzkaller.appspotmail.com
Reported-by: Ziyang Xuan <william.xuanziyang@huawei.com>
Signed-off-by: Oliver Hartkopp <socketcan@hartkopp.net>
Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
---
net/can/isotp.c | 14 +++++++++++++-
1 file changed, 13 insertions(+), 1 deletion(-)
diff --git a/net/can/isotp.c b/net/can/isotp.c
index 02cbcb2ecf0d..9149e8d8aefc 100644
--- a/net/can/isotp.c
+++ b/net/can/isotp.c
@@ -56,6 +56,7 @@
#include <linux/module.h>
#include <linux/init.h>
#include <linux/interrupt.h>
+#include <linux/spinlock.h>
#include <linux/hrtimer.h>
#include <linux/wait.h>
#include <linux/uio.h>
@@ -145,6 +146,7 @@ struct isotp_sock {
struct tpcon rx, tx;
struct list_head notifier;
wait_queue_head_t wait;
+ spinlock_t rx_lock; /* protect single thread state machine */
};
static LIST_HEAD(isotp_notifier_list);
@@ -615,11 +617,17 @@ static void isotp_rcv(struct sk_buff *skb, void *data)
n_pci_type = cf->data[ae] & 0xF0;
+ /* Make sure the state changes and data structures stay consistent at
+ * CAN frame reception time. This locking is not needed in real world
+ * use cases but the inconsistency can be triggered with syzkaller.
+ */
+ spin_lock(&so->rx_lock);
+
if (so->opt.flags & CAN_ISOTP_HALF_DUPLEX) {
/* check rx/tx path half duplex expectations */
if ((so->tx.state != ISOTP_IDLE && n_pci_type != N_PCI_FC) ||
(so->rx.state != ISOTP_IDLE && n_pci_type == N_PCI_FC))
- return;
+ goto out_unlock;
}
switch (n_pci_type) {
@@ -668,6 +676,9 @@ static void isotp_rcv(struct sk_buff *skb, void *data)
isotp_rcv_cf(sk, cf, ae, skb);
break;
}
+
+out_unlock:
+ spin_unlock(&so->rx_lock);
}
static void isotp_fill_dataframe(struct canfd_frame *cf, struct isotp_sock *so,
@@ -1444,6 +1455,7 @@ static int isotp_init(struct sock *sk)
so->txtimer.function = isotp_tx_timer_handler;
init_waitqueue_head(&so->wait);
+ spin_lock_init(&so->rx_lock);
spin_lock(&isotp_notifier_lock);
list_add_tail(&so->notifier, &isotp_notifier_list);
base-commit: 7db788ad627aabff2b74d4f1a3b68516d0fee0d7
--
2.34.1
^ permalink raw reply related [flat|nested] 4+ messages in thread
* [PATCH net 2/2] can: isotp: fix error path in isotp_sendmsg() to unlock wait queue
2022-02-09 8:01 [PATCH net 0/2] pull-request: can 2022-02-09 Marc Kleine-Budde
2022-02-09 8:01 ` [PATCH net 1/2] can: isotp: fix potential CAN frame reception race in isotp_rcv() Marc Kleine-Budde
@ 2022-02-09 8:01 ` Marc Kleine-Budde
1 sibling, 0 replies; 4+ messages in thread
From: Marc Kleine-Budde @ 2022-02-09 8:01 UTC (permalink / raw)
To: netdev
Cc: davem, kuba, linux-can, kernel, Oliver Hartkopp, stable,
Ziyang Xuan, Marc Kleine-Budde
From: Oliver Hartkopp <socketcan@hartkopp.net>
Commit 43a08c3bdac4 ("can: isotp: isotp_sendmsg(): fix TX buffer concurrent
access in isotp_sendmsg()") introduced a new locking scheme that may render
the userspace application in a locking state when an error is detected.
This issue shows up under high load on simultaneously running isotp channels
with identical configuration which is against the ISO specification and
therefore breaks any reasonable PDU communication anyway.
Fixes: 43a08c3bdac4 ("can: isotp: isotp_sendmsg(): fix TX buffer concurrent access in isotp_sendmsg()")
Link: https://lore.kernel.org/all/20220209073601.25728-1-socketcan@hartkopp.net
Cc: stable@vger.kernel.org
Cc: Ziyang Xuan <william.xuanziyang@huawei.com>
Signed-off-by: Oliver Hartkopp <socketcan@hartkopp.net>
Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
---
net/can/isotp.c | 15 +++++++++------
1 file changed, 9 insertions(+), 6 deletions(-)
diff --git a/net/can/isotp.c b/net/can/isotp.c
index 9149e8d8aefc..d2a430b6a13b 100644
--- a/net/can/isotp.c
+++ b/net/can/isotp.c
@@ -887,7 +887,7 @@ static int isotp_sendmsg(struct socket *sock, struct msghdr *msg, size_t size)
if (!size || size > MAX_MSG_LENGTH) {
err = -EINVAL;
- goto err_out;
+ goto err_out_drop;
}
/* take care of a potential SF_DL ESC offset for TX_DL > 8 */
@@ -897,24 +897,24 @@ static int isotp_sendmsg(struct socket *sock, struct msghdr *msg, size_t size)
if ((so->opt.flags & CAN_ISOTP_SF_BROADCAST) &&
(size > so->tx.ll_dl - SF_PCI_SZ4 - ae - off)) {
err = -EINVAL;
- goto err_out;
+ goto err_out_drop;
}
err = memcpy_from_msg(so->tx.buf, msg, size);
if (err < 0)
- goto err_out;
+ goto err_out_drop;
dev = dev_get_by_index(sock_net(sk), so->ifindex);
if (!dev) {
err = -ENXIO;
- goto err_out;
+ goto err_out_drop;
}
skb = sock_alloc_send_skb(sk, so->ll.mtu + sizeof(struct can_skb_priv),
msg->msg_flags & MSG_DONTWAIT, &err);
if (!skb) {
dev_put(dev);
- goto err_out;
+ goto err_out_drop;
}
can_skb_reserve(skb);
@@ -976,7 +976,7 @@ static int isotp_sendmsg(struct socket *sock, struct msghdr *msg, size_t size)
if (err) {
pr_notice_once("can-isotp: %s: can_send_ret %pe\n",
__func__, ERR_PTR(err));
- goto err_out;
+ goto err_out_drop;
}
if (wait_tx_done) {
@@ -989,6 +989,9 @@ static int isotp_sendmsg(struct socket *sock, struct msghdr *msg, size_t size)
return size;
+err_out_drop:
+ /* drop this PDU and unlock a potential wait queue */
+ old_state = ISOTP_IDLE;
err_out:
so->tx.state = old_state;
if (so->tx.state == ISOTP_IDLE)
--
2.34.1
^ permalink raw reply related [flat|nested] 4+ messages in thread
* Re: [PATCH net 1/2] can: isotp: fix potential CAN frame reception race in isotp_rcv()
2022-02-09 8:01 ` [PATCH net 1/2] can: isotp: fix potential CAN frame reception race in isotp_rcv() Marc Kleine-Budde
@ 2022-02-09 12:10 ` patchwork-bot+netdevbpf
0 siblings, 0 replies; 4+ messages in thread
From: patchwork-bot+netdevbpf @ 2022-02-09 12:10 UTC (permalink / raw)
To: Marc Kleine-Budde
Cc: netdev, davem, kuba, linux-can, kernel, socketcan, stable,
syzbot+4c63f36709a642f801c5, william.xuanziyang
Hello:
This series was applied to netdev/net.git (master)
by Marc Kleine-Budde <mkl@pengutronix.de>:
On Wed, 9 Feb 2022 09:01:53 +0100 you wrote:
> From: Oliver Hartkopp <socketcan@hartkopp.net>
>
> When receiving a CAN frame the current code logic does not consider
> concurrently receiving processes which do not show up in real world
> usage.
>
> Ziyang Xuan writes:
>
> [...]
Here is the summary with links:
- [net,1/2] can: isotp: fix potential CAN frame reception race in isotp_rcv()
https://git.kernel.org/netdev/net/c/7c759040c1dd
- [net,2/2] can: isotp: fix error path in isotp_sendmsg() to unlock wait queue
https://git.kernel.org/netdev/net/c/8375dfac4f68
You are awesome, thank you!
--
Deet-doot-dot, I am a bot.
https://korg.docs.kernel.org/patchwork/pwbot.html
^ permalink raw reply [flat|nested] 4+ messages in thread
end of thread, other threads:[~2022-02-09 12:20 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2022-02-09 8:01 [PATCH net 0/2] pull-request: can 2022-02-09 Marc Kleine-Budde
2022-02-09 8:01 ` [PATCH net 1/2] can: isotp: fix potential CAN frame reception race in isotp_rcv() Marc Kleine-Budde
2022-02-09 12:10 ` patchwork-bot+netdevbpf
2022-02-09 8:01 ` [PATCH net 2/2] can: isotp: fix error path in isotp_sendmsg() to unlock wait queue Marc Kleine-Budde
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).