@@ -84,7 +84,7 @@ struct vivid_fmt {
bool can_do_overlay;
u32 alpha_mask;
u8 planes;
- u32 data_offset[2];
+ u32 data_offset[TPG_MAX_PLANES];
};
extern struct vivid_fmt vivid_formats[];
@@ -185,6 +185,10 @@ bool tpg_s_fourcc(struct tpg_data *tpg, u32 fourcc)
case V4L2_PIX_FMT_ABGR32:
tpg->is_yuv = false;
break;
+ case V4L2_PIX_FMT_YUV420:
+ tpg->planes = 3;
+ tpg->is_yuv = true;
+ break;
case V4L2_PIX_FMT_NV16M:
case V4L2_PIX_FMT_NV61M:
tpg->planes = 2;
@@ -229,6 +233,11 @@ bool tpg_s_fourcc(struct tpg_data *tpg, u32 fourcc)
tpg->twopixelsize[0] = 2;
tpg->twopixelsize[1] = 2;
break;
+ case V4L2_PIX_FMT_YUV420:
+ tpg->twopixelsize[0] = 2;
+ tpg->twopixelsize[1] = 1;
+ tpg->twopixelsize[2] = 1;
+ break;
}
return true;
}
@@ -671,6 +680,11 @@ static void gen_twopix(struct tpg_data *tpg,
buf[0][offset] = r_y;
buf[1][offset] = odd ? g_u : b_v;
break;
+ case V4L2_PIX_FMT_YUV420:
+ buf[0][offset] = r_y;
+ buf[1][offset / 2] = g_u;
+ buf[2][offset / 2] = b_v;
+ break;
case V4L2_PIX_FMT_YUYV:
buf[0][offset] = r_y;
@@ -87,7 +87,7 @@ enum tpg_move_mode {
extern const char * const tpg_aspect_strings[];
-#define TPG_MAX_PLANES 2
+#define TPG_MAX_PLANES 3
#define TPG_MAX_PAT_LINES 8
struct tpg_data {
@@ -98,6 +98,13 @@ static int vid_cap_queue_setup(struct vb2_queue *vq, const struct v4l2_format *f
unsigned h = dev->fmt_cap_rect.height;
unsigned p;
+ dprintk(dev, 1, "%s, fourcc=0x%x, planes=%u\n", __func__, dev->tpg.fourcc,
+ planes);
+ //for (p = 0; p < planes; p++) {
+ //dprintk(dev, 1, "%s, %u bpl=%u, 2bytesize=%u\n", __func__,
+ // p, tpg_g_bytesperline(&dev->tpg, p), tpg_g_twopixelsize(&dev->tpg, p));
+ //}
+
if (dev->field_cap == V4L2_FIELD_ALTERNATE) {
/*
* You cannot use read() with FIELD_ALTERNATE since the field
@@ -149,12 +156,20 @@ static int vid_cap_queue_setup(struct vb2_queue *vq, const struct v4l2_format *f
*nplanes = planes;
+ for (p = 0; p < planes; p++) {
+ dprintk(dev, 1, "%s, %u bpl=%u, 2bytesize=%u\n", __func__,
+ p, tpg_g_bytesperline(&dev->tpg, p), tpg_g_twopixelsize(&dev->tpg, p));
+
+ }
/*
* videobuf2-vmalloc allocator is context-less so no need to set
* alloc_ctxs array.
*/
- if (planes == 2)
+ if (planes == 3)
+ dprintk(dev, 1, "%s, count=%d, sizes=%u, %u, %u\n", __func__,
+ *nbuffers, sizes[0], sizes[1], sizes[2]);
+ else if (planes == 2)
dprintk(dev, 1, "%s, count=%d, sizes=%u, %u\n", __func__,
*nbuffers, sizes[0], sizes[1]);
else
@@ -519,6 +534,8 @@ int vivid_g_fmt_vid_cap(struct file *file, void *priv,
struct v4l2_pix_format_mplane *mp = &f->fmt.pix_mp;
unsigned p;
+ dprintk(dev, 1, "%s, planes=%u\n", __func__, dev->fmt_cap->planes);
+
mp->width = dev->fmt_cap_rect.width;
mp->height = dev->fmt_cap_rect.height;
mp->field = dev->field_cap;
@@ -629,6 +646,8 @@ int vivid_s_fmt_vid_cap(struct file *file, void *priv,
unsigned factor = 1;
unsigned i;
+ dprintk(dev, 1, "@%s\n", __func__);
+
if (ret < 0)
return ret;
@@ -645,6 +664,10 @@ int vivid_s_fmt_vid_cap(struct file *file, void *priv,
dev->fmt_cap = vivid_get_format(dev, mp->pixelformat);
if (V4L2_FIELD_HAS_T_OR_B(mp->field))
factor = 2;
+ if (V4L2_TYPE_IS_MULTIPLANAR(f->type)) {
+ tpg_s_fourcc(&dev->tpg, dev->fmt_cap->fourcc);
+ dev->tpg.planes = mp->num_planes;
+ }
/* Note: the webcam input doesn't support scaling, cropping or composing */
@@ -732,6 +755,8 @@ int vivid_s_fmt_vid_cap(struct file *file, void *priv,
tpg_s_bytesperline(&dev->tpg, 0, mp->plane_fmt[0].bytesperline);
if (tpg_g_planes(&dev->tpg) > 1)
tpg_s_bytesperline(&dev->tpg, 1, mp->plane_fmt[1].bytesperline);
+ if (tpg_g_planes(&dev->tpg) > 2)
+ tpg_s_bytesperline(&dev->tpg, 2, mp->plane_fmt[2].bytesperline);
dev->field_cap = mp->field;
tpg_s_field(&dev->tpg, dev->field_cap);
tpg_s_crop_compose(&dev->tpg, &dev->crop_cap, &dev->compose_cap);
@@ -181,10 +181,18 @@ struct vivid_fmt vivid_formats[] = {
.planes = 2,
.data_offset = { 0, PLANE0_DATA_OFFSET },
},
+ {
+ .name = "4:2:0, planar, YUV",
+ .fourcc = V4L2_PIX_FMT_YUV420,
+ .depth = 8,
+ .is_yuv = true,
+ .planes = 3,
+ .data_offset = { 0, 0, 0},
+ },
};
-/* There are 2 multiplanar formats in the list */
-#define VIVID_MPLANAR_FORMATS 2
+/* There are 3 multiplanar formats in the list */
+#define VIVID_MPLANAR_FORMATS 3
const struct vivid_fmt *vivid_get_format(struct vivid_dev *dev, u32 pixelformat)
{