如何将 modport 接口连接到最初未使用 modport 声明的模块

问题描述 投票:0回答:2

我有一个模块,我最初是这样写的:

module design_name #(
  parameter AWIDTH = 32,
  parameter DWIDTH = 32,
  ...
  ) (
  input wire clk,
  input wire rst,
  input wire [AWIDTH-1:0] write_addr,
  ...
);
// logic, etc.
endmodule

我现在当然想在测试台上测试这个块。我想使用一个界面,所以我创建了一个这样的界面:

interface design_name_if #(
  parameter AWIDTH = 32,
  ...
) (
  input clk
);
  logic rst;
  logic [AWIDTH-1:0] write_addr;
  ...
  
  modport des (
    input rst,
    input write_addr,
    ...
  );
endinterface
  

我想我的问题现在开始了;我如何在我的测试台上使用这个接口?我目前有:

module tb;

  reg clk;

  design_name_if intf (clk);

  design_name dut (
    .clk        (intf.clk),
    .rst        (intf.des.rst),
    .write_addr (intf.des.write_addr),
    ...
// I don't think the above is correct

  initial begin
    clk = 0; // or intf.clk = 0; ?
    forever #1 clk = ~clk;
  end

  initial begin
    rst = 0;
    #10
    rst = 1;
  end

endmodule

我还尝试了一些其他简单的逻辑,比如只是尝试断言某些信号和其他东西,但我什至无法启动 clk,也无法在运行模拟时首先断言。如果重要,接口在同一文件中的 tb 上方声明。我正在测试的模块很可能在不同的文件中。通过在测试台内将所有信号声明为 reg 和 wire,我可以让测试台在没有接口的情况下正常工作,但我想使用带有任务、功能等的接口。感谢任何帮助,谢谢!

verilog system-verilog fpga hdl vivado
2个回答
0
投票

你们非常亲密。只需去掉引用中的 modport——

modport
不是作用域,它是端口连接或虚拟接口引用的一组访问权限。

 design_name dut (
    .clk        (intf.clk),
    .rst        (intf.rst),
    .write_addr (intf.write_addr),
    ...

0
投票

有几个问题:

  1. 从结构上看,一个接口就是一堆电线。 wire intf.clk 不同于 wire clk。发布的代码使用永久循环驱动 clk,但测试台将 intf.clk 连接到未驱动的 dut,因此 dut 将看不到任何时钟(驱动 dut clk 输入引脚的电线没有驱动程序)。这种模式也首先出现在信号/电线/变量上。

  2. 在测试平台中声明

永远 #1 clk = ~clk;

初始块中间的语句。这将阻止执行同一初始块中的所有其他语句。例如,它永远不会执行 #10 或 rst = 1 语句。解决方案是使用不同的初始块或始终块来驱动时钟(无论您选择使用接口或本地声明的时钟)。

  1. 在初始刺激块结束时没有 $finish 来停止测试。该测试台将在无限循环中运行模拟器。初始块需要模板:

    initial
     begin
     <statements>
     $finish;
     end
    

这样测试就不会让模拟器陷入循环。

© www.soinside.com 2019 - 2024. All rights reserved.