9.18 verilog100题学习

抄的太多记不住了

    • 1. 什么是亚稳态?
      • 建立时间与保持时间的概念?
    • 2. 亚稳态产生的原因
    • 3.什么是亚稳态?为什么两级触发器可以防止亚稳态传播?
    • 多bit接收
      • 异步fifo(略,顺序读出)
      • 保持寄存机构造的方案
    • 注意:设计关键:不知道时钟关系的情况下(知道的话,这么舒服怎么来)
    • 4:系统最高速度计算(最快时钟频率)和流水线设计思想:
    • 5:时序约束的概念和基本策略?
      • 基本时钟
      • 虚拟时钟
      • 生成时钟(生成IP自动生成,只需要加物理约束就可以)
    • 时钟组
      • 时序例外
    • 6:对于多位的异步信号如何进行同步?
    • 7.异步复位,同步复位,异步复位同步释放
      • 异步复位同步释放

1. 什么是亚稳态?

亚稳态是违背了触发器的建立和保持时间而产生的。设计中任何触发器都有特定的建立和保持时间,在时钟上升沿前后的这段时间窗口内,数据输入信号必须保持稳定。如果信号在这段时间发生了变化,那么输出将是未知的或者称为“亚稳的”。这种有害的传播就叫做亚稳态。
触发器都会在一个或者两个时钟周期内返回稳态

建立时间与保持时间的概念?

建立时间:触发器在时钟上升沿到来之前,其数据输入端的数据必须保持不变的最小时间。
保持时间:触发器在时钟上升沿到来之后,其数据输入端的数据必须保持不变的最小时间。
建立时间:Tsetup
保持时间:Thold
触发器从接受到时钟上升沿到触发器输出延迟:Tco

2. 亚稳态产生的原因

时序逻辑中大量使用D触发器,D触发器的一般结构是:两个串联的反相器加两个传输门构成锁存器,两个锁存器串联构成D触发器。D触发器是一种双稳态电路,两个稳定状态”1“、”0“。两个反向器构成的反馈回路可能会产生亚稳态
如图所示,当在输入数据在亚稳时间窗变化时,Tco增大,在Tco_max之后还没有稳定的情况就是亚稳态。

  • 输入信号是异步信号,容易不满足触发器的建立和保持时间

  • 跨时钟域

  • 时钟CLOCK的偏移和抖动 (更稳定的时钟驱动和随着路径增加加入MMCM相位偏移)

  • 系统的异步复位信号

  • 9.18 verilog100题学习_第1张图片

3.什么是亚稳态?为什么两级触发器可以防止亚稳态传播?

这也是一个异步电路同步化的问题。亚稳态是指触发器无法在某个规定的时间段内到达一个可以确认的状态。使用两级触发器来使异步电路同步化的电路其实叫做“一位同步器”,他只能用来对一位异步信号进行同步两级触发器可防止亚稳态传播的原理:假 设第一级触发器的输入不满足其建立保持时间**,它在第一个脉冲沿到来后输出的数据就为亚稳态,那么在下一个脉冲沿到来之前,其输出的亚稳态数据在一段恢复时 间后必须稳定下来,而且稳定的数据必须满足第二级触发器的建立时间**,如果都满足了,在下一个脉冲沿到来时,第二级触发器将不会出现亚稳态,因为其输入端的 数据满足其建立保持时间。同步器有效的条件:第一级触发器进入亚稳态后的恢复时间 + 第二级触发器的建立时间 < = 时钟周期。
关机:第一级输出可能为亚稳态,经过回复时间满足第二级触发器的建立好保持时间。那么亚稳态就消除了,并防止传播

  • 更确切地说,输入脉冲宽度必须大于同步时钟周期与第一级触发器所需的保持时间之和。最保险的脉冲宽度是两倍同步时钟周期。所以,这样的同步电路对于从较慢的时钟域来的异步信号进入较快的时钟域比较有效,对于进入一个较慢的时钟域,则没有作用。
    锁存器出现亚稳态
    (1)在其中一个输入端输入的脉冲太短。
    (2)两个端口输入同时有效,或两输入有效相差足够短。
    (3)在使能输入的边缘处,输入信号不稳定。

触发器出现亚稳态
(1)建立/保持时间内输入信号不稳定。
(2)时钟脉冲太窄。
(3)异步信号对时钟有效沿是随机的,易产生亚稳态。异步信号包括:不被时钟控制的信号;或被不同时钟域的时钟同步的信号。
9.18 verilog100题学习_第2张图片
异步输入信号的脉冲宽度小于时钟周期时的同步电路(高速时钟域→低速时钟域):脉冲同步器
资料:Verilog基础知识(亚稳态和跨时钟域的同步电路).
能保持两个周期,可以用到复位同步当中
9.18 verilog100题学习_第3张图片
9.18 verilog100题学习_第4张图片
1.对异步脉冲信号的处理——不归0翻转电路
**原理(脉冲扩展):**把在源时钟域,把脉冲信号翻转(翻转条件信号由0变到1),这样单个脉冲就被扩展到电平信号,在同步时钟域抓边沿就行了。
注意:源时钟域的每个脉冲之间(即每个0到1变换上升沿)长度,必须大于同步时钟域的一个时钟周期,这样保证同步时钟域不会漏采,注意:边沿使用异或检测。

2**.反馈设计:很巧妙**:结绳法可以解决快时钟域向慢时钟域过渡的问题,且适用的范围很广
初始状态:寄存器全都为0,目标检测高脉冲,与门 ,或门都为0

  • in 变为1:1.变为1。与门:变为1;或门:无论IN变成是什么都会为1;
  • 三个同步时钟域周期后:与门为0,如果in期间一直为0的话,三个同步周期系统回到初态。不为0,接着保持,所以至少需要6个周期才能完全恢复

多bit接收

异步fifo(略,顺序读出)

保持寄存机构造的方案

原链接握手机制的verilog实现

注意:设计关键:不知道时钟关系的情况下(知道的话,这么舒服怎么来)

  • 发送模块 :数据挂到总线上,在给请求
  • 接收模块:接收完数据后,再给ack
// 发送模块
module rst_csdn(
 input rst_n,
 input t_clk,
 input ack,
 output [7:0] dout,
 output reg req
);

reg ack_reg1,ack_reg2;
reg [7:0] data_buf;
reg [2:0]tr_state;
reg [7:0] TR_MEM_Addr;
reg [7:0] TR_MEM [255:0]; //保持寄存器 深度256

parameter TR_IDLE=3'b000, SND_DATA_REQ=3'b001, CHK_ACK_ACTIVE=3'b010, CHK_COMM_END=3'b100;

always@(negedge rst_n or posedge t_clk)
begin
 if(!rst_n)begin
  ack_reg1 <= 1'b0;
  ack_reg2 <= 1'b0;
 end
 else begin
  ack_reg1 <= ack;
  ack_reg2 <= ack_reg1;
 end
end

//
always@(posedge t_clk or negedge rst_n)
begin
 if(!rst_n)
 begin
  data_buf <= 1'b0;
  tr_state <= TR_IDLE;
  TR_MEM_Addr <= 1'b0;
 end
 else 
  case(tr_state)
   TR_IDLE:             //初始化状态
	begin
	 req <= 1'b0;
	 TR_MEM_Addr <= 1'b0;
	 tr_state <= SND_DATA_REQ;
	end
	SND_DATA_REQ:       //送数据到总线上和发送请求信号 
	begin
	 data_buf <= TR_MEM[TR_MEM_Addr];
	 req <= 1'b1;                  //发送请求信号,请求信号为高,表示请求接收
	 TR_MEM_Addr <= TR_MEM_Addr + 1;
	 tr_state <= CHK_ACK_ACTIVE;
	end
	CHK_ACK_ACTIVE:           //检测应答信号为高,释放请求信号
	begin
	 if(ack_reg2 == 1'b1)   //便于时序收敛
	 begin
	  req <= 1'b0;             //释放请求信号
	  tr_state <= CHK_COMM_END;
	 end
	 else tr_state <= CHK_ACK_ACTIVE;
	end
	CHK_COMM_END:            //检测握手通信结束,如果应答信号被释放,一次握手结束  
	begin
	 if(ack_reg2 == 1'b0)
	  tr_state <= SND_DATA_REQ;
	 else
	  tr_state <= CHK_COMM_END;
	  
	end
	default:tr_state <= TR_IDLE;	
  endcase
end
assign dout = data_buf;
endmodule

//接收模块
module woshou_rx(
 input rst_n,
 input r_clk,
 input req,
 input [7:0] din,
 output reg ack
 
);

reg req_reg1,req_reg2;

reg [2:0] re_state;
reg [7:0] RE_MEM_Addr;
reg [7:0] RE_MEM[255:0];

parameter RE_IDLE=3'b000, CHK_REQ_ACTIVE=3'b001, CHK_REQ_RELEASE=3'b010;

always@(posedge r_clk or negedge rst_n)
begin
 if(!rst_n)
 begin
  req_reg1 <= 1'b0;
  req_reg2 <= 1'b0;
 end
 else 
 begin
  req_reg1 <= req;
  req_reg2 <= req_reg1;
 end
 
 
end

//
always@(posedge r_clk or negedge rst_n)
begin
 if(!rst_n)
 begin
  re_state <= RE_IDLE;
  ack <= 1'b0;
  RE_MEM_Addr <= 1'b0;
 end
 else 
  case(re_state)
  RE_IDLE:                 //初始化状态
  begin
   RE_MEM_Addr <= 0;
	re_state <= CHK_REQ_ACTIVE;
  end
  CHK_REQ_ACTIVE:            //检测发送端的数据发送请求信号
  begin
   if(req_reg2 == 1)          //如果有请求信号,接收数据
	begin
    re_state <= CHK_REQ_RELEASE;
	 RE_MEM_Addr <= RE_MEM_Addr + 1;
	 RE_MEM[RE_MEM_Addr] <= din;    //接收数据存放到MEM
	 ack <= 1'b1;                  //检测到请求信号,发送接收端应答信号
   end
   else re_state <= CHK_REQ_ACTIVE;
  end
  CHK_REQ_RELEASE:                    //检测请求信号释放,释放应答信号
  begin
   if(req_reg2 == 0)
	begin
	 ack <= 1'b0;                    //释放应答信号,一次握手通信结束
	 re_state <= CHK_REQ_ACTIVE;
	end
	else re_state <= RE_IDLE;
  end
  default: re_state <= RE_IDLE;
  endcase
end
endmodule

4:系统最高速度计算(最快时钟频率)和流水线设计思想:

同步电路的速度是指同步系统时钟的速度,同步时钟愈快,电路处理数据的时间间隔越短,电路在单位时间内处理的数据量就愈大。假设Tco是触发器的输入数据被时钟打入到触发器到数据到达触发器输出端的延时时间(Tco=Tsetpup+Thold);Tdelay是组合逻辑的延时;Tsetup是D触发器的建立时间。假设数据已被时钟打入D触发器,那么数据到达第一个触发器的Q输出端需要的延时时间是Tco,经过组合逻辑的延时时间为Tdelay,然后到达第二个触发器的D端,要希望时钟能在第二个触发器再次被稳定地打入触发器,则时钟的延迟必须大于Tco+Tdelay+Tsetup,也就是说最小的时钟周期Tmin =Tco+Tdelay+Tsetup,即最快的时钟频率Fmax =1/Tmin。

提高频率的方法:

  • 时钟周期必须满足最大延时要求。故只有缩短最长延时路径,才能提高电路的工作频率
  • 插入触发器
  • 逻辑优化,分割
    注意:反馈不能加入流水线。比如状态机

5:时序约束的概念和基本策略?

时序约束主要包括周期约束,偏移约束,静态时序路径约束三种**。通过附加时序约束可以综合布线工具调整映射和布局布线,使设计达到时序要求。**
附加时序约束的一般策略是先附加全局约束,然后对快速和慢速例外路径附加专门约束。附加全局约束时,首先定义设计的所有时钟,对各时钟域内的同步元件进行分组,对分组附加周期约束

时钟的定义
1.定义一个引脚
2.通过周期和波形的属性描述时钟边沿强鲁昂
3.纳秒为周期,它对应重复波形所需要的时间
4.波形是时钟周期内以纳秒描述的上升沿和下降沿绝对值列表,第一个值是上升沿,第二个下降沿
以上是时钟的理想特性,实际中包括时钟的网络延迟和时钟的不确定性
**时钟的不确定性:**时钟抖动,相位误差,由设计者指定的其他不确定性(HLS中设置的是时钟的时间。

基本时钟

1.一个输入端口
2.一个吉比特收发器的输入引脚,如一个恢复时钟

//周期为10ns 占空比为50,相位为0
create_clock -period 10 [get_ports clk]
//pcb上名字devclk,通过端口clk输入FPGA,周期为10ns 占空比25% 相移90
create_clock -name devclk -period 10 -waveform{2.5,5} [get_ports clk]
//GT基本时钟   gt0/RXOUTCLK//FPGA 硬件上MMCM的原点
create_clock -name rxclk -period 3.33  [get_pins gt0/RXOUTCLK]

虚拟时钟

定义:没有任何物理连接和生成网表器件。
使用的目的:在约束中使用,通过虚拟时钟说明输入输出延迟约束

生成时钟(生成IP自动生成,只需要加物理约束就可以)

定义:有MMCM,PLL,或者用户逻辑生成
与主时钟的关系:

  • 分频
  • 倍频
  • 分频和倍频 (MMCM)得到
  • 相位移动或者波形反向
  • 占空比变换
  • 上面 的组合
    推荐先定义所有基本时钟,然后定义所需要的生成时钟
  • 使用create_generated_clock 创建
  • 使用-source 指定主时钟,可以是主时钟的原点或者生成时钟源单元的输入引脚,如寄存器二分频的D端,Q端为输出时钟最好使用主时钟原点定义约束
  • 也可以使用 -edges{} 按照源时钟边沿索引建立关系
  • 或者使用 **-edge_shift {}**添加相移 其中值可以为正值(代表边沿左移)和负值
//创建基本时钟
create_clock -name clkin -period 10 [get_ports clk]
//生成时钟
create_generated_clock -name clkdiv2 -source[get_ports clkin] -div_by 2 \ [get_pins REGA/Q]  //REGA/Q表示是这个寄存器的Q端生成的时钟驱动后面电路
//生成一个时钟,占空比比25%,相位移动90
create_generated_clock -name clkshift -source[get_ports clkin] -edges{1,2,3}\ -edge_shift{2.5,0 2.5}[get_pins mmcm0/CLKOUT]	

时钟组

-set_clock_groups 禁止在所标识的时钟组之间,以及在一个时钟组内的时钟进行时序分析。Vivado默认全部计算,忽略不代表两个时钟路径之间的工作是正常的,需要自己分析
同步时钟(相位可以预测):同一个时钟源,或者具有公共周期(vivado最大可算1000的公共周期,大于还没有公共周期就是不可扩展的,无法进行安全时序分析)
异步时钟:相位不可知
互斥时钟组:就是理论上不能同时存在的(mux),但是却能进行时序分析

时序例外

  • 多周期路径:修改建立和保持关系
  • 假路径

6:对于多位的异步信号如何进行同步?

对以一位的异步信号可以使用“一位同步器进行同步”(使用两级触发器),而对于多位的异步信号,可以采用如下方法:1:可以采用保持寄存器加握手信号的方法(多数据,控制,地址)2:特殊的具体应用电路结构,根据应用的不同而不同;3:异步FIFO。(最常用的缓存单元是DPRAM)
RTL:握手信号


7.异步复位,同步复位,异步复位同步释放

异步复位,同步复位,异步复位同步释放。
为什么使用:

  • 1.位于复位这个行为而言,异步操作时完全可以的,因为所有的元器件都会最终回到初始值,那么有没有出现亚稳态、谁先谁后其实都没有关系,就像电视剧里说的”反正早晚都是si,早si晚si又有什么区别“,就是这个道理,对功能完全不会有影响。
  • 2.但是对于撤销不行啊,一旦复位撤销了各个元器件就会开始工作了,如果复位撤销点到达各个元器件的时间有差别,或者正好打在了时钟的亚稳态窗(即在Tsetup+Thold内跳变了)上了,就会造成有的器件当前周期开始工作,而有的器件在下一周期开始工作,那整个系统就崩盘了这是绝对不允许的,因此复位的撤销一定要是同步的。

注意生成的硬件电路,只有异步复位是与寄存机直接连接,其他都是与D触发器输入端口D逻辑相连

同步复位与异步复位的优缺点
同步复位的优点:

一般能够确保电路是百分之百同步的。
确保复位只发生在有效时钟沿,可以作为过滤掉毛刺的手段。
同步复位的缺点

复位信号的有效时长必须大于时钟周期,才能真正被系统识别并完成复位。同时还要考虑如:时钟偏移、组合逻辑路径延时、复位延时等因素。
由于大多数的厂商目标库内的触发器都只有异步复位端口,采用同步复位的话,就会耗费较多的逻辑资源。
异步复位优点

异步复位信号识别方便,而且可以很方便的使用全局复位。
由于大多数的厂商目标库内的触发器都有异步复位端口,可以节约逻辑资源。
异步复位缺点

复位信号容易受到毛刺的影响。
复位结束时刻恰在亚稳态窗口内时,无法决定现在的复位状态是1还是0,会导致亚稳态。

异步复位同步释放

使用异步复位同步释放就可以消除上述缺点。所谓异步复位,同步释放就是在复位信号到来的时候不受时钟信号的同步,而是在复位信号释放的时候受到时钟信号的同步。异步复位同步释放的原理图和代码如下
复位时:是异步复位,显而易见,rst_async_n异步复位后,,与时钟无关,rst_sync_n将拉低,即实现异步复位。
释放时:这个是关键,看如何实现同步释放,即当复位信号rst_async_n撤除时,由于双缓冲电路的作用,rst_sync_n复位信号不会随着rst_async_n的撤除而撤除。,这样复位与时钟同步,在满足保持建立时间的情况下,不会出现亚稳态

如此一来,既解决了同步复位的资源消耗问题,也解决了异步复位的亚稳态问题。其根本思想,也是将异步信号同步化
9.18 verilog100题学习_第5张图片

module reset_best(clk,asyn_reset,syn_reset);
input clk;
input asyn_reset;
output syn_reset;


reg rst_s1;
reg rst_s2;


always @( posedge clk ,posedge  asyn_reset)
begin
if(asyn_reset)
 begin
 rst_s1<=1'b0;
 rst_s2<=1'b0;
 end
else 
begin
rst_s1<=1'b1;
rst_s2<=rst_s1;
end
end

assign syn_reset=rst_s2;

endmodule

你可能感兴趣的:(断情绝性)