--**************************************************************************-- library IEEE; use IEEE.std_logic_1164.all; use IEEE.STD_LOGIC_ARITH.all; --**************************************************************************-- entity PLAY is port(rst : in STD_LOGIC; clk : in STD_LOGIC; memadl : in STD_LOGIC_VECTOR (7 downto 0); memadh : in STD_LOGIC_VECTOR (7 downto 0); upp0 : in STD_LOGIC_VECTOR (7 downto 0); upwr : in STD_LOGIC; spk : out STD_LOGIC); end PLAY; --**************************************************************************-- architecture PLAY_ARCH of PLAY is constant C0_16 : UNSIGNED (15 downto 0) := "0000000000000000"; constant C1_16 : UNSIGNED (15 downto 0) := "0000000000000001"; constant F1_A : UNSIGNED (15 downto 0) := "0110101010001000"; constant F1_AS : UNSIGNED (15 downto 0) := "0110010010001110"; constant F1_B : UNSIGNED (15 downto 0) := "0101111011101000"; constant F1_C : UNSIGNED (15 downto 0) := "0101100110010110"; constant F1_CS : UNSIGNED (15 downto 0) := "0101010010001110"; constant F1_D : UNSIGNED (15 downto 0) := "0100111111010000"; constant F1_DS : UNSIGNED (15 downto 0) := "0100101101010100"; constant F1_E : UNSIGNED (15 downto 0) := "0100011100011010"; constant F1_F : UNSIGNED (15 downto 0) := "0100001100011100"; constant F1_FS : UNSIGNED (15 downto 0) := "0011111101011000"; constant F1_G : UNSIGNED (15 downto 0) := "0011101111001010"; constant F1_GS : UNSIGNED (15 downto 0) := "0011100001110000"; constant F2_A : UNSIGNED (15 downto 0) := "0011010101000100"; constant F2_AS : UNSIGNED (15 downto 0) := "0011001001000111"; constant F2_B : UNSIGNED (15 downto 0) := "0010111101110100"; constant F2_C : UNSIGNED (15 downto 0) := "0010110011001011"; constant F2_CS : UNSIGNED (15 downto 0) := "0010101001000111"; constant F2_D : UNSIGNED (15 downto 0) := "0010011111101000"; constant F2_DS : UNSIGNED (15 downto 0) := "0010010110101010"; constant F2_E : UNSIGNED (15 downto 0) := "0010001110001101"; constant F2_F : UNSIGNED (15 downto 0) := "0010000110001110"; constant F2_FS : UNSIGNED (15 downto 0) := "0001111110101100"; constant F2_G : UNSIGNED (15 downto 0) := "0001110111100101"; constant F2_GS : UNSIGNED (15 downto 0) := "0001110000111000"; constant F3_A : UNSIGNED (15 downto 0) := "0001101010100010"; constant F3_AS : UNSIGNED (15 downto 0) := "0001100100100011"; constant F3_B : UNSIGNED (15 downto 0) := "0001011110111010"; constant F3_C : UNSIGNED (15 downto 0) := "0001011001100101"; constant F3_CS : UNSIGNED (15 downto 0) := "0001010100100011"; constant F3_D : UNSIGNED (15 downto 0) := "0001001111110100"; constant F3_DS : UNSIGNED (15 downto 0) := "0001001011010101"; constant F3_E : UNSIGNED (15 downto 0) := "0001000111000110"; constant F3_F : UNSIGNED (15 downto 0) := "0001000011000111"; constant F3_FS : UNSIGNED (15 downto 0) := "0000111111010110"; constant F3_G : UNSIGNED (15 downto 0) := "0000111011110010"; constant F3_GS : UNSIGNED (15 downto 0) := "0000111000011100"; constant REG_ADDRH : STD_LOGIC_VECTOR (7 downto 0) := "11111111"; constant REG_ADDRL : STD_LOGIC_VECTOR (7 downto 0) := "00000000"; signal clk_div, clk_cnt : UNSIGNED (15 downto 0); signal toggle : STD_LOGIC; begin -- -- sound generator -- process(rst, clk, toggle) begin if( rst = '0' ) then clk_cnt <= C0_16; toggle <= '0'; spk <= '1'; elsif( clk'event and clk = '1' ) then if( clk_cnt = clk_div ) then clk_cnt <= C0_16; toggle <= not toggle; else clk_cnt <= clk_cnt + C1_16; end if; end if; spk <= toggle; end process; -- -- cpu read/write and note generator -- process(rst, clk) begin if( rst = '0' ) then clk_div <= C0_16; elsif( clk'event and clk = '1' ) then if( upwr = '0' ) then if( memadh = REG_ADDRH and memadl = REG_ADDRL ) then case upp0 is -- octave 1 when "00000000" => clk_div <= F1_A; when "00000001" => clk_div <= F1_AS; when "00000010" => clk_div <= F1_B; when "00000011" => clk_div <= F1_C; when "00000100" => clk_div <= F1_CS; when "00000101" => clk_div <= F1_D; when "00000110" => clk_div <= F1_DS; when "00000111" => clk_div <= F1_E; when "00001000" => clk_div <= F1_F; when "00001001" => clk_div <= F1_FS; when "00001010" => clk_div <= F1_G; when "00001011" => clk_div <= F1_GS; -- octave 2 when "00010000" => clk_div <= F2_A; when "00010001" => clk_div <= F2_AS; when "00010010" => clk_div <= F2_B; when "00010011" => clk_div <= F2_C; when "00010100" => clk_div <= F2_CS; when "00010101" => clk_div <= F2_D; when "00010110" => clk_div <= F2_DS; when "00010111" => clk_div <= F2_E; when "00011000" => clk_div <= F2_F; when "00011001" => clk_div <= F2_FS; when "00011010" => clk_div <= F2_G; when "00011011" => clk_div <= F2_GS; -- octave 3 when "00110000" => clk_div <= F3_A; when "00110001" => clk_div <= F3_AS; when "00110010" => clk_div <= F3_B; when "00110011" => clk_div <= F3_C; when "00110100" => clk_div <= F3_CS; when "00110101" => clk_div <= F3_D; when "00110110" => clk_div <= F3_DS; when "00110111" => clk_div <= F3_E; when "00111000" => clk_div <= F3_F; when "00111001" => clk_div <= F3_FS; when "00111010" => clk_div <= F3_G; when "00111011" => clk_div <= F3_GS; when others => clk_div <= C0_16; end case; end if; end if; end if; end process; end PLAY_ARCH;