90 lines
2.7 KiB
VHDL
90 lines
2.7 KiB
VHDL
![]() |
library ieee;
|
||
|
use ieee.std_logic_1164.all;
|
||
|
use ieee.numeric_std.all;
|
||
|
|
||
|
library work;
|
||
|
use work.reg32.all;
|
||
|
use work.avalon_slave.all;
|
||
|
|
||
|
entity avalon_slave_transitions is
|
||
|
generic (
|
||
|
REG_COUNT : natural;
|
||
|
REG_ACCESS_TYPES : work.reg32.AccessArray
|
||
|
);
|
||
|
port (
|
||
|
address : in std_logic_vector( 3 downto 0 );
|
||
|
read : in std_logic;
|
||
|
write : in std_logic;
|
||
|
|
||
|
current_state : in work.avalon_slave.State;
|
||
|
next_state : out work.avalon_slave.State;
|
||
|
reg_index : out integer range 0 to REG_COUNT - 1
|
||
|
);
|
||
|
end entity avalon_slave_transitions;
|
||
|
|
||
|
architecture rtl of avalon_slave_transitions is
|
||
|
|
||
|
signal is_access : boolean;
|
||
|
signal is_read : boolean;
|
||
|
signal is_write : boolean;
|
||
|
signal address_index : integer range 0 to 2 ** address'high - 1;
|
||
|
signal is_valid_reg_index : boolean;
|
||
|
signal access_type : work.reg32.AccessType;
|
||
|
signal is_valid_access : boolean;
|
||
|
signal is_valid_access_type : boolean;
|
||
|
signal index : integer range 0 to REG_COUNT - 1;
|
||
|
|
||
|
begin
|
||
|
|
||
|
c_is_access: is_access <= ( read or write ) = '1';
|
||
|
c_is_read: is_read <= read = '1';
|
||
|
c_is_write: is_write <= write = '1' and not is_read;
|
||
|
|
||
|
c_address_index: address_index <= to_integer( unsigned( address ) );
|
||
|
|
||
|
c_is_valid_reg_index: is_valid_reg_index <= address_index <= ( REG_COUNT - 1 );
|
||
|
|
||
|
c_index: index <= address_index when is_valid_reg_index else 0;
|
||
|
c_reg_index: reg_index <= index;
|
||
|
|
||
|
c_access_type: access_type <= REG_ACCESS_TYPES( index );
|
||
|
|
||
|
c_is_valid_access_type: is_valid_access_type <= true when
|
||
|
( is_read and work.reg32.allows_read( access_type ) ) or
|
||
|
( is_write and work.reg32.allows_write( access_type ) )
|
||
|
else false;
|
||
|
|
||
|
c_is_valid_access: is_valid_access <= is_access and is_valid_reg_index and
|
||
|
is_valid_access_type;
|
||
|
|
||
|
transition : process( all ) is
|
||
|
begin
|
||
|
case current_state is
|
||
|
when SLAVE_IDLE =>
|
||
|
if ( is_valid_access and is_read ) then
|
||
|
next_state <= SLAVE_READ;
|
||
|
elsif ( is_valid_access and is_write ) then
|
||
|
next_state <= SLAVE_WRITE;
|
||
|
else
|
||
|
next_state <= SLAVE_IDLE;
|
||
|
end if;
|
||
|
|
||
|
when SLAVE_READ =>
|
||
|
next_state <= SLAVE_READ_DATA;
|
||
|
|
||
|
when SLAVE_READ_DATA =>
|
||
|
if ( is_valid_access and is_read ) then
|
||
|
next_state <= SLAVE_READ;
|
||
|
elsif ( is_valid_access and is_write ) then
|
||
|
next_state <= SLAVE_WRITE;
|
||
|
else
|
||
|
next_state <= SLAVE_IDLE;
|
||
|
end if;
|
||
|
|
||
|
when SLAVE_WRITE =>
|
||
|
next_state <= SLAVE_IDLE;
|
||
|
end case;
|
||
|
end process transition;
|
||
|
|
||
|
end architecture rtl;
|