Industriële fabricage
Industrieel internet der dingen | Industriële materialen | Onderhoud en reparatie van apparatuur | Industriële programmering |
home  MfgRobots >> Industriële fabricage >  >> Industrial programming >> Verilog

Verilog voor Loop

Een for lus is de meest gebruikte lus in software, maar wordt voornamelijk gebruikt om te repliceren hardwarelogica in Verilog. Het idee achter een for lus is het herhalen van een reeks instructies die in de lus zijn gegeven, zolang de gegeven voorwaarde waar is. Dit lijkt erg op de while lus, maar wordt meer gebruikt in een context waar een iterator beschikbaar is en de voorwaarde afhankelijk is van de waarde van deze iterator.

Syntaxis

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

  

Het trefwoord for wordt gebruikt om dit type lus te specificeren en bestaat uit drie delen:

  1. Initiële voorwaarde om beginwaarden van signalen te specificeren
  2. Een controle om te evalueren of de gegeven voorwaarde waar is
  3. Controlevariabele bijwerken voor de volgende iteratie

De beginvoorwaarde en updates voor de controlevariabele zijn opgenomen in de for lus en hoeft niet apart te worden opgegeven in tegenstelling tot een while lus. Een while lus is meer algemeen bedoeld en wordt meestal alleen gebruikt wanneer de gegeven instructies moeten worden herhaald zolang een bepaalde voorwaarde. Maar de for lus heeft typisch een duidelijk begin en einde, bestuurd door de stapvariabele.

Hier is een eenvoudig voorbeeld dat het gebruik van een for-lus illustreert.

  
  
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

  
Simulatielogboek
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.

Ontwerpvoorbeeld

Laten we eens kijken hoe een 8-bits linkerschuifregister kan worden geïmplementeerd in Verilog zonder een for loop en vergelijk het dan met de code met behulp van een for loop alleen maar om het nut van een looping-constructie te waarderen.

  
  
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

  

Hetzelfde gedrag kan worden geïmplementeerd met een for lus die de code verkleint en schaalbaar maakt voor verschillende registerbreedtes. Als de breedte van het register een Verilog-parameter wordt, wordt de ontwerpmodule schaalbaar en kan dezelfde parameter worden gebruikt in de for lus.

  
  
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

  

Testbank

De testbench-code wordt hieronder weergegeven en geeft het ontwerp aan.

  
  
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

  

Verilog

  1. Inleiding tot Verilog
  2. C# voor lus
  3. C# foreach-lus
  4. C++ voor Loop
  5. Armstrong-nummer in JAVA-programma met For Loop
  6. Verilog-zelfstudie
  7. Verilog-aaneenschakeling
  8. Verilog-opdrachten
  9. Verilog blokkeren en niet-blokkeren
  10. Verilog-functies
  11. Verilog-taak