Mauvaises Pratiques
Conflits
Dans la description ci dessous, count est affecté :
- dans le process lors du reset
- En parallèle du process en recevant count_int
Ce forçage multiple correspond à un conflit ; la solution consite à gérer uniquement count_int dans le process et considérer count comme une copie de count_int en faisant count <= count_int en parallèle du process
library IEEE;
use IEEE.std_logic_1164.all;
use IEEE.numeric_std.all;
entity compteur_base is
port( clk,reset : in std_logic;
count : out std_logic_vector(3 downto 0));
end compteur_base;
architecture arch_compteur_base of compteur_base is
signal count_int : unsigned (3 downto 0);
begin
process(clk,reset)
begin
if reset='1' then count <= (others => '0');
elsif rising_edge(clk) then
if count_int="1111" then count_int <= (others => '0'); -- fin de comptage
else count_int <= count_int + 1; -- "+"(unsigned,int)
end if;
end if;
end process;
count <= std_logic_vector(count_int); -- count copie de count_int
end arch_compteur_base;
ET logique avec CLK
library IEEE;
use IEEE.std_logic_1164.all;
entity registre is
port( clk,reset,load : in std_logic;
d_in : in std_logic_vector(7 downto 0);
d_out : out std_logic_vector(7 downto 0));
end registre;
architecture arch_registre of registre is
begin
process(clk,reset)
begin
if reset='1' then d_out <= (others => '0');
elsif rising_edge(clk) and load='1' then
d_out <= d_in;
end if;
end process;
end arch_registre;
Le ET logique entre load et rising_edge(clk) a pour effet de générer une porte ET entre load et clk. Si cela ne change pas grand chose à la simulation, le composant décrit n’est plus synchrone à clk et pourra présenter un fonctionnement aléatoire dans un composant synthétisé.
Gestion des Signaux dans un Process
library IEEE;
use IEEE.std_logic_1164.all;
entity manip_signaux is
port( a : in std_logic;
s : out std_logic);
end manip_signaux;
architecture arch_manip_signaux of manip_signaux is
signal interne : std_logic;
begin
process(a)
begin
interne <= a; -- affectation de interne effective sur end process
s <= interne;
end process;
end arch_manip_signaux;
L’affectation de interne étant effective sur end process, s reçoit la valeur de interne au moment où on est entré dans le process.
Process Combinatoire
library IEEE;
use IEEE.std_logic_1164.all;
entity multiplexeur_faux is
port( E0,E1,E2,E3 : in std_logic_vector(7 downto 0);
sel : in std_logic_vector(1 downto 0);
S : out std_logic_vector(7 downto 0));
end multiplexeur_faux;
architecture arch_multiplexeur_faux of multiplexeur_faux is
begin
process(E0,E1,E2,E3)
begin
if sel="11" then S <= E3 ;
elsif sel="10" then S <= E2 ;
elsif sel="01" then S <= E1 ;
else S <= E0 ; -- cas par defaut obligatoire
end if;
end process;
end arch_multiplexeur_faux;
sel ne figurant pas dans la liste de sensibilité du process, S n’est pas modifié au moment où sel change (puisqu’on n’entre pas dans le process). Par conséquent on mémorise la valeur de S avec des bascules, il ne s’agit donc plus d’un composant combinatoire.
if then else : priorite
La structure if then elsif n’est pas équivalente à if then if
La première séquence induit une notion de priorité, de telle sorte que le reset est prioritaire, si reset=‘1’ on ignore la suite.
Dans le deuxième cas, même si reset=‘1’, on effectuera le chargement du registre si load=‘1’ (seule la dernière affectation est considérée)
|
|