---------------------------------------------------------------------------------- -- Company: ETH Zurich, Institute for Particle Physics -- Engineer: Q. Weitzel, P. Vogler -- -- Create Date: 10:38:40 08/18/2010 -- Design Name: -- Module Name: FTU_rate_counter - Behavioral -- Project Name: -- Target Devices: -- Tool versions: -- Description: Entity to count trigger and sum patch rates of FTU board -- -- Dependencies: -- -- Revision: -- Revision 0.01 - File Created -- Additional Comments: -- ---------------------------------------------------------------------------------- library IEEE; use IEEE.STD_LOGIC_1164.ALL; use IEEE.STD_LOGIC_ARITH.ALL; use IEEE.STD_LOGIC_UNSIGNED.ALL; library ftu_definitions; USE ftu_definitions.ftu_array_types.all; USE ftu_definitions.ftu_constants.all; ---- Uncomment the following library declaration if instantiating ---- any Xilinx primitives in this code. --library UNISIM; --use UNISIM.VComponents.all; entity FTU_rate_counter is port( clk : in std_logic; cntr_reset : in std_logic; trigger : in std_logic; prescaling : in std_logic_vector(7 downto 0); counts : out integer range 0 to 2**16 - 1 := 0; overflow : out std_logic := '0'; new_rate : out std_logic ); end FTU_rate_counter; architecture Behavioral of FTU_rate_counter is signal counting_period : integer range 0 to 128*COUNTER_FREQUENCY := 128*COUNTER_FREQUENCY; signal period_finished : std_logic := '0'; signal trigger_counts : integer range 0 to 2**16 - 1 := 0; signal clk_1M_sig : std_logic; signal overflow_sig : std_logic := '0'; signal new_rate_sig : std_logic := '0'; component Clock_Divider port( clock_in : IN STD_LOGIC; clock_out : OUT STD_LOGIC ); end component; begin Inst_Clock_Divider : Clock_Divider port map ( clock_in => clk, clock_out => clk_1M_sig ); process(cntr_reset, clk_1M_sig) variable clk_cntr : integer range 0 to 128*COUNTER_FREQUENCY := 0; begin if cntr_reset = '1' then clk_cntr := 0; period_finished <= '1'; new_rate_sig <= '0'; counts <= 0; overflow <= '0'; elsif rising_edge(clk_1M_sig) then if (clk_cntr < counting_period - 1) then clk_cntr := clk_cntr + 1; period_finished <= '0'; new_rate_sig <= '0'; else clk_cntr := 0; period_finished <= '1'; new_rate_sig <= '1'; counts <= trigger_counts; overflow <= overflow_sig; end if; end if; end process; process(trigger, period_finished) begin if period_finished = '1' then trigger_counts <= 0; overflow_sig <= '0'; else if rising_edge(trigger) then if (trigger_counts < 2**16 - 1) then trigger_counts <= trigger_counts + 1; else trigger_counts <= 0; overflow_sig <= '1'; end if; end if; end if; end process; process(cntr_reset, prescaling) begin if rising_edge(cntr_reset) then --formula to calculate counting period from prescaling value if (prescaling = "00000000") then counting_period <= COUNTER_FREQUENCY / (2 * CNTR_FREQ_DIVIDER); else counting_period <= ((conv_integer(unsigned(prescaling)) + 1) / 2) * (COUNTER_FREQUENCY / CNTR_FREQ_DIVIDER); end if; end if; end process; new_rate <= new_rate_sig; end Behavioral; ---------------------------------------------------------------------------------- library IEEE; use IEEE.STD_LOGIC_1164.ALL; use IEEE.STD_LOGIC_ARITH.ALL; use IEEE.STD_LOGIC_UNSIGNED.ALL; library ftu_definitions; USE ftu_definitions.ftu_array_types.all; USE ftu_definitions.ftu_constants.all; entity Clock_Divider is generic( divider : integer := INT_CLK_FREQUENCY / COUNTER_FREQUENCY ); port( clock_in : in std_logic; clock_out : out std_logic := '0' ); end entity Clock_Divider; architecture RTL of Clock_Divider is begin process (clock_in) variable Z: integer range 0 to divider - 1; begin if rising_edge(clock_in) then if (Z < divider - 1) then Z := Z + 1; else Z := 0; end if; if (Z = 0) then clock_out <= '1'; end if; if (Z = divider / 2) then clock_out <= '0'; end if; end if; end process; end architecture RTL;