-
Notifications
You must be signed in to change notification settings - Fork 0
/
axi_expander.vhd
69 lines (54 loc) · 1.89 KB
/
axi_expander.vhd
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std_unsigned.all;
entity axi_expander is
generic (
G_INPUT_SIZE : natural;
G_OUTPUT_SIZE : natural
);
port (
clk_i : in std_logic;
rst_i : in std_logic;
s_ready_o : out std_logic;
s_valid_i : in std_logic;
s_data_i : in std_logic_vector(G_INPUT_SIZE-1 downto 0);
m_ready_i : in std_logic;
m_valid_o : out std_logic;
m_data_o : out std_logic_vector(G_OUTPUT_SIZE-1 downto 0)
);
end entity axi_expander;
architecture synthesis of axi_expander is
constant C_CONCAT_SIZE : natural := G_OUTPUT_SIZE + G_INPUT_SIZE;
signal concat_s : std_logic_vector(C_CONCAT_SIZE-1 downto 0);
signal data_r : std_logic_vector(G_OUTPUT_SIZE-1 downto 0);
signal size_r : natural range 0 to C_CONCAT_SIZE;
begin
assert G_OUTPUT_SIZE > G_INPUT_SIZE;
s_ready_o <= '0' when rst_i = '1' else
'0' when m_valid_o = '1' and m_ready_i = '0' else
'1' when size_r + G_INPUT_SIZE <= G_OUTPUT_SIZE else
'1';
concat_s <= data_r & s_data_i;
p_expander : process (clk_i)
begin
if rising_edge(clk_i) then
if m_ready_i = '1' then
m_valid_o <= '0';
end if;
if s_valid_i = '1' and s_ready_o = '1' then
data_r <= concat_s(G_OUTPUT_SIZE-1 downto 0);
if size_r + G_INPUT_SIZE < G_OUTPUT_SIZE then
size_r <= size_r + G_INPUT_SIZE;
else
m_data_o <= concat_s(size_r+G_INPUT_SIZE-1 downto size_r+G_INPUT_SIZE-G_OUTPUT_SIZE);
m_valid_o <= '1';
size_r <= size_r + G_INPUT_SIZE - G_OUTPUT_SIZE;
end if;
end if;
if rst_i = '1' then
size_r <= 0;
m_valid_o <= '0';
end if;
end if;
end process p_expander;
end architecture synthesis;