MTK android11 平台 Camera Sensor以 IMX335 为例 移植完整指南

移植一颗新 sensor 到 MTK 平台,改驱动只是开始。真正让你加班的是散落在 10 多个目录里的配置文件 —— 漏一个就是不同的故障现象,而且报错信息几乎不会告诉你漏了哪个。
> 本文以 Sony IMX335(5MP MIPI RAW,工业/安防常用)移植到 MTK ISP_50 平台为例,梳理完整流程、给出检查清单、重点讲 7 个最容易踩的坑。

## 适用范围

| 项目 | 版本 |
|------|------|
| 芯片 | MTK MT67xx / MT68xx (ISP_50) |
| Android | 9 ~ 14 |
| Kernel | 4.14 / 4.19 / 5.10 |
| Sensor | Sony IMX335 5MP (2592x1944, MIPI 4-lane) |
| Sensor 类型 | MIPI RAW(CSI 接入)|

不同内核版本的路径略有差异,但整体流程和坑是一样的。

## 移植全景图

先看全局,再逐步展开。**加粗的是最容易遗漏的步骤**:

```
┌───────────────── Kernel 层 ─────────────────┐
│ 1. kd_imgsensor.h 注册 SENSOR_ID + DRVNAME  │
│ 2. imgsensor_sensor_list 注册(v1 + v1_1)   │
│ 3. imgsensor_cfg_table.c 电源时序            │
│ 4. defconfig 添加 sensor 名                  │
└──────────────────────────────────────────────┘
         ↓
┌───────────── Device 层(易漏)──────────────┐
│ 5. kernel-headers/kd_imgsensor.h 同步副本   │
└──────────────────────────────────────────────┘
         ↓
┌───────────────── HAL 层 ─────────────────────┐
│ 6. ProjectConfig.mk 四个 IMGSENSOR 变量      │
│ 7. imgsensor/ver1/{sensor}/ — 3A/ISP 参数    │
│ 8. imgsensor_metadata/{sensor}/ — 平台 meta  │
│ 9. sendepfeature/{sensor}/ — feature table   │
│ **10. common/hal/.../sensor/{sensor}/ (最致命)**│
│ 11. sensorlist.cpp 注册                      │
│ 12. cfg_setting_imgsensor.cpp 配置           │
└──────────────────────────────────────────────┘
         ↓
┌───────────────── 参数调整 ────────────────────┐
│ 13. 分辨率、镜头、对焦模式匹配               │
└──────────────────────────────────────────────┘
```

## Step 1-4:Kernel 驱动注册

### 1.1 注册 SENSOR_ID

在 `kd_imgsensor.h` 中新增 sensor 的 ID 宏和驱动名字符串:

```c
// kd_imgsensor.h — 新增两行
#define IMX335_SENSOR_ID                0x0335
#define SENSOR_DRVNAME_IMX335_MIPI_RAW  "imx335_mipi_raw"
```

### 1.2 注册驱动入口

两个文件需要同步修改:

| 文件 | 修改 |
|------|------|
| `imgsensor_sensor_list.h` | 声明 `IMX335_MIPI_RAW_SensorInit()` 函数原型 |
| `imgsensor_sensor_list.c` | 添加到 `kdSensorList[]` 数组 |

**注意:v1 和 v1_1 两个目录都要放驱动代码。** 原因见踩坑 #3。

### 1.3 电源时序

在 `imgsensor_cfg_table.c` 中添加你 sensor 的上电序列:

```c
// 关键:顺序和电压必须严格按 datasheet
{RST,       Vol_Low,  0},
{DOVDD,     Vol_1800, 0},
{AVDD,      Vol_2900, 0},    // ← IMX335 需要 2.9V,不是标准 2.8V!
{DVDD,      Vol_1200, 1},
{SensorMCLK,Vol_High, 1},
{RST,       Vol_High, 2}
```

### 1.4 defconfig

```
CONFIG_CUSTOM_KERNEL_IMGSENSOR="imx335_mipi_raw ..."
```

## Step 5:Device 层 kernel-headers 同步

```
device/mediatek/common/kernel-headers/kd_imgsensor.h
```

这是一个**独立的副本**,不会自动和 kernel 的 `kd_imgsensor.h` 同步。HAL 编译时引用的是这个文件。**漏改 = HAL 编译找不到 SENSOR_ID 定义。**

## Step 6-12:HAL 层(核心,也是坑最多的地方)

### 6. ProjectConfig.mk

四个变量都要配:

```makefile
CUSTOM_HAL_IMGSENSOR = imx335_mipi_raw ...
CUSTOM_HAL_MAIN_IMGSENSOR = imx335_mipi_raw    # 主摄
CUSTOM_KERNEL_IMGSENSOR = imx335_mipi_raw ...
CUSTOM_KERNEL_MAIN_IMGSENSOR = imx335_mipi_raw
```

少配一个,sensor 能检测到但 HAL 不认。

### 7-10. 四个 HAL 目录(最容易出错)

这是整个移植中最让人头疼的部分 —— **需要创建 4 个目录**,通常从已有 sensor(如 imx258)拷贝并重命名:

| # | 目录路径 | 文件数 | 说明 |
|---|---------|--------|------|
| 1 | `custom/{chip}/hal/imgsensor/ver1/{sensor}/` | ~50+ | 3A/ISP 调优参数 |
| 2 | `custom/{chip}/hal/imgsensor_metadata/{sensor}/` | ~6 | 平台级 metadata |
| 3 | `custom/{chip}/hal/sendepfeature/{sensor}/` | 1 | Feature table |
| **4** | **`custom/common/hal/imgsensor_metadata/sensor/{sensor}/`** | **1** | **Common metadata** |

**第 4 个目录只有 1 个头文件,却是最致命的坑。** 详见踩坑 #5。

### 11-12. 注册和配置

| 文件 | 修改 |
|------|------|
| `sensorlist.cpp` | 添加到 `SensorList[]` |
| `cfg_setting_imgsensor.cpp` | 配置 MCLK、CSI port、FOV 等 |

## Step 13:参数调整

从参考 sensor 拷贝的参数不能直接用,至少要改这些:

| 参数类别 | 必须调整的项 |
|---------|-------------|
| 分辨率 | `ACTIVE_ARRAY_SIZE`、`PHYSICAL_SIZE`、grabwindow |
| 镜头 | 光圈值、焦距 |
| 对焦 | 定焦 sensor 必须关闭 AF,Focus mode 改 `INFINITY + FIXED` |
| GIS | 分辨率和焦距要匹配 |

## 踩坑实录(7 个坑,个个要命)

### 坑 1:I2C 地址搞反(最常见)

模组图纸标的地址和实际地址可能不同,取决于 SLASEL 引脚电平。**先量 SLASEL 电平,再定 I2C 地址。**

MTK imgsensor 框架的 `i2c_addr_table` 填的是 **8-bit write 地址**,框架内部自动右移。如果你填了 7-bit 地址,会被二次右移,通信直接挂。

```c
.i2c_addr_table = {0x34, 0x6C, 0xff},  // ← 8-bit write 地址!
```

**定位方法**:I2C 通信失败一般是 `errno -6 (NACK)`。如果 sensor ID 读出全 0 或 0xFF,先查地址。

### 坑 2:电源时序漏配

`imgsensor_cfg_table.c` 里没有新 sensor 的条目 = sensor 根本没上电 = I2C 全部 ACK error。

**现象**:和坑 1 一样,sensor ID 读出 0/0xFF。区别在于示波器看 I2C 总线上根本没有信号(SDA/SCL 全低),说明是电源问题不是地址问题。

**额外注意**:有些 sensor 的 AVDD 不是标准 2.8V(比如 2.9V),务必查 datasheet 确认每路电源电压。

### 坑 3:v1 和 v1_1 都要放驱动

MTK 有一个 flicker 工具 `genimginfo.py`,它从 `common/v1_1/` 目录搜索驱动信息。只在 `common/v1/` 放驱动会导致编译报错,而且**错误信息完全看不出是因为 v1_1 缺文件**。

**建议**:v1 和 v1_1 放相同代码,改一处同步到另一处。

### 坑 4:device kernel-headers 不同步

上面 Step 5 已经说了。这个坑的恶心之处在于 —— **编译报错说的是 "undeclared identifier",你会下意识去查 kernel 的头文件,发现明明写了**。实际上 HAL 用的是 device 层的副本。

### 坑 5:第 4 个 HAL metadata 目录(最致命!)

```
custom/common/hal/imgsensor_metadata/sensor/{sensor_name}/
```

这个目录只有 **1 个头文件**:`config_static_metadata.sensor.{sensor}mipiraw.h`

但缺了它,**camerahalserver 会 SIGABRT 崩溃无限重启**。

原因链条:
1. 编译时该文件生成 `constructCustStaticMetadata_COMMON_SENSOR_*` 符号
2. 缺文件 = 缺符号 = `libcam.halsensor.so` 中没有对应函数
3. HAL 启动时 `checkSensorData()` 发现 `SENSITIVITY_RANGE` 为空
4. 直接 `abort()`

**定位方法**:
```bash
logcat | grep "camerahalserver\|SIGABRT\|checkSensorData"
```

看到反复出现 camerahalserver 崩溃 + SIGABRT,**第一件事就是检查这个目录**。

### 坑 6:Group Hold 时序导致 AE 暴动

某些 sensor 的曝光计算方式比较特殊。以 IMX335 为例,曝光 = VMAX - SHR0,和常见 sensor 的正向线性关系完全不同。如果 VMAX、SHR0、GAIN 不在同一个 group hold 事务中写入,中间帧的曝光值是错误的组合,导致 AE 反馈失调。

**现象**:画面忽亮忽暗,AE 在极端值间跳动。

**思路**:确保 `set_shutter` 和 `set_gain` 最终在一个 group hold 内统一写入所有相关寄存器。具体实现方式因 sensor 而异,需要看 datasheet 的 group hold 章节。

> IMX335 的 AE 暴动问题我们踩了很深的坑,涉及 MTK ISP_50 AE 算法的 9 层限制机制,后续会专门写一篇深度分析。

### 坑 7:AVDD 电压非标准

不是所有 sensor 都是 AVDD 2.8V。IMX335 就需要 **AVDD 2.9V**(Vol_2900)。填错电压可能出现两种情况:
- 偏低:sensor 不工作或 I2C 不稳定
- 偏高:sensor 短期能用但长期可能损坏

**原则**:每路电源电压必须查 datasheet 确认,不要想当然从参考 sensor 拷贝。

## 移植检查清单

**移植完成后逐项对照,避免遗漏:**

```
Kernel 层
  [ ] kd_imgsensor.h 加 SENSOR_ID + DRVNAME
  [ ] imgsensor_sensor_list.h/.c 注册(v1 + v1_1 两处)
  [ ] imgsensor_cfg_table.c 电源时序(电压逐路确认)
  [ ] defconfig 加 sensor 名

Device 层
  [ ] kernel-headers/kd_imgsensor.h 同步

HAL 层
  [ ] ProjectConfig.mk 四个 IMGSENSOR 变量
  [ ] imgsensor/ver1/{sensor}/ — 3A 参数目录
  [ ] imgsensor_metadata/{sensor}/ — platform metadata
  [ ] sendepfeature/{sensor}/ — feature table
  [ ] common/hal/imgsensor_metadata/sensor/{sensor}/ — 最易漏!
  [ ] sensorlist.cpp 注册
  [ ] cfg_setting_imgsensor.cpp 配置

参数
  [ ] 分辨率 ACTIVE_ARRAY / PHYSICAL_SIZE 已改
  [ ] 镜头光圈/焦距已改
  [ ] 定焦 sensor 已关闭 AF
  [ ] GIS 参数已匹配
```

## 总结

MTK Camera Sensor 移植的核心难点不在驱动本身,而在于 **10+ 个分散目录的文件需要逐一创建和配置**。报错信息往往指向别处,很难直接定位到"漏了哪个目录"。

两条实战建议:
1. **建自己的检查清单**(上面那个可以直接用)—— 每次移植照着过一遍,比什么经验都管用
2. **先跑通一颗参考 sensor**(如 imx258),确认全流程没问题后再改成目标 sensor —— 这样出了问题至少能二分定位
 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

海蓝光科技

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值