第三讲:时钟相位 CPHA 深入理解——采样边沿与相位偏移

上一讲我把 CPOL 讲透了,极性说白了就是时钟空闲时的电平。这一讲轮到相位 CPHA —— 这才是 SPI 通信里最容易踩坑的地方。我自己的经验是,很多工程师调了两天 SPI 没通,最后发现只是 CPHA 差了一位。嗯,咱们今天就把这个“一位”掰开揉碎。

3.1 CPHA=0:第一个边沿采样

CPHA=0 的意思是:第一个时钟边沿就采样数据。注意,第一个边沿是上升还是下降,要看 CPOL。CPOL=0 时第一个边沿是上升沿;CPOL=1 时第一个边沿是下降沿。但无论哪种极性,CPHA=0 都让数据在第一个边沿被采样。

我个人习惯先确定 CPOL,再考虑 CPHA。这样思路不乱。你想想看,CPOL 定的是空闲电平,CPHA 定的是采样时刻,两个相互独立。

CPHA=0 时,数据在 SS 变低之后、第一个时钟边沿到来之前就已经准备好。从机在这个“准备窗口”把数据放到 MISO 线上,主机在第一个边沿采样。这意味着一件事:SS 下降沿到第一个时钟边沿之间必须有足够的建立时间。

核心要点:CPHA=0 时,数据在第一个时钟边沿被锁存。数据变化发生在时钟边沿之后的那个半周期里。

我在项目中遇到过一块 AD 芯片,手册上写的是 CPHA=0、CPOL=0。但我按常规配了 CPOL=0、CPHA=1 去调,结果读出来的数据全是乱码。后来用示波器抓了波形才发现,主机在第二个边沿采样,而芯片在第一个边沿就把数据输出并保持了一个周期…… 这就是相位不匹配的典型症状。

3.2 CPHA=1:第二个边沿采样

CPHA=1 呢?数据在第二个时钟边沿被采样。同样,第二个边沿是上升还是下降取决于 CPOL。CPOL=0 时第二个边沿是下降沿,CPOL=1 时第二个边沿是上升沿。

CPHA=1 模式下,第一个时钟边沿实际上触发了一次数据变化,第二个时钟边沿才去采样。这个过程听起来有点绕,其实你只要记住:

  • CPHA=0 —— 采样在第一个边沿,数据变化在第二个边沿(或者 SS 下降沿后的准备期)
  • CPHA=1 —— 采样在第二个边沿,数据变化在第一个边沿

简单吧?但很多芯片手册偏偏不直说,而是给你画个时序图让你猜。我曾经被一个日本厂商的 datasheet 坑过,图上画了四根波形,标了 Mode 0 到 Mode 3,但没明确写 CPHA 是多少。后来我对照波形反推,才发现它用的 CPHA=1。

踩坑提醒:不要只看 Mode 编号!不同厂商对 Mode 0/1/2/3 的定义并不完全统一。有家欧洲厂商把 CPOL=0、CPHA=1 称为 Mode 1,而另一家可能管它叫 Mode 2。务必对照时序图自己推断。

3.3 相位偏移的实际影响

相位偏移说白了就是:数据采样点和数据变化点之间差了半个时钟周期。CPHA=0 时,采样点比数据变化点提前半个周期?不对,反过来——数据变化发生在采样之后。我们来把话说明白:

CPHA 第一个时钟边沿的作用 第二个时钟边沿的作用 采样时刻
0 采样数据 数据变化 第一个边沿
1 数据变化 采样数据 第二个边沿

从这个表可以直观看出,CPHA 决定了“谁先谁后”。如果主机和从机配置相反,那么主机在采样的时候,从机正在变化数据——相当于你伸手去接,对方却正在换手。数据要么还没稳定,要么已经跑掉。

我记得帮一个学生调毕业设计时,他用的是 STM32 作为主机,SPI 从机是一个 FPGA 模块。他用了默认的 CPHA=0,FPGA 那边却是 CPHA=1。结果通信成功率只有 20% 左右,示波器上看时序全是毛刺。改成一致之后,一次过。

一个小技巧:如果你不确定对方芯片的 CPHA,可以先用低速时钟(比如 100kHz)跑一下。低速下建立时间和保持时间的裕量都很大,即使相位不完美也可能通。先跑通,再降裕量,最后确定相位。

3.4 一张图看懂 CPHA 与采样边沿

为了帮你更直观地理解,我画了下面这张流程图。它展示了从 SS 有效到数据被采样的完整过程中,CPHA=0 和 CPHA=1 的路径差异。

CPHA 与采样边沿选择流程 SS 变低,通信开始 CPHA 等于? CPHA=0 第一个边沿采样 第二个边沿 数据变化 CPHA=1 第一个边沿数据变化 第二个边沿 采样数据 完成一个 bit 的传输 继续下一个 bit,直到 SS 变高 注意:采样边沿 与 CPOL 配合决定 上升还是下降沿

从这张图可以看出,两种模式都经历了“数据变化”和“数据采样”两个环节,只是顺序交换。真实的世界里,这个顺序决定了建立时间和保持时间的分配——如果你在第一个边沿采样,那么数据必须在第一个边沿之前稳定;如果你在第二个边沿采样,那么第一个边沿之后的变化不能影响到第二个边沿时的稳定。

3.5 实战中的避坑清单

说了这么多理论,我总结几条实操经验,你调 SPI 的时候可以对照着查:

  1. 先看时序图,再看模式编号。 芯片手册里一般会画 Mode 0~3 的波形,找到跟你配置接近的那一个,数一数采样是在第一个边沿还是第二个。
  2. 检查 SS 下降沿之后的准备时间。 CPHA=0 时,主机在第一个边沿采样,从机必须在 SS 下降沿到第一个边沿之间把数据准备好。如果这个时间不够,考虑增加时钟预置延时,或者改用 CPHA=1。
  3. 低速验证,高速确认。 我第一次调一个 20MHz 的 SPI 传感器时,低速能通,高速就丢 bit。最后发现我的 CPHA 和从机差了 180 度——相位错位在高速下没有足够裕量。
  4. 用示波器同时抓 SCK 和 MISO/MOSI。 我习惯在 MISO 线上叠加 CPHA 的参考标记。比如画一条竖线对齐第一个边沿,看看数据变化是在线之前还是之后。一步就能判断 CPHA 是否匹配。

再强调一遍:千万不要想当然地把主机 CPHA 设为 0,从机也是 0,就以为万事大吉。有些从机的内部逻辑默认 CPHA=1,你配成 0 之后,它可能仍然按 1 工作——但不会报错,只会默默送错数据。

好了,这一讲就到这里。CPHA 的核心其实就一句话:数据是在第一个时钟边沿变化,还是在第二个边沿变化,决定了哪一边沿用来采样。把这个顺序理清楚,SPI 相位就不再是玄学了。