物联网即将到来的明天,是各个岗位都需要人才的明天,不是别的不重要,是硬件一样重要,系统开发一样重要,驱动开发一样重要,结构MD一样重要......

注:此文档以在高通8916平台移植OV5648为例,给大家讲解Android SOC的底层Camera。

一、Kernel 部分

1.1 添加Device Tree代码:

代码路径:srcLINUXandroidkernelarcharmootdtsqcom

文件名:msm8916-camera-sensor-qrd-skui.dtsi

需添加的代码:

qcom,camera@6a {

——这需要与1.3节中添加的Clock地址向对应。

compatible = "ovti,ov5648";

——这要与1.5节中添加的驱动代码中的名字相对应,即:static const struct of_device_id ov5648_dt_match[] = {

{

.compatible = "ovti,ov5648",

.data = &ov5648_s_ctrl

},

reg = <0x6a 0x0>;

——这需要与1.3节中添加的Clock地址向对应。

qcom,slave-id = <0x6c 0x300a 0x5648>;

——0x6c为摄像头的I2C地址,0x300a为摄像头存放ID的寄存器地址,0x5648为摄像头的ID,这都需要查看datasheet或直接问模组厂。

qcom,csiphy-sd-index = <1>;

qcom,csid-sd-index = <1>;

——以上两个设置需要查看主板原理图,看主板上摄像头是接在CSI0还是CSI1上的,一般后摄像头都会接到CSI0上,前摄像头会接在CSI1上。

qcom,mount-angle = <270>;

——该参数为摄像头预览界面的方向,如果预览方向有被旋转,可以通过修改这个参数进行修正。

qcom,sensor-name = "ov5648_oty5f03";

——这个对应vendor中lib文件夹的文件名,具体可参看2.2节。

cam_vdig-supply = <&pm8916_l2>;

cam_vana-supply = <&pm8916_l17>;

cam_vio-supply = <&pm8916_l6>;

——以上三个参数分别对应DVDD(vdig)、AVDD(vana)、DOVDD(vio)三个电压,具体所接的是哪路电压,需要参看主板原理图。

qcom,cam-vreg-name = "cam_vdig", "cam_vio", "cam_vana";

qcom,cam-vreg-type = <0 1 0>;

qcom,cam-vreg-min-voltage = <1200000 0 2850000>;

qcom,cam-vreg-max-voltage = <1200000 0 2850000>;

qcom,cam-vreg-op-mode = <200000 0 80000>;

——这五个配置要分别与上面的三个电压一一对应(按照从上到下的顺序),如果有对焦马达的还要在后面填一路AF的电压,如下所示:

cam_vaf-supply = <&pm8916_l10>;

qcom,cam-vreg-name = "cam_vdig", "cam_vio", "cam_vana",

"cam_vaf";

qcom,cam-vreg-type = <0 1 0 0>;

qcom,cam-vreg-min-voltage = <1200000 0 2850000 2800000>;

qcom,cam-vreg-max-voltage = <1200000 0 2850000 2800000>;

qcom,cam-vreg-op-mode = <200000 0 80000 100000>;

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>;

——以上这两个需要区分的就是前后摄像头的配置不一样,上面这种配置是前摄像头的配置,后摄像头的配置如下所示:

pinctrl-names = "cam_default", "cam_suspend";

pinctrl-0 = <&cam_sensor_mclk0_default

&cam_sensor_rear_default>;

pinctrl-1 = <&cam_sensor_mclk0_sleep &cam_sensor_rear_sleep>;

gpios = <&msm_gpio 27 0>,

<&msm_gpio 28 0>,

<&msm_gpio 33 0>,

<&msm_gpio 119 0>;

qcom,gpio-reset = <1>;

qcom,gpio-standby = <2>;

qcom,gpio-vana = <3>;

qcom,gpio-req-tbl-num = <0 1 2 3>;

qcom,gpio-req-tbl-flags = <1 0 0 0>;

qcom,gpio-req-tbl-label = "CAMIF_MCLK",

"CAM_RESET",

"CAM_STANDBY",

"CAM_VANA";

——上面这部分主要是配置GPIO口,这里需要注意的是gpios的数组要与gpio-req-tbl-label的名字一一对应,即gpio 27对应CAMIF_MCLK,而reset 、standby 、vana 分别对应gpios数组中的第1、2、3参数,gpio-req-tbl-num也对应于gpios中数组的标号。

qcom,gpio-set-tbl-num = <1 1>;

qcom,gpio-set-tbl-flags = <0 2>;

qcom,gpio-set-tbl-delay = <1000 4000>;

——这三个参数是前摄像头的固定模式,后摄像头不需要这个设置,在配置后摄像头时直接去掉即可。

qcom,csi-lane-assign = <0x4320>;

——该参数为主芯片mipi Lane个数配置寄存器。

qcom,csi-lane-mask = <0x3>;

——该参数为配置mipi Lane个数,0x3为1组数据线加1组时钟线,0x07为2组数据线加1组时钟线,0x1f为4组数据线加1主时钟线。

qcom,sensor-position = <1>;

——该参数,如果添加的是前摄像头需要配置成1,如果是后摄像头需要配置成0

qcom,sensor-mode = <1>;

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";

——上面两个Clocks和Clock-names是前摄像头的配置,后摄像头的配置如下:

clocks = <&clock_gcc clk_mclk0_clk_src>,

<&clock_gcc clk_gcc_camss_mclk0_clk>;

clock-names = "cam_src_clk", "cam_clk";

};

另外如果有对焦马达还需要修改对焦马达的地址,如下所示:

actuator0: qcom,actuator@6e {

cell-index = <3>;

reg = <0x18>;

compatible = "qcom,actuator";

qcom,cci-master = <0>;

};

1.2 添加宏开关:

代码路径:srcLINUXandroidkernelarcharmconfigs

文件名:msm8916_defconfig 和msm8916-perf_defconfig

需添加的代码:

CONFIG_OV5648=y

1.3 添加Clock:

代码路径:srcLINUXandroidkernelarcharmmach-msm

文件名:clock-8226.c

需添加的代码:

/* MM sensor clocks */

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "6f.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk1_clk_src.c, "90.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "6d.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "6a.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "6c.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "20.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "78.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "6f.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk1_clk.c, "90.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "6d.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "6a.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "6c.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "78.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "20.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "62.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "62.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "0.qcom,camera"),

CLK_LOOKUP("cam_src_clk", mclk0_clk_src.c, "1.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "0.qcom,camera"),

CLK_LOOKUP("cam_clk", camss_mclk0_clk.c, "1.qcom,camera"),

需要注意的是这里的标示(如:6a)不能重复,并且添加的时候需要同时添加一组代码,即上面红色标示的地方。

1.4 Kconfig和Makefile文件中添加对应IC代码:

代码路径:srcLINUXandroidkerneldriversmediaplatformmsmcamera_v2(Kconfig路径),srcLINUXandroidkerneldriversmediaplatformmsmcamera_v2sensor(Makefile路径)

文件名:Kconfig和Makefile

需添加的代码:

添加Kconfig:

config OV5648

bool "Sensor OV5648 (BAYER 5M)"

depends on MSMB_CAMERA

---help---

OmniVision 5 MP Bayer Sensor, only use 1 mipi lane,

preview set to 1296*972 at 30 fps,

snapshot set to 2592*1944 at 12 fps,

This sensor driver does not support auto focus.

添加Makefile:

obj-$(CONFIG_OV5648) += ov5648.o

1.5 添加Camera驱动代码:

代码路径:srcLINUXandroidkerneldriversmediaplatformmsmcamera_v2sensor

文件名:ov5648.c

需添加的代码:

该部分主要要注意电源的设置,它包括传感器电源信息,IO控制和Mclk。通常情况下,无需修改该部分内容,因为大部分配置已在设备树文件中完成;但可以修改.delay = 0 字段来和时间匹配。

static struct msm_sensor_power_setting ov5648_power_setting[] = {

{

.seq_type = SENSOR_VREG,

.seq_val = CAM_VIO,

.config_val = 0,

.delay = 0,

},

{

.seq_type = SENSOR_VREG,

.seq_val = CAM_VAF,

.config_val = 0,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_VDIG,

.config_val = GPIO_OUT_LOW,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_VDIG,

.config_val = GPIO_OUT_HIGH,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_VANA,

.config_val = GPIO_OUT_HIGH,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_STANDBY,

.config_val = GPIO_OUT_LOW,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_STANDBY,

.config_val = GPIO_OUT_HIGH,

.delay = 10,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_RESET,

.config_val = GPIO_OUT_LOW,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_RESET,

.config_val = GPIO_OUT_HIGH,

.delay = 10,

},

{

.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 = 0,

},

};

static struct msm_sensor_power_setting ov5648_power_down_setting[] = {

{

.seq_type = SENSOR_VREG,

.seq_val = CAM_VIO,

.config_val = 0,

.delay = 0,

},

{

.seq_type = SENSOR_VREG,

.seq_val = CAM_VAF,

.config_val = 0,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_VANA,

.config_val = GPIO_OUT_LOW,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_STANDBY,

.config_val = GPIO_OUT_LOW,

.delay = 5,

},

{

.seq_type = SENSOR_GPIO,

.seq_val = SENSOR_GPIO_RESET,

.config_val = GPIO_OUT_LOW,

.delay = 10,

},

{

.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 = 0,

},

};

二、Vendor部分

2.1 在Makefile文件中添加IC代码:

代码路径:srcLINUXandroidendorqcomproprietarycommonconfig

文件名:device-vendor.mk

需添加的代码:

MM_CAMERA += libchromatix_ov5648_oty5f03_common

MM_CAMERA += libchromatix_ov5648_oty5f03_default_video

MM_CAMERA += libchromatix_ov5648_oty5f03_preview

MM_CAMERA += libchromatix_ov5648_oty5f03_snapshot

MM_CAMERA += libchromatix_ov5648_oty5f03_zsl

MM_CAMERA += libmmcamera_ov5648_oty5f03

注意:如果这里没有添加以上代码,在编译的时候就不会生成相应的so文件。这so文件可以在srcLINUXandroidout argetproductmsm8916_32systemendorlib目录下找到,如下所示:

libchromatix_ov5648_oty5f03_common.so

libchromatix_ov5648_oty5f03_default_video.so

libchromatix_ov5648_oty5f03_preview.so

libchromatix_ov5648_oty5f03_snapshot.so

libchromatix_ov5648_oty5f03_zsl.so

libmmcamera_ov5648_oty5f03.so

2.2 添加Lib驱动代码:

代码路径:

srcLINUXandroidendorqcomproprietarymm-cameramm-camera2media-controllermodulessensorssensor_libs

文件夹名:ov5648_oty5f03

需添加的代码:

2.2.1 移植相机接口配置

这部分内容定义了传感器接口配置,包括I2C和MIPI。请确认设置不会和dtsi文件中的类似内容冲突。

static struct msm_camera_sensor_slave_info sensor_slave_info = {

/* Camera slot where this camera is mounted */

.camera_id = CAMERA_0,

/* sensor slave address */

.slave_addr = 0x6c,

/* sensor address type */

.addr_type = MSM_CAMERA_I2C_WORD_ADDR,

/* sensor id info*/

.sensor_id_info = {

/* sensor id register address */

.sensor_id_reg_addr = 0x300a,

/* sensor id */

.sensor_id = 0x5648,

},

/* power up / down setting */

.power_setting_array = {

.power_setting = ov5648_oty5f03_power_setting,

.size = ARRAY_SIZE(ov5648_oty5f03_power_setting),

.power_down_setting = ov5648_oty5f03_power_down_setting,

.size_down = ARRAY_SIZE(ov5648_oty5f03_power_down_setting),

},

};

static sensor_output_t sensor_output = {

.output_format = SENSOR_BAYER,

.connection_mode = SENSOR_MIPI_CSI,

.raw_output = SENSOR_10_BIT_DIRECT,

};

#ifndef VFE_40

static struct csi_lane_params_t csi_lane_params = {

.csi_lane_assign = 0xE4,

.csi_lane_mask = 0x3,

.csi_if = 1,

.csid_core = {0},

.csi_phy_sel = 0,

};

#else

static struct csi_lane_params_t csi_lane_params = {

.csi_lane_assign = 0x4320,

.csi_lane_mask = 0x3,

.csi_if = 1,

.csid_core = {0},

.csi_phy_sel = 1,

};

#endif

2.2.2 移植传感器输出配置

这部分内容介绍了传感器不同模式的配置和设置,包含各模式的I2C 寄存器设备、CSI参数、crop参数、传感器输出信息和chormatix数组。这些配置的数组大小应和传感器支持的模式种类相同。

static struct msm_camera_i2c_reg_setting res_settings[] = {

{

.reg_setting = res0_reg_array,

.size = ARRAY_SIZE(res0_reg_array),

.addr_type = MSM_CAMERA_I2C_WORD_ADDR,

.data_type = MSM_CAMERA_I2C_BYTE_DATA,

.delay = 0,

},

{

.reg_setting = res1_reg_array,

.size = ARRAY_SIZE(res1_reg_array),

.addr_type = MSM_CAMERA_I2C_WORD_ADDR,

.data_type = MSM_CAMERA_I2C_BYTE_DATA,

.delay = 0,

},

};

……

static struct msm_camera_csi2_params *csi_params[] = {

&ov5648_oty5f03_csi_params, /* RES 0*/

&ov5648_oty5f03_csi_params, /* RES 1*/

};

……

static struct sensor_crop_parms_t crop_params[] = {

{0, 0, 0, 0}, /* RES 0 */

{0, 0, 0, 0}, /* RES 1 */

};

……

static struct sensor_lib_out_info_t sensor_out_info[] = {

{

.x_output = 2592,

.y_output = 1944,

.line_length_pclk = 2816,

.frame_length_lines = 2380,

.vt_pixel_clk = 84000000,

.op_pixel_clk = 84000000,

.binning_factor = 1,

.max_fps = 12.5,

.min_fps = 7.5,

.mode = SENSOR_DEFAULT_MODE,

},

{

.x_output = 1296,

.y_output = 972,

.line_length_pclk = 1408,

.frame_length_lines = 992,

.vt_pixel_clk = 42000000,

.op_pixel_clk = 42000000,

.binning_factor = 1,

.max_fps = 30.0,

.min_fps = 7.5,

.mode = SENSOR_DEFAULT_MODE,

},

};

……

static struct sensor_lib_chromatix_t ov5648_oty5f03_chromatix[] = {

{

.common_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(common),

.camera_preview_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(snapshot), /* RES0 */

.camera_snapshot_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(snapshot), /* RES0 */

.camcorder_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(default_video), /* RES0 */

},

{

.common_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(common),

.camera_preview_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(preview), /* RES2 */

.camera_snapshot_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(preview), /* RES2 */

.camcorder_chromatix = OV5648_OTY5F03_LOAD_CHROMATIX(default_video), /* RES2 */

},

};

2.2.3 镜头信息移植

相机处理流程(比如曝光计算)需要镜头信息。因此,以下结构需添加正确的镜头信息。

static sensor_lens_info_t default_lens_info = {

.focal_length = 2.37,

.pix_size = 1.4,

.f_number = 2.4,

.total_f_dist = 1.97,

.hor_view_angle = 70.24,

.ver_view_angle = 52.68,

};

2.2.4 曝光配置移植

通常情况下,不同传感器有不同的曝光控制方式。所以,当传感器打开后,需移植曝光配置以成功调试传感器的曝光控制。

包括以下函数:

n ov5648_real_to_register_gain – 将实际逻辑增益转换为寄存器值。

n ov5648_register_to_real_gain – 将寄存器值转换成真实的逻辑增益。

n ov5648_calculate_exposure – 获取曝光时间和增益的另一个曝光配置.

n ov5648_fill_exposure_array – 准备另一个曝光配置数组。

2.3 添加Chromatix文件:

代码路径:

srcLINUXandroidendorqcomproprietarymm-cameramm-camera2media-controllermodulessensorschromatix1libchromatix

文件夹名:chromatix_ov5648_oty5f03

需添加的代码:

该部分主要是针对raw格式是摄像头,而yuv格式的摄像头不需要做该步骤,而这添加的内容主要是raw摄像头效果参数的.h文件,这需要向模组或IC厂索要该部分的文件。

android camera(3)--- 高通平台8916 camera移植相关推荐

  1. android camera (2) ---高通平台camera开发

    1. 设置摄像头方向 2. 打开线程与预览线程 3. 设置参数 4. Camera外设按键 5. 自动对焦与触摸对焦 6. 拍照 7. 人脸检测 8. 位置管理 9. 旋转管理 10. 变焦 11. ...

  2. android lcd调试 高通平台lcd调试深入分析总结(mipi和rgb接口)

    各位网友:最近发现我这篇文章转载的到处都是,有的则以原创存在,转载时请注明出处,还有文中错误的地方请指正!谢谢合作. 一:点亮lcd in kernel 其实点亮lcd很简单必须保证以后几个步骤正确: ...

  3. android 6.0 高通平台sensor 工作机制及流程(原创)

    最近工作上有碰到sensor的相关问题,正好分析下其流程作个笔记. 这个笔记分三个部分: sensor硬件和驱动的工作机制 sensor 上层app如何使用 从驱动到上层app这中间的流程是如何 Se ...

  4. android 6.0 高通平台sensor 工作机制及流程

    最近工作上有碰到sensor的相关问题,正好分析下其流程作个笔记. 这个笔记分三个部分: sensor硬件和驱动的工作机制 sensor 上层app如何使用 从驱动到上层app这中间的流程是如何 Se ...

  5. 高通平台MSM8916LCM模块移植(一)-bootloader部分

    此次移植打算分成两个模块来说,bootloader部分和kernel部分.在实际的移植调试过程中也是这么分成了两个部分分别调试. 高通平台中的bootloader叫做LK(Little Kernel, ...

  6. android ROM ---(1)高通平台 Android O 升级学习

    1. Android Project Treble 与iOS相比,安卓系统有一个致命弱点,那就是新版本系统升级太慢,除了谷歌Nexus和Pixel等亲儿子机型,其他OEM商的机型更新新系统需要用户漫长 ...

  7. Android 7.0 高通平台-telephony-机器无Sim卡情况下,获取SIM卡状态方法getSimState偶现为6,而不是1

    TelephonyManager.java -------->getSimState接口 /** * Returns a constant indicating the state of the ...

  8. 高通平台Camera 框架简介

    接触高通平台camera不长时间,了解的不够深入,下面个人所了解内容的是基于高通平台的camera,有的地方能描述不一定会很清楚,以后会慢慢补充! 一 框架介绍 Package -> Framw ...

  9. 高通平台camera 移植过程

    1  camera基本代码架构 高通平台对于camera的代码组织,大体上还是遵循Android的框架:即上层应用和HAL层交互,高通平台在HAL层里面实现自己的一套管理策略:在kernel中实现se ...

最新文章

  1. windows平台下vlc编译之一:编译环境构建(2008.12.03更新)
  2. 雅客EXCEL(5)-tab键、同组数据录入、提取重复值、提取身份证号码的出生日期
  3. Winform中设置ZedGraph的曲线为折线、点折线、散点图
  4. mybatis xml标签,批量插入
  5. python moviepy 音量_python moviepy 视频剪辑代码
  6. 拔染印花几点注意事项
  7. 剑指offer(C++)-JZ6:从尾到头打印链表(数据结构-链表)
  8. word表格删除空白行java_Java批量删除Word中的空白段落
  9. 计算机有什么简便快捷方法,运行快捷键(电脑常用快捷键大全)
  10. centos7系统时间校对(和北京时间同步)
  11. Microsoft SQL Server2005服务器安全与维护-李晨光-专题视频课程
  12. 麻省理工大学公开课笔记:算法导论(二)——课程简介及算法分析
  13. 23.Consent 代码重构
  14. CryEngine3SDK尝鲜
  15. HDMI2.0/HDCP2.2 4x2 矩阵——GSV2008
  16. python实现简单的神经网络,python的神经网络编程
  17. MarkText下载安装与初始设置 免费markdown的工具
  18. 无线路由Buffalo G300N V2 CH小测
  19. html字体颜色字号,(前端)html与css,css 5、颜色、字体、字号量取方式
  20. XQN-vivado fix类型

热门文章

  1. DMA(direct memory access)控制方式
  2. flush什么意思中文翻译_flush是什么意思
  3. GAN网络(Generative Adversarial Networks )
  4. python 数据结构转换层_python – 具有Maxpooling1D和channel_first的Keras模型
  5. pip命令安装pygeme后 IDLE import pygame报错
  6. 贝塞尔曲线UIBezierPath简单使用
  7. 170630、springboot编程之普通类中调用spring管理的bean对象
  8. 制作登录注册密码找回网站常用控件
  9. 关于解决 从相册中选择照片后无法剪切图片以及无法加载图片的问题
  10. 编写Javascript时的注意事项