Lines Matching +full:conversion +full:- +full:start +full:- +full:gpios

1 // SPDX-License-Identifier: GPL-2.0
8 * V0.0X01.0X01 add conversion gain control
9 * V0.0X01.0X02 add debug interface for conversion gain control
24 #include <linux/rk-camera-module.h>
25 #include <media/media-entity.h>
26 #include <media/v4l2-async.h>
27 #include <media/v4l2-ctrls.h>
28 #include <media/v4l2-subdev.h>
29 #include <media/v4l2-fwnode.h>
30 #include <media/v4l2-mediabus.h>
32 #include <linux/rk-preisp.h>
45 #define OF_CAMERA_HDR_MODE "rockchip,camera-hdr-mode"
142 #define RHS1_MAX ((BRL * 2 - 1) / 4 * 4 + 1) // <3*BRL=2*1558 && 6n+1
146 #define RHS1_MAX_X3 ((BRL * 3 - 1) / 6 * 6 + 1)
1387 .vc[PAD1] = V4L2_MBUS_CSI2_CHANNEL_0,//L->csi wr0
1389 .vc[PAD3] = V4L2_MBUS_CSI2_CHANNEL_1,//M->csi wr2
1416 .vc[PAD1] = V4L2_MBUS_CSI2_CHANNEL_1,//M->csi wr0
1417 .vc[PAD2] = V4L2_MBUS_CSI2_CHANNEL_0,//L->csi wr1
1418 .vc[PAD3] = V4L2_MBUS_CSI2_CHANNEL_2,//S->csi wr2
1458 .vc[PAD1] = V4L2_MBUS_CSI2_CHANNEL_0,//L->csi wr0
1460 .vc[PAD3] = V4L2_MBUS_CSI2_CHANNEL_1,//M->csi wr2
1479 return -EINVAL; in imx464_write_reg()
1487 val_i = 4 - len; in imx464_write_reg()
1493 return -EIO; in imx464_write_reg()
1522 return -EINVAL; in IMX464_read_reg()
1526 msgs[0].addr = client->addr; in IMX464_read_reg()
1532 msgs[1].addr = client->addr; in IMX464_read_reg()
1535 msgs[1].buf = &data_be_p[4 - len]; in IMX464_read_reg()
1537 ret = i2c_transfer(client->adapter, msgs, ARRAY_SIZE(msgs)); in IMX464_read_reg()
1539 return -EIO; in IMX464_read_reg()
1549 return abs(mode->width - framefmt->width) + in IMX464_get_reso_dist()
1550 abs(mode->height - framefmt->height); in IMX464_get_reso_dist()
1556 struct v4l2_mbus_framefmt *framefmt = &fmt->format; in IMX464_find_best_fit()
1559 int cur_best_fit_dist = -1; in IMX464_find_best_fit()
1562 for (i = 0; i < IMX464->cfg_num; i++) { in IMX464_find_best_fit()
1563 dist = IMX464_get_reso_dist(&IMX464->support_modes[i], framefmt); in IMX464_find_best_fit()
1564 if ((cur_best_fit_dist == -1 || dist <= cur_best_fit_dist) && in IMX464_find_best_fit()
1565 IMX464->support_modes[i].bus_fmt == framefmt->code) { in IMX464_find_best_fit()
1571 return &IMX464->support_modes[cur_best_fit]; in IMX464_find_best_fit()
1583 mutex_lock(&IMX464->mutex); in IMX464_set_fmt()
1586 fmt->format.code = mode->bus_fmt; in IMX464_set_fmt()
1587 fmt->format.width = mode->width; in IMX464_set_fmt()
1588 fmt->format.height = mode->height; in IMX464_set_fmt()
1589 fmt->format.field = V4L2_FIELD_NONE; in IMX464_set_fmt()
1590 if (fmt->which == V4L2_SUBDEV_FORMAT_TRY) { in IMX464_set_fmt()
1592 *v4l2_subdev_get_try_format(sd, cfg, fmt->pad) = fmt->format; in IMX464_set_fmt()
1594 mutex_unlock(&IMX464->mutex); in IMX464_set_fmt()
1595 return -ENOTTY; in IMX464_set_fmt()
1598 IMX464->cur_mode = mode; in IMX464_set_fmt()
1599 h_blank = mode->hts_def - mode->width; in IMX464_set_fmt()
1600 __v4l2_ctrl_modify_range(IMX464->hblank, h_blank, in IMX464_set_fmt()
1602 vblank_def = mode->vts_def - mode->height; in IMX464_set_fmt()
1603 __v4l2_ctrl_modify_range(IMX464->vblank, vblank_def, in IMX464_set_fmt()
1604 IMX464_VTS_MAX - mode->height, in IMX464_set_fmt()
1606 IMX464->cur_vts = IMX464->cur_mode->vts_def; in IMX464_set_fmt()
1607 pixel_rate = (u32)link_freq_menu_items[mode->mipi_freq_idx] / mode->bpp * 2 * in IMX464_set_fmt()
1608 IMX464->bus_cfg.bus.mipi_csi2.num_data_lanes; in IMX464_set_fmt()
1609 __v4l2_ctrl_s_ctrl_int64(IMX464->pixel_rate, in IMX464_set_fmt()
1611 __v4l2_ctrl_s_ctrl(IMX464->link_freq, in IMX464_set_fmt()
1612 mode->mipi_freq_idx); in IMX464_set_fmt()
1615 mutex_unlock(&IMX464->mutex); in IMX464_set_fmt()
1625 const struct IMX464_mode *mode = IMX464->cur_mode; in IMX464_get_fmt()
1627 mutex_lock(&IMX464->mutex); in IMX464_get_fmt()
1628 if (fmt->which == V4L2_SUBDEV_FORMAT_TRY) { in IMX464_get_fmt()
1630 fmt->format = *v4l2_subdev_get_try_format(sd, cfg, fmt->pad); in IMX464_get_fmt()
1632 mutex_unlock(&IMX464->mutex); in IMX464_get_fmt()
1633 return -ENOTTY; in IMX464_get_fmt()
1636 fmt->format.width = mode->width; in IMX464_get_fmt()
1637 fmt->format.height = mode->height; in IMX464_get_fmt()
1638 fmt->format.code = mode->bus_fmt; in IMX464_get_fmt()
1639 fmt->format.field = V4L2_FIELD_NONE; in IMX464_get_fmt()
1640 if (fmt->pad < PAD_MAX && mode->hdr_mode != NO_HDR) in IMX464_get_fmt()
1641 fmt->reserved[0] = mode->vc[fmt->pad]; in IMX464_get_fmt()
1643 fmt->reserved[0] = mode->vc[PAD0]; in IMX464_get_fmt()
1645 mutex_unlock(&IMX464->mutex); in IMX464_get_fmt()
1656 if (code->index != 0) in IMX464_enum_mbus_code()
1657 return -EINVAL; in IMX464_enum_mbus_code()
1658 code->code = IMX464->cur_mode->bus_fmt; in IMX464_enum_mbus_code()
1669 if (fse->index >= IMX464->cfg_num) in IMX464_enum_frame_sizes()
1670 return -EINVAL; in IMX464_enum_frame_sizes()
1672 if (fse->code != IMX464->support_modes[fse->index].bus_fmt) in IMX464_enum_frame_sizes()
1673 return -EINVAL; in IMX464_enum_frame_sizes()
1675 fse->min_width = IMX464->support_modes[fse->index].width; in IMX464_enum_frame_sizes()
1676 fse->max_width = IMX464->support_modes[fse->index].width; in IMX464_enum_frame_sizes()
1677 fse->max_height = IMX464->support_modes[fse->index].height; in IMX464_enum_frame_sizes()
1678 fse->min_height = IMX464->support_modes[fse->index].height; in IMX464_enum_frame_sizes()
1687 const struct IMX464_mode *mode = IMX464->cur_mode; in IMX464_g_frame_interval()
1689 fi->interval = mode->max_fps; in IMX464_g_frame_interval()
1698 const struct IMX464_mode *mode = IMX464->cur_mode; in IMX464_g_mbus_config()
1700 u32 lane_num = IMX464->bus_cfg.bus.mipi_csi2.num_data_lanes; in IMX464_g_mbus_config()
1702 if (mode->hdr_mode == NO_HDR) { in IMX464_g_mbus_config()
1703 val = 1 << (lane_num - 1) | in IMX464_g_mbus_config()
1707 if (mode->hdr_mode == HDR_X2) in IMX464_g_mbus_config()
1708 val = 1 << (lane_num - 1) | in IMX464_g_mbus_config()
1712 if (mode->hdr_mode == HDR_X3) in IMX464_g_mbus_config()
1713 val = 1 << (lane_num - 1) | in IMX464_g_mbus_config()
1719 config->type = V4L2_MBUS_CSI2_DPHY; in IMX464_g_mbus_config()
1720 config->flags = val; in IMX464_g_mbus_config()
1729 strscpy(inf->base.sensor, IMX464_NAME, sizeof(inf->base.sensor)); in IMX464_get_module_inf()
1730 strscpy(inf->base.module, IMX464->module_name, in IMX464_get_module_inf()
1731 sizeof(inf->base.module)); in IMX464_get_module_inf()
1732 strscpy(inf->base.lens, IMX464->len_name, sizeof(inf->base.lens)); in IMX464_get_module_inf()
1738 struct i2c_client *client = IMX464->client; in IMX464_set_hdrae()
1749 u32 fsc = IMX464->cur_vts; in IMX464_set_hdrae()
1752 if (!IMX464->has_init_exp && !IMX464->streaming) { in IMX464_set_hdrae()
1753 IMX464->init_hdrae_exp = *ae; in IMX464_set_hdrae()
1754 IMX464->has_init_exp = true; in IMX464_set_hdrae()
1755 dev_dbg(&IMX464->client->dev, "IMX464 don't stream, record exp for hdr!\n"); in IMX464_set_hdrae()
1758 l_exp_time = ae->long_exp_reg; in IMX464_set_hdrae()
1759 m_exp_time = ae->middle_exp_reg; in IMX464_set_hdrae()
1760 s_exp_time = ae->short_exp_reg; in IMX464_set_hdrae()
1761 l_a_gain = ae->long_gain_reg; in IMX464_set_hdrae()
1762 m_a_gain = ae->middle_gain_reg; in IMX464_set_hdrae()
1763 s_a_gain = ae->short_gain_reg; in IMX464_set_hdrae()
1764 dev_dbg(&client->dev, in IMX464_set_hdrae()
1769 if (IMX464->cur_mode->hdr_mode == HDR_X2) { in IMX464_set_hdrae()
1773 cg_mode = ae->middle_cg_mode; in IMX464_set_hdrae()
1775 if (!IMX464->isHCG && cg_mode == GAIN_MODE_HCG) { in IMX464_set_hdrae()
1777 IMX464->isHCG = true; in IMX464_set_hdrae()
1778 } else if (IMX464->isHCG && cg_mode == GAIN_MODE_LCG) { in IMX464_set_hdrae()
1780 IMX464->isHCG = false; in IMX464_set_hdrae()
1810 * SHR1 + 9 <= SHR0 <= (FSC - 2) in IMX464_set_hdrae()
1812 * exp_l = FSC - SHR0 in IMX464_set_hdrae()
1813 * SHR0 = FSC - exp_l (2n, align with 2) in IMX464_set_hdrae()
1815 * exp_s = RHS1 - SHR1 in IMX464_set_hdrae()
1817 * SHR1 + 2 <= RHS1 <= SHR0 - 9 in IMX464_set_hdrae()
1818 * 9 <= SHR1 <= RHS1 - 2 (2n + 1) in IMX464_set_hdrae()
1820 * RHS1(n+1) >= (RHS1(n) + BRL * 2) - FSC + 2 in IMX464_set_hdrae()
1824 * T(l_exp) = FSC - SHR0, unit: H in IMX464_set_hdrae()
1825 * T(s_exp) = RHS1 - SHR1, unit: H in IMX464_set_hdrae()
1829 /* The HDR mode vts is already double by default to workaround T-line */ in IMX464_set_hdrae()
1832 shr0 = fsc - l_exp_time; in IMX464_set_hdrae()
1833 rhs1_max = (RHS1_MAX > (shr0 - 9)) ? (shr0 - 9) : RHS1_MAX; in IMX464_set_hdrae()
1835 dev_err(&client->dev, "line(%d) rhs1 %d\n", __LINE__, rhs1); in IMX464_set_hdrae()
1840 dev_dbg(&client->dev, "line(%d) rhs1 %d\n", __LINE__, rhs1); in IMX464_set_hdrae()
1843 rhs1_change_limit = rhs1_old + 2 * BRL - fsc + 2; in IMX464_set_hdrae()
1846 dev_err(&client->dev, in IMX464_set_hdrae()
1852 dev_dbg(&client->dev, in IMX464_set_hdrae()
1855 (rhs1_old + 2 * BRL - fsc + 2)); in IMX464_set_hdrae()
1860 if (rhs1 - s_exp_time <= SHR1_MIN) { in IMX464_set_hdrae()
1862 s_exp_time = rhs1 - shr1; in IMX464_set_hdrae()
1864 shr1 = rhs1 - s_exp_time; in IMX464_set_hdrae()
1869 else if (shr1 > (rhs1 - 2)) in IMX464_set_hdrae()
1870 shr1 = rhs1 - 2; in IMX464_set_hdrae()
1874 else if (shr0 > (fsc - 2)) in IMX464_set_hdrae()
1875 shr0 = fsc - 2; in IMX464_set_hdrae()
1877 dev_dbg(&client->dev, in IMX464_set_hdrae()
1880 dev_dbg(&client->dev, in IMX464_set_hdrae()
1931 struct i2c_client *client = IMX464->client; in IMX464_set_hdrae_3frame()
1945 if (!IMX464->has_init_exp && !IMX464->streaming) { in IMX464_set_hdrae_3frame()
1946 IMX464->init_hdrae_exp = *ae; in IMX464_set_hdrae_3frame()
1947 IMX464->has_init_exp = true; in IMX464_set_hdrae_3frame()
1948 dev_dbg(&IMX464->client->dev, "IMX464 is not streaming, save hdr ae!\n"); in IMX464_set_hdrae_3frame()
1951 l_exp_time = ae->long_exp_reg; in IMX464_set_hdrae_3frame()
1952 m_exp_time = ae->middle_exp_reg; in IMX464_set_hdrae_3frame()
1953 s_exp_time = ae->short_exp_reg; in IMX464_set_hdrae_3frame()
1954 l_a_gain = ae->long_gain_reg; in IMX464_set_hdrae_3frame()
1955 m_a_gain = ae->middle_gain_reg; in IMX464_set_hdrae_3frame()
1956 s_a_gain = ae->short_gain_reg; in IMX464_set_hdrae_3frame()
1958 if (IMX464->cur_mode->hdr_mode == HDR_X3) { in IMX464_set_hdrae_3frame()
1960 cg_mode = ae->long_cg_mode; in IMX464_set_hdrae_3frame()
1962 if (!IMX464->isHCG && cg_mode == GAIN_MODE_HCG) { in IMX464_set_hdrae_3frame()
1964 IMX464->isHCG = true; in IMX464_set_hdrae_3frame()
1965 } else if (IMX464->isHCG && cg_mode == GAIN_MODE_LCG) { in IMX464_set_hdrae_3frame()
1967 IMX464->isHCG = false; in IMX464_set_hdrae_3frame()
1970 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
1997 * exp_l = FSC - SHR0 + Toffset; in IMX464_set_hdrae_3frame()
1999 * SHR0 = FSC - exp_l + Toffset; in IMX464_set_hdrae_3frame()
2000 * SHR0 <= (FSC -3); in IMX464_set_hdrae_3frame()
2004 * exp_m = RHS1 - SHR1 + Toffset; in IMX464_set_hdrae_3frame()
2007 * RHS1 <= SHR2 - 13; in IMX464_set_hdrae_3frame()
2010 * SHR1 <= RHS1 - 3; in IMX464_set_hdrae_3frame()
2011 * RHS1(n+1) >= RHS1(n) + BRL * 3 -FSC + 3; in IMX464_set_hdrae_3frame()
2015 * exp_s = RHS2 - SHR2 + Toffset; in IMX464_set_hdrae_3frame()
2018 * RHS2 <= SHR0 - 13; in IMX464_set_hdrae_3frame()
2021 * SHR2 <= RHS2 - 3; in IMX464_set_hdrae_3frame()
2022 * RHS1(n+1) >= RHS1(n) + BRL * 3 -FSC + 3; in IMX464_set_hdrae_3frame()
2027 /* The HDR mode vts is double by default to workaround T-line */ in IMX464_set_hdrae_3frame()
2028 fsc = IMX464->cur_vts; in IMX464_set_hdrae_3frame()
2029 shr0 = fsc - l_exp_time; in IMX464_set_hdrae_3frame()
2030 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
2041 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
2047 rhs1_change_limit = rhs1_old + 3 * BRL - fsc + 3; in IMX464_set_hdrae_3frame()
2051 dev_err(&client->dev, in IMX464_set_hdrae_3frame()
2054 return -EINVAL; in IMX464_set_hdrae_3frame()
2059 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
2065 /* shr1 = rhs1 - s_exp_time */ in IMX464_set_hdrae_3frame()
2066 if (rhs1 - m_exp_time <= SHR1_MIN_X3) { in IMX464_set_hdrae_3frame()
2068 m_exp_time = rhs1 - shr1; in IMX464_set_hdrae_3frame()
2070 shr1 = rhs1 - m_exp_time; in IMX464_set_hdrae_3frame()
2075 if (rhs2 > (shr0 - 13)) in IMX464_set_hdrae_3frame()
2076 rhs2 = shr0 - 13; in IMX464_set_hdrae_3frame()
2080 dev_err(&client->dev, in IMX464_set_hdrae_3frame()
2086 rhs2_change_limit = rhs2_old + 3 * BRL - fsc + 3; in IMX464_set_hdrae_3frame()
2089 if ((shr0 - 13) < rhs2_change_limit) { in IMX464_set_hdrae_3frame()
2090 dev_err(&client->dev, in IMX464_set_hdrae_3frame()
2092 shr0 - 13, rhs2_change_limit); in IMX464_set_hdrae_3frame()
2093 return -EINVAL; in IMX464_set_hdrae_3frame()
2100 /* shr2 = rhs2 - s_exp_time */ in IMX464_set_hdrae_3frame()
2101 if (rhs2 - s_exp_time <= shr2_min) { in IMX464_set_hdrae_3frame()
2103 s_exp_time = rhs2 - shr2; in IMX464_set_hdrae_3frame()
2105 shr2 = rhs2 - s_exp_time; in IMX464_set_hdrae_3frame()
2107 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
2113 else if (shr0 > fsc - 3) in IMX464_set_hdrae_3frame()
2114 shr0 = fsc - 3; in IMX464_set_hdrae_3frame()
2116 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
2119 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
2122 dev_dbg(&client->dev, in IMX464_set_hdrae_3frame()
2200 struct i2c_client *client = IMX464->client; in IMX464_set_conversion_gain()
2204 if (IMX464->isHCG && cur_cg == GAIN_MODE_LCG) { in IMX464_set_conversion_gain()
2206 IMX464->isHCG = false; in IMX464_set_conversion_gain()
2207 } else if (!IMX464->isHCG && cur_cg == GAIN_MODE_HCG) { in IMX464_set_conversion_gain()
2209 IMX464->isHCG = true; in IMX464_set_conversion_gain()
2228 //ag: echo 0 > /sys/devices/platform/ff510000.i2c/i2c-1/1-0037/cam_s_cg
2261 for (i--; i >= 0 ; i--) in add_sysfs_interfaces()
2264 return -ENODEV; in add_sysfs_interfaces()
2279 if (ch_info->index < PAD0 || ch_info->index >= PAD_MAX) in IMX464_get_channel_info()
2280 return -EINVAL; in IMX464_get_channel_info()
2281 ch_info->vc = IMX464->cur_mode->vc[ch_info->index]; in IMX464_get_channel_info()
2282 ch_info->width = IMX464->cur_mode->width; in IMX464_get_channel_info()
2283 ch_info->height = IMX464->cur_mode->height; in IMX464_get_channel_info()
2284 ch_info->bus_fmt = IMX464->cur_mode->bus_fmt; in IMX464_get_channel_info()
2300 if (IMX464->cur_mode->hdr_mode == HDR_X2) in IMX464_ioctl()
2302 else if (IMX464->cur_mode->hdr_mode == HDR_X3) in IMX464_ioctl()
2310 hdr->esp.mode = HDR_NORMAL_VC; in IMX464_ioctl()
2311 hdr->hdr_mode = IMX464->cur_mode->hdr_mode; in IMX464_ioctl()
2315 w = IMX464->cur_mode->width; in IMX464_ioctl()
2316 h = IMX464->cur_mode->height; in IMX464_ioctl()
2317 for (i = 0; i < IMX464->cfg_num; i++) { in IMX464_ioctl()
2318 if (w == IMX464->support_modes[i].width && in IMX464_ioctl()
2319 h == IMX464->support_modes[i].height && in IMX464_ioctl()
2320 IMX464->support_modes[i].hdr_mode == hdr->hdr_mode) { in IMX464_ioctl()
2321 IMX464->cur_mode = &IMX464->support_modes[i]; in IMX464_ioctl()
2325 if (i == IMX464->cfg_num) { in IMX464_ioctl()
2326 dev_err(&IMX464->client->dev, in IMX464_ioctl()
2328 hdr->hdr_mode, w, h); in IMX464_ioctl()
2329 ret = -EINVAL; in IMX464_ioctl()
2331 w = IMX464->cur_mode->hts_def - IMX464->cur_mode->width; in IMX464_ioctl()
2332 h = IMX464->cur_mode->vts_def - IMX464->cur_mode->height; in IMX464_ioctl()
2333 __v4l2_ctrl_modify_range(IMX464->hblank, w, w, 1, w); in IMX464_ioctl()
2334 __v4l2_ctrl_modify_range(IMX464->vblank, h, in IMX464_ioctl()
2335 IMX464_VTS_MAX - IMX464->cur_mode->height, in IMX464_ioctl()
2337 IMX464->cur_vts = IMX464->cur_mode->vts_def; in IMX464_ioctl()
2338 …pixel_rate = (u32)link_freq_menu_items[IMX464->cur_mode->mipi_freq_idx] / IMX464->cur_mode->bpp * … in IMX464_ioctl()
2339 IMX464->bus_cfg.bus.mipi_csi2.num_data_lanes; in IMX464_ioctl()
2340 __v4l2_ctrl_s_ctrl_int64(IMX464->pixel_rate, in IMX464_ioctl()
2342 __v4l2_ctrl_s_ctrl(IMX464->link_freq, in IMX464_ioctl()
2343 IMX464->cur_mode->mipi_freq_idx); in IMX464_ioctl()
2354 ret = imx464_write_reg(IMX464->client, IMX464_REG_CTRL_MODE, in IMX464_ioctl()
2357 ret = imx464_write_reg(IMX464->client, IMX464_REG_CTRL_MODE, in IMX464_ioctl()
2367 *sync_mode = IMX464->sync_mode; in IMX464_ioctl()
2371 IMX464->sync_mode = *sync_mode; in IMX464_ioctl()
2374 ret = -ENOIOCTLCMD; in IMX464_ioctl()
2400 ret = -ENOMEM; in IMX464_compat_ioctl32()
2408 ret = -EFAULT; in IMX464_compat_ioctl32()
2415 ret = -ENOMEM; in IMX464_compat_ioctl32()
2423 ret = -EFAULT; in IMX464_compat_ioctl32()
2429 ret = -ENOMEM; in IMX464_compat_ioctl32()
2437 ret = -EFAULT; in IMX464_compat_ioctl32()
2444 ret = -ENOMEM; in IMX464_compat_ioctl32()
2452 ret = -EFAULT; in IMX464_compat_ioctl32()
2458 ret = -ENOMEM; in IMX464_compat_ioctl32()
2466 ret = -EFAULT; in IMX464_compat_ioctl32()
2474 ret = -EFAULT; in IMX464_compat_ioctl32()
2481 ret = -EFAULT; in IMX464_compat_ioctl32()
2487 ret = -ENOMEM; in IMX464_compat_ioctl32()
2495 ret = -EFAULT; in IMX464_compat_ioctl32()
2504 ret = -EFAULT; in IMX464_compat_ioctl32()
2512 ret = -EFAULT; in IMX464_compat_ioctl32()
2515 ret = -ENOIOCTLCMD; in IMX464_compat_ioctl32()
2525 struct i2c_client *client = IMX464->client; in IMX464_init_conversion_gain()
2544 ret = IMX464_write_array(IMX464->client, IMX464->cur_mode->reg_list); in __IMX464_start_stream()
2547 ret = IMX464_init_conversion_gain(IMX464, IMX464->isHCG); in __IMX464_start_stream()
2551 ret = __v4l2_ctrl_handler_setup(&IMX464->ctrl_handler); in __IMX464_start_stream()
2554 if (IMX464->has_init_exp && IMX464->cur_mode->hdr_mode != NO_HDR) { in __IMX464_start_stream()
2555 ret = IMX464_ioctl(&IMX464->subdev, PREISP_CMD_SET_HDRAE_EXP, in __IMX464_start_stream()
2556 &IMX464->init_hdrae_exp); in __IMX464_start_stream()
2558 dev_err(&IMX464->client->dev, in __IMX464_start_stream()
2564 if (IMX464->sync_mode == EXTERNAL_MASTER_MODE) { in __IMX464_start_stream()
2565 ret |= IMX464_write_array(IMX464->client, IMX464_external_sync_master_start_regs); in __IMX464_start_stream()
2566 v4l2_err(&IMX464->subdev, "cur externam master mode\n"); in __IMX464_start_stream()
2567 } else if (IMX464->sync_mode == INTERNAL_MASTER_MODE) { in __IMX464_start_stream()
2568 ret |= IMX464_write_array(IMX464->client, IMX464_interal_sync_master_start_regs); in __IMX464_start_stream()
2569 v4l2_err(&IMX464->subdev, "cur intertal master\n"); in __IMX464_start_stream()
2570 } else if (IMX464->sync_mode == SLAVE_MODE) { in __IMX464_start_stream()
2571 ret |= IMX464_write_array(IMX464->client, IMX464_slave_start_regs); in __IMX464_start_stream()
2572 v4l2_err(&IMX464->subdev, "cur slave mode\n"); in __IMX464_start_stream()
2574 if (IMX464->sync_mode == NO_SYNC_MODE) { in __IMX464_start_stream()
2575 ret = imx464_write_reg(IMX464->client, IMX464_REG_CTRL_MODE, in __IMX464_start_stream()
2578 ret |= imx464_write_reg(IMX464->client, IMX464_REG_MARSTER_MODE, in __IMX464_start_stream()
2581 ret |= imx464_write_reg(IMX464->client, IMX464_REG_MARSTER_MODE, in __IMX464_start_stream()
2591 IMX464->has_init_exp = false; in __IMX464_stop_stream()
2592 ret = imx464_write_reg(IMX464->client, IMX464_REG_CTRL_MODE, in __IMX464_stop_stream()
2595 if (IMX464->sync_mode == EXTERNAL_MASTER_MODE) in __IMX464_stop_stream()
2596 ret |= IMX464_write_array(IMX464->client, IMX464_external_sync_master_stop_regs); in __IMX464_stop_stream()
2597 else if (IMX464->sync_mode == INTERNAL_MASTER_MODE) in __IMX464_stop_stream()
2598 ret |= IMX464_write_array(IMX464->client, IMX464_interal_sync_master_stop_regs); in __IMX464_stop_stream()
2605 struct i2c_client *client = IMX464->client; in IMX464_s_stream()
2608 mutex_lock(&IMX464->mutex); in IMX464_s_stream()
2610 if (on == IMX464->streaming) in IMX464_s_stream()
2614 ret = pm_runtime_get_sync(&client->dev); in IMX464_s_stream()
2616 pm_runtime_put_noidle(&client->dev); in IMX464_s_stream()
2622 v4l2_err(sd, "start stream failed while write regs\n"); in IMX464_s_stream()
2623 pm_runtime_put(&client->dev); in IMX464_s_stream()
2628 pm_runtime_put(&client->dev); in IMX464_s_stream()
2631 IMX464->streaming = on; in IMX464_s_stream()
2634 mutex_unlock(&IMX464->mutex); in IMX464_s_stream()
2642 struct i2c_client *client = IMX464->client; in IMX464_s_power()
2645 mutex_lock(&IMX464->mutex); in IMX464_s_power()
2647 /* If the power state is not modified - no work to do. */ in IMX464_s_power()
2648 if (IMX464->power_on == !!on) in IMX464_s_power()
2652 ret = pm_runtime_get_sync(&client->dev); in IMX464_s_power()
2654 pm_runtime_put_noidle(&client->dev); in IMX464_s_power()
2658 ret = IMX464_write_array(IMX464->client, IMX464_global_regs); in IMX464_s_power()
2661 pm_runtime_put_noidle(&client->dev); in IMX464_s_power()
2665 IMX464->power_on = true; in IMX464_s_power()
2667 pm_runtime_put(&client->dev); in IMX464_s_power()
2668 IMX464->power_on = false; in IMX464_s_power()
2672 mutex_unlock(&IMX464->mutex); in IMX464_s_power()
2687 struct device *dev = &IMX464->client->dev; in __IMX464_power_on()
2689 if (!IS_ERR_OR_NULL(IMX464->pins_default)) { in __IMX464_power_on()
2690 ret = pinctrl_select_state(IMX464->pinctrl, in __IMX464_power_on()
2691 IMX464->pins_default); in __IMX464_power_on()
2696 ret = clk_set_rate(IMX464->xvclk, IMX464->cur_mode->mclk); in __IMX464_power_on()
2699 if (clk_get_rate(IMX464->xvclk) != IMX464->cur_mode->mclk) in __IMX464_power_on()
2700 dev_warn(dev, "xvclk mismatched, %lu\n", clk_get_rate(IMX464->xvclk)); in __IMX464_power_on()
2702 IMX464->cur_mclk = IMX464->cur_mode->mclk; in __IMX464_power_on()
2703 ret = clk_prepare_enable(IMX464->xvclk); in __IMX464_power_on()
2708 if (!IS_ERR(IMX464->reset_gpio)) in __IMX464_power_on()
2709 gpiod_set_value_cansleep(IMX464->reset_gpio, 0); in __IMX464_power_on()
2711 ret = regulator_bulk_enable(IMX464_NUM_SUPPLIES, IMX464->supplies); in __IMX464_power_on()
2717 if (!IS_ERR(IMX464->reset_gpio)) in __IMX464_power_on()
2718 gpiod_set_value_cansleep(IMX464->reset_gpio, 1); in __IMX464_power_on()
2721 if (!IS_ERR(IMX464->pwdn_gpio)) in __IMX464_power_on()
2722 gpiod_set_value_cansleep(IMX464->pwdn_gpio, 1); in __IMX464_power_on()
2731 clk_disable_unprepare(IMX464->xvclk); in __IMX464_power_on()
2739 struct device *dev = &IMX464->client->dev; in __IMX464_power_off()
2741 if (!IS_ERR(IMX464->pwdn_gpio)) in __IMX464_power_off()
2742 gpiod_set_value_cansleep(IMX464->pwdn_gpio, 0); in __IMX464_power_off()
2743 clk_disable_unprepare(IMX464->xvclk); in __IMX464_power_off()
2744 if (!IS_ERR(IMX464->reset_gpio)) in __IMX464_power_off()
2745 gpiod_set_value_cansleep(IMX464->reset_gpio, 0); in __IMX464_power_off()
2746 if (!IS_ERR_OR_NULL(IMX464->pins_sleep)) { in __IMX464_power_off()
2747 ret = pinctrl_select_state(IMX464->pinctrl, in __IMX464_power_off()
2748 IMX464->pins_sleep); in __IMX464_power_off()
2752 regulator_bulk_disable(IMX464_NUM_SUPPLIES, IMX464->supplies); in __IMX464_power_off()
2781 v4l2_subdev_get_try_format(sd, fh->pad, 0); in IMX464_open()
2782 const struct IMX464_mode *def_mode = &IMX464->support_modes[0]; in IMX464_open()
2784 mutex_lock(&IMX464->mutex); in IMX464_open()
2786 try_fmt->width = def_mode->width; in IMX464_open()
2787 try_fmt->height = def_mode->height; in IMX464_open()
2788 try_fmt->code = def_mode->bus_fmt; in IMX464_open()
2789 try_fmt->field = V4L2_FIELD_NONE; in IMX464_open()
2791 mutex_unlock(&IMX464->mutex); in IMX464_open()
2804 if (fie->index >= IMX464->cfg_num) in IMX464_enum_frame_interval()
2805 return -EINVAL; in IMX464_enum_frame_interval()
2807 fie->code = IMX464->support_modes[fie->index].bus_fmt; in IMX464_enum_frame_interval()
2808 fie->width = IMX464->support_modes[fie->index].width; in IMX464_enum_frame_interval()
2809 fie->height = IMX464->support_modes[fie->index].height; in IMX464_enum_frame_interval()
2810 fie->interval = IMX464->support_modes[fie->index].max_fps; in IMX464_enum_frame_interval()
2811 fie->reserved[0] = IMX464->support_modes[fie->index].hdr_mode; in IMX464_enum_frame_interval()
2815 #define CROP_START(SRC, DST) (((SRC) - (DST)) / 2 / 4 * 4)
2834 if (sel->target == V4L2_SEL_TGT_CROP_BOUNDS) { in IMX464_get_selection()
2835 sel->r.left = CROP_START(IMX464->cur_mode->width, DST_WIDTH); in IMX464_get_selection()
2836 sel->r.width = DST_WIDTH; in IMX464_get_selection()
2837 sel->r.top = CROP_START(IMX464->cur_mode->height, DST_HEIGHT); in IMX464_get_selection()
2838 sel->r.height = DST_HEIGHT; in IMX464_get_selection()
2841 return -EINVAL; in IMX464_get_selection()
2886 struct IMX464 *IMX464 = container_of(ctrl->handler, in IMX464_set_ctrl()
2888 struct i2c_client *client = IMX464->client; in IMX464_set_ctrl()
2889 const struct IMX464_mode *mode = IMX464->cur_mode; in IMX464_set_ctrl()
2897 switch (ctrl->id) { in IMX464_set_ctrl()
2900 if (mode->hdr_mode == NO_HDR) { in IMX464_set_ctrl()
2901 max = IMX464->cur_mode->height + ctrl->val - 3; in IMX464_set_ctrl()
2902 __v4l2_ctrl_modify_range(IMX464->exposure, in IMX464_set_ctrl()
2903 IMX464->exposure->minimum, max, in IMX464_set_ctrl()
2904 IMX464->exposure->step, in IMX464_set_ctrl()
2905 IMX464->exposure->default_value); in IMX464_set_ctrl()
2910 if (!pm_runtime_get_if_in_use(&client->dev)) in IMX464_set_ctrl()
2913 switch (ctrl->id) { in IMX464_set_ctrl()
2915 if (mode->hdr_mode == NO_HDR) { in IMX464_set_ctrl()
2916 shr0 = IMX464->cur_vts - ctrl->val; in IMX464_set_ctrl()
2917 ret = imx464_write_reg(IMX464->client, IMX464_LF_EXPO_REG_L, in IMX464_set_ctrl()
2920 ret |= imx464_write_reg(IMX464->client, IMX464_LF_EXPO_REG_M, in IMX464_set_ctrl()
2923 ret |= imx464_write_reg(IMX464->client, IMX464_LF_EXPO_REG_H, in IMX464_set_ctrl()
2926 dev_err(&client->dev, "set exposure 0x%x\n", in IMX464_set_ctrl()
2927 ctrl->val); in IMX464_set_ctrl()
2931 if (mode->hdr_mode == NO_HDR) { in IMX464_set_ctrl()
2932 ret = imx464_write_reg(IMX464->client, IMX464_LF_GAIN_REG_H, in IMX464_set_ctrl()
2934 IMX464_FETCH_GAIN_H(ctrl->val)); in IMX464_set_ctrl()
2935 ret |= imx464_write_reg(IMX464->client, IMX464_LF_GAIN_REG_L, in IMX464_set_ctrl()
2937 IMX464_FETCH_GAIN_L(ctrl->val)); in IMX464_set_ctrl()
2938 dev_err(&client->dev, "set analog gain 0x%x\n", in IMX464_set_ctrl()
2939 ctrl->val); in IMX464_set_ctrl()
2943 vts = ctrl->val + IMX464->cur_mode->height; in IMX464_set_ctrl()
2945 if (mode->hdr_mode == HDR_X2) { in IMX464_set_ctrl()
2947 IMX464->cur_vts = vts; in IMX464_set_ctrl()
2949 } else if (mode->hdr_mode == HDR_X3) { in IMX464_set_ctrl()
2951 IMX464->cur_vts = vts; in IMX464_set_ctrl()
2954 IMX464->cur_vts = vts; in IMX464_set_ctrl()
2956 ret = imx464_write_reg(IMX464->client, IMX464_VTS_REG_L, in IMX464_set_ctrl()
2959 ret |= imx464_write_reg(IMX464->client, IMX464_VTS_REG_M, in IMX464_set_ctrl()
2962 ret |= imx464_write_reg(IMX464->client, IMX464_VTS_REG_H, in IMX464_set_ctrl()
2966 dev_err(&client->dev, "set vts 0x%x\n", in IMX464_set_ctrl()
2974 ret |= imx464_write_reg(IMX464->client, IMX464_HREVERSE_REG, in IMX464_set_ctrl()
2975 IMX464_REG_VALUE_08BIT, !!ctrl->val); in IMX464_set_ctrl()
2982 flip = ctrl->val; in IMX464_set_ctrl()
2987 ret |= imx464_write_reg(IMX464->client, IMX464_VREVERSE_REG, in IMX464_set_ctrl()
2990 ret |= imx464_write_reg(IMX464->client, 0x3074, in IMX464_set_ctrl()
2992 ret |= imx464_write_reg(IMX464->client, 0x3075, in IMX464_set_ctrl()
2994 ret |= imx464_write_reg(IMX464->client, 0x3080, in IMX464_set_ctrl()
2996 ret |= imx464_write_reg(IMX464->client, 0x30ad, in IMX464_set_ctrl()
2998 ret |= imx464_write_reg(IMX464->client, 0x30b6, in IMX464_set_ctrl()
3000 ret |= imx464_write_reg(IMX464->client, 0x30b7, in IMX464_set_ctrl()
3002 ret |= imx464_write_reg(IMX464->client, 0x30d8, in IMX464_set_ctrl()
3004 ret |= imx464_write_reg(IMX464->client, 0x3114, in IMX464_set_ctrl()
3007 ret |= imx464_write_reg(IMX464->client, 0x3074, in IMX464_set_ctrl()
3009 ret |= imx464_write_reg(IMX464->client, 0x3075, in IMX464_set_ctrl()
3011 ret |= imx464_write_reg(IMX464->client, 0x3080, in IMX464_set_ctrl()
3013 ret |= imx464_write_reg(IMX464->client, 0x30ad, in IMX464_set_ctrl()
3015 ret |= imx464_write_reg(IMX464->client, 0x30b6, in IMX464_set_ctrl()
3017 ret |= imx464_write_reg(IMX464->client, 0x30b7, in IMX464_set_ctrl()
3019 ret |= imx464_write_reg(IMX464->client, 0x30d8, in IMX464_set_ctrl()
3021 ret |= imx464_write_reg(IMX464->client, 0x3114, in IMX464_set_ctrl()
3030 dev_warn(&client->dev, "%s Unhandled id:0x%x, val:0x%x\n", in IMX464_set_ctrl()
3031 __func__, ctrl->id, ctrl->val); in IMX464_set_ctrl()
3035 pm_runtime_put(&client->dev); in IMX464_set_ctrl()
3053 handler = &IMX464->ctrl_handler; in IMX464_initialize_controls()
3054 mode = IMX464->cur_mode; in IMX464_initialize_controls()
3058 handler->lock = &IMX464->mutex; in IMX464_initialize_controls()
3060 IMX464->link_freq = v4l2_ctrl_new_int_menu(handler, in IMX464_initialize_controls()
3063 __v4l2_ctrl_s_ctrl(IMX464->link_freq, in IMX464_initialize_controls()
3064 IMX464->cur_mode->mipi_freq_idx); in IMX464_initialize_controls()
3065 pixel_rate = (u32)link_freq_menu_items[mode->mipi_freq_idx] / mode->bpp * 2 * in IMX464_initialize_controls()
3066 IMX464->bus_cfg.bus.mipi_csi2.num_data_lanes; in IMX464_initialize_controls()
3067 IMX464->pixel_rate = v4l2_ctrl_new_std(handler, NULL, in IMX464_initialize_controls()
3071 h_blank = mode->hts_def - mode->width; in IMX464_initialize_controls()
3072 IMX464->hblank = v4l2_ctrl_new_std(handler, NULL, V4L2_CID_HBLANK, in IMX464_initialize_controls()
3074 if (IMX464->hblank) in IMX464_initialize_controls()
3075 IMX464->hblank->flags |= V4L2_CTRL_FLAG_READ_ONLY; in IMX464_initialize_controls()
3077 vblank_def = mode->vts_def - mode->height; in IMX464_initialize_controls()
3078 IMX464->vblank = v4l2_ctrl_new_std(handler, &IMX464_ctrl_ops, in IMX464_initialize_controls()
3080 IMX464_VTS_MAX - mode->height, in IMX464_initialize_controls()
3082 IMX464->cur_vts = mode->vts_def; in IMX464_initialize_controls()
3084 exposure_max = mode->vts_def - 3; in IMX464_initialize_controls()
3085 IMX464->exposure = v4l2_ctrl_new_std(handler, &IMX464_ctrl_ops, in IMX464_initialize_controls()
3088 mode->exp_def); in IMX464_initialize_controls()
3090 IMX464->anal_a_gain = v4l2_ctrl_new_std(handler, &IMX464_ctrl_ops, in IMX464_initialize_controls()
3097 if (handler->error) { in IMX464_initialize_controls()
3098 ret = handler->error; in IMX464_initialize_controls()
3099 dev_err(&IMX464->client->dev, in IMX464_initialize_controls()
3104 IMX464->subdev.ctrl_handler = handler; in IMX464_initialize_controls()
3105 IMX464->has_init_exp = false; in IMX464_initialize_controls()
3106 IMX464->isHCG = false; in IMX464_initialize_controls()
3119 struct device *dev = &IMX464->client->dev; in IMX464_check_sensor_id()
3127 return -ENODEV; in IMX464_check_sensor_id()
3140 IMX464->supplies[i].supply = IMX464_supply_names[i]; in IMX464_configure_regulators()
3142 return devm_regulator_bulk_get(&IMX464->client->dev, in IMX464_configure_regulators()
3144 IMX464->supplies); in IMX464_configure_regulators()
3150 struct device *dev = &client->dev; in IMX464_probe()
3151 struct device_node *node = dev->of_node; in IMX464_probe()
3168 return -ENOMEM; in IMX464_probe()
3171 &IMX464->module_index); in IMX464_probe()
3173 &IMX464->module_facing); in IMX464_probe()
3175 &IMX464->module_name); in IMX464_probe()
3177 &IMX464->len_name); in IMX464_probe()
3180 return -EINVAL; in IMX464_probe()
3186 IMX464->sync_mode = NO_SYNC_MODE; in IMX464_probe()
3190 IMX464->sync_mode = EXTERNAL_MASTER_MODE; in IMX464_probe()
3192 IMX464->sync_mode = INTERNAL_MASTER_MODE; in IMX464_probe()
3194 IMX464->sync_mode = SLAVE_MODE; in IMX464_probe()
3203 IMX464->client = client; in IMX464_probe()
3204 endpoint = of_graph_get_next_endpoint(dev->of_node, NULL); in IMX464_probe()
3207 return -EINVAL; in IMX464_probe()
3210 &IMX464->bus_cfg); in IMX464_probe()
3215 if (IMX464->bus_cfg.bus.mipi_csi2.num_data_lanes == 4) { in IMX464_probe()
3216 IMX464->support_modes = supported_modes; in IMX464_probe()
3217 IMX464->cfg_num = ARRAY_SIZE(supported_modes); in IMX464_probe()
3219 IMX464->support_modes = supported_modes_2lane; in IMX464_probe()
3220 IMX464->cfg_num = ARRAY_SIZE(supported_modes_2lane); in IMX464_probe()
3223 for (i = 0; i < IMX464->cfg_num; i++) { in IMX464_probe()
3224 if (hdr_mode == IMX464->support_modes[i].hdr_mode) { in IMX464_probe()
3225 IMX464->cur_mode = &IMX464->support_modes[i]; in IMX464_probe()
3229 IMX464->cur_mode = &IMX464->support_modes[0]; in IMX464_probe()
3230 IMX464->xvclk = devm_clk_get(dev, "xvclk"); in IMX464_probe()
3231 if (IS_ERR(IMX464->xvclk)) { in IMX464_probe()
3233 return -EINVAL; in IMX464_probe()
3236 IMX464->reset_gpio = devm_gpiod_get(dev, "reset", GPIOD_OUT_LOW); in IMX464_probe()
3237 if (IS_ERR(IMX464->reset_gpio)) in IMX464_probe()
3238 dev_warn(dev, "Failed to get reset-gpios\n"); in IMX464_probe()
3240 IMX464->pwdn_gpio = devm_gpiod_get(dev, "pwdn", GPIOD_OUT_LOW); in IMX464_probe()
3241 if (IS_ERR(IMX464->pwdn_gpio)) in IMX464_probe()
3242 dev_warn(dev, "Failed to get pwdn-gpios\n"); in IMX464_probe()
3244 IMX464->pinctrl = devm_pinctrl_get(dev); in IMX464_probe()
3245 if (!IS_ERR(IMX464->pinctrl)) { in IMX464_probe()
3246 IMX464->pins_default = in IMX464_probe()
3247 pinctrl_lookup_state(IMX464->pinctrl, in IMX464_probe()
3249 if (IS_ERR(IMX464->pins_default)) in IMX464_probe()
3252 IMX464->pins_sleep = in IMX464_probe()
3253 pinctrl_lookup_state(IMX464->pinctrl, in IMX464_probe()
3255 if (IS_ERR(IMX464->pins_sleep)) in IMX464_probe()
3267 mutex_init(&IMX464->mutex); in IMX464_probe()
3269 sd = &IMX464->subdev; in IMX464_probe()
3284 sd->internal_ops = &IMX464_internal_ops; in IMX464_probe()
3285 sd->flags |= V4L2_SUBDEV_FL_HAS_DEVNODE | in IMX464_probe()
3289 IMX464->pad.flags = MEDIA_PAD_FL_SOURCE; in IMX464_probe()
3290 sd->entity.function = MEDIA_ENT_F_CAM_SENSOR; in IMX464_probe()
3291 ret = media_entity_pads_init(&sd->entity, 1, &IMX464->pad); in IMX464_probe()
3297 if (strcmp(IMX464->module_facing, "back") == 0) in IMX464_probe()
3302 snprintf(sd->name, sizeof(sd->name), "m%02d_%s_%s %s", in IMX464_probe()
3303 IMX464->module_index, facing, in IMX464_probe()
3304 IMX464_NAME, dev_name(sd->dev)); in IMX464_probe()
3322 media_entity_cleanup(&sd->entity); in IMX464_probe()
3327 v4l2_ctrl_handler_free(&IMX464->ctrl_handler); in IMX464_probe()
3329 mutex_destroy(&IMX464->mutex); in IMX464_probe()
3341 media_entity_cleanup(&sd->entity); in IMX464_remove()
3343 v4l2_ctrl_handler_free(&IMX464->ctrl_handler); in IMX464_remove()
3344 mutex_destroy(&IMX464->mutex); in IMX464_remove()
3346 pm_runtime_disable(&client->dev); in IMX464_remove()
3347 if (!pm_runtime_status_suspended(&client->dev)) in IMX464_remove()
3349 pm_runtime_set_suspended(&client->dev); in IMX464_remove()
3351 remove_sysfs_interfaces(&client->dev); in IMX464_remove()