参数化功能错误

时间:2015-02-13 02:28:08

标签: verilog system-verilog hdl modelsim

我正在尝试编写以下systemverilog代码,其中不同的参数可以用于函数,因此只需更改参数而不是使用参数化模块就可以重用相同的函数。

我的以下代码编译时没有错误,但是当我尝试使用测试平台进行模拟时,它在Modelsim中给出错误211。我看到有人建议它与Modlesim的版本有关,所以我尝试了2个不同的版本,它给出了同样的错误。我认为它不是modelsim版本的问题,因为有些功能可以正常工作,但有些功能不行。

代码很简单,所以它应该可以工作。但是当第二个函数调用第一个函数时会发生错误。你能看到模拟失败的代码中或代码的任何其他部分有任何错误吗?

   /************This package is used in the module*************/

    package RealARITH;


    typedef struct {
        int  WIDTH_INT;
        int  WIDTH_FRAC;
        int SIG_TYPE;
        } FixP;


    /************1st parameterized function*************/

    virtual class resize_verilog 
   # (parameter Total_width_InB = 3, 
   parameter Total_width_InA = 4);

   static function [Total_width_InB-1:0] resize_verilog(input logic     [Total_width_InA-1:0] InA);

    logic [Total_width_InB-1:0] InB;

    InB = $signed(InA);
    if (Total_width_InA > Total_width_InB)
    InB[Total_width_InB-1] = InA[Total_width_InA-1];

   return InB;

   endfunction
   endclass

   /***************the 2nd parameterized function that uses the 1st function*/

   virtual class align_un
   # (
   parameter FixP InA_FixP = {2,3,1},
   parameter FixP InB_FixP = {2,3,1},
   parameter ExtraMSB = 0);

   static function [InB_FixP.WIDTH_INT+InB_FixP.WIDTH_FRAC+1:0]   RealALIGN_SIGNED(input logic    [InA_FixP.WIDTH_INT+InA_FixP.WIDTH_FRAC+InA_FixP.SIG_TYPE-1:0] InA);

   localparam Total_width_InA =     InA_FixP.WIDTH_INT+InA_FixP.WIDTH_FRAC+InA_FixP.SIG_TYPE;
   localparam Total_width_InB = InB_FixP.WIDTH_INT + InA_FixP.WIDTH_FRAC + 1;


   logic [Total_width_InB-1:0] InB;

   InB = resize_verilog #   (.Total_width_InA(Total_width_InA),.Total_width_InB(Total_width_InB))::resize_verilog(InA);  

   return InB;


   endfunction

endclass    

endpackage

/************module where the 2nd function  called from package********/

module test_align
import RealARITH::*; 
(
input logic [15:0] A,
output logic [18:0] B1);

parameter FixP InA = {5,10,1};
parameter FixP InB1 = {10,8,1};

assign B1 = align_un #(.InA_FixP(InA),.InB_FixP(InB1),.ExtraMSB(1))::RealALIGN_SIGNED(A);

endmodule 


/**************testbench***********************/

module test_align_tb;

logic [15:0] A;
logic [18:0] B1;

test_align DUT (.*);

initial 

begin

A = '0; 

# 10

A = 16'b0000000110000001;

end

endmodule 

/****************  Code ends here ***************************/

此处显示错误:

# Attempting stack trace sig 11
# Signal caught: signo [11]
# vsim_stacktrace.vstf written
# Current time Fri Feb 13 10:42:19 2015
# QuestaSim Stack Trace
# Program = vsim
# Id = "10.3"
# Version = "2014.01"
# Date = "Jan  6 2014"
# Platform = linux_x86_64
# 0    0x00007fefec1e40ca: '/home/sshahabu/Structure_test6_align_again/test.sv:49'
# 1    0x00000000007160a8: '<unknown (@0x7160a8)>'
# 2    0x0000000000716dd4: '<unknown (@0x716dd4)>'
# 3    0x00007fefec1e5cd6: '/home/sshahabu/Structure_test6_align_again/test.sv:17'
# 4    0x0000000000575364: '<unknown (@0x575364)>'
# 5    0x00007fefec1e48b4: '/home/sshahabu/Structure_test6_align_again/test.sv:49'
# 6    0x0000000000575364: '<unknown (@0x575364)>'
# 7    0x00007fefec1e76eb: '/home/sshahabu/Structure_test6_align_again/test.sv:71'
# 8    0x0000000000581a1c: '<unknown (@0x581a1c)>'
# 9    0x00000000006f0d07: '<unknown (@0x6f0d07)>'
# 10   0x00007fefec1e3b6e: '<unknown (@0x7fefec1e3b6e)>'
# 11   0x0000000000581a1c: '<unknown (@0x581a1c)>'
# 12   0x00000000006f0d07: '<unknown (@0x6f0d07)>'
# 13   0x00000000006f0f8c: '<unknown (@0x6f0f8c)>'
# 14   0x00000000006f11c9: '<unknown (@0x6f11c9)>'
# 15   0x00000000006f1f0e: '<unknown (@0x6f1f0e)>'
# 16   0x000000000074ff98: '<unknown (@0x74ff98)>'
# 17   0x0000000000751207: '<unknown (@0x751207)>'
# 18   0x0000000000aba60d: '<unknown (@0xaba60d)>'
# 19   0x00000000013c3a1f: '<unknown (@0x13c3a1f)>'
# 20   0x00000000013c4bd9: '<unknown (@0x13c4bd9)>'
# 21   0x000000000140739a: '<unknown (@0x140739a)>'
# 22   0x000000000140fecf: '<unknown (@0x140fecf)>'
# 23   0x00000000013c5ef3: '<unknown (@0x13c5ef3)>'
# 24   0x00000000013d0d84: '<unknown (@0x13d0d84)>'
# 25   0x00000000013c4bd9: '<unknown (@0x13c4bd9)>'
# 26   0x000000000140739a: '<unknown (@0x140739a)>'
# 27   0x00000000014101f0: '<unknown (@0x14101f0)>'
# 28   0x00000000013c35c3: '<unknown (@0x13c35c3)>'
# 29   0x00000000013d6088: '<unknown (@0x13d6088)>'
# 30   0x00000000013c4bd9: '<unknown (@0x13c4bd9)>'
# 31   0x00000000013c5826: '<unknown (@0x13c5826)>'
# 32   0x00000000013c5ba6: '<unknown (@0x13c5ba6)>'
# 33   0x0000000001102c3c: '<unknown (@0x1102c3c)>'
# 34   0x0000000001420bf1: '<unknown (@0x1420bf1)>'
# 35   0x0000000001469f81: '<unknown (@0x1469f81)>'
# 36   0x00000000014366ad: '<unknown (@0x14366ad)>'
# 37   0x00000000014369e5: '<unknown (@0x14369e5)>'
# 38   0x00000000012e02b6: '<unknown (@0x12e02b6)>'
# 39   0x000000000089c9cb: '<unknown (@0x89c9cb)>'
# End of Stack Trace


** Fatal: (SIGSEGV) Bad pointer access. Closing vsimk.
** Fatal: vsimk is exiting with code 211.
(Exit codes are defined in the QuestaSim messages appendix
of the QuestaSim User's Manual.)

第17行代码:

virtual class resize_verilog 
# (parameter Total_width_InB = 3, 
parameter Total_width_InA = 4);

第49行代码:

 InB = resize_verilog # (.Total_width_InA(Total_width_InA),.Total_width_InB(Total_width_InB))::resize_verilog(InA);

第71行:

assign B1 = align_un #(.InA_FixP(InA),.InB_FixP(InB1),.ExtraMSB(1))::RealALIGN_SIGNED(A);

1 个答案:

答案 0 :(得分:0)

问题在于您定义localparam的位置。任务和函数中不允许使用参数定义,请参阅IEEE Std 1800-2012§13.3任务和§13.4函数。这应该是一个编译错误。

将定义移到函数定义之上,运行时崩溃将消失。这也允许您在函数定义中使用localparam标识符。

其他注意事项:在使用结构文字和数组文字进行分配时,会重新使用'{}而不是{}。请参阅IEEE Std 1800-2012§5.10结构文字和§5.11数组文字

virtual class align_un
  #(
  parameter FixP InA_FixP = '{2,3,1},
  parameter FixP InB_FixP = '{2,3,1},
  parameter ExtraMSB = 0);

localparam Total_width_InA = InA_FixP.WIDTH_INT+InA_FixP.WIDTH_FRAC+InA_FixP.SIG_TYPE;
localparam Total_width_InB = InB_FixP.WIDTH_INT + InA_FixP.WIDTH_FRAC + 1;

  static function logic [Total_width_InB-1:0]  RealALIGN_SIGNED(
      input logic [Total_width_InA-1:0]  InA);
    logic [Total_width_InB-1:0] InB;
    InB = resize_verilog#(
      .Total_width_InA(Total_width_InA),
      .Total_width_InB(Total_width_InB)
      )::resize_verilog(InA);
    return InB;
  endfunction : RealALIGN_SIGNED
endclass : align_un