Skip to content

Commit 968b098

Browse files
haruki3hhhmarckleinebudde
authored andcommitted
can: esd_usb: add endpoint type validation
esd_usb_probe() constructs bulk pipes for two endpoints without verifying their transfer types: - usb_rcvbulkpipe(dev->udev, 1) for RX (version reply, async RX data) - usb_sndbulkpipe(dev->udev, 2) for TX (version query, CAN frames) A malformed USB device can present these endpoints with transfer types that differ from what the driver assumes, triggering the WARNING in usb_submit_urb(). Use usb_find_common_endpoints() to discover and validate the first bulk IN and bulk OUT endpoints at probe time, before any allocation. Found pipes are saved to struct esd_usb and code uses them directly instead of making pipes in place. Similar to - commit 136bed0 ("can: mcba_usb: properly check endpoint type") which established the usb_find_common_endpoints() + stored pipes pattern for CAN USB drivers. Fixes: 96d8e90 ("can: Add driver for esd CAN-USB/2 device") Suggested-by: Vincent Mailhol <mailhol@kernel.org> Signed-off-by: Ziyi Guo <n7l8m4@u.northwestern.edu> Reviewed-by: Vincent Mailhol <mailhol@kernel.org> Link: https://patch.msgid.link/20260213203927.599163-1-n7l8m4@u.northwestern.edu Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
1 parent ab3f894 commit 968b098

1 file changed

Lines changed: 17 additions & 13 deletions

File tree

drivers/net/can/usb/esd_usb.c

Lines changed: 17 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -272,6 +272,9 @@ struct esd_usb {
272272

273273
struct usb_anchor rx_submitted;
274274

275+
unsigned int rx_pipe;
276+
unsigned int tx_pipe;
277+
275278
int net_count;
276279
u32 version;
277280
int rxinitdone;
@@ -537,7 +540,7 @@ static void esd_usb_read_bulk_callback(struct urb *urb)
537540
}
538541

539542
resubmit_urb:
540-
usb_fill_bulk_urb(urb, dev->udev, usb_rcvbulkpipe(dev->udev, 1),
543+
usb_fill_bulk_urb(urb, dev->udev, dev->rx_pipe,
541544
urb->transfer_buffer, ESD_USB_RX_BUFFER_SIZE,
542545
esd_usb_read_bulk_callback, dev);
543546

@@ -626,9 +629,7 @@ static int esd_usb_send_msg(struct esd_usb *dev, union esd_usb_msg *msg)
626629
{
627630
int actual_length;
628631

629-
return usb_bulk_msg(dev->udev,
630-
usb_sndbulkpipe(dev->udev, 2),
631-
msg,
632+
return usb_bulk_msg(dev->udev, dev->tx_pipe, msg,
632633
msg->hdr.len * sizeof(u32), /* convert to # of bytes */
633634
&actual_length,
634635
1000);
@@ -639,12 +640,8 @@ static int esd_usb_wait_msg(struct esd_usb *dev,
639640
{
640641
int actual_length;
641642

642-
return usb_bulk_msg(dev->udev,
643-
usb_rcvbulkpipe(dev->udev, 1),
644-
msg,
645-
sizeof(*msg),
646-
&actual_length,
647-
1000);
643+
return usb_bulk_msg(dev->udev, dev->rx_pipe, msg,
644+
sizeof(*msg), &actual_length, 1000);
648645
}
649646

650647
static int esd_usb_setup_rx_urbs(struct esd_usb *dev)
@@ -677,8 +674,7 @@ static int esd_usb_setup_rx_urbs(struct esd_usb *dev)
677674

678675
urb->transfer_dma = buf_dma;
679676

680-
usb_fill_bulk_urb(urb, dev->udev,
681-
usb_rcvbulkpipe(dev->udev, 1),
677+
usb_fill_bulk_urb(urb, dev->udev, dev->rx_pipe,
682678
buf, ESD_USB_RX_BUFFER_SIZE,
683679
esd_usb_read_bulk_callback, dev);
684680
urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
@@ -903,7 +899,7 @@ static netdev_tx_t esd_usb_start_xmit(struct sk_buff *skb,
903899
/* hnd must not be 0 - MSB is stripped in txdone handling */
904900
msg->tx.hnd = BIT(31) | i; /* returned in TX done message */
905901

906-
usb_fill_bulk_urb(urb, dev->udev, usb_sndbulkpipe(dev->udev, 2), buf,
902+
usb_fill_bulk_urb(urb, dev->udev, dev->tx_pipe, buf,
907903
msg->hdr.len * sizeof(u32), /* convert to # of bytes */
908904
esd_usb_write_bulk_callback, context);
909905

@@ -1298,17 +1294,25 @@ static int esd_usb_probe_one_net(struct usb_interface *intf, int index)
12981294
static int esd_usb_probe(struct usb_interface *intf,
12991295
const struct usb_device_id *id)
13001296
{
1297+
struct usb_endpoint_descriptor *ep_in, *ep_out;
13011298
struct esd_usb *dev;
13021299
union esd_usb_msg *msg;
13031300
int i, err;
13041301

1302+
err = usb_find_common_endpoints(intf->cur_altsetting, &ep_in, &ep_out,
1303+
NULL, NULL);
1304+
if (err)
1305+
return err;
1306+
13051307
dev = kzalloc_obj(*dev);
13061308
if (!dev) {
13071309
err = -ENOMEM;
13081310
goto done;
13091311
}
13101312

13111313
dev->udev = interface_to_usbdev(intf);
1314+
dev->rx_pipe = usb_rcvbulkpipe(dev->udev, ep_in->bEndpointAddress);
1315+
dev->tx_pipe = usb_sndbulkpipe(dev->udev, ep_out->bEndpointAddress);
13121316

13131317
init_usb_anchor(&dev->rx_submitted);
13141318

0 commit comments

Comments
 (0)