Может ли последовательный постоянный блок запускаться кратковременным импульсом, поступающим от комбинированного блока?
Я попытался запустить блок Always, назначив значение и вернув значение 0 в попытке запустить последовательный блок Always, но безрезультатно, ниже приведен псевдокод
always_comb begin
...some code...
pulse_trigger = 1;
load_var= driver_var // assigning some values
pulse_trigger = 0;
...some code...
end
always @(pulse_trigger)begin
...some code part 2...
end
Я ожидаю, что при назначении 1 для pulse_trigger активируется блок «always@(pulse_trigger)», но в моем моделировании VCS это не так.
Возможно, это связано с тем, что триггеру импульса присвоено значение 1 и не назначено значение 1 в одном и том же комбинированном блоке, что занимает 0 времени моделирования, поэтому может показаться, что значение pulse_trigger не изменилось. Или этот метод должен был запускать «всегда @ (pulse_trigger)» и выполнять «... часть кода 2 ..», потому что я смотрю на неправильные значения?
При моделировании Verilog одновременно может оцениваться только один блок always. Итак, пока ваш always_comb
не завершится, никакие другие блоки always не могут быть оценены. Следовательно, симуляция не обнаружит никаких изменений pulse_trigger
(поскольку все изменения происходят внутри одного всегда блока.
Вы можете сделать что-то подобное, добавив задержки (при условии, что это не синтезируемый код):
always @* begin
pulse_trigger = 1;
load_var= driver_var // assigning some values
#1 // << this will stop execution of the block for 1 time unit and allow others.
pulse_trigger = 0;
end
Однако приведенный выше код можно синтезировать с помощью нет, но он может быть частью тестового стенда.
Кроме того, это запрещено в always_comb
.
Добавление задержки блокировки в комбинационный блок означает, что вы можете пропустить изменения во входных данных.
Результат неопределенный. Стандарт SystemVerilog написан таким образом, что симуляторы могут свободно переключаться между независимыми процессами в любой момент. Но большинство ждет события или контроля времени, чтобы приостановить процесс, прежде чем перейти к другому.
Если вы хотите гарантировать триггер, используйте неблокирующее назначение во втором назначении для pulse_trigger
или используйте именованное событие.
always @* begin
pulse_trigger = 1;
load_var= driver_var // assigning some values
pulse_trigger <= 0; // adds a delta cycle or <= #1 delay without blocking the process
end
Еще лучше заменить второй блок always @
объявлением функции, а затем вызвать функцию вместо запуска события.
привет, дэйв, не могли бы вы немного расширить то, что вы подразумеваете под «использовать неблокирующее назначение во втором назначении для pulse_trigger или использовать именованное событие». Спасибо
Это вызовет надежный сбой в том же временном тике только в симуляции. Однако такое поведение нельзя синтезировать. И у вас могут возникнуть трудности с его отладкой, так как сбои не легко отображаются с помощью инструментов waiveform.
но стоит ли активировать
always@(pulse_trigger)
?