mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
* [PATCH] media: msi2500: return buffers as QUEUED in buf_queue() before start_streaming()
@ 2026-11-06  8:41 zhangdaolong
  2026-11-11 12:29 ` Hans Verkuil
  0 siblings, 1 reply; 2+ messages in thread
From: zhangdaolong @ 2026-11-06  8:41 UTC (permalink / raw)
  To: Mauro Carvalho Chehab, Hans Verkuil
  Cc: Antti Palosaari, Valery Borovsky, linux-media, linux-kernel,
	syzbot+930e6201080a31e9d0c8, dlzhangak, stable

When vb2_start_streaming() is invoked, it first passes all pre-queued
buffers on q->queued_list to the driver via buf_queue() before setting
q->start_streaming_called and invoking start_streaming(). If
start_streaming() subsequently returns an error, videobuf2 requires all
buffers passed to the driver to be returned with VB2_BUF_STATE_QUEUED
and warns via WARN_ON(!list_empty(&q->done_list)) if any buffer was
completed with VB2_BUF_STATE_ERROR or VB2_BUF_STATE_DONE.

If the USB device disconnects before vb2_start_streaming() runs (for
example when v4l2_read() races with msi2500_disconnect()), dev->udev is
already NULL when vb2_start_streaming() enters. msi2500_buf_queue() sees
!dev->udev and immediately completes each pre-queued buffer with
VB2_BUF_STATE_ERROR (moving it onto q->done_list) instead of adding it
to dev->queued_bufs. Right after that, msi2500_start_streaming() also
sees !dev->udev and returns -ENODEV, triggering
WARN_ON(!list_empty(&q->done_list)) in vb2_start_streaming().

Fix this by checking vb2_start_streaming_called(vb->vb2_queue) in
msi2500_buf_queue() when !dev->udev: return VB2_BUF_STATE_QUEUED when
start_streaming() has not been called yet, and VB2_BUF_STATE_ERROR when
streaming is already active.

Reported-by: syzbot+930e6201080a31e9d0c8@syzkaller.appspotmail.com
Closes: https://syzkaller.appspot.com/bug?extid=930e6201080a31e9d0c8
Fixes: 977e444f59ad ("[media] Mirics MSi3101 SDR Dongle driver")
Cc: stable@vger.kernel.org
Signed-off-by: zhangdaolong <dlzhangak@isoftstone.com>
---
 drivers/media/usb/msi2500/msi2500.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/drivers/media/usb/msi2500/msi2500.c b/drivers/media/usb/msi2500/msi2500.c
index 282256ab812a..d89db57f924f 100644
--- a/drivers/media/usb/msi2500/msi2500.c
+++ b/drivers/media/usb/msi2500/msi2500.c
@@ -625,7 +625,9 @@ static void msi2500_buf_queue(struct vb2_buffer *vb)
 
 	/* Check the device has not disconnected between prep and queuing */
 	if (unlikely(!dev->udev)) {
-		vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_ERROR);
+		vb2_buffer_done(&buf->vb.vb2_buf,
+				vb2_start_streaming_called(vb->vb2_queue) ?
+				VB2_BUF_STATE_ERROR : VB2_BUF_STATE_QUEUED);
 		return;
 	}
 
-- 
2.48.1


^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: [PATCH] media: msi2500: return buffers as QUEUED in buf_queue() before start_streaming()
  2026-11-06  8:41 [PATCH] media: msi2500: return buffers as QUEUED in buf_queue() before start_streaming() zhangdaolong
@ 2026-11-11 12:29 ` Hans Verkuil
  0 siblings, 0 replies; 2+ messages in thread
From: Hans Verkuil @ 2026-11-11 12:29 UTC (permalink / raw)
  To: zhangdaolong, Mauro Carvalho Chehab
  Cc: Antti Palosaari, Valery Borovsky, linux-media, linux-kernel,
	syzbot+930e6201080a31e9d0c8, stable

On 06/11/2026 09:41, zhangdaolong wrote:
> When vb2_start_streaming() is invoked, it first passes all pre-queued
> buffers on q->queued_list to the driver via buf_queue() before setting
> q->start_streaming_called and invoking start_streaming(). If
> start_streaming() subsequently returns an error, videobuf2 requires all
> buffers passed to the driver to be returned with VB2_BUF_STATE_QUEUED
> and warns via WARN_ON(!list_empty(&q->done_list)) if any buffer was
> completed with VB2_BUF_STATE_ERROR or VB2_BUF_STATE_DONE.
> 
> If the USB device disconnects before vb2_start_streaming() runs (for
> example when v4l2_read() races with msi2500_disconnect()), dev->udev is
> already NULL when vb2_start_streaming() enters. msi2500_buf_queue() sees
> !dev->udev and immediately completes each pre-queued buffer with
> VB2_BUF_STATE_ERROR (moving it onto q->done_list) instead of adding it
> to dev->queued_bufs. Right after that, msi2500_start_streaming() also
> sees !dev->udev and returns -ENODEV, triggering
> WARN_ON(!list_empty(&q->done_list)) in vb2_start_streaming().
> 
> Fix this by checking vb2_start_streaming_called(vb->vb2_queue) in
> msi2500_buf_queue() when !dev->udev: return VB2_BUF_STATE_QUEUED when
> start_streaming() has not been called yet, and VB2_BUF_STATE_ERROR when
> streaming is already active.
> 
> Reported-by: syzbot+930e6201080a31e9d0c8@syzkaller.appspotmail.com
> Closes: https://syzkaller.appspot.com/bug?extid=930e6201080a31e9d0c8
> Fixes: 977e444f59ad ("[media] Mirics MSi3101 SDR Dongle driver")
> Cc: stable@vger.kernel.org
> Signed-off-by: zhangdaolong <dlzhangak@isoftstone.com>
> ---
>  drivers/media/usb/msi2500/msi2500.c | 4 +++-
>  1 file changed, 3 insertions(+), 1 deletion(-)
> 
> diff --git a/drivers/media/usb/msi2500/msi2500.c b/drivers/media/usb/msi2500/msi2500.c
> index 282256ab812a..d89db57f924f 100644
> --- a/drivers/media/usb/msi2500/msi2500.c
> +++ b/drivers/media/usb/msi2500/msi2500.c
> @@ -625,7 +625,9 @@ static void msi2500_buf_queue(struct vb2_buffer *vb)
>  
>  	/* Check the device has not disconnected between prep and queuing */
>  	if (unlikely(!dev->udev)) {
> -		vb2_buffer_done(&buf->vb.vb2_buf, VB2_BUF_STATE_ERROR);
> +		vb2_buffer_done(&buf->vb.vb2_buf,
> +				vb2_start_streaming_called(vb->vb2_queue) ?
> +				VB2_BUF_STATE_ERROR : VB2_BUF_STATE_QUEUED);
>  		return;
>  	}

I think the real problem is that msi2500_buf_queue is calling vb2_buffer_done
at all.

What happens if you just remove this 'if' completely?

I don't think I have seen vb2_buffer_done being called from buf_queue before.
It's very dubious code.

Regards,

	Hans

>  


^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2026-11-11 12:29 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-11-06  8:41 [PATCH] media: msi2500: return buffers as QUEUED in buf_queue() before start_streaming() zhangdaolong
2026-11-11 12:29 ` Hans Verkuil

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®