Altera_Forum
Honored Contributor
9 years agoTrouble with CIC filter
I'm trying to implement a CIC decimation filter( with R = 1000, M = 1 and N = 2 ) and Fs = 1 MHz without using the CIC IP core. Using matlab implementation I found out that the suppression of the CIC filter will be 26.58 dB for all frequencies above 500Hz which is relatively good for my project. But on implementing the CIC filter whenever I'm passing a signal of 1KHz, the output of the cic filter is a dc offset which is the expected result but on passing frequencies above 5KHz I'm getting output of the CIC filter as noise. Can anyone please help me finding what's wrong with the code. The attachment contains the matlab freq response.
The data input is 12 bit, so the output will be 32 bit as per the CIC filter register growth equation. ENTITY cic_filter IS PORT( clk_in : IN std_logic; -- input sample rate clock(1 MHz) data_in : IN std_logic_vector(11 downto 0); -- sample data in, Q12._ clk_out : OUT std_logic; -- output clock (clk_in / 1000) data_out : OUT std_logic_vector(31 downto 0) -- data out ); END cic_filter; ARCHITECTURE behavior OF cic_filter IS -- latched, 32-bit data in signal l_data_in : signed(31 downto 0); -- outputs for each integrator stage signal integrator_out_1, integrator_out_2 : signed(31 downto 0) := (others => '0'); -- delayed outputs for each integrator stage signal l_integrator_out_1, l_integrator_out_2 : signed(31 downto 0) := (others => '0'); -- inputs for each comb stage signal comb_in_1, comb_in_2 : signed(31 downto 0) := (others => '0'); -- delayed inputs for each comb stage signal l_comb_in_1, l_comb_in_2 : signed(31 downto 0) := (others => '0'); -- decimation clock signal clk_decimated : std_logic; signal count : natural range 1 to 1000 := 1; begin l_data_in <= resize(signed(data_in),32); integrators : process( clk_in ) begin if( rising_edge(clk_in) ) then -- sums integrator_out_1 <= (l_data_in) + l_integrator_out_1; integrator_out_2 <= integrator_out_1 + l_integrator_out_2; -- delays l_integrator_out_1 <= integrator_out_1; l_integrator_out_2 <= integrator_out_2; end if; end process; decimation_clock : process( clk_in ) begin if( rising_edge(clk_in) ) then if( count = 1000 ) then count <= 1; clk_decimated <= '1'; else count <= count + 1; clk_decimated <= '0'; end if; end if; end process decimation_clock; clk_out <= clk_decimated; combs : process( clk_decimated ) begin if( rising_edge(clk_decimated) ) then -- decimation of integrator output comb_in_1 <= integrator_out_2; -- sums comb_in_2 <= comb_in_1 - l_comb_in_1; data_out <= std_logic_vector( comb_in_2 - l_comb_in_2 ); -- delays l_comb_in_1 <= comb_in_1; l_comb_in_2 <= comb_in_2; end if; end process; end behavior;