如何强制信号,使释放后值改变?

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

出于测试目的,我使用 VHDL 功能

force

这会改变信号的当前值。 但是,更改仅在应用

force
时持续,除非通常控制信号的进程进行分配。

有什么方法可以使

force
应用于保存的信号,从而也适用于
release
之后?

波形示例如下所示,其中设计每 1 us 刻度更新一次 alpha_value。

在 0.5 us 处,它表明 alpha_value 变化在

release
之后从 13 回到 0。在 2.5 us 时,表明内部 alpha_value 在 2.0 us 时变为 42,因此 alpha_value 在
release
时恢复为 42。

示例代码为:

entity tb is
end entity;

architecture sim of tb is

  signal alpha_value  : natural;
  signal alpha_update : natural;  -- Increments at each update of alpha_value
  signal alpha_force  : boolean;  -- Shows when force to alpha_value is applied

begin

  -- Update process
  process is
  begin
    while true loop
      wait for 1.0 us;
      alpha_value  <= alpha_value + 1;
      alpha_update <= alpha_update + 1;
    end loop;
  end process;

  -- Force process
  process is
  begin
    -- Force between increment
    wait for 0.3 us;
    alpha_value <= force 13;  -- From 1 to 2 us
    alpha_force <= true;
    wait for 0.2 us;
    alpha_value <= release;
    alpha_force <= false;
    -- Force over increment
    wait for 1.0 us;
    alpha_value <= force 41;  -- From 5 to 7 us
    alpha_force <= true;
    wait for 1.0 us;
    alpha_value <= release;
    alpha_force <= false;
    wait;
  end process;

end architecture;
vhdl
1个回答
-1
投票

在你提供赏金以查看所涉及的内容之前,我已经实现了拉尔的评论方法:

第二:在您的示例代码中,由于没有目标,因此无法强制输入计数器。如果您将计数器拆分为组合信号

alpha_input <= alpha_value + 1
和分配计数器
alpha_value <= alpha_input
的时钟进程,您将能够通过在
alpha_input
上施加力来强制计数器的输入。您仍然需要正确计算施加力的时间,但您会将施加的值存储在计数器中。 – 拉尔 9 小时前

请注意,此处测试的抽象设计是由等待语句超时子句到期驱动的,就像“强制过程”一样。

architecture two_signals of tb is

    signal alpha_value:     natural;
    signal alpha_update:    natural;
    signal alpha_force:     boolean;
    signal alpha_val_in:    natural;  -- CHANGED ADDED

begin

VAL_INPUT:                               -- CHANGED ADDED 
    process (alpha_value)                -- there's a concurrent assignment
    begin                                -- statement equivalent
        alpha_val_in <= alpha_value + 1;
    end process;
    
COUNTERS_UPDATE:
    process
    begin
        while true loop
            wait for 1.0 us;
            -- alpha_value  <= alpha_value + 1;
            alpha_value <= alpha_val_in;
            alpha_update <= alpha_update + 1;
        end loop;
    end process;

FORCE_PROCESS:   -- Force process
    process is
    begin
        -- Force between increment
        wait for 0.3 us;
        alpha_value <= force 13;  -- From 1 to 2 us
        alpha_force <= true;
        wait for 0.7 us;          -- CHANGED WAS wait for 0.2 us
        alpha_value <= release;
        alpha_force <= false;
        -- Force over increment
        wait for 1.0 us;
        alpha_value <= force 41;  -- From 5 to 7 us
        alpha_force <= true;
        wait for 1.0 us;
        alpha_value <= release;
        alpha_force <= false;
        wait;
    end process;
end architecture;

您可以看到,您只是要求强制对于超时子句驱动的 alpha_value 计数器增量有效,与以下强制 41 相同:

那么如何才能在任意时间强制并保持强制值呢?

不要通过超时子句到期来驱动计数器,而是通过信号事件来驱动它们。如果我们将新事件注入到 alpha_value 计数器操作中,这可能需要单独的信号用于 alpha_value 和 alpha_update 计数器增量:

architecture event_driven of tb is

    signal alpha_value:     natural;
    signal alpha_update:    natural;
    signal alpha_force:     boolean;
    signal alpha_val_in:    natural;
    signal countv:          boolean;
    signal countu:          boolean;
begin

VAL_INPUT:
    process (alpha_value)
    begin
        alpha_val_in <= alpha_value + 1; 
    end process;

COUNTERS_EVENTS:
    process
    begin
        wait for 1 us;
        countv <= TRUE, FALSE after 500 ns;
        countu <= TRUE, FALSE after 500 ns;
    end process;
COUNT_UPDATE:
    process
    begin
        wait until rising_edge(countu);
        alpha_update <= alpha_update + 1;
    end process;

COUNT_VALUE:
    process
    begin
       --  while true loop  -- CHANGED while loop redundant
            -- wait for 1.0 us;
            -- alpha_value  <= alpha_value + 1;
        wait until rising_edge(countv);
        alpha_value <= alpha_val_in;
            -- alpha_update <= alpha_update + 1;
       -- end loop;
    end process;

FORCE_PROCESS:   -- Force process
  process is
  begin
    -- Force between increment
    wait for 0.3 us;
    alpha_val_in <= force 13;  -- From 1 to 2 us
    alpha_force <= true;
    countv <= force FALSE;     -- CHANGED ADDED force event
    wait for 50 ns;
    countv <= force  TRUE;
    wait for 50 ns;
    countv <= release;
    wait for 0.1 us;  -- CHANGED WAS 0.2 us;
    alpha_val_in <= release;
    alpha_force <= false;
    -- Force over increment
    wait for 1.0 us;
    alpha_val_in <= force 41;  -- From 5 to 7 us
    alpha_force <= true;
    wait for 1.0 us;
    alpha_val_in <= release;
    alpha_force <= false;
    wait;
  end process;

end architecture;

允许在 alpha_value 上发生独立事件:

进一步的改进可能包括使用来自被测设备的外部信号事件来对力过程中的刺激进行排序。

这是使用最近的 ghdl 提交夜间构建支持强制和发布来完成的,并且需要 IEEE Std 1076-2008 功能(ghdl 命令行选项 --std=08)。

我还没有尝试将 tb 设计规范分离为单独的设计单元,并使用据称需要 ghdl 的 mcode 版本的外部信号名称。如果外部名称得到充分支持,但超出了您的问题范围,同时作为您的赏金的附加标准,它应该可以工作。

因此 ghdl 的 mcode 版本将打算支持外部名称:

entity device_under_test is
end entity;

architecture external_names of device_under_test is
    signal alpha_value:     natural;
    signal alpha_update:    natural;
    signal alpha_val_in:    natural;
    signal countv:          boolean;
    signal countu:          boolean;
begin
VAL_INPUT:
    process (alpha_value)
    begin
        alpha_val_in <= alpha_value + 1;
    end process;

COUNTERS_EVENTS: 
    process
    begin
        wait for 1 us;
        countv <= TRUE, FALSE after 500 ns;
        countu <= TRUE, FALSE after 500 ns;
    end process;
COUNT_UPDATE:
    process
    begin
        wait until rising_edge(countu);
        alpha_update <= alpha_update + 1;
    end process;

COUNT_VALUE:
    process
    begin
        wait until rising_edge(countv);
        alpha_value <= alpha_val_in;
    end process;
    
end architecture;

architecture external_names of tb is
    signal alpha_force:     boolean;
begin
DUT:
    entity work.device_under_test;
    
FORCE_PROCESS:   -- Force process
  process
      alias alpha_value is <<signal .tb.dut.alpha_value: natural>>;
      alias alpha_val_in is <<signal .tb.dut.alpha_val_in: natural>>;
      alias countv is <<signal .tb.dut.countv: boolean>>;
  begin
    -- Force between increment
    wait for 0.3 us;
    alpha_val_in <= force 13;  -- From 1 to 2 us
    alpha_force <= true;
    countv <= force FALSE;  -- CHANGED, ADDED Force
    wait for 50 ns;
    countv <= force  TRUE;
    wait for 50 ns;
    countv <= release;
    wait for 0.1 us;  -- CHANGED WAS 0.2 us;
    alpha_val_in <= release;
    alpha_force <= false;
    -- Force over increment
    wait for 1.0 us;
    alpha_val_in <= force 41;  -- From 5 to 7 us
    alpha_force <= true;
    wait for 1.0 us;
    alpha_val_in <= release;
    alpha_force <= false;
    wait;
  end process;

end architecture;

这产生了相同的结果:

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