Verilog:连接模块端口而不实例化新线路

时间:2013-02-03 13:27:58

标签: module verilog system-verilog

有没有办法在不实例化新线的情况下连接两个模块端口?

小例子:

module comparator(max,min,in0,in1);

    input[7:0] in0,in1;
    output[7:0] max,min;

    wire[7:0] in0;
    wire[7:0] in1;
    wire[7:0] max;
    wire[7:0] min;

    assign max = (in0>in1) ? in0 : in1;
    assign min = (in0<in1) ? in0 : in1;

endmodule

我想在不使用新线的情况下连接2个比较器模块,是否存在某种隐式连接?我真的需要一种方法来做这样的事情来做这个网: enter image description here

模块之间有很多线路。

2 个答案:

答案 0 :(得分:1)

IEEE Std(1364-2001)引入了generate构造,允许将多个实例连接在一起。

IEEE Std(1800-2005)引入了“点星”(.*)语法,也称为隐式端口连接,以减少布线。如果您使用的是现代工具,则应支持此SystemVerilog语法。

答案 1 :(得分:1)

我猜你想要一个模块以类似于你的图表的方式多次实例化模块comparator。您需要一个数组(我的解决方案中的二维)是由参数控制的宽度,以获得最佳灵活性。在generate块中,使用for-loopsif-else语句建立连接。我的解决方案使用数组的切片,例如+:

这符合IEEE Std(1800-2009),IEEE Std(1800-2005)也应如此。

module comparator_list #(parameter int SIZE=10) (input logic [7:0] in [SIZE-1:0], output logic [7:0] out [SIZE-1:0]);
    generate
        if (SIZE==1) begin : pass_through
            always_comb out = in;
        end : pass_through
        else if (SIZE==2) begin : simple
            comparator c0 ( .max(out[0]), .min(out[1]), .in0(in[0]), .in1(in[1]) );
        end : simple
        else if (SIZE%2==1) begin : odd_list
            logic [7:0] in_buf [SIZE:0];
            logic [7:0] out_buf [SIZE:0];
            always_comb begin : link_in
                foreach(in[idx]) in_buf[idx] = in[idx];
                in_buf[SIZE] = 8'h00; // force last entry to 'h0 if unasigned, 'h80 if signed
            end : link_in
            always_comb begin : link_out
                foreach(out[idx]) out[idx] = out_buf[idx];
                // Note: out_buf[SIZE] is don't care
            end : link_out
            comparator_list #(SIZE+1) cl (.in(in_buf), .out(out_buf));
        end : odd_list
        else begin : even_list
            logic [(SIZE/2)*8-1:0] top [SIZE+1];
            logic [(SIZE/2)*8-1:0] bot [SIZE+1];

            for(genvar idx=0; idx<SIZE/2; idx+=1) begin : map
                always_comb {top[0][idx*8+:8],bot[0][idx*8+:8]} = {in[2*idx],in[2*idx+1]};
                always_comb {out[2*idx],out[2*idx+1]} = {top[SIZE][idx*8+:8],bot[SIZE][idx*8+:8]};
            end : map

            for(genvar stage=0; stage<SIZE; stage++) begin : link
                if(stage%2==0) begin : even
                    comparator c0[SIZE/2-1:0] (
                        .max(top[stage+1][0+:(SIZE/2)*8]), .in0(top[stage][0+:(SIZE/2)*8]),
                        .min(bot[stage+1][0+:(SIZE/2)*8]), .in1(bot[stage][0+:(SIZE/2)*8]) );
                end : even
                else begin : odd
                    assign top[stage+1][7:0] = top[stage][7:0];
                    comparator c1[SIZE/2-2:0] (
                        .max(bot[stage+1][0+:(SIZE/2-1)*8]),
                        .min(top[stage+1][8+:(SIZE/2-1)*8]),
                        .in0(bot[stage][0+:(SIZE/2-1)*8]),
                        .in1(top[stage][8+:(SIZE/2-1)*8])
                    );
                    assign bot[stage+1][(SIZE/2-1)*8+:8] = bot[stage][(SIZE/2-1)*8+:8];
                end : odd
            end : link
        end : even_list
    endgenerate
endmodule : comparator_list