verilog代码将二进制输入转换为残差数系统

时间:2015-03-11 06:48:25

标签: verilog fpga system-verilog

我编写了一个代码,使用查找表将我们的二进制数转换为残差。

首先,我创建了一个具有读写和启用值的存储器。在“我们”期间,'a'是我输入的8位...对于a的每一位,它检查10是否为a[bit position]==1 },它会在dout(output)处发送mem[addr]。检查完所有8位后,将其发送到sum3sum5sum7

但是我无法获得输出,我得到了未定义的输出。

module mem(clk,we,re,a,sum7,sum5,sum3);

parameter ADD_WIDTH=3;
parameter DATA_WIDTH=9;
input [7:0] a;
//integer i;
input clk;
input we;
input re;
reg[ADD_WIDTH-1:0] addr;
reg [DATA_WIDTH-1:0] dout0,dout1,dout2,dout3,dout4,dout5,dout6,dout7;
reg [2:0] mod70,mod71,mod72,mod73,mod74,mod75,mod76,mod77,mod50,mod51,mod52,mod53,mod54,mod55,mod56,mod57,mod30,mod31,mod32,mod33,mod34,mod35,mod36,mod37;

output reg [3:0] sum3,sum5,sum7;
reg [DATA_WIDTH - 1 : 0] mem [2**ADD_WIDTH -1 : 0] ;
reg [3:0] count,count1;

always@(posedge clk)
begin 
 if (we)
  begin 
    case(addr)
     4'b000: mem[addr]=9'b001001001;
     4'b001: mem[addr]=9'b010010010;
     4'b010: mem[addr]=9'b100100001;
     4'b011: mem[addr]=9'b001011010;
     4'b100: mem[addr]=9'b010001001;
     4'b101: mem[addr]=9'b100010010;
     4'b110: mem[addr]=9'b001100001;
     4'b111: mem[addr]=9'b010011010;         
     endcase
    end
end

always@(posedge clk)
begin
dout0=9'd0;
dout1=9'd0;
dout2=9'd0;
dout3=9'd0;
dout4=9'd0;
dout5=9'd0;
dout6=9'd0;
dout7=9'd0;
mod30=3'd0;
mod31=3'd0;
mod32=3'd0;
mod33=3'd0;
mod34=3'd0;
mod35=3'd0;
mod36=3'd0;
mod37=3'd0;
mod51=3'd0;
mod52=3'd0;
mod53=3'd0;
mod54=3'd0;
mod55=3'd0;
mod56=3'd0;
mod57=3'd0;
mod71=3'd0;
mod72=3'd0;
mod73=3'd0;
mod74=3'd0;
mod75=3'd0;
mod76=3'd0;
mod77=3'd0;

//if (count1==1)
//begin
if (re && !we  )
begin
 case(addr)
  3'b000:
   begin
    dout0= mem[addr];
    mod30= dout0[2:0];
    mod50= dout0[5:3];
   mod70= dout0[8:6];
  end

  3'b001:
   begin
    dout1= mem[addr];
    mod31= dout1[2:0];
    mod51= dout1[5:3];
   mod71= dout1[8:6];
  end

  3'b010:
   begin
    dout2= mem[addr];
    mod32= dout2[2:0];
    mod52= dout2[5:3];
   mod72= dout2[8:6];
  end

   3'b011:
   begin
    dout3= mem[addr];
    mod33= dout3[2:0];
    mod53= dout3[5:3];
   mod73= dout3[8:6];
  end

   3'b100:
   begin
    dout4= mem[addr];
    mod34= dout4[2:0];
    mod54= dout4[5:3];
   mod74= dout4[8:6];
  end

  3'b101:
   begin
    dout5= mem[addr];
    mod35= dout5[2:0];
    mod55= dout5[5:3];
   mod75= dout5[8:6];
  end

  3'b110:
   begin
    dout6= mem[addr];
    mod36= dout6[2:0];
    mod56= dout6[5:3];
   mod76= dout6[8:6];
  end

  3'b111:
   begin
    dout7= mem[addr];
    mod37= dout7[2:0];
    mod57= dout7[5:3];
   mod77= dout7[8:6];
  end
  endcase

 if (count1==4'b1000)
 begin
  sum7=mod70+mod71+mod72+mod73+mod74+mod75+mod76+mod77;
  sum5=mod50+mod51+mod52+mod53+mod54+mod55+mod56+mod57;
  sum3=mod30+mod31+mod32+mod33+mod34+mod35+mod36+mod37;
  end

 end
 end


always@(posedge clk)
begin
 if (count==4'b1001)
  count1<=0;
 else count1<=count+1;
 end

always@(posedge clk)
begin
case (1'b1)
  a[0]: addr=3'd0;
  a[1]: addr=3'd1;
  a[2]: addr=3'd2;
  a[3]: addr=3'd3;
  a[4]: addr=3'd4;
  a[5]: addr=3'd5;
  a[6]: addr=3'd6;
  a[7]: addr=3'd7;
  default: addr=3'd0; // to avoid inferring a latch when W==8'd0
endcase
end
endmodule

1 个答案:

答案 0 :(得分:1)

always@(posedge clk)中使用非阻止分配(<=)。

您定义初始值的方式并不典型。

使用和initial阻止或重置。

initial begin
  dout0=9'd0;
  dout1=9'd0;
  dout2=9'd0;
  dout3=9'd0;
  dout4=9'd0;
  dout5=9'd0;
  dout6=9'd0;
  dout7=9'd0;
  mod30=3'd0;
  mod31=3'd0;
  mod32=3'd0;
  mod33=3'd0;
  mod34=3'd0;
  mod35=3'd0;
  mod36=3'd0;
  mod37=3'd0;
  ...
end

always@(posedge clk, negedge rst_n) begin
  if(~rst_n) begin
    dout0<=9'd0;
    //...
  end 
  else begin
    if (re && !we  ) begin
      case(addr)
        3'b000: begin
          dout0 <= mem[addr];
          {mod70, mod50, mod30} <= dout0; //1 cycle latency for this
        end
      endcase
  end
end
对你的mod来说dout会有1个时钟周期的延迟,不应该是组合查找吗?

always @* begin
   dout0 = mem[addr];
end