interface中的setup_time和hold_time
input:约束input信号提前T时间采样,然后在时钟沿更新到input信号上。
output:约束output信号,在时钟沿T时间后驱动数据到output信号上。
这个两个时间和setup和hold没有关系,不知道为啥取这个名字。
clocking drv_cb @(posedge clk); default input #setup_time output #hold_time; output data; endclocking:drv_cb clocking mon_cb @(posedge clk); default input #setup_time output #hold_time; input data; endclocking:mon_cb
在DUT中这样与interface连接
initial begin force TH.data_in = drv_cb.data; end assign mon_cb.data = TH.data_out;
setup_time:用于monitor,提前时钟沿(posedge clk)setup_time时间采集DUT的信号数据,并在时钟沿将数据赋给interface的data上。
hold_time:用于driver,driver在时钟沿(posedge clk)采集interface中data的数据,并延时hold_time时间force到DUT的信号上。
在interface里面定义时钟块clocking block 可以控制同步信号相对于时钟的时序,时钟块中的任何信号都可以同步的驱动或采样,保证了测试平台在正确的时间点与信号交互。一个接口中可以有多个时钟块,每个时钟块中都只有一个时钟表达式,所以每一个时钟块对应各自的时钟域。
何为建立时间(Setup Time)和保持时间(Hold Time)?以D触发器为例,在作为接收端时;由于工艺、寄生参数、触发器结构等原因决定,被采样数据必需有一个稳定区间,保证数据可以正确的被触发器采样。通常我们把这个要求的稳定区间称为 Setup-Hold window。我们把 Setup-Hold window 和时钟沿对应起来,把Setup-Hold window 分解为两部分,建立时间(Setup Time)和保持时间(Hold Time)。
在触发器的时钟沿到来前,输入数据必须保持在一个稳定状态的最小时间;称为建立时间(setup time)。
在触发器的时钟沿到达后,输入数据需要继续保持在原状态的最小时间,称为保持时间(hold time)。
那么我们在验证环境中为了更加贴近实际的电路情况,也在时钟块里面定义了SETOU_TIME和HOLD_TIME。
这里的HOLD_TIME指的是driver将clocking block里面的输出信号驱动到总线上时会延时HOLD_TIME时间。
SETOU_TIME指的是monitor会在时钟沿前SETOU_TIME时间从总线上采集信号输入到clocking block里面。
如果用例通过,一般在Verdi上是看不到SETOU_TIME的效果的,为了能弄清楚SETUP_TIME和HOLD_TIME的意思,我将SETOU_TIME和HOLD_TIME的时间分别设为5ns和6ns,时间已经超出了时钟周期的一半,所以monitor采样的时候会报错。通过查看Verdi中的波形可以验证这一点。
从图中能够很容易看出,1和2之间的时间差是6ns,也就是说driver将信号驱动到总线上,其实是延迟了HOLD_TIME时间。但是SETOU_TIME不容易看出来,monitor需要在时钟沿的前SETOU_TIME时间,也就是提前5ns的时候采集总线上的数据,也就是在3时钟沿的时候提前5ns采集总线上的数据,这时,由于HOLD_TIME的时间为6ns,时钟周期为10ns,所以在3时钟沿,monitor中data采到的数据是72a6,data_valid采到的是0。只有在4时钟沿时data_valid 才为1,数据才有效,这就造成了有一拍的数据漏采,所以用例failed。将SETOU_TIME和HOLD_TIME的时间改成低于时钟周期的一半时,用例pass。