Lines Matching full:sensor

99 /* The VD56G3 is a portrait image sensor with native resolution of 1124x1364. */
192 * Sensor support 8bits and 10bits output in both variants
263 static int vd56g3_poll_reg(struct vd56g3 *sensor, u32 reg, u8 poll_val, in vd56g3_poll_reg() argument
276 ret = regmap_read_poll_timeout(sensor->regmap, CCI_REG_ADDR(reg), val, in vd56g3_poll_reg()
286 static int vd56g3_wait_state(struct vd56g3 *sensor, int state, int *err) in vd56g3_wait_state() argument
288 return vd56g3_poll_reg(sensor, VD56G3_REG_SYSTEM_FSM, state, err); in vd56g3_wait_state()
350 static int vd56g3_read_expo_cluster(struct vd56g3 *sensor, bool force_cur_val) in vd56g3_read_expo_cluster() argument
362 cci_read(sensor->regmap, VD56G3_REG_APPLIED_COARSE_EXPOSURE, &exposure, in vd56g3_read_expo_cluster()
364 cci_read(sensor->regmap, VD56G3_REG_APPLIED_ANALOG_GAIN, &again, &ret); in vd56g3_read_expo_cluster()
365 cci_read(sensor->regmap, VD56G3_REG_APPLIED_DIGITAL_GAIN, &dgain, &ret); in vd56g3_read_expo_cluster()
370 sensor->expo_ctrl->cur.val = exposure; in vd56g3_read_expo_cluster()
371 sensor->again_ctrl->cur.val = again; in vd56g3_read_expo_cluster()
372 sensor->dgain_ctrl->cur.val = dgain; in vd56g3_read_expo_cluster()
374 sensor->expo_ctrl->val = exposure; in vd56g3_read_expo_cluster()
375 sensor->again_ctrl->val = again; in vd56g3_read_expo_cluster()
376 sensor->dgain_ctrl->val = dgain; in vd56g3_read_expo_cluster()
382 static int vd56g3_update_patgen(struct vd56g3 *sensor, u32 patgen_index) in vd56g3_update_patgen() argument
396 cci_write(sensor->regmap, VD56G3_REG_DUSTER_CTRL, duster, &ret); in vd56g3_update_patgen()
397 cci_write(sensor->regmap, VD56G3_REG_DARKCAL_CTRL, darkcal, &ret); in vd56g3_update_patgen()
398 cci_write(sensor->regmap, VD56G3_REG_PATGEN_CTRL, patgen, &ret); in vd56g3_update_patgen()
403 static int vd56g3_update_expo_cluster(struct vd56g3 *sensor, bool is_auto) in vd56g3_update_expo_cluster() argument
408 if (sensor->ae_ctrl->is_new) in vd56g3_update_expo_cluster()
409 cci_write(sensor->regmap, VD56G3_REG_EXP_MODE, expo_state, in vd56g3_update_expo_cluster()
413 if (is_auto && sensor->ae_ctrl->is_new) { in vd56g3_update_expo_cluster()
414 cci_write(sensor->regmap, in vd56g3_update_expo_cluster()
416 sensor->expo_ctrl->val, &ret); in vd56g3_update_expo_cluster()
417 cci_write(sensor->regmap, VD56G3_REG_AE_COLDSTART_ANALOG_GAIN, in vd56g3_update_expo_cluster()
418 sensor->again_ctrl->val, &ret); in vd56g3_update_expo_cluster()
419 cci_write(sensor->regmap, VD56G3_REG_AE_COLDSTART_DIGITAL_GAIN, in vd56g3_update_expo_cluster()
420 sensor->dgain_ctrl->val, &ret); in vd56g3_update_expo_cluster()
424 if (!is_auto && sensor->expo_ctrl->is_new) in vd56g3_update_expo_cluster()
425 cci_write(sensor->regmap, VD56G3_REG_MANUAL_COARSE_EXPOSURE, in vd56g3_update_expo_cluster()
426 sensor->expo_ctrl->val, &ret); in vd56g3_update_expo_cluster()
428 if (!is_auto && sensor->again_ctrl->is_new) in vd56g3_update_expo_cluster()
429 cci_write(sensor->regmap, VD56G3_REG_MANUAL_ANALOG_GAIN, in vd56g3_update_expo_cluster()
430 sensor->again_ctrl->val, &ret); in vd56g3_update_expo_cluster()
432 if (!is_auto && sensor->dgain_ctrl->is_new) { in vd56g3_update_expo_cluster()
433 cci_write(sensor->regmap, VD56G3_REG_MANUAL_DIGITAL_GAIN_CH0, in vd56g3_update_expo_cluster()
434 sensor->dgain_ctrl->val, &ret); in vd56g3_update_expo_cluster()
435 cci_write(sensor->regmap, VD56G3_REG_MANUAL_DIGITAL_GAIN_CH1, in vd56g3_update_expo_cluster()
436 sensor->dgain_ctrl->val, &ret); in vd56g3_update_expo_cluster()
437 cci_write(sensor->regmap, VD56G3_REG_MANUAL_DIGITAL_GAIN_CH2, in vd56g3_update_expo_cluster()
438 sensor->dgain_ctrl->val, &ret); in vd56g3_update_expo_cluster()
439 cci_write(sensor->regmap, VD56G3_REG_MANUAL_DIGITAL_GAIN_CH3, in vd56g3_update_expo_cluster()
440 sensor->dgain_ctrl->val, &ret); in vd56g3_update_expo_cluster()
446 static int vd56g3_lock_exposure(struct vd56g3 *sensor, u32 lock_val) in vd56g3_lock_exposure() argument
451 if (sensor->ae_ctrl->val == V4L2_EXPOSURE_AUTO) in vd56g3_lock_exposure()
452 return cci_write(sensor->regmap, VD56G3_REG_EXP_MODE, in vd56g3_lock_exposure()
458 static int vd56g3_write_gpiox(struct vd56g3 *sensor, unsigned long gpio_mask) in vd56g3_write_gpiox() argument
465 gpio_val = sensor->gpios[io]; in vd56g3_write_gpiox()
468 sensor->led_ctrl->val == V4L2_FLASH_LED_MODE_NONE) in vd56g3_write_gpiox()
471 cci_write(sensor->regmap, VD56G3_REG_GPIO_0_CTRL + io, gpio_val, in vd56g3_write_gpiox()
480 struct vd56g3 *sensor = ctrl_to_vd56g3(ctrl); in vd56g3_g_volatile_ctrl() local
484 if (!pm_runtime_get_if_in_use(sensor->dev)) in vd56g3_g_volatile_ctrl()
489 ret = vd56g3_read_expo_cluster(sensor, false); in vd56g3_g_volatile_ctrl()
496 pm_runtime_put_autosuspend(sensor->dev); in vd56g3_g_volatile_ctrl()
503 struct vd56g3 *sensor = ctrl_to_vd56g3(ctrl); in vd56g3_s_ctrl() local
512 state = v4l2_subdev_get_locked_active_state(&sensor->sd); in vd56g3_s_ctrl()
523 ret = __v4l2_ctrl_modify_range(sensor->expo_ctrl, in vd56g3_s_ctrl()
530 __v4l2_ctrl_grab(sensor->ae_lock_ctrl, !is_auto); in vd56g3_s_ctrl()
531 __v4l2_ctrl_grab(sensor->ae_bias_ctrl, !is_auto); in vd56g3_s_ctrl()
541 if (!pm_runtime_get_if_in_use(sensor->dev)) in vd56g3_s_ctrl()
546 ret = cci_write(sensor->regmap, VD56G3_REG_ORIENTATION, in vd56g3_s_ctrl()
547 sensor->hflip_ctrl->val | in vd56g3_s_ctrl()
548 (sensor->vflip_ctrl->val << 1), in vd56g3_s_ctrl()
552 ret = vd56g3_update_patgen(sensor, ctrl->val); in vd56g3_s_ctrl()
555 ret = vd56g3_update_expo_cluster(sensor, is_auto); in vd56g3_s_ctrl()
558 ret = vd56g3_lock_exposure(sensor, ctrl->val); in vd56g3_s_ctrl()
564 ret = cci_write(sensor->regmap, VD56G3_REG_AE_COMPENSATION, in vd56g3_s_ctrl()
568 ret = cci_write(sensor->regmap, VD56G3_REG_FRAME_LENGTH, in vd56g3_s_ctrl()
572 ret = vd56g3_write_gpiox(sensor, sensor->ext_leds_mask); in vd56g3_s_ctrl()
579 pm_runtime_put_autosuspend(sensor->dev); in vd56g3_s_ctrl()
589 static int vd56g3_update_controls(struct vd56g3 *sensor) in vd56g3_update_controls() argument
599 state = v4l2_subdev_get_locked_active_state(&sensor->sd); in vd56g3_update_controls()
609 ret = __v4l2_ctrl_modify_range(sensor->hblank_ctrl, hblank, hblank, 1, in vd56g3_update_controls()
614 ret = __v4l2_ctrl_modify_range(sensor->vblank_ctrl, vblank_min, in vd56g3_update_controls()
619 ret = __v4l2_ctrl_s_ctrl(sensor->vblank_ctrl, vblank); in vd56g3_update_controls()
623 ret = __v4l2_ctrl_modify_range(sensor->expo_ctrl, VD56G3_EXPOSURE_MIN, in vd56g3_update_controls()
628 return __v4l2_ctrl_s_ctrl(sensor->expo_ctrl, VD56G3_EXPOSURE_DEFAULT); in vd56g3_update_controls()
631 static int vd56g3_init_controls(struct vd56g3 *sensor) in vd56g3_init_controls() argument
634 struct v4l2_ctrl_handler *hdl = &sensor->ctrl_handler; in vd56g3_init_controls()
642 sensor->hflip_ctrl = in vd56g3_init_controls()
644 if (sensor->hflip_ctrl) in vd56g3_init_controls()
645 sensor->hflip_ctrl->flags |= V4L2_CTRL_FLAG_MODIFY_LAYOUT; in vd56g3_init_controls()
647 sensor->vflip_ctrl = in vd56g3_init_controls()
649 if (sensor->vflip_ctrl) in vd56g3_init_controls()
650 sensor->vflip_ctrl->flags |= V4L2_CTRL_FLAG_MODIFY_LAYOUT; in vd56g3_init_controls()
652 sensor->patgen_ctrl = in vd56g3_init_controls()
659 (sensor->nb_of_lane == 2) ? in vd56g3_init_controls()
666 sensor->pixel_clock, sensor->pixel_clock, 1, in vd56g3_init_controls()
667 sensor->pixel_clock); in vd56g3_init_controls()
671 sensor->ae_ctrl = v4l2_ctrl_new_std_menu(hdl, ops, in vd56g3_init_controls()
676 sensor->ae_lock_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_3A_LOCK, 0, in vd56g3_init_controls()
679 sensor->ae_bias_ctrl = in vd56g3_init_controls()
690 sensor->again_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_ANALOGUE_GAIN, in vd56g3_init_controls()
692 sensor->dgain_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_DIGITAL_GAIN, in vd56g3_init_controls()
700 sensor->expo_ctrl = v4l2_ctrl_new_std(hdl, ops, V4L2_CID_EXPOSURE, in vd56g3_init_controls()
704 sensor->hblank_ctrl = in vd56g3_init_controls()
706 if (sensor->hblank_ctrl) in vd56g3_init_controls()
707 sensor->hblank_ctrl->flags |= V4L2_CTRL_FLAG_READ_ONLY; in vd56g3_init_controls()
708 sensor->vblank_ctrl = in vd56g3_init_controls()
712 if (sensor->ext_leds_mask) in vd56g3_init_controls()
713 sensor->led_ctrl = in vd56g3_init_controls()
724 v4l2_ctrl_cluster(2, &sensor->hflip_ctrl); in vd56g3_init_controls()
725 v4l2_ctrl_auto_cluster(4, &sensor->ae_ctrl, V4L2_EXPOSURE_MANUAL, true); in vd56g3_init_controls()
728 ret = v4l2_fwnode_device_parse(sensor->dev, &fwnode_props); in vd56g3_init_controls()
736 sensor->sd.ctrl_handler = hdl; in vd56g3_init_controls()
755 static u32 vd56g3_get_mbus_code(struct vd56g3 *sensor, u32 code) in vd56g3_get_mbus_code() argument
771 if (sensor->is_mono) in vd56g3_get_mbus_code()
774 j = 1 + (sensor->hflip_ctrl->val ? 1 : 0) + in vd56g3_get_mbus_code()
775 (sensor->vflip_ctrl->val ? 2 : 0); in vd56g3_get_mbus_code()
784 struct vd56g3 *sensor = to_vd56g3(sd); in vd56g3_enum_mbus_code() local
790 vd56g3_get_mbus_code(sensor, vd56g3_mbus_codes[code->index][0]); in vd56g3_enum_mbus_code()
810 static void vd56g3_update_img_pad_format(struct vd56g3 *sensor, in vd56g3_update_img_pad_format() argument
817 mbus_fmt->code = vd56g3_get_mbus_code(sensor, mbus_code); in vd56g3_update_img_pad_format()
829 struct vd56g3 *sensor = to_vd56g3(sd); in vd56g3_set_pad_fmt() local
839 vd56g3_update_img_pad_format(sensor, new_mode, sd_fmt->format.code, in vd56g3_set_pad_fmt()
855 return vd56g3_update_controls(sensor); in vd56g3_set_pad_fmt()
907 struct vd56g3 *sensor = to_vd56g3(sd); in vd56g3_enable_streams() local
911 unsigned int csi_mbps = ((sensor->nb_of_lane == 2) ? in vd56g3_enable_streams()
918 ret = pm_runtime_resume_and_get(sensor->dev); in vd56g3_enable_streams()
923 cci_write(sensor->regmap, VD56G3_REG_EXT_CLOCK, sensor->xclk_freq, in vd56g3_enable_streams()
925 cci_write(sensor->regmap, VD56G3_REG_CLK_PLL_PREDIV, sensor->pll_prediv, in vd56g3_enable_streams()
927 cci_write(sensor->regmap, VD56G3_REG_CLK_SYS_PLL_MULT, sensor->pll_mult, in vd56g3_enable_streams()
931 cci_write(sensor->regmap, VD56G3_REG_FORMAT_CTRL, in vd56g3_enable_streams()
933 cci_write(sensor->regmap, VD56G3_REG_OIF_CTRL, sensor->oif_ctrl, &ret); in vd56g3_enable_streams()
934 cci_write(sensor->regmap, VD56G3_REG_OIF_CSI_BITRATE, csi_mbps, &ret); in vd56g3_enable_streams()
935 cci_write(sensor->regmap, VD56G3_REG_OIF_IMG_CTRL, in vd56g3_enable_streams()
937 cci_write(sensor->regmap, VD56G3_REG_ISL_ENABLE, 0, &ret); in vd56g3_enable_streams()
949 cci_write(sensor->regmap, VD56G3_REG_READOUT_CTRL, binning, &ret); in vd56g3_enable_streams()
952 cci_write(sensor->regmap, VD56G3_REG_Y_START, crop->top, &ret); in vd56g3_enable_streams()
953 cci_write(sensor->regmap, VD56G3_REG_Y_END, in vd56g3_enable_streams()
955 cci_write(sensor->regmap, VD56G3_REG_OUT_ROI_X_START, crop->left, &ret); in vd56g3_enable_streams()
956 cci_write(sensor->regmap, VD56G3_REG_OUT_ROI_X_END, in vd56g3_enable_streams()
958 cci_write(sensor->regmap, VD56G3_REG_OUT_ROI_Y_START, 0, &ret); in vd56g3_enable_streams()
959 cci_write(sensor->regmap, VD56G3_REG_OUT_ROI_Y_END, crop->height - 1, in vd56g3_enable_streams()
961 cci_write(sensor->regmap, VD56G3_REG_AE_ROI_START_H, crop->left, &ret); in vd56g3_enable_streams()
962 cci_write(sensor->regmap, VD56G3_REG_AE_ROI_END_H, in vd56g3_enable_streams()
964 cci_write(sensor->regmap, VD56G3_REG_AE_ROI_START_V, 0, &ret); in vd56g3_enable_streams()
965 cci_write(sensor->regmap, VD56G3_REG_AE_ROI_END_V, crop->height - 1, in vd56g3_enable_streams()
971 ret = vd56g3_write_gpiox(sensor, GENMASK(VD56G3_NB_GPIOS - 1, 0)); in vd56g3_enable_streams()
976 ret = __v4l2_ctrl_handler_setup(&sensor->ctrl_handler); in vd56g3_enable_streams()
981 cci_write(sensor->regmap, VD56G3_REG_STBY, VD56G3_CMD_START_STREAM, in vd56g3_enable_streams()
983 vd56g3_poll_reg(sensor, VD56G3_REG_STBY, VD56G3_CMD_ACK, &ret); in vd56g3_enable_streams()
984 vd56g3_wait_state(sensor, VD56G3_SYSTEM_FSM_STREAMING, &ret); in vd56g3_enable_streams()
989 __v4l2_ctrl_grab(sensor->hflip_ctrl, true); in vd56g3_enable_streams()
990 __v4l2_ctrl_grab(sensor->vflip_ctrl, true); in vd56g3_enable_streams()
991 __v4l2_ctrl_grab(sensor->patgen_ctrl, true); in vd56g3_enable_streams()
996 dev_err(sensor->dev, "Failed to start streaming\n"); in vd56g3_enable_streams()
997 pm_runtime_put_sync(sensor->dev); in vd56g3_enable_streams()
1006 struct vd56g3 *sensor = to_vd56g3(sd); in vd56g3_disable_streams() local
1010 ret = vd56g3_read_expo_cluster(sensor, true); in vd56g3_disable_streams()
1012 cci_write(sensor->regmap, VD56G3_REG_STREAMING, VD56G3_CMD_STOP_STREAM, in vd56g3_disable_streams()
1014 vd56g3_poll_reg(sensor, VD56G3_REG_STREAMING, VD56G3_CMD_ACK, &ret); in vd56g3_disable_streams()
1015 vd56g3_wait_state(sensor, VD56G3_SYSTEM_FSM_SW_STBY, &ret); in vd56g3_disable_streams()
1018 __v4l2_ctrl_grab(sensor->hflip_ctrl, false); in vd56g3_disable_streams()
1019 __v4l2_ctrl_grab(sensor->vflip_ctrl, false); in vd56g3_disable_streams()
1020 __v4l2_ctrl_grab(sensor->patgen_ctrl, false); in vd56g3_disable_streams()
1022 pm_runtime_put_autosuspend(sensor->dev); in vd56g3_disable_streams()
1079 struct vd56g3 *sensor = to_vd56g3(sd); in vd56g3_power_on() local
1083 ret = regulator_bulk_enable(ARRAY_SIZE(sensor->supplies), in vd56g3_power_on()
1084 sensor->supplies); in vd56g3_power_on()
1090 ret = clk_prepare_enable(sensor->xclk); in vd56g3_power_on()
1096 gpiod_set_value_cansleep(sensor->reset_gpio, 0); in vd56g3_power_on()
1098 ret = vd56g3_wait_state(sensor, VD56G3_SYSTEM_FSM_READY_TO_BOOT, NULL); in vd56g3_power_on()
1100 dev_err(dev, "Sensor reset failed: %d\n", ret); in vd56g3_power_on()
1104 /* boot sensor */ in vd56g3_power_on()
1105 cci_write(sensor->regmap, VD56G3_REG_BOOT, VD56G3_CMD_BOOT, &ret); in vd56g3_power_on()
1106 vd56g3_poll_reg(sensor, VD56G3_REG_BOOT, VD56G3_CMD_ACK, &ret); in vd56g3_power_on()
1107 vd56g3_wait_state(sensor, VD56G3_SYSTEM_FSM_SW_STBY, &ret); in vd56g3_power_on()
1109 dev_err(dev, "Sensor boot failed: %d\n", ret); in vd56g3_power_on()
1116 gpiod_set_value_cansleep(sensor->reset_gpio, 1); in vd56g3_power_on()
1117 clk_disable_unprepare(sensor->xclk); in vd56g3_power_on()
1119 regulator_bulk_disable(ARRAY_SIZE(sensor->supplies), sensor->supplies); in vd56g3_power_on()
1127 struct vd56g3 *sensor = to_vd56g3(sd); in vd56g3_power_off() local
1129 gpiod_set_value_cansleep(sensor->reset_gpio, 1); in vd56g3_power_off()
1130 clk_disable_unprepare(sensor->xclk); in vd56g3_power_off()
1131 regulator_bulk_disable(ARRAY_SIZE(sensor->supplies), sensor->supplies); in vd56g3_power_off()
1144 static int vd56g3_check_csi_conf(struct vd56g3 *sensor, in vd56g3_check_csi_conf() argument
1161 dev_err(sensor->dev, "Invalid data lane number: %d\n", n_lanes); in vd56g3_check_csi_conf()
1165 sensor->nb_of_lane = n_lanes; in vd56g3_check_csi_conf()
1169 dev_err(sensor->dev, "Clock lane must be mapped to lane 0\n"); in vd56g3_check_csi_conf()
1186 sensor->oif_ctrl = n_lanes | in vd56g3_check_csi_conf()
1195 dev_err(sensor->dev, "link-frequency not found in DT\n"); in vd56g3_check_csi_conf()
1203 dev_err(sensor->dev, "Link frequency not supported: %lld\n", in vd56g3_check_csi_conf()
1215 static int vd56g3_parse_dt_gpios_array(struct vd56g3 *sensor, char *prop_name, in vd56g3_parse_dt_gpios_array() argument
1218 struct device *dev = sensor->dev; in vd56g3_parse_dt_gpios_array()
1250 static int vd56g3_parse_dt_gpios(struct vd56g3 *sensor) in vd56g3_parse_dt_gpios() argument
1259 sensor->gpios[i] = VD56G3_GPIOX_GPIO_IN; in vd56g3_parse_dt_gpios()
1260 sensor->ext_leds_mask = 0; in vd56g3_parse_dt_gpios()
1263 ret = vd56g3_parse_dt_gpios_array(sensor, "st,leds", led_gpios, in vd56g3_parse_dt_gpios()
1268 sensor->gpios[led_gpios[i]] = VD56G3_GPIOX_STROBE_MODE; in vd56g3_parse_dt_gpios()
1269 set_bit(led_gpios[i], &sensor->ext_leds_mask); in vd56g3_parse_dt_gpios()
1275 static int vd56g3_parse_dt(struct vd56g3 *sensor) in vd56g3_parse_dt() argument
1280 endpoint = fwnode_graph_get_endpoint_by_id(dev_fwnode(sensor->dev), 0, in vd56g3_parse_dt()
1283 dev_err(sensor->dev, "Endpoint node not found\n"); in vd56g3_parse_dt()
1287 ret = vd56g3_check_csi_conf(sensor, endpoint); in vd56g3_parse_dt()
1292 return vd56g3_parse_dt_gpios(sensor); in vd56g3_parse_dt()
1295 static int vd56g3_get_regulators(struct vd56g3 *sensor) in vd56g3_get_regulators() argument
1299 for (i = 0; i < ARRAY_SIZE(sensor->supplies); i++) in vd56g3_get_regulators()
1300 sensor->supplies[i].supply = vd56g3_supply_names[i]; in vd56g3_get_regulators()
1302 return devm_regulator_bulk_get(sensor->dev, in vd56g3_get_regulators()
1303 ARRAY_SIZE(sensor->supplies), in vd56g3_get_regulators()
1304 sensor->supplies); in vd56g3_get_regulators()
1307 static int vd56g3_prepare_clock_tree(struct vd56g3 *sensor) in vd56g3_prepare_clock_tree() argument
1314 if (sensor->xclk_freq < VD56G3_XCLK_FREQ_MIN || in vd56g3_prepare_clock_tree()
1315 sensor->xclk_freq > VD56G3_XCLK_FREQ_MAX) { in vd56g3_prepare_clock_tree()
1316 dev_err(sensor->dev, in vd56g3_prepare_clock_tree()
1318 sensor->xclk_freq / HZ_PER_MHZ); in vd56g3_prepare_clock_tree()
1324 sensor->pll_prediv = predivs[i]; in vd56g3_prepare_clock_tree()
1325 if (sensor->xclk_freq / sensor->pll_prediv < 12 * HZ_PER_MHZ) in vd56g3_prepare_clock_tree()
1330 sensor->pll_mult = (VD56G3_TARGET_PLL * sensor->pll_prediv + in vd56g3_prepare_clock_tree()
1331 sensor->xclk_freq / 2) / in vd56g3_prepare_clock_tree()
1332 sensor->xclk_freq; in vd56g3_prepare_clock_tree()
1333 pll_out = sensor->xclk_freq * sensor->pll_mult / sensor->pll_prediv; in vd56g3_prepare_clock_tree()
1336 sensor->pixel_clock = pll_out / VD56G3_VT_CLOCK_DIV; in vd56g3_prepare_clock_tree()
1341 static int vd56g3_detect(struct vd56g3 *sensor) in vd56g3_detect() argument
1343 struct device *dev = sensor->dev; in vd56g3_detect()
1352 ret = cci_read(sensor->regmap, VD56G3_REG_MODEL_ID, &model_id, NULL); in vd56g3_detect()
1357 dev_err(dev, "Unsupported sensor id: %x\n", (u16)model_id); in vd56g3_detect()
1361 ret = cci_read(sensor->regmap, VD56G3_REG_REVISION, &device_revision, in vd56g3_detect()
1371 ret = cci_read(sensor->regmap, VD56G3_REG_OPTICAL_REVISION, in vd56g3_detect()
1376 sensor->is_mono = in vd56g3_detect()
1378 if ((sensor->is_mono && model == VD56G3_MODEL_VD66GY) || in vd56g3_detect()
1379 (!sensor->is_mono && model == VD56G3_MODEL_VD56G3)) { in vd56g3_detect()
1380 dev_err(dev, "Found %s sensor, while %s model is defined in DT\n", in vd56g3_detect()
1381 (sensor->is_mono) ? "Mono" : "Bayer", in vd56g3_detect()
1389 static int vd56g3_subdev_init(struct vd56g3 *sensor) in vd56g3_subdev_init() argument
1395 sensor->sd.internal_ops = &vd56g3_internal_ops; in vd56g3_subdev_init()
1396 sensor->sd.flags |= V4L2_SUBDEV_FL_HAS_DEVNODE; in vd56g3_subdev_init()
1397 sensor->sd.entity.ops = &vd56g3_subdev_entity_ops; in vd56g3_subdev_init()
1400 sensor->pad.flags = MEDIA_PAD_FL_SOURCE; in vd56g3_subdev_init()
1401 sensor->sd.entity.function = MEDIA_ENT_F_CAM_SENSOR; in vd56g3_subdev_init()
1402 ret = media_entity_pads_init(&sensor->sd.entity, 1, &sensor->pad); in vd56g3_subdev_init()
1404 dev_err(sensor->dev, "Failed to init media entity: %d\n", ret); in vd56g3_subdev_init()
1409 ret = vd56g3_init_controls(sensor); in vd56g3_subdev_init()
1411 dev_err(sensor->dev, "Controls initialization failed: %d\n", in vd56g3_subdev_init()
1417 sensor->sd.state_lock = sensor->ctrl_handler.lock; in vd56g3_subdev_init()
1418 ret = v4l2_subdev_init_finalize(&sensor->sd); in vd56g3_subdev_init()
1420 dev_err(sensor->dev, "Subdev init failed: %d\n", ret); in vd56g3_subdev_init()
1425 state = v4l2_subdev_lock_and_get_active_state(&sensor->sd); in vd56g3_subdev_init()
1426 ret = vd56g3_update_controls(sensor); in vd56g3_subdev_init()
1429 dev_err(sensor->dev, "Controls update failed: %d\n", ret); in vd56g3_subdev_init()
1436 v4l2_ctrl_handler_free(sensor->sd.ctrl_handler); in vd56g3_subdev_init()
1439 media_entity_cleanup(&sensor->sd.entity); in vd56g3_subdev_init()
1444 static void vd56g3_subdev_cleanup(struct vd56g3 *sensor) in vd56g3_subdev_cleanup() argument
1446 v4l2_async_unregister_subdev(&sensor->sd); in vd56g3_subdev_cleanup()
1447 v4l2_subdev_cleanup(&sensor->sd); in vd56g3_subdev_cleanup()
1448 media_entity_cleanup(&sensor->sd.entity); in vd56g3_subdev_cleanup()
1449 v4l2_ctrl_handler_free(sensor->sd.ctrl_handler); in vd56g3_subdev_cleanup()
1455 struct vd56g3 *sensor; in vd56g3_probe() local
1458 sensor = devm_kzalloc(dev, sizeof(*sensor), GFP_KERNEL); in vd56g3_probe()
1459 if (!sensor) in vd56g3_probe()
1462 v4l2_i2c_subdev_init(&sensor->sd, client, &vd56g3_subdev_ops); in vd56g3_probe()
1463 sensor->dev = dev; in vd56g3_probe()
1465 ret = vd56g3_parse_dt(sensor); in vd56g3_probe()
1470 ret = vd56g3_get_regulators(sensor); in vd56g3_probe()
1474 sensor->xclk = devm_clk_get(dev, NULL); in vd56g3_probe()
1475 if (IS_ERR(sensor->xclk)) in vd56g3_probe()
1476 return dev_err_probe(dev, PTR_ERR(sensor->xclk), in vd56g3_probe()
1478 sensor->xclk_freq = clk_get_rate(sensor->xclk); in vd56g3_probe()
1479 ret = vd56g3_prepare_clock_tree(sensor); in vd56g3_probe()
1483 sensor->reset_gpio = devm_gpiod_get_optional(dev, "reset", in vd56g3_probe()
1485 if (IS_ERR(sensor->reset_gpio)) in vd56g3_probe()
1486 return dev_err_probe(dev, PTR_ERR(sensor->reset_gpio), in vd56g3_probe()
1489 sensor->regmap = devm_cci_regmap_init_i2c(client, 16); in vd56g3_probe()
1490 if (IS_ERR(sensor->regmap)) in vd56g3_probe()
1491 return dev_err_probe(dev, PTR_ERR(sensor->regmap), in vd56g3_probe()
1497 return dev_err_probe(dev, ret, "Sensor power on failed\n"); in vd56g3_probe()
1499 /* Enable PM runtime with autosuspend (sensor being ON, set active) */ in vd56g3_probe()
1507 ret = vd56g3_detect(sensor); in vd56g3_probe()
1509 dev_err(dev, "Sensor detect failed: %d\n", ret); in vd56g3_probe()
1514 ret = vd56g3_subdev_init(sensor); in vd56g3_probe()
1520 ret = v4l2_async_register_subdev(&sensor->sd); in vd56g3_probe()
1526 /* Sensor could now be powered off (after the autosuspend delay) */ in vd56g3_probe()
1529 dev_dbg(dev, "Successfully probe %s sensor\n", in vd56g3_probe()
1530 (sensor->is_mono) ? "vd56g3" : "vd66gy"); in vd56g3_probe()
1535 vd56g3_subdev_cleanup(sensor); in vd56g3_probe()
1548 struct vd56g3 *sensor = to_vd56g3(sd); in vd56g3_remove() local
1550 vd56g3_subdev_cleanup(sensor); in vd56g3_remove()
1552 pm_runtime_disable(sensor->dev); in vd56g3_remove()
1553 if (!pm_runtime_status_suspended(sensor->dev)) in vd56g3_remove()
1554 vd56g3_power_off(sensor->dev); in vd56g3_remove()
1555 pm_runtime_set_suspended(sensor->dev); in vd56g3_remove()
1556 pm_runtime_dont_use_autosuspend(sensor->dev); in vd56g3_remove()
1581 MODULE_DESCRIPTION("ST VD56G3 sensor driver");