1.毛刺(竞争冒险)
1.1 定义与成因
竞争:由于组合逻辑中存在的连线延迟和门延迟,以及各个信号高低电平转换需要的时间不同,导致同一个门(例如与门)的多个输入信号同时发生变化时,变化后的信号到达门电路输入端口的时间存在差别,这种现象叫做竞争。
冒险:由于竞争会导致门电路输出一些错误的尖峰信号,这些尖峰信号被称为毛刺。若电路输出会产生毛刺,我们就说电路中存在冒险。
由以上的定义可以看出,若电路有冒险,则一定有竞争,反之则不然。
以一个最简单的门电路
冒险可分为静态冒险和动态冒险,静态冒险指输入发生变化而输出不应该发生变化时却产生毛刺的冒险,动态冒险是输入发生变化,输出也发生变化时产生毛刺的冒险。冒险还可分为功能冒险和逻辑冒险,功能冒险指多个输入同时发生变化在输出端产生毛刺的冒险,逻辑冒险指一个输入发生变化在输出端产生毛刺的冒险。
1.2 判断方法
判断功能冒险的方式是只要输入信号不是按照循环码(格雷码)的形式变化的,就可能产生功能冒险。
判断逻辑冒险的方法可以用公式法或卡诺图法。若组合电路的逻辑表达式化简后包含诸如
1.3 消除毛刺的方法
由于毛刺一般是非常短促的脉冲,因此我们可以利用其无法满足D触发器保持/建立时间要求的特点(即触发器输入端对毛刺不敏感),通过同步电路触发器对组合逻辑输出进行采样的方法消除毛刺对后级电路的影响。此外还可以在输出信号的保持时间内产生一定宽度的高电平脉冲与组合逻辑电路输出信号进行与操作,从而完成采样,但这种方法对于脉冲信号的产生时机要求比较高,因此实现起来有较大难度。
对于功能冒险还可以使用格雷码计数器代替普通二进制计数器的方法来消除毛刺,即将多个信号同时变化改成每次只有一个bit位发生变化。
对于逻辑冒险则可以使用添加冗余项的方式来消除。例如逻辑表达式为
2.verilog代码与综合后的电路的对应关系
关于这一点我能想到的几个方面一是always块,若@包含的敏感列表为posedge形式或negedge形式,则综合后为触发器,且此时应用非阻塞赋值<=,且不能对同一个信号同时包含posedge和negedge(曾经想实现一个在时钟上下沿都能计数的计数器,后被师兄告知是不可综合的)。若@包含的敏感列表为电平信号,或*(代表always块中出现的所有信号),则即使always块中的信号定义为reg形式,也会被综合为组合逻辑电路,其此时应用阻塞赋值=。
另一个是if/else,case以及三元表达式A?B:C综合后电路的区别。以下面一段代码为例。
reg
从逻辑结果来看三个代码块中的b,c,d,e的结果是一样的,但就综合后的电路来说,b代码块中使用的if/else形式和d的三元表达式A?B:C形式会综合生成有先后顺序的电路,其中if的判断分支优先级最高,else if优先级依次降低;而c的case形式会生成多路选1的mux选择器,属于并行结构;e的纯门电路逻辑形式自然是生成无优先级的并行结构电路。
从以上例子可以看出,对同一种逻辑可以有多种不同的代码写法,而综合后的结果也是有很大差别的,需要仔细斟酌后选择,而不能像C++等高层次语言那样任选等价的表达式。此外,使用if/else和case语句时还要注意,在组合逻辑中一定要列出所有可能出现的情况,否则会在电路中生成latch锁存器,这是我们不希望看到的。
3.数字IC设计基本步骤
这在网上已经有很多总结的非常好的信息了,贴一个链接以供参考。
温戈:数字IC设计全流程介绍zhuanlan.zhihu.com