|
@@ -724,7 +724,7 @@ static int32_t cam_cci_data_queue(struct cci_device *cci_dev,
|
|
{
|
|
{
|
|
uint16_t i = 0, j = 0, k = 0, h = 0, len = 0;
|
|
uint16_t i = 0, j = 0, k = 0, h = 0, len = 0;
|
|
int32_t rc = 0, free_size = 0, en_seq_write = 0;
|
|
int32_t rc = 0, free_size = 0, en_seq_write = 0;
|
|
- uint8_t data[12];
|
|
|
|
|
|
+ uint8_t write_data[CAM_MAX_NUM_CCI_PAYLOAD_BYTES + 1] = {0};
|
|
struct cam_sensor_i2c_reg_setting *i2c_msg =
|
|
struct cam_sensor_i2c_reg_setting *i2c_msg =
|
|
&c_ctrl->cfg.cci_i2c_write_cfg;
|
|
&c_ctrl->cfg.cci_i2c_write_cfg;
|
|
struct cam_sensor_i2c_reg_array *i2c_cmd = i2c_msg->reg_setting;
|
|
struct cam_sensor_i2c_reg_array *i2c_cmd = i2c_msg->reg_setting;
|
|
@@ -848,7 +848,7 @@ static int32_t cam_cci_data_queue(struct cci_device *cci_dev,
|
|
cci_dev->soc_info.index, master, queue, cmd_size, i2c_cmd->reg_addr, i2c_cmd->reg_data);
|
|
cci_dev->soc_info.index, master, queue, cmd_size, i2c_cmd->reg_addr, i2c_cmd->reg_data);
|
|
delay = i2c_cmd->delay;
|
|
delay = i2c_cmd->delay;
|
|
i = 0;
|
|
i = 0;
|
|
- data[i++] = CCI_I2C_WRITE_CMD;
|
|
|
|
|
|
+ write_data[i++] = CCI_I2C_WRITE_CMD;
|
|
|
|
|
|
/*
|
|
/*
|
|
* in case of multiple command
|
|
* in case of multiple command
|
|
@@ -865,37 +865,34 @@ static int32_t cam_cci_data_queue(struct cci_device *cci_dev,
|
|
reg_addr = i2c_cmd->reg_addr;
|
|
reg_addr = i2c_cmd->reg_addr;
|
|
|
|
|
|
if (en_seq_write == 0) {
|
|
if (en_seq_write == 0) {
|
|
- /* either byte or word addr */
|
|
|
|
- if (i2c_msg->addr_type == CAMERA_SENSOR_I2C_TYPE_BYTE)
|
|
|
|
- data[i++] = reg_addr;
|
|
|
|
- else {
|
|
|
|
- data[i++] = (reg_addr & 0xFF00) >> 8;
|
|
|
|
- data[i++] = reg_addr & 0x00FF;
|
|
|
|
|
|
+ for (j = 0; j < i2c_msg->addr_type; j++) {
|
|
|
|
+ write_data[i2c_msg->addr_type - j] = (reg_addr >> (j * 8)) & 0xFF;
|
|
|
|
+ i++;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
- /* max of 10 data bytes */
|
|
|
|
|
|
+
|
|
do {
|
|
do {
|
|
if (i2c_msg->data_type == CAMERA_SENSOR_I2C_TYPE_BYTE) {
|
|
if (i2c_msg->data_type == CAMERA_SENSOR_I2C_TYPE_BYTE) {
|
|
- data[i++] = i2c_cmd->reg_data;
|
|
|
|
|
|
+ write_data[i++] = i2c_cmd->reg_data;
|
|
if (c_ctrl->cmd == MSM_CCI_I2C_WRITE_SEQ)
|
|
if (c_ctrl->cmd == MSM_CCI_I2C_WRITE_SEQ)
|
|
reg_addr++;
|
|
reg_addr++;
|
|
} else {
|
|
} else {
|
|
if ((i + 1) <= cci_dev->payload_size) {
|
|
if ((i + 1) <= cci_dev->payload_size) {
|
|
switch (i2c_msg->data_type) {
|
|
switch (i2c_msg->data_type) {
|
|
case CAMERA_SENSOR_I2C_TYPE_DWORD:
|
|
case CAMERA_SENSOR_I2C_TYPE_DWORD:
|
|
- data[i++] = (i2c_cmd->reg_data &
|
|
|
|
|
|
+ write_data[i++] = (i2c_cmd->reg_data &
|
|
0xFF000000) >> 24;
|
|
0xFF000000) >> 24;
|
|
/* fallthrough */
|
|
/* fallthrough */
|
|
case CAMERA_SENSOR_I2C_TYPE_3B:
|
|
case CAMERA_SENSOR_I2C_TYPE_3B:
|
|
- data[i++] = (i2c_cmd->reg_data &
|
|
|
|
|
|
+ write_data[i++] = (i2c_cmd->reg_data &
|
|
0x00FF0000) >> 16;
|
|
0x00FF0000) >> 16;
|
|
/* fallthrough */
|
|
/* fallthrough */
|
|
case CAMERA_SENSOR_I2C_TYPE_WORD:
|
|
case CAMERA_SENSOR_I2C_TYPE_WORD:
|
|
- data[i++] = (i2c_cmd->reg_data &
|
|
|
|
|
|
+ write_data[i++] = (i2c_cmd->reg_data &
|
|
0x0000FF00) >> 8;
|
|
0x0000FF00) >> 8;
|
|
/* fallthrough */
|
|
/* fallthrough */
|
|
case CAMERA_SENSOR_I2C_TYPE_BYTE:
|
|
case CAMERA_SENSOR_I2C_TYPE_BYTE:
|
|
- data[i++] = i2c_cmd->reg_data &
|
|
|
|
|
|
+ write_data[i++] = i2c_cmd->reg_data &
|
|
0x000000FF;
|
|
0x000000FF;
|
|
break;
|
|
break;
|
|
default:
|
|
default:
|
|
@@ -905,8 +902,7 @@ static int32_t cam_cci_data_queue(struct cci_device *cci_dev,
|
|
return -EINVAL;
|
|
return -EINVAL;
|
|
}
|
|
}
|
|
|
|
|
|
- if (c_ctrl->cmd ==
|
|
|
|
- MSM_CCI_I2C_WRITE_SEQ)
|
|
|
|
|
|
+ if (c_ctrl->cmd == MSM_CCI_I2C_WRITE_SEQ)
|
|
reg_addr++;
|
|
reg_addr++;
|
|
} else
|
|
} else
|
|
break;
|
|
break;
|
|
@@ -923,10 +919,10 @@ static int32_t cam_cci_data_queue(struct cci_device *cci_dev,
|
|
((i-1) == MSM_CCI_WRITE_DATA_PAYLOAD_SIZE_11) &&
|
|
((i-1) == MSM_CCI_WRITE_DATA_PAYLOAD_SIZE_11) &&
|
|
cci_dev->support_seq_write && cmd_size > 0 &&
|
|
cci_dev->support_seq_write && cmd_size > 0 &&
|
|
free_size > BURST_MIN_FREE_SIZE) {
|
|
free_size > BURST_MIN_FREE_SIZE) {
|
|
- data[0] |= 0xF0;
|
|
|
|
|
|
+ write_data[0] |= 0xF0;
|
|
en_seq_write = 1;
|
|
en_seq_write = 1;
|
|
} else {
|
|
} else {
|
|
- data[0] |= ((i-1) << 4);
|
|
|
|
|
|
+ write_data[0] |= ((i-1) << 4);
|
|
en_seq_write = 0;
|
|
en_seq_write = 0;
|
|
}
|
|
}
|
|
len = ((i-1)/4) + 1;
|
|
len = ((i-1)/4) + 1;
|
|
@@ -936,7 +932,7 @@ static int32_t cam_cci_data_queue(struct cci_device *cci_dev,
|
|
for (h = 0, k = 0; h < len; h++) {
|
|
for (h = 0, k = 0; h < len; h++) {
|
|
cmd = 0;
|
|
cmd = 0;
|
|
for (j = 0; (j < 4 && k < i); j++)
|
|
for (j = 0; (j < 4 && k < i); j++)
|
|
- cmd |= (data[k++] << (j * 8));
|
|
|
|
|
|
+ cmd |= (write_data[k++] << (j * 8));
|
|
CAM_DBG(CAM_CCI,
|
|
CAM_DBG(CAM_CCI,
|
|
"CCI%d_I2C_M%d_Q%d LOAD_DATA_ADDR 0x%x, len:%d, cnt: %d",
|
|
"CCI%d_I2C_M%d_Q%d LOAD_DATA_ADDR 0x%x, len:%d, cnt: %d",
|
|
cci_dev->soc_info.index, master, queue, cmd, len, read_val);
|
|
cci_dev->soc_info.index, master, queue, cmd, len, read_val);
|
|
@@ -1178,8 +1174,9 @@ read_again:
|
|
} else {
|
|
} else {
|
|
read_cfg->data[index] =
|
|
read_cfg->data[index] =
|
|
(val >> (i * 8)) & 0xFF;
|
|
(val >> (i * 8)) & 0xFF;
|
|
- CAM_DBG(CAM_CCI, "CCI%d_I2C_M%d_Q%d data[%d] 0x%x",
|
|
|
|
- cci_dev->soc_info.index, master, queue, index, read_cfg->data[index]);
|
|
|
|
|
|
+ CAM_DBG(CAM_CCI, "CCI%d_I2C_M%d_Q%d data[%d] 0x%x",
|
|
|
|
+ cci_dev->soc_info.index, master, queue, index,
|
|
|
|
+ read_cfg->data[index]);
|
|
index++;
|
|
index++;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
@@ -1271,6 +1268,8 @@ static int32_t cam_cci_read(struct v4l2_subdev *sd,
|
|
{
|
|
{
|
|
int32_t rc = 0;
|
|
int32_t rc = 0;
|
|
uint32_t val = 0;
|
|
uint32_t val = 0;
|
|
|
|
+ uint8_t read_data_byte[CAM_MAX_NUM_CCI_PAYLOAD_BYTES + 1] = {0};
|
|
|
|
+ uint32_t *reg_addr;
|
|
int32_t read_words = 0, exp_words = 0;
|
|
int32_t read_words = 0, exp_words = 0;
|
|
int32_t index = 0, first_byte = 0;
|
|
int32_t index = 0, first_byte = 0;
|
|
uint32_t i = 0;
|
|
uint32_t i = 0;
|
|
@@ -1363,18 +1362,23 @@ static int32_t cam_cci_read(struct v4l2_subdev *sd,
|
|
goto rel_mutex_q;
|
|
goto rel_mutex_q;
|
|
}
|
|
}
|
|
|
|
|
|
- val = CCI_I2C_WRITE_DISABLE_P_CMD | (read_cfg->addr_type << 4);
|
|
|
|
|
|
+ read_data_byte[0] = CCI_I2C_WRITE_DISABLE_P_CMD | (read_cfg->addr_type << 4);
|
|
for (i = 0; i < read_cfg->addr_type; i++) {
|
|
for (i = 0; i < read_cfg->addr_type; i++) {
|
|
- val |= ((read_cfg->addr >> (i << 3)) & 0xFF) <<
|
|
|
|
- ((read_cfg->addr_type - i) << 3);
|
|
|
|
|
|
+ read_data_byte[read_cfg->addr_type - i] = (read_cfg->addr >> (i * 8)) & 0xFF;
|
|
}
|
|
}
|
|
|
|
|
|
- rc = cam_cci_write_i2c_queue(cci_dev, val, master, queue);
|
|
|
|
- if (rc < 0) {
|
|
|
|
- CAM_DBG(CAM_CCI,
|
|
|
|
- "CCI%d_I2C_M%d_Q%d Failed to write disable_cmd for rc: %d",
|
|
|
|
- cci_dev->soc_info.index, master, queue, rc);
|
|
|
|
- goto rel_mutex_q;
|
|
|
|
|
|
+ reg_addr = (uint32_t *)&read_data_byte[0];
|
|
|
|
+ read_words = DIV_ROUND_UP(read_cfg->addr_type + 1, 4);
|
|
|
|
+
|
|
|
|
+ for (i = 0; i < read_words; i++) {
|
|
|
|
+ rc = cam_cci_write_i2c_queue(cci_dev, *reg_addr, master, queue);
|
|
|
|
+ if (rc < 0) {
|
|
|
|
+ CAM_DBG(CAM_CCI,
|
|
|
|
+ "CCI%d_I2C_M%d_Q%d Failed to write disable_cmd for rc: %d",
|
|
|
|
+ cci_dev->soc_info.index, master, queue, rc);
|
|
|
|
+ goto rel_mutex_q;
|
|
|
|
+ }
|
|
|
|
+ reg_addr++;
|
|
}
|
|
}
|
|
|
|
|
|
val = CCI_I2C_READ_CMD | (read_cfg->num_byte << 4);
|
|
val = CCI_I2C_READ_CMD | (read_cfg->num_byte << 4);
|