2017-02-08 2 views
0

При тестировании простой реализации счетчика симуляция GHDL не выходит из моделирования. Мое намерение состоит в том, чтобы остановить одновременные процессы с использованием общей переменной, измененной основным процессом. Но основной процесс не останавливает процесс синхронизации.Остановка моделирования VHDL с заявлениями ожидания

Моя реализация счетчика:

entity dff is 
port(
    direction, reset, clk, load : in std_logic; 
    din : in std_logic_vector(3 downto 0); 
    dout : out std_logic_vector(3 downto 0)); 
end dff; 

architecture behav of dff is 
    signal temp : std_logic_vector(3 downto 0); 
begin 
    process(clk, reset) 
begin 
    if (reset='1') then 
     temp <= "0000"; 
     elsif rising_edge(clk) then 
      if (load='1') then 
       temp <= din; 
      else 
       if (direction='0') then 
        temp <= std_logic_vector(unsigned(temp) + 1); 
       else 
        temp <= std_logic_vector(unsigned(temp) - 1); 
       end if; 
      end if; 
     end if; 
     dout <= temp; 
    end process; 
end behav; 

И мой испытательный стенд:

architecture behav of test_tb is 
    component dff port(
     direction, reset, clk, load : in std_logic; 
     din : in std_logic_vector(3 downto 0); 
     dout : out std_logic_vector(3 downto 0)); 
    end component; 
    signal direction, reset, clk, load : std_logic := '1'; 
    signal din, dout : std_logic_vector(3 downto 0) := x"7"; 
    shared variable simend : boolean := false; 
begin 

    clkk : process 
    begin 
     if simend=false then 
      clk <= not clk after 50 ns; 
     else 
      wait; 
     end if; 
    end process clkk; 

    uut : dff port map(
     direction, reset, clk, load, din, dout); 

    stim : process 
    begin 
     reset <= '0'; 
     wait for 1 us; 
     load <= '0'; 
     wait for 2 us; 
     direction <= '0'; 
     wait for 2 us; 
     load <= '1'; 
     wait for 1 us; 
     reset <= '1'; 
     wait for 0.5 us; 

     simend := true; 
     wait; 
    end process stim; 
end behav; 
+0

В последних выпусках ghdl вы можете использовать комбинацию [--assert-level = ] (http://ghdl.readthedocs.io/en/latest/Simulation_and_runtime.html?highlight=severity) и --ieee- asserts = блокирует предупреждения из стандартных пакетов, чтобы разрешить говорить в SEVERITY_LEVEL HALT в утверждении. Вы также можете отделить задержку от назначения 'wait 50 ns; clk <= not clk; если simend = true, тогда подождите; end if; 'Операторы процесса естественно замкнуты. – user1155120

+0

Я бы рекомендовал избежать накладных расходов на убийцу часов и вместо этого использовать std.env.stop, как было предложено @scary_jeff. –

ответ

0

Я бы закодировать свой тактовый генератор больше, как это:

clkk : process 
begin 
    while simend=false loop 
     clk <= not clk; 
     wait for 50 ns; 
    end loop; 
    wait; 
end process clkk; 

Можно выполнить ваш clkk процесс без выполнения инструкции wait. (Строка clk <= not clk after 50 ns не ждет или не блокируется - <= является неблокирующим назначением.) Поэтому у вас есть бесконечный цикл, который никогда не остановится. Вы можете увидеть это, запустив this example on EDA Playground, где время моделирования никогда не продвигается и, поскольку максимальное время работы на EDA Playground составляет 1 минуту, время истекает через 1 минуту.

Кроме того, я бы рекомендовал не использовать общую переменную для simend. Вместо этого, почему бы не использовать сигнал? Вы не сможете даже скомпилировать код в VHDL-2000, потому что после VHDL-2000 общие переменные должны были быть защищенных типов. Вы можете видеть, что на EDA Playground появляется предупреждение, если вы не установите параметр для компиляции VHDL-93. Компиляция для VHDL-93 предотвратит использование процедур stop (или finish).

1

Альтернативный способ закончить моделирование, если у вас есть VHDL2008-совместимый Тренажер для:

use std.env.stop; 

вы можете закончить моделирование с помощью вызова stop:

stop; 

Это мне кажется чтобы быть более элегантным, чем ждать отсутствия тактовых переходов, чтобы достичь предела итерации симулятора.

+0

В недавнем ghdl это означает компиляцию и разработку с помощью флага '--std = 08'. –

1

Я согласен с @scary_jeff, std.env.stop - отличный ответ здесь. Если я просто звоню в одном месте, я предпочитаю, чтобы оставить от ссылки пакета и назвать его просто:

std.env.stop; 

В случае, если вы застряли со старым тренажере, вы можете использовать

report "Just Kidding. Test Done." severity failure ; 

OTOH, если вам нужно согласовать завершение моделирования между несколькими процессами и добавить таймер сторожевой собаки к вашему прогону моделирования, вы можете рассмотреть процедуру Osvvm.TbUtilPkg.WaitForBarrier. Он используется, как показано ниже. Первый вызов WaitForBarrier (TestDone, 5 мс) просыпается через 5 мс в случае, если TestDone не произойдет до этого и прекратит симуляцию в это время.

signal TestDone : integer_barrier := 1 ; 

ControlProc : process 
begin 
    -- initialize test 
    SetAlertLogName("Uart1_Rx") ; 
    . . . 
    WaitForBarrier(TestDone, 5 ms) ; -- control process uses timeout 
    AlertIf(now >= 5 ms, "Test finished due to Time Out") ; 
    ReportAlerts ; 
    std.env.stop ; 
end process ControlProc ; 

CpuProc : process 
begin 
    InitDut(. . .)_; 
    Toggle(CpuReady) ; 
    -- run numerous Cpu test transactions 
    . . . 
    WaitForBarrier(TestDone) ; 
    wait ; 
end process CpuProc ; 

UartTxProc : process 
Begin 
    WaitForToggle(CpuReady) ; 
    -- run numerous Uart Transmit test transactions 
    . . . 
    WaitForBarrier(TestDone) ; 
    wait ; 
end process UartTxProc ; 
. . . 

Вы можете найти библиотеку OSVVM как на osvvm.org, так и на github. Существует также полное руководство пользователя для этого пакета при загрузке.

Смежные вопросы