After an evaluation, GNOME has moved from Bugzilla to GitLab. Learn more about GitLab.
No new issues can be reported in GNOME Bugzilla anymore.
To report an issue in a GNOME project, go to GNOME GitLab.
Do not go to GNOME Gitlab for: Bluefish, Doxygen, GnuCash, GStreamer, java-gnome, LDTP, NetworkManager, Tomboy.
Bug 769765 - v4l2: Sanitise buffer sizes provided by v4l2
v4l2: Sanitise buffer sizes provided by v4l2
Status: RESOLVED FIXED
Product: GStreamer
Classification: Platform
Component: gst-plugins-good
1.8.1
Other Linux
: Normal normal
: 1.10.1
Assigned To: GStreamer Maintainers
GStreamer Maintainers
Depends on:
Blocks:
 
 
Reported: 2016-08-11 20:42 UTC by Will Manley
Modified: 2016-11-04 17:39 UTC
See Also:
GNOME target: ---
GNOME version: ---


Attachments
patch (3.69 KB, patch)
2016-08-11 20:42 UTC, Will Manley
none Details | Review
patch (3.27 KB, patch)
2016-10-08 16:24 UTC, Will Manley
committed Details | Review

Description Will Manley 2016-08-11 20:42:25 UTC
Created attachment 333134 [details] [review]
patch

If the error flag is set we can't trust the rest of the fields in the
`v4l2_buffer` struct.  In particular I've seen problems where the
`bytesused` field of `v4l2_buffer` would be a silly number causing the
later call to:

    gst_memory_resize (group->mem[i], 0, group->planes[i].bytesused);

to result in this error to be printed:

    (pulsevideo:11): GStreamer-CRITICAL **: gst_memory_resize: assertion 'size + mem->offset + offset <= mem->maxsize' failed

besides causing who-knows what other problems.

We reenqueue these buffers and return `GST_V4L2_FLOW_CORRUPTED_BUFFER` so
this will not be a fatal error and dequeue will be attempted once again by
the loop in `gst_v4l2_buffer_pool_dqbuf`.

The invalid `v4l2_buffer` I saw from my capture device was:

    buffer = {
      index = 0,
      type = 1,
      bytesused = 534748928, // <- Invalid
      flags = 8260, // V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC | V4L2_BUF_FLAG_ERROR | V4L2_BUF_FLAG_DONE
      field = 01330, // <- Invalid
      timestamp = {
        tv_sec = 0,
        tv_usec = 0
      },
      timecode = {
        type = 0,
        flags = 0,
        frames = 0 '\000',
        seconds = 0 '\000',
        minutes = 0 '\000',
        hours = 0 '\000',
        userbits = "\000\000\000"
      },
      sequence = 0,
      memory = 2,
      m = {
        offset = 3537219584,
        userptr = 140706665836544, // Could be nonsense, not sure
        planes = 0x7ff8d2d5b000,
        fd = -757747712
      },
      length = 2764800,
      reserved2 = 0,
      reserved = 0
    }

This is from gdb with my own annotations added.

Tested with gst-plugins-good 1.8.1, a Magewell XI100DUSB-HDMI video
capture device and kernel 3.13 using a dodgy HDMI cable which is great at
breaking HDMI capture devices.  I'm using io-mode=userptr and have built
gst-plugins-good without libv4l.
Comment 1 Nicolas Dufresne (ndufresne) 2016-09-06 17:32:36 UTC
Review of attachment 333134 [details] [review]:

The V4L2 doc don't agree, since the error flag means corruption in the produced data. I think we should instead validate the size, if it's smaller then expected, then I'd use the code path where it drops. In decoder scenario, you'll have the error flag on each buffer the follow a drop, deciding to drop of not those is implementation dependant.
Comment 2 Nicolas Dufresne (ndufresne) 2016-09-12 14:44:59 UTC
Will you update your patch ?
Comment 3 Nicolas Dufresne (ndufresne) 2016-09-15 13:32:02 UTC
Ping.
Comment 4 Will Manley 2016-09-15 13:40:23 UTC
Will do, just a little busy at the moment.  I'll get back to you :).
Comment 5 Will Manley 2016-10-08 16:24:10 UTC
Created attachment 337242 [details] [review]
patch

Ok, I've reworked this patch.  I won't have a chance to test it until after the conference when I can get back to my hardware.
Comment 6 Nicolas Dufresne (ndufresne) 2016-10-09 11:50:36 UTC
Review of attachment 337242 [details] [review]:

Looks good to me, let me know when you are done with the test. I'm marking it as commit after freeze, should give you enough time. I think it's a good candidate for backports (1.8/1.10).
Comment 7 Sebastian Dröge (slomo) 2016-11-01 18:13:19 UTC
commit 56b1d088a9a6c69f8c1f3067bc261e88632fae4a
Author: William Manley <will@williammanley.net>
Date:   Sat Oct 8 18:11:17 2016 +0200

    v4l2: Warn, don't assert if v4l gives us a buffer with a too large size
    
    I've seen problems where the `bytesused` field of `v4l2_buffer` would be
    a silly number causing the later call to:
    
        gst_memory_resize (group->mem[i], 0, group->planes[i].bytesused);
    
    to result in this error to be printed:
    
        (pulsevideo:11): GStreamer-CRITICAL **: gst_memory_resize: assertion 'size + mem->offset + offset <= mem->maxsize' failed
    
    besides causing who-knows what other problems.