4. 设备树中SPI节点配置

在Linux内核中,SPI总线设备的硬件拓扑与配置参数通过设备树(Device Tree)进行描述。设备树为驱动提供了与硬件解耦的静态描述机制,使得同一份内核镜像可以适配不同板级配置。SPI设备树节点主要分为两类:SPI控制器节点(描述SoC内部的SPI主机控制器)和SPI从设备节点(描述挂载在SPI总线上的外设)。正确配置这些节点是SPI通信正常工作的前提。

核心原则:设备树中的SPI节点必须严格遵循芯片厂商提供的binding文档。错误的reg值或缺失的spi-max-frequency属性是导致SPI通信失败的最常见原因之一。

4.1 SPI控制器节点

SPI控制器节点通常位于SoC的soc或ahb总线节点下,描述了SPI主机控制器的寄存器基址、中断号、时钟源、DMA请求线以及Pinctrl配置。控制器节点是SPI子系统的根节点,所有挂载在该控制器下的从设备节点都必须作为其子节点存在。

以下是一个典型的SPI控制器节点示例(以i.MX6ULL为例):

&ecspi1 {
    pinctrl-names = "default";
    pinctrl-0 = &pinctrl_ecspi1;
    cs-gpios = <&gpio4 9 GPIO_ACTIVE_LOW>;
    status = "okay";

    spidev0: spidev@0 {
        compatible = "spidev";
        reg = <0>;
        spi-max-frequency = <1000000>;
    };
};

控制器节点关键属性说明:

属性名 类型 说明 是否必须
compatible 字符串 匹配驱动,如"fsl,imx6ul-ecspi" 是
reg u32数组 控制器寄存器基址和长度 是
interrupts u32数组 SPI中断号及触发类型 是
clocks phandle数组 SPI模块时钟和PIO时钟 是
pinctrl-0 phandle 引脚复用配置 推荐
cs-gpios gpio数组 片选GPIO列表(软件片选模式) 可选
dmas phandle数组 DMA传输通道 可选
status 字符串 "okay"或"disabled" 是
调试要点:如果SPI控制器节点缺少pinctrl配置,内核将无法正确配置SCLK、MOSI、MISO和CS引脚的复用功能,导致SPI总线无时钟输出。检查/sys/kernel/debug/gpio和cat /sys/kernel/debug/pinctrl/*/pinmux-pins可以验证引脚状态。
SPI设备树节点层级关系 / (根节点) soc / ahb 总线 SPI控制器节点 (ecspi1) compatible, reg, interrupts, clocks, pinctrl 从设备节点0 (spidev@0) reg=<0>, spi-max-frequency compatible = "spidev" 从设备节点1 (adc@1) reg=<1>, spi-max-frequency compatible = "ti,ads1256" 说明 从设备节点必须作为控制器节点的子节点;reg值对应硬件片选索引(CS0/CS1) 每个从设备节点独立配置spi-max-frequency,不能超过控制器支持的最高频率

4.2 SPI从设备节点

SPI从设备节点描述了挂载在SPI总线上的具体外设。每个从设备节点必须包含compatible、reg和spi-max-frequency三个核心属性。从设备节点是驱动匹配的入口,内核通过compatible属性查找对应的SPI设备驱动。

从设备节点典型结构:

&ecspi1 {
    status = "okay";

    /* 第一个从设备:温度传感器 */
    temp_sensor: max31865@0 {
        compatible = "maxim,max31865";
        reg = <0>;
        spi-max-frequency = <5000000>;
        spi-cpha;
        spi-cpol;
        status = "okay";
    };

    /* 第二个从设备:ADC转换器 */
    adc_device: ads1256@1 {
        compatible = "ti,ads1256";
        reg = <1>;
        spi-max-frequency = <19200000>;
        interrupts-extended = <&gpio5 19 IRQ_TYPE_EDGE_FALLING>;
        status = "okay";
    };
};

4.3 reg属性详解

reg属性在SPI从设备节点中表示该设备使用的片选(Chip Select, CS)索引号。SPI控制器通常支持多个片选信号(CS0、CS1、CS2...),每个片选对应一条独立的硬件CS线。内核通过解析reg值来确定在发起SPI传输时应该拉低哪条CS线。

reg值 对应片选 典型硬件连接 注意事项
0 CS0 连接从设备的CS引脚 大多数SPI控制器默认支持CS0
1 CS1 连接第二个从设备的CS引脚 需要控制器硬件支持多片选
2 CS2 连接第三个从设备的CS引脚 部分控制器通过GPIO模拟扩展
常见错误:如果两个从设备节点使用了相同的reg值(例如都设为0),内核在注册SPI设备时会报错:spi_master spi0: chipselect 0 already in use。此时第二个设备将无法注册成功。务必确保每个从设备的reg值在同一个控制器下唯一。

4.4 spi-max-frequency属性

spi-max-frequency定义了该从设备支持的最高SPI时钟频率,单位是Hz。内核SPI核心层在初始化传输时会读取该属性,并将其作为SCLK频率的上限。实际传输频率由控制器驱动根据硬件能力向下取整。

频率配置原则:

  • 不能超过控制器支持的最高频率:例如i.MX6ULL的ECSPI最高频率为60MHz,设置spi-max-frequency = <100000000>会被内核自动截断。
  • 不能超过从设备数据手册规定的最高频率:例如某SPI Flash最高支持50MHz,设置80MHz会导致通信不稳定或数据错误。
  • 频率越低,信号完整性越好:在长距离传输或高噪声环境下,适当降低频率可以提高通信可靠性。
/* 频率配置示例 */
/* 低速传感器,最高1MHz */
spi-max-frequency = <1000000>;

/* 高速SPI Flash,最高50MHz */
spi-max-frequency = <50000000>;

/* 调试阶段建议使用较低频率,排除时序问题 */
spi-max-frequency = <500000>;  /* 500KHz,适合调试 */

4.5 SPI模式属性(spi-cpha / spi-cpol)

SPI有四种工作模式,由时钟极性(CPOL)和时钟相位(CPHA)组合决定。设备树通过以下布尔属性配置SPI模式:

属性 含义 SPI模式 典型设备
无(默认) CPOL=0, CPHA=0 模式0 多数SPI Flash、SD卡
spi-cpha CPOL=0, CPHA=1 模式1 部分ADC、DAC
spi-cpol CPOL=1, CPHA=0 模式2 某些温度传感器
spi-cpol; spi-cpha; CPOL=1, CPHA=1 模式3 部分MEMS传感器
/* 模式3配置示例 */
spi-cpol;   /* 时钟空闲时为高电平 */
spi-cpha;   /* 数据在时钟的第二个边沿采样 */
调试技巧:如果SPI通信出现数据错位或CRC错误,首先检查SPI模式是否匹配。使用逻辑分析仪抓取SCLK和MOSI波形,对比数据手册中的时序图,确认CPOL和CPHA设置正确。模式不匹配是SPI调试中最隐蔽的问题之一。

4.6 其他关键属性

除了上述核心属性外,SPI从设备节点还支持以下常用属性:

  • spi-cs-high:片选信号高电平有效(默认低电平有效)。某些设备要求CS在高电平时被选中。
  • spi-3wire:使用三线制SPI(省略MISO或MOSI),适用于半双工设备。
  • spi-lsb-first:数据以LSB(最低有效位)优先传输(默认MSB优先)。
  • spi-rx-bus-width 和 spi-tx-bus-width:用于Quad SPI或Dual SPI模式,设置数据线宽度。
  • interrupts 或 interrupts-extended:从设备的中断引脚,用于事件通知。
/* 完整配置示例:使用四线SPI的Flash设备 */
spi_flash: flash@0 {
    compatible = "jedec,spi-nor";
    reg = <0>;
    spi-max-frequency = <80000000>;
    spi-rx-bus-width = <4>;   /* Quad SPI读取 */
    spi-tx-bus-width = <4>;   /* Quad SPI写入 */
    spi-cpol;
    spi-cpha;
    m25p,fast-read;
    status = "okay";
};

4.7 常见配置错误与排查方法

设备树SPI节点配置错误会导致驱动无法加载或通信异常。以下汇总了最常见的错误场景及排查方法:

错误现象 可能原因 排查方法
驱动probe不执行 compatible不匹配或status不是"okay" 检查/sys/bus/spi/devices目录是否存在设备节点
SPI时钟无输出 pinctrl配置缺失或错误 检查/sys/kernel/debug/pinctrl引脚复用状态
数据全部为0xFF 片选未正确拉低或MISO连接错误 用示波器测量CS和MISO引脚电平
数据错位 SPI模式(CPOL/CPHA)不匹配 逻辑分析仪抓取波形,对比数据手册时序
传输超时 spi-max-frequency过高或DMA配置错误 降低频率测试,关闭DMA使用PIO模式
设备注册失败 reg值冲突或控制器节点status为disabled 查看dmesg中spi_master相关错误日志
快速验证命令:在系统启动后,执行ls /sys/bus/spi/devices/查看已注册的SPI设备。如果设备节点存在但驱动未绑定,执行cat /sys/bus/spi/devices/spi0.0/modalias查看内核匹配的驱动名称,与设备树中的compatible对比。
SPI设备树配置错误排查流程 SPI通信异常 检查设备树status是否为"okay" 验证compatible与驱动匹配 确认reg值唯一且CS连接正确 检查spi-max-frequency是否合理 验证CPOL/CPHA模式与设备匹配 每步排查后使用dmesg查看内核日志,结合示波器/逻辑分析仪验证硬件信号