Commit 35758780 authored by mcattin's avatar mcattin

Add monostable, ext_pulse_sync and utils_pkg to repo. Where only localy on my pc.

git-svn-id: http://svn.ohwr.org/fmc-adc-100m14b4cha/trunk@80 ddd67a1a-c8ad-4635-afe9-0b8a11d8f8e4
parent dba7b671
--=============================================================================
-- @file ext_pulse_sync_rtl.vhd
--=============================================================================
--! Standard library
library IEEE;
--! Standard packages
use IEEE.STD_LOGIC_1164.all;
use IEEE.NUMERIC_STD.all;
use work.utils_pkg.all;
--! Specific packages
-------------------------------------------------------------------------------
-- --
-- CERN, BE-CO-HT, Synchronize an asnychronous external pulse to a clock
-- --
-------------------------------------------------------------------------------
--
-- Unit name: External pulse synchronizer (ext_pulse_sync_rtl)
--
--! @brief Synchronize an asnychronous external pulse to a clock
--!
--
--! @author Matthieu Cattin (matthieu dot cattin at cern dot ch)
--
--! @date 22\10\2009
--
--! @version v1.0
--
--! @details Latency = 5 clk_i ticks
--!
--! <b>Dependencies:</b>\n
--! utils_pkg.vhd
--!
--! <b>References:</b>\n
--!
--!
--! <b>Modified by:</b>\n
--! Author:
-------------------------------------------------------------------------------
--! \n\n<b>Last changes:</b>\n
--! 22.10.2009 mcattin Creation from pulse_sync_rtl.vhd
--! 27.10.2009 mcattin Possibility for output monostable to be
--! retriggerable
--! 03.03.2011 mcattin Input polarity from port instead of generic
-------------------------------------------------------------------------------
--! @todo
--
-------------------------------------------------------------------------------
--=============================================================================
--! Entity declaration for External pulse synchronizer
--=============================================================================
entity ext_pulse_sync is
generic(
g_MIN_PULSE_WIDTH : natural := 2; --! Minimum input pulse width
--! (in ns), must be >1 clk_i tick
g_CLK_FREQUENCY : natural := 40; --! clk_i frequency (in MHz)
g_OUTPUT_POLARITY : std_logic := '1'; --! pulse_o polarity
--! (1=negative, 0=positive)
g_OUTPUT_RETRIG : boolean := false; --! Retriggerable output monostable
g_OUTPUT_LENGTH : natural := 1 --! pulse_o lenght (in clk_i ticks)
);
port (
rst_n_i : in std_logic; --! Reset (active low)
clk_i : in std_logic; --! Clock to synchronize pulse
input_polarity_i : in std_logic; --! Input pulse polarity (1=negative, 0=positive)
pulse_i : in std_logic; --! Asynchronous input pulse
pulse_o : out std_logic --! Synchronized output pulse
);
end entity ext_pulse_sync;
--=============================================================================
--! Architecture declaration External pulse synchronizer
--=============================================================================
architecture rtl of ext_pulse_sync is
--! g_MIN_PULSE_WIDTH converted into clk_i ticks
constant c_NB_TICKS : natural := 1 + to_integer(to_unsigned(g_MIN_PULSE_WIDTH, log2_ceil(g_MIN_PULSE_WIDTH))*
to_unsigned(g_CLK_FREQUENCY, log2_ceil(g_CLK_FREQUENCY))/
to_unsigned(1000, log2_ceil(1000)));
--! FFs to synchronize input pulse
signal s_pulse_sync_reg : std_logic_vector(1 downto 0) := (others => '0');
--! Pulse length counter
signal s_pulse_length_cnt : unsigned(log2_ceil(c_NB_TICKS) downto 0) := (others => '0');
--! Output pulse monostable counter
signal s_monostable_cnt : unsigned(log2_ceil(g_OUTPUT_LENGTH) downto 0) := (others => '0');
--! Pulse to start output monostable
signal s_sync_pulse : std_logic_vector(1 downto 0) := (others => '0');
--! Output pulse for readback
signal s_output_pulse : std_logic := '0';
--=============================================================================
--! Architecture begin
--=============================================================================
begin
--*****************************************************************************
-- Begin of p_pulse_sync
--! Process: Synchronise input pulse to clk_i clock
--*****************************************************************************
p_pulse_sync : process(clk_i, rst_n_i)
begin
if rst_n_i = '0' then
s_pulse_sync_reg <= (others => '0');
elsif rising_edge(clk_i) then
s_pulse_sync_reg <= s_pulse_sync_reg(0) & pulse_i;
end if;
end process p_pulse_sync;
--*****************************************************************************
-- Begin of p_pulse_length_cnt
--! Process: Counts input pulse length
--*****************************************************************************
p_pulse_length_cnt : process(clk_i, rst_n_i)
begin
if rst_n_i = '0' then
s_pulse_length_cnt <= (others => '0');
s_sync_pulse(0) <= '0';
elsif rising_edge(clk_i) then
if s_pulse_sync_reg(1) = input_polarity_i then
s_pulse_length_cnt <= (others => '0');
s_sync_pulse(0) <= '0';
elsif s_pulse_length_cnt = to_unsigned(c_NB_TICKS, s_pulse_length_cnt'length) then
s_sync_pulse(0) <= '1';
elsif s_pulse_sync_reg(1) = not(input_polarity_i) then
s_pulse_length_cnt <= s_pulse_length_cnt + 1;
s_sync_pulse(0) <= '0';
end if;
end if;
end process p_pulse_length_cnt;
--*****************************************************************************
-- Begin of p_start_pulse
--! Process: FF to generate monostable start pulse
--*****************************************************************************
p_start_pulse : process (clk_i, rst_n_i)
begin
if rst_n_i = '0' then
s_sync_pulse(1) <= '0';
elsif rising_edge(clk_i) then
s_sync_pulse(1) <= s_sync_pulse(0);
end if;
end process p_start_pulse;
--*****************************************************************************
-- Begin of p_monostable
--! Process: Monostable to generate output pulse
--*****************************************************************************
p_monostable : process (clk_i, rst_n_i)
begin
if rst_n_i = '0' then
s_monostable_cnt <= (others => '0');
s_output_pulse <= g_OUTPUT_POLARITY;
elsif rising_edge(clk_i) then
if ((not(g_OUTPUT_RETRIG) and ((s_sync_pulse(0) and not(s_sync_pulse(1))) = '1')
and (s_output_pulse = g_OUTPUT_POLARITY)) -- non-retriggerable
or (g_OUTPUT_RETRIG and (s_sync_pulse(0) = '1'))) then -- retriggerable
s_monostable_cnt <= to_unsigned(g_OUTPUT_LENGTH, s_monostable_cnt'length) - 1;
s_output_pulse <= not(g_OUTPUT_POLARITY);
elsif s_monostable_cnt = to_unsigned(0, s_monostable_cnt'length) then
s_output_pulse <= g_OUTPUT_POLARITY;
else
s_monostable_cnt <= s_monostable_cnt - 1;
end if;
end if;
end process p_monostable;
pulse_o <= s_output_pulse;
end architecture rtl;
--=============================================================================
--! Architecture end
--=============================================================================
--=============================================================================
-- @file monostable_rtl.vhd
--=============================================================================
--! Standard library
library IEEE;
--! Standard packages
use IEEE.STD_LOGIC_1164.all;
use IEEE.NUMERIC_STD.all;
--! Specific packages
-------------------------------------------------------------------------------
-- --
-- CERN, BE-CO-HT, Monostable
-- --
-------------------------------------------------------------------------------
--
-- Unit name: Monostable (monostable_rtl)
--
--! @brief Monostable
--!
--
--! @author Matthieu Cattin (matthieu dot cattin at cern dot ch)
--
--! @date 27\10\2009
--
--! @version v1.0
--
--! @details
--!
--! <b>Dependencies:</b>\n
--!
--! <b>References:</b>\n
--!
--!
--! <b>Modified by:</b>\n
--! Author:
-------------------------------------------------------------------------------
--! \n\n<b>Last changes:</b>\n
--! 27.10.2009 mcattin Creation from ext_pulse_sync_rtl.vhd
--!
-------------------------------------------------------------------------------
--! @todo
--
-------------------------------------------------------------------------------
--=============================================================================
--! Entity declaration for Monostable
--=============================================================================
entity monostable is
generic(
g_INPUT_POLARITY : std_logic := '1'; --! trigger_i polarity
--! ('0'=negative, 1=positive)
g_OUTPUT_POLARITY : std_logic := '1'; --! pulse_o polarity
--! ('0'=negative, 1=positive)
g_OUTPUT_RETRIG : boolean := false; --! Retriggerable output monostable
g_OUTPUT_LENGTH : natural := 1 --! pulse_o lenght (in clk_i ticks)
);
port (
rst_n_i : in std_logic; --! Reset (active low)
clk_i : in std_logic; --! Clock
trigger_i : in std_logic; --! Trigger input pulse
pulse_o : out std_logic --! Monostable output pulse
);
end entity monostable;
--=============================================================================
--! Architecture declaration Monostable
--=============================================================================
architecture rtl of monostable is
--! log2 function
function log2_ceil(N : natural) return positive is
begin
if N <= 2 then
return 1;
elsif N mod 2 = 0 then
return 1 + log2_ceil(N/2);
else
return 1 + log2_ceil((N+1)/2);
end if;
end;
--! FFs for monostable start
signal s_trigger_d : std_logic_vector(1 downto 0) := (others => '0');
--! Output pulse monostable counter
signal s_monostable_cnt : unsigned(log2_ceil(g_OUTPUT_LENGTH) downto 0) := (others => '0');
--! Output pulse for readback
signal s_output_pulse : std_logic := '0';
--=============================================================================
--! Architecture begin
--=============================================================================
begin
--*****************************************************************************
-- Begin of p_trigger
--! Process: FF to generate monostable start pulse
--*****************************************************************************
p_trigger : process (clk_i)
begin
if rising_edge(clk_i) then
if rst_n_i = '0' then
s_trigger_d <= (others => '0');
else
if trigger_i = g_INPUT_POLARITY then
s_trigger_d(0) <= '1';
else
s_trigger_d(0) <= '0';
end if;
s_trigger_d(1) <= s_trigger_d(0);
end if;
end if;
end process p_trigger;
--*****************************************************************************
-- Begin of p_monostable
--! Process: Monostable to generate output pulse
--*****************************************************************************
p_monostable : process (clk_i)
begin
if rising_edge(clk_i) then
if rst_n_i = '0' then
s_monostable_cnt <= (others => '0');
s_output_pulse <= not(g_OUTPUT_POLARITY);
elsif ((not(g_OUTPUT_RETRIG)
and ((s_trigger_d(0) and not(s_trigger_d(1))) = '1')
and (s_output_pulse /= g_OUTPUT_POLARITY)) -- non-retriggerable
or (g_OUTPUT_RETRIG and (s_trigger_d(0) = '1'))) then -- retriggerable
s_monostable_cnt <= to_unsigned(g_OUTPUT_LENGTH, s_monostable_cnt'length) - 1;
s_output_pulse <= g_OUTPUT_POLARITY;
elsif s_monostable_cnt = to_unsigned(0, s_monostable_cnt'length) then
s_output_pulse <= not(g_OUTPUT_POLARITY);
else
s_monostable_cnt <= s_monostable_cnt - 1;
end if;
end if;
end process p_monostable;
pulse_o <= s_output_pulse;
end architecture rtl;
--=============================================================================
--! Architecture end
--=============================================================================
--=============================================================================
-- @file utils_pkg.vhd
--=============================================================================
--! Standard library
library IEEE;
--library unisim;
--! Standard packages
use IEEE.STD_LOGIC_1164.all;
use IEEE.NUMERIC_STD.all;
--use unisim.vcomponents.all;
--! Specific packages
-------------------------------------------------------------------------------
-- --
-- CERN, BE-CO-HT,
-- --
-------------------------------------------------------------------------------
--
-- Unit name:
--
--! @brief
--!
--
--! @author Matthieu Cattin (matthieu dot cattin at cern dot ch)
--
--! @date 22\10\2009
--
--! @version v.0.1
--
--! @details
--!
--! <b>Dependencies:</b>\n
--! None
--!
--! <b>References:</b>\n
--!
--!
--! <b>Modified by:</b>\n
--! Author:
-------------------------------------------------------------------------------
--! \n\n<b>Last changes:</b>\n
--! 22.10.2009 mcattin Creation
--! 07.03.2011 mcattin Fix bug in log2_ceil function
-------------------------------------------------------------------------------
--! @todo
--
-------------------------------------------------------------------------------
--=============================================================================
--! Package declaration for utils_pkg
--=============================================================================
package utils_pkg is
-- Functions
function log2_ceil(N : natural) return positive;
end utils_pkg;
--=============================================================================
--! Body declaration for utils_pkg
--=============================================================================
package body utils_pkg is
--*****************************************************************************
--! Function : Returns log of 2 of a natural number
--*****************************************************************************
function log2_ceil(N : natural) return positive is
begin
if N <= 2 then
return 1;
elsif N mod 2 = 0 then
return 1 + log2_ceil(N/2);
else
return 1 + log2_ceil((N+1)/2);
end if;
end;
end utils_pkg;
......@@ -12,8 +12,8 @@ files = ["../spec_top_fmc_adc_100Ms.ucf",
"../ip_cores/multishot_dpram.ngc",
"../ip_cores/wb_ddr_fifo.ngc",
"../ip_cores/adc_serdes.vhd",
"../../../../monostable/monostable_rtl.vhd",
"../../../../ext_pulse_sync/ext_pulse_sync_rtl.vhd",
"../../../../utils/utils_pkg.vhd"]
"../ip_cores/monostable/monostable_rtl.vhd",
"../ip_cores/ext_pulse_sync/ext_pulse_sync_rtl.vhd",
"../ip_cores/utils/utils_pkg.vhd"]
modules = { "local" : "../rtl" }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment