Загрузка данных
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity calculator is
port(
clk : in std_logic;
key : in std_logic_vector(1 downto 0); -- выбор режима
result : out integer;
trigger : out std_logic
);
end calculator;
architecture rtl of calculator is
-- Константы
constant A_VAL : integer := 4;
constant B_VAL : integer := 2;
component mult_5 is
port(
dataa : in std_logic_vector(7 downto 0);
datab : in std_logic_vector(7 downto 0);
result : out std_logic_vector(15 downto 0)
);
end component;
component logic is
port(
a : in integer;
b : in integer;
result : out integer
);
end component;
-- Сигнал переключения: '0' = захват нулей, '1' = захват A и B
signal sel : std_logic := '0';
-- Регистры для хранения текущих значений на входах умножителей
signal a_reg : std_logic_vector(7 downto 0) := (others => '0');
signal b_reg : std_logic_vector(7 downto 0) := (others => '0');
-- Выходы умножителей
signal dsp_result_vec : std_logic_vector(15 downto 0);
signal logic_result : integer;
-- Преобразованный результат DSP
signal dsp_result_int : integer;
-- Режим (кнопка)
signal mode : std_logic := '0'; -- '0' = logic, '1' = dsp
-- Регистр результата
signal result_reg : integer := 0;
signal trigger_reg : std_logic := '0';
-- Дребезг кнопок
signal key_r0, key_r1 : std_logic_vector(1 downto 0) := (others => '1');
begin
---------------------------------------------------------------
-- Переключение sel каждый такт
---------------------------------------------------------------
process(clk)
begin
if rising_edge(clk) then
sel <= not sel; -- каждый такт меняется: 0 -> 1 -> 0 -> 1 ...
end if;
end process;
---------------------------------------------------------------
-- Мультиплексоры для a_reg и b_reg
-- sel='1' => константы A,B
-- sel='0' => нули
---------------------------------------------------------------
process(clk)
begin
if rising_edge(clk) then
if sel = '1' then
a_reg <= std_logic_vector(to_unsigned(A_VAL, 8));
b_reg <= std_logic_vector(to_unsigned(B_VAL, 8));
else
a_reg <= (others => '0');
b_reg <= (others => '0');
end if;
end if;
end process;
---------------------------------------------------------------
-- Умножители (работают постоянно)
---------------------------------------------------------------
mult_inst: mult_5
port map(
dataa => a_reg,
datab => b_reg,
result => dsp_result_vec
);
dsp_result_int <= to_integer(unsigned(dsp_result_vec));
logic_inst: logic
port map(
a => to_integer(unsigned(a_reg)),
b => to_integer(unsigned(b_reg)),
result => logic_result
);
---------------------------------------------------------------
-- Обработка кнопок выбора режима
---------------------------------------------------------------
process(clk)
begin
if rising_edge(clk) then
key_r0 <= key;
key_r1 <= key_r0;
if key_r1(0) = '1' and key_r0(0) = '0' then
mode <= '0'; -- логическое умножение
elsif key_r1(1) = '1' and key_r0(1) = '0' then
mode <= '1'; -- DSP умножение
end if;
end if;
end process;
---------------------------------------------------------------
-- Выходной регистр (обновляется каждый такт)
---------------------------------------------------------------
process(clk)
begin
if rising_edge(clk) then
if mode = '0' then
result_reg <= logic_result;
else
result_reg <= dsp_result_int;
end if;
trigger_reg <= '1';
end if;
end process;
result <= result_reg;
trigger <= trigger_reg;
end rtl;