Verilog中的FFT实现:将线路输入分配给寄存器类型阵列

时间:2014-05-20 07:34:02

标签: fft verilog

我正在尝试在verilog中实现蝶形FFT算法。 DIT Butterfly Network

我创建K(此处为4)蝴蝶模块。我创建这样的模块。

localparam K = 4;
genvar     i;
generate 
for(i=0;i<N/2;i=i+1)
begin:BN
    butterfly #(
    .M_WDTH   (3 + 2*1),
    .X_WDTH   (4)
    )
    bf (
    .clk(clk), 
    .rst_n(rst_n), 
    .m_in(min), 
    .w(w[i]), 
    .xa(IN[i]), 
    .xb(IN[i+2]), 
    .x_nd(x_ndd), 
    .m_out(mout[i]), 
    .ya(OUT[i]),
    .yb(OUT[i+2]),
    .y_nd(y_nddd[i])
);
end

每个级别我必须为每个模块更改输入Xa和Xb(此处为第3级)。

所以我尝试初始化reg类型“IN”数组并将数组分配给输入Xa和Xb。当我手动初始化“IN”数组时,它可以很好地工作。

我现在面临的问题是,我无法将主模块输入X分配给寄存器类型“IN”数组。 主模块输入X,

input wire signed [N*2*X_WDTH-1:0] X,

我必须将此X分配到数组“IN”,

reg signed  [2*X_WDTH-1:0] IN [0:N-1];

我是这样分配的,

initial
begin

IN[0]= X[2*X_WDTH-1:0];
IN[1]=X[4*X_WDTH-1:2*X_WDTH];
IN[2]=X[6*X_WDTH-1:4*X_WDTH];
IN[3]= X[8*X_WDTH-1:6*X_WDTH];
IN[4]= X[10*X_WDTH-1:8*X_WDTH];
IN[5]=X[12*X_WDTH-1:10*X_WDTH];
IN[6]=X[14*X_WDTH-12*X_WDTH];
IN[7]= X[16*X_WDTH-1:14*X_WDTH];

end

我经历了很多教程和论坛。没有运气。

我们不能将线型分配给reg类型数组吗?如果是这样我怎么能解决这个问题。

这是我初始化Butterfly模块的主模块

module Network
#(
// N
parameter N = 8,
// K.
parameter K = 3,
 parameter M_WDTH=5,
 parameter X_WDTH=4

)
(
input wire                        clk,
input wire                        rst_n,

// X
input wire signed [N*2*X_WDTH-1:0] X,
//Y
output wire signed  [N*2*X_WDTH-1:0] Y,

output wire signed [K-1:0] y_ndd
);


wire   y_nddd    [K-1:0];
assign y_ndd ={y_nddd[1],y_nddd[0]};


reg [4:0] min=5'sb11111;
wire [4:0] mout [0:K-1];


reg   x_ndd;
reg [2:0] count=3'b100;

reg   [2*X_WDTH-1:0] w [K-1:0];
reg [2*X_WDTH-1:0] IN [0:N-1];
wire [2*X_WDTH-1:0] OUT [0:N-1];

assign Y = {OUT[3],OUT[2],OUT[1],OUT[0]};

reg [3:0] a;

initial
begin

//TODO : Here is the problem. Assigning Wire to reg array. Synthesize ok. In Simulate "red" output.
IN[0]= X[2*X_WDTH-1:0];
IN[1]=X[4*X_WDTH-1:2*X_WDTH];
IN[2]=X[6*X_WDTH-1:4*X_WDTH];
IN[3]= X[8*X_WDTH-1:6*X_WDTH];
IN[4]= X[10*X_WDTH-1:8*X_WDTH];
IN[5]=X[12*X_WDTH-1:10*X_WDTH];
IN[6]=X[14*X_WDTH-12*X_WDTH];
IN[7]= X[16*X_WDTH-1:14*X_WDTH];

//TODO :This is only a random values
w[0]=8'sb01000100;
w[1]=8'sb01000100;
w[2]=8'sb01000100;
w[3]=8'sb01000100;

end


/* levels */
genvar i;

generate 
for(i=0;i<N/2;i=i+1)
begin:BN
    butterfly #(
    .M_WDTH   (3 + 2*1),
    .X_WDTH   (4)
    )
    bf (
    .clk(clk), 
    .rst_n(rst_n), 
    .m_in(min), 
    .w(w[i]), 
    .xa(IN[i]), 
    .xb(IN[i+N/2]), 
    .x_nd(x_ndd), 
    .m_out(mout[i]), 
    .ya(OUT[2*i]),
    .yb(OUT[2*i+1]),
    .y_nd(y_nddd[i])
);
end

endgenerate


always @ (posedge clk)
begin
    if (count==3'b100)
    begin
        count=3'b001;
        x_ndd=1;
    end

    else
    begin
        count=count+1;
        x_ndd=0;
    end     
end



always@ (posedge y_ndd[0])
begin
    //TODO 
    //Here I have to swap OUT-->IN
end



endmodule

感谢任何帮助。 提前谢谢。

1 个答案:

答案 0 :(得分:4)

&#34;输出为红色&#34;,这可能意味着x这可能是由于多个驱动程序或未初始化的值。如果它是未驱动的,则为z

我认为主要问题是你这样做:

initial begin
  IN[0] = X[2*X_WDTH-1:0];
  IN[1] = X[4*X_WDTH-1:2*X_WDTH];
  ...

重要的部分是initial这只在时间0评估一次。通常一切都是零时的x。为了使这相当于线路使用assign IN[0] = ...的{​​{1}},这是一个组合块,当X发生变化时,它将更新IN的值。

always @* begin

我不确定您为什么不直接将X连接到您的蝴蝶always @* begin IN[0] = X[2*X_WDTH-1:0]; IN[1] = X[4*X_WDTH-1:2*X_WDTH]; ... .xa端口?

其他指示
.xb是一个错误的变量名称verilog,因为wire或reg可以包含四个值1,0,x或z。

X中,您应该使用非阻塞(always @(posedge clk))分配来正确建模触发器的行为。

<=是k位宽,但只分配了前2位。

y_ndd

分配应该是参数宽度/大小。例如output signed [K-1:0] y_ndd assign y_ndd = {y_nddd[1],y_nddd[0]}; IN个条目,但目前只分配了8个条目。 N时会出现问题。看看Indexing vectors and arrays with +:。例如:

N!=8