整理自 B站fpga奇哥
实例
ADC+UART.功能采集 ADC的数据通道 UART 发送数据 时钟域:
1.ADC的时钟域-5M 16bit
2.UART 的时钟域-9600
红色代表ADC时钟 绿色代表UART时钟 蓝色代表数据位
建立时间:tsu
有低电平到高电平的过程
保持时间:thd
高电平稳定的过程
如果在电平发生跳转时,读取数据会产生问题
问题:直接赋值:有亚稳态问题,不能保证每次赋值是正确的。
危害:产生亚稳态现象,导致赋值寄存器中数据随机 (XX) 01ZX
解决:跨时钟域处理
- 电平同步器 -单 bit
- 脉冲同步器 -单 bit.
- FIFO,RAM - 多 bit
为什么不能用同步器处理多比特?
因为同步器有很低的概率发生差错,多比特传输使的错误率变高。
复位问题:
因为fpga的平台不同,altera的可以异步低复位,Xilinx的推荐同步高电平复位。
代码
同步器
module reset_sync_module(
input i_sysclk ,
input i_rst ,
output o_sync_rst
);
(*ASYNC REG ="TRUE”*) //综合时放到一个clb里,降低亚稳态
reg r_rst1,r_rst2;
assign o_sync_rst = r_rst2;
always@(posedge i_sysclk)
if(i_rst) begin
r_rst1 <= 'd1;
r_rst2 <= 'd1;
end
else begin
r_rst1 <= i_rst;
r_rst2 <= r_rst1;
end
endmodule
慢到快 打两拍
module s2f_sync module(
input i_clk1,
input i_signal,
input i_clk2,
output o_signal
);
(*ASYNC REG ="TRUE"*)
reg r_s1,r_s2;
assign o_signal = r_s2;
always@(posedge i_clk2)begin
r_s1 <= i_signal;
r_s2 <= r_s1
end
endmodule
快到慢 信号延拓
module f2s_sync module(
input i_clk1 ,
input i_signal ,
input i_clk2 ,
output o_signal
);
reg r_d1,r_d2;
reg r_ pos;
assign r_pos = i_signal | r_d1 | r_d2;
always@(posedge i_clk1)begin
r_d1 <= i_signal;
r_d2 <= r_d1;
end
(*ASYNC REG ="TRUE"*)
reg r_p1,r_p2;
assign o_signal = r_p2;
always@(posedge i_clk2)begin
r_p1 <= r pos;
r p2 <= r p1;
end
endmodule