2016-01-11 2 views
3

Je suis en train d'écrire un test pour vérifier si le type time est synthétisé/simulé correctement dans divers outils du fournisseur FPGA. Un cas de coin est l'utilisation de vrais littéraux comme le littéral abstrait pour les valeurs de temps, par exemple: 1.001 us.Devrait être 1,001 us égal à 1001 ns en VHDL?

La norme IEEE Std. 1076-2008, Section 5.2.4.1 ou IEEE Std. 1076-1993, Section 3.1.3, Para 8 états:

Il y a un numéro de position correspondant à chaque valeur d'un type physique. Le numéro de position de la valeur correspondant à un nom d'unité est le nombre d'unités primaires représentées par ce nom d'unité. Le numéro de position de la valeur correspondant à un littéral physique avec une partie littérale abstraite est le plus grand nombre entier qui n'est pas supérieur à au produit de la valeur du littéral abstrait et à la position numéro du nom d'unité accompagnant.

Comme par définition TIME (voir l'article 16.2 ou 14.2), l'unité primaire est femtosecondes, de sorte que, le nombre de position de 1 us est 1000000000. Ainsi, le numéro de position 1.001 us devrait être 1,001,000,000, ce qui est également le numéro de position de 1001 ns. Ainsi, les deux valeurs doivent être égales. Mais, j'obtiens des résultats différents lorsque j'essaie de synthétiser ou de simuler l'unité dépouillée suivante. J'ai vérifié que la résolution temporelle minimale est de 1 fs ou 1 ps.

entity physical_test is 
    generic (
     C1 : time := 1001 ns; 
     C2 : time := 1.001 us; 
     C3 : time := TIME'val(integer(real(TIME'pos(1 us)) * 1.001)) 
    ); 
    port (
     y : out bit); 
end entity physical_test; 

architecture rtl of physical_test is 
    function f return boolean is 
    begin 
     report "C1 = " & TIME'image(C1) severity note; 
     report "C2 = " & TIME'image(C2) severity note; 
     report "C3 = " & TIME'image(C3) severity note; 
     return false; 
    end f; 

    constant C : boolean := f; 
begin -- architecture rtl 
    y <= '0'; 
end architecture rtl; 

QuestaSim (ModelSim) était le seul outil qui a rapporté l'attendu résultat:

# ** Note: C1 = 1001000000 fs 
# ** Note: C2 = 1001000000 fs 
# ** Note: C3 = 1001000000 fs 

Mais, la réelle résultat lors de la synthèse avec Quartus 15,0 ou ISE 14,7 est:

Note: "C1 = 1001000000 fs" 
Note: "C2 = 1000999999 fs" 
Note: "C3 = 1001000000 fs" 

Ainsi, la valeur C2 n'est pas comme prévu. Si j'écris le texte cité comme une équation, alors j'obtiens le résultat attendu dans la constante C3. Lorsque j'utilise les simulateurs intégrés de 14,7 ou ISE Vivado 2015,4, je reçois un résultat similaire:

Note: "C1 = 1001000 ps" 
Note: "C2 = 1000999 ps" 
Note: "C3 = 1001000 ps" 

Alors, devrait être le comportement de Quartus/ISE/Vivado considéré comme un bug? Ou est-il permis par la norme VHDL que 1.001 us n'est pas égal à 1001 ns?

EDIT: Le bug se produit également lorsque je compare 1.001 ps-1001 fs ainsi que quand je compare 1.001 ns-1001 ps. Comme le calcul manuel avec C3 était correct, cela ne devrait pas poser de problème avec la précision du réel.

Juste à noter, le synthétiseur de Vivado rapporte des résultats étranges:

Parameter C1 bound to: 32'b00111011101010100000110001000000 -- 1001000000 
Parameter C2 bound to: 32'b10010011011101001011110001101010 -- 2473901162 
Parameter C3 bound to: 32'sb00000000000000000000000000000001 -- 1 
+0

Vous pouvez ajouter ghdl (0.33) à la liste d'outils qui obtient la réponse que vous attendez. –

Répondre

2

Ceci est un problème avec des nombres à virgule flottante et a très peu à faire VHDL.Les nombres décimaux entiers peuvent être convertis en nombres binaires et en nombres décimaux sans perte d'informations (sauf si les nombres sont trop grands ou trop petits). Ce n'est pas le cas pour les fractions décimales. Le nombre décimal 1.001 converti en binaire est irrationnel. Lors de la conversion de binaire en décimal, il y aura des erreurs d'arrondi. Quart et ISE montrent le comportement attendu

Dans le cas Vivado quelque chose est arrivé avec le MSB de C2. Il semble que certaines conversions entre les entiers signés et non signés aient eu lieu, ce qui n'aurait pas dû être le cas. Et C3 était apparemment arrondi.

Vos exemples pourraient être utilisés pour soutenir la règle selon laquelle l'utilisation de l'unité principale est le meilleur choix.

+0

Le bug arrive aussi quand je compare '1.001 ps' '1001 fs' aussi bien que quand je compare' 1.001 ns '' 1001 ps'. Aussi le calcul manuel avec 'C3' était correct. Ainsi, il ne devrait pas être un problème avec l'exactitude du réel. –

+0

Vous parlez de Vivado maintenant? Ce n'est probablement pas un bug, juste une limitation ..;) – bogl

+0

Sérieusement, je n'ai jamais utilisé Vivado. Peut-être qu'il y a quelques indices dans la documentation. Votre exemple C3 est un peu artificiel, mais le problème avec C2 = 1.001 pourrait être soumis en tant que rapport de bogue. Xilinx est généralement très sensible. – bogl