介绍
FIFO是一个存储器,遵从先入先出原则,这里声明我所使用的FIFO是altera公司提供的IP核FIFO,它在时钟上升沿进行写入与写出。下面是一些FIFO时序实验的经验:
最好使用错位周期信号来保持上升沿
使用错位周期信号来保证FIFO处在时钟上升沿时,条件信号不要也跟着变来变去的。
首先定义如下的三个时钟周期,其中half_clk为最高频周期:
reg judge_clk;
reg half_clk;
reg half_clk_dly;
always@(posedge half_clk or negedge sys_rst_n)
if(sys_rst_n == 1'b0)
judge_clk<= 1'b0;
else
judge_clk<= ~judge_clk;
assign half_clk_dly = ~half_clk;
定义完成后将data_in与write的时序沿half_clk_dly来划分,这样write系列的条件语句就都能处在系统上升沿或者下降沿上了。
同理将read信号也沿half_clk_dly来划分,但要注意的是,FIFO的输出数据是以大时钟周期的上升沿来划分的,这一点要注意。
具体波形如下:
在上升沿写入信号是6,在上升沿读出信号是6,在下降沿变化条件信号,在上升沿读出输出信号。
好了,现在实验做完要总结一条经验了:
当你由一条时序时间带和一条数据时间带具体内容未定,但你知道你给出的时序时间带的上升沿处读取数据时间带的数据以赋值给别人的话,你最好用数据时间带的面盖住时序时间带的沿。
就像这个实验一样,如果你读取出来的FIFO数据,是要作为数据时间带输出给下一个模块用的话,那么下一个模块的时序时间带上升沿一定要命中在数据时间带的中心(就是一定要这么落,这么落最优且少bug)。读出的FIFO数据时间带实在大周期上升沿变化的,且会持续到下一个大周期的时间沿,因而数据时间带的周期是大周期的时间周期,对应了时序时间带的周期也是大周期的周期,数据时间带的上升沿是大周期的上升沿,所以时序时间带的上升沿应该是大周期的下降沿,也就是要在half_clk_dly的上升沿处变化才好。