8 votos

¿Por qué esta simple VHDL patrón para un registro de desplazamiento no funciona como se esperaba

A primera vista se podría esperar que el VHDL código fuente a continuación se comporte como un registro de desplazamiento. En la que p, a lo largo del tiempo sería

"UUUU0", "UUU00", "UU000", "U0000", "00000", ....

pero en su lugar es siempre U después de cinco (o más) días consecutivos, ciclos de reloj.

¿Por qué es esto?

Este código es en realidad un una versión muy simplificada de una forma mucho más complicado de simulación. Pero demuestra que los síntomas que veo.

Se presenta este resultado interesante e inesperado durante la simulación bajo ambos ModelSim y ActiveHDL, no he probado otros simuladores y (en segundo lugar a una explicación de la causa) como para saber si los demás actúan de la misma manera.

Para responder a esta pregunta correctamente, usted debe entender que:

  • Sé que esta no es la mejor manera de implementar un registro de desplazamiento
  • Sé que para RTL síntesis, este debe tener un reset.
  • Sé una matriz de std_logic es un std_logic_vector.
  • Sé el operador de agregación, &.

Lo que me he encontrado:

  • Si la asignación temp(0)<='0'; se mueve dentro del proceso, funciona.
  • Si el bucle se desenvuelve (ver código comentado), funciona.

Voy a reiterar que esta es una versión muy simplificada de una forma mucho más complicado de diseño (para un pipeline de la CPU), se ha configurado puramente mostrar los inesperados resultados de la simulación. El real tipos de señales son sólo una simplificación. Por esta razón, usted debe considerar sus respuestas con el código en la forma como se es.

Mi conjetura es que la simulación VHDL motor del optimizador de conversiones es erróneamente (o quizás como por especificación) que no molesta a ejecutar las expresiones dentro del bucle como no hay señales fuera de cambio, a pesar de que me puede refutar esto colocando el desempaquetado del bucle en un bucle.

Así que espero que la respuesta a esta pregunta es más para hacer con los estándares para la simulación VHDL de poco explícitas VHDL de la sintaxis y de cómo la simulación VHDL los motores de sus optimizaciones, más que si se les da el código de ejemplo es la mejor manera de hacer algo o no.

Y ahora el código que estoy simulando:

 library ieee;
 use ieee.std_logic_1164.all;   

 entity test_simple is
    port (
        clk : in  std_logic;
        q   : out std_logic
    );                   
 end entity;

 architecture example of test_simple is
    type   t_temp is array(4 downto 0) of std_logic;
    signal temp : t_temp;
 begin

    temp(0) <= '0';

    p : process (clk)
    begin               
        if rising_edge(clk) then
            for i in 1 to 4 loop
                    temp(i) <= temp(i - 1);
            end loop;

            --temp(1) <= temp(0);   
            --temp(2) <= temp(1);
            --temp(3) <= temp(2);
            --temp(4) <= temp(3);
        end if;
    end process p;
    q <= temp(4);
 end architecture;

Y el banco de pruebas:

library ieee;
use ieee.std_logic_1164.all;

entity Bench is
end entity;

architecture tb of bench is

component test_simple is
    port (
        clk : in  std_logic;
        q   : out std_logic
    );                   
end component;

signal clk:std_logic:='0';
signal q:std_logic;     
signal rst:std_logic;

constant freq:real:=100.0e3;

begin                       
    clk<=not clk after 0.5 sec / freq;

    TB:process
    begin
        rst<='1';
        wait for 10 us;
        rst<='0';
        wait for 100 us;
        wait;
    end process;

     --Note: rst is not connected
    UUT:test_simple  port map (clk=>clk,q=>q) ;
end architecture;

4voto

Brian Drummond Puntos 27798

Tiene que ver con lo que puede ser fácilmente evaluados en la elaboración de tiempo, formalmente, lo que se llama un "localmente estática de expresión". Este es un oscuro en busca de la regla, pero se merece un poco de pensamiento - finalmente lo hace tener algún sentido, y de su simulador es muy correcto en alerta por la generación de no evidentes resultados.

Ahora, temp(1) puede ser evaluada en tiempo de compilación (incluso antes de la elaboración de tiempo) y que puede generar un controlador en el bit 1 de "temp".

Sin embargo, temp(i) implica un poco más de trabajo para las herramientas. Dada la naturaleza trivial del bucle límites de aquí ( 1 a 4 ) es evidente para nosotros los seres humanos que temp(0) no puede ser impulsado y lo que están haciendo es seguro. Pero imagino que los límites eran las funciones lower(foo) to upper(bar) en un paquete declarado en otro lugar... ahora lo más que se puede decir con certeza es que temp es impulsado - por lo que el "localmente estática" la expresión es temp.

Y eso significa que el proceso está limitado por estas reglas a la unidad de todos los de temp, punto en el cual tiene varios controladores en temp(0) - el proceso de conducción (ningún valor inicial, es decir, 'u') y el externo temp(0) <= '0';. Así que, naturalmente, los dos conductores de resolver a la 'U'.

La alternativa sería un "chapucero poco regla" (opinión) que si el bucle límites fueron constantes, hacer una cosa, pero si ellos fueron declarados como algo más, algo distinto, y así sucesivamente ... el más excéntrico pocas reglas que hay, el más complejo, el lenguaje se convierte... en mi opinión, no una solución mejor.

i-Ciencias.com

I-Ciencias es una comunidad de estudiantes y amantes de la ciencia en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X