\r
ois = (struct fimc_is_ois *)v4l2_get_subdevdata(subdev);\r
if(!ois) {\r
- err("%s, ois subdev is NULL", __func__);\r
+ err("%s: ois subdev is NULL", __func__);\r
ret = -EINVAL;\r
return ret;\r
}\r
ret = fimc_is_ois_read(ois->client, MOT_BU24218_REG_FW_VERSION + 3, &version[3]);\r
check_result(ret);\r
\r
- info("%s: fw version:%d, %d, %d, %d", __func__, version[0], version[1], version[2], version[3]);\r
+ info("%s: version %d %d %d %d", __func__, version[0], version[1], version[2], version[3]);\r
*result = version[0] | (version[1] << 8) | (version[2] << 16) | (version[3] << 24);\r
\r
return 0;\r
}\r
\r
\r
-int fimc_is_factory_ois_get_hea(struct v4l2_subdev *subdev, uint32_t *result)\r
+int fimc_is_factory_ois_get_hea(struct v4l2_subdev *subdev, struct fimc_is_ois_hea_parameters *result)\r
{\r
int ret = 0;\r
- char data[4] = {0, 0, 0, 0};\r
+ uint32_t data[4] = {0, 0, 0, 0};\r
struct fimc_is_ois *ois = NULL;\r
\r
FIMC_BUG(!subdev);\r
\r
ois = (struct fimc_is_ois *)v4l2_get_subdevdata(subdev);\r
if(!ois) {\r
- err("%s, ois subdev is NULL", __func__);\r
+ err("%s: ois subdev is NULL", __func__);\r
ret = -EINVAL;\r
return ret;\r
}\r
WARN_ON(!ois);\r
\r
// 1. change to calibration mode\r
- ret = fimc_is_factory_ois_poll(ois->client, MOT_BU24218_REG_STATUS, 0x01);\r
+ ret = fimc_is_factory_ois_calibration_mode(ois->client);\r
check_result(ret);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_MODE, 0x01);\r
- ret = fimc_is_factory_ois_poll(ois->client, MOT_BU24218_REG_STATUS, 0x01);\r
+ usleep_range(500,500);\r
+ \r
+ // 2. set to zero position\r
+ ret = fimc_is_factory_ois_set_zero_pos(ois->client);\r
check_result(ret);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_MODE, 0x00);\r
- ret = fimc_is_factory_ois_poll(ois->client, MOT_BU24218_REG_STATUS, 0x01);\r
+ usleep_range(20000,20000);\r
+ \r
+ // 3. set x max position and read ADC\r
+ ret = fimc_is_factory_ois_set_x_pos(ois->client, MOT_BU24218_VCM_DRV_MAX_HI, MOT_BU24218_VCM_DRV_MAX_LO);\r
check_result(ret);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_MODE, 0x04);\r
- ret = fimc_is_factory_ois_poll(ois->client, MOT_BU24218_REG_STATUS, 0x01);\r
+ usleep_range(20000,20000);\r
+ ret = fimc_is_factory_ois_get_x_adc(ois->client,&data[0]);\r
check_result(ret);\r
- usleep_range(500, 500);\r
-\r
- // 2. set max postion\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_XCH, (uint8_t) MOT_BU24218_VCM_DRV_MAX_HI);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_XCH + 1, (uint8_t) MOT_BU24218_VCM_DRV_MAX_LO);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_YCH, (uint8_t) MOT_BU24218_VCM_DRV_MAX_HI);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_YCH + 1, (uint8_t) MOT_BU24218_VCM_DRV_MAX_LO);\r
- usleep_range(200, 200);\r
-\r
- // 3. check status reg\r
- ret = fimc_is_factory_ois_poll(ois->client, MOT_BU24218_REG_STATUS, 0x01);\r
+ \r
+ // 4. set x min position and read ADC\r
+ ret = fimc_is_factory_ois_set_x_pos(ois->client, MOT_BU24218_VCM_DRV_MIN_HI, MOT_BU24218_VCM_DRV_MIN_LO);\r
check_result(ret);\r
-\r
- // 4. read lens position\r
- ret = fimc_is_ois_read(ois->client, MOT_BU24218_REG_LENS_XCH, &data[0]);\r
+ usleep_range(20000,20000);\r
+ ret = fimc_is_factory_ois_get_x_adc(ois->client,&data[1]);\r
check_result(ret);\r
- ret = fimc_is_ois_read(ois->client, MOT_BU24218_REG_LENS_YCH, &data[1]);\r
+ \r
+ // 5. set to zero position\r
+ ret = fimc_is_factory_ois_set_zero_pos(ois->client);\r
check_result(ret);\r
-\r
- // 5. set min postion\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_XCH, (uint8_t) MOT_BU24218_VCM_DRV_MIN_HI);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_XCH + 1, (uint8_t) MOT_BU24218_VCM_DRV_MIN_LO);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_YCH, (uint8_t) MOT_BU24218_VCM_DRV_MIN_HI);\r
- fimc_is_ois_write(ois->client, MOT_BU24218_REG_POS_YCH + 1, (uint8_t) MOT_BU24218_VCM_DRV_MIN_LO);\r
- usleep_range(200, 200);\r
-\r
- // 6. check status reg\r
- ret = fimc_is_factory_ois_poll(ois->client, MOT_BU24218_REG_STATUS, 0x01);\r
+ usleep_range(20000,20000);\r
+ \r
+ // 6. set y max position and read ADC\r
+ ret = fimc_is_factory_ois_set_y_pos(ois->client, MOT_BU24218_VCM_DRV_MAX_HI, MOT_BU24218_VCM_DRV_MAX_LO);\r
check_result(ret);\r
-\r
- usleep_range(200, 200);\r
- // 7. read lens position\r
- ret = fimc_is_ois_read(ois->client, MOT_BU24218_REG_LENS_XCH, &data[2]);\r
+ usleep_range(20000,20000);\r
+ ret = fimc_is_factory_ois_get_y_adc(ois->client,&data[2]);\r
check_result(ret);\r
- ret = fimc_is_ois_read(ois->client, MOT_BU24218_REG_LENS_YCH, &data[3]);\r
+ \r
+ // 7. set y min position and read ADC\r
+ ret = fimc_is_factory_ois_set_y_pos(ois->client, MOT_BU24218_VCM_DRV_MIN_HI, MOT_BU24218_VCM_DRV_MIN_LO);\r
check_result(ret);\r
+ usleep_range(20000,20000);\r
+ ret = fimc_is_factory_ois_get_y_adc(ois->client,&data[3]);\r
+ check_result(ret);\r
+ \r
+ result->x_max = data[0];\r
+ result->x_min = data[1];\r
+ result->y_max = data[2];\r
+ result->y_min = data[3];\r
\r
- info("%s: actual pos:(%d, %d, %d, %d)", __func__,\r
- data[0], data[2], data[1], data[3]);\r
- // follow the format, Xmax, Xmin, Ymax, Ymin\r
- *result = data[0] | (data[2] << 8) | (data[1] << 16) | (data[3] << 24);\r
-\r
+ info("%s: result %d %d %d %d", __func__,\r
+ result->x_max, result->x_min, result->y_max, result->y_min);\r
+ \r
return 0;\r
\r
ERROR:\r
err("%s: Failed with %d", __func__, ret);\r
return -1;\r
}\r
+\r
+\r
+int fimc_is_factory_ois_calibration_mode(struct i2c_client *client)\r
+{\r
+ int ret = 0;\r
+ \r
+ fimc_is_ois_write(client, MOT_BU24218_REG_MODE, 0x01);\r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_STATUS, 0x01);\r
+ if (ret < 0) {\r
+ err("fail at calib 01");\r
+ return ret;\r
+ }\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_LINEARITY, 0x00);\r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_LINEARITY, 0x00);\r
+ if (ret < 0) {\r
+ err("fail at linearity");\r
+ return ret;\r
+ }\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_GYRO_ACCESS, 0x02);\r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_STATUS, 0x01);\r
+ if (ret < 0) {\r
+ err("fail at gyro access");\r
+ return ret;\r
+ }\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_MODE, 0x00);\r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_STATUS, 0x01);\r
+ if (ret < 0) {\r
+ err("fail at calib 00");\r
+ return ret;\r
+ }\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_MODE, 0x04);\r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_STATUS, 0x01);\r
+ if (ret < 0) {\r
+ err("fail at calib 04");\r
+ return ret;\r
+ }\r
+ \r
+ return ret;\r
+}\r
+\r
+int fimc_is_factory_ois_set_zero_pos(struct i2c_client *client)\r
+{\r
+ int ret = 0;\r
+ fimc_is_factory_ois_set_x_pos(client, MOT_BU24218_VCM_DRV_ZERO_HI, MOT_BU24218_VCM_DRV_ZERO_LO);\r
+ fimc_is_factory_ois_set_y_pos(client, MOT_BU24218_VCM_DRV_ZERO_HI, MOT_BU24218_VCM_DRV_ZERO_LO);\r
+ \r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_STATUS, 0x01);\r
+ if (ret < 0) {\r
+ err("fail at set to zero");\r
+ }\r
+ return ret;\r
+}\r
+\r
+int fimc_is_factory_ois_set_x_pos(struct i2c_client *client, uint8_t hi, uint8_t lo)\r
+{\r
+ int ret = 0;\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_POS_XCH, hi);\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_POS_XCH + 1, lo); \r
+ \r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_STATUS, 0x01);\r
+ if (ret < 0) {\r
+ err("fail at %s",__func__);\r
+ }\r
+ return ret;\r
+}\r
+\r
+int fimc_is_factory_ois_set_y_pos(struct i2c_client *client, uint8_t hi, uint8_t lo)\r
+{\r
+ int ret = 0;\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_POS_YCH, hi);\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_POS_YCH + 1, lo); \r
+ \r
+ ret = fimc_is_factory_ois_poll(client, MOT_BU24218_REG_STATUS, 0x01);\r
+ if (ret < 0) {\r
+ err("fail at %s",__func__);\r
+ }\r
+ return ret;\r
+}\r
+\r
+int fimc_is_factory_ois_get_x_adc(struct i2c_client *client, uint32_t* data)\r
+{\r
+ int ret = 0;\r
+ uint8_t raw_adc_hi = 0, raw_adc_lo = 0;\r
+\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_ADC_LATCH, MOT_BU24218_ADC_LATCH_X);\r
+ usleep_range(11000,11000);\r
+\r
+ ret = fimc_is_ois_read(client, MOT_BU24218_REG_ADC_VAL, &raw_adc_hi);\r
+ if (ret < 0) {\r
+ err("fail at %s",__func__);\r
+ return ret;\r
+ }\r
+ usleep_range(500,500);\r
+ ret = fimc_is_ois_read(client, MOT_BU24218_REG_ADC_VAL+1, &raw_adc_lo);\r
+ if (ret < 0) {\r
+ err("fail at %s",__func__);\r
+ return ret;\r
+ }\r
+ usleep_range(500,500);\r
+\r
+ *data = (uint32_t)(raw_adc_hi << 8) + raw_adc_lo;\r
+ return ret;\r
+}\r
+\r
+int fimc_is_factory_ois_get_y_adc(struct i2c_client *client, uint32_t* data)\r
+{\r
+ int ret = 0;\r
+ uint8_t raw_adc_hi = 0, raw_adc_lo = 0;\r
+\r
+ fimc_is_ois_write(client, MOT_BU24218_REG_ADC_LATCH, MOT_BU24218_ADC_LATCH_Y);\r
+ usleep_range(11000,11000);\r
+\r
+ ret = fimc_is_ois_read(client, MOT_BU24218_REG_ADC_VAL, &raw_adc_hi);\r
+ if (ret < 0) {\r
+ err("fail at %s",__func__);\r
+ return ret;\r
+ }\r
+ usleep_range(500,500);\r
+ ret = fimc_is_ois_read(client, MOT_BU24218_REG_ADC_VAL+1, &raw_adc_lo);\r
+ if (ret < 0) {\r
+ err("fail at %s",__func__);\r
+ return ret;\r
+ }\r
+ usleep_range(500,500);\r
+\r
+ *data = (uint32_t)(raw_adc_hi << 8) + raw_adc_lo;\r
+ return ret;\r
+}\r