@@ -61,6 +61,19 @@ MODULE_PARM_DESC(max_video_width, "Threshold for video mode");
61
61
module_param (max_video_height , int , S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH );
62
62
MODULE_PARM_DESC (max_video_height , "Threshold for video mode" );
63
63
64
+ /* Gstreamer bug https://bugzilla.gnome.org/show_bug.cgi?id=726521
65
+ * v4l2src does bad (and actually wrong) things when the vidioc_enum_framesizes
66
+ * function says type V4L2_FRMSIZE_TYPE_STEPWISE, which we do by default.
67
+ * It's happier if we just don't say anything at all, when it then
68
+ * sets up a load of defaults that it thinks might work.
69
+ * If gst_v4l2src_is_broken is non-zero, then we remove the function from
70
+ * our function table list (actually switch to an alternate set, but same
71
+ * result).
72
+ */
73
+ int gst_v4l2src_is_broken = 0 ;
74
+ module_param (gst_v4l2src_is_broken , int , S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH );
75
+ MODULE_PARM_DESC (gst_v4l2src_is_broken , "If non-zero, enable workaround for Gstreamer" );
76
+
64
77
static struct bm2835_mmal_dev * gdev ; /* global device data */
65
78
66
79
#define FPS_MIN 1
@@ -1352,6 +1365,47 @@ static const struct v4l2_ioctl_ops camera0_ioctl_ops = {
1352
1365
.vidioc_unsubscribe_event = v4l2_event_unsubscribe ,
1353
1366
};
1354
1367
1368
+ static const struct v4l2_ioctl_ops camera0_ioctl_ops_gstreamer = {
1369
+ /* overlay */
1370
+ .vidioc_enum_fmt_vid_overlay = vidioc_enum_fmt_vid_overlay ,
1371
+ .vidioc_g_fmt_vid_overlay = vidioc_g_fmt_vid_overlay ,
1372
+ .vidioc_try_fmt_vid_overlay = vidioc_try_fmt_vid_overlay ,
1373
+ .vidioc_s_fmt_vid_overlay = vidioc_s_fmt_vid_overlay ,
1374
+ .vidioc_overlay = vidioc_overlay ,
1375
+ .vidioc_g_fbuf = vidioc_g_fbuf ,
1376
+
1377
+ /* inputs */
1378
+ .vidioc_enum_input = vidioc_enum_input ,
1379
+ .vidioc_g_input = vidioc_g_input ,
1380
+ .vidioc_s_input = vidioc_s_input ,
1381
+
1382
+ /* capture */
1383
+ .vidioc_querycap = vidioc_querycap ,
1384
+ .vidioc_enum_fmt_vid_cap = vidioc_enum_fmt_vid_cap ,
1385
+ .vidioc_g_fmt_vid_cap = vidioc_g_fmt_vid_cap ,
1386
+ .vidioc_try_fmt_vid_cap = vidioc_try_fmt_vid_cap ,
1387
+ .vidioc_s_fmt_vid_cap = vidioc_s_fmt_vid_cap ,
1388
+
1389
+ /* buffer management */
1390
+ .vidioc_reqbufs = vb2_ioctl_reqbufs ,
1391
+ .vidioc_create_bufs = vb2_ioctl_create_bufs ,
1392
+ .vidioc_prepare_buf = vb2_ioctl_prepare_buf ,
1393
+ .vidioc_querybuf = vb2_ioctl_querybuf ,
1394
+ .vidioc_qbuf = vb2_ioctl_qbuf ,
1395
+ .vidioc_dqbuf = vb2_ioctl_dqbuf ,
1396
+ /* Remove this function ptr to fix gstreamer bug
1397
+ .vidioc_enum_framesizes = vidioc_enum_framesizes, */
1398
+ .vidioc_enum_frameintervals = vidioc_enum_frameintervals ,
1399
+ .vidioc_g_parm = vidioc_g_parm ,
1400
+ .vidioc_s_parm = vidioc_s_parm ,
1401
+ .vidioc_streamon = vb2_ioctl_streamon ,
1402
+ .vidioc_streamoff = vb2_ioctl_streamoff ,
1403
+
1404
+ .vidioc_log_status = v4l2_ctrl_log_status ,
1405
+ .vidioc_subscribe_event = v4l2_ctrl_subscribe_event ,
1406
+ .vidioc_unsubscribe_event = v4l2_event_unsubscribe ,
1407
+ };
1408
+
1355
1409
/* ------------------------------------------------------------------
1356
1410
Driver init/finalise
1357
1411
------------------------------------------------------------------*/
@@ -1598,6 +1652,11 @@ static int __init bm2835_mmal_init_device(struct bm2835_mmal_dev *dev,
1598
1652
int ret ;
1599
1653
1600
1654
* vfd = vdev_template ;
1655
+ if (gst_v4l2src_is_broken ) {
1656
+ v4l2_info (& dev -> v4l2_dev ,
1657
+ "Work-around for gstreamer issue is active.\n" );
1658
+ vfd -> ioctl_ops = & camera0_ioctl_ops_gstreamer ;
1659
+ }
1601
1660
1602
1661
vfd -> v4l2_dev = & dev -> v4l2_dev ;
1603
1662
0 commit comments