##// END OF EJS Templates
Versión con adquisición continua
Versión con adquisición continua

File last commit:

r224:225
r224:225
Show More
joiner_samp.vhd
324 lines | 9.5 KiB | text/x-vhdl | VhdlLexer
----------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 11:35:58 02/20/2017
-- Design Name:
-- Module Name: joiner_samp - Behavioral
-- Project Name:
-- Target Devices:
-- Tool versions:
-- Description:
--
-- Dependencies:
--
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
--
----------------------------------------------------------------------------------
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
-- Uncomment the following library declaration if using
-- arithmetic functions with Signed or Unsigned values
use IEEE.NUMERIC_STD.ALL;
-- Uncomment the following library declaration if instantiating
-- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity joiner_samp is
GENERIC(
DBIT_SZ: INTEGER :=3;
BITS_COUNT_SZ: INTEGER :=3;
RESUL_NP_SZ: INTEGER :=40;
SAMPLE_SZ: INTEGER :=24;
SAMPLE_COUNT_SZ: INTEGER := 12;
HEADER_NIB_SZ: INTEGER := 4;
DATA_HEADER_NIB_SZ: INTEGER := 4;
CH_COUNT_SZ: INTEGER :=4
);
PORT(
--Channel number
chn_id_acq: IN STD_LOGIC_VECTOR((CH_COUNT_SZ-1) downto 0);
--Reset del sistema
rst_bar: IN STD_LOGIC;
--Reloj principal
clk_main: IN STD_LOGIC; --Reloj externo de por lo menos 32MHz proveniente del m�dulo de sincronizaci�n
--Senhales con el microcontrolador
clk_acq: IN STD_LOGIC; --Senhal de "reloj" proveniente del XMEGA por canal del m�dulo de adquisici�n
chn_bits_acq: IN STD_LOGIC_VECTOR((DBIT_SZ-1) downto 0); --Nibble de datos provenientes del XMEGA por canal del m�dulo de adquisici�n
--Data req
dat_req_ch: IN STD_LOGIC;
--Senhales hacia el sistema
resul_samp: OUT STD_LOGIC_VECTOR((RESUL_NP_SZ-1) downto 0); --Salida al espacio de memoria para almacenar datos crudos
rdy_samp: OUT STD_LOGIC; --Senhal para indicar que el dato fue obtenido satisfactoriamente y esta listo para ser almacenado en memoria
ack_in: IN STD_LOGIC --Senhal para indicar que el dato presentado fue leido o no
);
end joiner_samp;
architecture Behavioral of joiner_samp is
--Registros para sincronizacion
SIGNAL clk_acq_r : std_logic_vector (2 downto 0) :=(OTHERS=>'1');
SIGNAL chn_bits_acq_bit0 : std_logic_vector (1 downto 0) :=(OTHERS=>'0');
SIGNAL chn_bits_acq_bit1 : std_logic_vector (1 downto 0) :=(OTHERS=>'0');
SIGNAL chn_bits_acq_bit2 : std_logic_vector (1 downto 0) :=(OTHERS=>'0');
--Senhales para deteccion de flancos
SIGNAL clk_acq_rise : std_logic :='0';
--Senhal Interna de dato completo
SIGNAL rdy_mem_aux: std_logic :='0';
--Constantes asociadas al contador de nibbles
SIGNAL dbits_counter : std_logic_vector ((BITS_COUNT_SZ-1) downto 0) :=(OTHERS=>'0');
CONSTANT TOP_COUNT: std_logic_vector((BITS_COUNT_SZ-1) downto 0) :="111";
CONSTANT BASE_COUNT: std_logic_vector((BITS_COUNT_SZ-1) downto 0) :=(OTHERS=>'0');
--Senhales para almacenar resultado a siguiente etapa
SIGNAL resul_mem_internal: std_logic_vector((SAMPLE_SZ-1) downto 0) :=(OTHERS=>'0');
SIGNAL resul_mem_internal_aux: std_logic_vector((RESUL_NP_SZ-1) downto 0) :=(OTHERS=>'0');
--Estados de la maquina de presentacion de datos a la RAM y RAM Controller
TYPE data_states IS ( idle,
data_pres, data_proc
);
SIGNAL data_cur_state: data_states := idle;
SIGNAL data_next_state: data_states := idle;
--Estados de la maquina de construccion de paquete
TYPE pack_states IS ( idle,
building
);
SIGNAL pack_cur_state : pack_states := idle;
SIGNAL pack_next_state : pack_states := idle;
SIGNAL nibble_aux: STD_LOGIC_VECTOR((DBIT_SZ-1) downto 0) := (OTHERS => '0');
SIGNAL samp_count: STD_LOGIC_VECTOR((SAMPLE_COUNT_SZ-1) downto 0) := (OTHERS => '0');
CONSTANT TOP_SAMPLES_COUNT: std_logic_vector((SAMPLE_COUNT_SZ-1) downto 0) := "001111101000";
begin
--Etapa de sincronizacion
sync_data: PROCESS(clk_main)
BEGIN
IF(rising_edge(clk_main)) THEN
IF(rst_bar = '0') THEN
chn_bits_acq_bit0 <= (OTHERS=>'0');
chn_bits_acq_bit1 <= (OTHERS=>'0');
chn_bits_acq_bit2 <= (OTHERS=>'0');
ELSE
chn_bits_acq_bit0 <= chn_bits_acq_bit0(0) & chn_bits_acq(0);
chn_bits_acq_bit1 <= chn_bits_acq_bit1(0) & chn_bits_acq(1);
chn_bits_acq_bit2 <= chn_bits_acq_bit2(0) & chn_bits_acq(2);
END IF;
END IF;
END PROCESS;
nibble_aux <= chn_bits_acq_bit2(1) &
chn_bits_acq_bit1(1) & chn_bits_acq_bit0(1);
--Etapa de deteccion de flancos
edge_det: PROCESS(clk_main)
BEGIN
IF(rising_edge(clk_main)) THEN
IF(rst_bar = '0') THEN
clk_acq_r <=(OTHERS =>'1');
clk_acq_rise <= '0';
ELSE
clk_acq_r <= clk_acq_r(1 downto 0) & clk_acq;
IF (clk_acq_r(2 downto 1) = "01") THEN
clk_acq_rise <= '1';
ELSE
clk_acq_rise <= '0';
END IF;
END IF;
END IF;
END PROCESS;
--Etapa de deteccion de cabecera y almacenamiento
cambio_estados: PROCESS(clk_main)
BEGIN
IF (rising_edge(clk_main)) THEN
IF(rst_bar = '0') THEN
pack_cur_state <= idle;
ELSE
pack_cur_state <= pack_next_state;
END IF;
END IF;
END PROCESS;
salidas_estados: PROCESS(pack_cur_state, dbits_counter,clk_acq_rise,dat_req_ch)
BEGIN
CASE pack_cur_state IS
WHEN idle =>
IF(dat_req_ch = '1') THEN
pack_next_state <= building;
ELSE
pack_next_state <= idle;
END IF;
WHEN building =>
IF(clk_acq_rise = '1') THEN
IF (dbits_counter = TOP_COUNT) THEN
pack_next_state <= idle;
ELSE
pack_next_state <= building;
END IF;
ELSE
pack_next_state <= building;
END IF;
WHEN OTHERS =>
pack_next_state <= idle;
END CASE;
END PROCESS;
save_bits: PROCESS(clk_main)
BEGIN
IF(rising_edge(clk_main)) THEN
IF (rst_bar = '0') THEN
dbits_counter <=(OTHERS => '0') ;
resul_mem_internal <=(OTHERS => '0') ;
ELSE
IF (pack_cur_state = building) THEN
IF(dat_req_ch = '1') THEN
dbits_counter <=(OTHERS => '0') ;
ELSIF(clk_acq_rise = '1') THEN
dbits_counter <=std_logic_vector(unsigned(dbits_counter)+1);
CASE dbits_counter IS
WHEN "000" =>
resul_mem_internal(23 downto 21) <= nibble_aux;
WHEN "001" =>
resul_mem_internal(20 downto 18) <= nibble_aux;
WHEN "010" =>
resul_mem_internal(17 downto 15) <= nibble_aux;
WHEN "011" =>
resul_mem_internal(14 downto 12) <= nibble_aux;
WHEN "100" =>
resul_mem_internal(11 downto 9) <= nibble_aux;
WHEN "101" =>
resul_mem_internal(8 downto 6) <= nibble_aux;
WHEN "110"=>
resul_mem_internal(5 downto 3) <= nibble_aux;
WHEN "111"=>
resul_mem_internal(2 downto 0) <= nibble_aux;
dbits_counter <=(OTHERS => '0');
WHEN OTHERS =>
dbits_counter <=(OTHERS => '0');
END CASE;
END IF;
END IF;
END IF;
END IF;
END PROCESS;
resul_mem_internal_aux(39 downto 36) <= chn_id_acq;
guardar_dato: PROCESS(clk_main)
BEGIN
IF (rising_edge(clk_main)) THEN
IF(data_cur_state = idle) THEN
IF(rdy_mem_aux = '1') THEN
resul_mem_internal_aux((RESUL_NP_SZ-5)downto 0) <= --chn_id_acq &
samp_count &
resul_mem_internal;
END IF;
END IF;
END IF;
END PROCESS;
conteo_muestra: PROCESS(clk_main)
BEGIN
IF (rising_edge(clk_main)) THEN
IF(dat_req_ch = '1') THEN
IF(samp_count = TOP_SAMPLES_COUNT) THEN
samp_count <= (OTHERS=>'0');
ELSE
samp_count <= std_logic_vector(unsigned(samp_count)+1) ;
END IF;
END IF;
END IF;
END PROCESS;
output_rdy_mem: PROCESS(clk_main)
BEGIN
IF(rising_edge(clk_main)) THEN
IF (rst_bar = '0') THEN
rdy_mem_aux <= '0';
ELSE
IF((dbits_counter = TOP_COUNT)) THEN
IF((clk_acq_rise = '1')) THEN
rdy_mem_aux <= '1';
END IF;
ELSE
rdy_mem_aux <= '0';
END IF;
END IF;
END IF;
END PROCESS;
cambio_estados_data: PROCESS(clk_main)
BEGIN
IF (rising_edge(clk_main)) THEN
IF(rst_bar = '0') THEN
data_cur_state <= idle;
ELSE
data_cur_state <= data_next_state;
END IF;
END IF;
END PROCESS;
salidas_estados_data: PROCESS(resul_mem_internal_aux,data_cur_state,ack_in,rdy_mem_aux)
BEGIN
CASE data_cur_state IS
WHEN idle =>
rdy_samp <= '0';
resul_samp <= (OTHERS => '0');
IF (rdy_mem_aux = '1') THEN
data_next_state <= data_pres;
ELSE
data_next_state <= idle;
END IF;
WHEN data_pres =>
rdy_samp <= '1';
resul_samp <= resul_mem_internal_aux;
IF (ack_in = '1') THEN
data_next_state <= data_proc;
ELSE
data_next_state <= data_pres;
END IF;
WHEN data_proc =>
rdy_samp <= '1';
resul_samp <= resul_mem_internal_aux;
IF (ack_in = '0') THEN --Si ya est� ocupado con el dato antes presentado entonces ya puedo ir pidiendo otro dato
data_next_state <= idle;
ELSE
data_next_state <= data_proc;
END IF;
WHEN OTHERS =>
rdy_samp <= '0';
resul_samp <= (OTHERS => '0');
data_next_state <= idle;
END CASE;
END PROCESS;
end Behavioral;