4-bits teller
De 4-bits teller begint met ophogen van 4'b0000 tot 4'h1111 en gaat dan terug naar 4'b0000. Het blijft tellen zolang het is voorzien van een lopende klok en de reset hoog wordt gehouden.
De rollover vindt plaats wanneer het meest significante deel van de laatste toevoeging wordt weggegooid. Wanneer de teller de maximale waarde van 4'b1111 heeft en nog een telverzoek krijgt, probeert de teller 5'b10000 te bereiken, maar aangezien deze slechts 4-bits kan ondersteunen, wordt de MSB verwijderd, wat resulteert in 0.
0000 0001 0010 ... 1110 1111 rolls over 0000 0001 ...
Het ontwerp bevat twee ingangen, één voor de klok en één voor een active-low reset. Een active-low-reset is een reset waarbij het ontwerp wordt gereset wanneer de waarde van de reset-pin 0 is. Er wordt een 4-bits uitgang opgeroepen die in wezen de tellerwaarden levert.
Elektronisch toonbankontwerp
module counter ( input clk, // Declare input port for clock to allow counter to count up
input rstn, // Declare input port for reset to allow the counter to be reset to 0 when required
output reg[3:0] out); // Declare 4-bit output port to get the counter values
// This always block will be triggered at the rising edge of clk (0->1)
// Once inside this block, it checks if the reset is 0, if yes then change out to zero
// If reset is 1, then design should be allowed to count up, so increment counter
always @ (posedge clk) begin
if (! rstn)
out <= 0;
else
out <= out + 1;
end
endmodule
De module
teller heeft een klok en active-low reset (aangeduid met n ) als ingangen en de tellerwaarde als 4-bits uitgang. De always
blok is altijd uitgevoerd wanneer de klok overgaat van 0 naar 1, wat een stijgende flank of een positieve flank betekent. De output wordt alleen verhoogd als reset hoog wordt gehouden of 1, bereikt door de if-else
blok. Als de reset laag blijkt te zijn aan de positieve flank van de klok, wordt de output gereset naar een standaardwaarde van 4'b0000.
Testbank
We kunnen het ontwerp instantiëren in onze testbench-module om te controleren of de teller telt zoals verwacht.
De testbench-module heet tb_counter en poorten zijn niet vereist, aangezien dit de bovenste module in de simulatie is. We hebben echter interne variabelen nodig om de klok te genereren, op te slaan en aan te sturen en opnieuw in te stellen. Voor dat doel hebben we twee variabelen van het type reg
. gedeclareerd voor klok en reset. We hebben ook een wire
. nodig typ net om verbinding te maken met de uitvoer van het ontwerp, anders wordt het standaard een 1-bit scalair net.
Klok wordt gegenereerd via always
blok dat een periode van 10 tijdseenheden geeft. De initial
blok wordt gebruikt om initiële waarden in te stellen voor onze interne variabelen en de resetwaarde naar het ontwerp te sturen. Het ontwerp is geïnstantieerd in de testbench en verbonden met onze interne variabelen, zodat het de waarden krijgt wanneer we ze van de testbench halen. We hebben geen $display
uitspraken in onze testbench en daarom zullen we geen bericht in de console zien.
module tb_counter;
reg clk; // Declare an internal TB variable called clk to drive clock to the design
reg rstn; // Declare an internal TB variable called rstn to drive active low reset to design
wire [3:0] out; // Declare a wire to connect to design output
// Instantiate counter design and connect with Testbench variables
counter c0 ( .clk (clk),
.rstn (rstn),
.out (out));
// Generate a clock that should be driven to design
// This clock will flip its value every 5ns -> time period = 10ns -> freq = 100 MHz
always #5 clk = ~clk;
// This initial block forms the stimulus of the testbench
initial begin
// 1. Initialize testbench variables to 0 at start of simulation
clk <= 0;
rstn <= 0;
// 2. Drive rest of the stimulus, reset is asserted in between
#20 rstn <= 1;
#80 rstn <= 0;
#50 rstn <= 1;
// 3. Finish the stimulus after 200ns
#20 $finish;
end
endmodule
Simulatielogboek ncsim> run [0ns] clk=0 rstn=0 out=0xx [5ns] clk=1 rstn=0 out=0x0 [10ns] clk=0 rstn=0 out=0x0 [15ns] clk=1 rstn=0 out=0x0 [20ns] clk=0 rstn=1 out=0x0 [25ns] clk=1 rstn=1 out=0x1 [30ns] clk=0 rstn=1 out=0x1 [35ns] clk=1 rstn=1 out=0x2 [40ns] clk=0 rstn=1 out=0x2 [45ns] clk=1 rstn=1 out=0x3 [50ns] clk=0 rstn=1 out=0x3 [55ns] clk=1 rstn=1 out=0x4 [60ns] clk=0 rstn=1 out=0x4 [65ns] clk=1 rstn=1 out=0x5 [70ns] clk=0 rstn=1 out=0x5 [75ns] clk=1 rstn=1 out=0x6 [80ns] clk=0 rstn=1 out=0x6 [85ns] clk=1 rstn=1 out=0x7 [90ns] clk=0 rstn=1 out=0x7 [95ns] clk=1 rstn=1 out=0x8 [100ns] clk=0 rstn=0 out=0x8 [105ns] clk=1 rstn=0 out=0x0 [110ns] clk=0 rstn=0 out=0x0 [115ns] clk=1 rstn=0 out=0x0 [120ns] clk=0 rstn=0 out=0x0 [125ns] clk=1 rstn=0 out=0x0 [130ns] clk=0 rstn=0 out=0x0 [135ns] clk=1 rstn=0 out=0x0 [140ns] clk=0 rstn=0 out=0x0 [145ns] clk=1 rstn=0 out=0x0 [150ns] clk=0 rstn=1 out=0x0 [155ns] clk=1 rstn=1 out=0x1 [160ns] clk=0 rstn=1 out=0x1 [165ns] clk=1 rstn=1 out=0x2 Simulation complete via $finish(1) at time 170 NS + 0
Merk op dat de teller teruggaat naar 0 wanneer de actief-laag reset 0 wordt, en wanneer de reset wordt opgeheven rond 150ns, begint de teller te tellen vanaf het volgende optreden van de positieve flank van de klok.
Hardwareschema
Verilog