这里以msm8939为例
1、将摄像头文件放到下面两个文件夹
vendor/qcom/proprietary/mm-camera/mm-camera2/media-controller/modules/sensors/sensor_libs/
vendor/qcom/proprietary/mm-camera/mm-camera2/media-controller/modules/sensors/chromatix/0301/libchromatix/
2、将上面的文件编译出来的模块添加到系统(grep -rinw LOCAL_MODULE *)
vendor/qcom/proprietary/common/config/device-vendor.mk,如MM_CAMERA += libmmcamera_gc2235_8916
3、定义初始化的sensorvendor/qcom/proprietary/mm-camera/mm-camera2/media-controller/modules/sensors/module/sensor_init.c
#define BOARD_SENSORS \
"ov8865_cm9462",\
"gc2235_8916", \
"ov5648_oty5f03",\
"ov13850",
上电过程小析
vendor/qcom/proprietary/mm-camera/mm-camera2/media-controller/modules/sensors/module/sensor_init.c
sensor_init_probe { sensor_probe(sd_fd, sensor_libs[i]); }
vendor/qcom/proprietary/mm-camera/mm-camera2/media-controller/modules/sensors/sensors/sensor.c
sensor_probe { if (LOG_IOCTL(fd, VIDIOC_MSM_SENSOR_INIT_CFG, &cfg) < 0) }
kernel/drivers/media/platform/msm/camera_v2/sensor/msm_sensor_init.c
case VIDIOC_MSM_SENSOR_INIT_CFG: msm_sensor_driver_cmd(s_init, arg); msm_sensor_driver_probe { /* Power up and probe sensor */ rc = s_ctrl->func_tbl->sensor_power_up(s_ctrl); } int msm_sensor_power_up(struct msm_sensor_ctrl_t *s_ctrl) { for (retry = 0; retry < 3; retry++) { rc = msm_camera_power_up(power_info, s_ctrl->sensor_device_type,sensor_i2c_client); if (rc < 0) return rc; rc = msm_sensor_check_id(s_ctrl); if (rc < 0) { msm_camera_power_down(power_info,s_ctrl->sensor_device_type, sensor_i2c_client); msleep(20); continue; } else { break; } } int msm_sensor_check_id(struct msm_sensor_ctrl_t *s_ctrl) { int rc; if (s_ctrl->func_tbl->sensor_match_id) rc = s_ctrl->func_tbl->sensor_match_id(s_ctrl); else rc = msm_sensor_match_id(s_ctrl); if (rc < 0) pr_err("%s:%d match id failed rc %d\n", __func__, __LINE__, rc); return rc; }
dts配置
qcom,camera@1 { cell-index = <1>; //1前摄 compatible = "qcom,camera"; reg = <0x1>; qcom,csiphy-sd-index = <1>; qcom,csid-sd-index = <1>; qcom,mount-angle = <90>; qcom,eeprom-src = <&eeprom1>; cam_vdig-supply = <&pm8916_l2>; cam_vana-supply = <&pm8916_l17>; cam_vio-supply = <&pm8916_l6>; qcom,cam-vreg-name = "cam_vdig", "cam_vio", "cam_vana"; qcom,cam-vreg-min-voltage = <1200000 0 2850000>; qcom,cam-vreg-max-voltage = <1200000 0 2850000>; qcom,cam-vreg-op-mode = <200000 0 80000>; //这里用了3个ldo,分别对应相应的最小最大电源,vio这里为0,跟这路ldo被其它器件使用并使能有关 pinctrl-names = "cam_default", "cam_suspend"; pinctrl-0 = <&cam_sensor_mclk1_default &cam_sensor_front_default>; pinctrl-1 = <&cam_sensor_mclk1_sleep &cam_sensor_front_sleep>; gpios = <&msm_gpio 27 0>, <&msm_gpio 28 0>, <&msm_gpio 33 0>; qcom,gpio-reset = <1>; qcom,gpio-standby = <2>; qcom,gpio-req-tbl-num = <0 1 2>; qcom,gpio-req-tbl-flags = <1 0 0>; qcom,gpio-req-tbl-label = "CAMIF_MCLK1", "SCAM_RESET", "SCAM_STANDBY"; // gpio_request_one(unsigned gpio, unsigned long flags, const char *label) //申请gpio用到这个函数,flags 1代表输入,0代表输出 qcom,sensor-position = <1>; qcom,sensor-mode = <0>; qcom,cci-master = <0>; status = "ok"; clocks = <&clock_gcc clk_mclk1_clk_src>, <&clock_gcc clk_gcc_camss_mclk1_clk>; clock-names = "cam_src_clk", "cam_clk"; };vendor/qcom/proprietary/mm-camera/mm-camera2/media-controller/modules/sensors/sensor_libs/ov8865_cm9462/ov8865_cm9462_lib.c
上电数组,如
static struct msm_sensor_power_setting power_setting[] = { { .seq_type = SENSOR_VREG, .seq_val = CAM_VIO, .config_val = 1, .delay = 1, }, { .seq_type = SENSOR_VREG, .seq_val = CAM_VANA, .config_val = 1, .delay = 1, }, { .seq_type = SENSOR_GPIO, .seq_val = SENSOR_GPIO_VDIG, .config_val = 1, .delay = 1, }, { .seq_type = SENSOR_VREG, .seq_val = CAM_VAF, .config_val = 1, .delay = 5, }, { .seq_type = SENSOR_GPIO, .seq_val = SENSOR_GPIO_STANDBY, .config_val = GPIO_OUT_LOW, .delay = 1, }, { .seq_type = SENSOR_GPIO, .seq_val = SENSOR_GPIO_RESET, .config_val = GPIO_OUT_LOW, .delay = 5, }, { .seq_type = SENSOR_GPIO, .seq_val = SENSOR_GPIO_AF_PWDM, .config_val = GPIO_OUT_LOW, .delay = 5, }, { .seq_type = SENSOR_GPIO, .seq_val = SENSOR_GPIO_STANDBY, .config_val = GPIO_OUT_HIGH, .delay = 5, }, { .seq_type = SENSOR_GPIO, .seq_val = SENSOR_GPIO_RESET, .config_val = GPIO_OUT_HIGH, .delay = 10, }, { .seq_type = SENSOR_GPIO, .seq_val = SENSOR_GPIO_AF_PWDM, .config_val = GPIO_OUT_HIGH, .delay = 5, }, { .seq_type = SENSOR_CLK, .seq_val = SENSOR_CAM_MCLK, .config_val = 23880000, .delay = 10, }, { .seq_type = SENSOR_I2C_MUX, .seq_val = 0, .config_val = 0, .delay = 10, }, };
type就是类型,主要有电源,io脚,时钟,i2c,这个数组解析下来就类似于
使能CAM_VIO
拉高某某io脚
配置时钟
相关的打印如下
[ 18.582925] camera id 0 [ 18.584333] slave_addr 0x6c [ 18.587109] addr_type 2 [ 18.589604] sensor_id_reg_addr 0x300b [ 18.593190] sensor_id 0x8865 [ 18.596054] size 12 [ 18.598137] size down 7 [ 18.600654] position 0 [ 18.602764] mount 0s_ctrl[0] ffffffc06fa45000 [ 18.607094] UP seq_type 2 seq_val 1 config_val 1 delay 1 [ 18.612630] UP seq_type 2 seq_val 2 config_val 1 delay 1 [ 18.617869] UP seq_type 1 seq_val 5 config_val 1 delay 1 [ 18.623218] UP seq_type 2 seq_val 3 config_val 1 delay 5 [ 18.628487] UP seq_type 1 seq_val 1 config_val 0 delay 1 [ 18.633756] UP seq_type 1 seq_val 0 config_val 0 delay 5 [ 18.639092] UP seq_type 1 seq_val 2 config_val 0 delay 5 [ 18.644348] UP seq_type 1 seq_val 1 config_val 2 delay 5 [ 18.649677] UP seq_type 1 seq_val 0 config_val 2 delay 10 [ 18.655025] UP seq_type 1 seq_val 2 config_val 2 delay 5 [ 18.660352] UP seq_type 0 seq_val 0 config_val 23880000 delay 10 [ 18.666317] UP seq_type 3 seq_val 0 config_val 0 delay 10 [ 18.671747] DOWN seq_type 1 seq_val 0 config_val 0 delay 1 [ 18.677165] DOWN seq_type 1 seq_val 1 config_val 0 delay 1 [ 18.682693] DOWN seq_type 0 seq_val 0 config_val 0 delay 1 [ 18.688095] DOWN seq_type 1 seq_val 2 config_val 0 delay 5 [ 18.693630] DOWN seq_type 2 seq_val 1 config_val 0 delay 1 [ 18.699069] DOWN seq_type 2 seq_val 3 config_val 0 delay 1 [ 18.704498] DOWN seq_type 1 seq_val 5 config_val 0 delay 1 [ 18.710041] msm_camera_fill_vreg_params:65 i 0 j 0 cam_vio [ 18.715437] msm_camera_fill_vreg_params:76 i 1 j 1 cam_vana [ 18.721026] msm_camera_fill_vreg_params:87 i 3 j 2 cam_vaf [ 18.726488] msm_camera_fill_vreg_params:65 i 4 j 0 cam_vio [ 18.732033] msm_camera_fill_vreg_params:87 i 5 j 2 cam_vaf [ 18.738258] msm_sensor_fill_actuator_subdevid_by_name qcom,actuator cell index 0, rc 0 [ 18.745304] msm_camera_power_up:1225 [ 18.749586] msm_camera_power_up index 0 [ 18.752695] msm_camera_power_up type 2 [ 18.758214] msm_camera_power_up index 1 [ 18.761032] msm_camera_power_up type 2 [ 18.767152] msm_camera_power_up index 2 [ 18.770113] msm_camera_power_up type 1 [ 18.773678] msm_camera_power_up:1298 gpio set val 1016 [ 18.780882] msm_camera_power_up index 3 [ 18.784417] msm_camera_power_up type 2 [ 18.794168] msm_camera_power_up index 4 [ 18.796986] msm_camera_power_up type 1 [ 18.800734] msm_camera_power_up:1298 gpio set val 936 [ 18.807780] msm_camera_power_up index 5 [ 18.810704] msm_camera_power_up type 1 [ 18.814344] msm_camera_power_up:1298 gpio set val 937 [ 18.825443] msm_camera_power_up index 6 [ 18.828301] msm_camera_power_up type 1 [ 18.832019] msm_camera_power_up:1298 gpio set val 1022 [ 18.843166] msm_camera_power_up index 7 [ 18.845963] msm_camera_power_up type 1 [ 18.851722] msm_camera_power_up:1298 gpio set val 936 [ 18.862352] msm_camera_power_up index 8 [ 18.865148] msm_camera_power_up type 1 [ 18.868955] msm_camera_power_up:1298 gpio set val 937 [ 18.884950] msm_camera_power_up index 9 [ 18.887746] msm_camera_power_up type 1 [ 18.891519] msm_camera_power_up:1298 gpio set val 1022 [ 18.902627] msm_camera_power_up index 10 [ 18.905508] msm_camera_power_up type 0 [ 18.921298] msm_camera_power_up index 11 [ 18.924181] msm_camera_power_up type 3 [ 18.939410] msm_cci_init: Failed in getting TOP gdscr regulator handle [ 18.945060] msm_cci_init:763: hw_version = 0x10020000 [ 18.946920] msm_camera_power_up exit [ 18.950111] msm_sensor_match_id: read id: 0x8865 expected id 0x8865: [ 18.955818] ov8865_cm9462 probe succeeded [ 18.959685] slave_info->is_flash_supported=1. [ 18.964138] s_ctrl->sensordata->sensor_info->subdev_id[SUB_MODULE_LED_FLASH=0. [ 18.974205] rc 0 session_id 1 [ 18.977189] msm_camera_power_down:1444 [ 18.980240] msm_camera_power_down index 0 [ 18.984099] msm_camera_power_down type 1 [ 18.989995] msm_camera_power_down index 1 [ 18.992969] msm_camera_power_down type 1 [ 18.998287] msm_camera_power_down index 2 [ 19.001261] msm_camera_power_down type 0 [ 19.007239] msm_camera_power_down index 3 [ 19.010246] msm_camera_power_down type 1 [ 19.020164] msm_camera_power_down index 4 [ 19.023133] msm_camera_power_down type 2 [ 19.028269] msm_camera_power_down index 5 [ 19.031299] msm_camera_power_down type 2 [ 19.038117] msm_camera_power_down index 6 [ 19.041161] msm_camera_power_down type 1 [ 19.047179] msm_camera_power_down exit
UP seq_type 2 seq_val 1 config_val 1 delay 1
从这些打印看,都是在执行power_setting的上电顺序type种类
enum msm_sensor_power_seq_type_t { SENSOR_CLK, SENSOR_GPIO, SENSOR_VREG, SENSOR_I2C_MUX, SENSOR_I2C, };
type1(SENSOR_GPIO),相应的值
enum msm_sensor_power_seq_gpio_t { SENSOR_GPIO_RESET, SENSOR_GPIO_STANDBY, SENSOR_GPIO_AF_PWDM, SENSOR_GPIO_VIO, SENSOR_GPIO_VANA, SENSOR_GPIO_VDIG, SENSOR_GPIO_VAF, SENSOR_GPIO_FL_EN, SENSOR_GPIO_FL_NOW, SENSOR_GPIO_FL_RESET, SENSOR_GPIO_CUSTOM1, SENSOR_GPIO_CUSTOM2, SENSOR_GPIO_MAX, };
type2(SENSOR_VREG电源),相应的值
enum msm_camera_vreg_name_t { CAM_VDIG, CAM_VIO, CAM_VANA, CAM_VAF, CAM_V_CUSTOM1, CAM_V_CUSTOM2, CAM_VREG_MAX, };