media: i2c: gc4663 support get channel info by ioctl

Signed-off-by: Zefa Chen <zefa.chen@rock-chips.com>
Change-Id: Ifa2c09a1037d904a5a2e830f89d638e97c9287e8
This commit is contained in:
Zefa Chen 2021-09-17 09:10:51 +08:00
commit 1b8544199b

View file

@ -773,11 +773,6 @@ static int gc4663_get_fmt(struct v4l2_subdev *sd,
fmt->format.height = mode->height;
fmt->format.code = mode->bus_fmt;
fmt->format.field = V4L2_FIELD_NONE;
/* format info: width/height/data type/virctual channel */
if (fmt->pad < PAD_MAX && mode->hdr_mode != NO_HDR)
fmt->reserved[0] = mode->vc[fmt->pad];
else
fmt->reserved[0] = mode->vc[PAD0];
}
mutex_unlock(&gc4663->mutex);
@ -1044,6 +1039,17 @@ static void gc4663_get_module_inf(struct gc4663 *gc4663,
strlcpy(inf->base.lens, gc4663->len_name, sizeof(inf->base.lens));
}
static int gc4663_get_channel_info(struct gc4663 *gc4663, struct rkmodule_channel_info *ch_info)
{
if (ch_info->index < PAD0 || ch_info->index >= PAD_MAX)
return -EINVAL;
ch_info->vc = gc4663->cur_mode->vc[ch_info->index];
ch_info->width = gc4663->cur_mode->width;
ch_info->height = gc4663->cur_mode->height;
ch_info->bus_fmt = gc4663->cur_mode->bus_fmt;
return 0;
}
static long gc4663_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg)
{
struct gc4663 *gc4663 = to_gc4663(sd);
@ -1051,6 +1057,7 @@ static long gc4663_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg)
u32 i, h, w;
long ret = 0;
u32 stream = 0;
struct rkmodule_channel_info *ch_info;
switch (cmd) {
case RKMODULE_GET_MODULE_INFO:
@ -1115,6 +1122,10 @@ static long gc4663_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg)
ret = gc4663_write_reg(gc4663->client, GC4663_REG_CTRL_MODE,
GC4663_REG_VALUE_08BIT, GC4663_MODE_SW_STANDBY);
break;
case RKMODULE_GET_CHANNEL_INFO:
ch_info = (struct rkmodule_channel_info *)arg;
ret = gc4663_get_channel_info(gc4663, ch_info);
break;
default:
ret = -ENOIOCTLCMD;
break;
@ -1134,6 +1145,7 @@ static long gc4663_compat_ioctl32(struct v4l2_subdev *sd,
struct preisp_hdrae_exp_s *hdrae;
long ret;
u32 stream = 0;
struct rkmodule_channel_info *ch_info;
switch (cmd) {
case RKMODULE_GET_MODULE_INFO:
@ -1144,8 +1156,11 @@ static long gc4663_compat_ioctl32(struct v4l2_subdev *sd,
}
ret = gc4663_ioctl(sd, cmd, inf);
if (!ret)
if (!ret) {
ret = copy_to_user(up, inf, sizeof(*inf));
if (ret)
ret = -EFAULT;
}
kfree(inf);
break;
case RKMODULE_AWB_CFG:
@ -1158,6 +1173,8 @@ static long gc4663_compat_ioctl32(struct v4l2_subdev *sd,
ret = copy_from_user(cfg, up, sizeof(*cfg));
if (!ret)
ret = gc4663_ioctl(sd, cmd, cfg);
else
ret = -EFAULT;
kfree(cfg);
break;
case RKMODULE_GET_HDR_CFG:
@ -1168,8 +1185,11 @@ static long gc4663_compat_ioctl32(struct v4l2_subdev *sd,
}
ret = gc4663_ioctl(sd, cmd, hdr);
if (!ret)
if (!ret) {
ret = copy_to_user(up, hdr, sizeof(*hdr));
if (ret)
ret = -EFAULT;
}
kfree(hdr);
break;
case RKMODULE_SET_HDR_CFG:
@ -1182,6 +1202,8 @@ static long gc4663_compat_ioctl32(struct v4l2_subdev *sd,
ret = copy_from_user(hdr, up, sizeof(*hdr));
if (!ret)
ret = gc4663_ioctl(sd, cmd, hdr);
else
ret = -EFAULT;
kfree(hdr);
break;
case PREISP_CMD_SET_HDRAE_EXP:
@ -1194,12 +1216,31 @@ static long gc4663_compat_ioctl32(struct v4l2_subdev *sd,
ret = copy_from_user(hdrae, up, sizeof(*hdrae));
if (!ret)
ret = gc4663_ioctl(sd, cmd, hdrae);
else
ret = -EFAULT;
kfree(hdrae);
break;
case RKMODULE_SET_QUICK_STREAM:
ret = copy_from_user(&stream, up, sizeof(u32));
if (!ret)
ret = gc4663_ioctl(sd, cmd, &stream);
else
ret = -EFAULT;
break;
case RKMODULE_GET_CHANNEL_INFO:
ch_info = kzalloc(sizeof(*ch_info), GFP_KERNEL);
if (!ch_info) {
ret = -ENOMEM;
return ret;
}
ret = gc4663_ioctl(sd, cmd, ch_info);
if (!ret) {
ret = copy_to_user(up, ch_info, sizeof(*ch_info));
if (ret)
ret = -EFAULT;
}
kfree(ch_info);
break;
default:
ret = -ENOIOCTLCMD;