Lines Matching refs:sc401ai

142 struct sc401ai {  struct
179 #define to_sc401ai(sd) container_of(sd, struct sc401ai, subdev) argument
526 static int sc401ai_set_gain_reg(struct sc401ai *sc401ai, u32 gain) in sc401ai_set_gain_reg() argument
627 ret = sc401ai_write_reg(sc401ai->client, in sc401ai_set_gain_reg()
631 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_gain_reg()
635 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_gain_reg()
639 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_gain_reg()
678 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_set_fmt() local
682 mutex_lock(&sc401ai->mutex); in sc401ai_set_fmt()
693 mutex_unlock(&sc401ai->mutex); in sc401ai_set_fmt()
697 sc401ai->cur_mode = mode; in sc401ai_set_fmt()
699 __v4l2_ctrl_modify_range(sc401ai->hblank, h_blank, in sc401ai_set_fmt()
702 __v4l2_ctrl_modify_range(sc401ai->vblank, vblank_def, in sc401ai_set_fmt()
705 sc401ai->cur_fps = mode->max_fps; in sc401ai_set_fmt()
706 sc401ai->cur_vts = mode->vts_def; in sc401ai_set_fmt()
709 mutex_unlock(&sc401ai->mutex); in sc401ai_set_fmt()
718 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_get_fmt() local
719 const struct sc401ai_mode *mode = sc401ai->cur_mode; in sc401ai_get_fmt()
721 mutex_lock(&sc401ai->mutex); in sc401ai_get_fmt()
726 mutex_unlock(&sc401ai->mutex); in sc401ai_get_fmt()
740 mutex_unlock(&sc401ai->mutex); in sc401ai_get_fmt()
749 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_enum_mbus_code() local
753 code->code = sc401ai->cur_mode->bus_fmt; in sc401ai_enum_mbus_code()
776 static int sc401ai_enable_test_pattern(struct sc401ai *sc401ai, u32 pattern) in sc401ai_enable_test_pattern() argument
781 ret = sc401ai_read_reg(sc401ai->client, SC401AI_REG_TEST_PATTERN, in sc401ai_enable_test_pattern()
787 ret |= sc401ai_write_reg(sc401ai->client, SC401AI_REG_TEST_PATTERN, in sc401ai_enable_test_pattern()
795 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_g_frame_interval() local
796 const struct sc401ai_mode *mode = sc401ai->cur_mode; in sc401ai_g_frame_interval()
798 if (sc401ai->streaming) in sc401ai_g_frame_interval()
799 fi->interval = sc401ai->cur_fps; in sc401ai_g_frame_interval()
810 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_g_mbus_config() local
811 const struct sc401ai_mode *mode = sc401ai->cur_mode; in sc401ai_g_mbus_config()
814 val = 1 << (sc401ai->lane_num - 1) | in sc401ai_g_mbus_config()
829 static void sc401ai_get_module_inf(struct sc401ai *sc401ai, in sc401ai_get_module_inf() argument
834 strscpy(inf->base.module, sc401ai->module_name, in sc401ai_get_module_inf()
836 strscpy(inf->base.lens, sc401ai->len_name, sizeof(inf->base.lens)); in sc401ai_get_module_inf()
841 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_ioctl() local
848 sc401ai_get_module_inf(sc401ai, (struct rkmodule_inf *)arg); in sc401ai_ioctl()
853 hdr->hdr_mode = sc401ai->cur_mode->hdr_mode; in sc401ai_ioctl()
867 ret = sc401ai_write_reg(sc401ai->client, in sc401ai_ioctl()
872 ret = sc401ai_write_reg(sc401ai->client, in sc401ai_ioctl()
988 static int __sc401ai_start_stream(struct sc401ai *sc401ai) in __sc401ai_start_stream() argument
992 ret = sc401ai_write_array(sc401ai->client, sc401ai->cur_mode->reg_list); in __sc401ai_start_stream()
997 ret = __v4l2_ctrl_handler_setup(&sc401ai->ctrl_handler); in __sc401ai_start_stream()
1001 return sc401ai_write_reg(sc401ai->client, in __sc401ai_start_stream()
1007 static int __sc401ai_stop_stream(struct sc401ai *sc401ai) in __sc401ai_stop_stream() argument
1009 return sc401ai_write_reg(sc401ai->client, in __sc401ai_stop_stream()
1017 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_s_stream() local
1018 struct i2c_client *client = sc401ai->client; in sc401ai_s_stream()
1021 mutex_lock(&sc401ai->mutex); in sc401ai_s_stream()
1023 if (on == sc401ai->streaming) in sc401ai_s_stream()
1033 ret = __sc401ai_start_stream(sc401ai); in sc401ai_s_stream()
1040 __sc401ai_stop_stream(sc401ai); in sc401ai_s_stream()
1044 sc401ai->streaming = on; in sc401ai_s_stream()
1047 mutex_unlock(&sc401ai->mutex); in sc401ai_s_stream()
1054 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_s_power() local
1055 struct i2c_client *client = sc401ai->client; in sc401ai_s_power()
1058 mutex_lock(&sc401ai->mutex); in sc401ai_s_power()
1061 if (sc401ai->power_on == !!on) in sc401ai_s_power()
1071 ret = sc401ai_write_array(sc401ai->client, sc401ai_global_regs); in sc401ai_s_power()
1078 sc401ai->power_on = true; in sc401ai_s_power()
1081 sc401ai->power_on = false; in sc401ai_s_power()
1085 mutex_unlock(&sc401ai->mutex); in sc401ai_s_power()
1096 static int __sc401ai_power_on(struct sc401ai *sc401ai) in __sc401ai_power_on() argument
1100 struct device *dev = &sc401ai->client->dev; in __sc401ai_power_on()
1102 if (!IS_ERR_OR_NULL(sc401ai->pins_default)) { in __sc401ai_power_on()
1103 ret = pinctrl_select_state(sc401ai->pinctrl, in __sc401ai_power_on()
1104 sc401ai->pins_default); in __sc401ai_power_on()
1108 ret = clk_set_rate(sc401ai->xvclk, SC401AI_XVCLK_FREQ); in __sc401ai_power_on()
1111 if (clk_get_rate(sc401ai->xvclk) != SC401AI_XVCLK_FREQ) in __sc401ai_power_on()
1113 ret = clk_prepare_enable(sc401ai->xvclk); in __sc401ai_power_on()
1118 if (!IS_ERR(sc401ai->reset_gpio)) in __sc401ai_power_on()
1119 gpiod_set_value_cansleep(sc401ai->reset_gpio, 0); in __sc401ai_power_on()
1121 ret = regulator_bulk_enable(SC401AI_NUM_SUPPLIES, sc401ai->supplies); in __sc401ai_power_on()
1127 if (!IS_ERR(sc401ai->reset_gpio)) in __sc401ai_power_on()
1128 gpiod_set_value_cansleep(sc401ai->reset_gpio, 1); in __sc401ai_power_on()
1131 if (!IS_ERR(sc401ai->pwdn_gpio)) in __sc401ai_power_on()
1132 gpiod_set_value_cansleep(sc401ai->pwdn_gpio, 1); in __sc401ai_power_on()
1134 if (!IS_ERR(sc401ai->reset_gpio)) in __sc401ai_power_on()
1146 clk_disable_unprepare(sc401ai->xvclk); in __sc401ai_power_on()
1151 static void __sc401ai_power_off(struct sc401ai *sc401ai) in __sc401ai_power_off() argument
1154 struct device *dev = &sc401ai->client->dev; in __sc401ai_power_off()
1156 if (!IS_ERR(sc401ai->pwdn_gpio)) in __sc401ai_power_off()
1157 gpiod_set_value_cansleep(sc401ai->pwdn_gpio, 0); in __sc401ai_power_off()
1158 clk_disable_unprepare(sc401ai->xvclk); in __sc401ai_power_off()
1159 if (!IS_ERR(sc401ai->reset_gpio)) in __sc401ai_power_off()
1160 gpiod_set_value_cansleep(sc401ai->reset_gpio, 0); in __sc401ai_power_off()
1161 if (!IS_ERR_OR_NULL(sc401ai->pins_sleep)) { in __sc401ai_power_off()
1162 ret = pinctrl_select_state(sc401ai->pinctrl, in __sc401ai_power_off()
1163 sc401ai->pins_sleep); in __sc401ai_power_off()
1167 regulator_bulk_disable(SC401AI_NUM_SUPPLIES, sc401ai->supplies); in __sc401ai_power_off()
1174 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_runtime_resume() local
1176 return __sc401ai_power_on(sc401ai); in sc401ai_runtime_resume()
1183 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_runtime_suspend() local
1185 __sc401ai_power_off(sc401ai); in sc401ai_runtime_suspend()
1193 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_open() local
1198 mutex_lock(&sc401ai->mutex); in sc401ai_open()
1205 mutex_unlock(&sc401ai->mutex); in sc401ai_open()
1266 static void sc401ai_modify_fps_info(struct sc401ai *sc401ai) in sc401ai_modify_fps_info() argument
1268 const struct sc401ai_mode *mode = sc401ai->cur_mode; in sc401ai_modify_fps_info()
1270 sc401ai->cur_fps.denominator = mode->max_fps.denominator * mode->vts_def / in sc401ai_modify_fps_info()
1271 sc401ai->cur_vts; in sc401ai_modify_fps_info()
1276 struct sc401ai *sc401ai = container_of(ctrl->handler, in sc401ai_set_ctrl() local
1277 struct sc401ai, ctrl_handler); in sc401ai_set_ctrl()
1278 struct i2c_client *client = sc401ai->client; in sc401ai_set_ctrl()
1287 max = sc401ai->cur_mode->height + ctrl->val - 4; in sc401ai_set_ctrl()
1288 __v4l2_ctrl_modify_range(sc401ai->exposure, in sc401ai_set_ctrl()
1289 sc401ai->exposure->minimum, max, in sc401ai_set_ctrl()
1290 sc401ai->exposure->step, in sc401ai_set_ctrl()
1291 sc401ai->exposure->default_value); in sc401ai_set_ctrl()
1300 if (sc401ai->cur_mode->hdr_mode == NO_HDR) { in sc401ai_set_ctrl()
1303 ret = sc401ai_write_reg(sc401ai->client, in sc401ai_set_ctrl()
1307 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_ctrl()
1311 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_ctrl()
1318 if (sc401ai->cur_mode->hdr_mode == NO_HDR) in sc401ai_set_ctrl()
1319 ret = sc401ai_set_gain_reg(sc401ai, ctrl->val); in sc401ai_set_ctrl()
1322 ret = sc401ai_write_reg(sc401ai->client, in sc401ai_set_ctrl()
1325 (ctrl->val + sc401ai->cur_mode->height) in sc401ai_set_ctrl()
1327 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_ctrl()
1330 (ctrl->val + sc401ai->cur_mode->height) in sc401ai_set_ctrl()
1333 sc401ai->cur_vts = ctrl->val + sc401ai->cur_mode->height; in sc401ai_set_ctrl()
1334 sc401ai_modify_fps_info(sc401ai); in sc401ai_set_ctrl()
1337 ret = sc401ai_enable_test_pattern(sc401ai, ctrl->val); in sc401ai_set_ctrl()
1340 ret = sc401ai_read_reg(sc401ai->client, SC401AI_FLIP_MIRROR_REG, in sc401ai_set_ctrl()
1342 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_ctrl()
1348 ret = sc401ai_read_reg(sc401ai->client, SC401AI_FLIP_MIRROR_REG, in sc401ai_set_ctrl()
1350 ret |= sc401ai_write_reg(sc401ai->client, in sc401ai_set_ctrl()
1370 static int sc401ai_parse_of(struct sc401ai *sc401ai) in sc401ai_parse_of() argument
1372 struct device *dev = &sc401ai->client->dev; in sc401ai_parse_of()
1389 sc401ai->lane_num = rval; in sc401ai_parse_of()
1391 if (sc401ai->lane_num == 2) { in sc401ai_parse_of()
1392 sc401ai->cur_mode = &supported_modes[1]; in sc401ai_parse_of()
1393 dev_info(dev, "lane_num(%d)\n", sc401ai->lane_num); in sc401ai_parse_of()
1394 } else if (sc401ai->lane_num == 4) { in sc401ai_parse_of()
1395 sc401ai->cur_mode = &supported_modes[0]; in sc401ai_parse_of()
1396 dev_info(dev, "lane_num(%d)\n", sc401ai->lane_num); in sc401ai_parse_of()
1398 dev_err(dev, "unsupported lane_num(%d)\n", sc401ai->lane_num); in sc401ai_parse_of()
1404 static int sc401ai_initialize_controls(struct sc401ai *sc401ai) in sc401ai_initialize_controls() argument
1408 struct device *dev = &sc401ai->client->dev; in sc401ai_initialize_controls()
1415 handler = &sc401ai->ctrl_handler; in sc401ai_initialize_controls()
1416 mode = sc401ai->cur_mode; in sc401ai_initialize_controls()
1420 handler->lock = &sc401ai->mutex; in sc401ai_initialize_controls()
1422 sc401ai->link_freq = v4l2_ctrl_new_int_menu(handler, NULL, in sc401ai_initialize_controls()
1426 __v4l2_ctrl_s_ctrl(sc401ai->link_freq, mode->mipi_freq_idx); in sc401ai_initialize_controls()
1436 sc401ai->pixel_rate = v4l2_ctrl_new_std(handler, NULL, in sc401ai_initialize_controls()
1442 sc401ai->hblank = v4l2_ctrl_new_std(handler, NULL, V4L2_CID_HBLANK, in sc401ai_initialize_controls()
1444 if (sc401ai->hblank) in sc401ai_initialize_controls()
1445 sc401ai->hblank->flags |= V4L2_CTRL_FLAG_READ_ONLY; in sc401ai_initialize_controls()
1447 sc401ai->vblank = v4l2_ctrl_new_std(handler, &sc401ai_ctrl_ops, in sc401ai_initialize_controls()
1452 sc401ai->exposure = v4l2_ctrl_new_std(handler, &sc401ai_ctrl_ops, in sc401ai_initialize_controls()
1458 sc401ai->anal_gain = v4l2_ctrl_new_std(handler, &sc401ai_ctrl_ops, in sc401ai_initialize_controls()
1470 dev_err(&sc401ai->client->dev, in sc401ai_initialize_controls()
1475 sc401ai->subdev.ctrl_handler = handler; in sc401ai_initialize_controls()
1476 sc401ai->cur_fps = mode->max_fps; in sc401ai_initialize_controls()
1477 sc401ai->cur_vts = mode->vts_def; in sc401ai_initialize_controls()
1487 static int sc401ai_check_sensor_id(struct sc401ai *sc401ai, in sc401ai_check_sensor_id() argument
1490 struct device *dev = &sc401ai->client->dev; in sc401ai_check_sensor_id()
1506 static int sc401ai_configure_regulators(struct sc401ai *sc401ai) in sc401ai_configure_regulators() argument
1511 sc401ai->supplies[i].supply = sc401ai_supply_names[i]; in sc401ai_configure_regulators()
1513 return devm_regulator_bulk_get(&sc401ai->client->dev, in sc401ai_configure_regulators()
1515 sc401ai->supplies); in sc401ai_configure_regulators()
1523 struct sc401ai *sc401ai; in sc401ai_probe() local
1534 sc401ai = devm_kzalloc(dev, sizeof(*sc401ai), GFP_KERNEL); in sc401ai_probe()
1535 if (!sc401ai) in sc401ai_probe()
1540 &sc401ai->module_index); in sc401ai_probe()
1542 &sc401ai->module_facing); in sc401ai_probe()
1544 &sc401ai->module_name); in sc401ai_probe()
1546 &sc401ai->len_name); in sc401ai_probe()
1552 sc401ai->client = client; in sc401ai_probe()
1555 sc401ai->cur_mode = &supported_modes[i]; in sc401ai_probe()
1560 sc401ai->cur_mode = &supported_modes[0]; in sc401ai_probe()
1562 sc401ai->xvclk = devm_clk_get(dev, "xvclk"); in sc401ai_probe()
1563 if (IS_ERR(sc401ai->xvclk)) { in sc401ai_probe()
1568 sc401ai->reset_gpio = devm_gpiod_get(dev, "reset", GPIOD_OUT_LOW); in sc401ai_probe()
1569 if (IS_ERR(sc401ai->reset_gpio)) in sc401ai_probe()
1572 sc401ai->pwdn_gpio = devm_gpiod_get(dev, "pwdn", GPIOD_OUT_LOW); in sc401ai_probe()
1573 if (IS_ERR(sc401ai->pwdn_gpio)) in sc401ai_probe()
1576 sc401ai->pinctrl = devm_pinctrl_get(dev); in sc401ai_probe()
1577 if (!IS_ERR(sc401ai->pinctrl)) { in sc401ai_probe()
1578 sc401ai->pins_default = in sc401ai_probe()
1579 pinctrl_lookup_state(sc401ai->pinctrl, in sc401ai_probe()
1581 if (IS_ERR(sc401ai->pins_default)) in sc401ai_probe()
1584 sc401ai->pins_sleep = in sc401ai_probe()
1585 pinctrl_lookup_state(sc401ai->pinctrl, in sc401ai_probe()
1587 if (IS_ERR(sc401ai->pins_sleep)) in sc401ai_probe()
1593 ret = sc401ai_configure_regulators(sc401ai); in sc401ai_probe()
1599 ret = sc401ai_parse_of(sc401ai); in sc401ai_probe()
1603 mutex_init(&sc401ai->mutex); in sc401ai_probe()
1605 sd = &sc401ai->subdev; in sc401ai_probe()
1607 ret = sc401ai_initialize_controls(sc401ai); in sc401ai_probe()
1611 ret = __sc401ai_power_on(sc401ai); in sc401ai_probe()
1615 ret = sc401ai_check_sensor_id(sc401ai, client); in sc401ai_probe()
1625 sc401ai->pad.flags = MEDIA_PAD_FL_SOURCE; in sc401ai_probe()
1627 ret = media_entity_pads_init(&sd->entity, 1, &sc401ai->pad); in sc401ai_probe()
1633 if (strcmp(sc401ai->module_facing, "back") == 0) in sc401ai_probe()
1639 sc401ai->module_index, facing, in sc401ai_probe()
1658 __sc401ai_power_off(sc401ai); in sc401ai_probe()
1660 v4l2_ctrl_handler_free(&sc401ai->ctrl_handler); in sc401ai_probe()
1662 mutex_destroy(&sc401ai->mutex); in sc401ai_probe()
1670 struct sc401ai *sc401ai = to_sc401ai(sd); in sc401ai_remove() local
1676 v4l2_ctrl_handler_free(&sc401ai->ctrl_handler); in sc401ai_remove()
1677 mutex_destroy(&sc401ai->mutex); in sc401ai_remove()
1681 __sc401ai_power_off(sc401ai); in sc401ai_remove()