diff --git a/driver/vidc/inc/msm_vidc.h b/driver/vidc/inc/msm_vidc.h index f8be2b787e..685e33f5b8 100644 --- a/driver/vidc/inc/msm_vidc.h +++ b/driver/vidc/inc/msm_vidc.h @@ -25,10 +25,8 @@ int msm_vidc_s_selection(void* instance, struct v4l2_selection* s); int msm_vidc_g_selection(void* instance, struct v4l2_selection* s); int msm_vidc_s_param(void *instance, struct v4l2_streamparm *sp); int msm_vidc_g_param(void *instance, struct v4l2_streamparm *sp); -int msm_vidc_s_ctrl(void *instance, struct v4l2_control *a); int msm_vidc_s_ext_ctrl(void *instance, struct v4l2_ext_controls *a); int msm_vidc_g_ext_ctrl(void *instance, struct v4l2_ext_controls *a); -int msm_vidc_g_ctrl(void *instance, struct v4l2_control *a); int msm_vidc_reqbufs(void *instance, struct v4l2_requestbuffers *b); int msm_vidc_release_buffer(void *instance, int buffer_type, unsigned int buffer_index); diff --git a/driver/vidc/inc/msm_vidc_control.h b/driver/vidc/inc/msm_vidc_control.h index 1f6a3ded26..d85577fd10 100644 --- a/driver/vidc/inc/msm_vidc_control.h +++ b/driver/vidc/inc/msm_vidc_control.h @@ -13,6 +13,7 @@ int msm_vidc_ctrl_init(struct msm_vidc_inst *inst); int msm_vidc_ctrl_deinit(struct msm_vidc_inst *inst); int msm_v4l2_op_s_ctrl(struct v4l2_ctrl *ctrl); +int msm_v4l2_op_g_volatile_ctrl(struct v4l2_ctrl *ctrl); int msm_vidc_adjust_bitrate(void *instance, struct v4l2_ctrl *ctrl); int msm_vidc_adjust_dynamic_layer_bitrate(void *instance, struct v4l2_ctrl *ctrl); int msm_vidc_adjust_bitrate_mode(void *instance, struct v4l2_ctrl *ctrl); diff --git a/driver/vidc/inc/msm_vidc_v4l2.h b/driver/vidc/inc/msm_vidc_v4l2.h index d4f387198c..d283adbe07 100644 --- a/driver/vidc/inc/msm_vidc_v4l2.h +++ b/driver/vidc/inc/msm_vidc_v4l2.h @@ -32,10 +32,6 @@ int msm_v4l2_s_parm(struct file *file, void *fh, struct v4l2_streamparm *a); int msm_v4l2_g_parm(struct file *file, void *fh, struct v4l2_streamparm *a); -int msm_v4l2_s_ctrl(struct file *file, void *fh, - struct v4l2_control *a); -int msm_v4l2_g_ctrl(struct file *file, void *fh, - struct v4l2_control *a); int msm_v4l2_reqbufs(struct file *file, void *fh, struct v4l2_requestbuffers *b); int msm_v4l2_qbuf(struct file *file, void *fh, diff --git a/driver/vidc/src/msm_vidc.c b/driver/vidc/src/msm_vidc.c index 55420647b3..1f2a4e2e19 100644 --- a/driver/vidc/src/msm_vidc.c +++ b/driver/vidc/src/msm_vidc.c @@ -375,50 +375,6 @@ int msm_vidc_g_param(void *instance, struct v4l2_streamparm *param) } EXPORT_SYMBOL(msm_vidc_g_param); -int msm_vidc_s_ctrl(void *instance, struct v4l2_control *control) -{ - struct msm_vidc_inst *inst = instance; - - if (!inst || !control) - return -EINVAL; - - if (!msm_vidc_allow_s_ctrl(inst, control->id)) - return -EBUSY; - - return v4l2_s_ctrl(NULL, &inst->ctrl_handler, control); -} -EXPORT_SYMBOL(msm_vidc_s_ctrl); - -int msm_vidc_g_ctrl(void *instance, struct v4l2_control *control) -{ - struct msm_vidc_inst *inst = instance; - struct v4l2_ctrl *ctrl = NULL; - int rc = 0; - - if (!inst || !control) { - d_vpr_e("%s: invalid params\n", __func__); - return -EINVAL; - } - ctrl = v4l2_ctrl_find(&inst->ctrl_handler, control->id); - if (ctrl) { - rc = msm_vidc_get_control(inst, ctrl); - if (!rc) - control->value = ctrl->val; - } else { - i_vpr_e(inst, "%s: invalid control\n", __func__); - return -EINVAL; - } - - if (rc) - i_vpr_e(inst, "%s: failed for control id %#x\n", - __func__, control->id); - else - i_vpr_h(inst, "%s: control id %#x, value %d\n", - __func__, control->id, control->value); - return rc; -} -EXPORT_SYMBOL(msm_vidc_g_ctrl); - int msm_vidc_reqbufs(void *instance, struct v4l2_requestbuffers *b) { int rc = 0; diff --git a/driver/vidc/src/msm_vidc_control.c b/driver/vidc/src/msm_vidc_control.c index 7a6366a5b3..6d6c7e4011 100644 --- a/driver/vidc/src/msm_vidc_control.c +++ b/driver/vidc/src/msm_vidc_control.c @@ -535,6 +535,13 @@ exit: return rc; } +void msm_vidc_add_volatile_flag(struct v4l2_ctrl *ctrl) +{ + if (ctrl->id == V4L2_CID_MIN_BUFFERS_FOR_OUTPUT || + ctrl->id == V4L2_CID_MIN_BUFFERS_FOR_CAPTURE) + ctrl->flags |= V4L2_CTRL_FLAG_VOLATILE; +} + int msm_vidc_ctrl_deinit(struct msm_vidc_inst *inst) { if (!inst) { @@ -690,6 +697,7 @@ int msm_vidc_ctrl_init(struct msm_vidc_inst *inst) * TODO(AS) * ctrl->flags |= capability->cap[idx].flags; */ + msm_vidc_add_volatile_flag(ctrl); ctrl->flags |= V4L2_CTRL_FLAG_EXECUTE_ON_WRITE; inst->ctrls[ctrl_idx] = ctrl; ctrl_idx++; @@ -786,6 +794,34 @@ static int msm_vidc_allow_secure_session(struct msm_vidc_inst *inst) return rc; } +int msm_v4l2_op_g_volatile_ctrl(struct v4l2_ctrl *ctrl) +{ + int rc = 0; + struct msm_vidc_inst *inst; + + if (!ctrl) { + d_vpr_e("%s: invalid ctrl parameter\n", __func__); + return -EINVAL; + } + + inst = container_of(ctrl->handler, + struct msm_vidc_inst, ctrl_handler); + if (!inst) { + d_vpr_e("%s: could not find inst for ctrl %s id %#x\n", __func__, ctrl->name, ctrl->id); + return -EINVAL; + } + + rc = msm_vidc_get_control(inst, ctrl); + if (rc) + i_vpr_e(inst, "%s: failed for ctrl %s id %#x\n", + __func__, ctrl->name, ctrl->id); + else + i_vpr_h(inst, "%s: ctrl %s id %#x, value %d\n", + __func__, ctrl->name, ctrl->id, ctrl->val); + + return rc; +} + int msm_v4l2_op_s_ctrl(struct v4l2_ctrl *ctrl) { int rc = 0; @@ -812,6 +848,12 @@ int msm_v4l2_op_s_ctrl(struct v4l2_ctrl *ctrl) i_vpr_h(inst, "%s: state %d, name %s, id 0x%x value %d\n", __func__, inst->state, ctrl->name, ctrl->id, ctrl->val); + if (!msm_vidc_allow_s_ctrl(inst, ctrl->id)) { + i_vpr_e(inst, "%s: state %d, name %s, id %#x not allowed\n", + __func__, inst->state, ctrl->name, ctrl->id, ctrl->val); + return -EBUSY; + } + cap_id = msm_vidc_get_cap_id(inst, ctrl->id); if (cap_id == INST_CAP_NONE) { i_vpr_e(inst, "%s: could not find cap_id for ctrl %s\n", diff --git a/driver/vidc/src/msm_vidc_driver.c b/driver/vidc/src/msm_vidc_driver.c index 52b454d9a4..3b7d59e425 100644 --- a/driver/vidc/src/msm_vidc_driver.c +++ b/driver/vidc/src/msm_vidc_driver.c @@ -1957,7 +1957,9 @@ int msm_vidc_get_control(struct msm_vidc_inst *inst, struct v4l2_ctrl *ctrl) i_vpr_h(inst, "g_min: input buffers %d\n", ctrl->val); break; default: - break; + i_vpr_e(inst, "invalid ctrl %s id %d\n", + ctrl->name, ctrl->id); + return -EINVAL; } return rc; @@ -3516,6 +3518,7 @@ int msm_vidc_event_queue_init(struct msm_vidc_inst *inst) return -EINVAL; v4l2_fh_init(&inst->event_handler, &core->vdev[index].vdev); + inst->event_handler.ctrl_handler = &inst->ctrl_handler; v4l2_fh_add(&inst->event_handler); return rc; diff --git a/driver/vidc/src/msm_vidc_platform.c b/driver/vidc/src/msm_vidc_platform.c index 1f441e4a0f..c212767100 100644 --- a/driver/vidc/src/msm_vidc_platform.c +++ b/driver/vidc/src/msm_vidc_platform.c @@ -64,8 +64,6 @@ static struct v4l2_ioctl_ops msm_v4l2_ioctl_ops_enc = { .vidioc_dqbuf = msm_v4l2_dqbuf, .vidioc_streamon = msm_v4l2_streamon, .vidioc_streamoff = msm_v4l2_streamoff, - .vidioc_s_ctrl = msm_v4l2_s_ctrl, - .vidioc_g_ctrl = msm_v4l2_g_ctrl, .vidioc_queryctrl = msm_v4l2_queryctrl, .vidioc_querymenu = msm_v4l2_querymenu, .vidioc_subscribe_event = msm_v4l2_subscribe_event, @@ -103,8 +101,6 @@ static struct v4l2_ioctl_ops msm_v4l2_ioctl_ops_dec = { .vidioc_dqbuf = msm_v4l2_dqbuf, .vidioc_streamon = msm_v4l2_streamon, .vidioc_streamoff = msm_v4l2_streamoff, - .vidioc_s_ctrl = msm_v4l2_s_ctrl, - .vidioc_g_ctrl = msm_v4l2_g_ctrl, .vidioc_queryctrl = msm_v4l2_queryctrl, .vidioc_querymenu = msm_v4l2_querymenu, .vidioc_subscribe_event = msm_v4l2_subscribe_event, @@ -115,6 +111,7 @@ static struct v4l2_ioctl_ops msm_v4l2_ioctl_ops_dec = { static struct v4l2_ctrl_ops msm_v4l2_ctrl_ops = { .s_ctrl = msm_v4l2_op_s_ctrl, + .g_volatile_ctrl = msm_v4l2_op_g_volatile_ctrl, }; static struct vb2_ops msm_vb2_ops = { diff --git a/driver/vidc/src/msm_vidc_v4l2.c b/driver/vidc/src/msm_vidc_v4l2.c index 31dfac4c9f..8ba23827f0 100644 --- a/driver/vidc/src/msm_vidc_v4l2.c +++ b/driver/vidc/src/msm_vidc_v4l2.c @@ -45,7 +45,6 @@ int msm_v4l2_open(struct file *filp) trace_msm_v4l2_vidc_open("END", NULL); return -ENOMEM; } - clear_bit(V4L2_FL_USES_V4L2_FH, &vdev->flags); filp->private_data = &(inst->event_handler); trace_msm_v4l2_vidc_open("END", inst); return 0; @@ -300,59 +299,6 @@ unlock: return rc; } -int msm_v4l2_s_ctrl(struct file *filp, void *fh, - struct v4l2_control *a) -{ - struct msm_vidc_inst *inst = get_vidc_inst(filp, fh); - int rc = 0; - - inst = get_inst_ref(g_core, inst); - if (!inst) { - d_vpr_e("%s: invalid instance\n", __func__); - return -EINVAL; - } - - inst_lock(inst, __func__); - if (is_session_error(inst)) { - i_vpr_e(inst, "%s: inst in error state\n", __func__); - rc = -EBUSY; - goto unlock; - } - rc = msm_vidc_s_ctrl((void *)inst, a); - if (rc) - goto unlock; - -unlock: - inst_unlock(inst, __func__); - put_inst(inst); - - return rc; -} - -int msm_v4l2_g_ctrl(struct file *filp, void *fh, - struct v4l2_control *a) -{ - struct msm_vidc_inst *inst = get_vidc_inst(filp, fh); - int rc = 0; - - inst = get_inst_ref(g_core, inst); - if (!inst) { - d_vpr_e("%s: invalid instance\n", __func__); - return -EINVAL; - } - - inst_lock(inst, __func__); - rc = msm_vidc_g_ctrl((void *)inst, a); - if (rc) - goto unlock; - -unlock: - inst_unlock(inst, __func__); - put_inst(inst); - - return rc; -} - int msm_v4l2_reqbufs(struct file *filp, void *fh, struct v4l2_requestbuffers *b) {