首页 > 解决方案 > 如何使同一个模块根据其实例化使用不同的包

问题描述

我有一个System Verilog在设计中多次实例化的模块。每个实例化都需要使用不同的包。实现这一点的最佳方法是什么?

  package A;
   parameter logic [15:0] array [0:15] = '{
   16'd1,
   16'd2,
   .
   .
   16'd16 
   }
  endpackage

  package B;
   parameter logic [15:0] array [0:7] = '{
   16'd1,
   16'd2,
   .
   .
   16'd8 
   }
  endpackage

   module test(

   );

    import packageA::*;

这就是我在模块的一个实例化中使用它的方式。但在第二次实例化中,我想使用packageB.

我应该使用:

  1. 如果定义?
  2. 如果可能的话,传递一个包名?或者
  3. 只是将它作为参数传递给模块?即使它是一个二维数组?

最好的方法是什么?

标签: verilogsystem-verilog

解决方案


系统 Verilog 语法不提供将包作为参数传递给任何东西的任何方式。可以使用会改变模块定义的宏。虽然这是可能的,但这是一种不好的做法,通常不推荐。最后我会举个例子。

处理它的唯一方法是参数化模块并在实例化时传递相应的数组,例如

package A;
parameter bit[3:0] data[4] = '{0,1,2,3};
endpackage

package B;
parameter bit[3:0] data[6] = '{5,4,3,2,1,0};
endpackage

module C#(int WDT = 1, bit [3:0] array [WDT] = '{0}) ();
  initial begin
    for (int i = 0; i < WDT; i++) 
      $display("%m: array[%0d] = %0d", i, array[i]);
  end
endmodule

module D();
  C #($size(A::data), A::data) c1();
  C #($size(B::data), B::data) c2();  
endmodule

还有其他版本的类型,即

package A;
typedef  bit[3:0] Array[4];
parameter Array array = {0,1,2,3};
endpackage

package B;
typedef  bit[3:0] Array[6] ;
parameter Array array = {5,4,3,2,1,0};
endpackage

typedef bit[3:0] DefaultArray[1];
module C#(type  X = DefaultArray, X array = {0}) ();
  initial begin
    for (int i = 0; i < $size(array); i++) 
      $display("%m array[%0d] = %0d", i, array[i]);
  end
endmodule

module D();
  D #(A::Array, A::array)d1();
  D #(B::Array, B::array)d2();
endmodule

对于宏,您可以在宏中定义整个模块。我觉得很丑

`define PMOD(NAME,PKG) module NAME (); ... import PKG""* ...
 ...
`PMOD(C1, A)
`PMOD(C2, B)

 ...
 C1 c1();
 C2 c2();

也可以使用ifdefs with包含。我不会推荐任何基于宏的方法,尤其是基于包含的方法。它们会产生可读性、可维护性、代码分析和调试问题。


推荐阅读