Commit 9c48eb1b authored by gilsoriano's avatar gilsoriano

Basic repetitor committed to repo.

parent 7ee393fc
This diff is collapsed.
This diff is collapsed.
---------------------------------------------------------------------------------
-- Company: CERN, BE-CO-HT
-- Engineer: Carlos Gil Soriano
--
-- Create Date: 09:58:06 10/12/2011
-- Design Name: HDL trigger
-- Module Name: trigger - Behavioral
-- Project Name: CTDAH
-- Target Devices: Spartan 6
-- Tool versions:
-- Description: This is the wishbone trigger which receives a debounced input
-- and outputs a trigger signal for the pulse converter
-- Dependencies: none
--
-- Revision:
-- Revision 0.1
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.NUMERIC_STD.ALL;
use work.ctdah_pkg.ALL;
entity basic_trigger_core is
port (
wb_rst_i : in STD_LOGIC;
wb_clk_i : in STD_LOGIC;
pulse_i : in STD_LOGIC;
pulse_o : out STD_LOGIC;
pulse_n_o : out STD_LOGIC;
led_o : out STD_LOGIC;
level_i : in STD_LOGIC --! 0 here means ttl
);
end basic_trigger_core;
architecture Behavioral of basic_trigger_core is
signal s_pulse : STD_LOGIC;
signal s_deglitched_pulse : STD_LOGIC;
signal s_deglitched_pulse_d0 : STD_LOGIC;
signal s_monostable : STD_LOGIC;
begin
s_pulse <= pulse_i;
inst_debo: gc_debouncer
generic map( g_LENGTH => 2)
port map(rst => wb_rst_i,
clk => wb_clk_i,
input => s_pulse,
output => s_deglitched_pulse,
glitch_mask => "11");
pulse_monostable : gc_simple_monostable
generic map (g_PULSE_LENGTH => 20)
port map (rst => wb_rst_i,
clk => wb_clk_i,
input => s_deglitched_pulse,
output => pulse_o,
output_n => pulse_n_o);
led_monostable : gc_simple_monostable
generic map (g_PULSE_LENGTH => 100000000) --! 500ms
port map (
rst => wb_rst_i,
clk => wb_clk_i,
input => s_deglitched_pulse,
output => led_o);
--output_n not connected
end Behavioral;
----------------------------------------------------------------------------------
-- Company: CERN, BE-CO-HT
-- Engineer: Carlos Gil Soriano
--
-- Create Date: 09:58:06 10/12/2011
-- Design Name: HDL trigger top
-- Module Name: trigger - Behavioral
-- Project Name: CTDAH
-- Target Devices: Spartan 6
-- Tool versions:
-- Description: This is the wishbone trigger which receives a input
-- and outputs a trigger signal for the pulse converter.
-- It internally debounces the inputs and control the output
-- driver.
-- The registers it has can be modified via wishbone access.
-- Dependencies: none
--
-- Revision:
-- Revision 0.1
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.NUMERIC_STD.ALL;
entity basic_trigger_top is
generic(g_NUMBER_OF_CHANNELS : NATURAL := 6);
port (
clk_i : in STD_LOGIC;
led_pw_o : out STD_LOGIC;
led_err_o : out STD_LOGIC;
led_ttl_o : out STD_LOGIC;
fpga_o_en : out STD_LOGIC;
fpga_o_ttl_en : out STD_LOGIC;
fpga_o_inv_en : out STD_LOGIC;
fpga_o_blo_en : out STD_LOGIC;
level : in STD_LOGIC;
switch_i : in STD_LOGIC; --! General enable
manual_rst_n_o : out STD_LOGIC; --! It allows power sequencing of the
--! 24V rail after a security given
--! delay
pulse_i_front : in STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
pulse_o_front : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
pulse_i_rear : in STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
pulse_o_rear : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
led_o_front : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
led_o_rear : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
--! WR LEDs not to let them ON
led_link_up_o : out STD_LOGIC;
led_pps_o : out STD_LOGIC;
led_wr_ok_o : out STD_LOGIC;
inv_i : in STD_LOGIC_VECTOR(4 downto 1);
inv_o : out STD_LOGIC_VECTOR(4 downto 1));
end basic_trigger_top;
architecture Behavioral of basic_trigger_top is
signal s_pulse_i : STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
signal s_pulse_i_rear : STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
signal s_pulse_i_front : STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
signal s_pulse_o : STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
signal s_pulse_n_o : STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
signal s_led : STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS downto 1);
signal s_level : STD_LOGIC;
signal s_fpga_o_en : STD_LOGIC;
signal s_fpga_o_ttl_en : STD_LOGIC;
signal s_fpga_o_inv_en : STD_LOGIC;
signal s_fpga_o_blo_en : STD_LOGIC;
signal s_rst : STD_LOGIC_VECTOR(7 downto 0) := (others => '1');
component basic_trigger_core is
port (wb_rst_i : in STD_LOGIC;
wb_clk_i : in STD_LOGIC;
pulse_i : in STD_LOGIC;
pulse_o : out STD_LOGIC;
pulse_n_o : out STD_LOGIC;
led_o : out STD_LOGIC;
level_i : in STD_LOGIC);
end component;
begin
s_level <= level;
led_pw_o <= '0';
led_err_o <= '1';
led_ttl_o <= s_level;
led_link_up_o <= '1';
led_pps_o <= '1';
led_wr_ok_o <= '1';
s_pulse_i_front <= pulse_i_front when s_level = '0' else not(pulse_i_front);
s_pulse_i <= s_pulse_i_front or pulse_i_rear;
fpga_o_en <= s_fpga_o_en when switch_i = '1' else '0';
fpga_o_ttl_en <= s_fpga_o_ttl_en;
fpga_o_inv_en <= s_fpga_o_inv_en;
fpga_o_blo_en <= s_fpga_o_blo_en;
led_o_front <= not(s_led);--! No need of accurate sync, hence we place
led_o_rear <= not(s_led);--! some combinatorial here.
inv_o <= inv_i;--! As we have one Schmitt inverter in the input,
--! and a buffer in the output, there's no need
--! of invert here.
i_repetitors: for i in 1 to g_NUMBER_OF_CHANNELS generate
begin
trigger: basic_trigger_core
port map (
wb_rst_i => s_rst(7),
wb_clk_i => clk_i,
pulse_i => s_pulse_i(i),
pulse_o => s_pulse_o(i),
pulse_n_o => s_pulse_n_o(i),
led_o => s_led(i),
level_i => '0');
end generate i_repetitors;
p_reset_chain : process(clk_i) is
begin
if rising_edge(clk_i) then
s_rst(0) <= '0';
for i in 1 to 7 loop
s_rst(i) <= s_rst(i-1);
end loop;
if s_rst(7) = '1' then
--! First we reset the FPGA general output enable
--! Then we let one clock delay for the rest of signals
manual_rst_n_o <= '0';
s_fpga_o_en <= '0';
s_fpga_o_ttl_en <= '0';
s_fpga_o_inv_en <= '0';
s_fpga_o_blo_en <= '0';
else
manual_rst_n_o <= '1';
s_fpga_o_en <= '1';
s_fpga_o_ttl_en <= s_fpga_o_en;
s_fpga_o_inv_en <= s_fpga_o_en;
s_fpga_o_blo_en <= s_fpga_o_en;
end if;
end if;
end process p_reset_chain;
--! We register the outputs for better synchronization of the outputs
p_reg_output : process(clk_i) is
begin
if rising_edge(clk_i) then
if s_rst(7) = '1' then
pulse_o_rear <= (others => '0');
if s_level = '0' then
pulse_o_front <= (others => '0');
else
pulse_o_front <= (others => '1');
end if;
else
pulse_o_rear <= s_pulse_o;
case s_level is
when '0' =>
pulse_o_front <= s_pulse_o;
when others =>
pulse_o_front <= s_pulse_n_o;
end case;
end if;
end if;
end process;
end Behavioral;
-- TestBench Template
LIBRARY ieee;
USE ieee.std_logic_1164.ALL;
USE ieee.numeric_std.ALL;
ENTITY trigger_top_tb IS
END trigger_top_tb;
ARCHITECTURE behavior OF trigger_top_tb IS
constant c_NUMBER_OF_CHANNELS : NATURAL := 6;
constant CLK_PERIOD : time := 50 ns;
signal s_clk : STD_LOGIC;
-- signal s_rst : STD_LOGIC;
signal led_pw_o : STD_LOGIC;
signal led_err_o : STD_LOGIC;
signal led_ttl_o : STD_LOGIC;
signal fpga_o_en : STD_LOGIC;
signal fpga_o_ttl_en : STD_LOGIC;
signal fpga_o_inv_en : STD_LOGIC;
signal fpga_o_blo_en : STD_LOGIC;
signal level_i : STD_LOGIC;
signal switch_i : STD_LOGIC;
signal manual_rst_n_o : STD_LOGIC;
signal pulse_i_front : STD_LOGIC_VECTOR(c_NUMBER_OF_CHANNELS - 1 downto 0);
signal pulse_o_front : STD_LOGIC_VECTOR(c_NUMBER_OF_CHANNELS - 1 downto 0);
signal pulse_i_rear : STD_LOGIC_VECTOR(c_NUMBER_OF_CHANNELS - 1 downto 0);
signal pulse_o_rear : STD_LOGIC_VECTOR(c_NUMBER_OF_CHANNELS - 1 downto 0);
signal led_o : STD_LOGIC_VECTOR(c_NUMBER_OF_CHANNELS - 1 downto 0);
signal led_link_up_o : STD_LOGIC;
signal led_pps_o : STD_LOGIC;
signal led_wr_ok_o : STD_LOGIC;
signal inv_i : STD_LOGIC_VECTOR(3 downto 0);
signal inv_o : STD_LOGIC_VECTOR(3 downto 0);
component basic_trigger_top is
generic(g_NUMBER_OF_CHANNELS : NATURAL := 6);
port (
clk_i : in STD_LOGIC;
led_pw_o : out STD_LOGIC;
led_err_o : out STD_LOGIC;
led_ttl_o : out STD_LOGIC;
fpga_o_en : out STD_LOGIC;
fpga_o_ttl_en : out STD_LOGIC;
fpga_o_inv_en : out STD_LOGIC;
fpga_o_blo_en : out STD_LOGIC;
level_i : in STD_LOGIC;
switch_i : in STD_LOGIC; --! General enable
manual_rst_n_o : out STD_LOGIC; --! It allows power sequencing of the
--! 24V rail after a security given
--! delay
pulse_i_front : in STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS - 1 downto 0);
pulse_o_front : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS - 1 downto 0);
pulse_i_rear : in STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS - 1 downto 0);
pulse_o_rear : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS - 1 downto 0);
led_o_front : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS - 1 downto 0);
led_o_rear : out STD_LOGIC_VECTOR(g_NUMBER_OF_CHANNELS - 1 downto 0);
--! WR LEDs not to let them ON
led_link_up_o : out STD_LOGIC;
led_pps_o : out STD_LOGIC;
led_wr_ok_o : out STD_LOGIC;
inv_i : in STD_LOGIC_VECTOR(3 downto 0);
inv_o : out STD_LOGIC_VECTOR(3 downto 0));
end component;
begin
uut: basic_trigger_top
port map(
clk_i => s_clk,
-- rst_i => s_rst,
led_pw_o => led_pw_o,
led_err_o => led_err_o,
led_ttl_o => led_ttl_o,
fpga_o_en => fpga_o_en,
fpga_o_ttl_en => fpga_o_ttl_en,
fpga_o_inv_en => fpga_o_inv_en,
fpga_o_blo_en => fpga_o_blo_en,
level_i => level_i,
switch_i => switch_i,
manual_rst_n_o => manual_rst_n_o ,
pulse_i_front => pulse_i_front,
pulse_o_front => pulse_o_front,
pulse_i_rear => pulse_i_rear,
pulse_o_rear => pulse_o_rear,
led_o_front => led_o,
led_o_rear => led_o,
led_link_up_o => led_link_up_o,
led_pps_o => led_pps_o,
led_wr_ok_o => led_wr_ok_o,
inv_i => inv_i,
inv_o => inv_o);
s_clk_process :process
begin
s_clk <= '1';
wait for CLK_PERIOD/2;
s_clk <= '0';
wait for CLK_PERIOD/2;
end process;
tb_proc: process
procedure initial_cond(level : STD_LOGIC) is
begin
-- s_rst <= '1';
switch_i <= '0';
inv_i <= (others => '0');
pulse_i_front <= (others => level);
pulse_i_rear <= (others => '0');
level_i <= level;
wait for CLK_PERIOD*50;
-- s_rst <= '0';
wait for CLK_PERIOD*2;
wait until rising_edge(s_clk);
end;
procedure input_pulse (signal pulse : out
STD_LOGIC_VECTOR(c_NUMBER_OF_CHANNELS - 1 downto 0);
channel: NATURAL;
length : time;
level : STD_LOGIC) is
variable v_pulse : STD_LOGIC := level;
begin
pulse(channel) <= level;
wait until rising_edge(s_clk);
pulse(channel) <= not(level);
wait for length;
pulse(channel) <= level;
wait until rising_edge(s_clk);
end;
procedure input_front_pulse (length : time; channel : NATURAL;
level : STD_LOGIC) is
begin
input_pulse (pulse_i_front, channel, length, level);
end;
procedure input_rear_pulse (length : time; channel : NATURAL) is
begin
input_pulse (pulse_i_rear, channel, length, '0');
end;
procedure input_two_pulses (channel : NATURAL; level : STD_LOGIC;
length1 : time;
length2 : time;
offset : time) is
begin
pulse_i_front(channel) <= level;
pulse_i_rear(channel) <= '0';
wait until rising_edge(s_clk);
pulse_i_rear(channel) <= '1';
wait for offset;
wait until rising_edge(s_clk);
pulse_i_front(channel) <= not(level);
wait for length1 - offset;
wait until rising_edge(s_clk);
pulse_i_rear(channel) <= '0';
wait for length2 - length1;
wait until rising_edge(s_clk);
pulse_i_front(channel) <= level;
wait until rising_edge(s_clk);
end;
begin
-- input_front_pulse (1200 ns, 0, '1');
--! First we put one pulse from the Blocking part, then we wait one-clock
--! and lastly we put another clock from the TTL input
initial_cond('0');
input_rear_pulse (1200 ns, 0);
wait until rising_edge(s_clk);
input_front_pulse (1200 ns, 0, level_i);
wait for 40*CLK_PERIOD;
--! We reboot the machine and change the switch to indicate level_i is
--! TTL_N
initial_cond('1');
input_rear_pulse (1200 ns, 0);
wait until rising_edge(s_clk);
input_front_pulse (1200 ns, 0, level_i);
input_two_pulses(0, '1',
1000 ns,
1000 ns,
212 ns);
wait for 40*CLK_PERIOD;
assert false report "End of test." severity failure;
end process;
end;
onerror {resume}
quietly WaveActivateNextPane {} 0
add wave -noupdate /trigger_top_tb/s_clk
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_blo_en
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_en
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_inv_en
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_ttl_en
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_blo_en
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_en
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_inv_en
add wave -noupdate -group {Output enable} /trigger_top_tb/fpga_o_ttl_en
add wave -noupdate -group LEDs /trigger_top_tb/led_o
add wave -noupdate -group LEDs /trigger_top_tb/led_pw_o
add wave -noupdate -group LEDs /trigger_top_tb/led_err_o
add wave -noupdate -group LEDs /trigger_top_tb/led_ttl_o
add wave -noupdate -group LEDs /trigger_top_tb/led_o
add wave -noupdate -group LEDs /trigger_top_tb/led_pw_o
add wave -noupdate -group LEDs /trigger_top_tb/led_err_o
add wave -noupdate -group LEDs /trigger_top_tb/led_ttl_o
add wave -noupdate /trigger_top_tb/switch_i
add wave -noupdate /trigger_top_tb/level_i
add wave -noupdate /trigger_top_tb/pulse_i_front
add wave -noupdate /trigger_top_tb/pulse_i_rear
add wave -noupdate /trigger_top_tb/pulse_o_front
add wave -noupdate /trigger_top_tb/pulse_o_rear
add wave -noupdate /trigger_top_tb/uut/s_pulse_i
add wave -noupdate /trigger_top_tb/uut/s_pulse_i_rear
add wave -noupdate /trigger_top_tb/uut/s_pulse_i_front
add wave -noupdate /trigger_top_tb/s_clk
add wave -noupdate /trigger_top_tb/switch_i
add wave -noupdate /trigger_top_tb/level_i
add wave -noupdate /trigger_top_tb/pulse_i_front
add wave -noupdate /trigger_top_tb/pulse_i_rear
add wave -noupdate /trigger_top_tb/pulse_o_front
add wave -noupdate /trigger_top_tb/pulse_o_rear
add wave -noupdate /trigger_top_tb/uut/s_pulse_i
add wave -noupdate /trigger_top_tb/uut/s_pulse_i_rear
add wave -noupdate /trigger_top_tb/uut/s_pulse_i_front
add wave -noupdate /trigger_top_tb/uut/s_rst
TreeUpdate [SetDefaultTree]
WaveRestoreCursors {{Cursor 1} {5128424 ps} 0}
configure wave -namecolwidth 150
configure wave -valuecolwidth 100
configure wave -justifyvalue left
configure wave -signalnamewidth 1
configure wave -snapdistance 10
configure wave -datasetprefix 0
configure wave -rowmargin 4
configure wave -childrowmargin 2
configure wave -gridoffset 0
configure wave -gridperiod 1
configure wave -griddelta 40
configure wave -timeline 0
configure wave -timelineunits ps
update
WaveRestoreZoom {0 ps} {14175 ns}
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