media: rockchip/vpu: Add support for non-standard controls
Rework the way controls are registered by the driver, so it can support non-standard controls, such as those used by stateless codecs. Signed-off-by: Ezequiel Garcia <ezequiel@collabora.com> Signed-off-by: Boris Brezillon <boris.brezillon@collabora.com> Signed-off-by: Hans Verkuil <hverkuil-cisco@xs4all.nl> Signed-off-by: Mauro Carvalho Chehab <mchehab+samsung@kernel.org>
This commit is contained in:
parent
8c3dc73d41
commit
6d9a39cffc
|
@ -112,7 +112,7 @@ const struct rockchip_vpu_variant rk3288_vpu_variant = {
|
|||
.enc_fmts = rk3288_vpu_enc_fmts,
|
||||
.num_enc_fmts = ARRAY_SIZE(rk3288_vpu_enc_fmts),
|
||||
.codec_ops = rk3288_vpu_codec_ops,
|
||||
.codec = RK_VPU_CODEC_JPEG,
|
||||
.codec = RK_VPU_JPEG_ENCODER,
|
||||
.vepu_irq = rk3288_vepu_irq,
|
||||
.init = rk3288_vpu_hw_init,
|
||||
.clk_names = {"aclk", "hclk"},
|
||||
|
|
|
@ -111,7 +111,7 @@ const struct rockchip_vpu_variant rk3399_vpu_variant = {
|
|||
.enc_offset = 0x0,
|
||||
.enc_fmts = rk3399_vpu_enc_fmts,
|
||||
.num_enc_fmts = ARRAY_SIZE(rk3399_vpu_enc_fmts),
|
||||
.codec = RK_VPU_CODEC_JPEG,
|
||||
.codec = RK_VPU_JPEG_ENCODER,
|
||||
.codec_ops = rk3399_vpu_codec_ops,
|
||||
.vepu_irq = rk3399_vepu_irq,
|
||||
.init = rk3399_vpu_hw_init,
|
||||
|
|
|
@ -34,7 +34,10 @@
|
|||
struct rockchip_vpu_ctx;
|
||||
struct rockchip_vpu_codec_ops;
|
||||
|
||||
#define RK_VPU_CODEC_JPEG BIT(0)
|
||||
#define RK_VPU_JPEG_ENCODER BIT(0)
|
||||
#define RK_VPU_ENCODERS 0x0000ffff
|
||||
|
||||
#define RK_VPU_DECODERS 0xffff0000
|
||||
|
||||
/**
|
||||
* struct rockchip_vpu_variant - information about VPU hardware variant
|
||||
|
@ -79,6 +82,18 @@ enum rockchip_vpu_codec_mode {
|
|||
RK_VPU_MODE_JPEG_ENC,
|
||||
};
|
||||
|
||||
/*
|
||||
* struct rockchip_vpu_ctrl - helper type to declare supported controls
|
||||
* @id: V4L2 control ID (V4L2_CID_xxx)
|
||||
* @codec: codec id this control belong to (RK_VPU_JPEG_ENCODER, etc.)
|
||||
* @cfg: control configuration
|
||||
*/
|
||||
struct rockchip_vpu_ctrl {
|
||||
unsigned int id;
|
||||
unsigned int codec;
|
||||
struct v4l2_ctrl_config cfg;
|
||||
};
|
||||
|
||||
/*
|
||||
* struct rockchip_vpu_func - rockchip VPU functionality
|
||||
*
|
||||
|
|
|
@ -245,22 +245,51 @@ static const struct v4l2_ctrl_ops rockchip_vpu_ctrl_ops = {
|
|||
.s_ctrl = rockchip_vpu_s_ctrl,
|
||||
};
|
||||
|
||||
static struct rockchip_vpu_ctrl controls[] = {
|
||||
{
|
||||
.id = V4L2_CID_JPEG_COMPRESSION_QUALITY,
|
||||
.codec = RK_VPU_JPEG_ENCODER,
|
||||
.cfg = {
|
||||
.min = 5,
|
||||
.max = 100,
|
||||
.step = 1,
|
||||
.def = 50,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
static int rockchip_vpu_ctrls_setup(struct rockchip_vpu_dev *vpu,
|
||||
struct rockchip_vpu_ctx *ctx)
|
||||
struct rockchip_vpu_ctx *ctx,
|
||||
int allowed_codecs)
|
||||
{
|
||||
v4l2_ctrl_handler_init(&ctx->ctrl_handler, 1);
|
||||
if (vpu->variant->codec & RK_VPU_CODEC_JPEG) {
|
||||
v4l2_ctrl_new_std(&ctx->ctrl_handler, &rockchip_vpu_ctrl_ops,
|
||||
V4L2_CID_JPEG_COMPRESSION_QUALITY,
|
||||
5, 100, 1, 50);
|
||||
int i, num_ctrls = ARRAY_SIZE(controls);
|
||||
|
||||
v4l2_ctrl_handler_init(&ctx->ctrl_handler, num_ctrls);
|
||||
|
||||
for (i = 0; i < num_ctrls; i++) {
|
||||
if (!(allowed_codecs & controls[i].codec))
|
||||
continue;
|
||||
if (!controls[i].cfg.elem_size) {
|
||||
v4l2_ctrl_new_std(&ctx->ctrl_handler,
|
||||
&rockchip_vpu_ctrl_ops,
|
||||
controls[i].id, controls[i].cfg.min,
|
||||
controls[i].cfg.max,
|
||||
controls[i].cfg.step,
|
||||
controls[i].cfg.def);
|
||||
} else {
|
||||
controls[i].cfg.id = controls[i].id;
|
||||
v4l2_ctrl_new_custom(&ctx->ctrl_handler,
|
||||
&controls[i].cfg, NULL);
|
||||
}
|
||||
|
||||
if (ctx->ctrl_handler.error) {
|
||||
vpu_err("Adding JPEG control failed %d\n",
|
||||
vpu_err("Adding control (%d) failed %d\n",
|
||||
controls[i].id,
|
||||
ctx->ctrl_handler.error);
|
||||
v4l2_ctrl_handler_free(&ctx->ctrl_handler);
|
||||
return ctx->ctrl_handler.error;
|
||||
}
|
||||
}
|
||||
|
||||
return v4l2_ctrl_handler_setup(&ctx->ctrl_handler);
|
||||
}
|
||||
|
||||
|
@ -274,7 +303,7 @@ static int rockchip_vpu_open(struct file *filp)
|
|||
struct video_device *vdev = video_devdata(filp);
|
||||
struct rockchip_vpu_func *func = rockchip_vpu_vdev_to_func(vdev);
|
||||
struct rockchip_vpu_ctx *ctx;
|
||||
int ret;
|
||||
int allowed_codecs, ret;
|
||||
|
||||
/*
|
||||
* We do not need any extra locking here, because we operate only
|
||||
|
@ -291,10 +320,12 @@ static int rockchip_vpu_open(struct file *filp)
|
|||
|
||||
ctx->dev = vpu;
|
||||
if (func->id == MEDIA_ENT_F_PROC_VIDEO_ENCODER) {
|
||||
allowed_codecs = vpu->variant->codec & RK_VPU_ENCODERS;
|
||||
ctx->buf_finish = rockchip_vpu_enc_buf_finish;
|
||||
ctx->fh.m2m_ctx = v4l2_m2m_ctx_init(vpu->m2m_dev, ctx,
|
||||
queue_init);
|
||||
} else if (func->id == MEDIA_ENT_F_PROC_VIDEO_DECODER) {
|
||||
allowed_codecs = vpu->variant->codec & RK_VPU_DECODERS;
|
||||
ctx->buf_finish = rockchip_vpu_dec_buf_finish;
|
||||
ctx->fh.m2m_ctx = v4l2_m2m_ctx_init(vpu->m2m_dev, ctx,
|
||||
queue_init);
|
||||
|
@ -313,7 +344,7 @@ static int rockchip_vpu_open(struct file *filp)
|
|||
|
||||
rockchip_vpu_reset_fmts(ctx);
|
||||
|
||||
ret = rockchip_vpu_ctrls_setup(vpu, ctx);
|
||||
ret = rockchip_vpu_ctrls_setup(vpu, ctx, allowed_codecs);
|
||||
if (ret) {
|
||||
vpu_err("Failed to set up controls\n");
|
||||
goto err_fh_free;
|
||||
|
|
Loading…
Reference in New Issue