clk événement vs rising edge()
j'ai toujours utilisé ce pour la détection d'un front montant:
if (clk'event and clk='1') then
mais cela peut aussi être utilisé:
if rising_edge(clk) then
Lecture ce post,rising_edge(clk)
est recommandé, mais il y a aussi commentaire indiquant que rising_edge(clk)
pourrait conduire à un mauvais comportement.
je ne peux pas décider lequel choisir pour l'avenir, en allant sur (clk'event and clk='1')
ou en adoptant rising_edge(clk)
.
toute expà © rience rà © elle sur ces deux? Des préférences?
Merci!
3 réponses
rising_edge est défini comme suit:
FUNCTION rising_edge (SIGNAL s : std_ulogic) RETURN BOOLEAN IS
BEGIN
RETURN (s'EVENT AND (To_X01(s) = '1') AND
(To_X01(s'LAST_VALUE) = '0'));
END;
FUNCTION To_X01 ( s : std_ulogic ) RETURN X01 IS
BEGIN
RETURN (cvt_to_x01(s));
END;
CONSTANT cvt_to_x01 : logic_x01_table := (
'X', -- 'U'
'X', -- 'X'
'0', -- '0'
'1', -- '1'
'X', -- 'Z'
'X', -- 'W'
'0', -- 'L'
'1', -- 'H'
'X' -- '-'
);
si votre horloge va seulement de 0 à 1, et de 1 à 0, alors rising_edge produira le code identique. Sinon, vous pouvez interpréter la différence.
personnellement, mes horloges ne vont que de 0 à 1 et vice versa. J'ai trouver rising_edge(clk)
pour être plus descriptifs que l' (clk'event and clk = '1')
variante.
le commentaire lié est incorrect : 'L' à '1' produira un bord Ascendant.
en outre, si votre signal d'horloge passe de 'H' à '1',rising_edge(clk)
(correctement) de ne pas déclencher alors que (clk'event and clk = '1')
(à tort).
certes, cela peut ressembler à un exemple artificiel, mais j'ai vu des formes d'onde d'horloge faire cela dans le matériel réel, en raison d'Échecs ailleurs.
exemple concret:
Imaginez que vous modélisez quelque chose comme un bus I2C (signaux appelés SCL
pour l'horloge et SDA
pour les données), où le bus est à trois états et les deux filets ont une faible traction. Votre banc d'essai doit modéliser la résistance de traction sur le PCB avec une valeur de "H".
scl <= 'H'; -- Testbench resistor pullup
vos périphériques maître I2C ou esclaves peuvent conduire le bus à '1 'ou' 0 'ou le laisser seul en assignant un'Z'
Attribution d'un '1' à la SCL net va provoquer un événement, parce que la valeur de SCL a changé.
Si vous avez une ligne de code qui s'appuie sur
(scl'event and scl = '1')
, alors vous aurez un faux déclenchement.Si vous avez une ligne de code qui s'appuie sur
rising_edge(scl)
, puis vous n'aurez pas de fausse gâchette.
continuer l'exemple: vous assignez un' 0 'à SCL, puis un'Z'. Le filet passe à "0", puis à "H".
ici, aller de '1' à '0' ne déclenche aucun des deux cas, mais passer de '0' à ' H ' déclenchera un rising_edge(scl)
condition (correct), mais le (scl'event and scl = '1')
cas manquer (incorrect).
Recommandation Générale:
Utiliser rising_edge(clk)
et falling_edge(clk)
au lieu de clk'event
pour tout le code.