内容部分由AI生成
一、基本概念:与时钟约束的区别
- 时钟约束 (
create_clock
,set_input_delay
等) :定义的是寄存器到寄存器 路径的时序要求。工具会根据时钟周期自动计算建立时间(Tclk - Tsu
)和保持时间(Thold
)的要求。这是最常用和推荐的方式。 - 最大/最小延时约束 :直接指定一条路径的最大和最小允许传输延迟 (单位为纳秒等)。它通常用于非寄存器到寄存器的路径,或者当时钟周期不能正确反映实际需求时。
核心思想 :当你无法或不希望用时钟周期来定义一条路径的时序时,就使用 set_max_delay
和 set_min_delay
。
二、set_max_delay
/ set_min_delay
的典型适用情况
1. 纯组合逻辑路径(无寄存器)
当路径的起点和终点都不是寄存器时,时钟约束无法直接覆盖这些路径。
-
示例:
- 从输入端口到输出端口:例如一个 bypass 逻辑、组合逻辑运算器。
- 从输入端口到黑盒(Black Box)的输入口:当你连接一个未经综合的第三方IP时。
- 内部组合逻辑环:(虽然不推荐,但有时存在)。
-
为什么需要:工具不知道这些路径需要多"快"或多"慢",必须由设计者明确指定时序要求。
-
约束命令:
# 约束从输入端口 A 到输出端口 B 的组合逻辑延迟不能超过 15ns set_max_delay 15 -from [get_ports A] -to [get_ports B] # 同时约束最小延迟,防止毛刺过快传播,确保保持时间检查 set_min_delay 2 -from [get_ports A] -to [get_ports B]
2. 跨时钟域 (CDC) 路径中的同步器前路径
这是最经典和关键的应用场景 。虽然跨时钟域路径整体是异步的(用 set_false_path
或 set_clock_groups
约束),但同步器之前的路径(发射域寄存器到同步器的第一级寄存器)必须满足时序要求,以防止亚稳态率过高。
-
为什么需要:这条路径的延迟决定了信号进入同步器的稳定性。延迟过长会增加亚稳态的建立时间(MTBF降低)。我们需要确保这条路径足够快。
-
示例 :信号从
clk_a
的寄存器reg_cdc
传出,进入clk_b
时钟域的同步器sync_ff1
。 -
约束命令:
# 首先,声明两个时钟域异步,不进行常规时序检查 set_clock_groups -asynchronous -group {clk_a} -group {clk_b} # 然后,对同步器前的路径施加最大延迟约束,例如要求小于半个 clk_b 周期 set_max_delay 5 -from [get_cells reg_cdc] -to [get_cells sync_ff1] -datapath_only
注意 :
-datapath_only
选项非常有用,它告诉工具只计算数据路径的延迟,忽略时钟路径的延迟(因为时钟是异步的,比较时钟路径延迟无意义)。
3. 异步时钟域之间的受控路径
有时,虽然两个时钟域异步,但设计上要求信号必须在特定的时间窗口内从一端传播到另一端。这时就不能简单设为 false_path
,而需要用 set_max_delay
和 set_min_delay
来定义一个合理的时序窗口。
-
示例:两个异步时钟域之间的握手信号(req/ack),虽然不需要每个周期都有效,但也不能延迟太久。
-
约束命令:
# 约束握手信号 req 从发射寄存器到接收寄存器的延迟在 3ns 到 10ns 之间 set_max_delay 10 -from [get_cells sender_reg] -to [get_cells receiver_reg] set_min_delay 3 -from [get_cells sender_reg] -to [get_cells receiver_reg]
4. 参考电压生成、模拟电路控制等路径
这些路径对数字逻辑的延迟非常敏感,需要非常精确的控制。
-
示例:控制DAC或PLL配置的串行总线(如SPI)、参考电压的开关控制信号。
-
为什么需要:一个过长的延迟可能导致模拟电路工作异常。必须指定一个严格的最大延迟。
-
约束命令:
# 约束到 DAC 芯片片选信号 CSn 的路径必须非常快 set_max_delay 1.5 -to [get_ports DAC_CSn]
5. 多周期路径的替代约束方式
虽然 set_multicycle_path
是标准做法,但在某些复杂情况下,也可以使用 set_max_delay
来间接实现多周期约束。
-
示例:一个路径需要 3 个时钟周期,时钟周期是 5ns。
-
约束命令:
# 用 set_multicycle_path 的标准方法 set_multicycle_path 3 -setup -from [get_clocks clk] -to [get_clocks clk] set_multicycle_path 2 -hold -from [get_clocks clk] -to [get_clocks clk] # 用 set_max_delay 的替代方法 (3个周期 = 15ns) set_max_delay 15 -from [get_cells start_reg] -to [get_cells end_reg]
注意 :这种方法不常见,因为它不如
set_multicycle_path
直观和自动化。
三、如何使用:语法和示例
基本语法:
set_max_delay <delay_value> [-from <start_point>] [-to <end_point>] [-through <through_point>] [-datapath_only]
set_min_delay <delay_value> [-from <start_point>] [-to <end_point>] [-through <through_point>]
<delay_value>
:单位通常是纳秒 (ns)。这是绝对的物理时间值。-from
:路径起点(时钟、端口、引脚、单元)。-to
:路径终点。-through
:路径必须经过的中间点(慎用,易过度约束)。-datapath_only
:极其有用的选项 ,特别针对CDC路径。它指示工具只计算数据路径的延迟,忽略源时钟和目的时钟的时钟路径延迟(latency
&uncertainty
)。
综合示例:一个带有同步器的跨时钟域信号。
# 定义时钟
create_clock -period 10 -name clk_a [get_ports clk_a]
create_clock -period 15 -name clk_b [get_ports clk_b]
# 声明时钟异步
set_clock_groups -asynchronous -group {clk_a} -group {clk_b}
# 约束同步器前的路径:要求从发射寄存器到同步器第一级寄存器的数据路径延迟小于 6ns
# 这个值通常取同步器侧时钟周期的一半左右(15ns/2 = 7.5ns,取更严格的6ns)
set_max_delay 6 -from [get_cells data_cdc_reg] -to [get_cells sync_ff1_reg] -datapath_only
# 如果需要,也可以约束最小延迟以防止保持时间问题(这里约束为0)
set_min_delay 0 -from [get_cells data_cdc_reg] -to [get_cells sync_ff1_reg] -datapath_only
四、重要注意事项和最佳实践
- 谨慎使用,优先考虑时钟约束 :首先要问自己"我为什么不能用时钟来约束这条路径?" 如果答案是"起点或终点不是寄存器"或"这是CDC同步器路径",那么使用最大/最小延时是合适的。如果只是一条普通的寄存器到寄存器路径,应优先使用时钟和多周期约束。
-datapath_only
是关键 :在约束CDC路径时,务必 加上-datapath_only
选项。否则,工具会加上时钟网络的延迟,导致约束计算错误。- 最大和最小要成对出现 :
set_max_delay
用于约束建立时间(信号不能太慢),set_min_delay
用于约束保持时间(信号不能太快)。只设置max_delay
而不设置min_delay
可能会导致保持时间违例被忽略。 - 与
set_false_path
的关系 :set_max_delay
覆盖set_false_path
。如果你对一条路径同时设置了set_false_path
和set_max_delay
,那么set_max_delay
会生效,false_path
会被忽略。这在处理CDC同步器路径时是期望的行为。 - 验证 :在STA工具(如PrimeTime)中,使用
report_timing -delay_type max
和report_timing -delay_type min
来检查这些受约束路径的时序是否满足。
总结 :set_max_delay
和 set_min_delay
是用于绝对物理时间约束 的强大工具,主要适用于纯组合逻辑路径 和跨时钟域同步器前路径。正确使用它们可以确保异步接口的可靠性,并约束那些无法被时钟周期定义的关键路径。