Message ID | 20241120110105.244413-3-hugues.fruchet@foss.st.com (mailing list archive) |
---|---|
State | New |
Headers | show |
Series | Add WebP support to hantro decoder | expand |
Le mercredi 20 novembre 2024 à 12:01 +0100, Hugues Fruchet a écrit : > Add WebP picture decoding support to VP8 stateless decoder. > > Signed-off-by: Hugues Fruchet <hugues.fruchet@foss.st.com> > --- > .../media/platform/verisilicon/hantro_g1_regs.h | 1 + > .../platform/verisilicon/hantro_g1_vp8_dec.c | 14 ++++++++++++++ > .../media/platform/verisilicon/hantro_v4l2.c | 2 ++ > .../platform/verisilicon/stm32mp25_vpu_hw.c | 17 +++++++++++++++-- > 4 files changed, 32 insertions(+), 2 deletions(-) > > diff --git a/drivers/media/platform/verisilicon/hantro_g1_regs.h b/drivers/media/platform/verisilicon/hantro_g1_regs.h > index c623b3b0be18..e7d4db788e57 100644 > --- a/drivers/media/platform/verisilicon/hantro_g1_regs.h > +++ b/drivers/media/platform/verisilicon/hantro_g1_regs.h > @@ -232,6 +232,7 @@ > #define G1_REG_DEC_CTRL7_DCT7_START_BIT(x) (((x) & 0x3f) << 0) > #define G1_REG_ADDR_STR 0x030 > #define G1_REG_ADDR_DST 0x034 > +#define G1_REG_ADDR_DST_CHROMA 0x038 > #define G1_REG_ADDR_REF(i) (0x038 + ((i) * 0x4)) > #define G1_REG_ADDR_REF_FIELD_E BIT(1) > #define G1_REG_ADDR_REF_TOPC_E BIT(0) > diff --git a/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c b/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c > index 851eb67f19f5..c83ee6f5edc8 100644 > --- a/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c > +++ b/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c > @@ -307,6 +307,12 @@ static void cfg_parts(struct hantro_ctx *ctx, > G1_REG_DEC_CTRL3_STREAM_LEN(dct_part_total_len), > G1_REG_DEC_CTRL3); > > + if (ctx->vpu_src_fmt->fourcc == V4L2_PIX_FMT_WEBP_FRAME) > + vdpu_write_relaxed(vpu, > + G1_REG_DEC_CTRL3_STREAM_LEN_EXT > + (dct_part_total_len >> 24), > + G1_REG_DEC_CTRL3); > + > /* DCT partitions base address */ > for (i = 0; i < hdr->num_dct_parts; i++) { > u32 byte_offset = dct_part_offset + dct_size_part_size + count; > @@ -427,6 +433,12 @@ static void cfg_buffers(struct hantro_ctx *ctx, > > dst_dma = hantro_get_dec_buf_addr(ctx, &vb2_dst->vb2_buf); > vdpu_write_relaxed(vpu, dst_dma, G1_REG_ADDR_DST); > + > + if (ctx->vpu_src_fmt->fourcc == V4L2_PIX_FMT_WEBP_FRAME) > + vdpu_write_relaxed(vpu, dst_dma + > + ctx->dst_fmt.plane_fmt[0].bytesperline * > + ctx->dst_fmt.height, > + G1_REG_ADDR_DST_CHROMA); > } > > int hantro_g1_vp8_dec_run(struct hantro_ctx *ctx) > @@ -471,6 +483,8 @@ int hantro_g1_vp8_dec_run(struct hantro_ctx *ctx) > reg |= G1_REG_DEC_CTRL0_SKIP_MODE; > if (hdr->lf.level == 0) > reg |= G1_REG_DEC_CTRL0_FILTERING_DIS; > + if (ctx->vpu_src_fmt->fourcc == V4L2_PIX_FMT_WEBP_FRAME) > + reg |= G1_REG_DEC_CTRL0_WEBP_E; > vdpu_write_relaxed(vpu, reg, G1_REG_DEC_CTRL0); > > /* Frame dimensions */ > diff --git a/drivers/media/platform/verisilicon/hantro_v4l2.c b/drivers/media/platform/verisilicon/hantro_v4l2.c > index 2513adfbd825..7075b2ba1ec2 100644 > --- a/drivers/media/platform/verisilicon/hantro_v4l2.c > +++ b/drivers/media/platform/verisilicon/hantro_v4l2.c > @@ -470,6 +470,7 @@ hantro_update_requires_request(struct hantro_ctx *ctx, u32 fourcc) > break; > case V4L2_PIX_FMT_MPEG2_SLICE: > case V4L2_PIX_FMT_VP8_FRAME: > + case V4L2_PIX_FMT_WEBP_FRAME: > case V4L2_PIX_FMT_H264_SLICE: > case V4L2_PIX_FMT_HEVC_SLICE: > case V4L2_PIX_FMT_VP9_FRAME: > @@ -492,6 +493,7 @@ hantro_update_requires_hold_capture_buf(struct hantro_ctx *ctx, u32 fourcc) > case V4L2_PIX_FMT_JPEG: > case V4L2_PIX_FMT_MPEG2_SLICE: > case V4L2_PIX_FMT_VP8_FRAME: > + case V4L2_PIX_FMT_WEBP_FRAME: > case V4L2_PIX_FMT_HEVC_SLICE: > case V4L2_PIX_FMT_VP9_FRAME: > vq->subsystem_flags &= ~(VB2_V4L2_FL_SUPPORTS_M2M_HOLD_CAPTURE_BUF); > diff --git a/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c b/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c > index 833821120b20..48d6912c3bab 100644 > --- a/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c > +++ b/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c > @@ -22,10 +22,10 @@ static const struct hantro_fmt stm32mp25_vdec_fmts[] = { > .codec_mode = HANTRO_MODE_NONE, > .frmsize = { > .min_width = FMT_MIN_WIDTH, > - .max_width = FMT_FHD_WIDTH, > + .max_width = FMT_4K_WIDTH, > .step_width = MB_DIM, > .min_height = FMT_MIN_HEIGHT, > - .max_height = FMT_FHD_HEIGHT, > + .max_height = FMT_4K_HEIGHT, I'm a little surprised of this change, since this is modifying VP8_FRAME, while we should instead introduce WEBP_FRAME. > .step_height = MB_DIM, > }, > }, > @@ -68,6 +68,19 @@ static const struct hantro_fmt stm32mp25_venc_fmts[] = { > .codec_mode = HANTRO_MODE_NONE, > .enc_fmt = ROCKCHIP_VPU_ENC_FMT_YUV420SP, > }, > + { > + .fourcc = V4L2_PIX_FMT_WEBP_FRAME, > + .codec_mode = HANTRO_MODE_VP8_DEC, > + .max_depth = 2, > + .frmsize = { > + .min_width = FMT_MIN_WIDTH, > + .max_width = FMT_4K_WIDTH, > + .step_width = MB_DIM, > + .min_height = FMT_MIN_HEIGHT, > + .max_height = FMT_4K_HEIGHT, > + .step_height = MB_DIM, > + }, > + }, This is venc_fmt (encoder), this shouldn't be there. > { > .fourcc = V4L2_PIX_FMT_YUYV, > .codec_mode = HANTRO_MODE_NONE,
diff --git a/drivers/media/platform/verisilicon/hantro_g1_regs.h b/drivers/media/platform/verisilicon/hantro_g1_regs.h index c623b3b0be18..e7d4db788e57 100644 --- a/drivers/media/platform/verisilicon/hantro_g1_regs.h +++ b/drivers/media/platform/verisilicon/hantro_g1_regs.h @@ -232,6 +232,7 @@ #define G1_REG_DEC_CTRL7_DCT7_START_BIT(x) (((x) & 0x3f) << 0) #define G1_REG_ADDR_STR 0x030 #define G1_REG_ADDR_DST 0x034 +#define G1_REG_ADDR_DST_CHROMA 0x038 #define G1_REG_ADDR_REF(i) (0x038 + ((i) * 0x4)) #define G1_REG_ADDR_REF_FIELD_E BIT(1) #define G1_REG_ADDR_REF_TOPC_E BIT(0) diff --git a/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c b/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c index 851eb67f19f5..c83ee6f5edc8 100644 --- a/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c +++ b/drivers/media/platform/verisilicon/hantro_g1_vp8_dec.c @@ -307,6 +307,12 @@ static void cfg_parts(struct hantro_ctx *ctx, G1_REG_DEC_CTRL3_STREAM_LEN(dct_part_total_len), G1_REG_DEC_CTRL3); + if (ctx->vpu_src_fmt->fourcc == V4L2_PIX_FMT_WEBP_FRAME) + vdpu_write_relaxed(vpu, + G1_REG_DEC_CTRL3_STREAM_LEN_EXT + (dct_part_total_len >> 24), + G1_REG_DEC_CTRL3); + /* DCT partitions base address */ for (i = 0; i < hdr->num_dct_parts; i++) { u32 byte_offset = dct_part_offset + dct_size_part_size + count; @@ -427,6 +433,12 @@ static void cfg_buffers(struct hantro_ctx *ctx, dst_dma = hantro_get_dec_buf_addr(ctx, &vb2_dst->vb2_buf); vdpu_write_relaxed(vpu, dst_dma, G1_REG_ADDR_DST); + + if (ctx->vpu_src_fmt->fourcc == V4L2_PIX_FMT_WEBP_FRAME) + vdpu_write_relaxed(vpu, dst_dma + + ctx->dst_fmt.plane_fmt[0].bytesperline * + ctx->dst_fmt.height, + G1_REG_ADDR_DST_CHROMA); } int hantro_g1_vp8_dec_run(struct hantro_ctx *ctx) @@ -471,6 +483,8 @@ int hantro_g1_vp8_dec_run(struct hantro_ctx *ctx) reg |= G1_REG_DEC_CTRL0_SKIP_MODE; if (hdr->lf.level == 0) reg |= G1_REG_DEC_CTRL0_FILTERING_DIS; + if (ctx->vpu_src_fmt->fourcc == V4L2_PIX_FMT_WEBP_FRAME) + reg |= G1_REG_DEC_CTRL0_WEBP_E; vdpu_write_relaxed(vpu, reg, G1_REG_DEC_CTRL0); /* Frame dimensions */ diff --git a/drivers/media/platform/verisilicon/hantro_v4l2.c b/drivers/media/platform/verisilicon/hantro_v4l2.c index 2513adfbd825..7075b2ba1ec2 100644 --- a/drivers/media/platform/verisilicon/hantro_v4l2.c +++ b/drivers/media/platform/verisilicon/hantro_v4l2.c @@ -470,6 +470,7 @@ hantro_update_requires_request(struct hantro_ctx *ctx, u32 fourcc) break; case V4L2_PIX_FMT_MPEG2_SLICE: case V4L2_PIX_FMT_VP8_FRAME: + case V4L2_PIX_FMT_WEBP_FRAME: case V4L2_PIX_FMT_H264_SLICE: case V4L2_PIX_FMT_HEVC_SLICE: case V4L2_PIX_FMT_VP9_FRAME: @@ -492,6 +493,7 @@ hantro_update_requires_hold_capture_buf(struct hantro_ctx *ctx, u32 fourcc) case V4L2_PIX_FMT_JPEG: case V4L2_PIX_FMT_MPEG2_SLICE: case V4L2_PIX_FMT_VP8_FRAME: + case V4L2_PIX_FMT_WEBP_FRAME: case V4L2_PIX_FMT_HEVC_SLICE: case V4L2_PIX_FMT_VP9_FRAME: vq->subsystem_flags &= ~(VB2_V4L2_FL_SUPPORTS_M2M_HOLD_CAPTURE_BUF); diff --git a/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c b/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c index 833821120b20..48d6912c3bab 100644 --- a/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c +++ b/drivers/media/platform/verisilicon/stm32mp25_vpu_hw.c @@ -22,10 +22,10 @@ static const struct hantro_fmt stm32mp25_vdec_fmts[] = { .codec_mode = HANTRO_MODE_NONE, .frmsize = { .min_width = FMT_MIN_WIDTH, - .max_width = FMT_FHD_WIDTH, + .max_width = FMT_4K_WIDTH, .step_width = MB_DIM, .min_height = FMT_MIN_HEIGHT, - .max_height = FMT_FHD_HEIGHT, + .max_height = FMT_4K_HEIGHT, .step_height = MB_DIM, }, }, @@ -68,6 +68,19 @@ static const struct hantro_fmt stm32mp25_venc_fmts[] = { .codec_mode = HANTRO_MODE_NONE, .enc_fmt = ROCKCHIP_VPU_ENC_FMT_YUV420SP, }, + { + .fourcc = V4L2_PIX_FMT_WEBP_FRAME, + .codec_mode = HANTRO_MODE_VP8_DEC, + .max_depth = 2, + .frmsize = { + .min_width = FMT_MIN_WIDTH, + .max_width = FMT_4K_WIDTH, + .step_width = MB_DIM, + .min_height = FMT_MIN_HEIGHT, + .max_height = FMT_4K_HEIGHT, + .step_height = MB_DIM, + }, + }, { .fourcc = V4L2_PIX_FMT_YUYV, .codec_mode = HANTRO_MODE_NONE,
Add WebP picture decoding support to VP8 stateless decoder. Signed-off-by: Hugues Fruchet <hugues.fruchet@foss.st.com> --- .../media/platform/verisilicon/hantro_g1_regs.h | 1 + .../platform/verisilicon/hantro_g1_vp8_dec.c | 14 ++++++++++++++ .../media/platform/verisilicon/hantro_v4l2.c | 2 ++ .../platform/verisilicon/stm32mp25_vpu_hw.c | 17 +++++++++++++++-- 4 files changed, 32 insertions(+), 2 deletions(-)