Lines Matching full:sensor
3 * Driver for VD55G1 global shutter sensor family driver
446 * This mode acquires 2 frames on the sensor, the first one is ditched
575 static const struct vd55g1_fmt_desc *vd55g1_get_fmt_desc(struct vd55g1 *sensor, in vd55g1_get_fmt_desc() argument
586 dev_warn(sensor->dev, "Unsupported code %d. default to 8 bpp\n", code); in vd55g1_get_fmt_desc()
591 static s32 vd55g1_get_pixel_rate(struct vd55g1 *sensor, in vd55g1_get_pixel_rate() argument
594 return sensor->mipi_rate / in vd55g1_get_pixel_rate()
595 vd55g1_get_fmt_desc(sensor, format->code)->bpp; in vd55g1_get_pixel_rate()
598 static unsigned int vd55g1_get_hblank_min(struct vd55g1 *sensor, in vd55g1_get_hblank_min() argument
608 vd55g1_get_fmt_desc(sensor, format->code)->bpp + in vd55g1_get_hblank_min()
610 (sensor->mipi_rate / MEGA); in vd55g1_get_hblank_min()
611 mipi_req_line_length = mipi_req_line_time * sensor->pixel_clock / in vd55g1_get_hblank_min()
616 if (sensor->hdr_ctrl->val == VD55G1_HDR_SUB) in vd55g1_get_hblank_min()
625 static void vd55g1_get_vblank_limits(struct vd55g1 *sensor, in vd55g1_get_vblank_limits() argument
634 #define vd55g1_read(sensor, reg, val, err) \ argument
635 cci_read((sensor)->regmap, reg, val, err)
637 #define vd55g1_write(sensor, reg, val, err) \ argument
638 cci_write((sensor)->regmap, reg, val, err)
640 static int vd55g1_write_array(struct vd55g1 *sensor, u32 reg, unsigned int len, in vd55g1_write_array() argument
656 ret = regmap_bulk_write(sensor->regmap, reg, array, sz); in vd55g1_write_array()
671 static int vd55g1_poll_reg(struct vd55g1 *sensor, u32 reg, u8 poll_val, in vd55g1_poll_reg() argument
680 ret = regmap_read_poll_timeout(sensor->regmap, CCI_REG_ADDR(reg), val, in vd55g1_poll_reg()
690 static int vd55g1_wait_state(struct vd55g1 *sensor, int state, int *err) in vd55g1_wait_state() argument
692 return vd55g1_poll_reg(sensor, VD55G1_REG_SYSTEM_FSM, state, err); in vd55g1_wait_state()
695 static int vd55g1_prepare_clock_tree(struct vd55g1 *sensor) in vd55g1_prepare_clock_tree() argument
699 if (sensor->xclk_freq < VD55G1_XCLK_FREQ_MIN || in vd55g1_prepare_clock_tree()
700 sensor->xclk_freq > VD55G1_XCLK_FREQ_MAX) { in vd55g1_prepare_clock_tree()
701 dev_err(sensor->dev, in vd55g1_prepare_clock_tree()
705 sensor->xclk_freq / HZ_PER_MHZ); in vd55g1_prepare_clock_tree()
710 sensor->mipi_rate = sensor->link_freq * 2; in vd55g1_prepare_clock_tree()
712 if (sensor->mipi_rate < VD55G1_MIPI_RATE_MIN || in vd55g1_prepare_clock_tree()
713 sensor->mipi_rate > VD55G1_MIPI_RATE_MAX) { in vd55g1_prepare_clock_tree()
714 dev_err(sensor->dev, in vd55g1_prepare_clock_tree()
718 sensor->mipi_rate / MEGA); in vd55g1_prepare_clock_tree()
722 if (sensor->mipi_rate <= 300 * MEGA) in vd55g1_prepare_clock_tree()
724 else if (sensor->mipi_rate <= 600 * MEGA) in vd55g1_prepare_clock_tree()
729 sys_clk = sensor->mipi_rate * mipi_div; in vd55g1_prepare_clock_tree()
738 sensor->pixel_clock = sys_clk / pixel_div; in vd55g1_prepare_clock_tree()
743 static int vd55g1_update_patgen(struct vd55g1 *sensor, u32 patgen_index) in vd55g1_update_patgen() argument
762 vd55g1_write(sensor, VD55G1_REG_DUSTER_CTRL, duster, &ret); in vd55g1_update_patgen()
763 vd55g1_write(sensor, VD55G1_REG_PATGEN_CTRL, reg, &ret); in vd55g1_update_patgen()
768 static int vd55g1_update_expo_cluster(struct vd55g1 *sensor, bool is_auto) in vd55g1_update_expo_cluster() argument
774 if (sensor->ae_ctrl->is_new) in vd55g1_update_expo_cluster()
775 vd55g1_write(sensor, VD55G1_REG_EXP_MODE(0), expo_state, &ret); in vd55g1_update_expo_cluster()
777 if (sensor->hdr_ctrl->val == VD55G1_HDR_SUB && in vd55g1_update_expo_cluster()
778 sensor->hdr_ctrl->is_new) { in vd55g1_update_expo_cluster()
779 vd55g1_write(sensor, VD55G1_REG_EXP_MODE(1), VD55G1_EXP_BYPASS, in vd55g1_update_expo_cluster()
785 if (!is_auto && sensor->expo_ctrl->is_new) in vd55g1_update_expo_cluster()
786 vd55g1_write(sensor, VD55G1_REG_MANUAL_COARSE_EXPOSURE, in vd55g1_update_expo_cluster()
787 sensor->expo_ctrl->val, &ret); in vd55g1_update_expo_cluster()
789 if (!is_auto && sensor->again_ctrl->is_new) in vd55g1_update_expo_cluster()
790 vd55g1_write(sensor, VD55G1_REG_MANUAL_ANALOG_GAIN, in vd55g1_update_expo_cluster()
791 sensor->again_ctrl->val, &ret); in vd55g1_update_expo_cluster()
793 if (!is_auto && sensor->dgain_ctrl->is_new) in vd55g1_update_expo_cluster()
794 vd55g1_write(sensor, VD55G1_REG_MANUAL_DIGITAL_GAIN, in vd55g1_update_expo_cluster()
795 sensor->dgain_ctrl->val, &ret); in vd55g1_update_expo_cluster()
800 static int vd55g1_lock_exposure(struct vd55g1 *sensor, u32 lock_val) in vd55g1_lock_exposure() argument
807 if (sensor->ae_ctrl->val == V4L2_EXPOSURE_AUTO) in vd55g1_lock_exposure()
808 vd55g1_write(sensor, VD55G1_REG_EXP_MODE(0), expo_state, &ret); in vd55g1_lock_exposure()
813 static int vd55g1_read_expo_cluster(struct vd55g1 *sensor) in vd55g1_read_expo_cluster() argument
820 vd55g1_read(sensor, VD55G1_REG_APPLIED_COARSE_EXPOSURE, &exposure, in vd55g1_read_expo_cluster()
822 vd55g1_read(sensor, VD55G1_REG_APPLIED_ANALOG_GAIN, &again, &ret); in vd55g1_read_expo_cluster()
823 vd55g1_read(sensor, VD55G1_REG_APPLIED_DIGITAL_GAIN, &dgain, &ret); in vd55g1_read_expo_cluster()
827 sensor->expo_ctrl->cur.val = exposure; in vd55g1_read_expo_cluster()
828 sensor->again_ctrl->cur.val = again; in vd55g1_read_expo_cluster()
829 sensor->dgain_ctrl->cur.val = dgain; in vd55g1_read_expo_cluster()
834 static int vd55g1_update_frame_length(struct vd55g1 *sensor, in vd55g1_update_frame_length() argument
839 if (sensor->hdr_ctrl->val == VD55G1_HDR_SUB) in vd55g1_update_frame_length()
840 vd55g1_write(sensor, VD55G1_REG_FRAME_LENGTH(1), frame_length, in vd55g1_update_frame_length()
842 vd55g1_write(sensor, VD55G1_REG_FRAME_LENGTH(0), frame_length, &ret); in vd55g1_update_frame_length()
847 static int vd55g1_update_exposure_target(struct vd55g1 *sensor, int index) in vd55g1_update_exposure_target() argument
851 * Defaut target exposure being 27 for the sensor. in vd55g1_update_exposure_target()
858 return vd55g1_write(sensor, VD55G1_REG_AE_TARGET_PERCENTAGE, in vd55g1_update_exposure_target()
862 static int vd55g1_apply_cold_start(struct vd55g1 *sensor, in vd55g1_apply_cold_start() argument
871 unsigned int line_length = crop->width + sensor->hblank_ctrl->val; in vd55g1_apply_cold_start()
873 sensor->pixel_clock); in vd55g1_apply_cold_start()
874 u8 d_gain = DIV_ROUND_CLOSEST(sensor->dgain_ctrl->val, 1 << 8); in vd55g1_apply_cold_start()
875 u8 a_gain = DIV_ROUND_CLOSEST(32, (32 - sensor->again_ctrl->val)); in vd55g1_apply_cold_start()
876 unsigned int expo_us = sensor->expo_ctrl->val * d_gain * a_gain * in vd55g1_apply_cold_start()
880 vd55g1_write(sensor, VD55G1_REG_AE_FORCE_COLDSTART, 1, &ret); in vd55g1_apply_cold_start()
881 vd55g1_write(sensor, VD55G1_REG_AE_COLDSTART_EXP_TIME, expo_us, &ret); in vd55g1_apply_cold_start()
886 static void vd55g1_update_pad_fmt(struct vd55g1 *sensor, in vd55g1_update_pad_fmt() argument
900 static int vd55g1_update_hdr_mode(struct vd55g1 *sensor) in vd55g1_update_hdr_mode() argument
904 switch (sensor->hdr_ctrl->val) { in vd55g1_update_hdr_mode()
906 vd55g1_write(sensor, VD55G1_REG_EXPOSURE_MAX_COARSE, in vd55g1_update_hdr_mode()
908 vd55g1_write(sensor, VD55G1_REG_EXPOSURE_USE_CASES, 0, &ret); in vd55g1_update_hdr_mode()
909 vd55g1_write(sensor, VD55G1_REG_NEXT_CTX, 0x0, &ret); in vd55g1_update_hdr_mode()
911 vd55g1_write(sensor, VD55G1_REG_CTX_REPEAT_COUNT_CTX0, 0, &ret); in vd55g1_update_hdr_mode()
913 vd55g1_write(sensor, VD55G1_REG_VT_MODE(0), in vd55g1_update_hdr_mode()
915 vd55g1_write(sensor, VD55G1_REG_MASK_FRAME_CTRL(0), in vd55g1_update_hdr_mode()
919 vd55g1_write(sensor, VD55G1_REG_EXPOSURE_MAX_COARSE, in vd55g1_update_hdr_mode()
921 vd55g1_write(sensor, VD55G1_REG_EXPOSURE_USE_CASES, in vd55g1_update_hdr_mode()
923 vd55g1_write(sensor, VD55G1_REG_NEXT_CTX, 0x0001, &ret); in vd55g1_update_hdr_mode()
925 vd55g1_write(sensor, VD55G1_REG_CTX_REPEAT_COUNT_CTX0, 1, &ret); in vd55g1_update_hdr_mode()
926 vd55g1_write(sensor, VD55G1_REG_CTX_REPEAT_COUNT_CTX1, 1, &ret); in vd55g1_update_hdr_mode()
928 vd55g1_write(sensor, VD55G1_REG_VT_MODE(0), in vd55g1_update_hdr_mode()
930 vd55g1_write(sensor, VD55G1_REG_MASK_FRAME_CTRL(0), in vd55g1_update_hdr_mode()
932 vd55g1_write(sensor, VD55G1_REG_EXPOSURE_INSTANCE(0), 0, &ret); in vd55g1_update_hdr_mode()
933 vd55g1_write(sensor, VD55G1_REG_VT_MODE(1), in vd55g1_update_hdr_mode()
935 vd55g1_write(sensor, VD55G1_REG_MASK_FRAME_CTRL(1), in vd55g1_update_hdr_mode()
937 vd55g1_write(sensor, VD55G1_REG_EXPOSURE_INSTANCE(1), 1, &ret); in vd55g1_update_hdr_mode()
946 static int vd55g1_set_framefmt(struct vd55g1 *sensor, in vd55g1_set_framefmt() argument
953 vd55g1_write(sensor, VD55G1_REG_FORMAT_CTRL, in vd55g1_set_framefmt()
954 vd55g1_get_fmt_desc(sensor, format->code)->bpp, &ret); in vd55g1_set_framefmt()
955 vd55g1_write(sensor, VD55G1_REG_OIF_IMG_CTRL, in vd55g1_set_framefmt()
956 vd55g1_get_fmt_desc(sensor, format->code)->data_type, in vd55g1_set_framefmt()
968 vd55g1_write(sensor, VD55G1_REG_READOUT_CTRL, binning, &ret); in vd55g1_set_framefmt()
970 vd55g1_write(sensor, VD55G1_REG_X_START(0), crop->left, &ret); in vd55g1_set_framefmt()
971 vd55g1_write(sensor, VD55G1_REG_X_WIDTH(0), crop->width, &ret); in vd55g1_set_framefmt()
972 vd55g1_write(sensor, VD55G1_REG_Y_START(0), crop->top, &ret); in vd55g1_set_framefmt()
973 vd55g1_write(sensor, VD55G1_REG_Y_HEIGHT(0), crop->height, &ret); in vd55g1_set_framefmt()
975 vd55g1_write(sensor, VD55G1_REG_X_START(1), crop->left, &ret); in vd55g1_set_framefmt()
976 vd55g1_write(sensor, VD55G1_REG_X_WIDTH(1), crop->width, &ret); in vd55g1_set_framefmt()
977 vd55g1_write(sensor, VD55G1_REG_Y_START(1), crop->top, &ret); in vd55g1_set_framefmt()
978 vd55g1_write(sensor, VD55G1_REG_Y_HEIGHT(1), crop->height, &ret); in vd55g1_set_framefmt()
983 static int vd55g1_update_gpios(struct vd55g1 *sensor, unsigned long gpio_mask) in vd55g1_update_gpios() argument
990 gpio_val = sensor->gpios[io]; in vd55g1_update_gpios()
993 sensor->led_ctrl->val == V4L2_FLASH_LED_MODE_NONE) { in vd55g1_update_gpios()
995 if (sensor->hdr_ctrl->val == VD55G1_HDR_SUB) { in vd55g1_update_gpios()
997 vd55g1_write(sensor, in vd55g1_update_gpios()
1003 ret = vd55g1_write(sensor, VD55G1_REG_GPIO_0_CTRL(0) + io, in vd55g1_update_gpios()
1010 static int vd55g1_ro_ctrls_setup(struct vd55g1 *sensor, struct v4l2_rect *crop) in vd55g1_ro_ctrls_setup() argument
1012 return vd55g1_write(sensor, VD55G1_REG_LINE_LENGTH, in vd55g1_ro_ctrls_setup()
1013 crop->width + sensor->hblank_ctrl->val, NULL); in vd55g1_ro_ctrls_setup()
1016 static void vd55g1_grab_ctrls(struct vd55g1 *sensor, bool enable) in vd55g1_grab_ctrls() argument
1019 v4l2_ctrl_grab(sensor->hflip_ctrl, enable); in vd55g1_grab_ctrls()
1020 v4l2_ctrl_grab(sensor->vflip_ctrl, enable); in vd55g1_grab_ctrls()
1021 v4l2_ctrl_grab(sensor->patgen_ctrl, enable); in vd55g1_grab_ctrls()
1022 v4l2_ctrl_grab(sensor->hdr_ctrl, enable); in vd55g1_grab_ctrls()
1029 struct vd55g1 *sensor = to_vd55g1(sd); in vd55g1_enable_streams() local
1036 ret = pm_runtime_resume_and_get(sensor->dev); in vd55g1_enable_streams()
1041 vd55g1_write(sensor, VD55G1_REG_MIPI_DATA_RATE, in vd55g1_enable_streams()
1042 sensor->mipi_rate, &ret); in vd55g1_enable_streams()
1043 vd55g1_write(sensor, VD55G1_REG_OIF_CTRL, sensor->oif_ctrl, &ret); in vd55g1_enable_streams()
1044 vd55g1_write(sensor, VD55G1_REG_ISL_ENABLE, 0, &ret); in vd55g1_enable_streams()
1048 ret = vd55g1_set_framefmt(sensor, format, crop); in vd55g1_enable_streams()
1053 ret = vd55g1_update_gpios(sensor, GENMASK(VD55G1_NB_GPIOS - 1, 0)); in vd55g1_enable_streams()
1057 ret = vd55g1_apply_cold_start(sensor, crop); in vd55g1_enable_streams()
1062 ret = __v4l2_ctrl_handler_setup(&sensor->ctrl_handler); in vd55g1_enable_streams()
1067 ret = vd55g1_ro_ctrls_setup(sensor, crop); in vd55g1_enable_streams()
1072 vd55g1_write(sensor, VD55G1_REG_STBY, VD55G1_STBY_START_STREAM, &ret); in vd55g1_enable_streams()
1073 vd55g1_poll_reg(sensor, VD55G1_REG_STBY, 0, &ret); in vd55g1_enable_streams()
1074 vd55g1_wait_state(sensor, VD55G1_SYSTEM_FSM_STREAMING, &ret); in vd55g1_enable_streams()
1078 vd55g1_grab_ctrls(sensor, true); in vd55g1_enable_streams()
1083 pm_runtime_put(sensor->dev); in vd55g1_enable_streams()
1091 struct vd55g1 *sensor = to_vd55g1(sd); in vd55g1_disable_streams() local
1095 ret = vd55g1_read_expo_cluster(sensor); in vd55g1_disable_streams()
1097 vd55g1_write(sensor, VD55G1_REG_STREAMING, VD55G1_STREAMING_STOP_STREAM, in vd55g1_disable_streams()
1099 vd55g1_poll_reg(sensor, VD55G1_REG_STREAMING, 0, &ret); in vd55g1_disable_streams()
1100 vd55g1_wait_state(sensor, VD55G1_SYSTEM_FSM_SW_STBY, &ret); in vd55g1_disable_streams()
1103 dev_warn(sensor->dev, "Can't disable stream\n"); in vd55g1_disable_streams()
1105 vd55g1_grab_ctrls(sensor, false); in vd55g1_disable_streams()
1107 pm_runtime_put_autosuspend(sensor->dev); in vd55g1_disable_streams()
1112 static int vd55g1_patch(struct vd55g1 *sensor) in vd55g1_patch() argument
1117 vd55g1_write_array(sensor, VD55G1_REG_FWPATCH_START_ADDR, in vd55g1_patch()
1119 vd55g1_write(sensor, VD55G1_REG_BOOT, VD55G1_BOOT_PATCH_SETUP, &ret); in vd55g1_patch()
1120 vd55g1_poll_reg(sensor, VD55G1_REG_BOOT, 0, &ret); in vd55g1_patch()
1122 dev_err(sensor->dev, "Failed to apply patch\n"); in vd55g1_patch()
1126 vd55g1_read(sensor, VD55G1_REG_FWPATCH_REVISION, &patch, &ret); in vd55g1_patch()
1129 dev_err(sensor->dev, "Bad patch version expected %d.%d got %d.%d\n", in vd55g1_patch()
1135 dev_dbg(sensor->dev, "patch %d.%d applied\n", in vd55g1_patch()
1176 static int vd55g1_new_format_change_controls(struct vd55g1 *sensor, in vd55g1_new_format_change_controls() argument
1187 vd55g1_get_vblank_limits(sensor, crop, &vblank); in vd55g1_new_format_change_controls()
1188 ret = __v4l2_ctrl_modify_range(sensor->vblank_ctrl, vblank.min, in vd55g1_new_format_change_controls()
1194 frame_length = crop->height + sensor->vblank_ctrl->val; in vd55g1_new_format_change_controls()
1196 ret = __v4l2_ctrl_modify_range(sensor->expo_ctrl, 0, expo_max, 1, in vd55g1_new_format_change_controls()
1202 ret = __v4l2_ctrl_s_ctrl_int64(sensor->pixel_rate_ctrl, in vd55g1_new_format_change_controls()
1203 vd55g1_get_pixel_rate(sensor, format)); in vd55g1_new_format_change_controls()
1208 hblank = vd55g1_get_hblank_min(sensor, format, crop); in vd55g1_new_format_change_controls()
1209 ret = __v4l2_ctrl_modify_range(sensor->hblank_ctrl, hblank, hblank, 1, in vd55g1_new_format_change_controls()
1219 struct vd55g1 *sensor = to_vd55g1(sd); in vd55g1_set_pad_fmt() local
1230 vd55g1_update_pad_fmt(sensor, new_mode, sd_fmt->format.code, in vd55g1_set_pad_fmt()
1235 * sensor. in vd55g1_set_pad_fmt()
1251 return vd55g1_new_format_change_controls(sensor, in vd55g1_set_pad_fmt()
1261 struct vd55g1 *sensor = to_vd55g1(sd); in vd55g1_init_state() local
1277 vd55g1_update_pad_fmt(sensor, &vd55g1_supported_modes[VD55G1_MODE_DEF], in vd55g1_init_state()
1324 struct vd55g1 *sensor = ctrl_to_vd55g1(ctrl); in vd55g1_g_volatile_ctrl() local
1328 if (!pm_runtime_get_if_in_use(sensor->dev)) in vd55g1_g_volatile_ctrl()
1333 ret = vd55g1_read_expo_cluster(sensor); in vd55g1_g_volatile_ctrl()
1340 pm_runtime_put_autosuspend(sensor->dev); in vd55g1_g_volatile_ctrl()
1347 struct vd55g1 *sensor = ctrl_to_vd55g1(ctrl); in vd55g1_s_ctrl() local
1351 v4l2_subdev_get_locked_active_state(&sensor->sd); in vd55g1_s_ctrl()
1356 unsigned int hblank = vd55g1_get_hblank_min(sensor, format, crop); in vd55g1_s_ctrl()
1368 ret = __v4l2_ctrl_modify_range(sensor->expo_ctrl, 0, expo_max, in vd55g1_s_ctrl()
1373 __v4l2_ctrl_grab(sensor->ae_lock_ctrl, !is_auto); in vd55g1_s_ctrl()
1374 __v4l2_ctrl_grab(sensor->ae_bias_ctrl, !is_auto); in vd55g1_s_ctrl()
1380 ret = __v4l2_ctrl_modify_range(sensor->hblank_ctrl, in vd55g1_s_ctrl()
1394 if (!pm_runtime_get_if_in_use(sensor->dev)) in vd55g1_s_ctrl()
1399 ret = vd55g1_write(sensor, VD55G1_REG_ORIENTATION, in vd55g1_s_ctrl()
1400 sensor->hflip_ctrl->val | in vd55g1_s_ctrl()
1401 (sensor->vflip_ctrl->val << 1), in vd55g1_s_ctrl()
1405 ret = vd55g1_update_patgen(sensor, ctrl->val); in vd55g1_s_ctrl()
1408 ret = vd55g1_update_expo_cluster(sensor, is_auto); in vd55g1_s_ctrl()
1411 ret = vd55g1_lock_exposure(sensor, ctrl->val); in vd55g1_s_ctrl()
1418 ret = vd55g1_update_exposure_target(sensor, ctrl->val); in vd55g1_s_ctrl()
1421 ret = vd55g1_update_frame_length(sensor, frame_length); in vd55g1_s_ctrl()
1424 ret = vd55g1_update_gpios(sensor, sensor->ext_leds_mask); in vd55g1_s_ctrl()
1427 ret = vd55g1_update_hdr_mode(sensor); in vd55g1_s_ctrl()
1434 pm_runtime_put_autosuspend(sensor->dev); in vd55g1_s_ctrl()
1444 static int vd55g1_init_ctrls(struct vd55g1 *sensor) in vd55g1_init_ctrls() argument
1447 struct v4l2_ctrl_handler *hdl = &sensor->ctrl_handler; in vd55g1_init_ctrls()
1453 v4l2_subdev_lock_and_get_active_state(&sensor->sd); in vd55g1_init_ctrls()
1458 s32 pixel_rate = vd55g1_get_pixel_rate(sensor, format); in vd55g1_init_ctrls()
1464 sensor->hflip_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_HFLIP, in vd55g1_init_ctrls()
1466 sensor->vflip_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_VFLIP, in vd55g1_init_ctrls()
1468 v4l2_ctrl_cluster(2, &sensor->hflip_ctrl); in vd55g1_init_ctrls()
1471 sensor->ae_ctrl = v4l2_ctrl_new_std_menu(hdl, ops, in vd55g1_init_ctrls()
1474 sensor->again_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_ANALOGUE_GAIN, in vd55g1_init_ctrls()
1476 sensor->dgain_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_DIGITAL_GAIN, in vd55g1_init_ctrls()
1479 sensor->expo_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_EXPOSURE, 0, in vd55g1_init_ctrls()
1483 v4l2_ctrl_auto_cluster(4, &sensor->ae_ctrl, V4L2_EXPOSURE_MANUAL, true); in vd55g1_init_ctrls()
1485 sensor->patgen_ctrl = in vd55g1_init_ctrls()
1490 0, 0, &sensor->link_freq); in vd55g1_init_ctrls()
1493 sensor->pixel_rate_ctrl = v4l2_ctrl_new_std(hdl, ops, in vd55g1_init_ctrls()
1497 if (sensor->pixel_rate_ctrl) in vd55g1_init_ctrls()
1498 sensor->pixel_rate_ctrl->flags |= V4L2_CTRL_FLAG_READ_ONLY; in vd55g1_init_ctrls()
1499 sensor->ae_lock_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_3A_LOCK, in vd55g1_init_ctrls()
1501 sensor->ae_bias_ctrl = in vd55g1_init_ctrls()
1507 sensor->hdr_ctrl = in vd55g1_init_ctrls()
1512 hblank = vd55g1_get_hblank_min(sensor, format, crop); in vd55g1_init_ctrls()
1513 sensor->hblank_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_HBLANK, in vd55g1_init_ctrls()
1515 if (sensor->hblank_ctrl) in vd55g1_init_ctrls()
1516 sensor->hblank_ctrl->flags |= V4L2_CTRL_FLAG_READ_ONLY; in vd55g1_init_ctrls()
1517 vd55g1_get_vblank_limits(sensor, crop, &vblank); in vd55g1_init_ctrls()
1518 sensor->vblank_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_VBLANK, in vd55g1_init_ctrls()
1523 if (sensor->ext_leds_mask) { in vd55g1_init_ctrls()
1524 sensor->led_ctrl = in vd55g1_init_ctrls()
1531 ret = v4l2_fwnode_device_parse(sensor->dev, &fwnode_props); in vd55g1_init_ctrls()
1539 sensor->sd.ctrl_handler = hdl; in vd55g1_init_ctrls()
1549 static int vd55g1_detect(struct vd55g1 *sensor) in vd55g1_detect() argument
1555 ret = vd55g1_read(sensor, VD55G1_REG_MODEL_ID, &id, NULL); in vd55g1_detect()
1560 dev_warn(sensor->dev, "Unsupported sensor id %x\n", (u32)id); in vd55g1_detect()
1564 ret = vd55g1_read(sensor, VD55G1_REG_REVISION, &device_rev, NULL); in vd55g1_detect()
1569 dev_err(sensor->dev, "Unsupported sensor revision (0x%x)\n", in vd55g1_detect()
1580 struct vd55g1 *sensor = to_vd55g1(sd); in vd55g1_power_on() local
1584 sensor->supplies); in vd55g1_power_on()
1590 ret = clk_prepare_enable(sensor->xclk); in vd55g1_power_on()
1596 gpiod_set_value_cansleep(sensor->reset_gpio, 0); in vd55g1_power_on()
1598 ret = vd55g1_wait_state(sensor, VD55G1_SYSTEM_FSM_READY_TO_BOOT, NULL); in vd55g1_power_on()
1600 dev_err(dev, "Sensor reset failed %d\n", ret); in vd55g1_power_on()
1604 ret = vd55g1_detect(sensor); in vd55g1_power_on()
1606 dev_err(dev, "Sensor detect failed %d\n", ret); in vd55g1_power_on()
1611 vd55g1_write(sensor, VD55G1_REG_EXT_CLOCK, sensor->xclk_freq, &ret); in vd55g1_power_on()
1613 ret = vd55g1_patch(sensor); in vd55g1_power_on()
1615 dev_err(dev, "Sensor patch failed %d\n", ret); in vd55g1_power_on()
1619 ret = vd55g1_wait_state(sensor, VD55G1_SYSTEM_FSM_SW_STBY, NULL); in vd55g1_power_on()
1621 dev_err(dev, "Sensor waiting after patch failed %d\n", in vd55g1_power_on()
1629 gpiod_set_value_cansleep(sensor->reset_gpio, 1); in vd55g1_power_on()
1630 clk_disable_unprepare(sensor->xclk); in vd55g1_power_on()
1633 sensor->supplies); in vd55g1_power_on()
1641 struct vd55g1 *sensor = to_vd55g1(sd); in vd55g1_power_off() local
1643 gpiod_set_value_cansleep(sensor->reset_gpio, 1); in vd55g1_power_off()
1644 clk_disable_unprepare(sensor->xclk); in vd55g1_power_off()
1645 regulator_bulk_disable(ARRAY_SIZE(sensor->supplies), sensor->supplies); in vd55g1_power_off()
1650 static int vd55g1_check_csi_conf(struct vd55g1 *sensor, in vd55g1_check_csi_conf() argument
1664 dev_err(sensor->dev, "Sensor only supports 1 lane, found %d\n", in vd55g1_check_csi_conf()
1672 dev_err(sensor->dev, "Clock lane must be mapped to lane 0\n"); in vd55g1_check_csi_conf()
1677 /* Handle polarities in sensor configuration */ in vd55g1_check_csi_conf()
1678 sensor->oif_ctrl = (ep.bus.mipi_csi2.lane_polarities[0] << 3) | in vd55g1_check_csi_conf()
1683 dev_err(sensor->dev, "link-frequency property not found in DT\n"); in vd55g1_check_csi_conf()
1688 dev_err(sensor->dev, "Multiple link frequencies not supported\n"); in vd55g1_check_csi_conf()
1692 sensor->link_freq = ep.link_frequencies[0]; in vd55g1_check_csi_conf()
1700 static int vd55g1_parse_dt_gpios_array(struct vd55g1 *sensor, in vd55g1_parse_dt_gpios_array() argument
1706 *nb = device_property_count_u32(sensor->dev, prop_name); in vd55g1_parse_dt_gpios_array()
1713 ret = device_property_read_u32_array(sensor->dev, in vd55g1_parse_dt_gpios_array()
1716 dev_err(sensor->dev, "Failed to read %s prop\n", prop_name); in vd55g1_parse_dt_gpios_array()
1721 dev_err(sensor->dev, "Invalid GPIO number %d\n", in vd55g1_parse_dt_gpios_array()
1730 static int vd55g1_parse_dt_gpios(struct vd55g1 *sensor) in vd55g1_parse_dt_gpios() argument
1739 sensor->gpios[i] = VD55G1_GPIO_MODE_IN; in vd55g1_parse_dt_gpios()
1740 sensor->ext_leds_mask = 0; in vd55g1_parse_dt_gpios()
1743 ret = vd55g1_parse_dt_gpios_array(sensor, "st,leds", led_gpios, in vd55g1_parse_dt_gpios()
1749 sensor->gpios[led_gpios[i]] = VD55G1_GPIO_MODE_STROBE; in vd55g1_parse_dt_gpios()
1750 set_bit(led_gpios[i], &sensor->ext_leds_mask); in vd55g1_parse_dt_gpios()
1756 static int vd55g1_parse_dt(struct vd55g1 *sensor) in vd55g1_parse_dt() argument
1761 endpoint = fwnode_graph_get_endpoint_by_id(dev_fwnode(sensor->dev), in vd55g1_parse_dt()
1764 dev_err(sensor->dev, "Endpoint node not found\n"); in vd55g1_parse_dt()
1768 ret = vd55g1_check_csi_conf(sensor, endpoint); in vd55g1_parse_dt()
1773 return vd55g1_parse_dt_gpios(sensor); in vd55g1_parse_dt()
1776 static int vd55g1_subdev_init(struct vd55g1 *sensor) in vd55g1_subdev_init() argument
1781 sensor->sd.flags |= V4L2_SUBDEV_FL_HAS_DEVNODE; in vd55g1_subdev_init()
1782 sensor->sd.internal_ops = &vd55g1_internal_ops; in vd55g1_subdev_init()
1785 sensor->pad.flags = MEDIA_PAD_FL_SOURCE; in vd55g1_subdev_init()
1786 sensor->sd.entity.function = MEDIA_ENT_F_CAM_SENSOR; in vd55g1_subdev_init()
1787 ret = media_entity_pads_init(&sensor->sd.entity, 1, &sensor->pad); in vd55g1_subdev_init()
1789 dev_err(sensor->dev, "Failed to init media entity: %d\n", ret); in vd55g1_subdev_init()
1793 sensor->sd.state_lock = sensor->ctrl_handler.lock; in vd55g1_subdev_init()
1794 ret = v4l2_subdev_init_finalize(&sensor->sd); in vd55g1_subdev_init()
1796 dev_err(sensor->dev, "Subdev init error: %d\n", ret); in vd55g1_subdev_init()
1804 ret = vd55g1_init_ctrls(sensor); in vd55g1_subdev_init()
1806 dev_err(sensor->dev, "Controls initialization failed %d\n", in vd55g1_subdev_init()
1814 v4l2_ctrl_handler_free(sensor->sd.ctrl_handler); in vd55g1_subdev_init()
1817 media_entity_cleanup(&sensor->sd.entity); in vd55g1_subdev_init()
1821 static void vd55g1_subdev_cleanup(struct vd55g1 *sensor) in vd55g1_subdev_cleanup() argument
1823 v4l2_async_unregister_subdev(&sensor->sd); in vd55g1_subdev_cleanup()
1824 v4l2_subdev_cleanup(&sensor->sd); in vd55g1_subdev_cleanup()
1825 media_entity_cleanup(&sensor->sd.entity); in vd55g1_subdev_cleanup()
1826 v4l2_ctrl_handler_free(sensor->sd.ctrl_handler); in vd55g1_subdev_cleanup()
1829 static int vd55g1_get_regulators(struct vd55g1 *sensor) in vd55g1_get_regulators() argument
1834 sensor->supplies[i].supply = vd55g1_supply_name[i]; in vd55g1_get_regulators()
1836 return devm_regulator_bulk_get(sensor->dev, in vd55g1_get_regulators()
1838 sensor->supplies); in vd55g1_get_regulators()
1844 struct vd55g1 *sensor; in vd55g1_probe() local
1847 sensor = devm_kzalloc(dev, sizeof(*sensor), GFP_KERNEL); in vd55g1_probe()
1848 if (!sensor) in vd55g1_probe()
1850 sensor->dev = &client->dev; in vd55g1_probe()
1852 v4l2_i2c_subdev_init(&sensor->sd, client, &vd55g1_subdev_ops); in vd55g1_probe()
1854 ret = vd55g1_parse_dt(sensor); in vd55g1_probe()
1859 ret = vd55g1_get_regulators(sensor); in vd55g1_probe()
1863 sensor->xclk = devm_clk_get(dev, NULL); in vd55g1_probe()
1864 if (IS_ERR(sensor->xclk)) in vd55g1_probe()
1865 return dev_err_probe(dev, PTR_ERR(sensor->xclk), in vd55g1_probe()
1868 sensor->xclk_freq = clk_get_rate(sensor->xclk); in vd55g1_probe()
1869 ret = vd55g1_prepare_clock_tree(sensor); in vd55g1_probe()
1873 sensor->reset_gpio = devm_gpiod_get_optional(dev, "reset", in vd55g1_probe()
1875 if (IS_ERR(sensor->reset_gpio)) in vd55g1_probe()
1876 return dev_err_probe(dev, PTR_ERR(sensor->reset_gpio), in vd55g1_probe()
1879 sensor->regmap = devm_cci_regmap_init_i2c(client, 16); in vd55g1_probe()
1880 if (IS_ERR(sensor->regmap)) in vd55g1_probe()
1881 return dev_err_probe(dev, PTR_ERR(sensor->regmap), in vd55g1_probe()
1884 /* Detect if sensor is present and if its revision is supported */ in vd55g1_probe()
1889 /* Enable pm_runtime and power off the sensor */ in vd55g1_probe()
1897 ret = vd55g1_subdev_init(sensor); in vd55g1_probe()
1903 ret = v4l2_async_register_subdev(&sensor->sd); in vd55g1_probe()
1912 vd55g1_subdev_cleanup(sensor); in vd55g1_probe()
1925 struct vd55g1 *sensor = to_vd55g1(sd); in vd55g1_remove() local
1927 vd55g1_subdev_cleanup(sensor); in vd55g1_remove()