«
Previous
|
Next
»
Revision 1526
Added by markw about 2 hours ago
| atari_chips/pokeyv2/filtered_sigmadelta.vhd | ||
|---|---|---|
|
GENERIC
|
||
|
(
|
||
|
implementation : integer :=1; --1:my 1st order, 2:my 2nd order, 3:3rd order (not mine)
|
||
|
lowpass : integer :=1; -- simple low pass. Was made for HDMI so can be turned off here with little impact to save resources.
|
||
|
LFSR_SEED : unsigned(15 downto 0) := x"ACE1"
|
||
|
lowpass : integer :=1 -- simple low pass. Was made for HDMI so can be turned off here with little impact to save resources.
|
||
|
);
|
||
|
PORT
|
||
|
(
|
||
| ... | ... | |
|
|
||
|
ENABLE_179 : IN STD_LOGIC;
|
||
|
|
||
|
DITHER_IN : IN STD_LOGIC_VECTOR(15 downto 0);
|
||
|
|
||
|
AUDIN : IN UNSIGNED(15 downto 0);
|
||
|
AUDOUT : OUT std_logic
|
||
|
);
|
||
| ... | ... | |
|
gen_2ndorder_dither_on : if implementation=4 generate
|
||
|
|
||
|
dac_2nd_dither : entity work.sigmadelta_2ndorder_dither
|
||
|
generic map
|
||
|
(
|
||
|
LFSR_SEED=>LFSR_SEED
|
||
|
)
|
||
|
port map
|
||
|
(
|
||
|
reset_n => reset_n,
|
||
|
clk => clk,
|
||
|
audin => AUDIO_FILTERED,
|
||
|
DITHER_IN => DITHER_IN,
|
||
|
AUDOUT => AUDOUT
|
||
|
);
|
||
|
end generate;
|
||
| atari_chips/pokeyv2/pokeymaxv1.qsf | ||
|---|---|---|
|
set_global_assignment -name VHDL_FILE latch_delay_line.vhdl
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_1storder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE filtered_sigmadelta.vhd
|
||
|
set_global_assignment -name VHDL_FILE fir_filter.vhdl
|
||
| atari_chips/pokeyv2/pokeymaxv2.qsf | ||
|---|---|---|
|
set_global_assignment -name VHDL_FILE latch_delay_line.vhdl
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_1storder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE filtered_sigmadelta.vhd
|
||
|
set_global_assignment -name VHDL_FILE fir_filter.vhdl
|
||
| atari_chips/pokeyv2/pokeymaxv3.qsf | ||
|---|---|---|
|
set_global_assignment -name VHDL_FILE latch_delay_line.vhdl
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_1storder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE filtered_sigmadelta.vhd
|
||
|
set_global_assignment -name VHDL_FILE fir_filter.vhdl
|
||
| atari_chips/pokeyv2/pokeymaxv4.5.qsf | ||
|---|---|---|
|
set_global_assignment -name VHDL_FILE latch_delay_line.vhdl
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_1storder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE filtered_sigmadelta.vhd
|
||
|
set_global_assignment -name VHDL_FILE fir_filter.vhdl
|
||
| atari_chips/pokeyv2/pokeymaxv4.qsf | ||
|---|---|---|
|
set_global_assignment -name VHDL_FILE latch_delay_line.vhdl
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_1storder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE sigmadelta_2ndorder_dither.vhd
|
||
|
set_global_assignment -name VHDL_FILE filtered_sigmadelta.vhd
|
||
|
set_global_assignment -name VHDL_FILE fir_filter.vhdl
|
||
| atari_chips/pokeyv2/sigmadelta_2ndorder_dither.vhd | ||
|---|---|---|
|
ENTITY sigmadelta_2ndorder_dither IS
|
||
|
GENERIC (
|
||
|
DITHER_ENABLE : integer := 1; -- 0/1
|
||
|
DITHER_BITS : integer := 3; -- 1..4; start small
|
||
|
LFSR_SEED : unsigned(15 downto 0) := x"ACE1"
|
||
|
DITHER_BITS : integer := 3 -- 1..4; start small
|
||
|
);
|
||
|
PORT
|
||
|
(
|
||
| ... | ... | |
|
RESET_N : IN STD_LOGIC;
|
||
|
|
||
|
ENABLE : IN STD_LOGIC := '1';
|
||
|
DITHER_IN : IN STD_LOGIC_VECTOR(15 downto 0);
|
||
|
|
||
|
AUDIN : IN UNSIGNED(15 downto 0);
|
||
|
AUDOUT : OUT std_logic
|
||
| ... | ... | |
|
signal ttl2_reg : signed(23 downto 1) := (others => '0');
|
||
|
signal out_reg : std_logic := '0';
|
||
|
|
||
|
signal lfsr : unsigned(15 downto 0) := LFSR_SEED;
|
||
|
|
||
|
function sat_add(a, b : signed) return signed is
|
||
|
variable aw : integer := a'length;
|
||
|
variable ext : signed(aw downto 0);
|
||
| ... | ... | |
|
ttl1_reg <= (others => '0');
|
||
|
ttl2_reg <= (others => '0');
|
||
|
out_reg <= '0';
|
||
|
lfsr <= LFSR_SEED;
|
||
|
elsif rising_edge(CLK) then
|
||
|
if ENABLE = '1' then
|
||
|
|
||
|
-- 16-bit Galois LFSR taps: 16,14,13,11
|
||
|
lfsr <= lfsr(14 downto 0) & (lfsr(15) xor lfsr(13) xor lfsr(12) xor lfsr(10));
|
||
|
|
||
|
-- Keep your original input shaping
|
||
|
audinadj := resize(AUDIN, 17) + to_unsigned(4096, 17) - resize(AUDIN(15 downto 3), 17);
|
||
|
|
||
|
-- Build tiny threshold dither (default ~±1..3 LSB at the *threshold* domain)
|
||
|
if DITHER_ENABLE = 1 then
|
||
|
u1 := resize(signed('0' & lfsr(DITHER_BITS-1 downto 0)), DITHER_BITS+1)
|
||
|
u1 := resize(signed('0' & DITHER_IN(DITHER_BITS-1 downto 0)), DITHER_BITS+1)
|
||
|
- to_signed(2**(DITHER_BITS-1), DITHER_BITS+1);
|
||
|
u2 := resize(signed('0' & lfsr(2*DITHER_BITS-1 downto DITHER_BITS)), DITHER_BITS+1)
|
||
|
u2 := resize(signed('0' & DITHER_IN(2*DITHER_BITS-1 downto DITHER_BITS)), DITHER_BITS+1)
|
||
|
- to_signed(2**(DITHER_BITS-1), DITHER_BITS+1);
|
||
|
dith23 := resize(resize(u1 - u2, 23), 23);
|
||
|
else
|
||
| atari_chips/pokeyv2/sigmadelta_dither.vhd | ||
|---|---|---|
|
---------------------------------------------------------------------------
|
||
|
-- (c) 2020 mark watson
|
||
|
-- I am happy for anyone to use this for non-commercial use.
|
||
|
-- If my vhdl files are used commercially or otherwise sold,
|
||
|
-- please contact me for explicit permission at scrameta (gmail).
|
||
|
-- This applies for source and binary form and derived works.
|
||
|
---------------------------------------------------------------------------
|
||
|
--
|
||
|
LIBRARY ieee;
|
||
|
USE ieee.std_logic_1164.all;
|
||
|
use ieee.numeric_std.all;
|
||
|
use IEEE.STD_LOGIC_MISC.all;
|
||
|
|
||
|
ENTITY sigmadelta_dither IS
|
||
|
GENERIC (
|
||
|
LFSR_SEED : unsigned(15 downto 0) := x"ACE1"
|
||
|
);
|
||
|
PORT
|
||
|
(
|
||
|
CLK : IN STD_LOGIC;
|
||
|
RESET_N : IN STD_LOGIC;
|
||
|
|
||
|
ENABLE : IN STD_LOGIC := '1';
|
||
|
|
||
|
DITHER_OUT1 : OUT STD_LOGIC_VECTOR(15 downto 0);
|
||
|
DITHER_OUT2 : OUT STD_LOGIC_VECTOR(15 downto 0);
|
||
|
DITHER_OUT3 : OUT STD_LOGIC_VECTOR(15 downto 0);
|
||
|
DITHER_OUT4 : OUT STD_LOGIC_VECTOR(15 downto 0)
|
||
|
);
|
||
|
END sigmadelta_dither;
|
||
|
|
||
|
architecture vhdl of sigmadelta_dither is
|
||
|
signal lfsr_next : unsigned(15 downto 0);
|
||
|
signal lfsr_reg : unsigned(15 downto 0);
|
||
|
begin
|
||
|
|
||
|
process(CLK, RESET_N)
|
||
|
begin
|
||
|
if RESET_N = '0' then
|
||
|
lfsr_reg <= LFSR_SEED;
|
||
|
elsif rising_edge(CLK) then
|
||
|
if ENABLE = '1' then
|
||
|
lfsr_reg <= lfsr_next;
|
||
|
end if;
|
||
|
end if;
|
||
|
end process;
|
||
|
|
||
|
-- 16-bit Galois LFSR taps: 16,14,13,11
|
||
|
lfsr_next <= lfsr_reg(14 downto 0) & (lfsr_reg(15) xor lfsr_reg(13) xor lfsr_reg(12) xor lfsr_reg(10));
|
||
|
|
||
|
DITHER_OUT1 <= std_logic_vector(lfsr_reg);
|
||
|
DITHER_OUT2 <= std_logic_vector(lfsr_reg(10 downto 0) & lfsr_reg(15 downto 11));
|
||
|
DITHER_OUT3 <= std_logic_vector(lfsr_reg(5 downto 0) & lfsr_reg(15 downto 6));
|
||
|
DITHER_OUT4 <= std_logic_vector(lfsr_reg(12 downto 0) & lfsr_reg(15 downto 13));
|
||
|
|
||
|
end vhdl;
|
||
|
|
||
Cut some LEs by sharing the dither LFSR