diff options
Diffstat (limited to 'pb_logique_seq.srcs/sources_1/imports/new')
26 files changed, 3467 insertions, 0 deletions
diff --git a/pb_logique_seq.srcs/sources_1/imports/new/affhex_pmodssd_v3.vhd b/pb_logique_seq.srcs/sources_1/imports/new/affhex_pmodssd_v3.vhd new file mode 100644 index 0000000..8e3b048 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/affhex_pmodssd_v3.vhd @@ -0,0 +1,172 @@ +---------------------------------------------------------------------------------------------
+-- circuit affhex_pmodssd_v3.vhd
+---------------------------------------------------------------------------------------------
+-- Université de Sherbrooke - Département de GEGI
+-- Version : 3.0
+-- Nomenclature : 0.8 GRAMS
+-- Date : revision 16 mai 2019
+-- Auteur(s) : Réjean Fontaine, Daniel Dalle
+-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20)
+--
+-- Outils : vivado 2016.1 64 bits, vivado 2018.2
+---------------------------------------------------------------------------------------------
+-- Description:
+-- Affichage sur module de 2 chiffes (7 segments) sur PmodSSD
+-- reference https://reference.digilentinc.com/reference/pmod/pmodssd/start
+-- PmodSSD™ Reference Manual Doc: 502-126 Digilent, Inc.
+--
+-- Revisions
+-- mise a jour D Dalle 16 mai 2019 controle de la memorisation de l'affichage
+-- mise a jour D Dalle 30 avril 2019 constantes horloges en Hz (pour coherence avec autres modules)
+-- mise a jour D Dalle 17 decembre 2018 constantes horloges en Hz (pour coherence avec autres modules)
+-- mise a jour D Dalle 22 octobre 2018 corrections, simplifications
+-- mise a jour D Dalle 15 octobre documentation affhex_pmodssd_sol_v0.vhd
+-- mise a jour D Dalle 12 septembre pour eviter l'usage d'une horloge interne
+-- mise a jour D Dalle 7 septembre, calcul des constantes.
+-- mise a jour D Dalle 5 septembre 2018, nom affhexPmodSSD, 6 septembre :division horloge
+-- module de commande le l'afficheur 2 segments 2 digits sur pmod
+-- Daniel Dalle revision pour sortir les signaux du connecteur Pmod directement
+-- Daniel Dalle 30 juillet 2018:
+-- revision pour une seule entre sur 8 bits affichee sur les deux chiffres Hexa
+--
+-- Creation selon affhex7segx4v3.vhd
+-- (Daniel Dalle, Réjean Fontaine Universite de Sherbrooke, Departement GEGI)
+-- 26 septembre 2011, revision 12 juin 2012, 25 janvier 2013, 7 mai 2015
+-- Contrôle de l'afficheur a sept segment (BASYS2 - NEXYS2)
+-- horloge 100MHz et diviseur interne
+---------------------------------------------------------------------------------------------
+-- À faire :
+--
+--
+--
+---------------------------------------------------------------------------------------------
+
+library IEEE;
+use IEEE.STD_LOGIC_1164.ALL;
+use ieee.std_logic_arith.all;
+use ieee.std_logic_unsigned.all;
+
+entity affhexPmodSSD_v3 is
+generic (const_CLK_Hz: integer := 100_000_000); -- horloge en Hz, typique 100 MHz
+ Port ( clk : in STD_LOGIC; -- horloge systeme, typique 100 MHz (preciser par le constante)
+ reset : in STD_LOGIC;
+ DA : in STD_LOGIC_VECTOR (7 downto 0); -- donnee a afficher sur 8 bits : chiffre hexa position 1 et 0
+ i_btn : in STD_LOGIC_vector(3 downto 0); -- demande memorisation affichage continu, si 0: continu
+ JPmod : out STD_LOGIC_VECTOR (7 downto 0) -- sorties directement adaptees au connecteur PmodSSD
+ );
+end affhexPmodSSD_v3;
+
+architecture Behavioral of affhexPmodSSD_v3 is
+
+-- realisation compteur division horloge pour multiplexer affichage SSD
+-- constante pour ajuster selon l horloge pilote du controle des afficheurs
+constant CLK_SSD_Hz_des : integer := 5000; --Hz -- horloge desiree pour raffraichir afficheurs 7 segment
+constant const_div_clk_SSD : integer := (const_CLK_Hz/CLK_SSD_Hz_des-1);
+constant cdvia : std_logic_vector (15 downto 0):= conv_std_logic_vector(const_div_clk_SSD, 16); -- donne 5 KHz soit 200 us
+signal counta : std_logic_vector (15 downto 0) := (others => '0');
+
+signal donn : STD_LOGIC_VECTOR (3 downto 0);
+signal DA_sel : STD_LOGIC_VECTOR (7 downto 0);
+signal segm : STD_LOGIC_VECTOR (6 downto 0);
+--
+signal SEL : STD_LOGIC;
+signal q_DA : std_logic_vector (7 downto 0);
+signal q_aff_mem : STD_LOGIC;
+
+begin
+
+-- selection chiffre pour affichage
+local_CLK_proc: process(CLK)
+begin
+ if(CLK'event and CLK = '1') then
+ counta <= counta + 1;
+ if (counta = cdvia) then -- devrait se produire aux 200 us approx
+ counta <= (others => '0');
+ SEL <= not SEL; -- bascule de la selection du chiffre (0 ou 1)
+ -- SEL devrait avoir periode de 400 us approx
+ end if;
+ end if;
+end process;
+
+-- multiplexage pour affichage digit
+sel_digit_proc: process(SEL, DA_sel)
+begin
+ if SEL = '0' then
+ donn <= DA_sel(3 downto 0);
+ else
+ donn <= DA_sel(7 downto 4);
+ end if;
+end process;
+
+-- multiplexage pour selection donnee (continue ou bloquée)
+sel_aff_proc: process(i_btn, DA)
+begin
+ if i_btn(2) = '0' then
+ DA_sel <= DA;
+ else
+ DA_sel <= q_DA;
+ end if;
+end process;
+
+ inst_reg_aff : process ( clk, reset)
+ begin
+ if (reset = '1') then
+ q_DA <= (others => '0');
+ else
+ -- if rising_edge (d_ac_bclk) and d_str_btn(1) = '1' then
+ if rising_edge (clk) and q_aff_mem = '0' and i_btn(2) ='0' then
+ q_DA <= DA;
+ end if;
+ end if;
+ end process;
+
+
+fin_continu_process : process (CLK)
+ begin
+ if (rising_edge(CLK)) then
+ q_aff_mem <= i_btn(2);
+ end if;
+ end process;
+
+-- correspondance des segments des afficheurs
+segment: process (donn, segm)
+ begin
+ case donn is
+ -- "gfedcba"
+ when "0000" => segm <= "0111111"; -- 0
+ when "0001" => segm <= "0000110"; -- 1
+ when "0010" => segm <= "1011011"; -- 2
+ when "0011" => segm <= "1001111"; -- 3
+ when "0100" => segm <= "1100110"; -- 4
+ when "0101" => segm <= "1101101"; -- 5
+ when "0110" => segm <= "1111101"; -- 6
+ when "0111" => segm <= "0000111"; -- 7
+ when "1000" => segm <= "1111111"; -- 8
+ when "1001" => segm <= "1101111"; -- 9
+ when "1010" => segm <= "1110111"; -- A
+ when "1011" => segm <= "1111100"; -- b
+ when "1100" => segm <= "0111001"; -- C
+ when "1101" => segm <= "1011110"; -- d
+ when "1110" => segm <= "1111001"; -- E
+ when "1111" => segm <= "1110001"; -- F
+ when others => segm <= "0000000";
+ end case;
+ end process;
+
+-- assignation des sorties sur le connecteur Pmod
+sortie_proc: process(segm, SEL)
+begin
+-- contenu segm "gfedcba" pour version Pmod
+ JPmod(0) <= segm(0);
+ JPmod(1) <= segm(1);
+ JPmod(2) <= segm(2);
+ JPmod(3) <= segm(3);
+ JPmod(4) <= segm(4);
+ JPmod(5) <= segm(5);
+ JPmod(6) <= segm(6);
+ JPmod(7) <= SEL;
+end process;
+
+
+end Behavioral;
+
diff --git a/pb_logique_seq.srcs/sources_1/imports/new/attenateur_pwm.vhd b/pb_logique_seq.srcs/sources_1/imports/new/attenateur_pwm.vhd new file mode 100644 index 0000000..d0c765d --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/attenateur_pwm.vhd @@ -0,0 +1,71 @@ +--------------------------------------------------------------------------------------------- +-- attenuateur_pwm.vhd +--------------------------------------------------------------------------------------------- +-- Generation d'horloge et de signaux de synchronisation +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 1.0 +-- Nomenclature : ref GRAMS +-- Date : 17 sept. 2018 +-- Auteur(s) : Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- Outils : vivado 2018.2 64 bits +-- +-------------------------------- +-- Description +-------------------------------- +-- Attenuateur par modulation pwm pour sorties leds +-- +-- +--------------------------------------------------------------------------------------------- +-- À FAIRE: +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.std_logic_arith.all; -- requis pour les constantes etc. +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +Library UNISIM; +use UNISIM.vcomponents.all; + +entity attenuateur_pwm is +generic (c_val_seuil: std_logic_vector(7 downto 0) := "00000111"); + Port ( + CLK : in STD_LOGIC; -- Entrée horloge + i_signal : in STD_LOGIC; -- entree + o_signal : out STD_LOGIC -- sortie + ); +end attenuateur_pwm; + +architecture Behavioral of attenuateur_pwm is + + -- constantes pour les diviseurs + + constant c_seuil : std_logic_vector(7 downto 0) := c_val_seuil; + signal d_val_compteur : std_logic_vector(7 downto 0) := "00000000"; + signal d_signal_on : std_logic := '1'; + + +begin + +o_signal <= d_signal_on AND i_signal; + +process(CLK) +begin + if(CLK'event and CLK = '1') then + d_val_compteur <= d_val_compteur + 1; + if (d_val_compteur = "00000000") then + d_signal_on <= '1'; -- on + else if (d_val_compteur = c_seuil) then + d_signal_on <= '0'; -- off + end if; + end if; + end if; +end process; + +end Behavioral; + diff --git a/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_1.vhd b/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_1.vhd new file mode 100644 index 0000000..3fd0a86 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_1.vhd @@ -0,0 +1,62 @@ + +--------------------------------------------------------------------------------------------- +-- calcul_param_1.vhd +--------------------------------------------------------------------------------------------- +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 5.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : 16 janvier 2020, 4 mai 2020 +-- Auteur(s) : +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2019.1 64 bits +-- +--------------------------------------------------------------------------------------------- +-- Description (sur une carte Zybo) +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- +-- À FAIRE: +-- Voir le guide de la problématique +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs +USE ieee.numeric_std.ALL; +Library UNISIM; +use UNISIM.vcomponents.all; + +---------------------------------------------------------------------------------- +-- +---------------------------------------------------------------------------------- +entity calcul_param_1 is + Port ( + i_bclk : in std_logic; -- bit clock (I2S) + i_reset : in std_logic; + i_en : in std_logic; -- un echantillon present a l'entrée + i_ech : in std_logic_vector (23 downto 0); -- echantillon en entrée + o_param : out std_logic_vector (7 downto 0) -- paramètre calculé + ); +end calcul_param_1; + +---------------------------------------------------------------------------------- + +architecture Behavioral of calcul_param_1 is + +--------------------------------------------------------------------------------- +-- Signaux +---------------------------------------------------------------------------------- + + +--------------------------------------------------------------------------------------------- +-- Description comportementale +--------------------------------------------------------------------------------------------- +begin + + o_param <= x"01"; -- temporaire ... + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_2.vhd b/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_2.vhd new file mode 100644 index 0000000..35574c9 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_2.vhd @@ -0,0 +1,62 @@ + +--------------------------------------------------------------------------------------------- +-- calcul_param_2.vhd (temporaire) +--------------------------------------------------------------------------------------------- +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 5.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : 16 janvier 2020, 4 mai 2020 +-- Auteur(s) : +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2019.1 64 bits +-- +--------------------------------------------------------------------------------------------- +-- Description (sur une carte Zybo) +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- +-- À FAIRE: +-- Voir le guide de la problématique +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs +USE ieee.numeric_std.ALL; +Library UNISIM; +use UNISIM.vcomponents.all; + +---------------------------------------------------------------------------------- +-- +---------------------------------------------------------------------------------- +entity calcul_param_2 is + Port ( + i_bclk : in std_logic; -- bit clock + i_reset : in std_logic; + i_en : in std_logic; -- un echantillon present + i_ech : in std_logic_vector (23 downto 0); + o_param : out std_logic_vector (7 downto 0) + ); +end calcul_param_2; + +---------------------------------------------------------------------------------- + +architecture Behavioral of calcul_param_2 is + +--------------------------------------------------------------------------------- +-- Signaux +---------------------------------------------------------------------------------- + + +--------------------------------------------------------------------------------------------- +-- Description comportementale +--------------------------------------------------------------------------------------------- +begin + + o_param <= x"02"; -- temporaire ... + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_3.vhd b/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_3.vhd new file mode 100644 index 0000000..4ae1d31 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/calcul_param_3.vhd @@ -0,0 +1,77 @@ + +--------------------------------------------------------------------------------------------- +-- calcul_param_3.vhd +--------------------------------------------------------------------------------------------- +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 6.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : 29 janvier 2019, rev 13 février +-- : revision 4 mai 2020 élimination de i_lrc +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +--------------------------------------------------------------------------------------------- +-- Description +-- Le troisième paramètre consiste à extraire la valeur pic de l'amplitude +-- du signal dans une fenêtre glissante couvrant les 48 échantillons les plus récents. +--------------------------------------------------------------------------------------------- +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs +USE ieee.numeric_std.ALL; +--use IEEE.std_logic_arith.all; -- requis pour les constantes etc. +--use IEEE.std_logic_arith.all; -- requis pour les constantes telles que cdviv6 etc. +Library UNISIM; +use UNISIM.vcomponents.all; + +---------------------------------------------------------------------------------- +-- **************************************************************************** -- +---------------------------------------------------------------------------------- +entity calcul_param_3 is + Port ( + i_bclk : in std_logic; -- bit clock + i_reset : in std_logic; -- + i_en : in std_logic; -- indique un echantillon present + -- i_lrc : in std_logic; -- "Left-Right clock" (I2S) + i_ech : in std_logic_vector (23 downto 0); -- valide si en = '1' + o_param : out std_logic_vector (7 downto 0) -- valeur paramètre evaluée + ); +end calcul_param_3; + + +---------------------------------------------------------------------------------- + + +architecture Behavioral of calcul_param_3 is + +--------------------------------------------------------------------------------- +-- Signaux +---------------------------------------------------------------------------------- + + +--------------------------------------------------------------------------------------------- +-- Description comportementale +--------------------------------------------------------------------------------------------- +begin +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE +-- PAS BESOIN D'IMPLÉMENTER CE PARAMÈTRE + o_param <= x"03"; -- temporaire ... + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/circuit_tr_signal.vhd b/pb_logique_seq.srcs/sources_1/imports/new/circuit_tr_signal.vhd new file mode 100644 index 0000000..6762780 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/circuit_tr_signal.vhd @@ -0,0 +1,274 @@ +--------------------------------------------------------------------------------------------- +-- circuit_tr_signal.vhd +--------------------------------------------------------------------------------------------- +-- Circuit de base pour la problématique sur la carte ZYBO avec codec SSM2603 +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 5.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : rev 10 janvier 2020, 4 mai 2020, 5 janvier 2022 +-- Auteur(s) : Daniel Dalle, Sébastien Roy, Réjean Fontaine, Julien Rossignol +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2020.2 +-- +--------------------------------------------------------------------------------------------- +-- Description (sur une carte Zybo) +-- Circuit de fondation pour la problématique, voir la documentation de l'APP et +-- en particulier l'annexe. +-- +-- Modification 5 janvier 2022 conversion vers block design +-- Modification 7 janvier 2020 documentation +-- Modification 6 mai 2019 introduction de decodeur_i2s_v1b +-- Developpement initial 2 février 2019 +-- +--------------------------------------------------------------------------------------------- +-- ref documents problématique +-- ref manual Zybo +-- https://reference.digilentinc.com/reference/programmable-logic/zybo-z7/reference-manual +-- ref schematic (public) +-- https://reference.digilentinc.com/_media/reference/programmable-logic/zybo-z7/zybo_z7_sch-public.pdf +-- ref Analog Devices SSM2603 Audio Codec +-- https://www.analog.com/media/en/technical-documentation/data-sheets/ssm2603.pdf +-- +-- carte ZYBO Z7-10 (voir les notes de projet) +-- sur PmodA double cable vers PmodSSD (version preliminaire) +-- sur PmodB vide PmodB n'existe pas sur Zybo-Z7-10 +-- sur PmodC ver Pmod8LD +-- sur PmodD signaux de tests +-- sur PmodE signaux de tests +-- +--------------------------------------------------------------------------------------------- +-- À FAIRE: +-- voir documents problématique +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +library UNISIM; +use UNISIM.VCOMPONENTS.ALL; +---------------------------------------------------------------------------------- +-- +---------------------------------------------------------------------------------- +entity circuit_tr_signal is +generic ( mode_simulation: std_logic := '0'); + Port ( + o_ac_bclk : out STD_LOGIC; -- bit clock ... I2S digital audio clk ~ mclk /4 + o_ac_mclk : out STD_LOGIC; -- SSM2603 Master Clock horloge ~ 12.288 MHz + o_ac_muten : out STD_LOGIC; -- DAC Output Mute, Active Low + o_ac_pbdat : out STD_LOGIC; -- I²S (Playback Data) + o_ac_pblrc : out STD_LOGIC; -- I²S (Playback Channel Clock) ~ 48. KHz (~ 20.8 us) + i_ac_recdat : in STD_LOGIC; -- I²S (Record Data) + o_ac_reclrc : out STD_LOGIC; -- I²S (Record Channel Clock) ~ 48. KHz (~ 20.8 us) + io_ac_scl : inout STD_LOGIC; -- horloge I2C SPI + io_ac_sda : inout STD_LOGIC; -- I2C 2-Wire Control Interface Data Input/Output. + -- + i_btn : in std_logic_vector (3 downto 0); + i_sw : in std_logic_vector (3 downto 0); + sysclk : in std_logic; + o_pmodssd : out std_logic_vector (7 downto 0); + o_led : out std_logic_vector (3 downto 0); + o_pmodled : out std_logic_vector (7 downto 0); + o_led6_r : out std_logic; + o_led6_g : out std_logic +-- +-- ; -- DIO pour tests avec analyseur logique +-- DIO : out std_logic_vector (15 downto 0) -- Signaux test pour analyseur logique +-- -- (connecteurs JD et JE) +-- -- voir avec fichier contraintes + ); +end circuit_tr_signal; + +architecture STRUCTURE of circuit_tr_signal is + + constant freq_sys_Hz: integer := 125_000_000; -- Hz + + component init_codec_v2 + Port ( + i_reset : in std_logic; + o_cfg_done : out STD_LOGIC; + o_cfg_busy : out STD_LOGIC; + o_ena : out STD_LOGIC; -- pour tests + -- pour interface avec partie I2C du codec + i_lrc : in STD_LOGIC; -- I²S (Record Channel Clock) ~ 48. KHz (~ 20.8 us) + io_scl : inout STD_LOGIC; -- horloge I2C SPI + io_sda : inout STD_LOGIC; -- I2C 2-Wire Control Interface Data Input/Output. + -- + i_strobe_1000Hz : in std_logic; + clk_p : in std_logic + ); + end component; + + component synchro_codec_v1 is + generic (cst_CLK_syst_Hz: integer := 100_000_000); -- valeur par defaut de fréquence de clkm + Port ( + sysclk : in STD_LOGIC; -- Entrée horloge systeme (typique 125 MHz (1/8 ns) ou 100 ( 1/10 ns)) + o_clk_0 : out STD_LOGIC; -- horloge via bufg 50. MHz (20 ns) + o_mclk : out STD_LOGIC; -- horloge via bufg 12.389 MHz (80,714 ns) + o_stb_1000Hz : out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1000Hz + o_stb_1Hz : out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1Hz + o_S_1Hz : out STD_LOGIC; -- Signal temoin 1 Hz + o_bclk : out STD_LOGIC; -- horloge bit clk (defaut 12.289 MHz / 4 soit 3,07225 MHz (325.49 ns) ) + o_reclrc : out STD_LOGIC -- horloge record, play back, sampling rate clock, left right channel (defaut 48 KHz (20,83 us)) + ); + end component; + + component attenuateur_pwm + generic (c_val_seuil: std_logic_vector(7 downto 0) := "00001111"); + port ( + CLK : in STD_LOGIC; -- Entrée horloge + i_signal : in STD_LOGIC; -- entree + o_signal : out STD_LOGIC -- sortie + ); + end component; + + component design_1 is + port ( + i_recdat : in STD_LOGIC; + i_lrc : in STD_LOGIC; + i_btn : in STD_LOGIC_VECTOR ( 3 downto 0 ); + i_sw : in STD_LOGIC_VECTOR ( 3 downto 0 ); + clk_100MHz : in STD_LOGIC; + o_pbdat : out STD_LOGIC_VECTOR ( 0 to 0 ); + JPmod : out STD_LOGIC_VECTOR ( 7 downto 0 ); + o_param : out STD_LOGIC_VECTOR ( 7 downto 0 ); + o_sel_fct : out STD_LOGIC_VECTOR ( 1 downto 0 ); + o_sel_par : out STD_LOGIC_VECTOR ( 1 downto 0 ) + ); + end component design_1; + +--------------------------------------------------------------------------------- +-- Signaux +---------------------------------------------------------------------------------- + + signal clk_p : std_logic; -- horloge de synchro principale + signal d_strobe_1000Hz : std_logic; + signal d_strobe_cfg : std_logic; + signal d_strobe_1Hz : std_logic := '0'; + + signal d_T1Hz : std_logic; + signal reset : std_logic; + + -- + signal d_sw : std_logic_vector (3 downto 0); -- 4 bits sur Zybo + signal d_btn : std_logic_vector (3 downto 0); + signal d_btn_db : std_logic_vector (3 downto 0); + -- signal d_str_btn : std_logic_vector (3 downto 0); + + + signal d_ac_bclk : std_logic; --out STD_LOGIC; -- horloge I2S digital audio sera mclk/4 + signal d_ac_mclk : std_logic; --out STD_LOGIC; -- Master Clock horloge ~ 12.288 MHz + signal d_ac_muten : std_logic; --out STD_LOGIC; -- DAC Output Mute, Active Low + signal d_ac_pbdat : std_logic; --out STD_LOGIC; -- I²S (Playback Data) + signal d_ac_pblrc : std_logic; --out STD_LOGIC; -- I²S (Playback Channel Clock) + signal d_ac_recdat : std_logic; --in STD_LOGIC; -- I²S (Record Data) + signal d_ac_reclrc : std_logic; --out STD_LOGIC; -- I²S (Record Channel Clock) + signal d_ac_scl : std_logic; --out STD_LOGIC; -- I2C SCLK active ou non + + signal d_cfg_busy : std_logic; + signal d_ena : std_logic; + signal d_cfg_done : std_logic; + + signal d_param : std_logic_vector (7 downto 0); + signal d_statut : std_logic_vector (3 downto 0); + +--------------------------------------------------------------------------------------------- +-- Description (sur une carte Zybo) +--------------------------------------------------------------------------------------------- +begin + + inst_synchro : synchro_codec_v1 + generic map (cst_CLK_syst_Hz => freq_sys_Hz) + port map ( + sysclk => sysclk, + o_clk_0 => clk_p, -- 50 MHz + o_mclk => d_ac_mclk, -- 12.288 MHz approx + o_stb_1000Hz => d_strobe_1000Hz, + o_stb_1Hz => d_strobe_1Hz, + o_S_1Hz => d_T1Hz, + o_bclk => d_ac_bclk, -- freq mclk / 4 + o_reclrc => d_ac_reclrc + ); + + +inst_init_codec: init_codec_v2 +--generic ( mode_simulation: std_logic := '0'); + Port map ( + i_reset => reset, + o_cfg_done => d_cfg_done, + o_cfg_busy => d_cfg_busy, + o_ena => d_ena, + -- + i_lrc => d_ac_reclrc, + io_scl => io_ac_scl, + io_sda => io_ac_sda, + -- + i_strobe_1000Hz => d_strobe_cfg, + clk_p => clk_p -- 50 MHz + ); + +d_strobe_cfg <= d_strobe_1000Hz; + +design_1_i: component design_1 port map ( + JPmod(7 downto 0) => o_pmodssd(7 downto 0), + clk_100MHz => d_ac_bclk, + i_btn(3 downto 0) => i_btn(3 downto 0), + i_recdat => d_ac_recdat, + i_lrc => d_ac_reclrc, + i_sw(3 downto 0) => i_sw(3 downto 0), + o_pbdat(0) => d_ac_pbdat, + o_param => d_param, + o_sel_fct => d_statut(3 downto 2), + o_sel_par => d_statut(1 downto 0) +); + + -- signaux d entree boutons et sw + d_btn <= i_btn; + d_sw <= i_sw; + + d_ac_muten <= '1'; -- DAC Output Mute, Active Low (Codec actif) ref SSM2603 + + o_led6_r <= d_T1Hz; -- signe de vie sur DEL rouge o_led6_r + o_pmodled <= d_param; + o_led <= d_statut; + + -- attenuateur pour modérer l'éclat de la led verte o_led6_g + inst_att: attenuateur_pwm + generic map (c_val_seuil => "00001111") + Port map + ( + CLK => clk_p, + i_signal => d_cfg_done, -- signal a afficher + o_signal => o_led6_g -- port led verte + ); + + + -- signaux d entree / sortie du codec + o_ac_bclk <= d_ac_bclk; --out STD_LOGIC; -- horloge I2S digital audio mclk/4 + o_ac_mclk <= d_ac_mclk; --out STD_LOGIC; -- Master Clock horloge 12.288 MHz clk_12_288MHz + o_ac_muten <= d_ac_muten; --out STD_LOGIC; -- DAC Output Mute, Active Low + d_ac_recdat <= i_ac_recdat; --in STD_LOGIC; -- I²S (Record Data) provenant du codec + + --signaux vers le codec (avec OBUF) + OBUF_o_pblrc : OBUF + port map ( + O => o_ac_pblrc, -- Buffer output + I => d_ac_pblrc -- Buffer input + ); + OBUF_o_reclrc : OBUF + port map ( + O => o_ac_reclrc, -- Buffer output + I => d_ac_reclrc -- Buffer input + ); + + OBUF_o_pbdat : OBUF + port map ( + O => o_ac_pbdat, -- Buffer output + I => d_ac_pbdat -- Buffer input + ); + + d_ac_pblrc <= d_ac_reclrc; -- I²S (Record et Playback Channel Clock) communs + +end STRUCTURE; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/compteur_nbits.vhd b/pb_logique_seq.srcs/sources_1/imports/new/compteur_nbits.vhd new file mode 100644 index 0000000..a8cf7d8 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/compteur_nbits.vhd @@ -0,0 +1,55 @@ +--------------------------------------------------------------------------------------------- +-- circuit compteur_nbits.vhd.vhd +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- Version : 1.0 +-- Nomenclature : 0.8 GRAMS +-- Date : 14 mai 2019 +-- Auteur(s) : Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- +-- Outils : vivado 2018.2 +--------------------------------------------------------------------------------------------- +-- Description: +-- Compteur a avec nombre de bits en parametre generic +--------------------------------------------------------------------------------------------- +-- À faire : +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +entity compteur_nbits is +generic (nbits : integer := 8); + port ( clk : in std_logic; + i_en : in std_logic; + reset : in std_logic; + o_val_cpt : out std_logic_vector (nbits-1 downto 0) + ); +end compteur_nbits; + +architecture BEHAVIORAL of compteur_nbits is +-- compteur simple + +signal d_val_cpt: std_logic_vector (nbits-1 downto 0); + +BEGIN + +compteur_proc : process (clk, reset, i_en) + begin + if ( reset = '1') then + d_val_cpt <= (others =>'0'); + else + if (rising_edge(clk) AND i_en = '1') then + d_val_cpt <= d_val_cpt + 1; + end if; + end if; + end process; +-- sortie + o_val_cpt <= d_val_cpt; + + END Behavioral; + diff --git a/pb_logique_seq.srcs/sources_1/imports/new/conditionne_btn_v7.vhd b/pb_logique_seq.srcs/sources_1/imports/new/conditionne_btn_v7.vhd new file mode 100644 index 0000000..5ebd314 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/conditionne_btn_v7.vhd @@ -0,0 +1,120 @@ +--------------------------------------------------------------------------------------------- +-- Circuit conditionne_btn_v7.vhd +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- Version : 7.0 +-- Nomenclature : 0.8 GRAMS +-- Date : 9 novembre 2018, 27 novembre 2018, 31 janvier 2019, 30 avril 2019, +-- 10 janvier 2020 +-- Auteur(s) : Réjean Fontaine, Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- +-- Outils : vivado 2019.1 +--------------------------------------------------------------------------------------------- +-- Description: +-- Circuit conditionnement des boutons avec horloge générique +-- V7 strobe sur transition descendante du bouton (relachement) +--------------------------------------------------------------------------------------------- +-- À faire : +-- +-- automatiser les calculs de constantes de délai (non requis si frequence 50 MHz pour CLK) +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.std_logic_arith.all; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +entity conditionne_btn_v7 is +generic (nbtn : integer := 4; mode_simul: std_logic := '0'); +port ( + CLK : in std_logic; -- horloge + i_btn : in std_logic_vector (nbtn-1 downto 0); -- signaux directs des boutons + -- + o_btn_db : out std_logic_vector (nbtn-1 downto 0); -- signaux nettoyés + -- (debounced) des boutons + o_strobe_btn : out std_logic_vector (nbtn-1 downto 0) -- impulsion + -- synchrone sur front CLK et transition descendante du bouton (relachement) + ); +end conditionne_btn_v7; + + +architecture Behavioral of conditionne_btn_v7 is + +component strb_gen is + Port ( + CLK : in STD_LOGIC; -- Entrée horloge + i_don : in STD_LOGIC; -- signal pour generer strobe au front montant + o_stb : out STD_LOGIC -- strobe synchrone resultant + ); + end component; + + signal d_btn: std_logic_vector (nbtn-1 downto 0); + signal q0_btn: std_logic_vector (nbtn-1 downto 0); + signal q1_btn: std_logic_vector (nbtn-1 downto 0); + signal q2_btn: std_logic_vector (nbtn-1 downto 0); + + signal ValueCounter : std_logic_vector(21 downto 0) := "0000000000000000000000"; + -- note a 5 MHz, le bit 15 change a une frequende de 76 Hz environ + -- note a 50 MHz, le bit 18 change a une frequende de 95 Hz environ + -- note a 50 MHz, le bit 16 change a une frequende de 381 Hz environ + signal d_strobe_bit: std_logic; + signal d_bit_count: std_logic; + +begin +-- version temporaire ..... +-- automatiser les calculs de constantes de délai + +process(CLK) +begin + if (CLK'event and CLK = '1') then -- sur front + ValueCounter <= ValueCounter + 1; + d_btn <= i_btn; + end if; +end process; + + +process (ValueCounter) +begin + if mode_simul = '1' then + d_bit_count <= ValueCounter(2); -- pour temps simulation: court delai + else + -- d_bit_count <= ValueCounter(21); -- pour temps reel: long delai (trop) + d_bit_count <= ValueCounter(16); -- pour temps reel: + end if; +end process; + + +inst_strb_bit : strb_gen + Port map ( + CLK => CLK, + i_don => d_bit_count, + o_stb => d_strobe_bit + ); + +debnc0_process : process (CLK) + begin + if (rising_edge(CLK)) then + q0_btn <= d_btn; + end if; + end process; + +debnc1_process : process (CLK, d_strobe_bit ) + begin + if ( rising_edge(CLK) and d_strobe_bit = '1') then + q1_btn <= q0_btn; + end if; + end process; + +debnc2_process : process (CLK) + begin + if (rising_edge(CLK)) then + q2_btn <= q1_btn; + end if; + end process; + +o_btn_db <= q1_btn; +o_strobe_btn <= not q1_btn AND q2_btn; -- transition descendante +--o_strobe_btn <= q1_btn AND not q2_btn; -- transition montante + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/ctrl_i2c_V4_codec_ssm2603.vhd b/pb_logique_seq.srcs/sources_1/imports/new/ctrl_i2c_V4_codec_ssm2603.vhd new file mode 100644 index 0000000..690f0ac --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/ctrl_i2c_V4_codec_ssm2603.vhd @@ -0,0 +1,472 @@ +--------------------------------------------------------------------------------------------- +-- ctrl_i2c_V4_ssm2603.vhd +--------------------------------------------------------------------------------------------- +-- controle codec SSM2603 par I2C +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 1.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : 20 novembre 2018 +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +-------------------------------- +-- Description +-------------------------------- +-- Contôle du codec SSM2603 sur une carte Zybo +-- +-- +-- Note; pour le SSM2603, le bus I2C est controlé de manière telle que +-- ref page 8 fiche ssm2603.pdf +-- +-- documents en reference +-- reference manual Zybo +-- https://reference.digilentinc.com/reference/programmable-logic/zybo-z7/reference-manual +-- schematic (public) +-- https://reference.digilentinc.com/_media/reference/programmable-logic/zybo-z7/zybo_z7_sch-public.pdf +-- ref Analog Devices SSM2603 Audio Codec +-- https://www.analog.com/media/en/technical-documentation/data-sheets/ssm2603.pdf +-- THE I 2C-BUS SPECIFICATIOn, VERSION 2.1 JANUARY 2000 Philips Semiconductors +-- +--- revisions +-- V3: synchronisation, V4 documentation, reset delai +-------------------------------- +-- À FAIRE: +-- +-------------------------------- + +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.std_logic_arith.all; -- requis pour les constantes etc. +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +Library UNISIM; +use UNISIM.vcomponents.all; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- ajoute par utilisateur... + + +entity ctrl_i2c_V4_ssm2603 is +-- horloge supposee 50 Mhz +generic ( c_clk_freq_Hz: integer := 50_000_000; c_bus_i2c_bps: integer := 100_000); + + Port ( + clk_master : in STD_LOGIC; -- horloge maitre pour le controleur (typique 50 MHz) + i_reset : in STD_LOGIC; + i_stb_read : in STD_LOGIC; -- demarre un cycle de lecture + i_stb_write : in STD_LOGIC; -- demarre un cycle d ecriture + i_adr_reg : in std_logic_vector(6 downto 0); -- adresse registres de configuration + i_dat_wreg : in std_logic_vector(8 downto 0); -- 9 bits -- data registre a transmettre + o_dat_rreg : out std_logic_vector(8 downto 0); -- 9 bits -- data registre recue + io_sda : inout std_logic ; -- pour developpement + io_scl : inout std_logic ; -- pour developpement + o_read_req : out std_logic ; -- pour tests + o_write_req : out std_logic ; -- pour tests + o_busy : out std_logic; -- pour tests; + o_ack_error : out STD_LOGIC; -- -- pour tests; + o_ena : out STD_LOGIC; -- -- pour tests; + o_rw : out STD_LOGIC -- -- pour tests; + ); + +end ctrl_i2c_V4_ssm2603; + +architecture Behavioral of ctrl_i2c_V4_ssm2603 is + +constant c_master_clk_freq_Hz : integer := c_clk_freq_Hz; + +type fsm_codec_ctrl_type is ( + -- read / write sequence SSM2603 *** a developper + sta_idle, -- + sta_write_seq_0, -- + sta_write_seq_1, -- + sta_write_seq_fin, -- + -- + sta_read_seq_0, -- + sta_read_seq_1, -- + sta_read_seq_2, -- + sta_read_seq_3, -- + sta_read_seq_4, -- + sta_read_seq_fin -- + ); + + +constant c_I2C_codec_Addr : std_logic_vector( 6 downto 0) := "0011010"; -- x"1A" + +-- machine etats pour controle i2c_master +signal fsm_i2c_etat_courant, fsm_i2c_etat_prochain : fsm_codec_ctrl_type := sta_idle; + +signal d_read_req : std_logic; +signal d_write_req : std_logic; +signal d_reset_req_read_write : std_logic; + + +-- signaux pour i2c_master, +signal d_reset_n : std_logic; +signal d_ena : std_logic; +signal d_codec_adr : std_logic_vector( 6 downto 0) := c_I2C_codec_Addr; +signal d_rw : std_logic; +signal d_data_wr : std_logic_vector(7 downto 0); +signal d_data_rd : std_logic_vector(7 downto 0); +signal en_d_data1_rd, en_d_data2_rd : std_logic; + +signal d_dat_readreg : std_logic_vector(8 downto 0); -- 9 bits +signal d_busy, q_busy_prec, q_busy : std_logic; + +signal d_delai : std_logic_vector(7 downto 0); -- delai en nombre de mclk pour changement etats +constant c_delai_max : std_logic_vector(7 downto 0) := "00101000"; -- +signal d_delai_synch : std_logic; + +signal d_ack_error : std_logic; + + + +component i2c_master +GENERIC( + input_clk : INTEGER := 50_000_000; --input clock speed from user logic in Hz + bus_clk : INTEGER := 400_000); --speed the i2c bus (scl) will run at in Hz + PORT( + clk : IN STD_LOGIC; --system clock + reset_n : IN STD_LOGIC; --active low reset + ena : IN STD_LOGIC; --latch in command + addr : IN STD_LOGIC_VECTOR(6 DOWNTO 0); --address of target slave + rw : IN STD_LOGIC; --'0' is write, '1' is read + data_wr : IN STD_LOGIC_VECTOR(7 DOWNTO 0); --data to write to slave + busy : OUT STD_LOGIC; --indicates transaction in progress + data_rd : OUT STD_LOGIC_VECTOR(7 DOWNTO 0); --data read from slave + ack_error : BUFFER STD_LOGIC; --flag if improper acknowledge from slave + sda : INOUT STD_LOGIC; --serial data output of i2c bus + scl : INOUT STD_LOGIC); +end component; + +BEGIN + +inst_i2c_master: i2c_master + generic map ( input_clk => c_clk_freq_Hz, bus_clk => c_bus_i2c_bps ) + port map( + clk => clk_master, + reset_n => d_reset_n, + ena => d_ena, + addr => d_codec_adr, + rw => d_rw, + data_wr => d_data_wr, + busy => d_busy, + data_rd => d_data_rd, + ack_error => d_ack_error, + sda => io_sda, + scl => io_scl + ); + + + + + -- latch de la requete read ou write + process(clk_master, d_reset_req_read_write, i_reset) + begin + if (d_reset_req_read_write = '1') or (i_reset = '1') then + d_read_req <= '0'; -- test + d_write_req <= '0'; -- test + else + if (clk_master'event and clk_master = '1' and (i_stb_read = '1') ) then + d_read_req <= '1'; -- test + end if; + if (clk_master'event and clk_master = '1' and (i_stb_write= '1') ) then + d_write_req <= '1'; -- test + end if; + end if; + end process; + + -- synchro du signal d_busy au front d'horloge + process(clk_master) + begin + if (clk_master'event and clk_master = '1' ) then + q_busy <= d_busy; + end if; + end process; + + + -- + -- Generation d'un signal d_delai_synch pour assurer duree minimale entre transition... + -- NON nécessaire ... utile pour avoir le temps de voir + -- des transitions rapides sur l'analyseur logique en periode de mise au point.. + -- + compteur_delai : process (clk_master, i_reset) + begin + if ( i_reset = '1') then + d_delai <= (others =>'0'); + d_delai_synch <= '0'; + else + if (rising_edge(clk_master)) then + d_delai <= d_delai + 1; + if (d_delai = c_delai_max) then + d_delai_synch <= '1'; + d_delai <= (others =>'0'); + else + d_delai_synch <= '0'; + end if; + end if; + end if; + end process; + + +-- Assignation du prochain état au front d'horloge +process(clk_master, i_reset) +begin + if (i_reset= '1') then + fsm_i2c_etat_courant <= sta_idle; + else + if (clk_master'event and clk_master = '1' and d_delai_synch = '1' ) then + --if (clk_master'event and clk_master = '1' ) then + fsm_i2c_etat_courant <= fsm_i2c_etat_prochain; + q_busy_prec <= q_busy; + end if; + end if; +end process; + + +-- Calcul des transitions du prochain état +-- nextstate: process(fsm_i2c_etat_courant, d_read_req, d_write_req, q_busy_prec, d_busy) +nextstate: process(fsm_i2c_etat_courant, d_read_req, d_write_req, q_busy_prec, q_busy) +begin + case fsm_i2c_etat_courant is + when sta_idle => + if (d_read_req = '1') and (q_busy = '0') then + fsm_i2c_etat_prochain <= sta_read_seq_0; -- demarrage d'une transaction de lecture + -- d_ack_debug <= not d_ack_debug; -- debug temporaire... + else + if (d_write_req = '1') and (q_busy = '0') then + fsm_i2c_etat_prochain <= sta_write_seq_0; -- demarrage d'une transaction d'écriture + -- d_ack_debug <= not d_ack_debug; -- debug temporaire... + else + fsm_i2c_etat_prochain <= sta_idle; + end if; + end if; + -- + -- Sequence lecture + when sta_read_seq_0 => + if (q_busy_prec = '0') and (q_busy = '1') then + fsm_i2c_etat_prochain <= sta_read_seq_1; + -- d_ack_debug <= not d_ack_debug; -- debug temporaire... + else + fsm_i2c_etat_prochain <= sta_read_seq_0; + end if; + when sta_read_seq_1 => + if (q_busy_prec = '0') and (q_busy = '1')then + fsm_i2c_etat_prochain <= sta_read_seq_2; + -- d_ack_debug <= not d_ack_debug; -- debug temporaire... + else + fsm_i2c_etat_prochain <= sta_read_seq_1; + end if; + when sta_read_seq_2 => + if (q_busy = '0') then + fsm_i2c_etat_prochain <= sta_read_seq_fin; + -- d_ack_debug <= not d_ack_debug; -- debug temporaire... + else + fsm_i2c_etat_prochain <= sta_read_seq_2; + end if; + when sta_read_seq_fin => + fsm_i2c_etat_prochain <= sta_idle; + -- d_ack_debug <= not d_ack_debug; -- debug temporaire... + -- + -- Sequence ecriture + when sta_write_seq_0 => + if (q_busy_prec = '0') and (q_busy = '1') then + fsm_i2c_etat_prochain <= sta_write_seq_1; + -- d_ack_debug <= not d_ack_debug; -- debug temporaire... + else + fsm_i2c_etat_prochain <= sta_write_seq_0; + end if; + when sta_write_seq_1 => + if (q_busy_prec = '0') and (q_busy = '1') then + fsm_i2c_etat_prochain <= sta_write_seq_fin; + --d_ack_debug <= not d_ack_debug; -- debug temporaire... + else + fsm_i2c_etat_prochain <= sta_write_seq_1; + end if; + + when sta_write_seq_fin => + fsm_i2c_etat_prochain <= sta_idle; + --d_ack_debug <= not d_ack_debug; -- debug temporaire... + + when others => + fsm_i2c_etat_prochain <= sta_idle; + end case; +end process; + +-- calcul des sorties de la MEF de controle +sorties: process(fsm_i2c_etat_courant, i_adr_reg, i_dat_wreg, d_data_rd) +-- Calcul des sorties +begin +-- +-- documentation **************************************************** +-- Sequence non déterminée +-- sta idle +-- sorties: +-- q_busy est 0 +-- pas d'opération +-- transitions +-- strobe i_stb_read détecté, prochain etat est sta_read_seq_0 sans autre condition +-- strobe i_stb_write détecté, prochain etat est sta_write_seq_0 sans autre condition +-- d_rw <= '1' ; -- commande prochaine requise est lecture (premiere partie contenu registre) +-- transitions prochaine +-- q_busy passe de 0 a 1 : la commande a ete saisie par codec, prochain etat sta_read_seq2 +-- sta_read_seq2 +-- d_rw <= '1' ; -- commande requise est lecture (seconde partie contenu registre) +-- transitions prochaine +-- quand q_busy = '0' la lecture premiere partie est disponible +-- q_busy passe de 0 a 1 : la commande a ete saisie par codec, prochain etat sta_read_seq_fin +--- +-- sta_read_seq_fin +-- le resultat de lecture est disponible (seconde partie contenu registre) +-- transitions +-- prochain etat sta_idle sans condition +-- +-- Sequence ecriture +-- sta_read_seq_fin +-- d_ena <= '0'; -- pas de prochaine commande +-- le resultat de lecture est disponible (seconde partie contenu registre) +-- transitions +-- prochain etat sta_idle sans condition +-- +-- Sequence ecriture +-- sta_write_seq0 +-- d_ena <= '1'; -- initialiser transaction (inferred latch) +-- d_rw <= '0' ; -- commande requise est ecriture +-- donnée a écrire sur d_data_wr (numero registre codec) + 1 bit du contenu du registre +-- adresse I2C déja en place sur addr +-- transitions +-- q_busy passe de 0 a 1 : la commande est saisie par codec, prochain etat sta_write_seq0 +-- sta_write_se1 +-- d_rw <= '0' ; -- commande requise est ecriture (seconde partie contenu registre 8 bits ) +-- -- donnée a écrire sur d_data_wr (seconde partie contenu registre 8 bits ) +-- transitions +-- q_busy passe de 0 a 1 : la commande a ete saisie par codec, prochain etat sta_write_seq_fin +-- sta_write_seq_fin +-- le resultat de lecture est disponible (seconde partie contenu registre) +-- transitions +-- prochain etat sta_idle sans condition +-- + + case fsm_i2c_etat_courant is + when sta_idle => + d_ena <= '0'; + -- + d_reset_req_read_write <='0'; + d_rw <= '1'; -- par defaut + d_data_wr(7 downto 0 ) <= (others => '0'); + en_d_data1_rd <= '0'; + en_d_data2_rd <= '0'; + -- Sequence lecture + when sta_read_seq_0 => -- on arrive ici avec q_busy = '0' + -- l'adresse I2C est deja fixee tours la meme dans ce contexte d_codec_adr + d_ena <= '1'; + d_rw <= '0'; -- commande ecriture (pour adresse registre codec) + d_data_wr(7 downto 0 ) <= i_adr_reg (6 downto 0) & '0'; -- data tx : adresse registre codec & '0' + d_reset_req_read_write <='0'; + -- + d_reset_req_read_write <='0'; + en_d_data1_rd <= '0'; + en_d_data2_rd <= '0'; + + when sta_read_seq_1 => -- le codec a repondu en levant q_busy = '1' + d_ena <= '1'; + d_rw <= '1'; -- (pour lire premiere partie contenu registre) + d_reset_req_read_write <='1'; + -- + d_data_wr(7 downto 0 ) <= (others => '0'); + en_d_data1_rd <= '0'; + en_d_data2_rd <= '0'; + + when sta_read_seq_2 => -- enregiste les 8 bits lu et enchaine une nouvelle commande immediatement lire 1 bits (parmi 8) + -- q_busy passse a zero -> transition vers le suivant + d_ena <= '1'; + d_rw <= '1'; -- (pour lire seconde partie contenu registre) + en_d_data1_rd <= '1'; -- + d_reset_req_read_write <='0'; + -- + d_data_wr(7 downto 0 ) <= (others => '0'); + en_d_data2_rd <= '0'; + + when sta_read_seq_fin => + d_ena <= '0'; + en_d_data2_rd <= '1'; -- + d_reset_req_read_write <='0'; + d_rw <= '1'; + d_data_wr(7 downto 0 ) <= (others => '0'); + en_d_data1_rd <= '0'; + -- + -- + -- + -- + when sta_write_seq_0 => + -- l'adresse I2C est deja fixee tours la meme dans ce contexte d_codec_adr + d_ena <= '1'; -- + d_rw <= '0'; -- + d_data_wr(7 downto 0 ) <= i_adr_reg (6 downto 0) & i_dat_wreg(8); -- data tx : adresse registre codec & 1 bit data + -- + d_reset_req_read_write <='0'; + en_d_data1_rd <= '0'; + en_d_data2_rd <= '0'; + -- + when sta_write_seq_1 => + d_ena <= '1'; + d_rw <= '0'; + d_data_wr(7 downto 0 ) <= i_dat_wreg (7 downto 0); -- data tx : 8 bits data + d_reset_req_read_write <='1'; + -- + en_d_data1_rd <= '0'; + en_d_data2_rd <= '0'; + -- + when sta_write_seq_fin => + d_ena <= '0'; + d_reset_req_read_write <='0'; + -- + d_rw <= '1'; + d_data_wr(7 downto 0 ) <= (others => '0'); + en_d_data1_rd <= '0'; + en_d_data2_rd <= '0'; + --when others => NULL; + when others => + d_ena <= '0'; + d_reset_req_read_write <='0'; + d_rw <= '1'; + d_data_wr(7 downto 0 ) <= (others => '0'); + en_d_data1_rd <= '0'; + en_d_data2_rd <= '0'; + end case; + + end process; + + +inst_dat_read: process(clk_master, i_reset) + begin + if (i_reset= '1') then + d_dat_readreg(8 downto 0) <= (others => '0'); + else + if (clk_master'event and clk_master = '1') then + if (en_d_data1_rd = '1') then + d_dat_readreg(7 downto 0) <= d_data_rd ; + else if (en_d_data2_rd = '1') then + d_dat_readreg(8) <= d_data_rd(0); + end if; + end if; + end if; + end if; + end process; + + + -- + d_reset_n <= not i_reset; + o_busy <= q_busy; + o_ack_error <= d_ack_error; + o_ena <= d_ena; + o_rw <= d_rw; + + o_read_req <= d_read_req; + o_write_req <= d_write_req; + o_dat_rreg <= d_dat_readreg; + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/gen_clk_codec.vhd b/pb_logique_seq.srcs/sources_1/imports/new/gen_clk_codec.vhd new file mode 100644 index 0000000..09ca6e9 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/gen_clk_codec.vhd @@ -0,0 +1,123 @@ +--------------------------------------------------------------------------------------------- +-- gen_clk_codec.vhd +--------------------------------------------------------------------------------------------- +-- Generation d'horloge et de signaux de synchronisation +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 1.0 +-- Nomenclature : ref GRAMS +-- Date : 30 octobre 2018, ..., 24 janvier 2019, 25 janvier +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +-------------------------------- +-- Description +-------------------------------- +-- Génération de signaux de synchronisation, incluant des "strobes" +-- (utilise un PLL) +-- Ref: +-- 7 Series Libraries Guide www.xilinx.com 418 UG953 (v2016.3) October 5, 2016 +-- (pages 425 PLLE2_BASE) +-- +-- revisions +-- mise a jour D Dalle 24 janvier 2019 commentaires +-- mise a jour D Dalle 18 janvier 2019 synchronisation o_reclrc +-- mise a jour D Dalle 9 janvier 2019 bufg sur o_bclk +-- Développement D Dalle 30 octobre 2018, 7 novembre 2018, 4 janvier 2019 +--------------------------------------------------------------------------------------------- +-- À FAIRE: +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs +library UNISIM; +use UNISIM.VComponents.all; + +entity gen_clk_codec is +port ( + i_rst : in STD_LOGIC; -- entree reset + m_clk : in STD_LOGIC; -- Entrée horloge maitre codec 12.389 MHz + o_bclk : out STD_LOGIC; -- horloge bit clk: freq m_clk MHz / 4 soit 3,097 MHz + o_reclrc : out STD_LOGIC -- horloge record, play back, sampling rate clock, left right channel 48,021 KHz + ); +end gen_clk_codec; + +architecture Behavioral of gen_clk_codec is + + signal d_bclk : std_logic := '0'; -- horloge I2S digital audio (50 MHz pour cet exemple) + signal d_reclrc : std_logic := '0'; -- I²S (Record Channel Clock) + signal q_reclrc : std_logic; -- I²S (Record Channel Clock) synchronisation + signal d_cpt_reclrc : std_logic_vector (7 downto 0) := "00000000"; + signal d_cpt_bclk : std_logic_vector (1 downto 0) := "00"; + + + begin + +-- generateur horloge echantillonnage (ADC sampling Rate) et transfert binaire +------------------------------------------------------------------------ +-- ref SSM2603 data sheet page 25 (defaut pour MCLK = 12.288 MHz) +-- RECLRC : MCLK / 256 BCLK : RECLRC / 4 + +reclrc_proc: process(m_clk) + begin + if rising_edge(m_clk) then + if i_rst = '1' then + d_reclrc <= '0'; + d_cpt_reclrc <= "00000000"; + else + if d_cpt_reclrc = 128 then -- 256/2 + d_cpt_reclrc <= "00000000"; + d_reclrc <= not d_reclrc; + else + d_cpt_reclrc <= d_cpt_reclrc + 1; + end if; + end if; + end if; + end process reclrc_proc; + +bclk_proc: process(m_clk) + begin + if rising_edge(m_clk) then + if i_rst = '1' then + d_bclk <= '0'; + d_cpt_bclk <= "00"; + else + if d_cpt_bclk = 01 then + d_cpt_bclk <= "00"; + d_bclk <= not d_bclk; + else + d_cpt_bclk <= d_cpt_bclk + 1; + end if; + end if; + end if; + end process bclk_proc; + +-- lrc_proc: process(m_clk) +-- begin +-- if falling_edge(m_clk) then +-- q_reclrc <= d_reclrc; +-- end if; +-- end process lrc_proc; + + -- forme 25 janvier + lrc_proc: process(d_bclk) + begin + if falling_edge(d_bclk) then + q_reclrc <= d_reclrc; + end if; + end process lrc_proc; + + + o_reclrc <= q_reclrc; + + -- o_bclk <= d_bclk; + ClockBufer1: bufg -- revision 9 janvier 2018 + port map( + I => d_bclk, + O => o_bclk + ); + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/i2c_master.vhd b/pb_logique_seq.srcs/sources_1/imports/new/i2c_master.vhd new file mode 100644 index 0000000..a4fe165 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/i2c_master.vhd @@ -0,0 +1,247 @@ +--------------------------------------------------------------------------------
+--
+-- FileName: i2c_master.vhd
+-- Dependencies: none
+-- Design Software: Quartus II 64-bit Version 13.1 Build 162 SJ Full Version
+--
+-- HDL CODE IS PROVIDED "AS IS." DIGI-KEY EXPRESSLY DISCLAIMS ANY
+-- WARRANTY OF ANY KIND, WHETHER EXPRESS OR IMPLIED, INCLUDING BUT NOT
+-- LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
+-- PARTICULAR PURPOSE, OR NON-INFRINGEMENT. IN NO EVENT SHALL DIGI-KEY
+-- BE LIABLE FOR ANY INCIDENTAL, SPECIAL, INDIRECT OR CONSEQUENTIAL
+-- DAMAGES, LOST PROFITS OR LOST DATA, HARM TO YOUR EQUIPMENT, COST OF
+-- PROCUREMENT OF SUBSTITUTE GOODS, TECHNOLOGY OR SERVICES, ANY CLAIMS
+-- BY THIRD PARTIES (INCLUDING BUT NOT LIMITED TO ANY DEFENSE THEREOF),
+-- ANY CLAIMS FOR INDEMNITY OR CONTRIBUTION, OR OTHER SIMILAR COSTS.
+--
+-- Version History
+-- Version 1.0 11/01/2012 Scott Larson
+-- Initial Public Release
+-- Version 2.0 06/20/2014 Scott Larson
+-- Added ability to interface with different slaves in the same transaction
+-- Corrected ack_error bug where ack_error went 'Z' instead of '1' on error
+-- Corrected timing of when ack_error signal clears
+-- Version 2.1 10/21/2014 Scott Larson
+-- Replaced gated clock with clock enable
+-- Adjusted timing of SCL during start and stop conditions
+-- Version 2.2 02/05/2015 Scott Larson
+-- Corrected small SDA glitch introduced in version 2.1
+--
+--------------------------------------------------------------------------------
+
+LIBRARY ieee;
+USE ieee.std_logic_1164.all;
+USE ieee.std_logic_unsigned.all;
+
+ENTITY i2c_master IS
+ GENERIC(
+ input_clk : INTEGER := 50_000_000; --input clock speed from user logic in Hz
+ bus_clk : INTEGER := 400_000); --speed the i2c bus (scl) will run at in Hz
+ PORT(
+ clk : IN STD_LOGIC; --system clock
+ reset_n : IN STD_LOGIC; --active low reset
+ ena : IN STD_LOGIC; --latch in command
+ addr : IN STD_LOGIC_VECTOR(6 DOWNTO 0); --address of target slave
+ rw : IN STD_LOGIC; --'0' is write, '1' is read
+ data_wr : IN STD_LOGIC_VECTOR(7 DOWNTO 0); --data to write to slave
+ busy : OUT STD_LOGIC; --indicates transaction in progress
+ data_rd : OUT STD_LOGIC_VECTOR(7 DOWNTO 0); --data read from slave
+ ack_error : BUFFER STD_LOGIC; --flag if improper acknowledge from slave
+ sda : INOUT STD_LOGIC; --serial data output of i2c bus
+ scl : INOUT STD_LOGIC); --serial clock output of i2c bus
+END i2c_master;
+
+ARCHITECTURE logic OF i2c_master IS
+ CONSTANT divider : INTEGER := (input_clk/bus_clk)/4; --number of clocks in 1/4 cycle of scl
+ TYPE machine IS(ready, start, command, slv_ack1, wr, rd, slv_ack2, mstr_ack, stop); --needed states
+ SIGNAL state : machine; --state machine
+ SIGNAL data_clk : STD_LOGIC; --data clock for sda
+ SIGNAL data_clk_prev : STD_LOGIC; --data clock during previous system clock
+ SIGNAL scl_clk : STD_LOGIC; --constantly running internal scl
+ SIGNAL scl_ena : STD_LOGIC := '0'; --enables internal scl to output
+ SIGNAL sda_int : STD_LOGIC := '1'; --internal sda
+ SIGNAL sda_ena_n : STD_LOGIC; --enables internal sda to output
+ SIGNAL addr_rw : STD_LOGIC_VECTOR(7 DOWNTO 0); --latched in address and read/write
+ SIGNAL data_tx : STD_LOGIC_VECTOR(7 DOWNTO 0); --latched in data to write to slave
+ SIGNAL data_rx : STD_LOGIC_VECTOR(7 DOWNTO 0); --data received from slave
+ SIGNAL bit_cnt : INTEGER RANGE 0 TO 7 := 7; --tracks bit number in transaction
+ SIGNAL stretch : STD_LOGIC := '0'; --identifies if slave is stretching scl
+BEGIN
+
+ --generate the timing for the bus clock (scl_clk) and the data clock (data_clk)
+ PROCESS(clk, reset_n)
+ VARIABLE count : INTEGER RANGE 0 TO divider*4; --timing for clock generation
+ BEGIN
+ IF(reset_n = '0') THEN --reset asserted
+ stretch <= '0';
+ count := 0;
+ ELSIF(clk'EVENT AND clk = '1') THEN
+ data_clk_prev <= data_clk; --store previous value of data clock
+ IF(count = divider*4-1) THEN --end of timing cycle
+ count := 0; --reset timer
+ ELSIF(stretch = '0') THEN --clock stretching from slave not detected
+ count := count + 1; --continue clock generation timing
+ END IF;
+ CASE count IS
+ WHEN 0 TO divider-1 => --first 1/4 cycle of clocking
+ scl_clk <= '0';
+ data_clk <= '0';
+ WHEN divider TO divider*2-1 => --second 1/4 cycle of clocking
+ scl_clk <= '0';
+ data_clk <= '1';
+ WHEN divider*2 TO divider*3-1 => --third 1/4 cycle of clocking
+ scl_clk <= '1'; --release scl
+ IF(scl = '0') THEN --detect if slave is stretching clock
+ stretch <= '1';
+ ELSE
+ stretch <= '0';
+ END IF;
+ data_clk <= '1';
+ WHEN OTHERS => --last 1/4 cycle of clocking
+ scl_clk <= '1';
+ data_clk <= '0';
+ END CASE;
+ END IF;
+ END PROCESS;
+
+ --state machine and writing to sda during scl low (data_clk rising edge)
+ PROCESS(clk, reset_n)
+ BEGIN
+ IF(reset_n = '0') THEN --reset asserted
+ state <= ready; --return to initial state
+ busy <= '1'; --indicate not available
+ scl_ena <= '0'; --sets scl high impedance
+ sda_int <= '1'; --sets sda high impedance
+ ack_error <= '0'; --clear acknowledge error flag
+ bit_cnt <= 7; --restarts data bit counter
+ data_rd <= "00000000"; --clear data read port
+ ELSIF(clk'EVENT AND clk = '1') THEN
+ IF(data_clk = '1' AND data_clk_prev = '0') THEN --data clock rising edge
+ CASE state IS
+ WHEN ready => --idle state
+ IF(ena = '1') THEN --transaction requested
+ busy <= '1'; --flag busy
+ addr_rw <= addr & rw; --collect requested slave address and command
+ data_tx <= data_wr; --collect requested data to write
+ state <= start; --go to start bit
+ ELSE --remain idle
+ busy <= '0'; --unflag busy
+ state <= ready; --remain idle
+ END IF;
+ WHEN start => --start bit of transaction
+ busy <= '1'; --resume busy if continuous mode
+ sda_int <= addr_rw(bit_cnt); --set first address bit to bus
+ state <= command; --go to command
+ WHEN command => --address and command byte of transaction
+ IF(bit_cnt = 0) THEN --command transmit finished
+ sda_int <= '1'; --release sda for slave acknowledge
+ bit_cnt <= 7; --reset bit counter for "byte" states
+ state <= slv_ack1; --go to slave acknowledge (command)
+ ELSE --next clock cycle of command state
+ bit_cnt <= bit_cnt - 1; --keep track of transaction bits
+ sda_int <= addr_rw(bit_cnt-1); --write address/command bit to bus
+ state <= command; --continue with command
+ END IF;
+ WHEN slv_ack1 => --slave acknowledge bit (command)
+ IF(addr_rw(0) = '0') THEN --write command
+ sda_int <= data_tx(bit_cnt); --write first bit of data
+ state <= wr; --go to write byte
+ ELSE --read command
+ sda_int <= '1'; --release sda from incoming data
+ state <= rd; --go to read byte
+ END IF;
+ WHEN wr => --write byte of transaction
+ busy <= '1'; --resume busy if continuous mode
+ IF(bit_cnt = 0) THEN --write byte transmit finished
+ sda_int <= '1'; --release sda for slave acknowledge
+ bit_cnt <= 7; --reset bit counter for "byte" states
+ state <= slv_ack2; --go to slave acknowledge (write)
+ ELSE --next clock cycle of write state
+ bit_cnt <= bit_cnt - 1; --keep track of transaction bits
+ sda_int <= data_tx(bit_cnt-1); --write next bit to bus
+ state <= wr; --continue writing
+ END IF;
+ WHEN rd => --read byte of transaction
+ busy <= '1'; --resume busy if continuous mode
+ IF(bit_cnt = 0) THEN --read byte receive finished
+ IF(ena = '1' AND addr_rw = addr & rw) THEN --continuing with another read at same address
+ sda_int <= '0'; --acknowledge the byte has been received
+ ELSE --stopping or continuing with a write
+ sda_int <= '1'; --send a no-acknowledge (before stop or repeated start)
+ END IF;
+ bit_cnt <= 7; --reset bit counter for "byte" states
+ data_rd <= data_rx; --output received data
+ state <= mstr_ack; --go to master acknowledge
+ ELSE --next clock cycle of read state
+ bit_cnt <= bit_cnt - 1; --keep track of transaction bits
+ state <= rd; --continue reading
+ END IF;
+ WHEN slv_ack2 => --slave acknowledge bit (write)
+ IF(ena = '1') THEN --continue transaction
+ busy <= '0'; --continue is accepted
+ addr_rw <= addr & rw; --collect requested slave address and command
+ data_tx <= data_wr; --collect requested data to write
+ IF(addr_rw = addr & rw) THEN --continue transaction with another write
+ sda_int <= data_wr(bit_cnt); --write first bit of data
+ state <= wr; --go to write byte
+ ELSE --continue transaction with a read or new slave
+ state <= start; --go to repeated start
+ END IF;
+ ELSE --complete transaction
+ state <= stop; --go to stop bit
+ END IF;
+ WHEN mstr_ack => --master acknowledge bit after a read
+ IF(ena = '1') THEN --continue transaction
+ busy <= '0'; --continue is accepted and data received is available on bus
+ addr_rw <= addr & rw; --collect requested slave address and command
+ data_tx <= data_wr; --collect requested data to write
+ IF(addr_rw = addr & rw) THEN --continue transaction with another read
+ sda_int <= '1'; --release sda from incoming data
+ state <= rd; --go to read byte
+ ELSE --continue transaction with a write or new slave
+ state <= start; --repeated start
+ END IF;
+ ELSE --complete transaction
+ state <= stop; --go to stop bit
+ END IF;
+ WHEN stop => --stop bit of transaction
+ busy <= '0'; --unflag busy
+ state <= ready; --go to idle state
+ END CASE;
+ ELSIF(data_clk = '0' AND data_clk_prev = '1') THEN --data clock falling edge
+ CASE state IS
+ WHEN start =>
+ IF(scl_ena = '0') THEN --starting new transaction
+ scl_ena <= '1'; --enable scl output
+ ack_error <= '0'; --reset acknowledge error output
+ END IF;
+ WHEN slv_ack1 => --receiving slave acknowledge (command)
+ IF(sda /= '0' OR ack_error = '1') THEN --no-acknowledge or previous no-acknowledge
+ ack_error <= '1'; --set error output if no-acknowledge
+ END IF;
+ WHEN rd => --receiving slave data
+ data_rx(bit_cnt) <= sda; --receive current slave data bit
+ WHEN slv_ack2 => --receiving slave acknowledge (write)
+ IF(sda /= '0' OR ack_error = '1') THEN --no-acknowledge or previous no-acknowledge
+ ack_error <= '1'; --set error output if no-acknowledge
+ END IF;
+ WHEN stop =>
+ scl_ena <= '0'; --disable scl
+ WHEN OTHERS =>
+ NULL;
+ END CASE;
+ END IF;
+ END IF;
+ END PROCESS;
+
+ --set sda output
+ WITH state SELECT
+ sda_ena_n <= data_clk_prev WHEN start, --generate start condition
+ NOT data_clk_prev WHEN stop, --generate stop condition
+ sda_int WHEN OTHERS; --set to internal sda signal
+
+ --set scl and sda outputs
+ scl <= '0' WHEN (scl_ena = '1' AND scl_clk = '0') ELSE 'Z';
+ sda <= '0' WHEN sda_ena_n = '0' ELSE 'Z';
+
+END logic;
diff --git a/pb_logique_seq.srcs/sources_1/imports/new/init_codec_v2.vhd b/pb_logique_seq.srcs/sources_1/imports/new/init_codec_v2.vhd new file mode 100644 index 0000000..a17a0cc --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/init_codec_v2.vhd @@ -0,0 +1,336 @@ + +--------------------------------------------------------------------------------------------- +-- init_codec_v2.vhd +--------------------------------------------------------------------------------------------- +-- configuration conversion A/N par codec SSM2603 sur la carte ZYBO +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 5.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : 13 janvier 2018, révision 21 janvier 2019, 1 février 2019, 20 février (delai ajusté) +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +--------------------------------------------------------------------------------------------- +-- Description (sur une carte Zybo) +-- initialisation du Codec SSM2603 de la carte Zybo-z7-10 (ou 20) +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- +-- +-- ref manual Zybo +-- https://reference.digilentinc.com/reference/programmable-logic/zybo-z7/reference-manual +-- ref schematic (public) +-- https://reference.digilentinc.com/_media/reference/programmable-logic/zybo-z7/zybo_z7_sch-public.pdf +-- ref Analog Devices SSM2603 Audio Codec +-- https://www.analog.com/media/en/technical-documentation/data-sheets/ssm2603.pdf +-- +-------------------------------- +-- À FAIRE: +-- Espacement de 4 ms entre chaque trame I2C (pour respecter délai power-on et activation) ref. SSM2603.pdf +-- Restructurer pour définir un module d'initialisation du codec qui peut être sous-module +-- dans la hiérarchie et utilisé comme boite noire. +-- verifier R4 Analog audio path (LINE ou MIC) OK, mais a suivre 11 janvier 2019 +-- En particlier, pour la suite, donner une option de configuration MIC ou LINE (actuellement choix fixe) +-------------------------------- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs +USE ieee.numeric_std.ALL; +--use IEEE.std_logic_arith.all; -- requis pour les constantes etc. +--use IEEE.std_logic_arith.all; -- requi pour les constantes telles que cdviv6 etc. + +-- Uncomment the following library declaration if instantiating +-- any Xilinx leaf cells in this code. +Library UNISIM; +use UNISIM.vcomponents.all; + +-- Uncomment the following library declaration if using +-- arithmetic functions with Signed or Unsigned values +--use IEEE.NUMERIC_STD.ALL; + +---------------------------------------------------------------------------------- +-- *****************************************************************************-- +---------------------------------------------------------------------------------- +entity init_codec_v2 is +--generic ( mode_simulation: std_logic := '0'); -- developpement futur si requis + Port ( + -- mode de controle necessaire ??? + i_reset : in std_logic; + o_cfg_done : out STD_LOGIC; + o_cfg_busy : out STD_LOGIC; + o_ena : out STD_LOGIC; -- pour tests + -- + -- Signaux I2C + i_lrc : in STD_LOGIC; -- I²S (Record Channel Clock) + io_scl : inout STD_LOGIC; -- horloge I2C SPI + io_sda : inout STD_LOGIC; -- I2C 2-Wire Control Interface Data Input/Output. + -- + i_strobe_1000Hz : in std_logic; -- pour synchro de configuration + clk_p : in std_logic + ); +end init_codec_v2; + + +---------------------------------------------------------------------------------- + +architecture Behavioral of init_codec_v2 is + + constant nbreboutons: integer := 4; + constant freq_sys_Hz: integer := 125_000_000; -- Hz + +type register_cfg is array (0 to 31) of std_logic_vector (15 downto 0); + --configuration programmee du codec (dans un ordre determine ref audio.c ) +signal cfg_ssm2603 : register_cfg := ( +-- adresse reg contenu seq registre +-- 15 9 8 0 +"0001111" & "000000000", -- 0 R15 Software reset +"0000110" & "000110000", -- 1 R6 Power management + -- R6 D8=0; + -- R6 D7=0; pwroff : power up; + -- R6 D6=0; clkout power : power up; + -- R6 D5=1; crystal power : power down; + -- R6 D4=1; output power : power down; + -- R6 D3=0; DAC power : power up; + -- R6 D2=0; ADC power : power up; + -- R6 D1=0; MIC in power : power up; + -- R6 D0=0; LINE in power : power up; + +"0000000" & "000010111", -- 2 R0 Left-channel ADC input volume + -- R0: disable loading left to right; disable mute; 0 dB +"0000001" & "000010111", -- 3 R1 Right-channel ADC input volume + -- R1: disable loading right to left; disable mute; 0 dB + +"0000010" & "001111001", -- 4 R2 Left-channel DAC volume (defaut / datasheet) + -- R2 disable left ch head phone vol data to right; volume 0dB (defaut / datasheet) +"0000011" & "001111001", -- 5 R3 Right-channel DAC volume (defaut / datasheet) + -- R3 disable right ch head phone vol data to left; volume 0dB (defaut / datasheet) +--"0000010" & "001101001", -- 4 R2 Left-channel DAC volume (defaut / datasheet) +-- -- R2 disable left ch head phone vol data to right; volume -16 dB (conseillé avec écouteurs....) +--"0000011" & "001101001", -- 5 R3 Right-channel DAC volume (defaut / datasheet) +-- -- R3 disable right ch head phone vol data to left; volume -16 dB (conseillé avec écouteurs....) + +-- "0000100" & "000000100", -- 6 R4 Analog audio path -- audio.c INSEL = mic +"0000100" & "000010000", -- 6 R4 Analog audio path -- INSEL = LINE + -- R4 D8=0; : 0 (def) + -- R4 D7=0; | : 0 + -- R4 D6=0; | mic sidetone gain ctrl : 00 -6dB (def) + -- R4 D5=0; sidetone_en : 0 disable (def) + -- R4 D4=1; DACSEL (mix DAC output) : 1 select DAC + -- R4 D3=0; BypAss : 0 = Bypass disabled + -- R4 D2=0; INSEL : 0 = LINE input select to ADC (def) ***** 1: MIC + -- R4 D1=0; MUTEMIC : 0 (disabled) + -- R4 D0=0; MICBOOST : 0 = 0 dB (def); +"0000101" & "000000000", -- 7 R5 Digital audio path +"0000111" & "000000010", -- 8 R7 Digital audio I/F + -- ref data sheet page 25/31 + -- 24 bits I2S mode, sampling ADC 48 KHz DAC 48 KHz +"0001000" & "000000000", -- 9 R8 Sampling rate +"0001001" & "000000001", -- 10 R9 Active +"0000110" & "000100000", -- 11 R6 Power management + -- R6 D8=0; + -- R6 D7=0; pwroff : power up; + -- R6 D6=0; clkout power : power up; + -- R6 D5=1; crystal power : power down; + -- R6 D4=0; output power : power up; + -- R6 D3=0; DAC power : power up; + -- R6 D2=0; ADC power : power up; + -- R6 D1=0; MIC in power : power up; +others => +"1111111" & "000000000" -- code adresse de registre non reelle signifie extremite table atteinte +); + + + COMPONENT ctrl_i2c_v4_ssm2603 is + generic ( c_clk_freq_Hz: integer := 50_000_000; c_bus_i2c_bps: integer := 100_000); + Port ( + clk_master : in STD_LOGIC; -- horloge maitre pour le controleur (typique 50 MHz) + i_reset : in STD_LOGIC; + i_stb_read : in STD_LOGIC; -- demarre un cycle de lecture + i_stb_write : in STD_LOGIC; -- demarre un cycle d ecriture + i_adr_reg : in std_logic_vector(6 downto 0); -- adresse registres de configuration + i_dat_wreg : in std_logic_vector(8 downto 0); -- 9 bits -- data registre a transmettre + o_dat_rreg : out std_logic_vector(8 downto 0); -- 9 bits -- data registre recue + io_sda : inout std_logic ; + io_scl : inout std_logic ; + o_read_req : out std_logic ; -- pour tests + o_write_req : out std_logic ; -- pour tests + o_busy : out std_logic; -- pour tests + o_ack_error : out STD_LOGIC; -- pour tests; + o_ena : out STD_LOGIC; -- pour tests; + o_rw : out STD_LOGIC -- pour tests; + + ); + + end COMPONENT; + + component sel_btn_reg + port ( clk : in std_logic; + i_str_sel_reg : in std_logic; + i_reset_sel_reg : in std_logic; + o_sel_reg : out std_logic_vector (6 downto 0) + ); + end component; + +-- Signaux +---------------------------------------------------------------------------------- + + signal clk_12_288MHz : std_logic; + signal d_strobe_1000Hz : std_logic; + signal d_strobe_trame_I2C : std_logic; + + signal d_stb_read : std_logic; + signal d_stb_write : std_logic; + signal d_read_req : std_logic; -- pour test + signal d_write_req : std_logic; -- pour test + + signal d_dat_wreg : std_logic_vector(8 downto 0); + signal d_dat_rreg : std_logic_vector(8 downto 0); + signal d_sclk : std_logic; + signal d_busy : std_logic; + signal d_ack_error : std_logic; + signal d_ena : std_logic; + signal d_rw : std_logic; + + signal d_adr_reg : std_logic_vector(6 downto 0) ; -- adresse I2c du registre codec + signal d_sel_reg : std_logic_vector(6 downto 0) ; -- selection registre (directe) + signal d_sel_cfg_reg: std_logic_vector(6 downto 0) ; -- selection registre indirecte par cfg_ssm2603 + signal q_sel_cfg_reg: std_logic_vector(6 downto 0) ; -- selection registre indirecte par cfg_ssm2603 + + signal d_reset_sel_reg : std_logic; + signal d_cfg_done : std_logic; + signal d_cfg_busy : std_logic; + + signal d_delai_trame_I2C : unsigned(7 downto 0); -- delai en nombre de bclk pour configuration + constant c_delai_trame_I2C_max : unsigned(7 downto 0) := "00000110"; -- pour delai 7 ms entre trames I2C + signal d_delai_trame_I2C_atteint : std_logic; + +--------------------------------------------------------------------------------------------- +-- init_codec +--------------------------------------------------------------------------------------------- +begin + + inst_ctrl_i2c: ctrl_i2c_v4_ssm2603 + generic map (c_clk_freq_Hz => 50_000_000, c_bus_i2c_bps => 100_000 ) + PORT MAP( + clk_master => clk_p, + i_reset => i_reset, + i_stb_read => d_stb_read, + i_stb_write => d_stb_write, + i_adr_reg => d_adr_reg, + i_dat_wreg => d_dat_wreg, + o_dat_rreg => d_dat_rreg, + io_scl => io_scl , + io_sda => io_sda, + o_ack_error => d_ack_error, + o_ena => d_ena, -- pour tests + o_rw => d_rw, -- pour tests + o_read_req => d_read_req, -- pour tests + o_write_req => d_write_req, -- pour tests + o_busy => d_busy -- + ); + + -- + -- Generation d'un signal de delai entre trames I2C + -- version 1 + compteur_delai_cfg : process (clk_p, i_reset) + begin + if ( i_reset = '1') then + d_delai_trame_I2C <= (others =>'0'); + d_delai_trame_I2C_atteint <= '0'; + else + if (rising_edge(clk_p) and d_strobe_1000Hz ='1') then + d_delai_trame_I2C <= d_delai_trame_I2C + 1; + if (d_delai_trame_I2C = c_delai_trame_I2C_max) then + d_delai_trame_I2C_atteint <= '1'; + d_delai_trame_I2C <= (others =>'0'); + else + d_delai_trame_I2C_atteint <= '0'; + end if; + end if; + end if; + end process; + +-- -- +-- -- Generation d'un signal de delai entre trames I2C +-- -- +-- compteur_delai_cfg : process (clk_p, i_reset) +-- begin +-- if ( i_reset = '1') then +-- d_delai_trame_I2C <= (others =>'0'); +-- else +-- if (rising_edge(clk_p) and d_strobe_1000Hz ='1') then +-- d_delai_trame_I2C <= d_delai_trame_I2C + 1; +-- if (d_delai_trame_I2C = c_delai_trame_I2C_max) then +-- d_delai_trame_I2C <= (others =>'0'); +-- end if; +-- end if; +-- end if; +-- end process; + +-- test_delai_cfg : process (clk_p, i_reset) +-- begin +-- if ( i_reset = '1') then +-- d_delai_trame_I2C_atteint <= '0'; +-- else +-- if (rising_edge(clk_p) and d_strobe_1000Hz ='1') then +-- if (d_delai_trame_I2C = c_delai_trame_I2C_max) then +-- d_delai_trame_I2C_atteint <= '1'; +-- else +-- d_delai_trame_I2C_atteint <= '0'; +-- end if; +-- end if; +-- end if; +-- end process; + + + + + d_strobe_trame_I2C <= d_strobe_1000Hz and d_delai_trame_I2C_atteint; + + inst_idx_cfg_reg : process (clk_p, i_reset) + begin + if (i_reset = '1') then + d_sel_cfg_reg <= (others =>'0'); + q_sel_cfg_reg <= (others =>'0'); -- non requis + d_cfg_done <= '0'; + else + if rising_edge(clk_p) and (d_strobe_trame_I2C = '1') and (d_cfg_busy = '1')then + if (d_sel_cfg_reg = "0001011") then -- limite index = 11 + --if (d_sel_cfg_reg = "0000010") then -- limite index = 2 -- pour certains test simulation + d_cfg_done <= '1'; + end if; + q_sel_cfg_reg <= d_sel_cfg_reg; -- valeur courante + d_sel_cfg_reg <= d_sel_cfg_reg + 1; -- prochaine valeur; + end if; + end if; + end process; + +--inst_busy_cfg_reg +inst_busy_cfg_reg : process (clk_p, d_cfg_done ) + begin + if ( d_cfg_done = '1') then + d_cfg_busy <= '0'; + else + if rising_edge(clk_p) then + d_cfg_busy <= '1'; + end if; + end if; + end process; + + d_reset_sel_reg <= i_reset; + o_cfg_done <= d_cfg_done; + o_cfg_busy <= d_cfg_busy; + o_ena <= d_ena; + d_strobe_1000Hz <= i_strobe_1000Hz; + d_stb_read <= '0'; + d_stb_write <= d_cfg_busy and d_strobe_trame_I2C; + d_dat_wreg <= cfg_ssm2603( to_integer (unsigned( q_sel_cfg_reg(4 downto 0) ))) (8 downto 0); + d_adr_reg <= cfg_ssm2603( to_integer (unsigned( q_sel_cfg_reg(4 downto 0) ))) (15 downto 9); + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/mef_cod_i2s_vsb.vhd b/pb_logique_seq.srcs/sources_1/imports/new/mef_cod_i2s_vsb.vhd new file mode 100644 index 0000000..2357567 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/mef_cod_i2s_vsb.vhd @@ -0,0 +1,200 @@ +--------------------------------------------------------------------------------------------- +-- circuit mef_cod_i2s_vsb.vhd.vhd +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- Version : 1.0 +-- Nomenclature : 0.8 GRAMS +-- Date : 5 mai 2019 +-- Auteur(s) : Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- +-- Outils : vivado 2019.1 +--------------------------------------------------------------------------------------------- +-- Description: +-- Codeur I2S +-- +-- notes +-- frequences (peuvent varier un peu selon les contraintes de mise en oeuvre) +-- i_lrc ~ 48. KHz (~ 20.8 us) +-- d_ac_mclk, ~ 12.288 MHz (~ 80,715 ns) (non utilisee dans le codeur) +-- i_bclk ~ 3,10 MHz (~ 322,857 ns) freq mclk/4 +-- La durée d'une période reclrc est de 64,5 périodes de bclk ... +-- +-- Revision +-- Revision 14 mai 2019 (version ..._vsb) composants dans entités et fichiers distincts +--------------------------------------------------------------------------------------------- +-- À faire : +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +entity mef_cod_i2s_vsb is + Port ( + i_bclk : in std_logic; + i_reset : in std_logic; + i_lrc : in std_logic; + i_cpt_bits : in std_logic_vector(6 downto 0); + -- + o_bit_enable : out std_logic ; -- + o_load_left : out std_logic ; -- + o_load_right : out std_logic ; -- + -- o_str_dat : out std_logic ; -- + o_cpt_bit_reset : out std_logic -- + +); +end mef_cod_i2s_vsb; + +architecture Behavioral of mef_cod_i2s_vsb is + +-- définition de la MEF de contrôle + type fsm_cI2S_etats is ( + sta_init, + sta_g0, + sta_g1, + sta_g2, + sta_g3, + sta_gf, + sta_d0, + sta_d1, + sta_d2, + sta_d3, + sta_df + ); + + signal fsm_EtatCourant, fsm_prochainEtat : fsm_cI2S_etats; + +begin + + -- Assignation du prochain état + process(i_bclk, i_reset) + begin + if (i_reset ='1') then + fsm_EtatCourant <= sta_init; + else + if rising_edge(i_bclk) then + fsm_EtatCourant <= fsm_prochainEtat; + end if; + end if; + end process; + +-- +-- conditions de transitions +transitions: process(i_lrc , fsm_EtatCourant, i_cpt_bits) +begin + case fsm_EtatCourant is + when sta_init => + if(i_lrc = '0') then + fsm_prochainEtat <= sta_gf; + else + fsm_prochainEtat <= sta_df; + end if; + when sta_gf => + if(i_lrc = '0') then + fsm_prochainEtat <= sta_gf; + else + fsm_prochainEtat <= sta_d0; + end if; + when sta_g0 => + fsm_prochainEtat <= sta_g1; + when sta_g1 => + if( i_cpt_bits = "010111" ) then + fsm_prochainEtat <= sta_g2; + else + fsm_prochainEtat <= sta_g1; + end if; + when sta_g2 => + fsm_prochainEtat <= sta_g3; + when sta_g3 => + fsm_prochainEtat <= sta_gf; + -- + when sta_df => + if(i_lrc = '0') then + fsm_prochainEtat <= sta_g0; + else + fsm_prochainEtat <= sta_df; + end if; + when sta_d0 => + fsm_prochainEtat <= sta_d1; + when sta_d1 => + if( i_cpt_bits = "010111" ) then + fsm_prochainEtat <= sta_d2; + else + fsm_prochainEtat <= sta_d1; + end if; + when sta_d2 => + fsm_prochainEtat <= sta_d3; + when sta_d3 => + fsm_prochainEtat <= sta_df; + end case; + end process; + + -- relations de sorties pour le contrôle du registre et du compteur + sortie: process(fsm_EtatCourant, i_lrc ) + begin + + case fsm_EtatCourant is + when sta_init => + o_cpt_bit_reset <= '0'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_g0=> + o_cpt_bit_reset <= '1'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_g1=> + o_cpt_bit_reset <= '0'; + o_bit_enable <= '1'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_g2=> + o_cpt_bit_reset <= '0'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_g3=> + o_cpt_bit_reset <= '0'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_gf => + o_cpt_bit_reset <= '0'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '1'; + -- + when sta_d0=> + o_cpt_bit_reset <= '1'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_d1=> + o_cpt_bit_reset <= '0'; + o_bit_enable <= '1'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_d2=> + o_cpt_bit_reset <= '0'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_d3=> + o_cpt_bit_reset <= '0'; + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + when sta_df=> + o_cpt_bit_reset <= '0'; + o_bit_enable <= '0'; + o_load_left <= '1'; + o_load_right <= '0'; + end case; + + end process; + +end Behavioral;
\ No newline at end of file diff --git a/pb_logique_seq.srcs/sources_1/imports/new/mef_decod_i2s_v1b.vhd b/pb_logique_seq.srcs/sources_1/imports/new/mef_decod_i2s_v1b.vhd new file mode 100644 index 0000000..0cd6843 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/mef_decod_i2s_v1b.vhd @@ -0,0 +1,111 @@ +--------------------------------------------------------------------------------------------- +-- circuit mef_decod_i2s_v1b.vhd Version mise en oeuvre avec des compteurs +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- Version : 1.0 +-- Nomenclature : 0.8 GRAMS +-- Date : 7 mai 2019 +-- Auteur(s) : Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- +-- Outils : vivado 2019.1 +--------------------------------------------------------------------------------------------- +-- Description: +-- MEF pour decodeur I2S version 1b +-- La MEF est substituee par un compteur +-- +-- notes +-- frequences (peuvent varier un peu selon les contraintes de mise en oeuvre) +-- i_lrc ~ 48. KHz (~ 20.8 us) +-- d_ac_mclk, ~ 12.288 MHz (~ 80,715 ns) (non utilisee dans le codeur) +-- i_bclk ~ 3,10 MHz (~ 322,857 ns) freq mclk/4 +-- La durée d'une période reclrc est de 64,5 périodes de bclk ... +-- +-- Revision +-- Revision 14 mai 2019 (version ..._v1b) composants dans entités et fichiers distincts +--------------------------------------------------------------------------------------------- +-- À faire : +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +entity mef_decod_i2s_v1b is + Port ( + i_bclk : in std_logic; + i_reset : in std_logic; + i_lrc : in std_logic; + i_cpt_bits : in std_logic_vector(6 downto 0); + -- + o_bit_enable : out std_logic ; -- + o_load_left : out std_logic ; -- + o_load_right : out std_logic ; -- + o_str_dat : out std_logic ; -- + o_cpt_bit_reset : out std_logic -- + +); +end mef_decod_i2s_v1b; + +architecture Behavioral of mef_decod_i2s_v1b is + + signal d_reclrc_prec : std_logic ; -- + +begin + + -- pour detecter transitions d_ac_reclrc + reglrc_I2S: process ( i_bclk) + begin + if i_bclk'event and (i_bclk = '1') then + d_reclrc_prec <= i_lrc; + end if; + end process; + + -- synch compteur codeur + rest_cpt: process (i_lrc, d_reclrc_prec, i_reset) + begin + o_cpt_bit_reset <= (d_reclrc_prec xor i_lrc) or i_reset; + end process; + + + -- decodage compteur avec case ... + sig_ctrl_I2S: process (i_cpt_bits, i_lrc ) + begin + case i_cpt_bits is + when "0000000" => + o_bit_enable <= '1'; + o_load_left <= '0'; + o_load_right <= '0'; + o_str_dat <= '0'; + when "0000001" | "0000010" | "0000011" | "0000100" + | "0000101" | "0000110" | "0000111" | "0001000" + | "0001001" | "0001010" | "0001011" | "0001100" + | "0001101" | "0001110" | "0001111" | "0010000" + | "0010001" | "0010010" | "0010011" | "0010100" + | "0010101" | "0010110" | "0010111" + => + o_bit_enable <= '1'; + o_load_left <= '0'; + o_load_right <= '0'; + o_str_dat <= '0'; + when "0011000" => + o_bit_enable <= '0'; + o_load_left <= not i_lrc; + o_load_right <= i_lrc; + o_str_dat <= '0'; + when "0011001" => + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + o_str_dat <= i_lrc; + when others => + o_bit_enable <= '0'; + o_load_left <= '0'; + o_load_right <= '0'; + o_str_dat <= '0'; + end case; + end process; + + end Behavioral;
\ No newline at end of file diff --git a/pb_logique_seq.srcs/sources_1/imports/new/module_commande.vhd b/pb_logique_seq.srcs/sources_1/imports/new/module_commande.vhd new file mode 100644 index 0000000..e36b87f --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/module_commande.vhd @@ -0,0 +1,68 @@ +-- module_commande.vhd
+-- D. Dalle 30 avril 2019, 16 janv 2020, 23 avril 2020
+-- module qui permet de réunir toutes les commandes (problematique circuit sequentiels)
+-- recues des boutons, avec conditionnement, et des interrupteurs
+
+-- 23 avril 2020 elimination constante mode_seq_bouton: std_logic := '0'
+
+LIBRARY ieee;
+USE ieee.std_logic_1164.all;
+
+entity module_commande IS
+generic (nbtn : integer := 4; mode_simulation: std_logic := '0');
+ PORT (
+ clk : in std_logic;
+ o_reset : out std_logic;
+ i_btn : in std_logic_vector (nbtn-1 downto 0); -- signaux directs des boutons
+ i_sw : in std_logic_vector (3 downto 0); -- signaux directs des interrupteurs
+ o_btn_cd : out std_logic_vector (nbtn-1 downto 0); -- signaux conditionnés
+ o_selection_fct : out std_logic_vector(1 downto 0);
+ o_selection_par : out std_logic_vector(1 downto 0)
+ );
+end module_commande;
+
+ARCHITECTURE BEHAVIOR OF module_commande IS
+
+
+component conditionne_btn_v7 is
+generic (nbtn : integer := nbtn; mode_simul: std_logic := '0');
+ port (
+ CLK : in std_logic; -- devrait etre de l ordre de 50 Mhz
+ i_btn : in std_logic_vector (nbtn-1 downto 0);
+ --
+ o_btn_db : out std_logic_vector (nbtn-1 downto 0);
+ o_strobe_btn : out std_logic_vector (nbtn-1 downto 0)
+ );
+end component;
+
+
+ signal d_strobe_btn : std_logic_vector (nbtn-1 downto 0);
+ signal d_btn_cd : std_logic_vector (nbtn-1 downto 0);
+ signal d_reset : std_logic;
+
+BEGIN
+
+
+ inst_cond_btn: conditionne_btn_v7
+ generic map (nbtn => nbtn, mode_simul => mode_simulation)
+ port map(
+ clk => clk,
+ i_btn => i_btn,
+ o_btn_db => d_btn_cd,
+ o_strobe_btn => d_strobe_btn
+ );
+
+ process(clk)
+ begin
+ if(rising_edge(clk)) then
+ o_reset <= d_reset;
+ end if;
+ end process;
+
+
+ o_btn_cd <= d_btn_cd;
+ o_selection_par <= i_sw(1 downto 0); -- mode de selection du parametre par sw
+ o_selection_fct <= i_sw(3 downto 2); -- mode de selection de la fonction par sw
+ d_reset <= i_btn(3); -- pas de contionnement particulier sur reset
+
+END BEHAVIOR;
diff --git a/pb_logique_seq.srcs/sources_1/imports/new/mux2.vhd b/pb_logique_seq.srcs/sources_1/imports/new/mux2.vhd new file mode 100644 index 0000000..ee18702 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/mux2.vhd @@ -0,0 +1,65 @@ +---------------------------------------------------------------------------------- +-- Company: +-- Engineer: +-- +-- Create Date: 11/23/2021 04:00:46 PM +-- Design Name: +-- Module Name: mux2 - Behavioral +-- Project Name: +-- Target Devices: +-- Tool Versions: +-- Description: +-- +-- Dependencies: +-- +-- Revision: +-- Revision 0.01 - File Created +-- Additional Comments: +-- +---------------------------------------------------------------------------------- + + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; + +-- Uncomment the following library declaration if using +-- arithmetic functions with Signed or Unsigned values +--use IEEE.NUMERIC_STD.ALL; + +-- Uncomment the following library declaration if instantiating +-- any Xilinx leaf cells in this code. +--library UNISIM; +--use UNISIM.VComponents.all; + +entity mux2 is + Generic ( input_length : integer := 24 ); + Port ( sel : in STD_LOGIC_VECTOR (1 downto 0); + input1 : in STD_LOGIC_VECTOR (input_length-1 downto 0); + input2 : in STD_LOGIC_VECTOR (input_length-1 downto 0); + output0 : out STD_LOGIC_VECTOR (input_length-1 downto 0)); +end mux2; + +architecture Behavioral of mux2 is + +signal tied_to_gnd : std_logic_vector(input_length - 1 downto 0) := (others => '0'); + +begin + +process(sel,input1, input2) +begin + case sel is + when "00" => + output0 <= tied_to_gnd; + when "01" => + output0 <= input1; + when "10" => + output0 <= input2; + when "11" => + output0 <= tied_to_gnd; + when others => + output0 <= tied_to_gnd; + end case; +end process; + + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/mux4.vhd b/pb_logique_seq.srcs/sources_1/imports/new/mux4.vhd new file mode 100644 index 0000000..4e46dbc --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/mux4.vhd @@ -0,0 +1,65 @@ +---------------------------------------------------------------------------------- +-- Company: +-- Engineer: +-- +-- Create Date: 11/18/2021 11:51:08 AM +-- Design Name: +-- Module Name: mux4 - Behavioral +-- Project Name: +-- Target Devices: +-- Tool Versions: +-- Description: +-- +-- Dependencies: +-- +-- Revision: +-- Revision 0.01 - File Created +-- Additional Comments: +-- +---------------------------------------------------------------------------------- + + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; + +-- Uncomment the following library declaration if using +-- arithmetic functions with Signed or Unsigned values +--use IEEE.NUMERIC_STD.ALL; + +-- Uncomment the following library declaration if instantiating +-- any Xilinx leaf cells in this code. +--library UNISIM; +--use UNISIM.VComponents.all; + +entity mux4 is + Generic ( input_length : integer := 24 ); + Port ( input0 : in STD_LOGIC_VECTOR (input_length-1 downto 0); + input1 : in STD_LOGIC_VECTOR (input_length-1 downto 0); + input2 : in STD_LOGIC_VECTOR (input_length-1 downto 0); + input3 : in STD_LOGIC_VECTOR (input_length-1 downto 0); + sel : in STD_LOGIC_VECTOR (1 downto 0); + output0 : out STD_LOGIC_VECTOR (input_length-1 downto 0)); +end mux4; + +architecture Behavioral of mux4 is + +begin + +process(sel, input0, input1, input2, input3) +begin + case sel is + when "00" => + output0 <= input0; + when "01" => + output0 <= input1; + when "10" => + output0 <= input2; + when "11" => + output0 <= input3; + when others => + output0 <= input0; + end case; +end process; + + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/or2.vhd b/pb_logique_seq.srcs/sources_1/imports/new/or2.vhd new file mode 100644 index 0000000..b76c01e --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/or2.vhd @@ -0,0 +1,47 @@ +---------------------------------------------------------------------------------- +-- Company: +-- Engineer: +-- +-- Create Date: 11/23/2021 04:00:46 PM +-- Design Name: +-- Module Name: or2 - Behavioral +-- Project Name: +-- Target Devices: +-- Tool Versions: +-- Description: +-- +-- Dependencies: +-- +-- Revision: +-- Revision 0.01 - File Created +-- Additional Comments: +-- +---------------------------------------------------------------------------------- + + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; + +-- Uncomment the following library declaration if using +-- arithmetic functions with Signed or Unsigned values +--use IEEE.NUMERIC_STD.ALL; + +-- Uncomment the following library declaration if instantiating +-- any Xilinx leaf cells in this code. +--library UNISIM; +--use UNISIM.VComponents.all; + +entity or2 is + Port ( in1 : in STD_LOGIC; + in2 : in STD_LOGIC; + output : out STD_LOGIC); +end or2; + +architecture Behavioral of or2 is + +begin + +output <= in1 or in2; + + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/reg_24b.vhd b/pb_logique_seq.srcs/sources_1/imports/new/reg_24b.vhd new file mode 100644 index 0000000..43dd7a9 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/reg_24b.vhd @@ -0,0 +1,55 @@ +--------------------------------------------------------------------------------------------- +-- circuit reg_24b.vhd +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- Version : 1.0 +-- Nomenclature : 0.8 GRAMS +-- Date : 10 janvier 2019, rev 29 janvier, 2 mai 2019, 5 mai 2019 +-- Auteur(s) : Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- +-- Outils : vivado 2018.2 +--------------------------------------------------------------------------------------------- +-- Description: +-- Registre de 24 bits +-- +-- Revision 14 mai 2019 +--------------------------------------------------------------------------------------------- +-- À faire : +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +entity reg_24b is + Port ( + i_clk : in std_logic; + i_reset : in std_logic; + i_en : in std_logic; + i_dat : in std_logic_vector(23 downto 0); + o_dat : out std_logic_vector(23 downto 0) +); +end reg_24b; + +architecture Behavioral of reg_24b is + + -- + signal q_reg : std_logic_vector(23 downto 0); -- registre + + begin + -- registre + reg_dec: process (i_clk, i_reset) + begin + if (i_reset = '1') then + q_reg <= (others =>'0'); + elsif rising_edge(i_clk) and (i_en = '1') then + q_reg <= i_dat; + end if; + end process; + + o_dat <= q_reg; + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/reg_dec_24b.vhd b/pb_logique_seq.srcs/sources_1/imports/new/reg_dec_24b.vhd new file mode 100644 index 0000000..1a6e708 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/reg_dec_24b.vhd @@ -0,0 +1,61 @@ +--------------------------------------------------------------------------------------------- +-- circuit reg_dec_24b.vhd +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- Version : 1.0 +-- Nomenclature : 0.8 GRAMS +-- Date : 15 mai 2019 +-- Auteur(s) : Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- +-- Outils : vivado 2018.2 +--------------------------------------------------------------------------------------------- +-- Description: +-- Registre à décalages de 24 bits +-- +-- Revision 14 mai 2019 +--------------------------------------------------------------------------------------------- +-- À faire : +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +entity reg_dec_24b is + Port ( + i_clk : in std_logic; -- horloge + i_reset : in std_logic; -- reinitialisation + i_load : in std_logic; -- activation chargement parallele + i_en : in std_logic; -- activation decalage + i_dat_bit : in std_logic; -- entree serie + i_dat_load : in std_logic_vector(23 downto 0); -- entree parallele + o_dat : out std_logic_vector(23 downto 0) -- sortie parallele +); +end reg_dec_24b; + +architecture Behavioral of reg_dec_24b is + + -- + signal q_shift_reg : std_logic_vector(23 downto 0); -- registre + + begin + -- registre a décalage, MSB arrive premier, entre par la droite, decalage a gauche + reg_dec: process (i_clk, i_reset) + begin + if (i_reset = '1') then + q_shift_reg <= (others =>'0'); + elsif rising_edge(i_clk) then + if (i_load = '1') then + q_shift_reg <= i_dat_load; + elsif (i_en = '1') then + q_shift_reg(23 downto 0) <= q_shift_reg(22 downto 0) & i_dat_bit; + end if; + end if; + end process; + + o_dat <= q_shift_reg; + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/reg_dec_24b_fd.vhd b/pb_logique_seq.srcs/sources_1/imports/new/reg_dec_24b_fd.vhd new file mode 100644 index 0000000..5a25998 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/reg_dec_24b_fd.vhd @@ -0,0 +1,61 @@ +--------------------------------------------------------------------------------------------- +-- circuit reg_dec_24b_fd.vhd +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- Version : 1.0 +-- Nomenclature : 0.8 GRAMS +-- Date : 15 mai 2019 +-- Auteur(s) : Daniel Dalle +-- Technologies : FPGA Zynq (carte ZYBO Z7-10 ZYBO Z7-20) +-- +-- Outils : vivado 2018.2 +--------------------------------------------------------------------------------------------- +-- Description: +-- Registre à décalages de 24 bits : *** fonctionne sur front descendant de l'horloge +-- +-- Revision 15 mai 2019 +--------------------------------------------------------------------------------------------- +-- À faire : +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +entity reg_dec_24b_fd is + Port ( + i_clk : in std_logic; + i_reset : in std_logic; + i_load : in std_logic; + i_en : in std_logic; + i_dat_bit : in std_logic; + i_dat_load : in std_logic_vector(23 downto 0); + o_dat : out std_logic_vector(23 downto 0) +); +end reg_dec_24b_fd; + +architecture Behavioral of reg_dec_24b_fd is + + -- + signal q_shift_reg : std_logic_vector(23 downto 0); -- registre a decalage + + begin + -- registre a décalage, MSB arrive premier, entre par la droite, decalage a gauche + reg_dec: process (i_clk, i_reset) + begin + if (i_reset = '1') then + q_shift_reg <= (others =>'0'); + elsif falling_edge(i_clk) then + if (i_load = '1') then + q_shift_reg <= i_dat_load; + elsif (i_en = '1') then + q_shift_reg(23 downto 0) <= q_shift_reg(22 downto 0) & i_dat_bit; + end if; + end if; + end process; + + o_dat <= q_shift_reg; + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/sig_fct_3.vhd b/pb_logique_seq.srcs/sources_1/imports/new/sig_fct_3.vhd new file mode 100644 index 0000000..2e19706 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/sig_fct_3.vhd @@ -0,0 +1,61 @@ +--------------------------------------------------------------------------------------------- +-- sig_fct_3.vhd (temporaire) +--------------------------------------------------------------------------------------------- +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 5.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : 29 janvier 2019 +-- Auteur(s) : +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +--------------------------------------------------------------------------------------------- +-- Description +-- fonction temporaire, aucun calcul +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- +-- À FAIRE: +-- Voir le guide de la problématique +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; +USE ieee.numeric_std.ALL; +Library UNISIM; +use UNISIM.vcomponents.all; + +--------------------------------------------------------------------------------------------- +-- Description comportementale +--------------------------------------------------------------------------------------------- +entity sig_fct_3 is + Port ( + i_ech : in std_logic_vector (23 downto 0); + o_ech_fct : out std_logic_vector (23 downto 0) + ); +end sig_fct_3; + +---------------------------------------------------------------------------------- + +architecture Behavioral of sig_fct_3 is + +--------------------------------------------------------------------------------- +-- Signaux +---------------------------------------------------------------------------------- + signal d_ech : std_logic_vector (23 downto 0); -- + signal d_ech_fct : std_logic_vector (23 downto 0); -- + signal d_ech_u24 : unsigned (23 downto 0); -- + +--------------------------------------------------------------------------------------------- +-- +begin + -- simple transfert... + d_ech_u24 <= unsigned (i_ech); + o_ech_fct <= std_logic_vector( d_ech_u24); + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/sig_fct_sat_dure.vhd b/pb_logique_seq.srcs/sources_1/imports/new/sig_fct_sat_dure.vhd new file mode 100644 index 0000000..2c0c463 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/sig_fct_sat_dure.vhd @@ -0,0 +1,105 @@ + +--------------------------------------------------------------------------------------------- +-- sig_fct_sat_dure_sol.vhd +---------------------------------------------------------------------------------------------YBO +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 5.0 +-- Nomenclature : inspiree de la nomenclature 0.2 GRAMS +-- Date : 6 mai 2020 +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +--------------------------------------------------------------------------------------------- +-- Description +-- Module qui applique une saturation au signal d'entrée. +-- La valeur de saturation est déterminée par c_ech_u24_max. +-- La fonction de saturation est symétrique pour les valeur positives et négatives. +-- Le signal est interprété en notation complément a 2 +--------------------------------------------------------------------------------------------- +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- +-- À FAIRE: +-- +--------------------------------------------------------------------------------------------- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs +USE ieee.numeric_std.ALL; +--use IEEE.std_logic_arith.all; -- requis pour les constantes etc. +--use IEEE.std_logic_arith.all; -- requis pour les constantes telles que cdviv6 etc. +Library UNISIM; +use UNISIM.vcomponents.all; + +---------------------------------------------------------------------------------- +-- +---------------------------------------------------------------------------------- +entity sig_fct_sat_dure is +generic (c_ech_u24_max : unsigned (23 downto 0) := x"1FFFFF"); + Port ( + i_ech : in std_logic_vector (23 downto 0); + o_ech_fct : out std_logic_vector (23 downto 0) + ); +end sig_fct_sat_dure; + +---------------------------------------------------------------------------------- + +architecture Behavioral of sig_fct_sat_dure is + + +--------------------------------------------------------------------------------- +-- Signaux +---------------------------------------------------------------------------------- + + -- constant c_ech_u24_max : unsigned (23 downto 0) := x"7FFFFF" / 4 ; -- seuil etabli pour test + signal d_ech_u24 : unsigned (23 downto 0); -- + signal d_ech_u24_abs : unsigned (23 downto 0); -- + signal d_ech_fct_u24 : unsigned (23 downto 0); -- + signal d_ech_fct_u24_satur : unsigned (23 downto 0); -- + + +--------------------------------------------------------------------------------------------- +-- Description +--------------------------------------------------------------------------------------------- +begin + d_ech_u24 <= unsigned (i_ech); + + inst_abs_in: process( d_ech_u24) + begin + if (d_ech_u24 = x"800000") then d_ech_u24_abs <= x"7FFFFF"; else + if d_ech_u24(23) = '1' then + d_ech_u24_abs <= not d_ech_u24 + 1; + else + d_ech_u24_abs <= d_ech_u24; + end if; + end if; + end process; + + inst_satur: process( d_ech_u24_abs) + + begin + if (d_ech_u24_abs > c_ech_u24_max) then + d_ech_fct_u24_satur <= c_ech_u24_max; + else + d_ech_fct_u24_satur <= d_ech_u24_abs; + end if; + end process; + + inst_vsign_out: process(d_ech_fct_u24_satur, d_ech_u24) + begin + if d_ech_u24(23) = '1' then + d_ech_fct_u24 <= not d_ech_fct_u24_satur + 1; + else + d_ech_fct_u24 <= d_ech_fct_u24_satur; + end if; + end process; + + o_ech_fct <= std_logic_vector( d_ech_fct_u24); + +end Behavioral; diff --git a/pb_logique_seq.srcs/sources_1/imports/new/strb_gen_v3.vhd b/pb_logique_seq.srcs/sources_1/imports/new/strb_gen_v3.vhd new file mode 100644 index 0000000..49d6e56 --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/strb_gen_v3.vhd @@ -0,0 +1,73 @@ +--------------------------------------------------------------------------------------------- +-- str_gen_v3_v3.vhd +--------------------------------------------------------------------------------------------- +-- Generation d'horloge et de signaux de synchronisation +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 3.0 révision de la nomenclature +-- Nomenclature : ref GRAMS +-- Date : 26 mai 2016, 19 juillet 2016, 31 août 2018, 11 septembre 2018, 31 octobre 2018 +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 PYNQ-Z1 (xc7z020clg400-1) antérieurement sur Artix 7 ( xc7a35tcpg236-1 ) +-- Outils : vivado 2018.2 64 bits +-- +-------------------------------- +-- Description +-------------------------------- +-- Génération de signaux de synchronisation, incluant des "strobes" +-- 11 septembre 2018: élimination des horloges internes pour réduire le nombre d signaux d'horloges +-------------------------------- +-- À FAIRE: +-------------------------------- +-- +-- +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; + +entity strb_gen is + + Port ( + CLK : in STD_LOGIC; -- Entrée horloge maitre + i_don : in STD_LOGIC; -- signal pour generer strobe au front montant + o_stb : out STD_LOGIC -- strobe synchrone + ); + +end strb_gen; + +architecture Behavioral of strb_gen is + + signal qstrobe : std_logic := '0'; + signal q_don : std_logic:= '0'; + +begin + +process(CLK, i_don) -- bascule synchro de l entree +begin + if(CLK'event and CLK = '1') then + q_don <= i_don; + end if; +end process; + +process(i_don, q_don) -- sortie impulsion synchrone +begin + o_stb <= i_don and not(q_don); +end process; + +-- autres version pour synchroniser l'entree si necessaire +--process(CLK, i_don) -- bascule second niveau +--begin +-- if(CLK'event and CLK = '1') then +-- qq_don <= q_don; +-- end if; +--end process; + +--process(i_don, q_don, qq_don) -- sortie impulsion synchrone +--begin +-- qstrobe <= q_don and not(qq_don); +--end process; + +end Behavioral; + diff --git a/pb_logique_seq.srcs/sources_1/imports/new/synchro_codec_v1.vhd b/pb_logique_seq.srcs/sources_1/imports/new/synchro_codec_v1.vhd new file mode 100644 index 0000000..ba6041e --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/synchro_codec_v1.vhd @@ -0,0 +1,158 @@ +--------------------------------------------------------------------------------------------- +-- synchro_codec_v1.vhd +--------------------------------------------------------------------------------------------- +-- Generation d'horloge et de signaux de synchronisation +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 1.0 +-- Nomenclature : ref GRAMS +-- Date : 30 octobre 2018, 7 novembre 2018, 4 janvier 2019, 24 janvier 2019, 10 décembre 2019 +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +-------------------------------- +-- Description +-------------------------------- +-- Génération de signaux de synchronisation, incluant des "strobes" +-- (utilise un PLL) +-- Ref: +-- 7 Series Libraries Guide www.xilinx.com 418 UG953 (v2016.3) October 5, 2016 +-- (pages 425 PLLE2_BASE) +-- +-- revisions +-- mise a jour D Dalle 10 decembre 2019 v1 synchro_zybo_v1 nomenclature synchro_demo_codec_v4 devient synchro_zybo_v1 +-- mise a jour D Dalle 24 janvier 2019 v4 strobe commentaires, élimination entrée reset +-- mise a jour D Dalle 7 janvier 2019 v3 strobe 1000Hz validation / correction S_1Hz +-- mise a jour D Dalle 4 janvier 2019 v3 strobe 1000Hz +-- mise a jour D Dalle 27 decembre 2018 v3 tous les strobes sur 50 MHz +-- mise a jour D Dalle 17 decembre 2018 constantes horloges en Hz (pour coherence avec autres modules) +--------------------------------------------------------------------------------------------- +-- À FAIRE: +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.std_logic_arith.all; -- requis pour les constantes etc. +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +Library UNISIM; +use UNISIM.vcomponents.all; + +entity synchro_codec_v1 is +generic (cst_CLK_syst_Hz: integer := 100_000_000); -- valeur par defaut fréquence de clkm + Port ( + sysclk : in STD_LOGIC; -- Entrée horloge système + -- (typique 125 MHz (1/8 ns) ou 100 ( 1/10 ns)) + o_clk_0 : out STD_LOGIC; -- horloge via bufg 50 MHz (20 ns) + --- (sera pour clk_p, horloge) + o_mclk : out STD_LOGIC; -- horloge via bufg 12.389 MHz + -- (80,714 ns) (pour codec) + o_stb_1000Hz : out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1000Hz + o_stb_1Hz : out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1Hz + o_S_1Hz : out STD_LOGIC; -- Signal temoin 1 Hz + o_bclk : out STD_LOGIC; -- horloge bit clk + -- (~ 12.289 MHz/4 soit 3,07225 MHz (325.49 ns) ) + o_reclrc : out STD_LOGIC -- horloge record, play back, + -- sampling rate clock, left right channel + -- (~ 48 KHz (20,83 us)) + ); +end synchro_codec_v1; + + + + +architecture Behavioral of synchro_codec_v1 is + + component synchro_zybo_v1 is + generic (const_CLK_syst_Hz: integer := 100_000_000); -- valeur par defaut de fréquence de clkm + Port ( + sysclk : in STD_LOGIC; -- Entrée horloge maitre (typique 125 MHz (1/8 ns) ou 100 ( 1/10 ns)) + o_clk_0 : out STD_LOGIC; -- horloge via bufg 50. MHz (20 ns) + o_clk_1 : out STD_LOGIC; -- horloge via bufg 12.389 MHz (80,714 ns) + o_stb_1000Hz : out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1000Hz + o_stb_1Hz : out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1Hz + o_S_1Hz : out STD_LOGIC -- Signal temoin 1 Hz + ); + end component; + + component gen_clk_codec + port ( + i_rst : in STD_LOGIC; -- entree reset + m_clk : in STD_LOGIC; -- Entrée horloge maitre codec (defaut 12.289 MHz (81.374 ns) ) + o_bclk : out STD_LOGIC; -- horloge bit clk (defaut 12.289 MHz / 4 soit 3,07225 MHz (325.49 ns) ) + o_reclrc : out STD_LOGIC -- horloge record, play back, sampling rate clock, left right channel (defaut 48 KHz (20,83 us)) + ); + end component; + +-- component strb_gen is +-- Port ( +-- CLK : in STD_LOGIC; -- Entrée horloge maitre +-- i_don : in STD_LOGIC; -- signal pour generer strobe au front montant +-- o_stb : out STD_LOGIC -- strobe synchrone +-- ); +-- end component; + + signal sysclk_int : std_logic; + signal clk_0_int : std_logic; + signal clk_1_int : std_logic; + + signal d_strobe_1000Hz_int : std_logic; + signal d_strobe_1Hz_int : std_logic; + signal d_S1Hz_int : std_logic; + signal d_bclk_int : std_logic; + signal d_lrc_int : std_logic; + signal d_T1Hz : std_logic; + -- signal reset : std_logic; + +begin + + inst_synchro : synchro_zybo_v1 + generic map (const_CLK_syst_Hz => cst_CLK_syst_Hz) + port map ( + sysclk => sysclk_int, + o_clk_0 => clk_0_int, -- 50 MHz + o_clk_1 => clk_1_int, -- master clk pour SSM2603 + o_stb_1000Hz => d_strobe_1000Hz_int, + o_stb_1Hz => d_strobe_1Hz_int, + o_S_1Hz => d_S1Hz_int + ); + + -- generateur horloge echantillonnage (ADC sampling Rate) et transfert binaire + inst_gen_clk_codec : gen_clk_codec + Port map ( + i_rst => '0', + m_clk => clk_1_int, + o_bclk => d_bclk_int, + o_reclrc => d_lrc_int + ); + +---- Outils développement du code +---- buffer horloge +--ClockBuf0: bufg +--port map( +-- I => CLKOUT0, +-- O => clk_0_interne +-- ); +--o_clk_0 <= clk_0_interne ; -- + +--ClockBufer1: bufg +-- port map( +-- I => CLKOUT1, +-- O => clk_1_interne +-- ); + +sysclk_int <= sysclk ; -- +o_clk_0 <= clk_0_int ; -- +o_mclk <= clk_1_int ; -- +o_S_1Hz <= d_S1Hz_int; +o_stb_1000Hz <= d_strobe_1000Hz_int; +o_stb_1Hz <= d_strobe_1Hz_int; + +o_bclk <= d_bclk_int; +o_reclrc <= d_lrc_int; + + +end Behavioral; + diff --git a/pb_logique_seq.srcs/sources_1/imports/new/synchro_zybo_v1.vhd b/pb_logique_seq.srcs/sources_1/imports/new/synchro_zybo_v1.vhd new file mode 100644 index 0000000..7feeaac --- /dev/null +++ b/pb_logique_seq.srcs/sources_1/imports/new/synchro_zybo_v1.vhd @@ -0,0 +1,266 @@ +--------------------------------------------------------------------------------------------- +-- synchro_zybo_v1.vhd +--------------------------------------------------------------------------------------------- +-- Generation d'horloge et de signaux de synchronisation +--------------------------------------------------------------------------------------------- +-- Université de Sherbrooke - Département de GEGI +-- +-- Version : 1.0 +-- Nomenclature : ref GRAMS +-- Date : 30 octobre 2018, 7 novembre 2018, 4 janvier 2019, 24 janvier 2019 +-- Auteur(s) : Daniel Dalle +-- Technologie : ZYNQ 7000 Zybo Z7-10 (xc7z010clg400-1) +-- Outils : vivado 2018.2 64 bits +-- +-------------------------------- +-- Description +-------------------------------- +-- Génération de signaux de synchronisation, incluant des "strobes" +-- (utilise un PLL) +-- Ref: +-- 7 Series Libraries Guide www.xilinx.com 418 UG953 (v2016.3) October 5, 2016 +-- (pages 425 PLLE2_BASE) +-- +-- revisions +-- mise a jour D Dalle 17 octobre 2019 nomenclature synchro_demo_codec_v4 devient synchro_zybo_v1 +-- mise a jour D Dalle 24 janvier 2019 v4 strobe commentaires, élimination entrée reset +-- mise a jour D Dalle 7 janvier 2019 v3 strobe 1000Hz validation / correction S_1Hz +-- mise a jour D Dalle 4 janvier 2019 v3 strobe 1000Hz +-- mise a jour D Dalle 27 decembre 2018 v3 tous les strobes sur 50 MHz +-- mise a jour D Dalle 17 decembre 2018 constantes horloges en Hz (pour coherence avec autres modules) +--------------------------------------------------------------------------------------------- +-- À FAIRE: +--------------------------------------------------------------------------------------------- + +library IEEE; +use IEEE.STD_LOGIC_1164.ALL; +use IEEE.std_logic_arith.all; -- requis pour les constantes etc. +use IEEE.STD_LOGIC_UNSIGNED.ALL; -- pour les additions dans les compteurs + +Library UNISIM; +use UNISIM.vcomponents.all; + + +entity synchro_zybo_v1 is +generic (const_CLK_syst_Hz: integer := 100_000_000); -- valeur par defaut fréquence de clkm +Port ( + sysclk : in STD_LOGIC; -- Entrée horloge maitre, typique 100 MHz (10 ns) ou 125 (8 ns) + o_clk_0 : out STD_LOGIC; -- horloge via bufg 50. MHz (20 ns) + o_clk_1 : out STD_LOGIC; -- horloge via bufg 12.389 MHz (80,714 ns) + o_stb_1000Hz: out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1000Hz + o_stb_1Hz : out STD_LOGIC; -- strobe durée 1/o_clk_0 sync sur 1Hz + o_S_1Hz : out STD_LOGIC -- Signal temoin 1 Hz + ); +end synchro_zybo_v1; + + +architecture Behavioral of synchro_zybo_v1 is + + component strb_gen is + Port ( + CLK : in STD_LOGIC; -- Entrée horloge maitre + i_don : in STD_LOGIC; -- signal pour generer strobe au front montant + o_stb : out STD_LOGIC -- strobe synchrone + ); + end component; + +-- parametres pour constantes du PLL -- sim 125 MHz sysclk + constant const_CLK_syst_MHz : integer := integer( real (const_CLK_syst_Hz) / 1000000.0); -- verif 125 + constant c_CLKFBOUT_MULT : integer := 56; -- Multiply value for all CLKOUT, (2-64) + constant c_CLKIN1_PERIOD : real := 1000.0 / real(const_CLK_syst_MHz) ; -- Input clock period in ns to ps resolution + -- (i.e. 33.333 is 30 MHz). +-- constant c_DIVCLK_DIVIDE : integer := 7; -- Master division value, (1-56) + constant c_DIVCLK_DIVIDE : integer := 5; -- Master division value, (1-56) + -- CLKOUT0_DIVIDE - CLKOUT5_DIVIDE: Divide amount for each CLKOUT (1-128) + constant c_CLKOUT0_DIVIDE : integer := const_CLK_syst_MHz*c_CLKFBOUT_MULT/c_DIVCLK_DIVIDE/50 ; -- pour obtenir 50 MHz + -- verif 28 + constant c_CLKOUT1_DIVIDE : integer := const_CLK_syst_MHz*c_CLKFBOUT_MULT*1000/c_DIVCLK_DIVIDE/12289; -- pour obtenir 12.289 MHz + -- verif 113 + + constant FRQ_exact_KHz : integer := 1000*const_CLK_syst_MHz*c_CLKFBOUT_MULT/c_DIVCLK_DIVIDE/c_CLKOUT0_DIVIDE ; + -- calcul des constantes avec CLKOUT1 comme fréquence de base (12,2888 MHz) ** CLKOUT1 CLKOUT1 CLKOUT1 CLKOUT1 + -- verif 50_000 + constant FRQ_niv1_KHz_des : integer := 200 ; -- KHz (clk intermediaire desiree pour compteurs) + -- verif 200 + constant ctmp1: integer :=(FRQ_exact_KHz/(FRQ_niv1_KHz_des)-1); + -- verif 249 ( = x"0F9") + constant cdiv1 : std_logic_vector(11 downto 0):= conv_std_logic_vector(ctmp1, 12); + -- verif x"0F9" + constant FRQ_niv1_KHz_exact : integer := FRQ_exact_KHz / ctmp1; + + constant FRQ_niv2_Hz_des : integer := 2000 ; -- Hz (frq toggle intermediaire desiree ) --- **** valeur v3 modifiee + -- constant ctmp2: integer :=(1000*FRQ_niv1_KHz_exact/(2*FRQ_niv2_Hz_des)-1); -- calcul avec toggle + + constant ctmp2: integer :=(1000*FRQ_niv1_KHz_exact/(FRQ_niv2_Hz_des)-1); -- + -- verif 99 + constant cdiv2 : std_logic_vector(11 downto 0):= conv_std_logic_vector(ctmp2, 12); -- + constant FRQ_niv2_Hz_exact : integer := 1000*FRQ_niv1_KHz_exact / (ctmp2); + -- verif 2020 + -- + constant FRQ_inter_3_Hz_des : integer := 1 ; -- Hz (clk desiree ) + constant ctmp3: integer :=(FRQ_niv2_Hz_exact/(2*FRQ_inter_3_Hz_des)-1); + -- verif 1009 (= x"3F1") + --constant ctmp3: integer :=(FRQ_niv2_Hz_exact/(FRQ_inter_3_Hz_des)-1); + + constant cdiv3 : std_logic_vector(11 downto 0):= conv_std_logic_vector(ctmp3, 12); + + signal ValueCounter1 : std_logic_vector(11 downto 0) := (others => '0'); + signal ValueCounter2 : std_logic_vector(11 downto 0) := (others => '0'); + signal ValueCounter3 : std_logic_vector(11 downto 0) := (others => '0'); + + signal d_TC_ValueCounter1Hz : std_logic := '0'; + + signal clk_0_interne : std_logic := '0'; + signal clk_1_interne : std_logic := '0'; + signal d_s1HzInt : std_logic := '0' ; + signal q_s1HzInt : std_logic := '0' ; + --signal d_200kHzInt : std_logic := '0' ; + signal d_s1000HzInt : std_logic := '0' ; +-- signal q_s100HzInt : std_logic := '0' ; +-- signal qq_s100HzInt : std_logic := '0' ; + signal d_strobe_1000HzInt : std_logic := '0' ; + signal d_strobe_1HzInt : std_logic := '0' ; + + signal CLKOUT0 : std_logic := '0' ; + signal CLKOUT1 : std_logic := '0' ; + signal CLKOUT2 : std_logic := '0' ; -- non utilisee + signal CLKOUT3 : std_logic := '0' ; -- non utilisee + signal CLKOUT4 : std_logic := '0' ; -- non utilisee + signal CLKOUT5 : std_logic := '0' ; -- non utilisee + + signal CLKFBOUT : std_logic; -- 1-bit output: Feedback clock + signal LOCKED : std_logic; -- 1-bit output: LOCK + signal clk_in : std_logic; -- 1-bit input: Input clock + + +begin + +PLLE2_BASE_inst : PLLE2_BASE + generic map ( + BANDWIDTH => "OPTIMIZED", -- OPTIMIZED, HIGH, LOW + CLKFBOUT_MULT => c_CLKFBOUT_MULT, -- Multiply value for all CLKOUT, (2-64) + CLKFBOUT_PHASE => 0.0, -- Phase offset in degrees of CLKFB, (-360.000-360.000). + CLKIN1_PERIOD => c_CLKIN1_PERIOD, -- Input clock period in ns to ps resolution (i.e. 33.333 is 30 MHz). + -- CLKOUT0_DIVIDE - CLKOUT5_DIVIDE: Divide amount for each CLKOUT (1-128) + CLKOUT0_DIVIDE => c_CLKOUT0_DIVIDE, + CLKOUT1_DIVIDE => c_CLKOUT1_DIVIDE, + CLKOUT2_DIVIDE => 1, + CLKOUT3_DIVIDE => 1, + CLKOUT4_DIVIDE => 1, + CLKOUT5_DIVIDE => 1, + -- CLKOUT0_DUTY_CYCLE - CLKOUT5_DUTY_CYCLE: Duty cycle for each CLKOUT (0.001-0.999). + CLKOUT0_DUTY_CYCLE => 0.5, + CLKOUT1_DUTY_CYCLE => 0.5, + CLKOUT2_DUTY_CYCLE => 0.5, + CLKOUT3_DUTY_CYCLE => 0.5, + CLKOUT4_DUTY_CYCLE => 0.5, + CLKOUT5_DUTY_CYCLE => 0.5, + -- CLKOUT0_PHASE - CLKOUT5_PHASE: Phase offset for each CLKOUT (-360.000-360.000). + CLKOUT0_PHASE => 0.0, + CLKOUT1_PHASE => 0.0, + CLKOUT2_PHASE => 0.0, + CLKOUT3_PHASE => 0.0, + CLKOUT4_PHASE => 0.0, + CLKOUT5_PHASE => 0.0, + DIVCLK_DIVIDE => c_DIVCLK_DIVIDE, -- Master division value, (1-56) + REF_JITTER1 => 0.01, -- Reference input jitter in UI, (0.000-0.999). + STARTUP_WAIT => "FALSE" -- Delay DONE until PLL Locks, ("TRUE"/"FALSE") + ) + port map ( +-- Clock Outputs: 1-bit (each) output: User configurable clock outputs +CLKOUT0 => CLKOUT0, -- 1-bit output: CLKOUT0 +CLKOUT1 => CLKOUT1, -- 1-bit output: CLKOUT1 +CLKOUT2 => CLKOUT2, -- 1-bit output: CLKOUT2 +CLKOUT3 => CLKOUT3, -- 1-bit output: CLKOUT3 +CLKOUT4 => CLKOUT4, -- 1-bit output: CLKOUT4 +CLKOUT5 => CLKOUT5, -- 1-bit output: CLKOUT5 +-- Feedback Clocks: 1-bit (each) output: Clock feedback ports +CLKFBOUT => CLKFBOUT, -- 1-bit output: Feedback clock +LOCKED => LOCKED, -- 1-bit output: LOCK +CLKIN1 => sysclk, -- 1-bit input: Input clock +-- Control Ports: 1-bit (each) input: PLL control ports +PWRDWN => '0', -- 1-bit input: Power-down +--RST => i_rst, -- 1-bit input: Reset +RST =>'0', -- 1-bit input: Reset +-- Feedback Clocks: 1-bit (each) input: Clock feedback ports +CLKFBIN => CLKFBOUT -- 1-bit input: Feedback clock + ); + +-- buffer horloge +ClockBuf0: bufg +port map( + I => CLKOUT0, + O => clk_0_interne + ); +o_clk_0 <= clk_0_interne ; -- + +ClockBufer1: bufg + port map( + I => CLKOUT1, + O => clk_1_interne + ); + +o_clk_1 <= clk_1_interne ; -- +o_S_1Hz <= d_s1HzInt; +o_stb_1000Hz <= d_strobe_1000HzInt; +o_stb_1Hz <= d_strobe_1HzInt; + +-- gestion des compteurs (estimes de durees calcules pour sysclk = 125 MHz) --V3 +process(clk_0_interne) -- avec 50 MHz +-- +begin -- Estimation avec clk1 = 12,288 + -- (12,389 selon calcul avec sysclk =125 MHz) + -- + if(clk_0_interne'event and clk_0_interne = '1') then -- evenement se produit aux 81 ns approx + ValueCounter1 <= ValueCounter1 + 1; + if (ValueCounter1 = cdiv1) then -- evenement se produit aux 5 us approx + ValueCounter1 <= "000000000000"; + ValueCounter2 <= ValueCounter2 + 1; + if (ValueCounter2 = cdiv2) then + d_s1000HzInt <= Not d_s1000HzInt; -- evenement se produit aux 500 us approx (2 KHz) + ValueCounter2 <= "000000000000"; -- la periode de d_s1000HzInt est alors ~ 1 ms + ValueCounter3 <= ValueCounter3 + 1; + if (ValueCounter3 = cdiv3) then -- evenement se produit aux 500 ms approx (2 Hz) + ValueCounter3 <= "000000000000"; + d_s1HzInt <= Not d_s1HzInt; -- ici on fait un toggle donc 2*500 ms + -- -> 1 sec. pour frequence de d_s1HzInt; + end if; + end if; + end if; + end if; +end process; + + + +inst_strb_1000Hz : strb_gen + -- les strobes sont synchronisés sur l'horloge clk_1_interne + Port map ( + CLK => clk_0_interne, + i_don => d_s1000HzInt, + o_stb => d_strobe_1000HzInt + ); + +inst_strb_1Hz : strb_gen + -- les strobes sont synchronisés sur l'horloge clk_1_interne + Port map ( + CLK => clk_0_interne, + i_don => d_s1HzInt, + o_stb => d_strobe_1HzInt + ); + + +--process(CLKOUT1, q_s100HzInt) -- bascule synchro de l entree +--begin +-- if(CLKOUT1'event and CLKOUT1 = '1') then +-- qq_s100HzInt <= q_s100HzInt; +-- end if; +--end process; + +--process(q_s100HzInt, qq_s100HzInt) -- sortie impulsion synchrone +--begin +-- d_strobe_100HzInt <= q_s100HzInt and not(qq_s100HzInt); +--end process; + + +end Behavioral; + |