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

Subversion Repositories dp_components

Compare Revisions

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

Rev 4 → Rev 5

/trunk/dp_block_gen.vhd
0,0 → 1,231
-------------------------------------------------------------------------------
--
-- Copyright (C) 2011
-- ASTRON (Netherlands Institute for Radio Astronomy) <http://www.astron.nl/>
-- P.O.Box 2, 7990 AA Dwingeloo, The Netherlands
--
-- This program is free software: you can redistribute it and/or modify
-- it under the terms of the GNU General Public License as published by
-- the Free Software Foundation, either version 3 of the License, or
-- (at your option) any later version.
--
-- This program is distributed in the hope that it will be useful,
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-- GNU General Public License for more details.
--
-- You should have received a copy of the GNU General Public License
-- along with this program. If not, see <http://www.gnu.org/licenses/>.
--
-------------------------------------------------------------------------------
 
-- Purpose : Generate the sosi control for a block of data under flow control
-- Description:
-- When enabled a block of g_nof_data words is output via src_out under flow
-- control by the ready. The ready depends on g_use_src_in:
--
-- . If g_use_src_in=TRUE then the src_in.ready is used and snk_in is
-- ignored. This can be used as a block reference input parallel to a
-- group of user inputs.
-- The g_preserve_* generics do not apply, because the snk_in is ignored.
--
-- . If g_use_src_in=FALSE then the src_in is not used and the snk_in data,
-- re, im are passed on and the snk_in.valid is used as ready. This can
-- be used as a BSN source that creates sync, bsn, sop and eop from
-- snk_in.valid for snk_in.data that has data not valid gaps. The
-- dp_bsn_source is similar but only supports data that is always valid.
-- The g_preserve_* generics can be used to preserve the corresponding
-- snk_in fields or to use the local generated values for this fields.
--
-- The first active ready starts the dp_block_gen. The first output block
-- will have a src_out.sync and every g_nof_blk_per_sync another
-- src_out.sync. Each block is marked by src_out.sop and src_out.eop. The
-- sop also marks the BSN. The BSN is the block sequence number that
-- increments for every block.
--
-- The snk_in.sop and snk_in.eop are always ignored, because g_nof_data
-- will set the src_out.sop/eop blocks.
--
-- If g_preserve_sync=TRUE then src_out.sync = snk_in.sync, else the
-- src_out.sync is depends on the first ready and on g_nof_blk_per_sync.
--
-- If g_preserve_bsn=TRUE then src_out.bsn = snk_in.bsn, else the
-- src_out.bsn is depends on the first ready and the initial g_bsn. If
-- g_preserve_bsn=TRUE then g_nof_data needs to match the snk_in.sop/eop
-- blocks.
--
-- If g_preserve_channel=TRUE then src_out.channel = snk_in.channel, else
-- the src_out.channel = g_channel.
--
-- Remarks:
-- . Ready latency (RL) = 1
-- . Alternatively consider using dp_block_gen_valid_arr.vhd or
-- dp_block_reshape.vhd.
 
 
LIBRARY IEEE, common_pkg_lib, dp_pkg_lib;
USE IEEE.STD_LOGIC_1164.ALL;
USE IEEE.NUMERIC_STD.ALL;
USE common_pkg_lib.common_pkg.ALL;
USE dp_pkg_lib.dp_stream_pkg.ALL;
 
ENTITY dp_block_gen IS
GENERIC (
g_use_src_in : BOOLEAN := TRUE; -- when true use src_in.ready else use snk_in.valid for flow control
g_nof_data : POSITIVE := 1; -- nof data per block
g_nof_blk_per_sync : POSITIVE := 8;
g_empty : NATURAL := 0;
g_channel : NATURAL := 0;
g_error : NATURAL := 0;
g_bsn : NATURAL := 0;
g_preserve_sync : BOOLEAN := FALSE;
g_preserve_bsn : BOOLEAN := FALSE;
g_preserve_channel : BOOLEAN := FALSE
);
PORT (
rst : IN STD_LOGIC;
clk : IN STD_LOGIC;
-- Streaming sink
snk_out : OUT t_dp_siso; -- pass on src_in.xon, pass on or force snk_out.ready dependend on g_use_src_in
snk_in : IN t_dp_sosi := c_dp_sosi_rst;
-- Streaming source
src_in : IN t_dp_siso := c_dp_siso_rdy;
src_out : OUT t_dp_sosi;
-- MM control
en : IN STD_LOGIC := '1'
);
END dp_block_gen;
 
 
ARCHITECTURE rtl OF dp_block_gen IS
 
TYPE t_state IS (s_sop, s_data, s_eop);
 
TYPE t_reg IS RECORD -- local registers
state : t_state;
data_cnt : NATURAL RANGE 0 TO g_nof_data;
blk_cnt : NATURAL RANGE 0 TO g_nof_blk_per_sync;
bsn : STD_LOGIC_VECTOR(c_dp_stream_bsn_w-1 DOWNTO 0);
src_out : t_dp_sosi;
END RECORD;
CONSTANT c_reg_rst : t_reg := (s_sop, 0, 0, TO_DP_BSN(g_bsn), c_dp_sosi_rst);
 
SIGNAL ready : STD_LOGIC;
-- Define the local registers in t_reg record
SIGNAL r : t_reg;
SIGNAL nxt_r : t_reg;
BEGIN
snk_out.ready <= src_in.ready WHEN g_use_src_in=TRUE ELSE '1'; -- force snk_out.ready = '1' when src_in.ready is not used
snk_out.xon <= src_in.xon; -- always pass on siso.xon
src_out <= r.src_out;
p_clk : PROCESS(rst, clk)
BEGIN
IF rst='1' THEN
r <= c_reg_rst;
ELSIF rising_edge(clk) THEN
r <= nxt_r;
END IF;
END PROCESS;
 
ready <= src_in.ready WHEN g_use_src_in=TRUE ELSE snk_in.valid;
p_state : PROCESS(r, en, ready, snk_in)
BEGIN
nxt_r <= r;
IF g_use_src_in=FALSE THEN
nxt_r.src_out.data <= snk_in.data;
nxt_r.src_out.re <= snk_in.re;
nxt_r.src_out.im <= snk_in.im;
END IF;
 
IF g_preserve_sync = FALSE THEN
nxt_r.src_out.sync <= '0';
ELSE
nxt_r.src_out.sync <= snk_in.sync;
END IF;
 
nxt_r.src_out.valid <= '0';
nxt_r.src_out.sop <= '0';
nxt_r.src_out.eop <= '0';
IF g_preserve_bsn=TRUE THEN
nxt_r.src_out.bsn <= snk_in.bsn;
END IF;
IF g_preserve_channel=TRUE THEN
nxt_r.src_out.channel <= snk_in.channel;
END IF;
CASE r.state IS
WHEN s_sop =>
nxt_r.data_cnt <= 0; -- for clarity init data count to 0 (because it will become 1 anyway at sop)
IF en='0' THEN -- if disabled then reset block generator and remain in this state
nxt_r.blk_cnt <= 0;
nxt_r.bsn <= TO_DP_BSN(g_bsn);
ELSE -- enabled block generator
IF ready='1' THEN -- once enabled the complete block will be output dependent on the flow control
-- use input sync or create local sync
IF g_preserve_sync = FALSE THEN
IF r.blk_cnt=0 THEN
nxt_r.src_out.sync <= '1'; -- use local sync for this block, local sync starts at first ready
END IF;
IF r.blk_cnt>=g_nof_blk_per_sync-1 THEN -- maintain local sync interval
nxt_r.blk_cnt <= 0;
ELSE
nxt_r.blk_cnt <= r.blk_cnt+1;
END IF;
END IF;
nxt_r.src_out.valid <= '1';
nxt_r.src_out.sop <= '1';
-- use input bsn or create local bsn
IF g_preserve_bsn=FALSE THEN
nxt_r.bsn <= INCR_UVEC(r.bsn, 1); -- increment local bsn for next block
nxt_r.src_out.bsn <= r.bsn; -- use local bsn for this block
END IF;
-- use input channel or create fixed local channel
IF g_preserve_channel=FALSE THEN
nxt_r.src_out.channel <= TO_DP_CHANNEL(g_channel);
END IF;
IF g_nof_data=1 THEN
nxt_r.src_out.eop <= '1'; -- single word block
nxt_r.src_out.empty <= TO_DP_EMPTY(g_empty);
nxt_r.src_out.err <= TO_DP_ERROR(g_error);
ELSIF g_nof_data=2 THEN
nxt_r.data_cnt <= 1; -- start of two word block
nxt_r.state <= s_eop;
ELSE
nxt_r.data_cnt <= 1; -- start of multi word block
nxt_r.state <= s_data;
END IF;
END IF;
END IF;
WHEN s_data =>
IF ready='1' THEN
nxt_r.data_cnt <= r.data_cnt+1;
nxt_r.src_out.valid <= '1';
IF r.data_cnt=g_nof_data-2 THEN
nxt_r.state <= s_eop;
END IF;
END IF;
WHEN OTHERS => -- s_eop
IF ready='1' THEN
nxt_r.src_out.valid <= '1';
nxt_r.src_out.eop <= '1';
nxt_r.src_out.empty <= TO_DP_EMPTY(g_empty);
nxt_r.src_out.err <= TO_DP_ERROR(g_error);
nxt_r.state <= s_sop;
END IF;
END CASE;
END PROCESS;
END rtl;
/trunk/dp_bsn_restore_global.vhd
0,0 → 1,121
-------------------------------------------------------------------------------
--
-- Copyright (C) 2017
-- ASTRON (Netherlands Institute for Radio Astronomy) <http://www.astron.nl/>
-- JIVE (Joint Institute for VLBI in Europe) <http://www.jive.nl/>
-- P.O.Box 2, 7990 AA Dwingeloo, The Netherlands
--
-- This program is free software: you can redistribute it and/or modify
-- it under the terms of the GNU General Public License as published by
-- the Free Software Foundation, either version 3 of the License, or
-- (at your option) any later version.
--
-- This program is distributed in the hope that it will be useful,
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-- GNU General Public License for more details.
--
-- You should have received a copy of the GNU General Public License
-- along with this program. If not, see <http://www.gnu.org/licenses/>.
--
-------------------------------------------------------------------------------
 
LIBRARY IEEE, common_pkg_lib, common_components_lib, dp_pkg_lib;
USE IEEE.std_logic_1164.all;
USE common_pkg_lib.common_pkg.ALL;
USE dp_pkg_lib.dp_stream_pkg.ALL;
 
-- Author: Eric Kooistra, 17 nov 2017
-- Purpose:
-- Restore global BSN.
-- Description:
-- The input global BSN is active at the sync. In between sync the other BSN
-- BSN at the sop may count a local BSN that restarted at 0 for every sync.
-- This dp_bsn_restore_global takes the BSN at the sync and starts counting
-- from there for every sop, so in this way it restores the global BSN count
-- for the blocks in between syncs.
-- The increment for each restored BSN is 1. The assumption is that the
-- number of blocks between syncs equals the difference in global BSN values
-- between syncs. In this way the restored BSN counts without gaps or
-- duplicates.
-- Remarks:
 
ENTITY dp_bsn_restore_global IS
GENERIC (
g_bsn_w : NATURAL := c_dp_stream_bsn_w;
g_pipeline : NATURAL := 1 -- 0 for wires, > 0 for registers
);
PORT (
rst : IN STD_LOGIC;
clk : IN STD_LOGIC;
-- ST sink
snk_out : OUT t_dp_siso;
snk_in : IN t_dp_sosi;
-- ST source
src_in : IN t_dp_siso := c_dp_siso_rdy;
src_out : OUT t_dp_sosi
);
END dp_bsn_restore_global;
 
 
ARCHITECTURE str OF dp_bsn_restore_global IS
 
SIGNAL blk_sync : STD_LOGIC;
SIGNAL bsn_at_sync : STD_LOGIC_VECTOR(g_bsn_w-1 DOWNTO 0);
SIGNAL nxt_bsn_at_sync : STD_LOGIC_VECTOR(g_bsn_w-1 DOWNTO 0);
SIGNAL bsn_restored : STD_LOGIC_VECTOR(g_bsn_w-1 DOWNTO 0);
SIGNAL snk_in_restored : t_dp_sosi;
BEGIN
 
-- keep BSN at sync
p_clk : PROCESS(clk, rst)
BEGIN
IF rst='1' THEN
bsn_at_sync <= (OTHERS=>'0');
ELSIF rising_edge(clk) THEN
bsn_at_sync <= nxt_bsn_at_sync;
END IF;
END PROCESS;
-- Store global BSN at sync
nxt_bsn_at_sync <= snk_in.bsn(g_bsn_w-1 DOWNTO 0) WHEN snk_in.sync='1' ELSE bsn_at_sync;
-- Create block sync from snk_in.sync, this blk_sync is active during entire first sop-eop block of sync interval
u_common_switch : ENTITY common_components_lib.common_switch
GENERIC MAP (
g_rst_level => '0', -- Defines the output level at reset.
g_priority_lo => FALSE, -- When TRUE then input switch_low has priority, else switch_high. Don't care when switch_high and switch_low are pulses that do not occur simultaneously.
g_or_high => TRUE, -- When TRUE and priority hi then the registered switch_level is OR-ed with the input switch_high to get out_level, else out_level is the registered switch_level
g_and_low => FALSE -- When TRUE and priority lo then the registered switch_level is AND-ed with the input switch_low to get out_level, else out_level is the registered switch_level
)
PORT MAP (
rst => rst,
clk => clk,
switch_high => snk_in.sync, -- A pulse on switch_high makes the out_level go high
switch_low => snk_in.eop, -- A pulse on switch_low makes the out_level go low
out_level => blk_sync
);
-- Use stored global BSN at sync and add local BSN to restore the global BSN for every next sop
bsn_restored <= snk_in.bsn WHEN blk_sync='1' ELSE ADD_UVEC(bsn_at_sync, snk_in.bsn, g_bsn_w);
snk_in_restored <= func_dp_stream_bsn_set(snk_in, bsn_restored);
-- Add pipeline to ensure timing closure for the restored BSN summation
u_pipeline : ENTITY work.dp_pipeline
GENERIC MAP (
g_pipeline => g_pipeline -- 0 for wires, > 0 for registers
)
PORT MAP (
rst => rst,
clk => clk,
-- ST sink
snk_out => snk_out,
snk_in => snk_in_restored,
-- ST source
src_in => src_in,
src_out => src_out
);
END str;
/trunk/hdllib.cfg
10,6 → 10,7
dp_hold_ctrl.vhd
dp_hold_input.vhd
dp_xonoff.vhd
dp_block_gen.vhd
test_bench_files =
tb_dp_latency_adapter.vhd

powered by: WebSVN 2.1.0

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