0001
0002
0003
0004
0005
0006
0007
0008 #include <media/v4l2-ctrls.h>
0009 #include <media/v4l2-event.h>
0010 #include <media/v4l2-subdev.h>
0011
0012 #include "vimc-common.h"
0013
0014 #define VIMC_LENS_MAX_FOCUS_POS 1023
0015 #define VIMC_LENS_MAX_FOCUS_STEP 1
0016
0017 struct vimc_lens_device {
0018 struct vimc_ent_device ved;
0019 struct v4l2_subdev sd;
0020 struct v4l2_ctrl_handler hdl;
0021 u32 focus_absolute;
0022 };
0023
0024 static const struct v4l2_subdev_core_ops vimc_lens_core_ops = {
0025 .log_status = v4l2_ctrl_subdev_log_status,
0026 .subscribe_event = v4l2_ctrl_subdev_subscribe_event,
0027 .unsubscribe_event = v4l2_event_subdev_unsubscribe,
0028 };
0029
0030 static const struct v4l2_subdev_ops vimc_lens_ops = {
0031 .core = &vimc_lens_core_ops
0032 };
0033
0034 static int vimc_lens_s_ctrl(struct v4l2_ctrl *ctrl)
0035 {
0036 struct vimc_lens_device *vlens =
0037 container_of(ctrl->handler, struct vimc_lens_device, hdl);
0038 if (ctrl->id == V4L2_CID_FOCUS_ABSOLUTE) {
0039 vlens->focus_absolute = ctrl->val;
0040 return 0;
0041 }
0042 return -EINVAL;
0043 }
0044
0045 static const struct v4l2_ctrl_ops vimc_lens_ctrl_ops = {
0046 .s_ctrl = vimc_lens_s_ctrl,
0047 };
0048
0049 static struct vimc_ent_device *vimc_lens_add(struct vimc_device *vimc,
0050 const char *vcfg_name)
0051 {
0052 struct v4l2_device *v4l2_dev = &vimc->v4l2_dev;
0053 struct vimc_lens_device *vlens;
0054 int ret;
0055
0056
0057 vlens = kzalloc(sizeof(*vlens), GFP_KERNEL);
0058 if (!vlens)
0059 return ERR_PTR(-ENOMEM);
0060
0061 v4l2_ctrl_handler_init(&vlens->hdl, 1);
0062
0063 v4l2_ctrl_new_std(&vlens->hdl, &vimc_lens_ctrl_ops,
0064 V4L2_CID_FOCUS_ABSOLUTE, 0,
0065 VIMC_LENS_MAX_FOCUS_POS, VIMC_LENS_MAX_FOCUS_STEP, 0);
0066 vlens->sd.ctrl_handler = &vlens->hdl;
0067 if (vlens->hdl.error) {
0068 ret = vlens->hdl.error;
0069 goto err_free_vlens;
0070 }
0071 vlens->ved.dev = vimc->mdev.dev;
0072
0073 ret = vimc_ent_sd_register(&vlens->ved, &vlens->sd, v4l2_dev,
0074 vcfg_name, MEDIA_ENT_F_LENS, 0,
0075 NULL, &vimc_lens_ops);
0076 if (ret)
0077 goto err_free_hdl;
0078
0079 return &vlens->ved;
0080
0081 err_free_hdl:
0082 v4l2_ctrl_handler_free(&vlens->hdl);
0083 err_free_vlens:
0084 kfree(vlens);
0085
0086 return ERR_PTR(ret);
0087 }
0088
0089 static void vimc_lens_release(struct vimc_ent_device *ved)
0090 {
0091 struct vimc_lens_device *vlens =
0092 container_of(ved, struct vimc_lens_device, ved);
0093
0094 v4l2_ctrl_handler_free(&vlens->hdl);
0095 media_entity_cleanup(vlens->ved.ent);
0096 kfree(vlens);
0097 }
0098
0099 struct vimc_ent_type vimc_lens_type = {
0100 .add = vimc_lens_add,
0101 .release = vimc_lens_release
0102 };