例说verilog中的generate

贴出我项目代码中一部分的generate代码,跟大家分享一下这种表达方式,期待大家领略其精神实质。

    genvar i;
    generate    
	for(i=0;i<32;i=i+1)    begin:down_wreq_gen        
    always @(posedge up_clk )down_wreq[i]<=(up_waddr[13:9]==i)&&(up_wreq==1);    
    end    
	endgenerate

 

这其实是一种类似脚本语言的描述方法,就是循环展开32次。我们可以用C语言写个小代码实现这部分展开:


void main (void){
int i ;
 
	
	
		for(i=0;i<32;i=i+1) //   begin:down_wreq_gen        
    printf("always @(posedge up_clk )down_wreq[%-2d]<=(up_waddr[13:9]==%-2d)&&(up_wreq==1);\n",i,i);    
    //end    
	
	 
}
 

		
 

从上面程序段很清晰看到其实就是generate语句用c语言复述一遍。

C语言执行后,打印出来的结果如下:

always @(posedge up_clk )down_wreq[0 ]<=(up_waddr[13:9]==0 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[1 ]<=(up_waddr[13:9]==1 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[2 ]<=(up_waddr[13:9]==2 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[3 ]<=(up_waddr[13:9]==3 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[4 ]<=(up_waddr[13:9]==4 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[5 ]<=(up_waddr[13:9]==5 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[6 ]<=(up_waddr[13:9]==6 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[7 ]<=(up_waddr[13:9]==7 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[8 ]<=(up_waddr[13:9]==8 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[9 ]<=(up_waddr[13:9]==9 )&&(up_wreq==1);
always @(posedge up_clk )down_wreq[10]<=(up_waddr[13:9]==10)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[11]<=(up_waddr[13:9]==11)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[12]<=(up_waddr[13:9]==12)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[13]<=(up_waddr[13:9]==13)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[14]<=(up_waddr[13:9]==14)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[15]<=(up_waddr[13:9]==15)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[16]<=(up_waddr[13:9]==16)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[17]<=(up_waddr[13:9]==17)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[18]<=(up_waddr[13:9]==18)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[19]<=(up_waddr[13:9]==19)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[20]<=(up_waddr[13:9]==20)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[21]<=(up_waddr[13:9]==21)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[22]<=(up_waddr[13:9]==22)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[23]<=(up_waddr[13:9]==23)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[24]<=(up_waddr[13:9]==24)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[25]<=(up_waddr[13:9]==25)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[26]<=(up_waddr[13:9]==26)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[27]<=(up_waddr[13:9]==27)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[28]<=(up_waddr[13:9]==28)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[29]<=(up_waddr[13:9]==29)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[30]<=(up_waddr[13:9]==30)&&(up_wreq==1);
always @(posedge up_clk )down_wreq[31]<=(up_waddr[13:9]==31)&&(up_wreq==1);

这一堆代码就对应上述generate描述的内容。这些代码完全可以替代之前的用generate的描述。

通过这个是不是很形象的理解generate作为脚本语言实现循环罗列的功能了呢?

另外还有一个重要功能就是条件编译,就类似于预处理语句ifdef。这方面例子很多,不多说。

你可能感兴趣的:(VERILOG,ZEDBOARD)