微波EDA网,见证研发工程师的成长!
首页 > 研发问答 > 嵌入式设计讨论 > FPGA,CPLD和ASIC > verilog求助

verilog求助

时间:10-02 整理:3721RD 点击:
我是初学者,下面是我学着写的一个异步fifo的代码:
module fifo(clka,clkb,rd_en,wt_en,full,empty,clr,din,dout);

parameter width = 7,
           addr_width = 9,
                   max_width = 1023,
                   gray_txt = 10'b1000000000;
                  
input clka,clkb,clr,rd_en,wt_en;
input[width:0] din;
output[width:0] dout;
output full,empty;

reg[width:0] dout;
reg full,empty;
reg[width:0] remb[0:max_width];
reg[addr_width:0] rd_p,wt_p;
reg txta,txtb;
// write data
always @(posedge clka)
begin
if(full == 0 && wt_en)
remb[wt_p] <= din;
end

// read data
always @(posedge clkb)
begin
if(empty == 0 && rd_en)
dout <= remb[rd_p];
end

//write pointer
always @(posedge clka or negedge clr)
begin
wt_p <= gray(clr,(full || (wt_en == 0)));
end

//read pointer
always @(posedge clkb or negedge clr)
begin
rd_p <= gray1(clr,(empty || (rd_en == 0)));
end

//singal txta for write
always @(posedge clka or negedge clr)
begin
if(!clr)
txta <= 0;
else if(wt_p == gray_txt)
txta <= ~txta;
end

//singal txtb for read
always @(posedge clkb or negedge clr)
begin
if(!clr)
txtb <= 0;
else if(rd_p == gray_txt)
txtb <= ~txtb;
end

// full generate
always @(posedge clka or negedge clr)
begin
if(!clr)
full <= 0;
else if(txta == ~txtb && wt_p == rd_p)
full <= 1;
else
full <= 0;
end

// empty generate
always @(posedge clkb or negedge clr)
begin
if(!clr)
empty <= 1;
else if(txta == txtb && wt_p == rd_p)
empty <= 1;
else
empty <= 0;
end


//gray for address pointer
function[addr_width:0] gray;
input clr;
input en;

reg[addr_width:0] cnt;

begin
cnt = clr? (en ? cnt : (cnt + 1)) : 0;
/*  
   if(clr)
   begin
     if(en)
       cnt = cnt;
     else
       cnt = cnt + 1;
    end
  else
    cnt = 0;
*/     

   gray[addr_width] = 0 ^ cnt[addr_width];
   gray[addr_width - 1]  = cnt[addr_width] ^ cnt[addr_width - 1];
   gray[addr_width - 2]  = cnt[addr_width - 1] ^ cnt[addr_width - 2];
   gray[addr_width - 3]  = cnt[addr_width - 2] ^ cnt[addr_width - 3];
   gray[addr_width - 4]  = cnt[addr_width - 3] ^ cnt[addr_width - 4];
   gray[addr_width - 5]  = cnt[addr_width - 4] ^ cnt[addr_width - 5];
   gray[addr_width - 6]  = cnt[addr_width - 5] ^ cnt[addr_width - 6];
   gray[addr_width - 7]  = cnt[addr_width - 6] ^ cnt[addr_width - 7];
   gray[addr_width - 8]  = cnt[addr_width - 7] ^ cnt[addr_width - 8];
   gray[addr_width - 9]  = cnt[addr_width - 8] ^ cnt[addr_width - 9];

end
endfunction


function[addr_width:0] gray1;
input clr;
input en;

reg[addr_width:0] cnt;
         
begin
cnt = clr? (en ? cnt : (cnt + 1)) : 0;
/*  
   if(clr)
   begin
     if(en)
       cnt = cnt;
     else
       cnt = cnt + 1;
    end
  else
    cnt = 0;
*/     

   gray1[addr_width] = 0 ^ cnt[addr_width];
   gray1[addr_width - 1]  = cnt[addr_width] ^ cnt[addr_width - 1];
   gray1[addr_width - 2]  = cnt[addr_width - 1] ^ cnt[addr_width - 2];
   gray1[addr_width - 3]  = cnt[addr_width - 2] ^ cnt[addr_width - 3];
   gray1[addr_width - 4]  = cnt[addr_width - 3] ^ cnt[addr_width - 4];
   gray1[addr_width - 5]  = cnt[addr_width - 4] ^ cnt[addr_width - 5];
   gray1[addr_width - 6]  = cnt[addr_width - 5] ^ cnt[addr_width - 6];
   gray1[addr_width - 7]  = cnt[addr_width - 6] ^ cnt[addr_width - 7];
   gray1[addr_width - 8]  = cnt[addr_width - 7] ^ cnt[addr_width - 8];
   gray1[addr_width - 9]  = cnt[addr_width - 8] ^ cnt[addr_width - 9];

end
endfunction

endmodule

我用synplify综合出来没有错,但报了很多警告,大致如下:   综合出来后的RTL图和TECHNOLOGY图只有一个触发器和一些buffer,我知道可能和我写代码有问题,但我实在找不出问题出在哪里,请高手指教。   对了,这段代码我在quartusii 上面能综合,只报一些警告;而在ise上就无法综合,说我的调用函数的描述不符合FF规则。
@N: CG364 :"E:\sim_test\synplify\fifo\fifo.v":1:7:1:10|Synthesizing module fifo
@N: CL134 :"E:\sim_test\synplify\fifo\fifo.v":21:1:21:6|Found RAM remb, depth=1024, width=8
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <9> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <8> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <7> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <6> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <5> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <4> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <3> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <2> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register bit <1> of rd_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <9> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <8> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <7> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <6> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <5> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <4> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <3> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <2> of wt_p[9:0]
@W: CL171 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register bit <1> of wt_p[9:0]
@W: CL189 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Register bit wt_p[0] is always 0, optimizing ...
@W: CL189 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Register bit rd_p[0] is always 0, optimizing ...
@W: CL169 :"E:\sim_test\synplify\fifo\fifo.v":35:1:35:6|Pruning Register wt_p[0]
@W: CL169 :"E:\sim_test\synplify\fifo\fifo.v":41:1:41:6|Pruning Register rd_p[0]
@W: CL190 :"E:\sim_test\synplify\fifo\fifo.v":76:1:76:6|Optimizing register bit empty to a constant 1
@W: CL190 :"E:\sim_test\synplify\fifo\fifo.v":65:1:65:6|Optimizing register bit full to a constant 0
@W: CL169 :"E:\sim_test\synplify\fifo\fifo.v":65:1:65:6|Pruning Register full
@W: CL169 :"E:\sim_test\synplify\fifo\fifo.v":76:1:76:6|Pruning Register empty
@W: CL169 :"E:\sim_test\synplify\fifo\fifo.v":21:1:21:6|Pruning Register remb[7:0]
@W: CL159 :"E:\sim_test\synplify\fifo\fifo.v":8:7:8:10|Input clka is unused
@W: CL159 :"E:\sim_test\synplify\fifo\fifo.v":8:21:8:25|Input rd_en is unused
@W: CL159 :"E:\sim_test\synplify\fifo\fifo.v":8:27:8:31|Input wt_en is unused
@W: CL159 :"E:\sim_test\synplify\fifo\fifo.v":8:17:8:19|Input clr is unused
@W: CL159 :"E:\sim_test\synplify\fifo\fifo.v":9:16:9:18|Input din is unused
@END

如果是初学者,建议:
1. 把这里面的参数都去掉吧,就老老实实的写一个16深度,16宽度的异步FIFO。从简单的开始写,功能正确了再写复杂的。
2. 写完了之后做个功能仿真,直接 syncplify或者quartus,甚至ISE综合没有任何意义。错误和警告都没有意义,一个没有经过功能验证的东西,哪怕综合没有错误和警告,也不能在FPGA上应用。
3. if(empty == 0 && rd_en):这句话麻烦把优先级用括号表示清楚,比如:if((empty == 0) && rd_en),因为初学者十有八九会被运算优先级搞晕了脑子,那还不如别偷懒,乖乖的用括号。
4. 不要用function表示,老老实实的用代码一个个的写出来。千万别想一步登天,简简单单慢慢搞,从你写的function来看,你连combinational loop都写出来了,甚至,也许你还不清楚什么叫combinational loop。多多理解时序的概念,而很多的task和function会让你对时序晕头转向。
祝你进步。

your code should work



    谢谢 收益匪浅

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top