4、组合逻辑优化:减少逻辑级数、使用并行结构、操作符平衡
组合逻辑,说白了就是没有记忆功能的电路。信号从输入进来,经过一堆门,直接跑到输出。这中间每经过一级门,就多一份延迟。我刚开始做设计那会儿,总觉得组合逻辑写起来很爽,一行表达式搞定所有功能。结果一跑时序分析,好家伙,路径延迟直接爆表。
为什么会这样?因为综合工具不是万能的。你写出来的RTL代码,决定了综合后电路的拓扑结构。代码写得不好,工具再怎么优化也救不回来。所以,咱们得从源头下手——优化组合逻辑。
4.1 减少逻辑级数
逻辑级数,就是信号从输入到输出经过的逻辑门层数。级数越多,延迟越大。这个道理很简单,但实际项目中很多人会忽略。
举个例子,一个8输入的与门,如果你写成:
assign y = a & b & c & d & e & f & g & h;
综合工具可能会把它展开成多级逻辑。比如先算 a&b,再算 (a&b)&c,以此类推。这样级数就多了。
更好的做法是手动构建树形结构:
assign ab = a & b;
assign cd = c & d;
assign ef = e & f;
assign gh = g & h;
assign abcd = ab & cd;
assign efgh = ef & gh;
assign y = abcd & efgh;
这样逻辑级数从7级降到了3级。我在一个高速接口项目中遇到过类似问题,原本时序怎么都收敛不了,改成这种结构后,一下子就过了。
4.2 使用并行结构
并行结构,就是把串行的计算拆成并行的。你想想看,串行是一条路走到黑,并行是几条路同时走,谁快谁慢一目了然。
比如一个加法器链:
assign sum = a + b + c + d + e + f + g + h;
这会被综合成串行加法器链,延迟很大。改成并行加法树:
assign s1 = a + b;
assign s2 = c + d;
assign s3 = e + f;
assign s4 = g + h;
assign s5 = s1 + s2;
assign s6 = s3 + s4;
assign sum = s5 + s6;
这样只需要3级加法,而不是7级。我曾经在一个DSP加速器里用这个技巧,把关键路径从5.2ns降到了3.1ns,效果立竿见影。
4.3 操作符平衡(Balanced Tree)
操作符平衡,说白了就是把表达式里的操作符组织成平衡树结构。这样每条路径的延迟差不多,不会出现某一条路径特别长的情况。
比如一个多输入的比较器:
assign match = (a == b) & (c == d) & (e == f) & (g == h);
如果不加干预,综合工具可能会先算 (a==b)&(c==d),再跟 (e==f) 与,最后跟 (g==h) 与。这样级数不均匀。
手动平衡一下:
assign eq1 = (a == b) & (c == d);
assign eq2 = (e == f) & (g == h);
assign match = eq1 & eq2;
这样两条路径的延迟就一样了。嗯,这里要注意,平衡树不仅适用于与或逻辑,也适用于加法、乘法等算术运算。
4.4 实战中的避坑指南
我曾经在一个项目中,遇到一个复杂的组合逻辑块,里面嵌套了多层条件表达式。代码看起来挺简洁,但时序分析报告显示路径延迟超标了40%。
我仔细一看,发现是这么写的:
assign y = (sel0) ? (sel1 ? a : b) : (sel2 ? c : d);
这种嵌套的MUX,综合出来级数很多。改成并行MUX结构后,问题就解决了:
assign y = sel0 ? (sel1 ? a : b) : (sel2 ? c : d);
// 改成
wire mux1 = sel1 ? a : b;
wire mux2 = sel2 ? c : d;
assign y = sel0 ? mux1 : mux2;
你看,其实就是把嵌套展开成两级并行MUX。级数从3级降到了2级,而且两条路径对称。
| 优化方法 | 适用场景 | 效果 | 代价 |
|---|---|---|---|
| 减少逻辑级数 | 大扇入逻辑 | 延迟降低明显 | 面积略增 |
| 并行结构 | 串行运算链 | 延迟大幅降低 | 面积增加较多 |
| 操作符平衡 | 多输入运算 | 路径延迟均衡 | 面积少量增加 |
我个人习惯是,在写RTL之前先画个草图,看看信号是怎么流动的。如果发现某条路径特别长,就提前做优化。别等到时序分析报告出来再改,那时候改起来就费劲了。
4.5 知识体系总览
下面这张图总结了组合逻辑优化的核心思路。你可以看到,三种方法其实都是围绕一个目标:让信号走更短的路。
说白了,组合逻辑优化就是跟延迟赛跑。你跑得比时钟快,时序就收敛;跑不过,就出问题。我建议你在写RTL的时候,脑子里时刻想着「这条路径有多少级门?」。养成这个习惯,时序收敛就不再是难题。
可可精品资料库