4. CDC静态检查与结构识别
在Agilex器件上做CDC验证,第一步不是写约束,而是让工具把“哪些路径真的跨了时钟域”找出来。Quartus Prime Pro的静态检查能力主要依托两条线:一是Timing Analyzer中的时钟关系与跨时钟路径分析,二是Design Assistant与CDC相关的规则检查。前者回答“路径在哪里、裕量多少”,后者回答“结构上是否违规”。两者结合,才能形成可追溯的CDC问题清单。
一、先建立时钟域清单,再谈跨域识别
工具识别CDC的前提是它知道每个时钟的归属。在Agilex设计中,时钟来源通常包括外部晶振引脚、收发器恢复时钟、PLL输出以及内部逻辑分频。建议先用SDC把每个时钟显式声明,并给同源时钟打上同一组-group,避免工具把同源异步关系误判为跨域。例如:
create_clock -name clk_core -period 2.500 [get_ports clk_core_in]
create_clock -name clk_ddr -period 1.250 [get_ports clk_ddr_in]
create_clock -name clk_100m -period 10.000 [get_ports clk_100m_in]
derive_pll_clocks
derive_clock_uncertainty
set_clock_groups -asynchronous \
-group {clk_core clk_core_pll} \
-group {clk_ddr clk_ddr_pll} \
-group {clk_100m}
这里set_clock_groups -asynchronous的作用是告诉工具:这三组时钟之间不存在可分析的确定相位关系,因此不做建立/保持时间检查,但路径仍然会被标记为跨时钟域。注意,它只“关闭时序检查”,并不等于“CDC已安全”,真正的安全性仍要靠同步结构保证。
二、用CDC路径报告定位跨域端点
在Timing Analyzer中,可通过Report CDC或Clock Domain Crossing报告查看跨域路径。报告的核心字段包括:源时钟、目的时钟、源寄存器、目的寄存器、路径类型(如Setup、Recovery)、是否被约束为异步、以及是否被识别为同步器。一个典型的报告条目会呈现如下信息:
| 源时钟 | 目的时钟 | 源寄存器 | 目的寄存器 | 结构判定 |
|---|---|---|---|---|
| clk_core | clk_ddr | u_tx/data_cnt[3] | u_rx/sync_ff1 | 两级同步器 |
| clk_ddr | clk_100m | u_rx/status_reg | u_ctrl/ctrl_state[1] | 无同步结构 |
| clk_100m | clk_core | u_ctrl/req_toggle | u_tx/req_sync1 | 握手/脉冲同步 |
读报告时不要只看“有没有跨域”,而要重点看“目的端第一个接收单元是什么”。如果目的寄存器直接由源时钟域的组合逻辑驱动,且中间没有同步器,就属于高风险结构。Agilex的Design Assistant通常会给出类似CDC-10001、CDC-10002的规则编号,分别对应“缺少同步器”“同步器级数不足”“多比特跨域未做格雷码或握手”等。
三、时钟域交叉矩阵:把零散路径变成全局视图
当设计中有五六个时钟域时,逐条看路径很容易遗漏。此时应构建时钟域交叉矩阵:行表示源时钟域,列表示目的时钟域,单元格填入该方向上的跨域路径数量与最严重违例等级。矩阵的价值在于快速暴露“热点方向”。例如某设计矩阵如下:
| 源\目的 | clk_core | clk_ddr | clk_100m |
|---|---|---|---|
| clk_core | — | 12条 / 2级同步 | 3条 / 无同步 |
| clk_ddr | 8条 / 握手 | — | 5条 / 1级同步 |
| clk_100m | 1条 / 脉冲同步 | 4条 / 无同步 | — |
矩阵中clk_core→clk_100m的3条无同步路径、clk_ddr→clk_100m的5条一级同步路径,就是优先处理对象。一级同步在慢到快场景下可能勉强工作,但在快到慢且信号宽度不足一个目的时钟周期时会直接丢失,因此应升级为两级或改用脉冲展宽。
四、违例分类与处置优先级
把报告和矩阵合并后,通常可归为四类。第一类是完全无同步结构,风险最高,必须插入两级触发器或改用异步FIFO。第二类是同步级数不足,例如只有一级,在MTBF估算中往往达不到要求,应补到两级。第三类是多比特信号未做保护,如计数器、状态向量直接跨域,必须改为格雷码或握手协议。第四类是脉冲宽度不足,源域脉冲窄于目的时钟周期,需做脉冲展宽或翻转同步。
五、把检查结果落成可执行清单
静态检查的最终产出不应只是一份报告,而应是一份可跟踪的CDC问题清单。建议每条记录包含:源时钟、目的时钟、源寄存器、目的寄存器、当前结构、违例类型、处置方式、复检状态。复检时重新运行Timing Analyzer的CDC报告,确认该路径已被识别为同步结构,且Design Assistant不再报对应规则编号。只有“报告清零”与“结构确认”同时满足,才能认为该CDC路径通过验证。
set_clock_groups -asynchronous只是关闭时序检查,不会自动修复CDC。若误把它当作“已处理”,会把真实违例掩盖掉。正确顺序是先识别结构、再修复结构、最后用约束表达异步关系。