4. Sensor 寄存器配置基础:I2C/SPI 通信协议、寄存器地址与数据格式、常用寄存器组

Sensor 的寄存器配置是图像传感器工作的“大脑”。所有曝光时间、增益大小、帧率、输出格式等行为,都通过读写内部寄存器实现。本章聚焦于物理层通信协议(I2C/SPI)、寄存器寻址与数据格式,以及最核心的增益、曝光、帧长、行长寄存器组。

4.1 I2C 与 SPI 通信协议对比

Sensor 与 ISP/主控之间的控制通道通常采用 I2C 或 SPI。两者在引脚数、速率、拓扑结构上差异明显,选型需根据项目需求权衡。

特性I2C(Inter-Integrated Circuit)SPI(Serial Peripheral Interface)
引脚数2 线:SCL(时钟)、SDA(数据)4 线:SCLK、MOSI、MISO、CS
拓扑多主多从,总线式一主多从,片选独立
速率标准 100kHz / 快速 400kHz / 高速 3.4MHz通常 10MHz ~ 50MHz,甚至更高
寻址方式7 位或 10 位设备地址 + 寄存器地址片选信号 + 无设备地址
数据方向半双工,主从双向共用 SDA全双工,MOSI/MISO 独立
抗干扰开漏输出,上拉电阻,适合短距离推挽输出,信号完整度更好
典型场景手机摄像头、消费类 Sensor工业相机、高帧率 Sensor、多 Sensor 同步
选型建议: 对于 1080P@30fps 以下的 Sensor 配置,I2C 400kHz 足够;对于 4K@60fps 或需要频繁改写多组寄存器的场景,推荐使用 SPI 以提高配置吞吐量。

4.1.1 I2C 读写时序

I2C 写操作流程:主设备发送起始条件 → 设备地址 + 写位 → 从设备 ACK → 寄存器高字节地址 → ACK → 寄存器低字节地址 → ACK → 数据字节 → ACK → 停止条件。

// I2C 写 2 字节数据到 16 位地址寄存器示例(伪代码)
uint8_t write_buf[4];
write_buf[0] = (reg_addr >> 8) & 0xFF;  // 地址高字节
write_buf[1] = reg_addr & 0xFF;         // 地址低字节
write_buf[2] = (data >> 8) & 0xFF;      // 数据高字节
write_buf[3] = data & 0xFF;             // 数据低字节
i2c_master_write(dev_addr, write_buf, 4);
I2C 写寄存器时序(16位地址 + 16位数据) S Dev Addr+W ACK Addr[15:8] ACK Addr[7:0] ACK Data[15:8] ACK Data[7:0] ACK P 主设备每发送一个字节后,从设备必须回复 ACK(低电平),否则通信终止 16位寄存器地址通常分高8位和低8位两次发送,大端序(MSB first)

4.1.2 SPI 读写时序

SPI 写操作:CS 拉低 → 在 SCLK 上升沿发送 8 位命令(通常写命令为 0x02)→ 发送 16 位寄存器地址 → 发送 N 字节数据 → CS 拉高。

// SPI 写 2 字节到 16 位地址寄存器示例(伪代码)
uint8_t spi_tx[5];
spi_tx[0] = 0x02;                    // 写命令
spi_tx[1] = (reg_addr >> 8) & 0xFF; // 地址高字节
spi_tx[2] = reg_addr & 0xFF;        // 地址低字节
spi_tx[3] = (data >> 8) & 0xFF;     // 数据高字节
spi_tx[4] = data & 0xFF;            // 数据低字节
spi_cs_low();
spi_transfer(spi_tx, 5);
spi_cs_high();
SPI 写寄存器时序(16位地址 + 16位数据) CS 0x02 Addr[15:8] Addr[7:0] Data[15:8] Data[7:0] SPI 无 ACK 机制,主设备只管发送,从设备在 MISO 上可同时返回状态或数据 CS 在整个传输过程中保持低电平,传输结束后拉高

4.2 寄存器地址与数据格式

Sensor 寄存器地址长度通常为 8 位或 16 位,数据宽度多为 8 位、16 位或 32 位。理解地址映射规则和数据排列方式,是正确配置 Sensor 的前提。

4.2.1 地址映射规则

  • 8 位地址空间: 常见于低分辨率 Sensor,寄存器数量少,地址范围 0x00 ~ 0xFF。
  • 16 位地址空间: 主流 Sensor 采用,地址范围 0x0000 ~ 0xFFFF,支持大量功能寄存器。
  • 页切换(Page): 部分 Sensor 将寄存器分组到不同页,通过页选择寄存器切换访问。
// 页切换示例(以 OV5640 为例)
// 切换到页 0
i2c_write(0x3008, 0x82);  // 软件复位
i2c_write(0x3100, 0x01);  // 页选择寄存器 = 0x01 表示页 0
// 切换到页 1
i2c_write(0x3100, 0x05);  // 页选择寄存器 = 0x05 表示页 1

4.2.2 数据格式与位域操作

寄存器数据通常以 大端序(Big-Endian) 存储,即高字节在前、低字节在后。多字节寄存器需要按位域拆分,避免误写保留位。

位域寄存器地址位 [7:4]位 [3:0]
增益控制0x3503增益模式(0x0=模拟,0x1=数字)保留(写 0)
曝光高字节0x3500曝光时间高 8 位
曝光低字节0x3501曝光时间低 8 位
常见错误: 直接对整个寄存器赋值,未保留位被意外改写,导致 Sensor 进入异常模式。务必使用“读-改-写”模式或按位域掩码操作。
// 读-改-写示例:设置增益模式为数字增益,保留其他位
uint8_t reg_val = i2c_read(0x3503);
reg_val &= 0x0F;          // 清除高 4 位
reg_val |= (0x01 << 4);  // 设置位 [7:4] = 0x1(数字增益模式)
i2c_write(0x3503, reg_val);

4.3 常用寄存器组详解

AE 联调中最常操作的寄存器组包括:增益、曝光时间、帧长(VTS)、行长(HTS)。这四个参数直接决定图像亮度和帧率。

4.3.1 增益寄存器(Gain)

增益分为模拟增益(Analog Gain)和数字增益(Digital Gain)。模拟增益在像素读出前放大信号,噪声较低;数字增益在 ADC 之后放大,会放大噪声。

  • 模拟增益: 通常以 0.1dB 或 0.3dB 步进,范围 1x ~ 16x。
  • 数字增益: 范围 1x ~ 8x,步进 0.125x。
  • 全局增益: 部分 Sensor 提供组合增益寄存器,自动分配模拟/数字比例。
// 设置模拟增益为 2x(假设增益寄存器 0x3503 步进为 0.1dB)
// 2x = 6.02dB → 6.02 / 0.1 = 60 → 0x3C
i2c_write(0x3503, 0x3C);

4.3.2 曝光时间寄存器(Exposure / Shutter)

曝光时间通过控制电子快门的行数(Line Count)实现。曝光行数 × 行时间 = 实际曝光时间。

  • 曝光行数寄存器: 通常为 16 位或 20 位,地址连续。
  • 最大曝光行数: 受帧长(VTS)限制,通常 ≤ VTS - 4(预留消隐行)。
  • 最小曝光行数: 受 Sensor 最小消隐要求限制,通常 ≥ 1 行。
// 设置曝光行数为 1000 行(16 位寄存器 0x3500-0x3501)
uint16_t exposure_lines = 1000;
i2c_write(0x3500, (exposure_lines >> 8) & 0xFF);  // 高字节
i2c_write(0x3501, exposure_lines & 0xFF);         // 低字节

4.3.3 帧长寄存器(VTS / Vertical Total Size)

帧长决定一帧图像的总行数,包括有效行和垂直消隐行。帧长直接影响帧率:帧率 = PCLK / (HTS × VTS)。

  • VTS 寄存器: 通常为 16 位,地址如 0x320E-0x320F。
  • 调整影响: 增大 VTS 会降低帧率,但可增加最大曝光行数。
  • AE 联动: 当曝光行数接近 VTS 时,AE 算法需考虑是否扩展 VTS 以增加曝光空间。
// 设置帧长为 1500 行
uint16_t vts = 1500;
i2c_write(0x320E, (vts >> 8) & 0xFF);
i2c_write(0x320F, vts & 0xFF);

4.3.4 行长寄存器(HTS / Horizontal Total Size)

行长决定一行像素的总数,包括有效像素和水平消隐。行长通常固定,但部分 Sensor 支持调整以微调帧率。

  • HTS 寄存器: 通常为 16 位,地址如 0x320C-0x320D。
  • 固定场景: 多数 Sensor 在初始化时设定 HTS,AE 联调中不修改。
  • 动态场景: 高帧率模式可能需要减小 HTS 以压缩行时间。
// 设置行长为 2200 像素(含消隐)
uint16_t hts = 2200;
i2c_write(0x320C, (hts >> 8) & 0xFF);
i2c_write(0x320D, hts & 0xFF);

4.4 常用寄存器组关系图

AE 联调核心寄存器组关系 增益寄存器 模拟/数字增益 曝光寄存器 曝光行数 帧长 VTS 总行数 行长 HTS 每行像素数 曝光行数 ≤ VTS - 消隐行数;帧率 = PCLK / (HTS × VTS);增益与曝光共同决定图像亮度

4.5 实战配置流程

  1. 初始化通信: 配置 I2C/SPI 控制器速率、引脚、模式。
  2. 读取 Sensor ID: 验证通信正常,读取芯片 ID 寄存器(如 0x300A-0x300B)。
  3. 写入初始化序列: 按 datasheet 写入 PLL、分辨率、输出格式等寄存器。
  4. 设置帧长和行长: 确定目标帧率,计算 VTS 和 HTS 并写入。
  5. 设置初始曝光和增益: 写入默认曝光行数和增益值。
  6. 启动视频流: 写入启动寄存器(如 0x0100 = 0x01)。
  7. AE 联调: 根据亮度反馈,动态调整曝光和增益寄存器。
关键检查点: 每次写入寄存器后,建议回读验证,确保写入值与目标值一致。尤其在 I2C 总线负载高时,可能出现 NACK 导致写入失败。