Max WellPERSONAL NOTES
工作技术 / CLOCK & HANDSHAKE

快慢同步时钟之间,
怎样让一次传输只发生一次

慢侧保持一拍的 valid,快侧可能看到好几个采样边沿。subedge 适配要解决的,是让两侧对“这一项数据已经传过了”达成一致。

2026-10-01 · 工作技术同步分频 / Ready–Valid / 反压

这类电路依赖确定的快慢时钟关系:慢→快用一位状态记住“已接收”,快→慢用窗口限制“何时消费”。本地流水级负责存数据和保持反压;适配逻辑本身不必包含数据缓冲。

01先把时钟关系说清楚

设快时钟为 clk_fast,慢时钟为 clk_slow。在一个固定分频模型中,慢周期是快周期的 N 倍;本文取 N=4,慢侧相邻两个上升沿之间包含四个快周期。这里把慢周期内的快侧采样边沿称为 subedge。

“频率比例为 4:1”还不够。两者必须有可约束的相位关系,并满足跨时钟路径的建立、保持时间。下文的示例取同相上升沿;这是讲解用的时序模型,不代表任意实现都天然满足。

通用信号含义需要约定的行为
clk_fast / clk_slow快、慢侧采样时钟分频比、相位、偏斜及门控关系可确定
slow_en向快侧标记慢侧边界或接收窗口的使能必须定义脉冲宽度及相对两侧采样沿的位置
valid / ready传输有效 / 可以接收在各自约定的采样边沿,两者同时为 1 才完成传输
data完整数据总线尚未完成源端握手时,有效数据保持稳定

分频时钟和 slow_en 由外部时钟逻辑提供。本文的适配器不生成分频时钟,也不靠内部相位计数器选择某个固定 subedge。本文所有公式均为通用教学表达,省略具体实现的层级、位宽和命名。

02慢→快:接收一次,再屏蔽重复

慢到快接口信号方向慢侧源端向适配逻辑发送 slow_data、slow_valid 和 slow_en;适配逻辑向快侧接收端发送 fast_data、fast_valid。fast_ready 从快侧返回适配逻辑,slow_ready 从适配逻辑返回慢侧。done 在快时钟下更新。 慢侧源端适配逻辑done:快侧去重状态快侧接收端 slow_datafast_dataslow_validfast_validslow_readyfast_readyslow_en clk_slow 采样clk_fast 更新 doneclk_fast 采样
图 1 · 慢→快接口。data、valid 向前传递,ready 反向返回;slow_en 从慢侧时序逻辑送到适配器。两侧时钟属于同一个同步系统。

慢侧送出一项 A 后,通常要一直保持 valid 和 data,直到自己的采样边沿确认 ready。快侧却可能在这段时间里遇到多个上升沿。如果直接把慢侧 valid 接过去,同一项 A 可能被快侧重复接收。

一个简洁的办法是在快侧增加一位 done:它表示当前慢侧传输项已经被快侧接受。关键逻辑可以抽象为:

fast_valid = slow_valid & ~done
slow_ready = fast_ready | done
accept     = fast_valid & fast_ready

// 每个快时钟上升沿更新;slow_en 清零优先
done_next  = (done | accept) & ~slow_en
// 复位时 done = 0;data 直接传递,不在这里寄存
  1. done=0 时,慢侧 valid 可以向快侧传播。第一次快侧握手成功,done 置 1。
  2. done=1 后,fast_valid=0,同一项保持有效的数据不会在后续快沿被再次接收。
  3. slow_ready=1 保留“已经接收”的事实,直到慢侧在自己的边沿观察到它并推进到下一项。
  4. 约定的 slow_en 边界清除 done,重新开放下一项的接收机会。

done 不是“缓冲区里存着数据”的标志。它只记录接收事实,没有保存 data。slow_ready 中的 done 分支,也不是承诺快侧此刻能再接一项;它是在告诉慢侧:当前这一项早已被接收。

若 slow_en 与 accept 同沿为 1,清零优先,done 不会留下这次接收记录。外围时序必须避免因此重新接受同一项,或保证慢侧及时推进。不能仅靠这几个布尔公式证明所有相位下都不会重复。

03一个有明确前提的 4:1 示例

假设慢侧在 F0 前已稳定送出 A;慢沿位于 F0、F4、F8;slow_en 仅在这些边沿被快侧采到为 1。快侧在 F0 不 ready,在 F1 接收 A,在 F5 接收 B。源端遵守保持型握手,跨域信号满足建立与保持时间。

4:1 同相模型中,一项慢侧数据仅被快侧接受一次慢沿在 F0、F4、F8,快侧在 F1 接收 A、在 F5 接收 B。done 在接收后置位,在下一慢边界清零;慢侧在 F4 确认 A,在 F8 确认 B。 快侧边沿慢侧边沿源端 datadone(沿后)快侧接收 F0F1F2F3F4F5F6F7F8 A:快侧已接收,慢侧仍保持B:快侧已接收,慢侧仍保持 接受 A接受 B 慢侧确认 A,边沿后换 B慢侧确认 B
图 2 · 4:1 逐拍示例。done 曲线展示各边沿更新后的状态。
采样沿slow_en源端数据
沿前 → 沿后
done
沿前 → 沿后
fast_valid / ready
沿前值
结果
F0 / 慢沿1A → A0 → 01 / 0清状态;两侧均未完成 A 的握手
F10A → A0 → 11 / 1快侧接受 A;源端继续保持
F2–F30A → A1 → 10 / 任意屏蔽 A 的重复接收;slow_ready=1
F4 / 慢沿1A → B1 → 00 / 任意慢侧确认 A;沿后切换 B、重新开放窗口
F50B → B0 → 11 / 1快侧接受 B
F6–F70B → B1 → 10 / 任意屏蔽 B 的重复接收
F8 / 慢沿1B → 下一项1 → 00 / 任意慢侧确认 B;重新开放窗口

关键是区分两个完成时刻:快侧在 F1 已接收 A,慢侧在 F4 才确认 A。中间由 done 保存这一事实。F1 只是示例中的首次就绪边沿;若 ready 更晚到达,接收可以发生在其他合法快沿。

本例有意让 F0 不 ready,避开“首次接收与清零同时发生”的情况。真实电路若采用其他 enable 相位或脉宽,应重新检查慢侧确认、状态清零和新数据建立的先后关系。

04快→慢:只在慢侧能采样时消费

快到慢接口信号方向快侧源端向窗口逻辑发送 fast_data 和 fast_valid,窗口逻辑向慢侧接收端发送 slow_data 和 slow_valid。slow_ready 和 slow_en 从慢侧返回窗口逻辑,fast_ready 从窗口逻辑返回快侧源端。 快侧源端适配逻辑ready 接收窗口限定慢侧接收端 fast_dataslow_datafast_validslow_validfast_readyslow_readyslow_en clk_fast 采样组合窗口逻辑clk_slow 采样
图 3 · 快→慢接口。data、valid 向前传递;slow_ready 与 slow_en 返回适配器,共同产生 fast_ready。slow_en 由慢侧时序逻辑提供。

反方向的难点是:快侧不能因为慢侧 ready 保持为 1,就在每个快沿连续释放数据。常见的适配方式是让 data 和 valid 向慢侧传播,同时用 slow_en 限制返回快侧的 ready:

slow_valid = fast_valid
slow_data  = fast_data
fast_ready = slow_ready & slow_en

快侧只在 slow_ready 和接收窗口同时有效时消费当前项。窗口之外,fast_ready=0,快侧保持 data 和 valid,等待下一次慢侧接收机会。

窗口慢侧 ready快侧 ready结果
F0 / 慢沿,slow_en=100数据 R 保留
F1–F3,slow_en=0任意0快侧不消费,继续保持 R
F4 / 慢沿,slow_en=100继续等待
F8 / 慢沿,slow_en=111两侧在约定边沿完成 R 的交接

ready 门控成立的前提,是 slow_en 准确对应慢侧接收边沿。使能若覆盖多个有效快沿,或错开慢沿,就不能单凭 AND 门保证两侧消费次数一致。

05数据保持,由本地流水级负责

时钟适配和弹性缓冲承担不同职责。适配器解决两侧的消费时刻和消费次数;相邻的本地寄存器或弹性流水级,在反压期间保存有效数据。它们可以串接在数据通路上,但不能混称为一个异步 FIFO。

部分存储内容职责
慢→快适配状态一位 done记住当前项已接收,避免重复
快→慢窗口逻辑本例没有数据寄存器限定快侧消费时机
本地弹性流水级data、valid 及占用状态保存被阻塞的数据,并向上游反压

慢→快尚未被接受时,done=0 且快侧不 ready,慢侧必须保持当前项。快→慢尚未到窗口,或慢侧不 ready 时,快侧必须保持当前项。如果包含 Head、Tail 等边界标志,它们也随 data 一起保持;其中 Head 仅指 1-bit 标志,Hdr 才指数据总线中的头域。

因此,背压可以延长等待,但不会自动增加适配器的容量。实际能缓存多少项、连续传输时有多少延迟,应由完整流水级和队列结构确定。

06这个模型能用到哪里

本电路的适用前提是:整个系统都是同步系统。快、慢两侧时钟虽然频率不同,但必须是同步时钟,具有确定、可约束的频率与相位关系,并对跨时钟路径进行同步时序分析。仅有相同的频率比例,不能说明两个时钟同步。

上述适配逻辑依赖这一同步关系;不能直接用于两个独立、相位无关的异步时钟域。

边界需要确认的条件
时钟与使能真实分频比、slow_en 脉宽及相位,与采样模型一致;含门控后的边沿关系
实现时序data、valid、ready、slow_en、done 相关路径满足建立/保持要求,并计入时钟偏斜
复位done 初始化为 0;两侧流水级的复位释放及首个有效窗口协调一致
停钟 / 改分频定义在途项如何处理及何时允许恢复传输;不能把稳态推导当作动态切换证明
功能验证覆盖 ready 延迟、连续项、接收与清零同沿、复位打断和使能边界,检查无丢失、无重复及顺序保持

逻辑上最值得记住的是:done 把一次快侧接收保留到慢侧能够确认;slow_en 把一次快侧消费约束到慢侧能够接收。它们与两侧的数据保持协议一起工作,最终仍需要真实时钟、复位和时序约束来闭合正确性。