LIBRARY ieee;
USE ieee.std_logic_1164.all;

ENTITY Scurve_1input_16bits_sk2_cms IS
	PORT (
			n_reset		: IN STD_LOGIC ;
			n_read		: IN STD_LOGIC ;
			subadd		: IN STD_LOGIC_VECTOR (6 DOWNTO 0);
			user_data	: INOUT STD_LOGIC_VECTOR (7 DOWNTO 0);
			En_Test_Scurve	: IN STD_LOGIC ;
			Resetb_Scurve	: IN STD_LOGIC ;
			PULSER		: IN STD_LOGIC ;
			TRIGGER			: IN STD_LOGIC ;
			Fast_CLK		: IN STD_LOGIC ; -- 5MHz clock
			nb_Scurves		: IN STD_LOGIC_VECTOR (1 DOWNTO 0);
			RazChn			: OUT	STD_LOGIC;
			SPY1			: OUT	STD_LOGIC;
			SPY2			: OUT	STD_LOGIC;
			SPY3			: OUT	STD_LOGIC;
			SPY4			: OUT	STD_LOGIC
		);
END Scurve_1input_16bits_sk2_cms;

ARCHITECTURE SYN OF Scurve_1input_16bits_sk2_cms IS
	SIGNAL EnableCountP		: Std_Logic;
	SIGNAL EnableCountT		: Std_Logic;
	SIGNAL CptFull,EndCpt	: Std_Logic_vector (0 downto 0);
	SIGNAL Reset_Int		: Std_Logic;
	SIGNAL temp0, temp1		: Std_Logic_vector (0 downto 0);
	SIGNAL RS_0, RS_1, RS_2	: Std_Logic_vector (0 downto 0);
	SIGNAL bascule_RS		: Std_Logic;
	SIGNAL sel_word			: Std_logic_vector (7 downto 0);
	SIGNAL sel_scurves		: Std_logic_vector (15 downto 0);
	SIGNAL pulse_cnt		: Std_logic_vector (15 downto 0);
	SIGNAL word_8, word_18	: Std_logic_vector (7 downto 0);
	SIGNAL trigger_cnt		: Std_logic_vector (15 downto 0);
	SIGNAL word_9, word_19	: Std_logic_vector (7 downto 0);
	SIGNAL aclr				: Std_Logic;
	
COMPONENT Read_Word
	PORT
	(
	reset		: IN	STD_LOGIC;
	n_read		: IN	STD_LOGIC;
	selection	: IN	STD_LOGIC;	-- selection lecture 
	word_x		: IN	STD_LOGIC_VECTOR(7 DOWNTO 0); -- registre à lire
	User_Data	: INOUT	STD_LOGIC_VECTOR(7 DOWNTO 0) -- bus USB
	);
END	COMPONENT;

component count16bits
	PORT
	(
		aclr		: IN STD_LOGIC ;
		clock		: IN STD_LOGIC ;
		cnt_en		: IN STD_LOGIC ;
		q		: OUT STD_LOGIC_VECTOR (15 DOWNTO 0)
	);
end component;

component flipflopaclr
	PORT (
			aclr	: IN STD_LOGIC ;
			clock	: IN STD_LOGIC ;
			q		: OUT STD_LOGIC_VECTOR (0 DOWNTO 0);
			data	: IN STD_LOGIC_VECTOR (0 DOWNTO 0)
	);
	END COMPONENT;

BEGIN
--								// Counters
count8bits_pulse : count16bits PORT MAP (
		aclr	 => aclr,
		clock	 => PULSER,
		cnt_en	 => EnableCountP,
		q	 => (pulse_cnt)
	);

count8bits_trig : count16bits PORT MAP (
		aclr	 => aclr,
		clock	 => RS_2(0), -- digital_probe1 : OR36 with latch
		cnt_en	 => EnableCountT,
		q	 => (trigger_cnt)
	);

--	// Machine de lecture du Word 8 (ecriture sur bus USB)
Read_Word8 : Read_Word PORT MAP (
		reset		=> n_reset,
		n_read		=> n_read,
		selection	=> sel_word(0), 
		word_x		=> word_8,	-- registre à lire
		User_Data	=> user_data -- bus USB
	);

--	// Machine de lecture du Word 18 (ecriture sur bus USB)
Read_Word18 : Read_Word PORT MAP (
		reset		=> n_reset,
		n_read		=> n_read,
		selection	=> sel_word(2), 
		word_x		=> word_18,	-- registre à lire
		User_Data	=> user_data -- bus USB
	);

--	// Machine de lecture du Word 9 (ecriture sur bus USB)
Read_Word9 : Read_Word PORT MAP (
		reset		=> n_reset,
		n_read		=> n_read,
		selection	=> sel_word(1), 
		word_x		=> word_9,	-- registre à lire
		User_Data	=> user_data -- bus USB
	);

--	// Machine de lecture du Word 19 (ecriture sur bus USB)
Read_Word19 : Read_Word PORT MAP (
		reset		=> n_reset,
		n_read		=> n_read,
		selection	=> sel_word(3), 
		word_x		=> word_19,	-- registre à lire
		User_Data	=> user_data -- bus USB
	);

Sync1 : flipflopaclr	PORT MAP(
		aclr	=> Reset_Int,
		clock	=> NOT(PULSER),
		data	=> "1",
		q		=> temp0
	);
Sync2 : flipflopaclr	PORT MAP(
		aclr	=> Reset_Int,
		clock	=> NOT(PULSER),
		data	=> temp0,
		q		=> temp1
	);

EnableCountP <= temp1(0);
EnableCountT <= (PULSER AND EnableCountP);
					
SyncEnd : flipflopaclr	PORT MAP(
		aclr	=> aclr,
		clock	=> NOT(PULSER),
		data	=> EndCpt,
		q		=> CptFull
	);

SyncTrig_1 : flipflopaclr	PORT MAP(
		aclr	=> NOT (EnableCountT),
		clock	=> Fast_CLK,
		data	=> RS_0,
		q		=> RS_1
	);

SyncTrig_2 : flipflopaclr	PORT MAP(
		aclr	=> NOT (EnableCountT),
		clock	=> Fast_CLK,
		data	=> RS_1,
		q		=> RS_2
	);

make_sel_word : PROCESS(subadd)
BEGIN
	CASE subadd IS
	WHEN "0001000"	=>	sel_word <= "00000001";	-- add(word_8)
	WHEN "0001001"	=>	sel_word <= "00000010";	-- add(word_9)
	WHEN "0010010"	=>	sel_word <= "00000100";	-- add(word_18)
	WHEN "0010011"	=>	sel_word <= "00001000";	-- add(word_19)
	WHEN OTHERS	=>	sel_word <= "00000000";
END CASE;
END PROCESS make_sel_word;

make_nb_scurve : PROCESS(nb_Scurves)
BEGIN
	CASE nb_Scurves IS
	WHEN "00"	=>	sel_scurves <= "0000000011001000";	-- 200
	WHEN "01"	=>	sel_scurves <= "0000001111101000";	-- 1000
	WHEN "10"	=>	sel_scurves <= "0010011100010000";	-- 10000
	WHEN "11"	=>	sel_scurves <= "1100001101010000";	-- 50000
	WHEN OTHERS	=>	sel_scurves <= "0000000011001000";
END CASE;
END PROCESS make_nb_scurve;

Reset_Int <= '1' WHEN (aclr = '1' OR En_Test_Scurve='0' OR CptFull(0)='1')
				ELSE '0';
EndCpt(0) <= '1' WHEN (sel_scurves <= pulse_cnt)
				ELSE '0';
				
word_18 <= pulse_cnt(15 downto 8);
word_8 <= pulse_cnt(7 downto 0);
word_19 <= trigger_cnt(15 downto 8);
word_9 <= trigger_cnt(7 downto 0);

aclr <= NOT(n_reset AND Resetb_Scurve);
bascule_RS <= (bascule_RS OR TRIGGER) AND EnableCountT;
RS_0(0) <= bascule_RS ;
RazChn <= EnableCountP AND NOT (EnableCountT) ;

SPY1 <= RS_2(0);
SPY2 <= CptFull(0);
SPY3 <= EnableCountP;
SPY4 <= EnableCountT;

END SYN;
