--- /dev/null
+kate: space-indent on; indent-width 3; tab-width 3; replace-tabs on;
--- /dev/null
+#!/usr/bin/env perl
+# little tool to decode a CTS subevent provided via stdin in the daq_anal
+# format. just copy and paste the frame starting with the subevent header
+
+use strict;
+use warnings;
+use Data::Dumper;
+
+my $input = '';
+while (my $line = <STDIN>) {
+ chomp($line);
+ last unless $line;
+ $input .= $line . ' ';
+};
+
+my @dec = grep(/^0x/, (split /\s+/, $input));
+shift @dec;
+
+
+my $word = hex(shift @dec);
+my $evt = {
+ 'itc_state' => $word & 0xffff,
+ 'input_counters' => ($word >> 16) & 0xf,
+ 'itc_counters' => ($word >> 20) & 0xf,
+ 'idledead' => ($word >> 25) & 0x1,
+ 'trigger_stats' => ($word >> 26) & 0x1,
+ 'timestamp' => ($word >> 27) & 0x1,
+ 'etm_mode' => ($word >> 28) & 0x2
+};
+
+print Dumper $evt;
+
+for(my $i=0; $i < $evt->{'input_counters'}; $i++) {
+ printf "Input %d Level Counter: % 14d\n", $i, hex(shift(@dec));
+ printf "Input %d Edge Counter: % 14d\n", $i, hex(shift(@dec));
+}
+
+for(my $i=0; $i < $evt->{'itc_counters'}; $i++) {
+ printf "ITC %02d Level Counter: % 14d\n", $i, hex(shift(@dec));
+ printf "ITC %02d Edge Counter: % 14d\n", $i, hex(shift(@dec));
+}
+
+if ($evt->{'idledead'}) {
+ printf "Idle Time: %e s\n", hex(shift(@dec)) * 1e-8;
+ printf "Dead Time: %e s\n", hex(shift(@dec)) * 1e-8;
+}
+
+if ($evt->{'trigger_stats'}) {
+ printf "Trigger asserted : % 14d cycles\n", hex(shift(@dec));
+ printf "Trigger rising edge: % 14d edges\n", hex(shift(@dec));
+ printf "Trigger accepted : % 14d evts\n", hex(shift(@dec));
+}
+
+if ($evt->{'timestamp'}) {
+ printf "Timestamp: %d cycles\n", hex(shift(@dec));
+}
+
+my $etmno = (!$evt->{'timestamp'} < 2) ? (!$evt->{'timestamp'}) : ((!$evt->{'timestamp'} == 2) ? 4 : -1);
+if ($etmno >= 0) {
+ for(my $i=0; $i < $etmno; $i++) {
+ printf "ETM data: %s\n", $i, shift(@dec);
+ }
+}
library work;
use work.trb_net_components.all;
+ use work.trb_net_std.all;
use work.CTS_PKG.ALL;
-- Debug and status registers
--
-- 0x04 Buffered trigger status
-- 15 : 00 Trigger bitmask (before filtering)
--- 19 : 16 Trigger type
+-- 19 :16 Trigger type
--
-- 0x05 TD FSM State (Trigger Distribution). One-Hot-Encoding:
-- 0 TD_FSM_IDLE
--
-- 0x0d Event Builder selection
-- 15 : 00 Event Builder mask (default: 0x1)
--- 23 : 16 Number of events before selecting next builder (useful to aggregate events to support large data packets
+-- 23 : 16 Number of events before selecting next builder (useful to aggregate events to support large data packets)
-- 27 : 24 Event Builder number of calibration trigger
-- 28 If asserted: Use special event builder for calibration trigger, otherwise, use ordinary round robin selection.
-- </address_table>
TRIGGER_RAND_PULSER : integer range 0 to 1 := 1;
ADDON_LINE_COUNT : integer := 22; -- number of lines available from add-on board
+
TRIGGER_ADDON_COUNT : integer range 0 to 15 := 2; -- number of module instances used to patch through those lines
+ ADDON_GROUPS : integer range 1 to 8 := 5;
+ ADDON_GROUP_UPPER : CTS_GROUP_CONFIG_T := (3,7,11,12,13, others=>'0');
EXTERNAL_TRIGGER_ID : std_logic_vector(7 downto 0) := X"00";
TIME_REFERENCE_OUT : out std_logic;
ADDON_TRIGGERS_IN : in std_logic_vector(ADDON_LINE_COUNT-1 downto 0) := (others => '0');
+ ADDON_GROUP_ACTIVITY_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
+ ADDON_GROUP_SELECTED_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
-- External trigger logic
EXT_TRIGGER_IN : in std_logic;
-- we can switch to a sequential process instead of a parallel priority encoder
eb_sel_loop: for i in 0 to 15 loop
if eb_mask_buf_i(i) = '1' then
- eb_mask_buf_i(i) <= '0';
+ if OR_ALL(eb_mask_buf_i(15 downto i+1)) = '0' then
+ eb_mask_buf_i <= eb_mask_i;
+ else
+ eb_mask_buf_i(i downto 0) <= (others => '0');
+ end if;
+
eb_selection_i <= STD_LOGIC_VECTOR(TO_UNSIGNED(i, 4));
exit eb_sel_loop;
TRIGGER_COIN_COUNT => TRIGGER_COIN_COUNT,
TRIGGER_PULSER_COUNT => TRIGGER_PULSER_COUNT,
TRIGGER_RAND_PULSER => TRIGGER_RAND_PULSER,
+
ADDON_LINE_COUNT => ADDON_LINE_COUNT,
+ ADDON_GROUPS => ADDON_GROUPS,
+ ADDON_GROUP_UPPER => ADDON_GROUP_UPPER,
+
TRIGGER_ADDON_COUNT => TRIGGER_ADDON_COUNT,
EXTERNAL_TRIGGER_ID => EXTERNAL_TRIGGER_ID
)
port map (
CLK_IN => CLK,
+ CLK_1KHZ_IN => clk_1khz_i,
RESET_IN => RESET,
TRIGGERS_IN => TRIGGERS_IN,
ADDON_TRIGGERS_IN => ADDON_TRIGGERS_IN,
+ ADDON_GROUP_ACTIVITY_OUT => ADDON_GROUP_ACTIVITY_OUT,
+ ADDON_GROUP_SELECTED_OUT => ADDON_GROUP_SELECTED_OUT,
EXT_TRIGGER_IN => EXT_TRIGGER_IN,
EXT_STATUS_IN => EXT_STATUS_IN,
use ieee.numeric_std.all;
package cts_pkg is
+ type CTS_GROUP_CONFIG_T is array(0 to 7) of integer;
+
component CTS is
generic (
-- The total number of trigger units below has to be below 16
ADDON_LINE_COUNT : integer range 0 to 255 := 22; -- number of lines available from add-on board
TRIGGER_ADDON_COUNT : integer range 0 to 15 := 2; -- number of module instances used to patch through those lines
+ ADDON_GROUPS : integer range 1 to 8 := 5;
+ ADDON_GROUP_UPPER : CTS_GROUP_CONFIG_T := (3,7,11,12,13, others=>'0');
EXTERNAL_TRIGGER_ID : std_logic_vector(7 downto 0) := X"00";
TIME_REFERENCE_OUT : out std_logic;
ADDON_TRIGGERS_IN : in std_logic_vector(ADDON_LINE_COUNT-1 downto 0) := (others => '0');
+ ADDON_GROUP_ACTIVITY_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
+ ADDON_GROUP_SELECTED_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
-- External trigger logic
EXT_TRIGGER_IN : in std_logic;
ADDON_LINE_COUNT : integer range 0 to 255 := 22; -- number of lines available from add-on board
TRIGGER_ADDON_COUNT : integer range 0 to 15 := 2; -- number of module instances used to patch through those lines
+ ADDON_GROUPS : integer range 1 to 8 := 5;
+ ADDON_GROUP_UPPER : CTS_GROUP_CONFIG_T := (3,7,11,12,13, others=>'0');
+
EXTERNAL_TRIGGER_ID : std_logic_vector(7 downto 0) := X"00"
);
port (
CLK_IN : in std_logic;
+ CLK_1KHZ_IN : in std_logic;
RESET_IN : in std_logic;
-- Input pins
TRIGGERS_IN : in std_logic_vector(TRIGGER_INPUT_COUNT - 1 downto 0);
ADDON_TRIGGERS_IN : in std_logic_vector(ADDON_LINE_COUNT-1 downto 0) := (others => '0');
+ ADDON_GROUP_ACTIVITY_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
+ ADDON_GROUP_SELECTED_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
-- External
EXT_TRIGGER_IN : in std_logic;
TRIGGER_COIN_COUNT : integer range 0 to 15 := 4;
TRIGGER_PULSER_COUNT : integer range 0 to 15 := 2;
TRIGGER_RAND_PULSER : integer range 0 to 15 := 1;
- TRIGGER_ADDON_COUNT : integer range 0 to 15 := 2;
+ TRIGGER_ADDON_COUNT : integer range 0 to 15 := 2;
ADDON_LINE_COUNT : integer range 0 to 255 := 22;
+ ADDON_GROUPS : integer range 1 to 8 := 5;
+ ADDON_GROUP_UPPER : CTS_GROUP_CONFIG_T := (3,7,11,12,13, others=>'0');
EXTERNAL_TRIGGER_ID : std_logic_vector(7 downto 0) := X"00"
);
port (
CLK_IN : in std_logic;
+ CLK_1KHZ_IN : in std_logic;
RESET_IN : in std_logic;
-- Trigger Inputs
TRIGGERS_IN : in std_logic_vector(TRIGGER_INPUT_COUNT-1 downto 0);
+
ADDON_TRIGGERS_IN : in std_logic_vector(ADDON_LINE_COUNT-1 downto 0) := (others => '0');
-
+ ADDON_GROUP_ACTIVITY_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
+ ADDON_GROUP_SELECTED_OUT : out std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
+
-- External
EXT_TRIGGER_IN : in std_logic;
EXT_STATUS_IN : in std_logic_vector(31 downto 0) := X"00000000";
-- Add On
type trigger_addon_configs_t is array(TRIGGER_ADDON_COUNT - 1 downto 0) of std_logic_vector(7 downto 0);
signal trigger_addon_configs_i : trigger_addon_configs_t;
+ signal addon_group_activity_i : std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
+ signal addon_group_selected_i : std_logic_vector(ADDON_GROUPS-1 downto 0) := (others => '0');
-- Trigger Type Assoc
type trigger_type_assoc_t is array(0 to 15) of std_logic_vector(3 downto 0);
CHANNEL_COUNTERS_OUT(i*32 + 31 downto i*32) <= channel_counters_i(i);
CHANNEL_EDGE_COUNTERS_OUT(i*32 + 31 downto i*32) <= channel_edge_counters_i(i);
end generate;
+
+-- AddOn Leds
+-----------------------------------------
+ process(CLK_IN) is
+ variable from : integer;
+ begin
+ if rising_edge(CLK_IN) then
+ from := 0;
+ if CLK_1KHZ_IN ='1' then
+ addon_group_activity_i <= (others => '0');
+
+ else
+ for i in 0 to ADDON_GROUPS-1 loop
+ addon_group_activity_i(i) <= addon_group_activity_i(i) or
+ OR_ALL(ADDON_TRIGGERS_IN(ADDON_GROUP_UPPER(i) downto from));
+
+ addon_group_selected_i(i) <= '0';
+ for j in 0 to TRIGGER_ADDON_COUNT-1 loop
+ if from <= to_integer( UNSIGNED(trigger_addon_configs_i(j)) ) and
+ to_integer( UNSIGNED(trigger_addon_configs_i(j)) ) <= ADDON_GROUP_UPPER(i) then
+ addon_group_selected_i(i) <= '1';
+ end if;
+ end loop;
+
+ from := ADDON_GROUP_UPPER(i)+1;
+ end loop;
+ end if;
+ end if;
+ end process;
+
+ ADDON_GROUP_ACTIVITY_OUT <= addon_group_activity_i;
+ ADDON_GROUP_SELECTED_OUT <= addon_group_selected_i;
+-- RegIO
+-----------------------------------------
proc_regio: process(CLK_IN) is
variable addr : integer range 0 to 255;
variable ref_addr : integer range 0 to 255;
constant CTS_ADDON_LINE_COUNT : integer := 14;
signal cts_addon_triggers_in : std_logic_vector(CTS_ADDON_LINE_COUNT-1 downto 0);
+ signal cts_addon_activity_i,
+ cts_addon_selected_i : std_logic_vector(4 downto 0);
signal cts_trg_send : std_logic;
signal cts_trg_type : std_logic_vector(3 downto 0);
signal tdc_ctrl_reg : std_logic_vector(5*32-1 downto 0);
signal tdc_debug : std_logic_vector(15 downto 0);
-
+ signal led_time_ref_i : std_logic;
begin
-- MBS Module
gen_mbs_vulom_as_etm : if ETM_CHOICE = ETM_CHOICE_MBS_VULOM generate
TRIGGER_PULSER_COUNT => 2,
TRIGGER_RAND_PULSER => 1,
TRIGGER_ADDON_COUNT => 2,
- ADDON_LINE_COUNT => CTS_ADDON_LINE_COUNT
+
+ ADDON_LINE_COUNT => CTS_ADDON_LINE_COUNT,
+ ADDON_GROUPS => 5,
+ ADDON_GROUP_UPPER => (3,7,11,12,13, others=>0)
)
port map (
CLK => clk_100_i,
RESET => reset_i,
TRIGGERS_IN => trigger_in_buf_i,
- ADDON_TRIGGERS_IN => cts_addon_triggers_in,
TRIGGER_BUSY_OUT => trigger_busy_i,
TIME_REFERENCE_OUT => cts_trigger_out,
+ ADDON_TRIGGERS_IN => cts_addon_triggers_in,
+ ADDON_GROUP_ACTIVITY_OUT => cts_addon_activity_i,
+ ADDON_GROUP_SELECTED_OUT => cts_addon_selected_i,
+
EXT_TRIGGER_IN => cts_ext_trigger,
EXT_STATUS_IN => cts_ext_status,
EXT_CONTROL_OUT => cts_ext_control,
FEE_DATA_FINISHED_OUT => cts_rdo_finished
);
- process is begin
+ process is
+ begin
wait until rising_edge(clk_100_i);
cts_addon_triggers_in( 3 downto 0) <= ECL_IN;
cts_addon_triggers_in( 7 downto 4) <= JIN1;
cts_addon_triggers_in(13 downto 12) <= NIM_IN;
end process;
+ LED_BANK(7 downto 6) <= cts_addon_activity_i(4 downto 3);
+ LED_RJ_GREEN <= (
+ 0 => cts_addon_activity_i(1),
+ 1 => cts_addon_activity_i(2),
+ 5 => cts_addon_activity_i(0),
+ others => '0'
+ );
+
+ LED_RJ_RED <= (
+ 0 => cts_addon_selected_i(1),
+ 1 => cts_addon_selected_i(2),
+ 5 => cts_addon_selected_i(0),
+ others => '0'
+ );
+
-- cts_rdo_trg_status_bits <= cts_rdo_trg_status_bits_cts OR cts_rdo_trg_status_bits_additional;
TRIGGER_OUT <= cts_trigger_out;
TRIGGER_OUT2 <= cts_trigger_out;
TRG_FANOUT_ADDON <= cts_trigger_out;
+
+end process;
+
+process(clk_100_i) is begin
+ if rising_edge(clk_100_i) then
+ if timer_ticks(0) = '1' then
+ led_time_ref_i <= '0';
+ else
+ led_time_ref_i <= led_time_ref_i or cts_trigger_out;
+ end if;
+ end if;
end process;
JOUTLVDS <= x"00";
JTTL <= x"0000";
- LED_BANK <= x"FF";
- LED_RJ_GREEN <= "111111";
- LED_RJ_RED <= "111111";
- LED_FAN_GREEN <= '1';
- LED_FAN_ORANGE <= '1';
- LED_FAN_RED <= '1';
- LED_FAN_YELLOW <= '1';
+ LED_BANK(5 downto 0) <= (others => '0');
+ LED_FAN_GREEN <= led_time_ref_i;
+ LED_FAN_ORANGE <= '0';
+ LED_FAN_RED <= trigger_busy_i;
+ LED_FAN_YELLOW <= '0';
---------------------------------------------------------------------------