一、飞控总线概览:为什么飞控需要SPI和I2C?

做飞控这些年,我经常被刚入行的朋友问到一个问题:"飞控板上那么多传感器,为什么非得用SPI和I2C?直接用串口不行吗?"

嗯,这个问题问得挺好。说白了,飞控就是一个实时数据采集与处理系统。它需要在极短的时间内,把陀螺仪、加速度计、气压计、磁力计、GPS模块的数据全部读进来,然后算出姿态,再输出控制信号给电机。

你想想看,如果每个传感器都用串口——那飞控主控得有多少个UART外设?而且串口是一对一的,一个口只能接一个设备,板子上的走线会乱成一锅粥。

所以,SPI和I2C就是为这种"一主多从"的场景设计的。它们用很少的引脚,就能挂载多个传感器。我在项目中遇到过最极端的情况:一块飞控板上挂了6个SPI设备和4个I2C设备,总共只用了不到20个GPIO。

为什么飞控离不开这两种总线?

我个人的习惯是,把飞控上的设备分成两类:

  • 高速、大数据量设备:比如IMU(惯性测量单元)、外部Flash存储芯片。这些设备需要频繁读写,数据量大,延迟要求高。SPI是首选。
  • 低速、小数据量设备:比如气压计、磁力计、温度传感器。这些设备数据更新率低,但对功耗和引脚数量敏感。I2C更合适。

说白了,SPI负责"快准狠",I2C负责"多省稳"。两者互补,缺一不可。

核心观点:飞控的实时性要求决定了总线选型。SPI提供低延迟高吞吐,I2C提供多设备挂载能力。没有哪一种总线能包打天下。

二、SPI与I2C的物理层对比

这部分是硬核知识。我建议你对照着手边的飞控原理图来看,会更有感觉。

引脚数量对比

特性 SPI I2C
最少引脚数 4根(MOSI, MISO, SCLK, CS) 2根(SDA, SCL)
每增加一个从设备 增加1根CS片选线 无需增加引脚(地址区分)
全双工能力 支持(同时收发) 不支持(半双工)

这里有个细节:SPI的CS片选线是硬伤。我记得有一次设计飞控,要挂5个SPI设备,结果主控的GPIO不够用了,最后不得不加了一个GPIO扩展芯片。而I2C就没有这个问题,7位地址最多能挂127个设备,飞控上那三五个传感器根本不在话下。

速率对比

特性 SPI I2C
标准速率 10MHz ~ 80MHz(常见) 100kHz(标准模式)
高速模式 可达100MHz以上 3.4MHz(高速模式)
实际飞控常用 10MHz ~ 20MHz 400kHz(快速模式)

为什么会这样?SPI没有协议开销,主控直接拉低CS,然后按时钟节拍收发数据,干净利落。而I2C每次通信都要先发设备地址、读写位,还要等ACK应答,光协议开销就占了20%~30%的带宽。

个人经验:飞控上的IMU(比如MPU6000、ICM20602),我建议用SPI。因为IMU的数据输出频率通常在1kHz~8kHz,每次要读6轴或9轴数据,数据量不小。用I2C的话,400kHz的速率读一次要几十微秒,而SPI 10MHz只需要几微秒。这几十微秒的差距,在飞控的1ms控制周期里,可能就是生与死的区别。

拓扑结构对比

先看一张我画的对比图,帮你建立直观印象:

SPI与I2C拓扑结构对比 SPI(星型拓扑) 主控 从设备1 从设备2 从设备3 CS1 CS2 CS3 共享:MOSI, MISO, SCLK I2C(总线型拓扑) 主控 R R 从设备1 地址: 0x68 从设备2 地址: 0x76 从设备3 地址: 0x77 SDA (数据线) SCL (时钟线) 每个从设备独占一根CS线 所有设备共享两根总线,通过地址区分

从图上可以看得很清楚:SPI是星型拓扑,主控和每个从设备之间都有独立的片选线。而I2C是总线型拓扑,所有设备都挂在同两根线上,通过地址来区分。

物理层差异总结

  • SPI:引脚多,速率高,全双工,适合高速传感器和存储芯片。缺点是占用的GPIO多,走线复杂。
  • I2C:引脚少,速率低,半双工,适合低速传感器和配置芯片。缺点是速率受限,且总线电容不能太大(一般不超过400pF)。

避坑指南:我曾经在一个项目中,把I2C总线拉得太长(超过30cm),结果通信时好时坏。后来用示波器一看,SCL和SDA的上升沿都变成了圆弧形——总线电容太大了。解决办法是降低I2C速率到100kHz,或者用更小的上拉电阻。但最根本的,还是布线要短,走线要粗

飞控上的实际应用场景

我列一个典型的飞控传感器分配表,你一看就明白了:

传感器类型 推荐总线 原因
IMU(陀螺仪+加速度计) SPI 高数据率,低延迟要求
气压计(MS5611、BMP280) I2C 数据率低,功耗敏感
磁力计(HMC5883、IST8310) I2C 数据率低,引脚节省
外部Flash(W25Q系列) SPI 大数据量读写,需要高速
GPS模块 UART 标准协议,距离远

你看,SPI和I2C各有各的阵地。IMU这种"心脏级"传感器,必须用SPI保证实时性。而气压计、磁力计这些"辅助级"传感器,用I2C就足够了,还能省下宝贵的GPIO。

一个小技巧:如果你发现飞控上的I2C设备通信不稳定,先别急着怀疑代码。拿万用表量一下SDA和SCL对地的电压——正常应该是3.3V(或1.8V,取决于你的系统电压)。如果电压偏低,说明上拉电阻太小;如果波形圆润,说明总线电容太大。我遇到过好几次,最后发现是PCB布局时把I2C走线绕了太远。

好了,这一章我们聊了飞控为什么需要SPI和I2C,以及它们在物理层上的差异。下一章我们会深入SPI的通信协议细节,包括时钟极性、相位这些让新手头疼的概念。到时候我会用实际飞控的波形图来讲解,保证你一看就懂。


专注资料整理