Initial commit
This commit is contained in:
193
FiltroHDL/Filter.vhd
Normal file
193
FiltroHDL/Filter.vhd
Normal file
@@ -0,0 +1,193 @@
|
||||
library IEEE;
|
||||
use IEEE.STD_LOGIC_1164.ALL;
|
||||
use IEEE.NUMERIC_STD.ALL;
|
||||
use work.array_functions.all;
|
||||
|
||||
entity Filter is
|
||||
generic (
|
||||
CLK_FREQ : integer := 200e6;
|
||||
DATA_RATE: integer := 250e3;
|
||||
|
||||
|
||||
SIMETRIC : boolean := TRUE;
|
||||
CONSTANTS : array_of_integers := (-10,-9,-8,-7,-6,-5,-4,3,-2,-1,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20)
|
||||
|
||||
);
|
||||
port (
|
||||
clk_i : in std_logic;
|
||||
enable: in std_logic;
|
||||
reset: in std_logic;
|
||||
|
||||
d_i : in std_logic;
|
||||
d_o : out std_logic
|
||||
);
|
||||
end Filter;
|
||||
|
||||
architecture Behavioral of Filter is
|
||||
|
||||
--~ Array con las constantes, ordenadas de 0 a N
|
||||
constant K : array_of_integers := reorder_array(CONSTANTS, SIMETRIC);
|
||||
--~ Tamaño del array
|
||||
constant N : integer := K'length;
|
||||
--~ Frecuencia a la que se samplea la entrada
|
||||
constant SAMPLE_RATE : integer := DATA_RATE * (N-1);
|
||||
|
||||
--~ Shift Register
|
||||
signal LSR : std_logic_vector(N-1 downto 0) := (others => '0');
|
||||
|
||||
|
||||
--~ Constante y señales para el contador/divisor de frecuencia
|
||||
constant MAX_COUNT : integer := CLK_FREQ / (SAMPLE_RATE);
|
||||
signal counter : integer range 0 to MAX_COUNT - 1 := 0;
|
||||
signal sample_clk_s : std_logic := '0';
|
||||
|
||||
|
||||
--~ Acumulador:
|
||||
signal accum: integer range -MAX_RANGE to MAX_RANGE := 0;
|
||||
signal i : integer range 0 to N-1 := 0;
|
||||
signal i_rst : std_logic := '0';
|
||||
|
||||
|
||||
signal d_s : std_logic := '0';
|
||||
|
||||
type STATUS_T is ( wait_start,
|
||||
clear,
|
||||
sum_loop );
|
||||
|
||||
signal state, next_state : STATUS_T := wait_start;
|
||||
|
||||
|
||||
|
||||
|
||||
begin
|
||||
|
||||
d_o <= d_s;
|
||||
|
||||
--~ Proceso sincrónico para cambio de estados
|
||||
stateProcess:
|
||||
process(clk_i)
|
||||
begin
|
||||
if ( rising_edge(clk_i) ) then
|
||||
if ( reset = '1' ) then
|
||||
state <= wait_start;
|
||||
elsif ( enable = '1' ) then
|
||||
state <= next_state;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
|
||||
--~ Tranciciones entre estados
|
||||
stateTransition:
|
||||
process(state,i,sample_clk_s)
|
||||
begin
|
||||
case state is
|
||||
when wait_start =>
|
||||
i_rst <= '0';
|
||||
|
||||
if ( sample_clk_s = '1' ) then
|
||||
next_state <= clear;
|
||||
else
|
||||
next_state <= wait_start;
|
||||
end if;
|
||||
|
||||
when clear =>
|
||||
i_rst <= '1';
|
||||
|
||||
next_state <= sum_loop;
|
||||
|
||||
when sum_loop =>
|
||||
i_rst <= '0';
|
||||
|
||||
if ( i = N-1 ) then
|
||||
next_state <= wait_start;
|
||||
else
|
||||
next_state <= sum_loop;
|
||||
end if;
|
||||
|
||||
end case;
|
||||
end process;
|
||||
|
||||
|
||||
|
||||
--~ Proceso sincrónico para contador interno y para acumulador
|
||||
process(clk_i)
|
||||
begin
|
||||
if ( rising_edge(clk_i) ) then
|
||||
|
||||
if ( enable = '1' ) then
|
||||
if ( i_rst = '1' ) then
|
||||
i <= 0;
|
||||
accum <= 0;
|
||||
|
||||
else
|
||||
if ( i < N-1 ) then
|
||||
i <= i + 1;
|
||||
|
||||
if ( LSR(i) = '1' ) then
|
||||
accum <= accum + K(i);
|
||||
else
|
||||
accum <= accum - K(i);
|
||||
end if;
|
||||
|
||||
end if;
|
||||
end if;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
|
||||
|
||||
--~ Latch de la salida,
|
||||
--~ Si. la salida va a estar latcheada
|
||||
OutputLatch:
|
||||
process(clk_i)
|
||||
begin
|
||||
if ( rising_edge(clk_i) ) then
|
||||
if ( enable = '1' and sample_clk_s = '1' and i = N-1 ) then
|
||||
if ( accum > 0 ) then
|
||||
d_s <= '1';
|
||||
else
|
||||
d_s <= '0';
|
||||
end if;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
|
||||
|
||||
--~ Registro de desplazamiento para el sobremuestreo
|
||||
LSRprocess:
|
||||
process ( clk_i )
|
||||
begin
|
||||
if ( rising_edge(clk_i) ) then
|
||||
if ( reset = '1' ) then
|
||||
LSR <= ( others => '0' );
|
||||
|
||||
elsif ( enable = '1' and sample_clk_s = '1' ) then
|
||||
LSR( 0 ) <= d_i;
|
||||
LSR( N-1 downto 1 ) <= LSR( N-2 downto 0 );
|
||||
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
--~ Divisor de frecuencia, para obtener la frecuencia de sampleo
|
||||
sample_clk_s <= '1' when counter = MAX_COUNT -1 else '0';
|
||||
|
||||
ClkDiv:
|
||||
process( clk_i, reset )
|
||||
begin
|
||||
if ( rising_edge(clk_i) ) then
|
||||
if ( enable = '1' ) then
|
||||
if ( counter = MAX_COUNT -1 ) then
|
||||
counter <= 0;
|
||||
else
|
||||
counter <= counter + 1;
|
||||
end if;
|
||||
end if;
|
||||
end if;
|
||||
end process;
|
||||
|
||||
end Behavioral;
|
||||
|
||||
Reference in New Issue
Block a user