Pregunta sobre Synthesizable For loop y Generate

3

Estoy usando el lenguaje Verilog y Zedboard como un tablero de destino.

Por lo que sé, el bucle for se puede sintetizar, y la herramienta de síntesis traduce el bucle for como una secuencia de instrucciones duplicadas, como el desenrollado del bucle.

Por ejemplo,

for ( i = 0; i < 4; i=i+1) begin
  mem[i] = i;
end

will be translated to 
mem[0] = 0;
mem[1] = 1;
mem[2] = 2;
mem[3] = 3;

Por lo tanto, por lo que sé, el bucle for puede usarse si el recurso está disponible para inferir las puertas múltiples pero con el mismo propósito.

Sin embargo, parece que la generación en Verilog puede usarse para, no solo implicar las múltiples instancias, sino también las múltiples instrucciones iguales a las del bucle for.

Entiendo que el generador solo puede implicar las múltiples instancias del módulo y el bucle for no se puede usar para ese propósito.

Entonces, ¿cuál es la diferencia entre generar + para bucle y solo para bucle? Aunque creo que ambos funcionan como el bucle que se desenrolla. ¿Hay alguna diferencia notable? Si no hay diferencia, ¿cuál es el estilo de codificación preferible para inducir el desenrollado del bucle?

    
pregunta JaeHyuk Lee

1 respuesta

3

Verilog for-loops se puede sintetizar perfectamente bajo ciertas condiciones:

  • Puede usar cualquier declaración de procedimiento dentro de un bucle (por ejemplo, if-else).
  • El número de bucles debe estar predeterminado .
    • La expresión limitante debe ser una comparación entre la variable de bucle y una constante o un parámetro.
    • La asignación de pasos debe aumentar el valor del bucle en una cantidad constante.
  • Puede asignar un valor diferente a la misma variable en cada bucle (por ejemplo, calcular un índice a partir de la variable de bucle).
  • Para fines de síntesis, el bucle se evalúa en tiempo cero, es decir, si intenta hacer un contador, solo verá el valor final.

Esas mismas reglas se aplican tanto si utiliza un bucle for en un bloque de procedimiento como en un bloque de generación.

Cuando se realiza en un bloque de procedimiento, initial y always , puede usar un bucle for para cambiar elementos en una matriz (exactamente como su ejemplo), o puede cambiar el mismo valor varias veces, por ejemplo:

for (idx = 0; idx < 4; idx=idx+1) begin
    a = a + b[idx];
    c = c + 2;     //You can change more than one variable in a for loop
end

En ese ejemplo, el hardware resultante será una cadena de sumadores, que suma los valores de cuatro índices de matriz.

La clave es que no se pueden crear nuevas variables o módulos en un procedimiento para bucle. Esta regla se aplica a los bloques de procedimientos en general, no solo a los bucles (es decir, no se puede declarar una variable en un bloque de procedimientos).

Los bloques de generación, por otro lado, permiten la creación de variables y la creación de instancias de módulos. Eso significa que en un bloque de generación, puede usar un ciclo de generación de for para inferir módulos. Esa es prácticamente la única diferencia.

Para generar bucles, debe usar genvar como variable de bucle (es decir, el valor que usa para contar a través de cada bucle). También debes darle un nombre al bucle for:

for (loopVal = 0; loopVal < 4; loopVal = loopVal + 1) begin : loopName

Este nombre se añade a cualquier pieza de hardware que cree en el bucle. Entonces, si creas una instancia llamada bob , el bucle anterior crearía instancias:

loopName[0]|bob
loopName[1]|bob
loopName[2]|bob
loopName[3]|bob

Esto da como resultado múltiples instancias con nombres únicos.

Tanto la generación como el procedimiento de los bucles realizarán el desenrollado del bucle, como usted dice. La diferencia es simplemente cómo puedes usarlos. El procedimiento puede utilizarse en bloques de procedimiento (por ejemplo, para inicializar una memoria). Generar solo se puede utilizar en generar bloques.

Ambos son útiles y preferidos. Uno no puede reemplazar al otro.

    
respondido por el Tom Carpenter

Lea otras preguntas en las etiquetas