Différence entre l'instruction If-else et Case dans VHDL


11

Je veux comprendre comment différentes constructions en code VHDL sont synthétisées en RTL.

  • Quelqu'un peut-il me dire la différence entre la construction If-Else et les constructions d' instructions Case d'un processus en VHDL en termes de la façon dont le code est inféré dans le circuit RTL par l'outil de synthèse?
  • Considérez le cas de plusieurs if-else imbriqués et le mélange d'instructions de cas avec la construction if-else à l' intérieur d'un processus.
  • Aussi quand utiliser quelle construction?

PS: J'ai vu une question connexe "Plusieurs déclarations if en cours dans vhdl" mais cela ne répond pas à ma question de toute façon.


Je ne peux pas commenter la façon dont les portes physiques seraient configurées, mais dans la plupart des compilateurs qui émettent un assemblage x86, un if-else existe généralement comme une seule vérification avec un saut conditionnel (par exemple jg, jl, jz, jnz, etc.), tandis que switch organise les cas par ordre numérique et fait des instructions dec/ itératives jz, ce qui est beaucoup plus efficace. Peut-être qu'une optimisation similaire est appliquée ici.
Polynôme

@Polynomial Le comportement de If-else et de case est significativement différent dans les langages matériels par rapport à votre programmation linéaire typique. Les optimisations de code opérationnel ne sont pas très pertinentes car l'instruction HDL s'exécute "instantanément".
W5VO

Réponses:


10

Quelqu'un peut-il me dire la différence entre la construction If-Else et les constructions d'instructions Case d'un processus en VHDL en termes de la façon dont le code est inféré dans le circuit RTL par l'outil de synthèse?

La if-elsif-elseconstruction déduit un réseau de routage prioritaire:

schématique

simuler ce circuit - Schéma créé à l'aide de CircuitLab

Cela correspond à

if bool_expr_1 then
    sig <= val_expr_1;
elsif bool_expr_2 then
    sig <= val_expr_2;
elsif bool_expr_3 then
    sig <= val_expr_3;
else
    sig <= val_expr_4;
end if;

La caseconstruction, d'autre part, induit un grand ol 'mux:

entrez la description de l'image ici

Cela correspond à

case case_expr is
  when c0 =>
    sig <= val_expr_0;
  when c1 =>
    sig <= val_expr_1;
  when c2 =>
    sig <= val_expr_2;
      ...
  when others =>
    sig <= val_expr_N;
end case;

Évidemment, ce sont des conceptions très simplifiées avec une seule expression de valeur, résultant en une sortie.

Considérez le cas de plusieurs if-else imbriqués et le mélange d'instructions de cas avec la construction if-else à l'intérieur d'un processus.

Par ce qui précède, vous pouvez voir comment ils s'emboîtent / se mélangent.

Aussi quand utiliser quelle construction?

Puisque if-elseinfère la priorité, il doit être utilisé lorsque plusieurs conditions d'entrée peuvent se produire. L'utilisation case, d'autre part, est appropriée lorsque les entrées s'excluent mutuellement.


Je comprends que l'énoncé de cas ne fonctionne que pour une condition d'entrée unique et que if-else peut fonctionner pour plusieurs conditions d'entrée. Mais les deux constructions génèrent essentiellement des multiplexeurs (en l'absence de clk). N'est-il pas possible que la synthèse logique optimise une seule entrée if-else en un seul grand multiplexeur au lieu d'une chaîne de multiplexeurs? En outre, qu'est-ce qu'un réseau de routage prioritaire ... n'est-ce pas simplement une chaîne de multiplexeurs au lieu d'un grand multiplexeur?
nurabha

De plus, lorsque nous avons un processus sensible à une horloge, if-else peut générer des éléments séquentiels tels que des registres, des verrous, etc. Une instruction case peut-elle également générer une logique séquentielle?
nurabha

Oui, un réseau de routage prioritaire est exactement cela - une chaîne de multiplexeurs. La nature de la if-elseconstruction, cependant, est à l'origine de cette chaîne. La première condition doit échouer pour que la deuxième condition soit testée. Ce n'est pas le cas pour, euh, la caseconstruction, et c'est pourquoi une if-elsedéclaration n'a pas pu être synthétisée comme un seul grand multiplexeur.
Angelo Stavrow

1
Et oui, une caseinstruction peut également générer une logique séquentielle. J'ai trouvé "Real World VHDL" , une série de diapositives de cours de l'Université de Glasgow, qui pourraient vous être utiles.
Angelo Stavrow

Ceci est une bonne référence.
nurabha

4

Dans cet ancien article de blog , l'auteur a écrit et synthétisé deux versions fonctionnellement équivalentes du code VHDL. L'un utilisant if-else, l'autre utilisant case. Le résultat:

J'ai synthétisé ce code et obtenu les résultats exacts. Même le schéma RTL était exactement le même pour les deux programmes.

Et sa conclusion:

Cela montre que les instructions «case» et «if ... elsif ... else» sont toutes deux tout aussi efficaces. Mais si vous voulez écrire un code clair, vous feriez mieux d'utiliser «case». «Case» est très utile lorsque La sortie dépend d'un grand nombre de conditions, mais si le nombre de conditions est très petit (2 ou 3), vous pouvez utiliser 'if..elseif..else'.

Il existe également des dizaines de publications sur ce sujet sur Stack Overflow pour toutes les langues imaginables. La conclusion est généralement la même, qu'il n'y a pas de différence en termes de performances. Parfois, s'il existe un grand nombre de cas, un compilateur peut être suffisamment intelligent pour créer une table de recherche qui produirait des performances légèrement meilleures.

Un synthétiseur VHDL peut faire quelque chose de similaire. Mais vous auriez toujours besoin d'un grand nombre de cas auquel cas (jeu de mots), vous voudriez probablement utiliser une déclaration de cas de toute façon car elle offre une meilleure lisibilité là où il y a un grand nombre d'options.

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.