0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

什么样的Verilog代码风格是好的风格?

ruikundianzi 来源:硅农 作者:硅农 2022-10-24 15:23 次阅读

写代码是给别人和多年后的自己看的。 关于Verilog代码设计的一些风格和方法之前也写过一些Verilog有什么奇技淫巧?

模块化设计

把所有的代码都写到一个模块里,也不是一个好的风格。 积累自己的小IP,在芯片设计阶段,就将功能模块划分仔细,划分清楚,可复用的功能做成一个可参数化IP。搭建起你的数字积木。

对齐

把编辑器设置成tap自动替换成2/4个空格。 用空格对齐代码,提高代码观赏性。

 //case0
 input                   clk;
 input                   rst_n;
 inout                   in;
 output       [6:0]      out;
 //case1
 input                   clk     ;
 input                   rst_n   ;
 inout                   in      ;
 output       [6:0]      out     ;
连分号也要对齐的对齐狂魔,大可不必,徒增功耗。 关于提高Verilog代码编写效率的Gvim插件本订阅号之前也分享过,I/O端口按如上所示风格编写好后,直接可以生成端口列表。直接写assign和always块语句,也可以直接生成定义。省去手动定义的麻烦。

括号

用括号将表达式的条件括起来,让层次关系更清晰,一些情况不括起来功能上也没有问题,但是会引起阅读者的歧义和可读性差。善用括号,避免阅读歧义和工具理解歧义。

assign flag = cnt == 2'd1 && (mode != 2'd1 && (|v_shift) || cnt2 < 8'd15);


assign flag = (cnt == 2'd1) && ((mode != 2'd1) && (|v_shift) || (cnt2 < 8'd15));

能少写则少写

always @(posedge clk or negedge rst_n) 
begin
    if(!rst_n) begin
        out <= 0;
    end 
    else if(en)begin
        out <= in;
    end
    else begin
        out <= out;
    end
end


always @(posedge clk or negedge rst_n) begin
    if(!rst_n) 
        out <= 0;
    else if(en)
        out <= in;
end
只有单行语句可以省略去begin-end,一个always块只对一个变量操作。else分支如果是保持的话,可以省略。还有begin的位置...,能少写一行算一行。 注意,在组合逻辑中else分支不写会产生锁存器,写成了保持就是组合逻辑环,这一点要和时序逻辑分开。时序逻辑中else分支不写代表保持。
 always @(*)begin
     case(in[1:0])
         2'd0 : data[1:0] = 2'd0;
         2'd1 : data[1:0] = 2'd1;
         2'd2 : data[1:0] = 2'd2;
         default : data[1:0] = 2'd3;
     endcase
 end
case语句也一样,不写default分支会产生锁存器,如果case中的所有情况都达到,就可以不用写default分支,但在ASIC设计中可能工具会报lint,所以这样的写法是最完美的。

FSM

状态机采用三段式

591fe3be-5352-11ed-a3b6-dac502259ad0.png

Tips,在写状态机时,将第二段需要保持状态循环的状态写法,写成这样的写法,可以省去很多else的分支。 万物基于状态机——状态机大法好

assign语句慎用

assign语句+三目运算符/与或门逻辑慎用

 assign data_out[5:0] = data_vld0 ? data0[5:0] :
     data_vld1 ? data1[5:0] :
     data_vld2 ? data2[5:0] :
     data_vld3 ? data3[5:0] : 6'b0;
 
 assign data_out[5:0] = ({6{data_vld0}} & data0[5:0])
     | ({6{data_vld1}} & data1[5:0])
     | ({6{data_vld2}} & data2[5:0])
     | ({6{data_vld0}} & data3[5:0]);
这两种写法一个带有优先级另一个不带优先级,本身没什么问题。不过覆盖率的expression中会将这个表达式中的所有条件满足与否列出来。 其实很多情况是不可能出现的,比如这几个vld同时1,data为0的情况组合,但是这就需要designer一个个去waive掉,然后写出原因,选择的语句少了还好,但是如果非常多,waive起来工作量还是很大的,徒增功耗。 这样的问题可在开发阶段就避免。
 always @(*)begin
     if(data_vld0) 
         data_out[5:0] = data0[5:0];
     else if(data_vld1)
         data_out[5:0] = data1[5:0];
     else if(data_vld2)
         data_out[5:0] = data2[5:0];
     else if(data_vld3)
         data_out[5:0] = data3[5:0];
     else 
         data_out[5:0] = 6'd0;
 end
写成这样,所有条件跑到就可以了。并行的语句用case。用与门和或门做的表达可能会省一些cell,但是比起后来waive时漫长的体力活,省这一毛两毛的干啥。 看过一本书上的写法,将所有的组合逻辑都用assign做,把D触发器都做成IP,直接需要打拍的时候再调用。这样的思想很好,准确的将组合逻辑和时序逻辑分开,从代码到电路。 作者提到另一个原因是由于if-else和case不能传播不定态,有的EDA工具有X态传播选项,可以强行传播,一般也需要license,但并不是所有的EDA工具都有这个功能。 但是我个人(浅薄的)认为这样的风格不适合所有人。比如上面提到的覆盖率问题,还有代码的可读性问题,assign式的写法可读性会变差。 直接在声明wire时就给变量赋值这样的写法,连spyglass都过不了。还是先声明再用吧。 关于工具的license问题,看看公司怎么给解决。

乘法器分时复用

一个设计要考虑PPA最优,就要考虑乘法器的数量多少以及复用能不能最大化,追求最好的设计是整个数据通路中乘法器空闲不下来。 乘法器调用方法,一般是在乘法器的输入保证寄存器输入,结果输出到各个复用模块时打一拍再使用。可以做成在进行完乘法运算后,就打拍,这样消耗的寄存器会少很多。画个图意思一下(单bit)。
593d20dc-5352-11ed-a3b6-dac502259ad0.png
修改前
595af0d0-5352-11ed-a3b6-dac502259ad0.png

修改后

修改完后的寄存器省了很多,但是乘法器的输出寄存器负载会变大,不过后端综合时约束了max_fan_out工具会自动插buffer和复制寄存器,经过实测还是会节省很多面积,把一些优化工作可以交给工具去做,了解它,信任它,使用它。

数据位宽写全

 assign dout = din;
 
 always @(posedge clk or negedge rst_n)begin
     if(!rst_n)
         dout[255:0] <= 'd0;
     else 
         dout[255:0] <= din;
 end
写成这样
 assign dout[3:0] = din[3:0];
 
 always @(posedge clk or negedge rst_n)begin
     if(!rst_n)
         dout[255:0] <= 256'd0;
     else 
         dout[255:0] <= din;
 end
写代码时将数据位宽写全,方便编辑器插件自动生成定义,而且写上位宽再后续阅读代码时能一眼看变量的位宽,提高阅读效率。 寄存器赋初始值 'd0 'h0等等,功能应该没有问题,这样写工具会默认是最大32bit??lint检查工具可能会报出来,最后还是得修改,不如一次到位。

良好的代码风格

写了这么多,总结一起,其实关于代码风格的问题,通过多看书,多看一些代码风格的写法,很多书上都有关于一些常见的风格阐述,多写代码多积累,最后形成自己的代码风格习惯,另外一般公司都会有代码规范的文档,到时候参加工作以后,一定要记得多读几遍。

审核编辑:汤梓红

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • Verilog
    +关注

    关注

    28

    文章

    1326

    浏览量

    109302
  • 代码
    +关注

    关注

    30

    文章

    4555

    浏览量

    66771
  • 编辑器
    +关注

    关注

    1

    文章

    788

    浏览量

    30187

原文标题:什么样的Verilog代码风格是好的风格?

文章出处:【微信号:IP与SoC设计,微信公众号:IP与SoC设计】欢迎添加关注!文章转载请注明出处。

收藏 人收藏

    评论

    相关推荐

    FPGA实战演练逻辑篇39:代码风格与书写规范

    实现的书写方式,它更多的是强调代码的设计。要想做好一个FPGA设计,代码风格能够起到事半功倍的效果。(特权同学,版权所有)下面我们将就这两个方面做一些深入的探讨,也许没有绝对意义上
    发表于 06-19 10:38

    FPGA实战演练逻辑篇41:代码风格

    只有一个办法,便是要求设计者写出的HDL代码尽可能最优化。那么,我们又回到了老议题上——设计者的代码风格。而到底如何书写HDL代码才算是最优化,什么
    发表于 06-25 09:41

    勇敢的芯伴你玩转Altera FPGA连载35:Verilog代码风格概述

    设计者的用心良苦,也只有一个办法,便是要求设计者写出的HDL代码尽可能最优化。那么,我们又回到了老议题上——设计者的代码风格。而到底如何书写HDL代码才算是最优化,
    发表于 12-27 10:07

    Linux内核编码风格(编程代码风格推荐)

    这是翻译版本,英文原版是linux源码Documentation文件夹下的CodingStyle一个良好风格的程序看起来直观、美观,便于阅读,还能有助于对程序的理解,特别在代码量比较大情况下更显
    发表于 08-24 09:45

    C语言代码风格有哪些

    C语言代码的命名风格是怎样的?C语言代码的程序风格是怎样的?
    发表于 02-25 07:21

    什么是良好的Verilog代码风格

    推荐的代码风格。3、代码风格1、规则总览在设计这个模块的时候,我主要遵从了以下几条规则:Verilog2001标准的端口定义DUMMY模块逻
    发表于 06-02 14:48

    Altera代码风格讲义--作者:骏龙小马

    一个讲解Altera代码风格的讲义,适合初学者看看,verilog代码风格
    发表于 11-17 18:07 0次下载

    山东分公司的风格山东分公司的风格山东分公司的风格山东分公司的风格

    东分公司的风格东分公司的风格东分公司的风格东分公司的风格东分公司的风格东分公司的风格东分公司的
    的头像 发表于 09-07 14:57 1109次阅读

    你想iPhone变成什么样,iPhone 4中框风格最完美

    你心中的理想iPhone长什么样?日前,爆料达人Ben Geskin给出了自己心中完美iPhone的模样,刘海消失,中框重回iPhone 4风格,先来感受一下:
    的头像 发表于 11-22 09:11 2574次阅读

    Linux内核的首选代码风格应该如何设置

    这是一个简短的文档,描述了Linux内核的首选代码风格代码风格是因人而异的,而且我不愿意把我的观点强加给任何人,不过这里所讲述的是我必须要维护的
    发表于 11-04 17:17 6次下载
    Linux内核的首选<b class='flag-5'>代码</b><b class='flag-5'>风格</b>应该如何设置

    Verilog HIDL的RTL设计风格指南资源下载

    Verilog HIDL的RTL设计风格指南资源下载
    发表于 04-13 10:09 9次下载

    C语言代码风格

    个人代码风格记录此文将看到的一些好的代码风格规范总结起来,作为自己以后写代码时的参考。命名业界流行的3种命名
    发表于 01-13 13:13 1次下载
    C语言<b class='flag-5'>代码</b><b class='flag-5'>风格</b>

    什么是良好的Verilog代码风格

    相对于verilog1995的端口定义,这种定义方式将端口方向,reg或wire类型,端口位宽等信息都整合到了一起,减少了不必要的重复打字和出错几率,也使得代码长度大大缩短,非常紧凑。
    的头像 发表于 12-22 14:33 593次阅读

    Verilog编码风格的建议

    良好的编码风格,有助于代码的阅读、调试和修改。虽然 Verilog 代码可以在保证语法正确的前提下任意编写,但是潦草的编码风格往往是一锤子买
    的头像 发表于 06-01 16:27 493次阅读
    <b class='flag-5'>Verilog</b>编码<b class='flag-5'>风格</b>的建议

    浅谈Verilog HDL代码编写风格

    深层次的问题,对于这个行业来说可能我才是一直脚踩在门外面。所以这篇文章是写给一些刚开始学习FPGA、Verilog HDL的同学,我看过一些大神写的代码,然后尽量模仿大神写法,经过好几个大神的影响和自己
    的头像 发表于 11-20 10:04 309次阅读
    浅谈<b class='flag-5'>Verilog</b> HDL<b class='flag-5'>代码</b>编写<b class='flag-5'>风格</b>