Итак, в моем последнем школьном проекте мне пришлось реализовать в VHDL алгоритм, который вычислял комплексное среднее значений различных наборов значений.vhdl fsm counter conditions
Нам пришлось использовать FSM с внешними счетчиками для управления адресами памяти и управления изменениями состояния. Итак, когда я закончил набор, я хотел перейти из состояния 3 в состояние 4, состояние 4 в состояние 5 и состояние 5 в init. Это делается с использованием сигнала под названием Олин (для счетчика memIn) и OlOut (для счетчика memOut)
entity control is
Port (clk : in STD_LOGIC;
rst : in STD_LOGIC;
finish: out STD_LOGIC;
op1, op2 : out STD_LOGIC;
muxes : out STD_LOGIC_VECTOR (3 downto 0);
enables : out STD_LOGIC_VECTOR (2 downto 0);
cenO, cenI : out STD_LOGIC;
olIn, olOut : in STD_LOGIC;
we: out STD_LOGIC);
end control;
architecture Behavioral of control is
type fsm_states is (s_init, load, cycle1, cycle2, cycle3, cycle4, cycle5, done);
signal next_state, state: fsm_states;
signal sfinish: STD_LOGIC;
begin
state_reg : process(clk,rst)
begin
if (clk'event and clk='1') then
if(rst = '1') then
state <= s_init;
else
state <= next_state;
end if;
end if;
end process;
state_comb: process(state,sfinish, olIn, olOut)
begin
next_state <= state;
case state is
when s_init =>
next_state <= load;
when load =>
next_state <= cycle1;
when cycle1 =>
next_state <= cycle2;
when cycle2 =>
next_state <= cycle3;
when cycle3 =>
next_state <= cycle4;
when cycle4 =>
if(olIn='1') then
next_state <= cycle5;
else
next_state <= cycle1;
end if;
when cycle5 =>
if(olOut='1') then
next_state <= done;
else
next_state <= s_init;
end if;
when done =>
next_state <= done;
end case;
end process;
process (state,olIn)
begin
case state is
when s_init =>
cenI <= '1';
cenO <= '0';
muxes <= "XXXX";
enables <= "X11";
op1 <= 'X';
op2 <= 'X';
sfinish <= '0';
we <= '0';
when load =>
cenI <= '0';
cenO <= '0';
muxes <= "XXX0";
enables <= "110";
op1 <= 'X';
op2 <= 'X';
sfinish <= '0';
we <= '0';
when cycle1 =>
cenI <= '0';
cenO <= '0';
muxes <= "0001";
enables <= "110";
op1 <= '0';
op2 <= '0';
sfinish <= '0';
we <= '0';
when cycle2 =>
cenI <= '0';
cenO <= '0';
muxes <= "1011";
enables <= "110";
op1 <= '0';
op2 <= '0';
sfinish <= '0';
we <= '0';
when cycle3 =>
cenI <= '1';
cenO <= '0';
muxes <= "X101";
enables <= "010";
op1 <= '1';
op2 <= '0';
sfinish <= '0';
we <= '0';
when cycle4 =>
cenI <= '0';
cenO <= '0';
muxes <= "XXXX";
enables <= "100";
op1 <= 'X';
op2 <= 'X';
sfinish <= '0';
we <= '0';
if(olIn = '1') then
we <= '1';
cenO <= '1';
end if;
when cycle5 =>
cenI <= '0';
cenO <= '1';
muxes <= "XXXX";
enables <= "110";
op1 <= 'X';
op2 <= 'X';
sfinish <= '0';
we <= '0';
if (olIn = '1') then
we <= '1';
cenO<= '1';
cenI <= '1';
end if;
when done =>
cenI <= '0';
cenO <= '0';
muxes <= "XXXX";
enables <= "000";
op1 <= 'X';
op2 <= 'X';
sfinish <= '1';
we <= '0';
end case;
end process;
finish <= sfinish;
end Behavioral;
так, как я реализованный счетчик memIn было так:
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
use ieee.numeric_std.all;
entity counter is
generic (N : integer := 4; -- numero de bits do contador global
Ni : integer := 3; -- numero de bits do contador local
I : integer := 0 -- valor inicial dos contadores
);
Port (
clk : in STD_LOGIC;
rst: in STD_LOGIC;
cen : in STD_LOGIC;
ol : out STD_LOGIC;
counter : out STD_LOGIC_VECTOR (N-1 downto 0));
end counter;
architecture Behavioral of counter is
signal counter2: std_logic_vector (Ni-1 downto 0);
signal tmp, i_aux: std_logic_vector (N-1 downto 0);
begin
i_aux<=std_logic_vector(to_unsigned(I, i_aux'length));
process (clk, rst, cen, i_aux, counter2)
begin
if (rst ='1') then
tmp <= i_aux;
counter2 <= i_aux(Ni-1 downto 0);
elsif (clk'event and clk = '1') and (cen = '1') then
ol <= '0';
tmp <= tmp + 1;
counter2 <= counter2 + 1;
end if;
if (counter2 = "1010") then
ol <= '1';
end if;
if (counter2 = "1011") then
ol <= '0';
counter2 <= (0 => '1', others => '0');
end if;
end process;
counter <= tmp;
end Behavioral;
, но, поскольку обнаружение паттерна происходит за пределами процесса, неудачное моделирование после трассировки. Если я установил обнаружение паттерна внутри процесса, он всегда был одним циклом раньше или последним слишком долго, и я не смог его исправить.
Образец для обнаружения - это число девять в двоичном (1010), то счетчик посылает сигнал Ol для управления, который сигнализирует о завершении обработки всех данных в наборе.
Процесс, в котором это обнаружение должно происходить, находится в процессе, который находится внутри счетчика, но единственный способ, которым я мог заставить его работать, был вне этого процесса.
Бит 0 счетчика: выход не входит в память (я должен оставаться в одном и том же адресе памяти для двух циклов), поэтому счетчик должен рассчитывать на восемь (4 адреса памяти (от 1 до 4) Адрес памяти ноль для подготовки данных.
Как я мог бы сделать это лучше? Должен ли я просто поставить обнаружение внутри процесса и пытался труднее получить детектор матча, который работал?
Благодаря
Что такое «обнаружение шаблонов» и какой процесс? Я вижу четыре процесса и не могу сказать, о ком вы говорите. –
@BrianDrummond Извините, добавили эту информацию на исходное сообщение. Обнаружение паттерна - это обнаружение числа 1010 в компоненте счетчика. Процесс - это процесс внутри компонента счетчика. –
Почему вы синтезируете логику с присвоениями «X»? Это означает защелки с включенными комбинаторными значениями состояний. Используйте назначения по умолчанию перед оператором case и не считайте защелки. Вероятно, это улучшит время и позволит использовать комбинаторные «детекторы». Не является [минимальным, полным и проверяемым примером] (http://stackoverflow.com/help/mcve) - связь между «ol» и «olIn» и «olOut» не отображается, а также цель тактовой частоты , 'control' не анализируется без контекстного предложения. Не смешивайте std_logic_arith/unsigned и numeric_std. – user1155120