kernel-4.4\drivers\misc\mediatek\imgsensor\src\common\v1
imgsensor.c
imgsensor_probe
--->imgsensor_i2c_create();
imgsensor_i2c.c
imgsensor_i2c_create()
---->i2c_add_driver
kernel-4.4\drivers\misc\mediatek\imgsensor\src\mt6739\camera_hw imgsensor_cfg_table.h中有如下定义
#define IMGSENSOR_I2C_OF_DRV_NAME_0 "mediatek,camera_main" // 匹配后摄的驱动
#define IMGSENSOR_I2C_OF_DRV_NAME_1 "mediatek,camera_sub" // 匹配后摄的驱动
#define IMGSENSOR_I2C_OF_DRV_NAME_2 "mediatek,camera_main_two"
mediatek,camera_main 、mediatek,camera_sub这两个字串在codegen.dws文件中匹配。dws 用工具可查看
camera 驱动文件 kernel-4.4\drivers\misc\mediatek\imgsensor\src\common\v1 imgsensor_i2c.c
有如下定义:
#ifdef CONFIG_OF
static const struct of_device_id gof_device_id_0[] = {
{ .compatible = IMGSENSOR_I2C_OF_DRV_NAME_0, }, //后摄
{}
};
static const struct of_device_id gof_device_id_1[] = { //前摄
{ .compatible = IMGSENSOR_I2C_OF_DRV_NAME_1, },
{}
};
static const struct of_device_id gof_device_id_2[] = {
{ .compatible = IMGSENSOR_I2C_OF_DRV_NAME_2, },
{}
};
#endif
i2c driver 注册结构体
static struct i2c_driver gi2c_driver[IMGSENSOR_I2C_DEV_MAX_NUM] = {
{
.probe = imgsensor_i2c_probe_0,
.remove = imgsensor_i2c_remove,
.driver = {
.name = IMGSENSOR_I2C_DRV_NAME_0,
.owner = THIS_MODULE,
#ifdef CONFIG_OF
.of_match_table = gof_device_id_0,
#endif
},
.id_table = gi2c_dev_id,
},
{
.probe = imgsensor_i2c_probe_1,
.remove = imgsensor_i2c_remove,
.driver = {
.name = IMGSENSOR_I2C_DRV_NAME_1,
.owner = THIS_MODULE,
#ifdef CONFIG_OF
.of_match_table = gof_device_id_1,
#endif
},
.id_table = gi2c_dev_id,
},
{
.probe = imgsensor_i2c_probe_2,
.remove = imgsensor_i2c_remove,
.driver = {
.name = IMGSENSOR_I2C_DRV_NAME_2,
.owner = THIS_MODULE,
#ifdef CONFIG_OF
.of_match_table = gof_device_id_2,
#endif
},
.id_table = gi2c_dev_id,
}
};
i2c 读写驱动
enum IMGSENSOR_RETURN imgsensor_i2c_read_main(
struct IMGSENSOR_I2C_CFG *pi2c_cfg,
u8 *pwrite_data,
u16 write_length,
u8 *pread_data,
u16 read_length,
u16 id,
int speed)
{
struct IMGSENSOR_I2C_INST *pinst = pi2c_cfg->pinst;
enum IMGSENSOR_RETURN ret = IMGSENSOR_RETURN_SUCCESS;
pinst = &gi2c.inst[0];
pi2c_cfg->pi2c_driver = &gi2c_driver[0];
mutex_lock(&pi2c_cfg->i2c_mutex);
pinst->msg[0].addr = id >> 1;
pinst->msg[0].flags = 0;
pinst->msg[0].len = write_length;
pinst->msg[0].buf = pwrite_data;
pinst->msg[1].addr = id >> 1;
pinst->msg[1].flags = I2C_M_RD;
pinst->msg[1].len = read_length;
pinst->msg[1].buf = pread_data;
if (mtk_i2c_transfer(
pinst->pi2c_client->adapter,
pinst->msg,
IMGSENSOR_I2C_MSG_SIZE_READ,
(pi2c_cfg->pinst->status.filter_msg) ? I2C_A_FILTER_MSG : 0,
((speed > 0) && (speed <= 1000)) ? speed * 1000 : IMGSENSOR_I2C_SPEED * 1000)
!= IMGSENSOR_I2C_MSG_SIZE_READ) {
static DEFINE_RATELIMIT_STATE(ratelimit, 1 * HZ, 30);
if (__ratelimit(&ratelimit))
PK_PR_ERR("I2C read failed (0x%x)! speed(0=%d) (0x%x)\n", ret, speed, *pwrite_data);
ret = IMGSENSOR_RETURN_ERROR;
}
mutex_unlock(&pi2c_cfg->i2c_mutex);
return ret;
}
enum IMGSENSOR_RETURN imgsensor_i2c_write_main(
struct IMGSENSOR_I2C_CFG *pi2c_cfg,
u8 *pwrite_data,
u16 write_length,
u16 write_per_cycle,
u16 id,
int speed)
{
struct IMGSENSOR_I2C_INST *pinst = pi2c_cfg->pinst;
enum IMGSENSOR_RETURN ret = IMGSENSOR_RETURN_SUCCESS;
struct i2c_msg *pmsg = pinst->msg;
u8 *pdata = pwrite_data;
u8 *pend = pwrite_data + write_length;
int i = 0;
pinst = &gi2c.inst[0];
pi2c_cfg->pi2c_driver = &gi2c_driver[0];
pmsg = pinst->msg;
mutex_lock(&pi2c_cfg->i2c_mutex);
while (pdata < pend && i < IMGSENSOR_I2C_CMD_LENGTH_MAX) {
pmsg->addr = id >> 1;
pmsg->flags = 0;
pmsg->len = write_per_cycle;
pmsg->buf = pdata;
i++;
pmsg++;
pdata += write_per_cycle;
}
if (mtk_i2c_transfer(
pinst->pi2c_client->adapter,
pinst->msg,
i,
(pi2c_cfg->pinst->status.filter_msg) ? I2C_A_FILTER_MSG : 0,
((speed > 0) && (speed <= 1000)) ? speed * 1000 : IMGSENSOR_I2C_SPEED * 1000)
!= i) {
static DEFINE_RATELIMIT_STATE(ratelimit, 1 * HZ, 30);
if (__ratelimit(&ratelimit))
PK_PR_ERR("I2C write failed (0x%x)! speed(0=%d) (0x%x)\n", ret, speed, *pwrite_data);
ret = IMGSENSOR_RETURN_ERROR;
}
mutex_unlock(&pi2c_cfg->i2c_mutex);
return ret;
}
int main_camera_is_open = 0;//
EXPORT_SYMBOL(main_camera_is_open);