OpenCores
URL https://opencores.org/ocsvn/wb_tk/wb_tk/trunk

Subversion Repositories wb_tk

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /
    from Rev 3 to Rev 4
    Reverse comparison

Rev 3 → Rev 4

/trunk/TestBench/wb_out_reg_TB.vhd
0,0 → 1,279
--
-- A test bench for 32-bit access
--
 
library ieee,wb_tk;
use ieee.std_logic_1164.all;
use wb_tk.technology.all;
use wb_tk.wb_test.all;
 
entity wb_out_reg_tb_32 is
-- Generic declarations of the tested unit
generic(
width : POSITIVE := 16;
bus_width : POSITIVE := 32;
offset : INTEGER := 4 );
end wb_out_reg_tb_32;
 
architecture TB of wb_out_reg_tb_32 is
-- Component declaration of the tested unit
component wb_out_reg
generic(
width : POSITIVE := width;
bus_width : POSITIVE := bus_width;
offset : INTEGER := offset );
port (
clk_i: in std_logic;
rst_i: in std_logic;
rst_val: std_logic_vector(width-1 downto 0) := (others => '0');
cyc_i: in std_logic := '1';
stb_i: in std_logic;
sel_i: in std_logic_vector ((bus_width/8)-1 downto 0) := (others => '1');
we_i: in std_logic;
ack_o: out std_logic;
ack_oi: in std_logic := '-';
adr_i: in std_logic_vector (size2bits((width+offset+bus_width-1)/bus_width)-1 downto 0) := (others => '0');
dat_i: in std_logic_vector (bus_width-1 downto 0);
dat_oi: in std_logic_vector (bus_width-1 downto 0) := (others => '-');
dat_o: out std_logic_vector (bus_width-1 downto 0);
q: out std_logic_vector (width-1 downto 0)
);
end component;
 
-- Stimulus signals - signals mapped to the input and inout ports of tested entity
signal adr_i : std_logic_vector (size2bits((width+offset+bus_width-1)/bus_width)-1 downto 0) := (others => '0');
signal clk_i : std_logic;
signal rst_i : std_logic;
signal rst_val : std_logic_vector((width-1) downto 0) := (others => '0');
signal cyc_i : std_logic;
signal stb_i : std_logic;
signal sel_i : std_logic_vector(((bus_width/8)-1) downto 0) := (others => '1');
signal we_i : std_logic;
signal ack_oi : std_logic;
signal dat_i : std_logic_vector((bus_width-1) downto 0);
signal dat_oi : std_logic_vector((bus_width-1) downto 0);
-- Observed signals - signals mapped to the output ports of tested entity
signal ack_o : std_logic;
signal dat_o : std_logic_vector((bus_width-1) downto 0);
signal q : std_logic_vector((width-1) downto 0);
 
-- Add your code here ...
 
begin
rst_val <= (others => '0');
ack_oi <= 'U';
dat_oi <= (others => 'U');
 
-- Unit Under Test port map
UUT : wb_out_reg
port map
(clk_i => clk_i,
rst_i => rst_i,
rst_val => rst_val,
cyc_i => cyc_i,
stb_i => stb_i,
sel_i => sel_i,
we_i => we_i,
ack_o => ack_o,
ack_oi => ack_oi,
adr_i => adr_i,
dat_i => dat_i,
dat_oi => dat_oi,
dat_o => dat_o,
q => q );
 
clk: process is
begin
clk_i <= '0';
wait for 25ns;
clk_i <= '1';
wait for 25ns;
end process;
reset: process is
begin
rst_i <= '1';
wait for 150ns;
rst_i <= '0';
wait;
end process;
master: process is
begin
we_i <= '0';
cyc_i <= '0';
stb_i <= '0';
adr_i <= (others => '0');
dat_i <= (others => '0');
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
 
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","00000000000000000000000000000000");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","00000000000000000000000000000000");
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","11111111111111111111111111111111");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","11111111111111111111111111111111");
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","01110110010101000011001000010000");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","01110110010101000011001000010000");
 
sel_i <= add_one(sel_i);
-- if (sel_i = "1111") then wait; end if;
end process;
end TB;
 
configuration TB_wb_out_reg_32 of wb_out_reg_tb_32 is
for TB
for UUT : wb_out_reg
use entity work.wb_out_reg(wb_out_reg);
end for;
end for;
end TB_wb_out_reg_32;
 
 
 
--
-- A test bench for 16-bit access
--
 
 
library ieee,wb_tk;
use ieee.std_logic_1164.all;
use wb_tk.technology.all;
use wb_tk.wb_test.all;
 
entity wb_out_reg_tb_16 is
-- Generic declarations of the tested unit
generic(
width : POSITIVE := 16;
bus_width : POSITIVE := 16;
offset : INTEGER := 4 );
end wb_out_reg_tb_16;
 
architecture TB of wb_out_reg_tb_16 is
-- Component declaration of the tested unit
component wb_out_reg
generic(
width : POSITIVE := width;
bus_width : POSITIVE := bus_width;
offset : INTEGER := offset );
port (
clk_i: in std_logic;
rst_i: in std_logic;
rst_val: std_logic_vector(width-1 downto 0) := (others => '0');
cyc_i: in std_logic := '1';
stb_i: in std_logic;
sel_i: in std_logic_vector ((bus_width/8)-1 downto 0) := (others => '1');
we_i: in std_logic;
ack_o: out std_logic;
ack_oi: in std_logic := '-';
adr_i: in std_logic_vector (max(log2((width+offset+bus_width-1)/bus_width)-1,0) downto 0) := (others => '0');
dat_i: in std_logic_vector (bus_width-1 downto 0);
dat_oi: in std_logic_vector (bus_width-1 downto 0) := (others => '-');
dat_o: out std_logic_vector (bus_width-1 downto 0);
q: out std_logic_vector (width-1 downto 0)
);
end component;
 
signal adr_i : std_logic_vector (max(log2((width+offset+bus_width-1)/bus_width)-1,0) downto 0) := (others => '0');
-- Stimulus signals - signals mapped to the input and inout ports of tested entity
signal clk_i : std_logic;
signal rst_i : std_logic;
signal rst_val : std_logic_vector((width-1) downto 0) := (others => '0');
signal cyc_i : std_logic;
signal stb_i : std_logic;
signal sel_i : std_logic_vector(((bus_width/8)-1) downto 0) := (others => '1');
signal we_i : std_logic;
signal ack_oi : std_logic;
signal dat_i : std_logic_vector((bus_width-1) downto 0);
signal dat_oi : std_logic_vector((bus_width-1) downto 0);
-- Observed signals - signals mapped to the output ports of tested entity
signal ack_o : std_logic;
signal dat_o : std_logic_vector((bus_width-1) downto 0);
signal q : std_logic_vector((width-1) downto 0);
 
-- Add your code here ...
 
begin
rst_val <= (others => '0');
ack_oi <= 'U';
dat_oi <= (others => 'U');
 
-- Unit Under Test port map
UUT : wb_out_reg
port map
(clk_i => clk_i,
rst_i => rst_i,
rst_val => rst_val,
cyc_i => cyc_i,
stb_i => stb_i,
sel_i => sel_i,
we_i => we_i,
ack_o => ack_o,
ack_oi => ack_oi,
adr_i => adr_i,
dat_i => dat_i,
dat_oi => dat_oi,
dat_o => dat_o,
q => q );
 
clk: process is
begin
clk_i <= '0';
wait for 25ns;
clk_i <= '1';
wait for 25ns;
end process;
reset: process is
begin
rst_i <= '1';
wait for 150ns;
rst_i <= '0';
wait;
end process;
master: process is
begin
we_i <= '0';
cyc_i <= '0';
stb_i <= '0';
adr_i <= (others => '0');
dat_i <= (others => '0');
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
 
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"1","0000000000000000");
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","0000000000000000");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"1","0000000000000000");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","0000000000000000");
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"1","1111111111111111");
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","1111111111111111");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"1","1111111111111111");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","1111111111111111");
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"1","0111011001010100");
wr_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","0011001000010000");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"1","0111011001010100");
rd_val(clk_i, adr_i,dat_o,dat_i,we_i,cyc_i,stb_i,ack_o,"0","0011001000010000");
 
sel_i <= add_one(sel_i);
end process;
end TB;
 
configuration TB_wb_out_reg_16 of wb_out_reg_tb_16 is
for TB
for UUT : wb_out_reg
use entity work.wb_out_reg(wb_out_reg);
end for;
end for;
end TB_wb_out_reg_16;
/trunk/TestBench/wb_bus_dnsize_TB.vhd
0,0 → 1,174
--*************************************************************
--* This file is automatically generated test bench template *
--* By ACTIVE-VHDL <TBgen v1.10>. Copyright (C) ALDEC Inc. *
--* *
--* This file was generated on: 15:34, 2001.04.22. *
--* Tested entity name: wb_bus_dnsize *
--* File name contains tested entity: $DSN\src\wb_bus_dnsize.vhd *
--*************************************************************
 
library ieee,wb_tk,synopsys;
use ieee.std_logic_1164.all;
use wb_tk.technology.all;
use synopsys.std_logic_arith.all;
use wb_tk.wb_test.all;
 
entity wb_bus_dnsize_tb is
generic(
m_bus_width : POSITIVE := 64;
m_addr_width : POSITIVE := 6;
s_bus_width : POSITIVE := 16;
s_addr_width : POSITIVE := 8;
little_endien : BOOLEAN := true );
end wb_bus_dnsize_tb;
 
architecture TB of wb_bus_dnsize_tb is
component wb_bus_dnsize
generic(
m_bus_width : POSITIVE := m_bus_width;
m_addr_width : POSITIVE := m_addr_width;
s_bus_width : POSITIVE := s_bus_width;
s_addr_width : POSITIVE := s_addr_width;
little_endien : BOOLEAN := little_endien
);
port(
m_adr_i : in std_logic_vector((m_addr_width-1) downto 0);
m_sel_i : in std_logic_vector(((m_bus_width/8)-1) downto 0);
m_dat_i : in std_logic_vector((m_bus_width-1) downto 0);
m_dat_oi : in std_logic_vector((m_bus_width-1) downto 0);
m_dat_o : out std_logic_vector((m_bus_width-1) downto 0);
m_cyc_i : in std_logic;
m_ack_o : out std_logic;
m_ack_oi : in std_logic;
m_err_o : out std_logic;
m_err_oi : in std_logic;
m_rty_o : out std_logic;
m_rty_oi : in std_logic;
m_we_i : in std_logic;
m_stb_i : in std_logic;
s_adr_o : out std_logic_vector((s_addr_width-1) downto 0);
s_sel_o : out std_logic_vector(((s_bus_width/8)-1) downto 0);
s_dat_i : in std_logic_vector((s_bus_width-1) downto 0);
s_dat_o : out std_logic_vector((s_bus_width-1) downto 0);
s_cyc_o : out std_logic;
s_ack_i : in std_logic;
s_err_i : in std_logic;
s_rty_i : in std_logic;
s_we_o : out std_logic;
s_stb_o : out std_logic
);
end component;
 
-- Stimulus signals - signals mapped to the input and inout ports of tested entity
signal m_adr_i : std_logic_vector((m_addr_width-1) downto 0);
signal m_sel_i : std_logic_vector(((m_bus_width/8)-1) downto 0) := (others => '0');
signal m_dat_i : std_logic_vector((m_bus_width-1) downto 0);
signal m_dat_oi : std_logic_vector((m_bus_width-1) downto 0) := (others => 'U');
signal m_cyc_i : std_logic;
signal m_ack_oi : std_logic := 'U';
signal m_err_oi : std_logic := 'U';
signal m_rty_oi : std_logic := 'U';
signal m_we_i : std_logic;
signal m_stb_i : std_logic;
signal s_dat_i : std_logic_vector((s_bus_width-1) downto 0);
signal s_ack_i : std_logic;
signal s_err_i : std_logic;
signal s_rty_i : std_logic;
-- Observed signals - signals mapped to the output ports of tested entity
signal m_dat_o : std_logic_vector((m_bus_width-1) downto 0);
signal m_ack_o : std_logic;
signal m_err_o : std_logic;
signal m_rty_o : std_logic;
signal s_adr_o : std_logic_vector((s_addr_width-1) downto 0);
signal s_sel_o : std_logic_vector(((s_bus_width/8)-1) downto 0);
signal s_dat_o : std_logic_vector((s_bus_width-1) downto 0);
signal s_cyc_o : std_logic;
signal s_we_o : std_logic;
signal s_stb_o : std_logic;
 
signal clk_i: std_logic;
signal rst_i: std_logic;
begin
 
-- Unit Under Test port map
UUT : wb_bus_dnsize
port map
(m_adr_i => m_adr_i,
m_sel_i => m_sel_i,
m_dat_i => m_dat_i,
m_dat_oi => m_dat_oi,
m_dat_o => m_dat_o,
m_cyc_i => m_cyc_i,
m_ack_o => m_ack_o,
m_ack_oi => m_ack_oi,
m_err_o => m_err_o,
m_err_oi => m_err_oi,
m_rty_o => m_rty_o,
m_rty_oi => m_rty_oi,
m_we_i => m_we_i,
m_stb_i => m_stb_i,
s_adr_o => s_adr_o,
s_sel_o => s_sel_o,
s_dat_i => s_dat_i,
s_dat_o => s_dat_o,
s_cyc_o => s_cyc_o,
s_ack_i => s_ack_i,
s_err_i => s_err_i,
s_rty_i => s_rty_i,
s_we_o => s_we_o,
s_stb_o => s_stb_o );
 
clk: process is
begin
clk_i <= '0';
wait for 25ns;
clk_i <= '1';
wait for 25ns;
end process;
reset: process is
begin
rst_i <= '1';
wait for 150ns;
rst_i <= '0';
wait;
end process;
master: process is
begin
m_we_i <= '0';
m_cyc_i <= '0';
m_stb_i <= '0';
m_adr_i <= (others => '0');
m_dat_i <= (others => '0');
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
 
wr_val(clk_i, m_adr_i,m_dat_o,m_dat_i,m_we_i,m_cyc_i,m_stb_i,m_ack_o,"000101","1111111011011100101110101001100001110110010101000011001000010000");
rd_val(clk_i, m_adr_i,m_dat_o,m_dat_i,m_we_i,m_cyc_i,m_stb_i,m_ack_o,"000101","1111111011011100101110101001100001110110010101000011001000010000");
-- wr_val(clk_i, m_adr_i,m_dat_o,m_dat_i,m_we_i,m_cyc_i,m_stb_i,m_ack_o,"000101","01110110010101000011001000010000");
-- rd_val(clk_i, m_adr_i,m_dat_o,m_dat_i,m_we_i,m_cyc_i,m_stb_i,m_ack_o,"000101","01110110010101000011001000010000");
 
m_sel_i <= add_one(m_sel_i);
-- if (sel_i = "1111") then wait; end if;
end process;
 
s_ack_i <= s_stb_o;
s_dat_i <= (others => '1');
s_err_i <= '0';
s_rty_i <= '0';
end TB;
 
configuration TB_wb_bus_dnsize of wb_bus_dnsize_tb is
for TB
for UUT : wb_bus_dnsize
use entity work.wb_bus_dnsize(wb_bus_dnsize);
end for;
end for;
end TB_wb_bus_dnsize;
 
/trunk/wb_async_slave.vhd
0,0 → 1,184
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_async_slave: Wishbone bus to async (SRAM-like) bus slave bridge.
 
-------------------------------------------------------------------------------
--
-- wb_async_slave
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library wb_tk;
use wb_tk.technology.all;
 
entity wb_async_slave is
generic (
width: positive := 16;
addr_width: positive := 20
);
port (
clk_i: in std_logic;
rst_i: in std_logic := '0';
-- interface for wait-state generator state-machine
wait_state: in std_logic_vector (3 downto 0);
 
-- interface to wishbone master device
adr_i: in std_logic_vector (addr_width-1 downto 0);
sel_i: in std_logic_vector ((addr_width/8)-1 downto 0);
dat_i: in std_logic_vector (width-1 downto 0);
dat_o: out std_logic_vector (width-1 downto 0);
dat_oi: in std_logic_vector (width-1 downto 0) := (others => '-');
we_i: in std_logic;
stb_i: in std_logic;
ack_o: out std_logic := '0';
ack_oi: in std_logic := '-';
-- interface to async slave
a_data: inout std_logic_vector (width-1 downto 0) := (others => 'Z');
a_addr: out std_logic_vector (addr_width-1 downto 0) := (others => 'U');
a_rdn: out std_logic := '1';
a_wrn: out std_logic := '1';
a_cen: out std_logic := '1';
-- byte-enable signals
a_byen: out std_logic_vector ((width/8)-1 downto 0)
);
end wb_async_slave;
 
architecture wb_async_slave of wb_async_slave is
-- multiplexed access signals to memory
signal i_ack: std_logic;
signal sm_ack: std_logic;
 
type states is (sm_idle, sm_wait, sm_deact);
signal state: states;
signal cnt: std_logic_vector(3 downto 0);
begin
ack_o <= (stb_i and i_ack) or (not stb_i and ack_oi);
dat_o_gen: for i in dat_o'RANGE generate
dat_o(i) <= (stb_i and a_data(i)) or (not stb_i and dat_oi(i));
end generate;
-- For 0WS operation i_ack is an async signal otherwise it's a sync one.
i_ack_gen: process is
begin
wait on sm_ack, stb_i, wait_state, state;
if (wait_state = "0000") then
case (state) is
when sm_deact => i_ack <= '0';
when others => i_ack <= stb_i;
end case;
else
i_ack <= sm_ack;
end if;
end process;
-- SRAM signal-handler process
sram_signals: process is
begin
wait on state,we_i,a_data,adr_i,rst_i, stb_i, sel_i, dat_i;
if (rst_i = '1') then
a_wrn <= '1';
a_rdn <= '1';
a_cen <= '1';
a_addr <= (others => '-');
a_data <= (others => 'Z');
a_byen <= (others => '1');
else
case (state) is
when sm_deact =>
a_wrn <= '1';
a_rdn <= '1';
a_cen <= '1';
a_addr <= (others => '-');
a_data <= (others => 'Z');
a_byen <= (others => '1');
when others =>
a_addr <= adr_i;
a_rdn <= not (not we_i and stb_i);
a_wrn <= not (we_i and stb_i);
a_cen <= not stb_i;
a_byen <= not sel_i;
if (we_i = '1') then
a_data <= dat_i;
else
a_data <= (others => 'Z');
end if;
end case;
end if;
end process;
 
-- Aysnc access state-machine.
async_sm: process is
-- variable cnt: std_logic_vector(3 downto 0) := "0000";
-- variable state: states := init;
begin
wait until clk_i'EVENT and clk_i = '1';
if (rst_i = '1') then
state <= sm_idle;
cnt <= ((0) => '1', others => '0');
sm_ack <= '0';
else
case (state) is
when sm_idle =>
-- Check if anyone needs access to the memory.
-- it's rdy signal will already be pulled low, so we only have to start the access
if (stb_i = '1') then
case wait_state is
when "0000" =>
sm_ack <= '1';
state <= sm_deact;
when "0001" =>
sm_ack <= '1';
cnt <= "0001";
state <= sm_wait;
when others =>
sm_ack <= '0';
cnt <= "0001";
state <= sm_wait;
end case;
end if;
when sm_wait =>
if (cnt = wait_state) then
-- wait cycle completed.
state <= sm_deact;
sm_ack <= '0';
cnt <= "0000";
else
if (add_one(cnt) = wait_state) then
sm_ack <= '1';
else
sm_ack <= '0';
end if;
cnt <= add_one(cnt);
end if;
when sm_deact =>
if (stb_i = '1') then
case wait_state is
when "0000" =>
cnt <= "0000";
sm_ack <= '0';
state <= sm_wait;
when others =>
sm_ack <= '0';
cnt <= "0000";
state <= sm_wait;
end case;
else
sm_ack <= '0';
state <= sm_idle;
end if;
end case;
end if;
end process;
end wb_async_slave;
 
/trunk/wb_arbiter.vhd
0,0 → 1,245
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_arbiter: two-way bus arbiter. Asyncronous logic ensures 0-ws operation on shared bus
 
-------------------------------------------------------------------------------
--
-- wb_arbiter
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library wb_tk;
use wb_tk.technology.all;
 
entity wb_arbiter is
port (
-- clk: in std_logic;
rst_i: in std_logic := '0';
-- interface to master device a
a_we_i: in std_logic;
a_stb_i: in std_logic;
a_cyc_i: in std_logic;
a_ack_o: out std_logic;
a_ack_oi: in std_logic := '-';
a_err_o: out std_logic;
a_err_oi: in std_logic := '-';
a_rty_o: out std_logic;
a_rty_oi: in std_logic := '-';
-- interface to master device b
b_we_i: in std_logic;
b_stb_i: in std_logic;
b_cyc_i: in std_logic;
b_ack_o: out std_logic;
b_ack_oi: in std_logic := '-';
b_err_o: out std_logic;
b_err_oi: in std_logic := '-';
b_rty_o: out std_logic;
b_rty_oi: in std_logic := '-';
 
-- interface to shared devices
s_we_o: out std_logic;
s_stb_o: out std_logic;
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
mux_signal: out std_logic; -- 0: select A signals, 1: select B signals
 
-- misc control lines
priority: in std_logic -- 0: A have priority over B, 1: B have priority over A
);
end wb_arbiter;
 
-- This acthitecture is a clean asyncron state-machine. However it cannot be mapped to FPGA architecture
architecture behaviour of wb_arbiter is
type states is (idle,aa,ba);
signal i_mux_signal: std_logic;
signal e_state: states;
begin
mux_signal <= i_mux_signal;
sm: process is
variable state: states;
begin
wait on a_cyc_i, b_cyc_i, priority, rst_i;
if (rst_i = '1') then
state := idle;
i_mux_signal <= priority;
else
case (state) is
when idle =>
if (a_cyc_i = '1' and (priority = '0' or b_cyc_i = '0')) then
state := aa;
i_mux_signal <= '0';
elsif (b_cyc_i = '1' and (priority = '1' or a_cyc_i = '0')) then
state := ba;
i_mux_signal <= '1';
else
i_mux_signal <= priority;
end if;
when aa =>
if (a_cyc_i = '0') then
if (b_cyc_i = '1') then
state := ba;
i_mux_signal <= '1';
else
state := idle;
i_mux_signal <= priority;
end if;
else
i_mux_signal <= '0';
end if;
when ba =>
if (b_cyc_i = '0') then
if (a_cyc_i = '1') then
state := aa;
i_mux_signal <= '0';
else
state := idle;
i_mux_signal <= priority;
end if;
else
i_mux_signal <= '1';
end if;
end case;
end if;
e_state <= state;
end process;
signal_mux: process is
begin
wait on a_we_i, a_stb_i, a_ack_oi, a_err_oi, a_rty_oi, a_cyc_i,
b_we_i, b_stb_i, b_ack_oi, b_err_oi, b_rty_oi, b_cyc_i,
s_ack_i, s_err_i, s_rty_i, i_mux_signal;
if (i_mux_signal = '0') then
s_we_o <= a_we_i;
s_stb_o <= a_stb_i;
s_cyc_o <= a_cyc_i;
a_ack_o <= (a_stb_i and s_ack_i) or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and s_err_i) or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and s_rty_i) or (not a_stb_i and a_rty_oi);
b_ack_o <= (b_stb_i and '0') or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and '0') or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and '0') or (not b_stb_i and b_rty_oi);
else
s_we_o <= b_we_i;
s_stb_o <= b_stb_i;
s_cyc_o <= b_cyc_i;
b_ack_o <= (b_stb_i and s_ack_i) or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and s_err_i) or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and s_rty_i) or (not b_stb_i and b_rty_oi);
a_ack_o <= (a_stb_i and '0') or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and '0') or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and '0') or (not a_stb_i and a_rty_oi);
end if;
end process;
end behaviour;
 
-- This acthitecture is a more-or-less structural implementation. Fits for FPGA realization.
architecture FPGA of wb_arbiter is
component d_ff
port ( d : in STD_LOGIC;
clk: in STD_LOGIC;
ena: in STD_LOGIC := '1';
clr: in STD_LOGIC := '0';
pre: in STD_LOGIC := '0';
q : out STD_LOGIC
);
end component;
signal i_mux_signal: std_logic;
type states is (idle,aa,ba,XX);
signal e_state: states;
 
-- signals for a DFF in FPGA
signal idle_s, aa_s, ba_s: std_logic;
signal aa_clk, aa_ena, aa_clr, aa_pre: std_logic;
signal ba_clk, ba_ena, ba_clr, ba_pre: std_logic;
 
begin
mux_signal <= i_mux_signal;
idle_s <= not (a_cyc_i or b_cyc_i);
aa_clr <= rst_i or not a_cyc_i;
aa_clk <= a_cyc_i;
aa_ena <= not b_cyc_i and priority;
aa_pre <= (a_cyc_i and not priority and not ba_s) or (a_cyc_i and not b_cyc_i);
aa_ff: d_ff port map (
d => '1',
clk => aa_clk,
ena => aa_ena,
clr => aa_clr,
pre => aa_pre,
q => aa_s
);
ba_clr <= rst_i or not b_cyc_i;
ba_clk <= b_cyc_i;
ba_ena <= not a_cyc_i and not priority;
ba_pre <= (b_cyc_i and priority and not aa_s) or (b_cyc_i and not a_cyc_i);
ba_ff: d_ff port map (
d => '1',
clk => ba_clk,
ena => ba_ena,
clr => ba_clr,
pre => ba_pre,
q => ba_s
);
i_mux_signal <= (priority and idle_s) or ba_s;
signal_mux: process is
begin
wait on a_we_i, a_stb_i, a_ack_oi, a_err_oi, a_rty_oi, a_cyc_i,
b_we_i, b_stb_i, b_ack_oi, b_err_oi, b_rty_oi, b_cyc_i,
s_ack_i, s_err_i, s_rty_i, i_mux_signal;
if (i_mux_signal = '0') then
s_we_o <= a_we_i;
s_stb_o <= a_stb_i;
s_cyc_o <= a_cyc_i;
a_ack_o <= (a_stb_i and s_ack_i) or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and s_err_i) or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and s_rty_i) or (not a_stb_i and a_rty_oi);
b_ack_o <= (b_stb_i and '0') or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and '0') or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and '0') or (not b_stb_i and b_rty_oi);
else
s_we_o <= b_we_i;
s_stb_o <= b_stb_i;
s_cyc_o <= b_cyc_i;
b_ack_o <= (b_stb_i and s_ack_i) or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and s_err_i) or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and s_rty_i) or (not b_stb_i and b_rty_oi);
a_ack_o <= (a_stb_i and '0') or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and '0') or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and '0') or (not a_stb_i and a_rty_oi);
end if;
end process;
gen_e_state: process is
begin
wait on idle_s,aa_s,ba_s;
if (idle_s = '1' and ba_s = '0' and aa_s = '0') then e_state <= idle;
elsif (idle_s = '0' and ba_s = '1' and aa_s = '0') then e_state <= aa;
elsif (idle_s = '0' and ba_s = '0' and aa_s = '1') then e_state <= ba;
else e_state <= XX;
end if;
end process;
end FPGA;
 
/trunk/wb_async_master.vhd
0,0 → 1,127
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_async_master: async bus master to Wishbone bus bridge.
 
-------------------------------------------------------------------------------
--
-- wb_async_master
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library wb_tk;
use wb_tk.technology.all;
 
entity wb_async_master is
generic (
width: positive := 16;
addr_width: positive := 20
);
port (
clk_i: in std_logic;
rst_i: in std_logic := '0';
-- interface to wb slave devices
s_adr_o: out std_logic_vector (addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((width/8)-1 downto 0);
s_dat_i: in std_logic_vector (width-1 downto 0);
s_dat_o: out std_logic_vector (width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic;
 
-- interface to asyncron master device
a_data: inout std_logic_vector (width-1 downto 0) := (others => 'Z');
a_addr: in std_logic_vector (addr_width-1 downto 0) := (others => 'U');
a_rdn: in std_logic := '1';
a_wrn: in std_logic := '1';
a_cen: in std_logic := '1';
a_byen: in std_logic_vector ((width/8)-1 downto 0);
a_waitn: out std_logic
);
end wb_async_master;
 
architecture wb_async_master of wb_async_master is
component d_ff
port ( d : in STD_LOGIC;
clk: in STD_LOGIC;
ena: in STD_LOGIC := '1';
clr: in STD_LOGIC := '0';
pre: in STD_LOGIC := '0';
q : out STD_LOGIC
);
end component;
signal wg_clk, wg_pre, wg_q: std_logic;
signal i_cyc_o, i_stb_o, i_we_o: std_logic;
signal i_waitn: std_logic;
begin
ctrl: process is
begin
wait until clk_i'EVENT and clk_i = '1';
if (rst_i = '1') then
i_cyc_o <= '0';
i_stb_o <= '0';
i_we_o <= '0';
else
if (a_cen = '0') then
i_stb_o <= not (a_rdn and a_wrn);
i_we_o <= not a_wrn;
i_cyc_o <= '1';
else
i_cyc_o <= '0';
i_stb_o <= '0';
i_we_o <= '0';
end if;
end if;
end process;
s_cyc_o <= i_cyc_o and not i_waitn;
s_stb_o <= i_stb_o and not i_waitn;
s_we_o <= i_we_o and not i_waitn;
 
w_ff1: d_ff port map (
d => s_ack_i,
clk => clk_i,
ena => '1',
clr => rst_i,
pre => '0',
q => wg_q
);
wg_clk <= not a_cen;
wg_pre <= wg_q or rst_i;
w_ff2: d_ff port map (
d => '0',
clk => wg_clk,
ena => '1',
clr => '0',
pre => wg_pre,
q => i_waitn
);
a_waitn <= i_waitn;
 
s_adr_o <= a_addr;
negate: for i in s_sel_o'RANGE generate s_sel_o(i) <= not a_byen(i); end generate;
s_dat_o <= a_data;
 
a_data_out: process is
begin
wait on s_dat_i, a_rdn, a_cen;
if (a_rdn = '0' and a_cen = '0') then
a_data <= s_dat_i;
else
a_data <= (others => 'Z');
end if;
end process;
end wb_async_master;
 
/trunk/wb_bus_upsize.vhd
0,0 → 1,111
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_bus_upsize: bus upsizer.
 
-------------------------------------------------------------------------------
--
-- wb_bus_upsize
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library wb_tk;
use wb_tk.technology.all;
 
entity wb_bus_upsize is
generic (
m_bus_width: positive := 8; -- master bus width
m_addr_width: positive := 21; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 20; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
 
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
 
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end wb_bus_upsize;
 
architecture wb_bus_upsize of wb_bus_upsize is
constant addr_diff: integer := log2(s_bus_width/m_bus_width);
signal i_m_dat_o: std_logic_vector(m_bus_width-1 downto 0);
begin
assert (m_addr_width = s_addr_width+addr_diff) report "Address widths are not consistent" severity FAILURE;
s_adr_o <= m_adr_i(m_addr_width-addr_diff downto addr_diff);
s_we_o <= m_we_i;
m_ack_o <= (m_stb_i and s_ack_i) or (not m_stb_i and m_ack_oi);
m_err_o <= (m_stb_i and s_err_i) or (not m_stb_i and m_err_oi);
m_rty_o <= (m_stb_i and s_rty_i) or (not m_stb_i and m_rty_oi);
s_stb_o <= m_stb_i;
s_cyc_o <= m_cyc_i;
 
sel_dat_mux: process is
begin
wait on s_dat_i, m_adr_i;
if (little_endien) then
for i in s_sel_o'RANGE loop
if (equ(m_adr_i(addr_diff-1 downto 0),i)) then
s_sel_o(i) <= '1';
i_m_dat_o <= s_dat_i(8*i+7 downto 8*i+0);
else
s_sel_o(i) <= '0';
end if;
end loop;
else
for i in s_sel_o'RANGE loop
if (equ(m_adr_i(addr_diff-1 downto 0),i)) then
s_sel_o(s_sel_o'HIGH-i) <= '1';
i_m_dat_o <= s_dat_i(s_dat_i'HIGH-8*i downto s_dat_i'HIGH-8*i-7);
else
s_sel_o(s_sel_o'HIGH-i) <= '0';
end if;
end loop;
end if;
end process;
 
d_i_for: for i in m_dat_o'RANGE generate
m_dat_o(i) <= (m_stb_i and i_m_dat_o(i)) or (not m_stb_i and m_dat_oi(i));
end generate;
 
d_o_for: for i in s_sel_o'RANGE generate
s_dat_o(8*i+7 downto 8*i+0) <= m_dat_i;
end generate;
end wb_bus_upsize;
 
/trunk/compile.sh
0,0 → 1,78
#!/bin/bash
#
# Script to compile sources to a library using Active HDL
# (c) Copyright Andras Tantos <tantos@opencores.org> 2001/04/25
# This code is distributed under the terms and conditions of the GNU General Public Lince.
#
# USAGE:
#
# Set APATH to the installation directory of ActiveHDL and
# LIB to whatever name your library has
# RESULT_PATH to where generated files you wish to be put
# Also make sure that you upadted the Library.cfg file to contain
# the specified library name.
# After the common part, list all files you wish to include in your library
# with 'compile_file' preciding the file name.
#
# NOTES:
#
# This script depends on the following executables:
# bash
# cat
# rm
# mv
# mkdir
# echo
# test
# they are available under all UNIX-es and can be installed for windows
# and DOS too. The windows version of these files can be obtained from
# GNU Cygnus distribution (http://sources.redhat.com/cygwin)
# The minimal package of these utilities are also available from
# OpenCores web-site.
 
APATH=C:/CAED/ActiveHDL.36/
LIB=wb_tk
RESULT_PATH=ahdl
 
# ___________Common part of the script____________
 
LIB_FILE=$RESULT_PATH/$LIB.lib
CMP_FILE=$RESULT_PATH/0.mgf
CMP=$APATH/bin/acombat.exe
CMP_FLAGS="-avhdl $APATH -lib $LIB -93"
 
compile_file() {
LOG_FILE=$1
LOG_FILE=$RESULT_PATH/${LOG_FILE/.vhd/.rlt}
ERR_FILE=${LOG_FILE/.rtl/.err}
rm -f $LOG_FILE
rm -f $ERR_FILE
$CMP $CMP_FLAGS -log $LOG_FILE $1 || {
mv $LOG_FILE $ERR_FILE
cat $ERR_FILE
exit 1
}
cat $LOG_FILE
}
 
if test ! -d $RESULT_PATH; then
mkdir $RESULT_PATH
fi
rm -f $RESULT_PATH/*
if test ! -f $LIB_FILE; then
echo > $LIB_FILE
fi
# ___________End of common part of the script____________
 
compile_file technology.vhd
compile_file wb_arbiter.vhd
compile_file wb_async_master.vhd
compile_file wb_async_slave.vhd
compile_file wb_bus_dnsize.vhd
compile_file wb_bus_upsize.vhd
compile_file wb_bus_resize.vhd
compile_file wb_out_reg.vhd
compile_file wb_ram.vhd
compile_file wb_test.vhd
compile_file wb_tk.vhd
 
/trunk/wb_bus_resize.vhd
0,0 → 1,249
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_bus_resize: bus resizer.
 
-------------------------------------------------------------------------------
--
-- wb_bus_resize
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library wb_tk;
use wb_tk.technology.all;
use wb_tk.all;
 
entity wb_bus_resize is
generic (
m_bus_width: positive := 32; -- master bus width
m_addr_width: positive := 19; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 20; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
 
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
 
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end wb_bus_resize;
 
architecture wb_bus_resize of wb_bus_resize is
component wb_bus_upsize is
generic (
m_bus_width: positive := 8; -- master bus width
m_addr_width: positive := 21; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 20; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end component;
 
component wb_bus_dnsize is
generic (
m_bus_width: positive := 32; -- master bus width
m_addr_width: positive := 20; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 21; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end component;
begin
dn_sel: if (m_bus_width > s_bus_width) generate
dnsizer: wb_bus_dnsize
generic map (
m_bus_width => m_bus_width,
m_addr_width => m_addr_width,
s_bus_width => s_bus_width,
s_addr_width => s_addr_width,
little_endien => little_endien
)
port map
(m_adr_i => m_adr_i,
m_sel_i => m_sel_i,
m_dat_i => m_dat_i,
m_dat_oi => m_dat_oi,
m_dat_o => m_dat_o,
m_cyc_i => m_cyc_i,
m_ack_o => m_ack_o,
m_ack_oi => m_ack_oi,
m_err_o => m_err_o,
m_err_oi => m_err_oi,
m_rty_o => m_rty_o,
m_rty_oi => m_rty_oi,
m_we_i => m_we_i,
m_stb_i => m_stb_i,
s_adr_o => s_adr_o,
s_sel_o => s_sel_o,
s_dat_i => s_dat_i,
s_dat_o => s_dat_o,
s_cyc_o => s_cyc_o,
s_ack_i => s_ack_i,
s_err_i => s_err_i,
s_rty_i => s_rty_i,
s_we_o => s_we_o,
s_stb_o => s_stb_o
);
end generate;
up_sel: if (m_bus_width < s_bus_width) generate
upsizer: wb_bus_upsize
generic map (
m_bus_width => m_bus_width,
m_addr_width => m_addr_width,
s_bus_width => s_bus_width,
s_addr_width => s_addr_width,
little_endien => little_endien
)
port map
(m_adr_i => m_adr_i,
m_sel_i => m_sel_i,
m_dat_i => m_dat_i,
m_dat_oi => m_dat_oi,
m_dat_o => m_dat_o,
m_cyc_i => m_cyc_i,
m_ack_o => m_ack_o,
m_ack_oi => m_ack_oi,
m_err_o => m_err_o,
m_err_oi => m_err_oi,
m_rty_o => m_rty_o,
m_rty_oi => m_rty_oi,
m_we_i => m_we_i,
m_stb_i => m_stb_i,
s_adr_o => s_adr_o,
s_sel_o => s_sel_o,
s_dat_i => s_dat_i,
s_dat_o => s_dat_o,
s_cyc_o => s_cyc_o,
s_ack_i => s_ack_i,
s_err_i => s_err_i,
s_rty_i => s_rty_i,
s_we_o => s_we_o,
s_stb_o => s_stb_o
);
end generate;
eq_sel: if (m_bus_width = s_bus_width) generate
dat_o_for: for i in m_dat_o'RANGE generate
dat_o_gen: m_dat_o(i) <= (s_dat_i(i) and m_stb_i and not m_we_i) or (m_dat_oi(i) and not (m_stb_i and not m_we_i));
end generate;
m_ack_o <= (s_ack_i and m_stb_i and not m_we_i) or (m_ack_oi and not (m_stb_i and not m_we_i));
m_err_o <= (s_err_i and m_stb_i and not m_we_i) or (m_err_oi and not (m_stb_i and not m_we_i));
m_rty_o <= (s_rty_i and m_stb_i and not m_we_i) or (m_rty_oi and not (m_stb_i and not m_we_i));
s_adr_o <= m_adr_i;
s_sel_o <= m_sel_i;
s_dat_o <= m_dat_i;
s_cyc_o <= m_cyc_i;
s_we_o <= m_we_i;
s_stb_o <= m_stb_i;
end generate;
end wb_bus_resize;
 
--configuration c_wb_bus_resize of wb_bus_resize is
-- for wb_bus_resize
-- for dnsizer: wb_bus_dnsize
-- use entity wb_bus_dnsize(wb_bus_dnsize);
-- end for;
-- for upsizer: wb_bus_upsize
-- use entity wb_bus_upsize(wb_bus_upsize);
-- end for;
-- end for;
--end c_wb_bus_resize;
 
/trunk/wb_tk.vhd
10,9 → 10,12
-- wb_async_slave: Wishbone bus to async (SRAM-like) bus slave bridge.
-- wb_arbiter: two-way bus arbiter. Asyncronous logic ensures 0-ws operation on shared bus
-- wb_out_reg: Wishbone bus compatible output register.
-- wb_bus_resize: Wishbone bus resizer.
 
library IEEE;
use IEEE.std_logic_1164.all;
library wb_tk;
use wb_tk.technology.all;
 
package wb_tk is
component wb_bus_upsize is
56,7 → 59,91
s_stb_o: out std_logic
);
end component;
 
component wb_bus_dnsize is
generic (
m_bus_width: positive := 32; -- master bus width
m_addr_width: positive := 20; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 21; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end component;
component wb_bus_resize is
generic (
m_bus_width: positive := 32; -- master bus width
m_addr_width: positive := 20; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 21; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end component;
component wb_async_master is
generic (
width: positive := 16;
166,749 → 253,28
end component;
component wb_out_reg is
generic (
width : positive := 8;
bus_width: positive := 8;
offset: integer := 0
);
port (
clk_i: in std_logic;
rst_i: in std_logic;
rst_val: std_logic_vector(width-1 downto 0) := (others => '0');
dat_i: in std_logic_vector (bus_width-1 downto 0);
dat_oi: in std_logic_vector (bus_width-1 downto 0) := (others => '-');
dat_o: out std_logic_vector (bus_width-1 downto 0);
q: out std_logic_vector (width-1 downto 0);
we_i: in std_logic;
stb_i: in std_logic;
ack_o: out std_logic;
ack_oi: in std_logic := '-'
);
generic (
width : positive := 8;
bus_width: positive := 8;
offset: integer := 0
);
port (
clk_i: in std_logic;
rst_i: in std_logic;
rst_val: std_logic_vector(width-1 downto 0) := (others => '0');
cyc_i: in std_logic := '1';
stb_i: in std_logic;
sel_i: in std_logic_vector ((bus_width/8)-1 downto 0) := (others => '1');
we_i: in std_logic;
ack_o: out std_logic;
ack_oi: in std_logic := '-';
adr_i: in std_logic_vector (size2bits((width+offset+bus_width-1)/bus_width)-1 downto 0) := (others => '0');
dat_i: in std_logic_vector (bus_width-1 downto 0);
dat_oi: in std_logic_vector (bus_width-1 downto 0) := (others => '-');
dat_o: out std_logic_vector (bus_width-1 downto 0);
q: out std_logic_vector (width-1 downto 0)
);
end component;
end wb_tk;
 
-------------------------------------------------------------------------------
--
-- wb_bus_upsize
--
-------------------------------------------------------------------------------
 
library IEEE;
library synopsys;
use IEEE.std_logic_1164.all;
use synopsys.std_logic_arith.all;
 
library work;
use work.technology.all;
 
entity wb_bus_upsize is
generic (
m_bus_width: positive := 8; -- master bus width
m_addr_width: positive := 21; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 20; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
 
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
 
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end wb_bus_upsize;
 
architecture wb_bus_upsize of wb_bus_upsize is
function log2(inp : integer) return integer is
begin
if (inp < 1) then return 0; end if;
if (inp < 2) then return 0; end if;
if (inp < 4) then return 1; end if;
if (inp < 8) then return 2; end if;
if (inp < 16) then return 3; end if;
if (inp < 32) then return 4; end if;
if (inp < 64) then return 5; end if;
if (inp < 128) then return 6; end if;
if (inp < 256) then return 7; end if;
if (inp < 512) then return 8; end if;
if (inp < 1024) then return 9; end if;
if (inp < 2048) then return 10; end if;
if (inp < 4096) then return 11; end if;
if (inp < 8192) then return 12; end if;
if (inp < 16384) then return 13; end if;
if (inp < 32768) then return 14; end if;
if (inp < 65538) then return 15; end if;
return 16;
end;
function equ(a : std_logic_vector; b : integer) return boolean is
variable b_s : std_logic_vector(a'RANGE);
begin
b_s := CONV_STD_LOGIC_VECTOR(b,a'HIGH+1);
return (a = b_s);
end;
constant addr_diff: integer := log2(s_bus_width/m_bus_width);
signal i_m_dat_o: std_logic_vector(m_bus_width-1 downto 0);
begin
assert (m_addr_width = s_addr_width+addr_diff) report "Address widths are not consistent" severity FAILURE;
s_adr_o <= m_adr_i(m_addr_width-addr_diff downto addr_diff);
s_we_o <= m_we_i;
m_ack_o <= (m_stb_i and s_ack_i) or (not m_stb_i and m_ack_oi);
m_err_o <= (m_stb_i and s_err_i) or (not m_stb_i and m_err_oi);
m_rty_o <= (m_stb_i and s_rty_i) or (not m_stb_i and m_rty_oi);
s_stb_o <= m_stb_i;
s_cyc_o <= m_cyc_i;
 
sel_dat_mux: process is
begin
wait on s_dat_i, m_adr_i;
if (little_endien) then
for i in s_sel_o'RANGE loop
if (equ(m_adr_i(addr_diff-1 downto 0),i)) then
s_sel_o(i) <= '1';
i_m_dat_o <= s_dat_i(8*i+7 downto 8*i+0);
else
s_sel_o(i) <= '0';
end if;
end loop;
else
for i in s_sel_o'RANGE loop
if (equ(m_adr_i(addr_diff-1 downto 0),i)) then
s_sel_o(s_sel_o'HIGH-i) <= '1';
i_m_dat_o <= s_dat_i(s_dat_i'HIGH-8*i downto s_dat_i'HIGH-8*i-7);
else
s_sel_o(s_sel_o'HIGH-i) <= '0';
end if;
end loop;
end if;
end process;
 
d_i_for: for i in m_dat_o'RANGE generate
m_dat_o(i) <= (m_stb_i and i_m_dat_o(i)) or (not m_stb_i and m_dat_oi(i));
end generate;
 
d_o_for: for i in s_sel_o'RANGE generate
s_dat_o(8*i+7 downto 8*i+0) <= m_dat_i;
end generate;
end wb_bus_upsize;
 
-------------------------------------------------------------------------------
--
-- wb_async_master
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library work;
use work.technology.all;
 
entity wb_async_master is
generic (
width: positive := 16;
addr_width: positive := 20
);
port (
clk_i: in std_logic;
rst_i: in std_logic := '0';
-- interface to wb slave devices
s_adr_o: out std_logic_vector (addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((width/8)-1 downto 0);
s_dat_i: in std_logic_vector (width-1 downto 0);
s_dat_o: out std_logic_vector (width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic;
 
-- interface to asyncron master device
a_data: inout std_logic_vector (width-1 downto 0) := (others => 'Z');
a_addr: in std_logic_vector (addr_width-1 downto 0) := (others => 'U');
a_rdn: in std_logic := '1';
a_wrn: in std_logic := '1';
a_cen: in std_logic := '1';
a_byen: in std_logic_vector ((width/8)-1 downto 0);
a_waitn: out std_logic
);
end wb_async_master;
 
architecture wb_async_master of wb_async_master is
component d_ff
port ( d : in STD_LOGIC;
clk: in STD_LOGIC;
ena: in STD_LOGIC := '1';
clr: in STD_LOGIC := '0';
pre: in STD_LOGIC := '0';
q : out STD_LOGIC
);
end component;
signal wg_clk, wg_pre, wg_q: std_logic;
signal i_cyc_o, i_stb_o, i_we_o: std_logic;
signal i_waitn: std_logic;
begin
ctrl: process is
begin
wait until clk_i'EVENT and clk_i = '1';
if (rst_i = '1') then
i_cyc_o <= '0';
i_stb_o <= '0';
i_we_o <= '0';
else
if (a_cen = '0') then
i_stb_o <= not (a_rdn and a_wrn);
i_we_o <= not a_wrn;
i_cyc_o <= '1';
else
i_cyc_o <= '0';
i_stb_o <= '0';
i_we_o <= '0';
end if;
end if;
end process;
s_cyc_o <= i_cyc_o and not i_waitn;
s_stb_o <= i_stb_o and not i_waitn;
s_we_o <= i_we_o and not i_waitn;
 
w_ff1: d_ff port map (
d => s_ack_i,
clk => clk_i,
ena => '1',
clr => rst_i,
pre => '0',
q => wg_q
);
wg_clk <= not a_cen;
wg_pre <= wg_q or rst_i;
w_ff2: d_ff port map (
d => '0',
clk => wg_clk,
ena => '1',
clr => '0',
pre => wg_pre,
q => i_waitn
);
a_waitn <= i_waitn;
 
s_adr_o <= a_addr;
negate: for i in s_sel_o'RANGE generate s_sel_o(i) <= not a_byen(i); end generate;
s_dat_o <= a_data;
 
a_data_out: process is
begin
wait on s_dat_i, a_rdn, a_cen;
if (a_rdn = '0' and a_cen = '0') then
a_data <= s_dat_i;
else
a_data <= (others => 'Z');
end if;
end process;
end wb_async_master;
 
-------------------------------------------------------------------------------
--
-- wb_async_slave
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library work;
use work.technology.all;
 
entity wb_async_slave is
generic (
width: positive := 16;
addr_width: positive := 20
);
port (
clk_i: in std_logic;
rst_i: in std_logic := '0';
-- interface for wait-state generator state-machine
wait_state: in std_logic_vector (3 downto 0);
 
-- interface to wishbone master device
adr_i: in std_logic_vector (addr_width-1 downto 0);
sel_i: in std_logic_vector ((addr_width/8)-1 downto 0);
dat_i: in std_logic_vector (width-1 downto 0);
dat_o: out std_logic_vector (width-1 downto 0);
dat_oi: in std_logic_vector (width-1 downto 0) := (others => '-');
we_i: in std_logic;
stb_i: in std_logic;
ack_o: out std_logic := '0';
ack_oi: in std_logic := '-';
-- interface to async slave
a_data: inout std_logic_vector (width-1 downto 0) := (others => 'Z');
a_addr: out std_logic_vector (addr_width-1 downto 0) := (others => 'U');
a_rdn: out std_logic := '1';
a_wrn: out std_logic := '1';
a_cen: out std_logic := '1';
-- byte-enable signals
a_byen: out std_logic_vector ((width/8)-1 downto 0)
);
end wb_async_slave;
 
architecture wb_async_slave of wb_async_slave is
-- multiplexed access signals to memory
signal i_ack: std_logic;
signal sm_ack: std_logic;
 
type states is (sm_idle, sm_wait, sm_deact);
signal state: states;
signal cnt: std_logic_vector(3 downto 0);
begin
ack_o <= (stb_i and i_ack) or (not stb_i and ack_oi);
dat_o_gen: for i in dat_o'RANGE generate
dat_o(i) <= (stb_i and a_data(i)) or (not stb_i and dat_oi(i));
end generate;
-- For 0WS operation i_ack is an async signal otherwise it's a sync one.
i_ack_gen: process is
begin
wait on sm_ack, stb_i, wait_state, state;
if (wait_state = "0000") then
case (state) is
when sm_deact => i_ack <= '0';
when others => i_ack <= stb_i;
end case;
else
i_ack <= sm_ack;
end if;
end process;
-- SRAM signal-handler process
sram_signals: process is
begin
wait on state,we_i,a_data,adr_i,rst_i, stb_i, sel_i, dat_i;
if (rst_i = '1') then
a_wrn <= '1';
a_rdn <= '1';
a_cen <= '1';
a_addr <= (others => '-');
a_data <= (others => 'Z');
a_byen <= (others => '1');
else
case (state) is
when sm_deact =>
a_wrn <= '1';
a_rdn <= '1';
a_cen <= '1';
a_addr <= (others => '-');
a_data <= (others => 'Z');
a_byen <= (others => '1');
when others =>
a_addr <= adr_i;
a_rdn <= not (not we_i and stb_i);
a_wrn <= not (we_i and stb_i);
a_cen <= not stb_i;
a_byen <= not sel_i;
if (we_i = '1') then
a_data <= dat_i;
else
a_data <= (others => 'Z');
end if;
end case;
end if;
end process;
 
-- Aysnc access state-machine.
async_sm: process is
-- variable cnt: std_logic_vector(3 downto 0) := "0000";
-- variable state: states := init;
begin
wait until clk_i'EVENT and clk_i = '1';
if (rst_i = '1') then
state <= sm_idle;
cnt <= ((0) => '1', others => '0');
sm_ack <= '0';
else
case (state) is
when sm_idle =>
-- Check if anyone needs access to the memory.
-- it's rdy signal will already be pulled low, so we only have to start the access
if (stb_i = '1') then
case wait_state is
when "0000" =>
sm_ack <= '1';
state <= sm_deact;
when "0001" =>
sm_ack <= '1';
cnt <= "0001";
state <= sm_wait;
when others =>
sm_ack <= '0';
cnt <= "0001";
state <= sm_wait;
end case;
end if;
when sm_wait =>
if (cnt = wait_state) then
-- wait cycle completed.
state <= sm_deact;
sm_ack <= '0';
cnt <= "0000";
else
if (add_one(cnt) = wait_state) then
sm_ack <= '1';
else
sm_ack <= '0';
end if;
cnt <= add_one(cnt);
end if;
when sm_deact =>
if (stb_i = '1') then
case wait_state is
when "0000" =>
cnt <= "0000";
sm_ack <= '0';
state <= sm_wait;
when others =>
sm_ack <= '0';
cnt <= "0000";
state <= sm_wait;
end case;
else
sm_ack <= '0';
state <= sm_idle;
end if;
end case;
end if;
end process;
end wb_async_slave;
 
-------------------------------------------------------------------------------
--
-- wb_arbiter
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library work;
use work.technology.all;
 
entity wb_arbiter is
port (
-- clk: in std_logic;
rst_i: in std_logic := '0';
-- interface to master device a
a_we_i: in std_logic;
a_stb_i: in std_logic;
a_cyc_i: in std_logic;
a_ack_o: out std_logic;
a_ack_oi: in std_logic := '-';
a_err_o: out std_logic;
a_err_oi: in std_logic := '-';
a_rty_o: out std_logic;
a_rty_oi: in std_logic := '-';
-- interface to master device b
b_we_i: in std_logic;
b_stb_i: in std_logic;
b_cyc_i: in std_logic;
b_ack_o: out std_logic;
b_ack_oi: in std_logic := '-';
b_err_o: out std_logic;
b_err_oi: in std_logic := '-';
b_rty_o: out std_logic;
b_rty_oi: in std_logic := '-';
 
-- interface to shared devices
s_we_o: out std_logic;
s_stb_o: out std_logic;
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
mux_signal: out std_logic; -- 0: select A signals, 1: select B signals
 
-- misc control lines
priority: in std_logic -- 0: A have priority over B, 1: B have priority over A
);
end wb_arbiter;
 
-- This acthitecture is a clean asyncron state-machine. However it cannot be mapped to FPGA architecture
architecture behaviour of wb_arbiter is
type states is (idle,aa,ba);
signal i_mux_signal: std_logic;
signal e_state: states;
begin
mux_signal <= i_mux_signal;
sm: process is
variable state: states;
begin
wait on a_cyc_i, b_cyc_i, priority, rst_i;
if (rst_i = '1') then
state := idle;
i_mux_signal <= priority;
else
case (state) is
when idle =>
if (a_cyc_i = '1' and (priority = '0' or b_cyc_i = '0')) then
state := aa;
i_mux_signal <= '0';
elsif (b_cyc_i = '1' and (priority = '1' or a_cyc_i = '0')) then
state := ba;
i_mux_signal <= '1';
else
i_mux_signal <= priority;
end if;
when aa =>
if (a_cyc_i = '0') then
if (b_cyc_i = '1') then
state := ba;
i_mux_signal <= '1';
else
state := idle;
i_mux_signal <= priority;
end if;
else
i_mux_signal <= '0';
end if;
when ba =>
if (b_cyc_i = '0') then
if (a_cyc_i = '1') then
state := aa;
i_mux_signal <= '0';
else
state := idle;
i_mux_signal <= priority;
end if;
else
i_mux_signal <= '1';
end if;
end case;
end if;
e_state <= state;
end process;
signal_mux: process is
begin
wait on a_we_i, a_stb_i, a_ack_oi, a_err_oi, a_rty_oi, a_cyc_i,
b_we_i, b_stb_i, b_ack_oi, b_err_oi, b_rty_oi, b_cyc_i,
s_ack_i, s_err_i, s_rty_i, i_mux_signal;
if (i_mux_signal = '0') then
s_we_o <= a_we_i;
s_stb_o <= a_stb_i;
s_cyc_o <= a_cyc_i;
a_ack_o <= (a_stb_i and s_ack_i) or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and s_err_i) or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and s_rty_i) or (not a_stb_i and a_rty_oi);
b_ack_o <= (b_stb_i and '0') or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and '0') or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and '0') or (not b_stb_i and b_rty_oi);
else
s_we_o <= b_we_i;
s_stb_o <= b_stb_i;
s_cyc_o <= b_cyc_i;
b_ack_o <= (b_stb_i and s_ack_i) or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and s_err_i) or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and s_rty_i) or (not b_stb_i and b_rty_oi);
a_ack_o <= (a_stb_i and '0') or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and '0') or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and '0') or (not a_stb_i and a_rty_oi);
end if;
end process;
end behaviour;
 
-- This acthitecture is a more-or-less structural implementation. Fits for FPGA realization.
architecture FPGA of wb_arbiter is
component d_ff
port ( d : in STD_LOGIC;
clk: in STD_LOGIC;
ena: in STD_LOGIC := '1';
clr: in STD_LOGIC := '0';
pre: in STD_LOGIC := '0';
q : out STD_LOGIC
);
end component;
signal i_mux_signal: std_logic;
type states is (idle,aa,ba,XX);
signal e_state: states;
 
-- signals for a DFF in FPGA
signal idle_s, aa_s, ba_s: std_logic;
signal aa_clk, aa_ena, aa_clr, aa_pre: std_logic;
signal ba_clk, ba_ena, ba_clr, ba_pre: std_logic;
 
begin
mux_signal <= i_mux_signal;
idle_s <= not (a_cyc_i or b_cyc_i);
aa_clr <= rst_i or not a_cyc_i;
aa_clk <= a_cyc_i;
aa_ena <= not b_cyc_i and priority;
aa_pre <= (a_cyc_i and not priority and not ba_s) or (a_cyc_i and not b_cyc_i);
aa_ff: d_ff port map (
d => '1',
clk => aa_clk,
ena => aa_ena,
clr => aa_clr,
pre => aa_pre,
q => aa_s
);
ba_clr <= rst_i or not b_cyc_i;
ba_clk <= b_cyc_i;
ba_ena <= not a_cyc_i and not priority;
ba_pre <= (b_cyc_i and priority and not aa_s) or (b_cyc_i and not a_cyc_i);
ba_ff: d_ff port map (
d => '1',
clk => ba_clk,
ena => ba_ena,
clr => ba_clr,
pre => ba_pre,
q => ba_s
);
i_mux_signal <= (priority and idle_s) or ba_s;
signal_mux: process is
begin
wait on a_we_i, a_stb_i, a_ack_oi, a_err_oi, a_rty_oi, a_cyc_i,
b_we_i, b_stb_i, b_ack_oi, b_err_oi, b_rty_oi, b_cyc_i,
s_ack_i, s_err_i, s_rty_i, i_mux_signal;
if (i_mux_signal = '0') then
s_we_o <= a_we_i;
s_stb_o <= a_stb_i;
s_cyc_o <= a_cyc_i;
a_ack_o <= (a_stb_i and s_ack_i) or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and s_err_i) or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and s_rty_i) or (not a_stb_i and a_rty_oi);
b_ack_o <= (b_stb_i and '0') or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and '0') or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and '0') or (not b_stb_i and b_rty_oi);
else
s_we_o <= b_we_i;
s_stb_o <= b_stb_i;
s_cyc_o <= b_cyc_i;
b_ack_o <= (b_stb_i and s_ack_i) or (not b_stb_i and b_ack_oi);
b_err_o <= (b_stb_i and s_err_i) or (not b_stb_i and b_err_oi);
b_rty_o <= (b_stb_i and s_rty_i) or (not b_stb_i and b_rty_oi);
a_ack_o <= (a_stb_i and '0') or (not a_stb_i and a_ack_oi);
a_err_o <= (a_stb_i and '0') or (not a_stb_i and a_err_oi);
a_rty_o <= (a_stb_i and '0') or (not a_stb_i and a_rty_oi);
end if;
end process;
gen_e_state: process is
begin
wait on idle_s,aa_s,ba_s;
if (idle_s = '1' and ba_s = '0' and aa_s = '0') then e_state <= idle;
elsif (idle_s = '0' and ba_s = '1' and aa_s = '0') then e_state <= aa;
elsif (idle_s = '0' and ba_s = '0' and aa_s = '1') then e_state <= ba;
else e_state <= XX;
end if;
end process;
end FPGA;
 
-------------------------------------------------------------------------------
--
-- wb_out_reg
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library work;
use work.technology.all;
 
entity wb_out_reg is
generic (
width : positive := 8;
bus_width: positive := 8;
offset: integer := 0
);
port (
clk_i: in std_logic;
rst_i: in std_logic;
rst_val: std_logic_vector(width-1 downto 0) := (others => '0');
 
dat_i: in std_logic_vector (bus_width-1 downto 0);
dat_oi: in std_logic_vector (bus_width-1 downto 0) := (others => '-');
dat_o: out std_logic_vector (bus_width-1 downto 0);
q: out std_logic_vector (width-1 downto 0);
we_i: in std_logic;
stb_i: in std_logic;
ack_o: out std_logic;
ack_oi: in std_logic := '-'
);
end wb_out_reg;
 
architecture wb_out_reg of wb_out_reg is
signal content : std_logic_vector (width-1 downto 0);
begin
-- output bus handling with logic
gen_dat_o: process is
variable rd_sel: std_logic;
begin
wait on dat_oi, we_i, stb_i, content;
rd_sel := stb_i and not we_i;
for i in bus_width-1 downto 0 loop
if (i >= offset and i < offset+width) then
dat_o(i) <= (dat_oi(i) and not rd_sel) or (content(i-offset) and rd_sel);
else
dat_o(i) <= dat_oi(i);
end if;
end loop;
end process;
 
-- this item never generates any wait-states
ack_o <= stb_i or ack_oi;
reg: process is
begin
wait until clk_i'EVENT and clk_i='1';
if (rst_i = '1') then
content <= rst_val;
else
if (stb_i = '1' and we_i = '1') then
content <= dat_i(width+offset-1 downto offset);
end if;
end if;
end process;
q <= content;
end wb_out_reg;
/trunk/wb_ram.vhd
0,0 → 1,85
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_ram: ram element.
 
-------------------------------------------------------------------------------
--
-- wb_ram
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library wb_tk;
use wb_tk.technology.all;
 
entity wb_ram is
generic (
data_width: positive := 8;
addr_width: positive := 10
);
port (
clk_i: in std_logic;
-- rst_i: in std_logic := '0';
adr_i: in std_logic_vector (addr_width-1 downto 0);
-- sel_i: in std_logic_vector ((bus_width/8)-1 downto 0) := (others => '1');
dat_i: in std_logic_vector (data_width-1 downto 0);
dat_oi: in std_logic_vector (data_width-1 downto 0) := (others => '-');
dat_o: out std_logic_vector (data_width-1 downto 0);
cyc_i: in std_logic;
ack_o: out std_logic;
ack_oi: in std_logic := '-';
-- err_o: out std_logic;
-- err_oi: in std_logic := '-';
-- rty_o: out std_logic;
-- rty_oi: in std_logic := '-';
we_i: in std_logic;
stb_i: in std_logic
);
end wb_ram;
 
architecture wb_ram of wb_ram is
component ram
generic (
data_width : positive;
addr_width : positive
);
port (
clk : in std_logic;
we : in std_logic;
addr : in std_logic_vector(addr_width-1 downto 0);
d_in : in std_logic_vector(data_width-1 downto 0);
d_out : out std_logic_vector(data_width-1 downto 0)
);
end component;
signal mem_we: std_logic;
signal mem_dat_o: std_logic_vector(data_width-1 downto 0);
begin
mem_we <= we_i and stb_i and cyc_i;
tech_ram: ram
generic map (
data_width => data_width,
addr_width => addr_width
)
port map (
clk => clk_i,
we => mem_we,
addr => adr_i,
d_in => dat_i,
d_out => mem_dat_o
);
dat_o_gen: for i in dat_o'RANGE generate
dat_o(i) <= (mem_dat_o(i) and stb_i and cyc_i and not we_i) or (dat_oi(i) and not (stb_i and cyc_i and not we_i));
end generate;
ack_o <= ('1' and stb_i and cyc_i) or (ack_oi and not (stb_i and cyc_i));
end wb_ram;
 
/trunk/wb_test.vhd
0,0 → 1,222
--
-- Wishbone bus tester utilities.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/04/17
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- procedure wr_chk_val: writes a value, reads it back an checks if it's the same
-- procedure wr_val: writes a value
-- procedure rd_val: reads a value
-- procedure chk_val: checks (after read) a value
 
library IEEE;
use IEEE.std_logic_1164.all;
 
package wb_test is
procedure wr_chk_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
constant data: in STD_LOGIC_VECTOR
);
procedure wr_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
constant data: in STD_LOGIC_VECTOR
);
procedure rd_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
variable data: out STD_LOGIC_VECTOR
);
procedure chk_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
constant data: in STD_LOGIC_VECTOR
);
end wb_test;
 
 
package body wb_test is
procedure wr_chk_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
constant data: in STD_LOGIC_VECTOR
) is
variable adr_zero: STD_LOGIC_VECTOR(adr_i'RANGE) := (others => '0');
variable dat_undef: STD_LOGIC_VECTOR(dat_i'RANGE) := (others => 'U');
begin
adr_i <= adr_zero;
dat_i <= dat_undef;
stb_i <= '0';
we_i <= '0';
cyc_i <= '0';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
adr_i <= addr;
dat_i <= data;
cyc_i <= '1';
stb_i <= '1';
we_i <= '1';
wait until clk_i'EVENT and clk_i = '1' and ack_o = '1';
adr_i <= adr_zero;
dat_i <= dat_undef;
cyc_i <= '0';
stb_i <= '0';
we_i <= '0';
wait until clk_i'EVENT and clk_i = '1';
adr_i <= addr;
dat_i <= dat_undef;
cyc_i <= '1';
stb_i <= '1';
we_i <= '0';
wait until clk_i'EVENT and clk_i = '1' and ack_o = '1';
assert dat_o = data report "Value does not match!" severity ERROR;
adr_i <= adr_zero;
stb_i <= '0';
cyc_i <= '0';
end procedure;
 
procedure wr_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
constant data: in STD_LOGIC_VECTOR
) is
variable adr_zero: STD_LOGIC_VECTOR(adr_i'RANGE) := (others => '0');
variable dat_undef: STD_LOGIC_VECTOR(dat_i'RANGE) := (others => 'U');
begin
adr_i <= adr_zero;
dat_i <= dat_undef;
stb_i <= '0';
we_i <= '0';
cyc_i <= '0';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
adr_i <= addr;
dat_i <= data;
cyc_i <= '1';
stb_i <= '1';
we_i <= '1';
wait until clk_i'EVENT and clk_i = '1' and ack_o = '1';
adr_i <= adr_zero;
dat_i <= dat_undef;
cyc_i <= '0';
stb_i <= '0';
we_i <= '0';
end procedure;
procedure rd_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
variable data: out STD_LOGIC_VECTOR
) is
variable adr_zero: STD_LOGIC_VECTOR(adr_i'RANGE) := (others => '0');
variable dat_undef: STD_LOGIC_VECTOR(dat_i'RANGE) := (others => 'U');
begin
adr_i <= adr_zero;
dat_i <= dat_undef;
cyc_i <= '0';
stb_i <= '0';
we_i <= '0';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
adr_i <= addr;
dat_i <= dat_undef;
cyc_i <= '1';
stb_i <= '1';
we_i <= '0';
wait until clk_i'EVENT and clk_i = '1' and ack_o = '1';
data := dat_o;
adr_i <= adr_zero;
stb_i <= '0';
cyc_i <= '0';
end procedure;
procedure chk_val(
signal clk_i: in STD_LOGIC;
signal adr_i: out STD_LOGIC_VECTOR;
signal dat_o: in STD_LOGIC_VECTOR;
signal dat_i: out STD_LOGIC_VECTOR;
signal we_i: out STD_LOGIC;
signal cyc_i: out std_logic;
signal stb_i: out STD_LOGIC;
signal ack_o: in STD_LOGIC;
constant addr: in STD_LOGIC_VECTOR;
constant data: in STD_LOGIC_VECTOR
) is
variable adr_zero: STD_LOGIC_VECTOR(adr_i'RANGE) := (others => '0');
variable dat_undef: STD_LOGIC_VECTOR(dat_i'RANGE) := (others => 'U');
begin
adr_i <= adr_zero;
dat_i <= dat_undef;
cyc_i <= '0';
stb_i <= '0';
we_i <= '0';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
wait until clk_i'EVENT and clk_i = '1';
adr_i <= addr;
dat_i <= dat_undef;
cyc_i <= '1';
stb_i <= '1';
we_i <= '0';
wait until clk_i'EVENT and clk_i = '1' and ack_o = '1';
assert dat_o = data report "Value does not match!" severity ERROR;
adr_i <= adr_zero;
stb_i <= '0';
cyc_i <= '0';
end procedure;
end package body wb_test;
/trunk/technology.vhd
16,6 → 16,11
function sl(l: std_logic_vector; r: integer) return std_logic_vector;
-- procedure inc(data : inout std_logic_vector);
function "+"(op_l, op_r: std_logic_vector) return std_logic_vector;
function log2(inp : integer) return integer;
function size2bits(inp : integer) return integer;
function max(a : integer; b: integer) return integer;
function min(a : integer; b: integer) return integer;
function equ(a : std_logic_vector; b : integer) return boolean;
 
component d_ff is
port ( d : in STD_LOGIC;
49,6 → 54,8
use IEEE.std_logic_1164.all;
library exemplar;
use exemplar.exemplar_1164.all;
library synopsys;
use synopsys.std_logic_arith.all;
 
package body technology is
function "+"(op_l, op_r: std_logic_vector) return std_logic_vector is
77,6 → 84,69
-- begin
-- data := addone(data);
-- end;
function max(a : integer; b: integer) return integer is
begin
if (a > b) then return a; end if;
return b;
end;
function min(a : integer; b: integer) return integer is
begin
if (a < b) then return a; end if;
return b;
end;
function log2(inp : integer) return integer is
begin
if (inp < 1) then return 0; end if;
if (inp < 2) then return 0; end if;
if (inp < 4) then return 1; end if;
if (inp < 8) then return 2; end if;
if (inp < 16) then return 3; end if;
if (inp < 32) then return 4; end if;
if (inp < 64) then return 5; end if;
if (inp < 128) then return 6; end if;
if (inp < 256) then return 7; end if;
if (inp < 512) then return 8; end if;
if (inp < 1024) then return 9; end if;
if (inp < 2048) then return 10; end if;
if (inp < 4096) then return 11; end if;
if (inp < 8192) then return 12; end if;
if (inp < 16384) then return 13; end if;
if (inp < 32768) then return 14; end if;
if (inp < 65538) then return 15; end if;
return 16;
end;
 
function size2bits(inp : integer) return integer is
begin
if (inp < 1) then return 1; end if;
if (inp < 2) then return 1; end if;
if (inp < 4) then return 2; end if;
if (inp < 8) then return 3; end if;
if (inp < 16) then return 4; end if;
if (inp < 32) then return 5; end if;
if (inp < 64) then return 6; end if;
if (inp < 128) then return 7; end if;
if (inp < 256) then return 8; end if;
if (inp < 512) then return 9; end if;
if (inp < 1024) then return 10; end if;
if (inp < 2048) then return 11; end if;
if (inp < 4096) then return 12; end if;
if (inp < 8192) then return 13; end if;
if (inp < 16384) then return 14; end if;
if (inp < 32768) then return 15; end if;
if (inp < 65538) then return 16; end if;
return 17;
end;
 
function equ(a : std_logic_vector; b : integer) return boolean is
variable b_s : std_logic_vector(a'RANGE);
begin
b_s := CONV_STD_LOGIC_VECTOR(b,a'HIGH+1);
return (a = b_s);
end;
 
end package body technology;
 
150,10 → 220,169
);
end altera;
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library exemplar;
use exemplar.exemplar_1164.all;
 
library lpm;
use lpm.all;
 
entity ram is
generic (
data_width : positive;
addr_width : positive
);
port (
clk : in std_logic;
we : in std_logic;
addr : in std_logic_vector(addr_width-1 downto 0);
d_in : in std_logic_vector(data_width-1 downto 0);
d_out : out std_logic_vector(data_width-1 downto 0)
);
end ram;
 
architecture altera of ram is
component lpm_ram_dp
generic (
lpm_width: positive;
lpm_widthad: positive;
lpm_numwords: natural := 0;
lpm_type: string := "lpm_ram_dp";
lpm_indata: string := "REGISTERED";
lpm_outdata: string := "UNREGISTERED";
lpm_rdaddress_control: string := "REGISTERED";
lpm_wraddress_control: string := "REGISTERED";
lpm_file: string := "UNUSED";
lpm_hint: string := "UNUSED"
);
port (
rdaddress, wraddress: in std_logic_vector(lpm_widthad-1 downto 0);
rdclock, wrclock: in std_logic := '0';
rden, rdclken, wrclken: in std_logic := '1';
wren: in std_logic;
data: in std_logic_vector(lpm_width-1 downto 0);
q: out std_logic_vector(lpm_width-1 downto 0)
);
end component;
begin
altera_ram: lpm_ram_dp
generic map (
lpm_width => data_width,
lpm_widthad => addr_width,
lpm_numwords => 2 ** addr_width,
lpm_type => "lpm_ram_dp",
lpm_indata => "REGISTERED",
lpm_wraddress_control => "REGISTERED",
lpm_outdata => "UNREGISTERED",
lpm_rdaddress_control => "UNREGISTERED",
lpm_file => "UNUSED",
lpm_hint => "UNUSED"
)
port map (
rdclock => clk,
rdclken => '1',
rdaddress => addr,
q => d_out,
rden => '1',
 
wrclock => clk,
wrclken => '1',
wraddress => addr,
data => d_in,
wren => we
);
end altera;
 
 
 
 
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library exemplar;
use exemplar.exemplar_1164.all;
 
library lpm;
use lpm.all;
 
entity dpram is
generic (
data_width : positive;
addr_width : positive
);
port (
clk : in std_logic;
 
r_d_out : out std_logic_vector(data_width-1 downto 0);
r_rd : in std_logic;
r_clk_en : in std_logic;
r_addr : in std_logic_vector(addr_width-1 downto 0);
 
w_d_in : in std_logic_vector(data_width-1 downto 0);
w_wr : in std_logic;
w_clk_en : in std_logic;
w_addr : in std_logic_vector(addr_width-1 downto 0)
);
end dpram;
 
architecture altera of dpram is
component lpm_ram_dp
generic (
lpm_width: positive;
lpm_widthad: positive;
lpm_numwords: natural := 0;
lpm_type: string := "lpm_ram_dp";
lpm_indata: string := "REGISTERED";
lpm_outdata: string := "UNREGISTERED";
lpm_rdaddress_control: string := "REGISTERED";
lpm_wraddress_control: string := "REGISTERED";
lpm_file: string := "UNUSED";
lpm_hint: string := "UNUSED"
);
port (
rdaddress, wraddress: in std_logic_vector(lpm_widthad-1 downto 0);
rdclock, wrclock: in std_logic := '0';
rden, rdclken, wrclken: in std_logic := '1';
wren: in std_logic;
data: in std_logic_vector(lpm_width-1 downto 0);
q: out std_logic_vector(lpm_width-1 downto 0)
);
end component;
begin
altera_ram: lpm_ram_dp
generic map (
lpm_width => data_width,
lpm_widthad => addr_width,
lpm_numwords => 2 ** addr_width,
lpm_type => "lpm_ram_dp",
lpm_indata => "REGISTERED",
lpm_wraddress_control => "REGISTERED",
lpm_outdata => "UNREGISTERED",
lpm_rdaddress_control => "UNREGISTERED",
lpm_file => "UNUSED",
lpm_hint => "UNUSED"
)
port map (
rdclock => clk,
rdclken => r_clk_en,
rdaddress => r_addr,
q => r_d_out,
rden => r_rd,
 
wrclock => clk,
wrclken => w_clk_en,
wraddress => w_addr,
data => w_d_in,
wren => w_wr
);
end altera;
 
library IEEE;
use IEEE.std_logic_1164.all;
 
library altera_exemplar;
use altera_exemplar.all;
 
/trunk/wb_out_reg.vhd
0,0 → 1,94
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_out_reg: Wishbone bus compatible output register.
 
-------------------------------------------------------------------------------
--
-- wb_out_reg
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
 
library wb_tk;
use wb_tk.technology.all;
 
entity wb_out_reg is
generic (
width : positive := 8;
bus_width: positive := 8;
offset: integer := 0
);
port (
clk_i: in std_logic;
rst_i: in std_logic;
rst_val: std_logic_vector(width-1 downto 0) := (others => '0');
 
cyc_i: in std_logic := '1';
stb_i: in std_logic;
sel_i: in std_logic_vector ((bus_width/8)-1 downto 0) := (others => '1');
we_i: in std_logic;
ack_o: out std_logic;
ack_oi: in std_logic := '-';
adr_i: in std_logic_vector (size2bits((width+offset+bus_width-1)/bus_width)-1 downto 0) := (others => '0');
dat_i: in std_logic_vector (bus_width-1 downto 0);
dat_oi: in std_logic_vector (bus_width-1 downto 0) := (others => '-');
dat_o: out std_logic_vector (bus_width-1 downto 0);
q: out std_logic_vector (width-1 downto 0)
);
end wb_out_reg;
 
architecture wb_out_reg of wb_out_reg is
signal content : std_logic_vector (width-1 downto 0);
begin
-- output bus handling with logic
gen_dat_o: process is
variable rd_sel: std_logic;
variable adr: integer;
variable reg_i: integer;
begin
wait on dat_oi, we_i, stb_i, content, adr_i, cyc_i, sel_i;
rd_sel := cyc_i and stb_i and not we_i;
for i in dat_i'RANGE loop
adr := CONV_INTEGER(adr_i);
reg_i := i-offset+adr*bus_width;
if ((reg_i >= 0) and (reg_i < width) and (sel_i(i/8) = '1')) then
dat_o(i) <= (dat_oi(i) and not rd_sel) or (content(reg_i) and rd_sel);
else
dat_o(i) <= dat_oi(i);
end if;
end loop;
end process;
 
-- this item never generates any wait-states
ack_o <= stb_i or ack_oi;
reg: process is
variable adr: integer;
variable reg_i: integer;
begin
wait until clk_i'EVENT and clk_i='1';
if (rst_i = '1') then
content <= rst_val;
else
if (stb_i = '1' and cyc_i = '1' and we_i = '1') then
for i in dat_i'RANGE loop
adr := CONV_INTEGER(adr_i);
reg_i := i-offset+adr*bus_width;
if ((reg_i >= 0) and (reg_i < width) and (sel_i(i/8) = '1')) then
content(reg_i) <= dat_i(i);
end if;
end loop;
end if;
end if;
end process;
q <= content;
end wb_out_reg;
/trunk/Makefile
0,0 → 1,2
all:
bash compile.sh
/trunk/wb_bus_dnsize.vhd
0,0 → 1,138
--
-- Wishbone bus toolkit.
--
-- (c) Copyright Andras Tantos <andras_tantos@yahoo.com> 2001/03/31
-- This code is distributed under the terms and conditions of the GNU General Public Lince.
--
--
-- ELEMENTS:
-- wb_bus_dnsize: bus downsizer.
-- doesn't split access cycles so granularity on the input bus must not be greater than
-- the width of the output bus.
 
-------------------------------------------------------------------------------
--
-- wb_bus_upsize
--
-------------------------------------------------------------------------------
 
library IEEE;
use IEEE.std_logic_1164.all;
use IEEE.STD_LOGIC_UNSIGNED.all;
 
library wb_tk;
use wb_tk.technology.all;
 
library synopsys;
use synopsys.std_logic_arith.all;
 
entity wb_bus_dnsize is
generic (
m_bus_width: positive := 32; -- master bus width
m_addr_width: positive := 20; -- master bus width
s_bus_width: positive := 16; -- slave bus width
s_addr_width: positive := 21; -- master bus width
little_endien: boolean := true -- if set to false, big endien
);
port (
-- clk_i: in std_logic;
-- rst_i: in std_logic := '0';
 
-- Master bus interface
m_adr_i: in std_logic_vector (m_addr_width-1 downto 0);
m_sel_i: in std_logic_vector ((m_bus_width/8)-1 downto 0) := (others => '1');
m_dat_i: in std_logic_vector (m_bus_width-1 downto 0);
m_dat_oi: in std_logic_vector (m_bus_width-1 downto 0) := (others => '-');
m_dat_o: out std_logic_vector (m_bus_width-1 downto 0);
m_cyc_i: in std_logic;
m_ack_o: out std_logic;
m_ack_oi: in std_logic := '-';
m_err_o: out std_logic;
m_err_oi: in std_logic := '-';
m_rty_o: out std_logic;
m_rty_oi: in std_logic := '-';
m_we_i: in std_logic;
m_stb_i: in std_logic;
 
-- Slave bus interface
s_adr_o: out std_logic_vector (s_addr_width-1 downto 0);
s_sel_o: out std_logic_vector ((s_bus_width/8)-1 downto 0);
s_dat_i: in std_logic_vector (s_bus_width-1 downto 0);
s_dat_o: out std_logic_vector (s_bus_width-1 downto 0);
s_cyc_o: out std_logic;
s_ack_i: in std_logic;
s_err_i: in std_logic := '-';
s_rty_i: in std_logic := '-';
s_we_o: out std_logic;
s_stb_o: out std_logic
);
end wb_bus_dnsize;
 
architecture wb_bus_dnsize of wb_bus_dnsize is
constant addr_diff: integer := log2(m_bus_width/s_bus_width);
constant mux_mask: integer := ((m_bus_width / 8)-1) - ((s_bus_width/8)-1);
signal i_m_dat_o: std_logic_vector(m_bus_width-1 downto 0);
signal mux_sel: std_logic_vector(log2(m_sel_i'HIGH+1)-1 downto 0);
signal i_mux_sel: integer := 0;
function prior_decode(inp: std_logic_vector) return integer is
begin
-- variable ret: std_logic_vector(log2(inp'HIGH)-1 downto 0) := (others = '1');
for i in inp'HIGH downto 0 loop
if (inp(i) = '1') then
return i;
end if;
end loop;
return inp'HIGH;
end;
begin
assert (s_addr_width = m_addr_width+addr_diff) report "Address widths are not consistent" severity FAILURE;
 
-- Reconstructing address bits (mux_sel)
compute_mux_sel: process is
variable i: integer;
begin
wait on m_sel_i;
i := prior_decode(m_sel_i);
mux_sel <= CONV_STD_LOGIC_VECTOR(i,log2(m_sel_i'HIGH+1)) and CONV_STD_LOGIC_VECTOR(mux_mask,log2(m_sel_i'HIGH+1));
end process;
i_mux_sel <= CONV_INTEGER(mux_sel);
 
-- create slave address bus
s_adr_o(s_addr_width-1 downto addr_diff) <= m_adr_i;
s_adr_o_gen: process is
variable all_ones: std_logic_vector(addr_diff-1 downto 0) := (others => '1');
begin
wait on mux_sel(mux_sel'HIGH downto mux_sel'HIGH-addr_diff+1);
if (little_endien) then
s_adr_o(addr_diff-1 downto 0) <= mux_sel(mux_sel'HIGH downto mux_sel'HIGH-addr_diff+1);
else
s_adr_o(addr_diff-1 downto 0) <= all_ones-mux_sel(mux_sel'HIGH downto mux_sel'HIGH-addr_diff+1);
end if;
end process;
-- create output byte select signals
s_sel_o <= m_sel_i(i_mux_sel+(s_bus_width/8)-1 downto i_mux_sel);
 
s_we_o <= m_we_i;
m_ack_o <= (m_stb_i and s_ack_i) or (not m_stb_i and m_ack_oi);
m_err_o <= (m_stb_i and s_err_i) or (not m_stb_i and m_err_oi);
m_rty_o <= (m_stb_i and s_rty_i) or (not m_stb_i and m_rty_oi);
s_stb_o <= m_stb_i;
s_cyc_o <= m_cyc_i;
-- Multiplex data-bus down to the slave width
s_dat_o <= m_dat_i((i_mux_sel)*8-1+s_bus_width downto (i_mux_sel)*8);
m_dat_o_mux: process is
begin
wait on m_dat_oi, s_dat_i, i_mux_sel, m_stb_i, m_we_i;
m_dat_o <= m_dat_oi;
if (m_stb_i = '1' and m_we_i = '0') then
m_dat_o((i_mux_sel)*8-1+s_bus_width downto (i_mux_sel)*8) <= s_dat_i;
end if;
end process;
end wb_bus_dnsize;
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.