----------------------------------------------------------------------- -- $Header: /tmp/cvsroot/VHDL/lib/JBUS/src/busmaster_sync.vhd,v 1.6 2013-08-03 19:31:19 jens Exp $ ----------------------------------------------------------------------- library IEEE; use IEEE.STD_LOGIC_1164.ALL; use IEEE.NUMERIC_STD.ALL; use work.utils_pkg.all; use work.busmaster_types.all; ------------------------------------------------------------------ entity busmaster_sync is Generic ( DATA_WIDTH : natural := 32; FIFO_DEPTH : natural := 4 ); Port ( clk : in std_logic; rst : in std_logic; cmd_cycle_finished : out std_logic; cmd_cycle_en : in std_logic; cmd_rdy : out std_logic; cmd_we : in std_logic; cmd_in : in bm_cmd_t; din : in unsigned(DATA_WIDTH-1 downto 0); din_rdy : out std_logic; din_we : in std_logic; dout : out unsigned(DATA_WIDTH-1 downto 0); dout_vld : out std_logic; dout_re : in std_logic; -- J-BUS signals ACK_I : in std_logic; SRDY_I : in std_logic; MDAT_I : in unsigned(DATA_WIDTH-1 downto 0); MDAT_O : out unsigned(DATA_WIDTH-1 downto 0); ADDR_O : out unsigned(31 downto 0); SEL_O : out unsigned(DATA_WIDTH/8-1 downto 0); WE_O : out std_logic; CYC_O : out std_logic; STB_O : out std_logic; MRDY_O : out std_logic ); end busmaster_sync; architecture Behavioral of busmaster_sync is -- Bus Command FIFO signal cmd_fifo_din : unsigned(32+DATA_WIDTH/8+1-1 downto 0); signal cmd_fifo_dout : unsigned(32+DATA_WIDTH/8+1-1 downto 0); signal cmd_fifo_re : std_logic; signal cmd_fifo_we : std_logic; signal cmd_fifo_full : std_logic; signal cmd_fifo_empty : std_logic; -- Bus Read FIFO signal read_fifo_re : std_logic; signal read_fifo_we : std_logic; signal read_fifo_full : std_logic; signal read_fifo_empty : std_logic; signal write_fifo_re : std_logic; signal write_fifo_we : std_logic; signal write_fifo_full : std_logic; signal write_fifo_empty : std_logic; signal cycle_busy : std_logic; signal cmd_en : std_logic; signal cmd_read_en : std_logic; signal read_cnt : integer range 0 to 65535; signal write : std_logic; begin cmd_en <= cmd_cycle_en and cmd_we and not cmd_fifo_full; cmd_read_en <= cmd_en and not cmd_in.rw; write <= cmd_fifo_dout(32+DATA_WIDTH/8); dout_vld <= not read_fifo_empty; MRDY_O <= not read_fifo_full; read_fifo_we <= ACK_I and cycle_busy; read_fifo_re <= dout_re; ADDR_O <= cmd_fifo_dout(31 downto 0); SEL_O <= cmd_fifo_dout(32+DATA_WIDTH/8-1 downto 32); WE_O <= write; cmd_fifo_din <= cmd_in.rw & cmd_in.sel & cmd_in.addr; cmd_rdy <= not cmd_fifo_full; cmd_fifo_we <= cmd_en; cmd_fifo_re <= SRDY_I and cycle_busy; din_rdy <= not write_fifo_full; write_fifo_we <= din_we; write_fifo_re <= SRDY_I and cycle_busy and write and not cmd_fifo_empty; STB_O <= not cmd_fifo_empty; CYC_O <= cycle_busy; cmd_cycle_finished <= not cycle_busy; -- proc_bus_read_counter: -- process(clk) -- begin -- if rising_edge(clk) then -- if rst = '1' then -- read_cnt <= 0; -- elsif cmd_read_en = '1' and read_fifo_we = '0' then -- read_cnt <= read_cnt + 1; -- elsif cmd_read_en = '0' and read_fifo_we = '1' then -- read_cnt <= read_cnt - 1; -- end if; -- end if; -- end process; proc_bus_read_counter: process(clk) begin if rising_edge(clk) then if rst = '1' then read_cnt <= 0; elsif cmd_read_en = '1' and read_fifo_empty = '1' then read_cnt <= read_cnt + 1; elsif cmd_read_en = '0' and read_fifo_empty = '0' and dout_re = '1' then read_cnt <= read_cnt - 1; end if; end if; end process; proc_cycle_busy: process(clk) begin if rising_edge(clk) then if rst = '1' then cycle_busy <= '0'; elsif cmd_cycle_en = '1' then if cmd_we = '1' then cycle_busy <= '1'; end if; elsif read_cnt = 0 and cmd_fifo_empty = '1' and write_fifo_empty = '1' then cycle_busy <= '0'; end if; end if; end process; -- Bus READ FIFO inst_BM_READ_FIFO: entity work.fifo_sync GENERIC MAP ( addr_width => NextExpBaseTwo(FIFO_DEPTH), data_width => DATA_WIDTH, do_last_read_update => true ) PORT MAP ( rst => rst, clk => clk, we => read_fifo_we, re => read_fifo_re, fifo_full => read_fifo_full, fifo_empty => read_fifo_empty, fifo_afull => open, fifo_aempty => open, data_w => MDAT_I, data_r => dout ); -- Bus WRITE FIFO inst_BM_WRITE_FIFO: entity work.fifo_sync GENERIC MAP ( addr_width => NextExpBaseTwo(FIFO_DEPTH), data_width => DATA_WIDTH, do_last_read_update => false ) PORT MAP ( rst => rst, clk => clk, we => write_fifo_we, re => write_fifo_re, fifo_full => write_fifo_full, fifo_empty => write_fifo_empty, fifo_afull => open, fifo_aempty => open, data_w => din, data_r => MDAT_O ); -- Bus command FIFO inst_BM_CMD_FIFO: entity work.fifo_sync GENERIC MAP ( addr_width => NextExpBaseTwo(FIFO_DEPTH), data_width => cmd_fifo_din'length, do_last_read_update => false ) PORT MAP ( rst => rst, clk => clk, we => cmd_fifo_we, re => cmd_fifo_re, fifo_full => cmd_fifo_full, fifo_empty => cmd_fifo_empty, fifo_afull => open, fifo_aempty => open, data_w => cmd_fifo_din, data_r => cmd_fifo_dout ); end Behavioral;