Обработка предполагаемых часов во время синтеза RTL

Я пытаюсь синтезировать дизайн на VHDL в FPGA ProASIC3 с помощью инструмента Synplify Pro. В сводном отчете содержится следующее предупреждение о предполагаемых часах.

@W:MT420 :  | Found inferred clock counter_unit| pstate_inferred_clock[1with period 10.00ns. Please declare a user-defined clock on object "n:bcu_ins.ctr_ins.pstate[1]"

Я проследил до части кода, где генерируется предупреждение, и то же самое воспроизводится здесь для справки.

p_fsm_clk : process(reset_n_in, clk_25mhz_in)
begin
    if (reset_n_in = '0') then
        pstate <= s0;
    elsif rising_edge(clk_25mhz_in) then
        pstate <= nstate;
    end if;
end process p_fsm_clk;

p_fsm : process(pstate,restart_ctr,enable_ctr2,sys_fail)
begin
    start_ctr1 <= '0';
    start_ctr2 <= '0';

    case pstate is
        when s0 =>
        --Reset state. All counters are reset
            if (sys_fail = '0' and restart_ctr = '1') then
                nstate <= s1;   --move to start counter1
            else
                nstate <= s0;
            end if;

        when s1 =>
            start_ctr1 <= '1';  --Initiate counter1
            if (restart_ctr = '1') then
            --restart the counters
                start_ctr1 <= '0';  --reset counter1
                nstate <= s1;
            elsif (enable_ctr2 = '1') then
            --move to start counter2
                nstate <= s2;
            else
                nstate <= s1;
            end if;

        when s2 =>
        --Save the counter1 value and start counter2
            start_ctr2 <= '1';  --assert flag to start counter2
            if (restart_ctr = '1') then
            --restart the counters
                nstate <= s1;
            else
                nstate <= s3;
            end if;

        when s3 =>
            start_ctr2 <= '1';
            if (sys_fail = '1') then
                nstate <= s0;
            elsif (restart_ctr = '1') then
            --restart the counters
                nstate <= s1;
            else
                nstate <= s3;
            end if;

        when others =>
            nstate <= s0;

    end case;
end process p_fsm;

--counter1
p_ctr1 : process(reset_n_in, clk_25mhz_in)
begin
    if (reset_n_in = '0') then
        ctr1 <= 0;  --value on reset
    elsif rising_edge(clk_25mhz_in) then
        if (start_ctr1 = '1') then
        --flag is asserted to start counter1
            ctr1 <= ctr1 + 1;   --increment counter
        else
        --flag de-asserted
            ctr1 <= 0;  --reset the counter
        end if;
    end if;
end process p_offset_cnt;

--save the value of counter1
offset_val <= ctr1 when pstate = s2;

Логика содержит два счетчика – ctr1и ctr2. Счетчики запускаются при отсутствии системных сбоев. На первом этапе ctr1запускается, за которым затем следует ctr2. ctr1перестает считать, когда ctr2включен. Значение ctr1определяет, насколько позже ctr2запускается (с точки зрения тактового периода 25 МГц), называемое смещением. Это значение смещения сохраняется в векторе сигнала, как видно из последней строки кода. Состояние s2используется для захвата значения ctr1до его сброса в 0.

offset_val <= ctr1 when pstate = s2;

Я понял, что этот оператор присваивания вызывает предполагаемые часы в дизайне (но не знаю, почему). Когда я помещаю тот же оператор в синхронизируемый процесс, предполагаемое предупреждение о часах исчезает. Однако моя логика работает неправильно.

Я ищу несколько разъяснений в этом отношении.

  1. Почему в этом дизайне есть предполагаемые часы на pstate[1]?
  2. Нормально ли иметь такие заявления в дизайне? Указывает ли наличие предполагаемых часов на плохую практику проектирования?
  3. Если недопустимо иметь предполагаемые часы в дизайне, как я могу это исправить, закодировав логику по-другому?
  4. Если можно выводить предполагаемые часы, как я могу сообщить об этом инструменту? Какое ограничение периода я могу предоставить для таких предполагаемых часов? Как я могу определить значимый период для таких предполагаемых часов?

Ответы (1)

Вы добавили FPGAтег, поэтому я отвечу с точки зрения FPGA. Если вы создаете ASIC или используете какой-либо другой поток, может применяться другой ответ.

1. Почему в этом дизайне включены предполагаемые часы pstate[1]?

offset_val <= ctr1 when pstate = s2;

Эта строка не описывает ничего, что происходит, когдаpstate нет . Это представляет собой закрытую защелку. В любой ПЛИС, которую я использовал, это будет реализовано путем активации режима «защелки» в обычном триггере с использованием контакта «часы» в качестве «ворота». Ваш сигнал затвора в этот момент использует тактовый ресурс, но в конечном итоге он получен из другого сигнала «данных», а не «настоящих» часов. s2

2. Можно ли иметь такие утверждения в дизайне? Указывает ли наличие предполагаемых часов на плохую практику проектирования?

Защелок в целом следует избегать, если только нет веских причин для их использования, потому что они обычно обеспечивают плохие временные характеристики и могут легко привести к опасностям и гонкам в конструкции. Одним из примеров, когда необходимо использовать защелки, может быть, если какой-то внешний интерфейс должен использовать какой-либо вход, чувствительный к уровню. В вашем случае похоже, что избежать защелки должно быть довольно легко.

3. Если недопустимо иметь предполагаемые часы в дизайне, как я могу исправить это, закодировав логику по-другому?

Используйте синхронизированный процесс, который содержит назначение. Это будет означать триггер для offset_val. Вам придется смоделировать свой проект или протестировать его на плате, чтобы убедиться, что функция эквивалентна в вашем конкретном случае, но основная философия в FPGA должна заключаться в том, что любое назначение, кроме простого, a <= b and c;или some_vec <= smaller_vec & another_bit;использует синхронизированный процесс. Это даст вам предсказуемые временные результаты и упростит написание ограничений. Есть исключения, но это должно быть отправной точкой.

4. Если выводить предполагаемые часы — это нормально, как я могу сообщить об этом инструменту? Какое ограничение периода я могу предоставить для таких предполагаемых часов? Как я могу определить значимый период для таких предполагаемых часов?

В случае внешнего интерфейса чувствительный к уровню вход будет иметь некоторую минимальную ширину импульса, и вы можете использовать это для создания ограничения периода, которое представляет собой наихудший возможный случай того, как этот сигнал может переключаться. Для любых внутренних интерфейсов я бы работал над тем, чтобы защелки вообще не существовали, но может применяться тот же метод. Избегая защелок вообще, вы избегаете необходимости думать о такого рода проблемах.


В дополнение к этому, конструкция конечного автомата с двумя процессами, показанная в вашем коде, не требуется. Вы можете поместить всю машину и переходы состояний в один тактовый процесс. Результирующий процесс будет очень похож на ваш второй процесс, описанный выше, со всем, что заключено в if (rising_edge(clk)) then, и каждое вхождение nstateзаменено на pstate. Вы должны быть в состоянии найти существующие ответы относительно дизайна конечного автомата либо здесь, в EE, либо в теге VHDL Stack Overflow .

+1. Конечный автомат единого процесса позволяет избежать многих потенциальных ловушек, а также является короче и проще. Стоит учиться.
Это было довольно информативно. Теперь мне ясно, что инструмент определил защелку для этого утверждения. Однако инструмент не генерировал для этого предупреждение о предполагаемой защелке. В отчете отображается только предупреждение о предполагаемых часах . Есть идеи, почему?
Вы это упомянули If you are creating an ASIC or using some other flow, a different answer might apply. Как будет отличаться синтез в случае ASIC? Не является ли здесь проблемой наличие предполагаемых защелок?
@rvkrysh Разные инструменты выдают разные предупреждения, и я никогда не использовал Synplify Pro, поэтому не знаю. Я упомянул, что может применяться другой ответ, потому что я знаю, что защелки могут использоваться вместо регистров в некоторых проектах как способ улучшить производительность в строго контролируемой части проекта, но у меня нет опыта работы с ASIC, поэтому Я оставил это как утверждение типа «может быть».