原创 Verilog代码优化之case语句

2008-7-29 21:45 17126 10 17 分类: FPGA/CPLD

Verilog代码优化之case语句<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />


       题记:那天做完13路脉冲计数并写入dual RAM模块的设计后组长看了我的资源占用,吃惊的说怎么占用资源这么少啊,以为我偷工减料了。呵呵,其实这个也是一直困扰初学者的一个课题,可综合的verilog是一个,最优化的代码也是一个,所以就想说说这方面的问题,算是自己攒的一点经验分享吧,可能会有所欠缺或者说的不太对,还望EDN的各路高手指点。那就先从case语句和ifelse语句开始吧。


 


代码一:


module test_3(clk,rst_n,data,add);


 


input clk;


input rst_n;


input[3:0] data;


output[2:0] add;


 


reg[2:0] add;


 


always @ (posedge clk) begin


       if(!rst_n) begin


              add <= 0;


              end


       else begin


              case(data)


              0,1,2,3:   add <= 1;


              4,5,6,7:   add <= 2;


              8,9,10,11:       add <= 3;


              12,13,14,15: add <= 4;


              default: ;


              endcase


              end


end


 


endmodule


资源占用情况:


Design Statistics


# IOs                              : 9


 


Macro Statistics :


# RAM                              : 1


#      16x3-bit single-port block RAM: 1


 


Cell Usage :


# BELS                             : 3


#      GND                         : 1


#      INV                         : 1


#      VCC                         : 1


# RAMS                             : 1


#      RAMB16_S36                  : 1


# Clock Buffers                    : 1


#      BUFGP                       : 1


# IO Buffers                       : 8


#      IBUF                        : 5


#      OBUF                        : 3


 


Selected Device : 3s50pq208-5


 


 Number of bonded IOBs:                  9  out of    124     7% 


 Number of BRAMs:                        1  out of      4    25% 


 Number of GCLKs:                        1  out of      8    12%


 


 


代码二:


module test_3(clk,rst_n,data,add);


 


input clk;


input rst_n;


input[3:0] data;


output[2:0] add;


 


reg[2:0] add;


 


always @ (posedge clk) begin


       if(!rst_n) begin


              add <= 0;


              end


       else begin


              casex(data)


              4'b00xx:  add <= 1;


              4'b01xx:  add <= 2;


              4'b10xx:  add <= 3;


              4'b11xx:  add <= 4;


              default: ;


              endcase


              end


end


 


endmodule


资源占用情况:


Design Statistics


# IOs                              : 9


 


Macro Statistics :


# Registers                        : 1


#      3-bit register              : 1


 


Cell Usage :


# BELS                             : 4


#      INV                         : 2


#      LUT2                        : 2


# FlipFlops/Latches                : 3


#      FDR                         : 3


# Clock Buffers                    : 1


#      BUFGP                       : 1


# IO Buffers                       : 6


#      IBUF                        : 3


#      OBUF                        : 3


 


Selected Device : 3s50pq208-5


 


 Number of Slices:                       2  out of    768     0% 


 Number of Slice Flip Flops:             3  out of   1536     0% 


 Number of 4 input LUTs:                 2  out of   1536     0% 


 Number of bonded IOBs:                  9  out of    124     7% 


 Number of GCLKs:                        1  out of      8    12%


 


 


代码三:


module test_3(clk,rst_n,data,add);


 


input clk;


input rst_n;


input[3:0] data;


output[2:0] add;


 


reg[2:0] add;


 


always @ (posedge clk) begin


       if(!rst_n) begin


              add <= 0;


              end


       else begin


              if(data<4) add <= 1;


              else if(data<8) add <= 2;


              else if(data<12) add <= 3;


              else add <= 4;


              end


end


 


endmodule


资源占用情况:


Design Statistics


# IOs                              : 9


 


Macro Statistics :


# Registers                        : 3


#      1-bit register              : 3


# Multiplexers                     : 1


#      3-bit 4-to-1 multiplexer    : 1


# Comparators                      : 3


#      4-bit comparator less       : 3


 


Cell Usage :


# BELS                             : 6


#      INV                         : 1


#      LUT2                        : 4


#      LUT3                        : 1


# FlipFlops/Latches                : 3


#      FDR                         : 2


#      FDRS                        : 1


# Clock Buffers                    : 1


#      BUFGP                       : 1


# IO Buffers                       : 6


#      IBUF                        : 3


#      OBUF                        : 3


 


Number of Slices:                       3  out of    768     0% 


 Number of Slice Flip Flops:             3  out of   1536     0% 


 Number of 4 input LUTs:                 5  out of   1536     0% 


 Number of bonded IOBs:                  9  out of    124     7% 


 Number of GCLKs:                        1  out of      8    12% 


 


 


结语:硬件设计和软件编程不同,在C语言里ifelsefor循环满天飞,可以说用这两个语句打天下都是不成问题的,但是HDL设计中这是万万不可的。我们先分析上面的结果,从以上的代码综合后的占用资源情况对比,case语句和casex语句是差不多的,一般在设计中如果可以使用casex语句那就优先考虑,其次case语句也是很常用的,至于ifelse语句,明眼人一看就知道,比case(x)语句多出的寄存器比较器如果是一个更高级的ifelse嵌套那么无非对硬件资源是一个巨大的浪费,至于for语句,这里没有进行对比,虽然在很多的综合工具里这个语句是可综合的,但是因为它在设计中往往不是可以和case或者ifelse语句互相代替使用,所以放在后面再讨论。


 

文章评论7条评论)

登录后参与讨论

用户1668914 2014-3-23 21:25

有时候还是要用一下真值表的,不能全部依靠EDA工具去优化,代码的风格和实现方式影响也很大

用户1639510 2012-3-8 23:27

<1>我看网上其它文章的时候,说一般不用casex,有没有道理呢? <2>可以只用data[3:2]来判断,同样可以达到一样的效果。<3>对于您说的情况,我们可以画个真值表,然后化简,再用case语句。

用户380644 2011-3-5 16:40

是不是就是用外部硬件实现DMA功能呀 大尺寸的液晶屏都需要硬件加速吧 不然由于带宽的原因 显示效果无法忍受

用户305327 2010-12-26 15:48

特权你好,我问一个问题:如果想用if来判断表达式中的不确定状态时怎么会得不到想要的结果? 例如:if(cnt==3'b1??) express1; else express2; 可运行时发现express1根本没有执行过,这是什么原因呀?难道cnt==3'b1??在if表达式中总是被判错的?为什么?

ilove314_323192455 2010-10-20 11:56

YES

用户237273 2010-10-19 23:20

这是不是有点像DMA?

用户546604 2010-10-14 14:49

casex dc可以综合出来?版主

用户546604 2010-10-14 14:21

bozhu 人才 谢谢你的经验介绍

用户553565 2010-8-26 09:28

希望能得到你的答复。。谢谢

用户553565 2010-8-26 09:27

实际数: 0x08 0x06 0x00 0x02 0x00 0x00 0x00 0x09 我得出的数据。 0x08 0x06 0x00 0x02 0x00 0x00 0x00(这里为空字符) 开始USB 设备请求 设置地址 设备请求 置配请求。。。0x08 0x06 0x00 0x02 0x00 0x00 0x00 (这里为空字符) 就在这里出错。。读不出长度。。停一会,再重新枚举, 最后还能枚举成功,不明什么原因?我用D11和D12都是一样。用圈圈的程序也是一样,(因为我用AVR,可能会有点不同,但总体上相同。)郁闷啊。 reset重起 suspend挂起 reset重起 suspend挂起 suspend挂起 reset重起 设备描述符请求。 设地址 设备描述符请求。 配置描述符。。。()这里没有给出长度。。/。?不明。 如果发现上面情况如何解决,都被这个问题弄了几个月了,都不知原因。。。
相关推荐阅读
特权ilove314 2016-06-30 21:16
例说FPGA连载6:FPGA开发所需的技能
例说FPGA连载6:FPGA开发所需的技能 特权同学,版权所有 配套例程和更多资料下载链接: http://pan.baidu.com/s/1c0nf6Qc   前面的文字已经做了很多铺垫,相信读...
特权ilove314 2016-06-28 21:09
例说FPGA连载5:FPGA的优势与局限性
例说FPGA连载5:FPGA的优势与局限性 特权同学,版权所有 配套例程和更多资料下载链接: http://pan.baidu.com/s/1c0nf6Qc   若要准确评估FPGA技术能否满足开...
特权ilove314 2016-06-28 21:05
例说FPGA连载5:FPGA的优势与局限性
例说FPGA连载5:FPGA的优势与局限性 特权同学,版权所有 配套例程和更多资料下载链接: http://pan.baidu.com/s/1c0nf6Qc   若要准确评估FPGA技术能否满足开...
特权ilove314 2016-06-26 22:11
例说FPGA连载4:FPGA语言与厂商介绍
例说FPGA连载4:FPGA语言与厂商介绍 特权同学,版权所有 配套例程和更多资料下载链接: http://pan.baidu.com/s/1c0nf6Qc   Verilog与VHDL 说到FP...
特权ilove314 2016-06-23 21:26
例说FPGA连载3:FPGA与其它主流芯片的比较
例说FPGA连载3:FPGA与其它主流芯片的比较 特权同学,版权所有 配套例程和更多资料下载链接: http://pan.baidu.com/s/1c0nf6Qc   FPGA、ASIC和ASSP...
特权ilove314 2016-06-21 20:32
例说FPGA连载2:FPGA是什么
例说FPGA连载2:FPGA是什么 特权同学,版权所有 配套例程和更多资料下载链接: http://pan.baidu.com/s/1c0nf6Qc   2015年伊始,Intel欲出资百亿美金收...
我要评论
7
10
关闭 站长推荐上一条 /2 下一条