--******************************************************************************
--* @short 16 bit VME status register (read only)
--*
--* always contains data that is input at data port
--******************************************************************************
--* @author SAKULIN Hannes <hsakulin@dsy-srv2.cern.ch>
--* @version $Revision: 1.5 $
--* @date $Date: 2005/01/20 14:41:42 $
--******************************************************************************
--/
library IEEE;
use IEEE.Std_logic_1164.all;
use IEEE.Numeric_Std.all;
entity VMEStatusReg is
generic (
my_vme_base_address : integer := 0); -- VME address of this instance
port (
-- data port
data : in std_logic_vector(15 downto 0);
-- VME port
vme_addr : in std_logic_vector; -- leave unconstrained
vme_en : in std_logic;
vme_wr : in std_logic;
vme_data_out : out std_logic_vector;
vme_en_out : out std_logic;
vme_clk : in std_logic;
reset : in std_logic);
end VMEStatusReg;
-------------------------------------------------------------------------------
-- Implementation
-------------------------------------------------------------------------------
architecture behavioral of VMEStatusReg is
signal vme_en_i : std_logic;
begin -- behavioral
--------------------------------------------------------------------------------
-- VME port
--------------------------------------------------------------------------------
assert vme_addr'high >= 5 report "error: VME addr width has to be greater than 5" severity error;
-- purpose: decode VME address and generate internal enable signal
-- ( asynchronous )
vme_addr_decode : process (vme_addr, vme_en) is
variable my_addr_vec : std_logic_vector(vme_addr'high downto 0);
variable selected : boolean;
begin -- process vme_addr_decode
my_addr_vec := std_logic_vector( TO_UNSIGNED ( my_vme_base_address, vme_addr'high+1 ) );
selected := my_addr_vec(vme_addr'high downto 1) = vme_addr(vme_addr'high downto 1);
vme_en_i <= '0' ;
if selected then
vme_en_i <= vme_en;
end if;
end process vme_addr_decode;
-- generate VME enable out when addressed
reg_enout: process (vme_clk, reset) is
begin -- process reg
if reset = '1' then -- asynchronous reset
vme_en_out <= '0';
elsif vme_clk'event and vme_clk = '1' then -- rising clock edge
if (vme_wr = '0') then
vme_en_out <= vme_en_i;
end if;
end if;
end process reg_enout;
-- always output status data
vme_data_out <= data;
end behavioral;