代码综合后的电路对比(不定期更新)
来源:互联网 发布:知乎电子书 编辑:程序博客网 时间:2024/06/11 08:08
这里来记录一下相似代码之间的不同差异,比如同步复位与异步复位触发器的对比,上升沿复位和下降沿复位的对比等等。这里主要使用ISE的综合引擎。直接附上代码和综合后电路图,有些会有部分讲解。
一、异步复位与同步复位
我在复位电路里面讲解了同步复位和异步复位的区别,这里就不详细介绍了,链接如下:http://www.cnblogs.com/IClearner/p/6683100.html
(1)异步复位
异步复位的代码如下所示:
module DFF1( input clk, input rst_n, input d, output reg q);always@(posedge clk or negedge rst_n) if(!rst_n) q <= 0; //异步清 0,低电平有效 else q <= d;endmodule
综合得到的电路图如下所示:
可以看到使用了一个反相器单元和一个触发器单元;从代码中我们可以推断出,这是一个高电平有效的、异步复位触发器。
(2)同步复位
同步复位触发器代码如下所示,注意黑体部分
module DFF2( input clk, input rst_n, input d, output reg q);always@(posedge clk )//注意这里有所不同 if(!rst_n) q <= 0; //同步清 0,低电平有效 else q <= d;endmodule
综合得到的电路如下所示:
我们可以看到,也是由一个反向器单元和一个触发器单元构成,注意,这里的触发器跟上面的触发器显然不是同一个类型的触发器,管脚名称改变了;结合代码我们可以知道,这个触发器是高电平触发、同步复位的触发器(由于是输入信号是低电平有效,所以加了个反相器)。
二、不同电平之间的复位差异
(1)高电平触发的异步复位VS低电平触发的异步复位
①高电平触发的异步复位(异步置位)
代码如下所示:
![](http://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
![](http://images.cnblogs.com/OutliningIndicators/ExpandedBlockStart.gif)
1 module DFF3( 2 input clk, 3 input rst_r, 4 input d, 5 output reg q 6 ); 7 8 always@(posedge clk or posedge rst_r) 9 if(rst_r)10 q <= 0; 11 else12 q <= d;13 14 endmodule
综合得到的电路如下所示:
根据代码,容易推断得出这是一个高电平触发、异步复位的触发器(或者叫异步置位),这也与前面的内容相符合(高电平触发复位,所以不用加反相器)。
②低电平触发的异步复位
代码和电路跟 一(1)的代码和电路相同,这里不进行重述。
(2)高电平触发的同步复位VS低电平触发的同步复位
①高电平触发的同步复位
代码如下所示:
1 module DFF4( 2 input clk, 3 input rst_r, 4 input d, 5 output reg q 6 ); 7 8 always@(posedge clk ) 9 if(rst_r)10 q <= 0; 11 else12 q <= d;13 14 endmodule
综合得到的电路如下所示:
可以知道,这是一个高电平有效、同步复位的触发器单元。
②低电平触发的同步复位
代码和电路同一(2),这里不进行重述
三、阻塞赋值和非阻塞赋值
(1)阻塞赋值综合的触发器
代码如下所示,这里为了使用高电平触发的触发器单元,写出高电平复位:
1 module DFF_chain( 2 input clk, 3 input rst_r, 4 input d, 5 output reg q 6 ); 7 reg reg_m ; 8 always @(posedge clk )//high level reset,synchronization 9 if(rst_r)begin10 reg_m = 0;//block11 q = 0; 12 end else begin13 reg_m = d;14 q = reg_m ;15 end16 endmodule
综合得到的电路如下所示:
可以看到,综合得到只有一个触发器,中间的触发器变量reg_m被优化掉了,只剩下q这个触发器。
(2)换个顺序的非阻塞赋值的触发器
把后面的这两个语句对调一下,同时把中间的变量改个名字,改成reg_block(这里改名字只是为了区分后面的非阻塞赋值的情况)
即要综合的代码如下所示:
1 module DFF_chain( 2 input clk, 3 input rst_r, 4 input d, 5 output reg q 6 ); 7 reg reg_block ; 8 always @(posedge clk )//high level reset,synchronization 9 if(rst_r)begin//block10 reg_block = 0;11 q = 0; 12 end else begin //here has changed13 q = reg_block ;14 reg_block = d; 15 end16 endmodule
综合得到的电路如下所示:
可以看到,调换顺序之后,得到了我们我们想要的触发器链。
结论:描述时序逻辑使用阻塞赋值可能得到正确的结果,也可以得到不正确的结果,因此时序逻辑不建议使用阻塞赋值。
(3)非阻塞赋值综合的触发器
代码如下所示:
1 module DFF_chain( 2 input clk, 3 input rst_r, 4 input d, 5 output reg q 6 ); 7 reg reg_m ; 8 always @(posedge clk )//high level reset,synchronization 9 if(rst_r)begin10 reg_m <= 0;//non block 11 q <= 0; 12 end else begin13 reg_m <= d;14 q <= reg_m ;15 end16 endmodule
综合得到的电路如下所示:
从电路图中可以看到,综合得到了两个触发器,中间的触发器reg_m被保留下来了,达到了我们预想中的触发器链。
(4)换个顺序后的非阻塞赋值
跟前面的阻塞赋值一样,我们换一下顺序,代码如下所示:
1 module DFF_chain( 2 input clk, 3 input rst_r, 4 input d, 5 output reg q 6 ); 7 reg reg_nonblock ; 8 always @(posedge clk )//high level reset,synchronization 9 if(rst_r)begin//non block10 reg_nonblock <= 0;11 q <= 0; 12 end else begin13 q <= reg_nonblock ;14 reg_nonblock <= d; 15 end16 endmodule
综合得到的电路如下所示:
从电路中可以看到,即使调换了顺序,电路还是我们需要的触发器链。
结论:描述时序逻辑,使用非阻塞赋值可以得到正确的结果,因此时序逻辑推荐使用非阻塞赋值。
(5)描述组合逻辑电路时的阻塞赋值和非阻塞赋值
阻塞赋值描述组合逻辑(加法器),代码如下所示:
1 module Adder( 2 input a, 3 input b, 4 input c, 5 output reg q 6 ); 7 reg sum_block ; 8 always @(* ) 9 begin10 sum_block = a + b ;11 q = sum_block + c; 12 end13 endmodule
综合得到电路如下所示:
综合得到的电路是一个加法器。
我们改成非阻塞赋值看看,代码如下所示:
1 module Adder( 2 input a, 3 input b, 4 input c, 5 output reg q 6 ); 7 reg sum_block ; 8 always @(* ) 9 begin10 sum_block <= a + b ;11 q <= sum_block + c; 12 end13 endmodule
综合得到的电路:
综合得到的电路也是一个加法器。
因此可以冒险地得到一个结论,无论是阻塞赋值还是非阻塞赋值,都可以描述组合逻辑,但是一般情况下,我们推荐使用阻塞赋值,一方面是对仿真有用,另一方面是区别于描述时序逻辑的非阻塞赋值。
最后我尝试着在同一个块中使用阻塞赋值和非阻塞赋值,ISE的综合器报错。
- 代码综合后的电路对比(不定期更新)
- 工作积累的一些代码教训(不定期更新)
- 代码如诗(不定期更新)
- PHP常用代码整理(不定期更新)
- JS练习代码库(不定期更新)
- 消息使用的积累(不定期更新)
- Sqlite3的使用小结(不定期更新)
- Sqlite3的使用小结(不定期更新)
- android-listview的总结(不定期更新)
- CodeBlocks 的使用方法(不定期更新)
- java的一些总结(不定期更新)
- oracle的坑(不定期更新)
- 要看的文章(不定期更新)
- TextView的使用(不定期更新)
- 最近读的书(不定期更新)
- 有价值的问题(不定期更新)
- LeetCode解题的总结(不定期更新)
- 不定期更新的英语
- 多线程编程1
- 盒子中的div垂直居中方法记录
- 非库存采购的自动记帐
- 第六天:图像的基本运算
- 浅析GridView制作九宫格列表
- 代码综合后的电路对比(不定期更新)
- 一文读懂集成学习
- 问题 G: 想上分的鲸鱼
- Linux编程5中IO模型
- unity实现任意多边形三角剖分
- KazaQ's Socks
- Mayor's posters(区间覆盖+点离散化)
- [ubuntu]安装virtualenv,virtualenvwrapper出错
- Zookeeper系列(一)