Manufactura industrial
Internet industrial de las cosas | Materiales industriales | Mantenimiento y reparación de equipos | Programación industrial |
home  MfgRobots >> Manufactura industrial >  >> Industrial programming >> Verilog

Verilog para bucle

Un for loop es el loop más utilizado en el software, pero se usa principalmente para replicar lógica de hardware en Verilog. La idea detrás de un for loop es iterar un conjunto de declaraciones dadas dentro del ciclo siempre que la condición dada sea verdadera. Esto es muy similar al while loop, pero se usa más en un contexto donde hay un iterador disponible y la condición depende del valor de este iterador.

Sintaxis

  
  
	for (<initial_condition>; <condition>; <step_assignment>) begin
		// Statements
	end

  

La palabra clave for se utiliza para especificar este tipo de bucle y consta de tres partes:

  1. Condición inicial para especificar valores iniciales de señales
  2. Una verificación para evaluar si la condición dada es verdadera
  3. Actualizar la variable de control para la próxima iteración

La condición inicial y las actualizaciones de la variable de control se incluyen en el for bucle y no es necesario que se especifique por separado a diferencia de un while círculo. Un while loop tiene un propósito más general y se usa principalmente solo cuando se requiere que las declaraciones dadas se repitan mientras se cumpla una condición dada. Sin embargo, el for el bucle normalmente tiene un comienzo y un final definidos controlados por la variable de paso.

Aquí hay un ejemplo simple que ilustra el uso de un ciclo for.

  
  
module my_design;
	integer i;
	
	initial begin
		// Note that ++ operator does not exist in Verilog !
		for (i = 0; i < 10; i = i + 1) begin
			$display ("Current loop#%0d ", i);
		end
	end
endmodule

  
Registro de simulación
ncsim> run
Current loop#0 
Current loop#1 
Current loop#2 
Current loop#3 
Current loop#4 
Current loop#5 
Current loop#6 
Current loop#7 
Current loop#8 
Current loop#9 
ncsim: *W,RNQUIE: Simulation is complete.

Ejemplo de diseño

Echemos un vistazo a cómo se puede implementar un registro de desplazamiento a la izquierda de 8 bits en Verilog sin un for loop y luego compararlo con el código usando un for bucle solo para apreciar la utilidad de una construcción de bucle.

  
  
module lshift_reg (input 						clk,				// Clock input
                   input 						rstn,				// Active low reset input
                   input [7:0] 			load_val, 	// Load value 
                   input 						load_en, 		// Load enable
                   output reg [7:0] op); 				// Output register value

	 // At posedge of clock, if reset is low set output to 0
	 // If reset is high, load new value to op if load_en=1
	 // If reset is high, and load_en=0 shift register to left
	 always @ (posedge clk) begin
	    if (!rstn) begin
	      op <= 0;
	    end else begin
	    	if (load_en) begin
	      	op <= load_val;
	      end else begin
	        op[0] <= op[7];
	        op[1] <= op[0];
	        op[2] <= op[1];
	        op[3] <= op[2];
	        op[4] <= op[3];
	        op[5] <= op[4];
	        op[6] <= op[5];
	        op[7] <= op[6];
	      end
	    end
	  end
endmodule

  

El mismo comportamiento se puede implementar usando un for bucle que reducirá el código y lo hará escalable para diferentes anchos de registro. Si el ancho del registro se convierte en un parámetro de Verilog, el módulo de diseño se volverá escalable y el mismo parámetro se puede usar dentro del for bucle.

  
  
module lshift_reg (input 						clk,				// Clock input
                   input    				rstn,				// Active low reset input
                   input [7:0] 			load_val, 	// Load value 
                   input 						load_en, 		// Load enable
                   output reg [7:0] op); 				// Output register value

	 integer i;
	 
	 // At posedge of clock, if reset is low set output to 0
	 // If reset is high, load new value to op if load_en=1
	 // If reset is high, and load_en=0 shift register to left
	 always @ (posedge clk) begin
	    if (!rstn) begin
	      op <= 0;
	    end else begin
	    
	    	// If load_en is 1, load the value to op
	    	// else keep shifting for every clock
	    	if (load_en) begin
	      	op <= load_val;
	      end else begin
            for (i = 0; i < 8; i = i + 1) begin
              op[i+1] <= op[i];
            end
            op[0] <= op[7];
	      end
	    end
	  end
endmodule

  

Banco de pruebas

El código del banco de pruebas se muestra a continuación e instancia el diseño.

  
  
module tb;
  reg clk;
  reg rstn;
  reg [7:0] load_val;
  reg load_en;
  wire [7:0] op;
  
  // Setup DUT clock
  always #10 clk = ~clk;
  
  // Instantiate the design
  lshift_reg u0 ( .clk(clk),
                 .rstn (rstn),
                 .load_val (load_val),
                 .load_en (load_en),
                 .op (op));
  
  initial begin
  	// 1. Initialize testbench variables
    clk <= 0;
    rstn <= 0;
    load_val <= 8'h01;
    load_en <= 0;
    
    // 2. Apply reset to the design
    repeat (2) @ (posedge clk);
    rstn <= 1;
    repeat (5) @ (posedge clk);
    
    // 3. Set load_en for 1 clk so that load_val is loaded
    load_en <= 1;
    repeat(1) @ (posedge clk);
    load_en <= 0;
    
    // 4. Let design run for 20 clocks and then finish
    repeat (20) @ (posedge clk);
    $finish;
  end
endmodule

  
hardware schematic for shift register

Verilog

  1. Introducción a Verilog
  2. C# para bucle
  3. Bucle foreach de C#
  4. C++ para bucle
  5. Número de Armstrong en el programa JAVA utilizando For Loop
  6. Tutorial de Verilog
  7. Concatenación Verilog
  8. Asignaciones de Verilog
  9. Bloqueo y no bloqueo de Verilog
  10. Funciones de Verilog
  11. Tarea Verilog