Skip to content

Commit 849110e

Browse files
6by9popcornmix
authored andcommitted
media: hevc_dec: Add in downstream single planar SAND variant
Upstream will take the multi-planar SAND format, but add back in the downstream single planar variant for backwards compatibility Signed-off-by: Dave Stevenson <dave.stevenson@raspberrypi.com>
1 parent ee8c64f commit 849110e

File tree

2 files changed

+151
-47
lines changed

2 files changed

+151
-47
lines changed

drivers/media/platform/raspberrypi/hevc_dec/hevc_d_h265.c

Lines changed: 70 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1652,12 +1652,27 @@ void hevc_d_h265_setup(struct hevc_d_ctx *ctx, struct hevc_d_run *run)
16521652
de->cmd_len = 0;
16531653
de->dpbno_col = ~0U;
16541654

1655-
de->luma_stride = ctx->dst_fmt.height * 128;
1656-
de->frame_luma_addr =
1657-
vb2_dma_contig_plane_dma_addr(&run->dst->vb2_buf, 0);
1658-
de->chroma_stride = de->luma_stride / 2;
1659-
de->frame_chroma_addr =
1660-
vb2_dma_contig_plane_dma_addr(&run->dst->vb2_buf, 1);
1655+
switch (ctx->dst_fmt.pixelformat) {
1656+
case V4L2_PIX_FMT_NV12MT_COL128:
1657+
case V4L2_PIX_FMT_NV12MT_10_COL128:
1658+
de->luma_stride = ctx->dst_fmt.height * 128;
1659+
de->frame_luma_addr =
1660+
vb2_dma_contig_plane_dma_addr(&run->dst->vb2_buf, 0);
1661+
de->chroma_stride = de->luma_stride / 2;
1662+
de->frame_chroma_addr =
1663+
vb2_dma_contig_plane_dma_addr(&run->dst->vb2_buf, 1);
1664+
break;
1665+
case V4L2_PIX_FMT_NV12_COL128:
1666+
case V4L2_PIX_FMT_NV12_10_COL128:
1667+
de->luma_stride = ctx->dst_fmt.plane_fmt[0].bytesperline * 128;
1668+
de->frame_luma_addr =
1669+
vb2_dma_contig_plane_dma_addr(&run->dst->vb2_buf, 0);
1670+
de->chroma_stride = de->luma_stride;
1671+
de->frame_chroma_addr = de->frame_luma_addr +
1672+
(ctx->dst_fmt.height * 128);
1673+
break;
1674+
}
1675+
16611676
de->frame_aux = NULL;
16621677

16631678
if (s->sps.bit_depth_luma_minus8 !=
@@ -1669,15 +1684,16 @@ void hevc_d_h265_setup(struct hevc_d_ctx *ctx, struct hevc_d_run *run)
16691684
goto fail;
16701685
}
16711686
if (s->sps.bit_depth_luma_minus8 == 0) {
1672-
if (ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12MT_COL128) {
1687+
if (ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12MT_COL128 &&
1688+
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12_COL128) {
16731689
v4l2_err(&dev->v4l2_dev,
16741690
"Pixel format %#x != NV12MT_COL128 for 8-bit output",
16751691
ctx->dst_fmt.pixelformat);
16761692
goto fail;
16771693
}
16781694
} else if (s->sps.bit_depth_luma_minus8 == 2) {
1679-
if (ctx->dst_fmt.pixelformat !=
1680-
V4L2_PIX_FMT_NV12MT_10_COL128) {
1695+
if (ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12MT_10_COL128 &&
1696+
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12_10_COL128) {
16811697
v4l2_err(&dev->v4l2_dev,
16821698
"Pixel format %#x != NV12MT_10_COL128 for 10-bit output",
16831699
ctx->dst_fmt.pixelformat);
@@ -1688,20 +1704,40 @@ void hevc_d_h265_setup(struct hevc_d_ctx *ctx, struct hevc_d_run *run)
16881704
s->sps.bit_depth_luma_minus8 + 8);
16891705
goto fail;
16901706
}
1691-
if (run->dst->vb2_buf.num_planes != 2) {
1692-
v4l2_warn(&dev->v4l2_dev, "Capture planes (%d) != 2\n",
1693-
run->dst->vb2_buf.num_planes);
1694-
goto fail;
1695-
}
1696-
if (run->dst->planes[0].length < ctx->dst_fmt.plane_fmt[0].sizeimage ||
1697-
run->dst->planes[1].length < ctx->dst_fmt.plane_fmt[1].sizeimage) {
1698-
v4l2_warn(&dev->v4l2_dev,
1699-
"Capture planes length (%d/%d) < sizeimage (%d/%d)\n",
1700-
run->dst->planes[0].length,
1701-
run->dst->planes[1].length,
1702-
ctx->dst_fmt.plane_fmt[0].sizeimage,
1703-
ctx->dst_fmt.plane_fmt[1].sizeimage);
1704-
goto fail;
1707+
switch (ctx->dst_fmt.pixelformat) {
1708+
case V4L2_PIX_FMT_NV12MT_COL128:
1709+
case V4L2_PIX_FMT_NV12MT_10_COL128:
1710+
if (run->dst->vb2_buf.num_planes != 2) {
1711+
v4l2_warn(&dev->v4l2_dev, "Capture planes (%d) != 2\n",
1712+
run->dst->vb2_buf.num_planes);
1713+
goto fail;
1714+
}
1715+
if (run->dst->planes[0].length < ctx->dst_fmt.plane_fmt[0].sizeimage ||
1716+
run->dst->planes[1].length < ctx->dst_fmt.plane_fmt[1].sizeimage) {
1717+
v4l2_warn(&dev->v4l2_dev,
1718+
"Capture planes length (%d/%d) < sizeimage (%d/%d)\n",
1719+
run->dst->planes[0].length,
1720+
run->dst->planes[1].length,
1721+
ctx->dst_fmt.plane_fmt[0].sizeimage,
1722+
ctx->dst_fmt.plane_fmt[1].sizeimage);
1723+
goto fail;
1724+
}
1725+
break;
1726+
case V4L2_PIX_FMT_NV12_COL128:
1727+
case V4L2_PIX_FMT_NV12_10_COL128:
1728+
if (run->dst->vb2_buf.num_planes != 1) {
1729+
v4l2_warn(&dev->v4l2_dev, "Capture planes (%d) != 1\n",
1730+
run->dst->vb2_buf.num_planes);
1731+
goto fail;
1732+
}
1733+
if (run->dst->planes[0].length < ctx->dst_fmt.plane_fmt[0].sizeimage) {
1734+
v4l2_warn(&dev->v4l2_dev,
1735+
"Capture planes length (%d) < sizeimage (%d)\n",
1736+
run->dst->planes[0].length,
1737+
ctx->dst_fmt.plane_fmt[0].sizeimage);
1738+
goto fail;
1739+
}
1740+
break;
17051741
}
17061742

17071743
/*
@@ -1861,8 +1897,13 @@ void hevc_d_h265_setup(struct hevc_d_ctx *ctx, struct hevc_d_run *run)
18611897

18621898
de->ref_addrs[i][0] =
18631899
vb2_dma_contig_plane_dma_addr(buf, 0);
1864-
de->ref_addrs[i][1] =
1865-
vb2_dma_contig_plane_dma_addr(buf, 1);
1900+
if (ctx->dst_fmt.pixelformat == V4L2_PIX_FMT_NV12MT_COL128 ||
1901+
ctx->dst_fmt.pixelformat == V4L2_PIX_FMT_NV12MT_10_COL128)
1902+
de->ref_addrs[i][1] =
1903+
vb2_dma_contig_plane_dma_addr(buf, 1);
1904+
else
1905+
de->ref_addrs[i][1] = de->ref_addrs[i][0] +
1906+
(ctx->dst_fmt.height * 128);
18661907
}
18671908

18681909
/* Move DPB from temp */
@@ -2414,9 +2455,11 @@ static int try_ctrl_sps(struct v4l2_ctrl *ctrl)
24142455
return 0;
24152456

24162457
if ((sps->bit_depth_luma_minus8 == 0 &&
2417-
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12MT_COL128) ||
2458+
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12MT_COL128 &&
2459+
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12_COL128) ||
24182460
(sps->bit_depth_luma_minus8 == 2 &&
2419-
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12MT_10_COL128)) {
2461+
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12MT_10_COL128 &&
2462+
ctx->dst_fmt.pixelformat != V4L2_PIX_FMT_NV12_10_COL128)) {
24202463
v4l2_warn(&dev->v4l2_dev,
24212464
"SPS luma depth %d does not match capture format\n",
24222465
sps->bit_depth_luma_minus8 + 8);

drivers/media/platform/raspberrypi/hevc_dec/hevc_d_video.c

Lines changed: 81 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -150,17 +150,55 @@ static void hevc_d_prepare_dst_format(struct v4l2_pix_format_mplane *pix_fmt)
150150
bytesperline = width * 4 / 3;
151151
sizeimage = bytesperline * height;
152152
break;
153+
154+
case V4L2_PIX_FMT_NV12_COL128:
155+
/* Width rounds up to columns */
156+
width = ALIGN(width, 128);
157+
height = ALIGN(height, 8);
158+
159+
/* column height
160+
* Accept suggested shape if at least min & < 2 * min
161+
*/
162+
bytesperline = constrain2x(bytesperline, height * 3 / 2);
163+
sizeimage = bytesperline * width;
164+
break;
165+
166+
case V4L2_PIX_FMT_NV12_10_COL128:
167+
/* width in pixels (3 pels = 4 bytes) rounded to 128 byte
168+
* columns
169+
*/
170+
width = ALIGN(((width + 2) / 3), 32) * 3;
171+
height = ALIGN(height, 8);
172+
173+
/* column height
174+
* Accept suggested shape if at least min & < 2 * min
175+
*/
176+
bytesperline = constrain2x(bytesperline, height * 3 / 2);
177+
sizeimage = bytesperline * width * 4 / 3;
178+
break;
153179
}
154180

155181
pix_fmt->width = width;
156182
pix_fmt->height = height;
157183

158184
pix_fmt->field = V4L2_FIELD_NONE;
159-
pix_fmt->plane_fmt[0].bytesperline = bytesperline;
160-
pix_fmt->plane_fmt[0].sizeimage = sizeimage;
161-
pix_fmt->plane_fmt[1].bytesperline = bytesperline;
162-
pix_fmt->plane_fmt[1].sizeimage = sizeimage / 2;
163-
pix_fmt->num_planes = 2;
185+
switch (pix_fmt->pixelformat) {
186+
default:
187+
case V4L2_PIX_FMT_NV12MT_COL128:
188+
case V4L2_PIX_FMT_NV12MT_10_COL128:
189+
pix_fmt->plane_fmt[0].bytesperline = bytesperline;
190+
pix_fmt->plane_fmt[0].sizeimage = sizeimage;
191+
pix_fmt->plane_fmt[1].bytesperline = bytesperline;
192+
pix_fmt->plane_fmt[1].sizeimage = sizeimage / 2;
193+
pix_fmt->num_planes = 2;
194+
break;
195+
case V4L2_PIX_FMT_NV12_COL128:
196+
case V4L2_PIX_FMT_NV12_10_COL128:
197+
pix_fmt->plane_fmt[0].bytesperline = bytesperline;
198+
pix_fmt->plane_fmt[0].sizeimage = sizeimage;
199+
pix_fmt->num_planes = 1;
200+
break;
201+
}
164202
}
165203

166204
static int hevc_d_querycap(struct file *file, void *priv,
@@ -245,19 +283,31 @@ static int hevc_d_hevc_validate_sps(const struct v4l2_ctrl_hevc_sps * const sps)
245283
static u32 pixelformat_from_sps(const struct v4l2_ctrl_hevc_sps * const sps,
246284
const int index)
247285
{
286+
static const u32 all_formats[] = {
287+
V4L2_PIX_FMT_NV12MT_COL128,
288+
V4L2_PIX_FMT_NV12MT_10_COL128,
289+
V4L2_PIX_FMT_NV12_COL128,
290+
V4L2_PIX_FMT_NV12_10_COL128,
291+
};
248292
u32 pf = 0;
249293

250294
if (!is_sps_set(sps) || !hevc_d_hevc_validate_sps(sps)) {
251295
/* Treat this as an error? For now return both */
252-
if (index == 0)
253-
pf = V4L2_PIX_FMT_NV12MT_COL128;
254-
else if (index == 1)
255-
pf = V4L2_PIX_FMT_NV12MT_10_COL128;
256-
} else if (index == 0) {
257-
if (sps->bit_depth_luma_minus8 == 0)
258-
pf = V4L2_PIX_FMT_NV12MT_COL128;
259-
else if (sps->bit_depth_luma_minus8 == 2)
260-
pf = V4L2_PIX_FMT_NV12MT_10_COL128;
296+
297+
if (index < ARRAY_SIZE(all_formats))
298+
pf = all_formats[index];
299+
} else {
300+
if (index == 0) {
301+
if (sps->bit_depth_luma_minus8 == 0)
302+
pf = V4L2_PIX_FMT_NV12MT_COL128;
303+
else if (sps->bit_depth_luma_minus8 == 2)
304+
pf = V4L2_PIX_FMT_NV12MT_10_COL128;
305+
} else if (index == 1) {
306+
if (sps->bit_depth_luma_minus8 == 0)
307+
pf = V4L2_PIX_FMT_NV12_COL128;
308+
else if (sps->bit_depth_luma_minus8 == 2)
309+
pf = V4L2_PIX_FMT_NV12_10_COL128;
310+
}
261311
}
262312

263313
return pf;
@@ -469,17 +519,28 @@ static int hevc_d_queue_setup(struct vb2_queue *vq, unsigned int *nbufs,
469519
}
470520

471521
if (*nplanes) {
472-
if (*nplanes != expected_nplanes ||
473-
sizes[0] < pix_fmt->plane_fmt[0].sizeimage ||
474-
sizes[1] < pix_fmt->plane_fmt[1].sizeimage)
475-
return -EINVAL;
522+
if (pix_fmt->pixelformat == V4L2_PIX_FMT_NV12MT_COL128 ||
523+
pix_fmt->pixelformat == V4L2_PIX_FMT_NV12MT_10_COL128) {
524+
if (*nplanes != expected_nplanes ||
525+
sizes[0] < pix_fmt->plane_fmt[0].sizeimage ||
526+
sizes[1] < pix_fmt->plane_fmt[1].sizeimage)
527+
return -EINVAL;
528+
} else {
529+
if (sizes[0] < pix_fmt->plane_fmt[0].sizeimage)
530+
return -EINVAL;
531+
}
476532
} else {
477533
sizes[0] = pix_fmt->plane_fmt[0].sizeimage;
478534
if (V4L2_TYPE_IS_OUTPUT(vq->type)) {
479535
*nplanes = 1;
480536
} else {
481-
sizes[1] = pix_fmt->plane_fmt[1].sizeimage;
482-
*nplanes = 2;
537+
if (pix_fmt->pixelformat == V4L2_PIX_FMT_NV12MT_COL128 ||
538+
pix_fmt->pixelformat == V4L2_PIX_FMT_NV12MT_10_COL128) {
539+
sizes[1] = pix_fmt->plane_fmt[1].sizeimage;
540+
*nplanes = 2;
541+
} else {
542+
*nplanes = 1;
543+
}
483544
}
484545
}
485546

0 commit comments

Comments
 (0)