diff --git a/lib/filter/sim/tb_fir_stage_sys.fdo b/lib/filter/sim/tb_fir_stage_sys.fdo new file mode 100644 index 0000000..9c95a3c --- /dev/null +++ b/lib/filter/sim/tb_fir_stage_sys.fdo @@ -0,0 +1,17 @@ +vmap ieee_proposed ../../../Common/sim/ieee_proposed + +vlib work +vcom -explicit -93 "../../../lib/misc/utils_pkg.vhd" +vcom -explicit -93 "../../../lib/fixed/fixed_util_pkg.vhd" +vcom -explicit -93 "../../../lib/PCK_FIO-2002.7/PCK_FIO_1993.vhd" +vcom -explicit -93 "../../../lib/PCK_FIO-2002.7/PCK_FIO_1993_BODY.vhd" +vcom -explicit -93 "../src/filter_pkg.vhd" +vcom -explicit -93 "../src/fir_stage_pkg.vhd" +vcom -explicit -93 "../src/fir_stage_sys.vhd" +vcom -explicit -93 "../src/tb_fir_stage_sys.vhd" +vsim -t 1ps -lib work tb_fir_stage_sys +do {tb_fir_stage_sys.wdo} +view wave +view structure +view signals +run 2us diff --git a/lib/filter/sim/tb_fir_stage_sys.wdo b/lib/filter/sim/tb_fir_stage_sys.wdo new file mode 100644 index 0000000..21e822e --- /dev/null +++ b/lib/filter/sim/tb_fir_stage_sys.wdo @@ -0,0 +1,28 @@ +onerror {resume} +quietly WaveActivateNextPane {} 0 +add wave -noupdate -format Logic /tb_fir_stage_sys/clk +add wave -noupdate -divider Input +add wave -noupdate -format Literal -radix decimal /tb_fir_stage_sys/x_in +add wave -noupdate -format Literal /tb_fir_stage_sys/xi +add wave -noupdate -divider Output +add wave -noupdate -format Literal -radix decimal /tb_fir_stage_sys/y_out +add wave -noupdate -format Analog-Step -height 50 -scale 50.0 /tb_fir_stage_sys/yo +add wave -noupdate -divider {Stage signals} +add wave -noupdate -format Literal -radix decimal /tb_fir_stage_sys/x +add wave -noupdate -format Literal -radix decimal /tb_fir_stage_sys/y +TreeUpdate [SetDefaultTree] +WaveRestoreCursors {{Cursor 1} {1060000 ps} 0} +configure wave -namecolwidth 140 +configure wave -valuecolwidth 100 +configure wave -justifyvalue left +configure wave -signalnamewidth 1 +configure wave -snapdistance 10 +configure wave -datasetprefix 0 +configure wave -rowmargin 4 +configure wave -childrowmargin 2 +configure wave -gridoffset 0 +configure wave -gridperiod 1 +configure wave -griddelta 40 +configure wave -timeline 0 +update +WaveRestoreZoom {706931 ps} {1268317 ps} diff --git a/lib/filter/src/fir_stage_sys.vhd b/lib/filter/src/fir_stage_sys.vhd new file mode 100644 index 0000000..3488c2f --- /dev/null +++ b/lib/filter/src/fir_stage_sys.vhd @@ -0,0 +1,125 @@ +-------------------------------------------------------------------------------- +-- Company: +-- Engineer: +-- +-- Create Date: 12:16:14 10/02/05 +-- Design Name: +-- Module Name: fir_stage - Behavioral +-- Project Name: +-- Target Device: +-- Tool versions: +-- Description: +-- +-- Dependencies: +-- +-- Revision: +-- Revision 0.01 - File Created +-- Additional Comments: +-- +-------------------------------------------------------------------------------- +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.MATH_REAL.ALL; +USE ieee.numeric_std.ALL; + +library ieee_proposed; +use ieee_proposed.math_utility_pkg.all; +use ieee_proposed.fixed_pkg.all; + +library work; +use work.utils_pkg.all; +use work.fixed_util_pkg.all; +use work.fir_stage_pkg.all; + +---- Uncomment the following library declaration if instantiating +---- any Xilinx primitives in this code. +--library UNISIM; +--use UNISIM.VComponents.all; +entity fir_stage_sys is +Generic +( + nbits_in : integer := 12; + nbits_in_frac : integer := 12; + nbits_out : integer := 12; + nbits_out_frac : integer := 12; + input_latency : integer := 1; + pipe_latency : integer := 2 +); +Port +( + clk : in std_logic; + x_in : in sfixed; + y_in : in sfixed; + h_in : in sfixed; + x_out : out sfixed; + y_out : out sfixed +); +end fir_stage_sys; + +architecture Behavioral of fir_stage_sys is + +constant min_input_lat : integer := 1; +constant min_pipe_lat : integer := 2; +constant mult_latency : integer := pipe_latency-1; + +subtype in_t is sfixed(shi(nbits_in, nbits_in_frac) downto slo(nbits_in, nbits_in_frac)); +subtype out_t is sfixed(shi(nbits_out, nbits_out_frac) downto slo(nbits_out, nbits_out_frac)); + +type input_pipe_t is array (0 to input_latency) of in_t; +type mult_pipe_t is array (0 to mult_latency) of out_t; + +signal x_pipe : input_pipe_t; +signal mult_pipe : mult_pipe_t; + +signal xin : sfixed(shi(nbits_in, nbits_in_frac) downto slo(nbits_in, nbits_in_frac)); +signal yin : sfixed(shi(nbits_in, nbits_in_frac) downto slo(nbits_in, nbits_in_frac)); +signal hin : sfixed(shi(nbits_in, nbits_in_frac) downto slo(nbits_in, nbits_in_frac)); +signal prod : sfixed(shi(nbits_out, nbits_out_frac) downto slo(nbits_out, nbits_out_frac)); + +------------------------------------------------------------ +begin + + assert input_latency >= min_input_lat report "Input latency must be greater than " & natural'image(min_input_lat-1) & "!" severity error; + assert pipe_latency >= min_pipe_lat report "Pipe latency must be greater than " & natural'image(min_pipe_lat-1) & "!" severity error; + + prod <= mult_pipe(mult_latency); + yin <= resize(y_in, yin); + hin <= resize(h_in, hin); + xin <= x_pipe(input_latency); + x_out <= resize(xin, shi(nbits_out, nbits_out_frac), slo(nbits_out, nbits_out_frac)); + +------------------------------------------------------------ + proc_in_reg: process(clk, x_in) + begin + x_pipe(0) <= resize(x_in, x_pipe(0)); + if rising_edge(clk) then + for i in 1 to input_latency loop + x_pipe(i) <= x_pipe(i-1); + end loop; + end if; + + end process; + +------------------------------------------------------------ + proc_pipe_reg: process(clk, xin, hin) + begin + mult_pipe(0) <= resize(xin * hin, mult_pipe(0)); + if rising_edge(clk) then + for i in 1 to mult_latency loop + mult_pipe(i) <= mult_pipe(i-1); + end loop; + end if; + end process; + +------------------------------------------------------------ + proc_out_reg: process(clk) + variable yout : sfixed(shi(nbits_out, nbits_out_frac) downto slo(nbits_out, nbits_out_frac)); + begin + if rising_edge(clk) then + yout := resize(yin + prod, yout, fixed_wrap, fixed_truncate); + y_out <= yout; + end if; + end process; + +------------------------------------------------------------ +end Behavioral; diff --git a/lib/filter/src/tb_fir_stage_sys.vhd b/lib/filter/src/tb_fir_stage_sys.vhd new file mode 100644 index 0000000..bb34477 --- /dev/null +++ b/lib/filter/src/tb_fir_stage_sys.vhd @@ -0,0 +1,222 @@ +-------------------------------------------------------------------------------- +-- Company: +-- Engineer: +-- +-- Create Date: 17:16:42 13.05.2007 +-- Design Name: tb_fir_stage +-- Module Name: tb_fir_stage.vhd +-- Project Name: fir_stage +-- Target Device: +-- Tool versions: +-- Description: +-- +-------------------------------------------------------------------------------- +LIBRARY ieee; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.MATH_REAL.ALL; +USE ieee.numeric_std.ALL; +use std.textio.all; -- Imports the standard textio package. + +library ieee_proposed; +use ieee_proposed.math_utility_pkg.all; +use ieee_proposed.fixed_pkg.all; + +library work; +use work.fixed_util_pkg.all; +use work.fir_stage_pkg.all; +use work.filter_pkg.all; + +use work.PCK_FIO.all; + +ENTITY tb_fir_stage_sys IS + Generic + ( + ntaps : integer := 33; + nbits_in : integer := 24; + nbits_in_frac : integer := 23; + nbits_stages : integer := 25; + nbits_stages_frac : integer := 23; + nbits_out : integer := 24; + nbits_out_frac : integer := 22 + ); +END tb_fir_stage_sys; + +ARCHITECTURE behavior OF tb_fir_stage_sys IS + + -- Component Declaration for the Unit Under Test (UUT) + COMPONENT fir_stage_sys + GENERIC + ( + nbits_in : integer; + nbits_in_frac : integer; + nbits_out : integer; + nbits_out_frac : integer; + input_latency : integer; + pipe_latency : integer + ); + PORT + ( + clk : in std_logic; + x_in : in sfixed; + y_in : in sfixed; + h_in : in sfixed; + x_out : out sfixed; + y_out : out sfixed + ); + END COMPONENT; + + type stages_t is array (natural range <>) of sfixed(shi(nbits_stages, nbits_stages_frac) downto slo(nbits_stages, nbits_stages_frac)); + + --Constants + constant PERIOD : time := 10 ns; + constant zero_in : sfixed := to_sfixed(0, nbits_in, nbits_in_frac); + + --Inputs + SIGNAL clk : std_logic := '0'; + SIGNAL x_in : sfixed(shi(nbits_in, nbits_in_frac) downto slo(nbits_in, nbits_in_frac)); + + --Outputs + SIGNAL x_out : sfixed(shi(nbits_out, nbits_out_frac) downto slo(nbits_out, nbits_out_frac)); + SIGNAL y_out : sfixed(shi(nbits_out, nbits_out_frac) downto slo(nbits_out, nbits_out_frac)); + + SIGNAL x : stages_t(0 to ntaps-2); + SIGNAL y : stages_t(0 to ntaps-2); + + SIGNAL fileout_enable : std_logic := '1'; + + -- Test coefficients + function to_sfixed(x_real : real_array_t) return stages_t is + variable res : stages_t(x_real'range); + begin + for i in x_real'range loop + res(i) := to_sfixed(x_real(i), res(i), fixed_wrap, fixed_round); + end loop; + + return res; + end to_sfixed; + + constant h : stages_t(0 to ntaps-1) := to_sfixed(FilterCoef_Lowpass(ntaps, 0.25, 1.0)); + + SIGNAL xi, yo : real := 0.0; + +BEGIN + + xi <= to_real(x_in); + yo <= to_real(y_out); + + ---------------------------------------- + -- Instantiate the Unit Under Test (UUT) + ---------------------------------------- + uut_first_stage_sys: fir_stage_sys + GENERIC MAP + ( + nbits_in => nbits_in, + nbits_in_frac => nbits_in_frac, + nbits_out => nbits_stages, + nbits_out_frac => nbits_stages_frac, + input_latency => 1, + pipe_latency => 2 + ) + PORT MAP + ( + clk => clk, + x_in => x_in, + y_in => zero_in, + h_in => h(ntaps-1), + x_out => x(0), + y_out => y(0) + ); + + ---------------------------------------- + gen_stages: + for i in 1 to ntaps-2 generate + uut_stages: fir_stage_sys + GENERIC MAP + ( + nbits_in => nbits_stages, + nbits_in_frac => nbits_stages_frac, + nbits_out => nbits_stages, + nbits_out_frac => nbits_stages_frac, + input_latency => 2, + pipe_latency => 2 + ) + PORT MAP + ( + clk => clk, + x_in => x(i-1), + y_in => y(i-1), + h_in => h(ntaps-i-1), + x_out => x(i), + y_out => y(i) + ); + end generate; + + ---------------------------------------- + uut_last_stage: fir_stage_sys + GENERIC MAP + ( + nbits_in => nbits_stages, + nbits_in_frac => nbits_stages_frac, + nbits_out => nbits_out, + nbits_out_frac => nbits_out_frac, + input_latency => 2, + pipe_latency => 2 + ) + PORT MAP + ( + clk => clk, + x_in => x(ntaps-2), + y_in => y(ntaps-2), + h_in => h(0), + x_out => x_out, + y_out => y_out + ); + + ---------------------------------------- + -- Finished instantiation + ---------------------------------------- + tb_clk : PROCESS + BEGIN + clk <= not clk; + wait for PERIOD/2; + END PROCESS; + + tb : PROCESS + + BEGIN + + -- Wait 100 ns for global reset to finish + wait for 4*PERIOD; + + x_in <= to_sfixed(0.0, x_in); + + wait for 40*PERIOD; + wait until rising_edge(clk); + x_in <= to_sfixed(0.0, x_in); + wait until rising_edge(clk); + x_in <= to_sfixed(1.0, x_in); + wait until rising_edge(clk); + x_in <= to_sfixed(0.0, x_in); + wait until rising_edge(clk); + x_in <= to_sfixed(0.0, x_in); + wait until rising_edge(clk); + x_in <= to_sfixed(0.0, x_in); + + wait for 150*PERIOD; + + assert false report "Test finished" severity error; + wait; + END PROCESS; + + tb_fo : PROCESS(clk, fileout_enable) + file RESULT_FIR: text open write_mode is "fir.txt"; + variable L: line; + + BEGIN + if rising_edge(clk) and fileout_enable = '1' then + fprint(RESULT_FIR, L,"%s\n", REAL'image(yo)); + end if; + + END PROCESS; + +END;