Initial import

git-svn-id: http://moon:8086/svn/vhdl/trunk@5 cc03376c-175c-47c8-b038-4cd826a8556b
This commit is contained in:
2008-08-23 08:20:30 +00:00
parent bfbeba5129
commit d3bd08bb52
160 changed files with 56260 additions and 0 deletions
+223
View File
@@ -0,0 +1,223 @@
--------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 12:16:14 10/02/05
-- Design Name:
-- Module Name: cordic_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;
use work.fixed_pkg.all;
use work.nco_pkg.all;
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity nco is
Generic
(
nbits_wave : integer := 18;
nbits_phase : integer := 16;
nbits_lut_depth : integer := 12;
nbits_dither : integer := 4;
nbits_lfsr : integer := 12;
q_phase : phase_relation_t := phase_90deg;
has_pipe_reg : boolean := false;
has_out_reg : boolean := false
);
Port
(
srst : in std_logic;
clk : in std_logic;
pacc_clr : in std_logic;
pacc_inc : in std_logic;
freq_in : in unsigned(nbits_phase-1 downto 0);
freq_load : in std_logic;
phase_in : in unsigned(nbits_phase-1 downto 0);
phase_load : in std_logic;
phase_out : out unsigned(nbits_phase-1 downto 0);
wave_out_i : out sfixed;
wave_out_q : out sfixed;
out_valid : out std_logic
);
end nco;
architecture Behavioral of nco is
COMPONENT wavelut
Generic
(
nbits_wave : integer;
nbits_wave_frac : integer;
nbits_lut_depth : integer;
q_phase : phase_relation_t;
has_out_reg : boolean
);
Port
(
clk : in std_logic;
rst : in std_logic;
addr_valid : in std_logic;
addr : in unsigned(nbits_lut_depth-1 downto 0);
wave_i_out : out sfixed;
wave_q_out : out sfixed;
valid_out : out std_logic
);
END COMPONENT;
-------------------------------------------------------------------------------
constant nbits_wave_frac : integer := nbits_wave;
-------------------------------------------------------------------------------
constant lfsr_gen_poly : unsigned(nbits_lfsr-1 downto 0) := to_unsigned(lfsr_poly(nbits_lfsr), nbits_lfsr); -- 24
signal phase : unsigned(nbits_phase-1 downto 0);
signal freq_in_r : unsigned(nbits_phase-1 downto 0);
signal phase_in_r : unsigned(nbits_phase-1 downto 0);
signal lut_addr_d : unsigned(nbits_lut_depth-1 downto 0);
signal wave_i_d, wave_q_d : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
type lfsr_t is array (0 to 1) of unsigned(nbits_lfsr-1 downto 0);
signal lfsr : lfsr_t;
signal lfsr_out : unsigned(nbits_dither-1 downto 0);
signal lut_addr_valid, lfsr_valid, wave_d_valid : std_logic;
-------------------------------------------------------------------------------
begin
wave_out_i <= wave_i_d;
wave_out_q <= wave_q_d;
out_valid <= wave_d_valid;
------------------------------------------------------------
proc_lfsr: process(srst, clk, lfsr, pacc_inc)
variable lo : unsigned(nbits_dither-1 downto 0);
begin
if rising_edge(clk) then
if srst = '1' then
lfsr_valid <= '0';
lfsr_out <= (others => '0');
for i in lfsr'range loop
lfsr(i) <= to_unsigned(2**i, nbits_lfsr);
end loop;
else
lfsr_valid <= '0';
if pacc_inc ='1' then
lfsr_valid <= '1';
lo := (others => '0');
for i in lfsr'range loop
if lfsr(i)(lfsr(i)'left) = '1' then
lfsr(i) <= (lfsr(i)(lfsr(i)'left-1 downto 0) & lfsr(i)(lfsr(i)'left)) xor lfsr_gen_poly;
else
lfsr(i) <= lfsr(i)(lfsr(i)'left-1 downto 0) & lfsr(i)(lfsr(i)'left);
end if;
end loop;
for i in lfsr'range loop
lo := lo + lfsr(i)(nbits_dither-1 downto 0);
end loop;
-- lo := lfsr(0)(nbits_dither downto 0);
lfsr_out <= lo(nbits_dither-1 downto 0);
end if;
end if;
end if;
end process;
------------------------------------------------------------
proc_phase_accu: process(clk, phase)
variable phase_accu : unsigned(nbits_phase-1 downto 0);
begin
if rising_edge(clk) then
if srst = '1' then
phase_accu := (others => '0');
else
phase <= phase_accu + phase_in_r;
if pacc_clr = '1' then
phase_accu := (others => '0');
elsif pacc_inc = '1' then
phase_accu := phase_accu + freq_in_r;
end if;
end if;
end if;
phase_out <= phase;
end process;
------------------------------------------------------------
freq_in_reg: process(srst, clk, freq_load, freq_in)
begin
if rising_edge(clk) then
if srst = '1' then
freq_in_r <= (others => '0');
elsif freq_load = '1' then
freq_in_r <= freq_in;
end if;
end if;
end process;
------------------------------------------------------------
phase_in_reg: process(srst, clk, phase_load, phase_in)
begin
if rising_edge(clk) then
if srst = '1' then
phase_in_r <= (others => '0');
elsif phase_load = '1' then
phase_in_r <= phase_in;
end if;
end if;
end process;
------------------------------------------------------------
proc_pipe_reg: process(clk)
variable lfsr_sum : unsigned(nbits_phase-1 downto 0);
begin
if rising_edge(clk) then
lut_addr_valid <= '0';
if srst = '1' then
lfsr_sum := (others => '0');
elsif lfsr_valid = '1' then
lut_addr_valid <= '1';
lfsr_sum := lfsr_out + phase;
end if;
end if;
lut_addr_d <= lfsr_sum(nbits_phase-1 downto nbits_phase-nbits_lut_depth);
end process;
------------------------------------------------------------
inst_wavelut_d: wavelut
GENERIC MAP
(
nbits_wave => nbits_wave,
nbits_wave_frac => nbits_wave_frac,
nbits_lut_depth => nbits_lut_depth,
q_phase => q_phase,
has_out_reg => has_out_reg
)
PORT MAP
(
rst => srst,
clk => clk,
addr_valid => lut_addr_valid,
addr => lut_addr_d,
wave_i_out => wave_i_d,
wave_q_out => wave_q_d,
valid_out => wave_d_valid
);
------------------------------------------------------------
end Behavioral;
+240
View File
@@ -0,0 +1,240 @@
--------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 12:16:14 10/02/05
-- Design Name:
-- Module Name: cordic_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;
use work.fixed_pkg.all;
use work.nco_pkg.all;
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity nco is
Generic
(
nbits_wave : integer := 12;
nbits_phase : integer := 16;
nbits_lut_depth : integer := 12;
nbits_dither : integer := 4;
nbits_lfsr : integer := 12;
has_pipe_reg : boolean := false;
has_out_reg : boolean := false
);
Port
(
srst : in std_logic;
clk : in std_logic;
pacc_clr : in std_logic;
pacc_inc : in std_logic;
freq_in : in unsigned(nbits_phase-1 downto 0);
freq_load : in std_logic;
phase_in : in unsigned(nbits_phase-1 downto 0);
phase_load : in std_logic;
phase_out : out unsigned(nbits_phase-1 downto 0);
wave_out_i : out sfixed;
wave_out_q : out sfixed;
out_valid : out std_logic
);
end nco;
architecture Behavioral of nco is
COMPONENT wavelut
Generic
(
nbits_wave : integer;
nbits_wave_frac : integer;
nbits_lut_depth : integer;
has_out_reg : boolean
);
Port
(
clk : in std_logic;
addr_valid : in std_logic;
addr : in unsigned(nbits_lut_depth-1 downto 0);
wave_i_out : out sfixed;
wave_q_out : out sfixed
);
END COMPONENT;
-------------------------------------------------------------------------------
constant nbits_wave_frac : integer := nbits_wave;
-------------------------------------------------------------------------------
constant lfsr_gen_poly : unsigned(nbits_lfsr-1 downto 0) := to_unsigned(lfsr_poly(nbits_lfsr), nbits_lfsr); -- 24
signal valid : std_logic_vector(3 downto 0);
signal phase : unsigned(nbits_phase-1 downto 0);
signal freq_in_r : unsigned(nbits_phase-1 downto 0);
signal phase_in_r : unsigned(nbits_phase-1 downto 0);
signal lsfr_sum : unsigned(nbits_phase-1 downto 0);
signal lut_addr : unsigned(nbits_lut_depth-1 downto 0);
signal wave_i, wave_q : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
type lfsr_t is array (0 to 1) of unsigned(nbits_lfsr-1 downto 0);
signal lfsr : lfsr_t;
signal lfsr_out : unsigned(nbits_dither-1 downto 0);
signal lut_addr_valid _ std_logic;
-------------------------------------------------------------------------------
begin
wave_out_i <= wave_i;
wave_out_q <= wave_q;
------------------------------------------------------------
proc_ctrl: process(srst, clk, pacc_inc, pacc_clr)
begin
if rising_edge(clk) then
if srst = '1' then
valid <= (others => '0');
else
valid <= valid(valid'left-1 downto valid'right) & (pacc_inc or pacc_clr);
end if;
end if;
end process;
------------------------------------------------------------
proc_lfsr: process(srst, clk, lfsr, pacc_inc)
variable lo : unsigned(nbits_dither downto 0);
begin
if rising_edge(clk) then
if srst = '1' then
for i in lfsr'range loop
lfsr(i) <= to_unsigned(1234+2**i, nbits_lfsr);
end loop;
elsif pacc_inc ='1' then
lo := (others => '0');
for i in lfsr'range loop
if lfsr(i)(lfsr(i)'left) = '1' then
lfsr(i) <= (lfsr(i)(lfsr(i)'left-1 downto 0) & lfsr(i)(lfsr(i)'left)) xor lfsr_gen_poly;
else
lfsr(i) <= lfsr(i)(lfsr(i)'left-1 downto 0) & lfsr(i)(lfsr(i)'left);
end if;
end loop;
for i in lfsr'range loop
lo := lo + lfsr(i)(nbits_dither-1 downto 0);
end loop;
-- lo := lfsr(0)(nbits_dither downto 0);
lfsr_out <= lo(nbits_dither-1 downto 0);
end if;
end if;
end process;
------------------------------------------------------------
proc_phase_accu: process(srst, clk, pacc_clr, pacc_inc, freq_in_r, phase_in_r)
variable phase_accu : unsigned(nbits_phase-1 downto 0);
begin
if rising_edge(clk) then
if srst = '1' then
phase_accu := (others => '0');
else
phase <= phase_accu + phase_in_r;
if pacc_clr = '1' then
phase_accu := (others => '0');
elsif pacc_inc = '1' then
phase_accu := phase_accu + freq_in_r;
end if;
end if;
end if;
end process;
------------------------------------------------------------
freq_in_reg: process(srst, clk, freq_load, freq_in)
begin
if rising_edge(clk) then
if srst = '1' then
freq_in_r <= (others => '0');
elsif freq_load = '1' then
freq_in_r <= freq_in;
end if;
end if;
end process;
------------------------------------------------------------
phase_in_reg: process(srst, clk, phase_load, phase_in)
begin
if rising_edge(clk) then
if srst = '1' then
phase_in_r <= (others => '0');
elsif phase_load = '1' then
phase_in_r <= phase_in;
end if;
end if;
end process;
------------------------------------------------------------
proc_pipe_reg: process(clk)
begin
if rising_edge(clk) then
lsfr_sum <= lfsr_out + phase;
lut_addr <= lsfr_sum(nbits_phase-1 downto nbits_phase-nbits_lut_depth);
end if;
end process;
------------------------------------------------------------
proc_out_reg: process(clk, phase)
begin
if has_out_reg = true then
if rising_edge(clk) then
phase_out <= phase;
end if;
else
phase_out <= phase;
end if;
end process;
------------------------------------------------------------
proc_valid_reg: process(clk, valid)
begin
out_valid <= valid(valid'right+1);
if has_out_reg = true then
out_valid <= valid(valid'right+2);
if has_pipe_reg = true then
out_valid <= valid(valid'right+3);
end if;
elsif has_pipe_reg = true then
out_valid <= valid(valid'right+2);
end if;
end process;
------------------------------------------------------------
inst_wavelut_d: wavelut
GENERIC MAP
(
nbits_wave => nbits_wave,
nbits_wave_frac => nbits_wave_frac,
nbits_lut_depth => nbits_lut_depth,
has_out_reg => has_out_reg
)
PORT MAP
(
clk => clk,
addr => lut_addr,
addr_valid => lut_addr_valid,
wave_i_out => wave_i,
wave_q_out => wave_q
);
------------------------------------------------------------
end Behavioral;
+253
View File
@@ -0,0 +1,253 @@
--------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 12:16:14 10/02/05
-- Design Name:
-- Module Name: cordic_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;
use work.fixed_pkg.all;
use work.nco_pkg.all;
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity nco is
Generic
(
nbits_wave : integer := 18;
nbits_phase : integer := 16;
nbits_lut_depth : integer := 12;
nbits_dither : integer := 4;
nbits_lfsr : integer := 12;
q_phase : phase_relation_t := phase_90deg;
has_pipe_reg : boolean := false;
has_out_reg : boolean := false
);
Port
(
srst : in std_logic;
clk : in std_logic;
pacc_clr : in std_logic;
pacc_inc : in std_logic;
freq_in : in unsigned(nbits_phase-1 downto 0);
freq_load : in std_logic;
phase_in : in unsigned(nbits_phase-1 downto 0);
phase_load : in std_logic;
phase_out : out unsigned(nbits_phase-1 downto 0);
wave_out_i : out sfixed;
wave_out_q : out sfixed;
out_valid : out std_logic;
debug_out : out debug_out_t
);
end nco;
architecture Behavioral of nco is
COMPONENT wavelut
Generic
(
nbits_wave : integer;
nbits_wave_frac : integer;
nbits_lut_depth : integer;
q_phase : phase_relation_t;
has_out_reg : boolean
);
Port
(
clk : in std_logic;
rst : in std_logic;
addr_valid : in std_logic;
addr : in unsigned(nbits_lut_depth-1 downto 0);
wave_i_out : out sfixed;
wave_q_out : out sfixed;
valid_out : out std_logic
);
END COMPONENT;
-------------------------------------------------------------------------------
constant nbits_wave_frac : integer := nbits_wave;
-------------------------------------------------------------------------------
constant lfsr_gen_poly : unsigned(nbits_lfsr-1 downto 0) := to_unsigned(lfsr_poly(nbits_lfsr), nbits_lfsr); -- 24
signal phase : unsigned(nbits_phase-1 downto 0);
signal freq_in_r : unsigned(nbits_phase-1 downto 0);
signal phase_in_r : unsigned(nbits_phase-1 downto 0);
signal lut_addr_ud : unsigned(nbits_lut_depth-1 downto 0);
signal lut_addr_d : unsigned(nbits_lut_depth-1 downto 0);
signal wave_i_d, wave_q_d : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
signal wave_i_ud, wave_q_ud : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
type lfsr_t is array (0 to 1) of unsigned(nbits_lfsr-1 downto 0);
signal lfsr : lfsr_t;
signal lfsr_out : unsigned(nbits_dither-1 downto 0);
signal lut_addr_valid, lfsr_valid, wave_d_valid, wave_ud_valid : std_logic;
-------------------------------------------------------------------------------
begin
wave_out_i <= wave_i_d;
wave_out_q <= wave_q_d;
out_valid <= wave_d_valid;
debug_out.lfsr <= (debug_out.lfsr'left downto (debug_out.lfsr'right+lfsr_out'left+1) => '0') & lfsr_out;
debug_out.i_d <= to_real(wave_i_d);
debug_out.q_d <= to_real(wave_q_d);
debug_out.i_ud <= to_real(wave_i_ud);
debug_out.q_ud <= to_real(wave_q_ud);
------------------------------------------------------------
proc_lfsr: process(srst, clk, lfsr, pacc_inc)
variable lo : unsigned(nbits_dither-1 downto 0);
begin
if rising_edge(clk) then
if srst = '1' then
lfsr_valid <= '0';
lfsr_out <= (others => '0');
for i in lfsr'range loop
lfsr(i) <= to_unsigned(2**i, nbits_lfsr);
end loop;
else
lfsr_valid <= '0';
if pacc_inc ='1' then
lfsr_valid <= '1';
lo := (others => '0');
for i in lfsr'range loop
if lfsr(i)(lfsr(i)'left) = '1' then
lfsr(i) <= (lfsr(i)(lfsr(i)'left-1 downto 0) & lfsr(i)(lfsr(i)'left)) xor lfsr_gen_poly;
else
lfsr(i) <= lfsr(i)(lfsr(i)'left-1 downto 0) & lfsr(i)(lfsr(i)'left);
end if;
end loop;
for i in lfsr'range loop
lo := lo + lfsr(i)(nbits_dither-1 downto 0);
end loop;
-- lo := lfsr(0)(nbits_dither downto 0);
lfsr_out <= lo(nbits_dither-1 downto 0);
end if;
end if;
end if;
end process;
------------------------------------------------------------
proc_phase_accu: process(srst, clk, pacc_clr, pacc_inc, freq_in_r, phase_in_r)
variable phase_accu : unsigned(nbits_phase-1 downto 0);
begin
if rising_edge(clk) then
if srst = '1' then
phase_accu := (others => '0');
else
phase <= phase_accu + phase_in_r;
if pacc_clr = '1' then
phase_accu := (others => '0');
elsif pacc_inc = '1' then
phase_accu := phase_accu + freq_in_r;
end if;
end if;
end if;
phase_out <= phase;
end process;
------------------------------------------------------------
freq_in_reg: process(srst, clk, freq_load, freq_in)
begin
if rising_edge(clk) then
if srst = '1' then
freq_in_r <= (others => '0');
elsif freq_load = '1' then
freq_in_r <= freq_in;
end if;
end if;
end process;
------------------------------------------------------------
phase_in_reg: process(srst, clk, phase_load, phase_in)
begin
if rising_edge(clk) then
if srst = '1' then
phase_in_r <= (others => '0');
elsif phase_load = '1' then
phase_in_r <= phase_in;
end if;
end if;
end process;
------------------------------------------------------------
proc_pipe_reg: process(clk)
variable lfsr_sum : unsigned(nbits_phase-1 downto 0);
begin
if rising_edge(clk) then
lut_addr_valid <= '0';
if srst = '1' then
lfsr_sum := (others => '0');
elsif lfsr_valid = '1' then
lut_addr_valid <= '1';
lfsr_sum := lfsr_out + phase;
end if;
end if;
lut_addr_d <= lfsr_sum(nbits_phase-1 downto nbits_phase-nbits_lut_depth);
lut_addr_ud <= phase(nbits_phase-1 downto nbits_phase-nbits_lut_depth);
end process;
------------------------------------------------------------
inst_wavelut_ud: wavelut
GENERIC MAP
(
nbits_wave => nbits_wave,
nbits_wave_frac => nbits_wave_frac,
nbits_lut_depth => nbits_lut_depth,
q_phase => q_phase,
has_out_reg => has_out_reg
)
PORT MAP
(
rst => srst,
clk => clk,
addr_valid => lut_addr_valid,
addr => lut_addr_ud,
wave_i_out => wave_i_ud,
wave_q_out => wave_q_ud,
valid_out => wave_ud_valid
);
inst_wavelut_d: wavelut
GENERIC MAP
(
nbits_wave => nbits_wave,
nbits_wave_frac => nbits_wave_frac,
nbits_lut_depth => nbits_lut_depth,
q_phase => q_phase,
has_out_reg => has_out_reg
)
PORT MAP
(
rst => srst,
clk => clk,
addr_valid => lut_addr_valid,
addr => lut_addr_d,
wave_i_out => wave_i_d,
wave_q_out => wave_q_d,
valid_out => wave_d_valid
);
------------------------------------------------------------
end Behavioral;
+117
View File
@@ -0,0 +1,117 @@
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use ieee.numeric_std.all;
use IEEE.MATH_REAL.ALL;
use work.fixed_pkg.all;
-------------------------------------------------------------------------------
package nco_pkg is
constant tpd : time := 0 ns;
-- Global set arithmetic rounding mode
constant pi : real := 3.141592653589793e+000;
constant sqrt2 : real := 1.414213562373095e+000;
constant sqrt2_inv : real := 7.071067811865475e-001;
type real_array_t is array (natural range <>) of real;
type natural_array_t is array (natural range <>) of natural;
type phase_relation_t is (phase_90deg, phase_270deg);
type debug_out_t is record
lfsr : unsigned(31 downto 0);
i_ud : real;
q_ud : real;
i_d : real;
q_d : real;
end record;
constant lfsr_poly : natural_array_t(3 to 24) :=
(
12, -- 3
24, -- 4
58, -- 5
114, -- 6
210, -- 7
500, -- 8
1000, -- 9
1824, -- 10
3712, -- 11
7184, -- 12
14592, -- 13
28674, -- 14
59392, -- 15
106512, -- 16
245760, -- 17
466944, -- 18
933888, -- 19
1654784, -- 20
3735552, -- 21
7342080, -- 22
14745600, -- 23
14811138 -- 24
);
function sin_tbl(nsamples : integer; omega, phi_in : real) return real_array_t;
function cos_tbl(nsamples : integer; omega, phi_in : real) return real_array_t;
-------------------------------------------------------------
-- Constructor helpers
-- Use: variable v8u6 : ufixed_t(ufixed(8,6)'range);
function uproto (nbits : integer; nbits_frac : integer) return ufixed;
-- Use: variable v8s6 : sfixed_t(sfixed(8,6)'range);
function sproto (nbits : integer; nbits_frac : integer) return sfixed;
end; -- package nco_pkg;
-------------------------------------------------------------------------------
package body nco_pkg is
function sin_tbl(nsamples : integer; omega, phi_in : real) return real_array_t is
variable tbl : real_array_t (0 to nsamples-1);
variable phi : real := phi_in;
variable dphi : real := 2.0*pi*omega;
begin
for i in 0 to nsamples-1 loop
tbl(i) := sin(phi);
phi := phi + dphi;
end loop;
return tbl;
end sin_tbl;
-------------------------------------------------------------
function cos_tbl(nsamples : integer; omega, phi_in : real) return real_array_t is
variable tbl : real_array_t (0 to nsamples-1);
variable phi : real := phi_in;
variable dphi : real := 2.0*pi*omega;
begin
for i in 0 to nsamples-1 loop
tbl(i) := cos(phi);
phi := phi + dphi;
end loop;
return tbl;
end cos_tbl;
-------------------------------------------------------------
-- Constuctor helpers
function uproto (nbits : integer; nbits_frac : integer) return ufixed is
constant result : ufixed (nbits-nbits_frac-1 downto -nbits_frac) := (others => '0');
begin
return result(nbits-nbits_frac-1 downto -nbits_frac);
end uproto;
-------------------------------------------------------------
function sproto (nbits : integer; nbits_frac : integer) return sfixed is
constant result : sfixed (nbits-nbits_frac downto -nbits_frac+1) := (others => '0');
begin
return result(nbits-nbits_frac downto -nbits_frac+1);
end sproto;
-------------------------------------------------------------------------------
end; -- package nco_pkg;
+299
View File
@@ -0,0 +1,299 @@
--------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 17:16:42 13.05.2007
-- Design Name: tb_nco
-- Module Name: tb_nco.vhd
-- Project Name: nco
-- 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 work;
use work.fixed_pkg.all;
use work.nco_pkg.all;
use work.PCK_FIO.all;
ENTITY tb_nco IS
Generic (
nbits_wave : integer := 18;
nbits_phase : integer := 16;
nbits_lut_depth : integer := 12;
nbits_dither : integer := 4;
nbits_lfsr : integer := 12;
q_phase : phase_relation_t := phase_270deg;
has_pipe_reg : boolean := true;
has_out_reg : boolean := true
);
END tb_nco;
ARCHITECTURE behavior OF tb_nco IS
-- Component Declaration for the Unit Under Test (UUT)
COMPONENT nco
GENERIC (
nbits_wave : integer;
nbits_phase : integer;
nbits_lut_depth : integer;
nbits_dither : integer;
nbits_lfsr : integer;
q_phase : phase_relation_t;
has_pipe_reg : boolean;
has_out_reg : boolean
);
PORT(
srst : in std_logic;
clk : in std_logic;
-- ce : in std_logic;
pacc_clr : in std_logic;
pacc_inc : in std_logic;
freq_in : in unsigned(nbits_phase-1 downto 0);
freq_load : in std_logic;
phase_in : in unsigned(nbits_phase-1 downto 0);
phase_load : in std_logic;
phase_out : out unsigned(nbits_phase-1 downto 0);
wave_out_i : out sfixed;
wave_out_q : out sfixed;
out_valid : out std_logic;
debug_out : out debug_out_t
);
END COMPONENT;
--Constants
constant f : REAL := 4.1667E6;
constant df : REAL := 10.0E3;
constant fa : REAL := 100.0E6;
constant PERIOD : time := 10 ns;
constant nbits_wave_frac : integer := nbits_wave;
SIGNAL freq_word : integer := integer(f/fa*2.0**nbits_phase);
SIGNAL dfreq_word : integer := integer(df/fa*2.0**nbits_phase);
--Inputs
SIGNAL clk : std_logic := '0';
-- SIGNAL ce : std_logic := '0';
SIGNAL srst : std_logic := '1';
SIGNAL pacc_clr : std_logic := '0';
SIGNAL pacc_inc : std_logic := '0';
SIGNAL phase_load : std_logic := '0';
SIGNAL freq_load : std_logic := '0';
SIGNAL freq_in : unsigned(nbits_phase-1 downto 0);
SIGNAL phase_in : unsigned(nbits_phase-1 downto 0);
--Outputs
SIGNAL wave_out_i : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
SIGNAL wave_out_q : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
SIGNAL out_valid : std_logic;
SIGNAL phase_out : unsigned(nbits_phase-1 downto 0);
SIGNAL debug_out : debug_out_t;
SIGNAL fileout_enable : std_logic := '0';
BEGIN
-- Instantiate the Unit Under Test (UUT)
uut: nco
GENERIC MAP (
nbits_wave => nbits_wave,
nbits_phase => nbits_phase,
nbits_lut_depth => nbits_lut_depth,
nbits_dither => nbits_dither,
nbits_lfsr => nbits_lfsr,
q_phase => q_phase,
has_pipe_reg => has_pipe_reg,
has_out_reg => has_out_reg
)
PORT MAP(
srst => srst,
clk => clk,
-- ce => ce,
pacc_clr => pacc_clr,
pacc_inc => pacc_inc,
freq_in => freq_in,
freq_load => freq_load,
phase_in => phase_in,
phase_load => phase_load,
phase_out => phase_out,
wave_out_i => wave_out_i,
wave_out_q => wave_out_q,
out_valid => out_valid,
debug_out => debug_out
);
tb_clk : PROCESS
BEGIN
clk <= not clk;
wait for PERIOD/2;
END PROCESS;
tb : PROCESS
file RESULT_FREQ: text open write_mode is "freq.txt";
variable L: line;
BEGIN
-- Wait 100 ns for global reset to finish
wait for 4*PERIOD;
srst <= '0';
fprint(RESULT_FREQ, L,"%s\n", REAL'image(f));
wait for 2*PERIOD;
-- ce <= '1';
-------------------------------------------
-- 1
phase_in <= to_unsigned(0,nbits_phase);
wait until rising_edge(clk);
phase_load <= '1';
wait until rising_edge(clk);
phase_load <= '0';
freq_in <= to_unsigned(1411,nbits_phase);
wait until rising_edge(clk);
freq_load <= '1';
wait until rising_edge(clk);
freq_load <= '0';
wait for 2*PERIOD;
pacc_inc <= '1';
wait for 2*PERIOD;
wait until rising_edge(clk);
wait for 40*PERIOD;
-------------------------------------------
freq_in <= to_unsigned(643,nbits_phase);
wait until rising_edge(clk);
freq_load <= '1';
wait until rising_edge(clk);
freq_load <= '0';
wait for 40*PERIOD;
-------------------------------------------
phase_in <= to_unsigned(800,nbits_phase);
wait until rising_edge(clk);
phase_load <= '1';
wait until rising_edge(clk);
phase_load <= '0';
wait for 20*PERIOD;
-------------------------------------------
phase_in <= to_unsigned(45072,nbits_phase);
wait until rising_edge(clk);
phase_load <= '1';
wait until rising_edge(clk);
phase_load <= '0';
wait for 20*PERIOD;
-------------------------------------------
phase_in <= to_unsigned(20593,nbits_phase);
wait until rising_edge(clk);
phase_load <= '1';
wait until rising_edge(clk);
phase_load <= '0';
-------------------------------------------
freq_in <= to_unsigned(freq_word,nbits_phase);
wait until rising_edge(clk);
freq_load <= '1';
wait until rising_edge(clk);
freq_load <= '0';
wait for 20*PERIOD;
fileout_enable <= '1';
wait for 20000*PERIOD;
fileout_enable <= '0';
-------------------------------------------
-- Sweep
freq_word <= 100;
for i in 1 to 200 loop
wait for 20*PERIOD;
freq_word <= freq_word + dfreq_word;
freq_in <= to_unsigned(freq_word,nbits_phase);
wait until rising_edge(clk);
freq_load <= '1';
wait until rising_edge(clk);
freq_load <= '0';
end loop;
pacc_inc <= '0';
wait for 20*PERIOD;
fileout_enable <= '0';
wait until rising_edge(clk);
pacc_clr <= '1';
wait until rising_edge(clk);
pacc_clr <= '0';
wait for 20*PERIOD;
pacc_inc <= '1';
wait for 20*PERIOD;
wait until rising_edge(clk);
pacc_clr <= '1';
wait until rising_edge(clk);
pacc_clr <= '0';
wait for 20*PERIOD;
pacc_inc <= '0';
wait for 20*PERIOD;
wait until rising_edge(clk);
pacc_inc <= '1';
wait until rising_edge(clk);
pacc_inc <= '0';
wait for 20*PERIOD;
wait until rising_edge(clk);
srst <= '1';
wait until rising_edge(clk);
srst <= '0';
freq_in <= to_unsigned(freq_word,nbits_phase);
wait until rising_edge(clk);
freq_load <= '1';
wait until rising_edge(clk);
freq_load <= '0';
wait for 20*PERIOD;
pacc_inc <= '1';
wait for 20*PERIOD;
wait until rising_edge(clk);
srst <= '1';
wait until rising_edge(clk);
srst <= '0';
wait for 20*PERIOD;
pacc_inc <= '0';
wait for 20*PERIOD;
assert false report "Test finished" severity error;
wait;
END PROCESS;
tb_fo : PROCESS(clk, fileout_enable, out_valid)
file RESULT_I: text open write_mode is "i_ud.txt";
file RESULT_Q: text open write_mode is "q_ud.txt";
file RESULT_ID: text open write_mode is "i_d.txt";
file RESULT_QD: text open write_mode is "q_d.txt";
file RESULT_LFSR: text open write_mode is "lfsr.txt";
variable L: line;
BEGIN
if rising_edge(clk) and fileout_enable = '1' and out_valid = '1' then
fprint(RESULT_I, L,"%s\n", REAL'image(debug_out.i_ud));
fprint(RESULT_Q, L,"%s\n", REAL'image(debug_out.q_ud));
fprint(RESULT_ID, L,"%s\n", REAL'image(debug_out.i_d));
fprint(RESULT_QD, L,"%s\n", REAL'image(debug_out.q_d));
fprint(RESULT_LFSR, L,"%s\n", INTEGER'image(to_integer(debug_out.lfsr)));
end if;
END PROCESS;
END;
+239
View File
@@ -0,0 +1,239 @@
--------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 12:16:14 10/02/05
-- Design Name:
-- Module Name: cordic_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;
use work.fixed_pkg.all;
use work.nco_pkg.all;
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity wavelut is
Generic
(
nbits_wave : integer := 12;
nbits_wave_frac : integer := 12;
nbits_lut_depth : integer := 12;
q_phase : phase_relation_t := phase_90deg;
has_out_reg : boolean := false
);
Port
(
rst : in std_logic;
clk : in std_logic;
addr_valid : in std_logic;
addr : in unsigned(nbits_lut_depth-1 downto 0);
wave_i_out : out sfixed;
wave_q_out : out sfixed;
valid_out : out std_logic
);
end wavelut;
architecture Behavioral of wavelut is
COMPONENT waverom_dual
Generic
(
nbits_wave : integer;
nbits_wave_frac : integer;
nbits_rom_depth : integer
);
Port
(
clk : in std_logic;
addr_i : in unsigned(nbits_rom_depth-1 downto 0);
addr_q : in unsigned(nbits_rom_depth-1 downto 0);
wave_i_out : out sfixed;
wave_q_out : out sfixed
);
END COMPONENT;
-------------------------------------------------------------------------------
constant nbits_rom_depth : integer := nbits_lut_depth-2;
-------------------------------------------------------------------------------
signal wave_i : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
signal wave_q : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
signal inv_i : std_logic;
signal inv_q : std_logic;
signal addr_i : unsigned(nbits_rom_depth-1 downto 0);
signal addr_q : unsigned(nbits_rom_depth-1 downto 0);
signal zero_i : std_logic;
signal zero_q : std_logic;
-------------------------------------------------------------------------------
begin
inst_waverom_dual: waverom_dual
GENERIC MAP
(
nbits_wave => nbits_wave,
nbits_wave_frac => nbits_wave_frac,
nbits_rom_depth => nbits_rom_depth
)
PORT MAP
(
clk => clk,
addr_i => addr_i,
addr_q => addr_q,
wave_i_out => wave_i,
wave_q_out => wave_q
);
------------------------------------------------------------
proc_valid: process(clk)
variable v : unsigned(0 to 1);
begin
if rising_edge(clk) then
if rst = '1' then
v := (others => '0');
valid_out <= '0';
else
valid_out <= v(1);
v(1) := v(0);
v(0) := addr_valid;
end if;
end if;
end process;
------------------------------------------------------------
proc_tbl_addr_i: process(clk, addr)
variable index : unsigned(addr'left downto addr'right);
variable n2 : integer;
constant N_2 : integer := 2**(nbits_lut_depth-1);
constant N_4 : integer := 2**(nbits_lut_depth-2);
begin
n2 := to_integer(addr(addr'left-1 downto addr'right));
if n2 > N_4 then
index := to_unsigned(N_2 - n2, index'length);
else
index := to_unsigned(n2, index'length);
end if;
if rising_edge(clk) then
if rst = '1' then
addr_i <= (others => '0');
zero_i <= '0';
inv_i <= '0';
elsif addr_valid = '1' then
addr_i <= index(addr'left-2 downto addr'right);
zero_i <= index(addr'left-1);
inv_i <= addr(addr'left) xor addr(addr'left-1);
end if;
end if;
end process;
-------------------------------------------------------------------------------
proc_tbl_addr_q: process(clk, addr)
variable index : unsigned(addr'left downto addr'right);
variable n2 : integer;
constant N_4 : integer := 2**(nbits_lut_depth-2);
begin
n2 := to_integer(addr(addr'left-1 downto addr'right));
if n2 > N_4 then
index := to_unsigned(n2 - N_4, index'length);
else
index := to_unsigned(N_4 - n2, index'length);
end if;
if rising_edge(clk) then
if rst = '1' then
addr_q <= (others => '0');
zero_q <= '0';
inv_q <= '0';
elsif addr_valid = '1' then
addr_q <= index(addr'left-2 downto addr'right);
zero_q <= index(addr'left-1);
if q_phase = phase_90deg then
inv_q <= addr(addr'left);
elsif q_phase = phase_270deg then
inv_q <= not addr(addr'left);
end if;
end if;
end if;
end process;
------------------------------------------------------------
proc_out_i: process(clk, wave_i, inv_i, zero_i)
variable w : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
variable z, inv : std_logic;
begin
w := to_sfixed(0.0, w);
if z = '0' then
w := wave_i;
if inv = '1' then
w := resize(-wave_i, w, fixed_truncate, fixed_wrap);
end if;
end if;
if has_out_reg = true then
if rising_edge(clk) then
wave_i_out <= w;
end if;
else
wave_i_out <= w;
end if;
if rising_edge(clk) then
z := zero_i;
inv := inv_i;
end if;
end process;
------------------------------------------------------------
proc_out_q: process(clk, wave_q, inv_q, zero_q)
variable w : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
variable z, inv : std_logic;
begin
w := to_sfixed(0.0, w);
if z = '0' then
w := wave_q;
if inv = '1' then
w := resize(-wave_q, w, fixed_truncate, fixed_wrap);
end if;
end if;
if has_out_reg = true then
if rising_edge(clk) then
wave_q_out <= w;
end if;
else
wave_q_out <= w;
end if;
if rising_edge(clk) then
z := zero_q;
inv := inv_q;
end if;
end process;
------------------------------------------------------------
end Behavioral;
+86
View File
@@ -0,0 +1,86 @@
--------------------------------------------------------------------------------
-- Company:
-- Engineer:
--
-- Create Date: 12:16:14 10/02/05
-- Design Name:
-- Module Name: cordic_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;
use work.fixed_pkg.all;
use work.nco_pkg.all;
---- Uncomment the following library declaration if instantiating
---- any Xilinx primitives in this code.
--library UNISIM;
--use UNISIM.VComponents.all;
entity waverom_dual is
Generic
(
nbits_wave : integer := 12;
nbits_wave_frac : integer := 12;
nbits_rom_depth : integer := 12
);
Port
(
clk : in std_logic;
addr_i : in unsigned(nbits_rom_depth-1 downto 0);
addr_q : in unsigned(nbits_rom_depth-1 downto 0);
wave_i_out : out sfixed;
wave_q_out : out sfixed
);
end waverom_dual;
architecture Behavioral of waverom_dual is
-------------------------------------------------------------------------------
constant rom_depth : integer := 2**nbits_rom_depth;
type wave_mem_t is array (0 to rom_depth-1) of sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low);
constant sfixed_proto : sfixed(sproto(nbits_wave, nbits_wave_frac)'high downto sproto(nbits_wave, nbits_wave_frac)'low) := (others => '0');
-------------------------------------------------------------------------------
function to_wave_mem(wave_real : real_array_t; len : integer; proto : sfixed) return wave_mem_t is
variable res : wave_mem_t;
begin
for i in 0 to len-1 loop
res(i) := to_sfixed(wave_real(i), proto, fixed_round, fixed_saturate);
end loop;
return res;
end to_wave_mem;
-------------------------------------------------------------------------------
-- Create ROM
constant real_wave_tbl : real_array_t(0 to rom_depth-1) := cos_tbl(rom_depth, 0.25/real(rom_depth), 0.0);
constant wave_tbl : wave_mem_t := to_wave_mem(real_wave_tbl, rom_depth, sfixed_proto);
-------------------------------------------------------------------------------
begin
-------------------------------------------------------------------------------
proc_wave: process(clk)
begin
if rising_edge(clk) then
wave_i_out <= wave_tbl(to_integer(addr_i));
wave_q_out <= wave_tbl(to_integer(addr_q));
end if;
end process;
------------------------------------------------------------
end Behavioral;