In this lab you will create a digital stopwatch. As shown in the video below, the stopwatch will be displayed on the eight-digit seven-segment display.
Read about the Seven Segment Controller module that is provided to you. The module cycles through the eight seven-segment digits, lighting up one at a time.
At the heart of your stopwatch will be a counter module for each of the eight digits. The counter should be a modulus counter, meaning it counts up to some predetermined value, then rolls over to 0 and continues counting.
You will use a SystemVerilog parameter, MOD_VALUE
to indicate the modulus value. The counter should reach (MOD_VALUE-1)
and then roll over to 0. This approach will allow us to use this module for digits that count 0-9, as well as digits that count 0-5. Consult the Parameterization in Dataflow SystemVerilog section in the textbook (Chapter 14) for an example on adding parameters to your SystemVerilog modules.
Module Name = mod_counter | |||
---|---|---|---|
Parameter | Default Value | Description | |
MOD_VALUE | 10 | Sets the modulus value of the counter. The counter will count from 0 up to (MOD_VALUE-1), then continue again at 0. | |
Port Name | Direction | Width | Description |
clk | Input | 1 | 100 MHz Input Clock |
reset | Input | 1 | Reset |
increment | Input | 1 | When high, increment the counter value on the next clock edge. |
rolling_over | Output | 1 | High when the counter is about to roll-over (increment is high and counter is at the maximum value). NOW, re-read the previous sentence carefully - it is NOT asserted just when the counter is at the maximum value. Do you see the difference? |
count | Output | 4 | The counter value |
What you need to do:
mod_counter
module.rolling_over
wrong the first time. Why? Go re-read the description for this signal above a third time. Exactly what is the logic condition for this signal? Does it involve the 'clk' signal and a register or is it purely combinational logic? If you put the code to generate this signal this inside an always_ff
block will it generate a register or will it generate combinational logic? What is it that you really want?increment
is high, and that the rolling_over
output is high only in the appropriate condition. Also, don't forget to do the Tcl file in this general order: a) set up the clocking, b) reset the design and simulate a few cycles, and then c) exercise the rest of your counter functionality.Include your Tcl simulation script in your lab report.
Pass-Off: Show the TA your simulation and explain how you tested the correctness of your module.
In this exercise you will create the stopwatch module which will consist of eight instances of your mod_counter
module . Each of these instances will be responsible for generating the value for one digit of the display. In addition, you will create one counter which will serve as a timer module to time the refreshing of your 7-segment display. The figure below shows the overall outline of your stopwatch
module.
Your stopwatch will contain eight copies of your mod_counter
. Each counter's rolling_over
output is fed into the increment
signal for the next most significant digit, as shown below. You will need to declare those intermediate signals as local signals in your SystemVerilog code.
Make sure you set the roll-over parameter for each of your mod_counter
instances. The most significant two digits represent minutes, and the next two digits represent seconds; both should roll over at 59. The lower four digits represent fractions of a second, and should behave accordingly.
Note the module in the upper left - this is a counter that rolls over every 0.0001s. When this counter rolls over, it should generate a single cycle pulse on its output. That pulse then is the input to the increment
signal for the least significant digit of the 8 digits. This 0.0001s counter should increment every cycle that the run
input is high, and reset to 0 if the reset
input is high (where reset takes precedence).
Given that the system clock is 100MHz, what value does your counter need to count to in order to roll over every 0.0001s?
To answer this question you should a) compute how long (in seconds) one clock period is for a 100MHz clock. Then calculate how many of those will fit into a 0.0001s interval. That is the maximum count value for this counter. Also, once you compute this you should then be able to calculate how many bits wide the counter should be. Remember: you can only count from 0-15 using 4-bits, to count from 0-1023 takes 10 bits, to count from 0-2047 takes 11 bits, and so on. Once you know the maximum count value and the number of bits for the counter, you can design it.
You have two ways to design this timer, you can choose which to use.
mod_counter
module. In fact, you could largely just copy the code and change the number of bits in the counter.mod_counter
module to be parameterized for width and then just instance another copy of it. Note that it already is parameterized with a MOD_VALUE
parameter for its maximum count. If you simply add a second parameter to parameterize number of bits for the counter signal you can then just instance another copy of your mod_counter
design for this timer
module. #(parameter PARAM1 = val1, PARAM2 = val2)
. mod_counter #(10, 495) TIMER (clk, run, …)
.
Now that you have all the blocks designed, create a stopwatch
module and instance all of the needed modules inside it.
Some things to remember:
timer
module output ('count') is not tied to anything. You will still need to declare a local signal for it to wire up to the timer
module, but that signal will not connect to anything else in your stopwatch
module.Module Name = stopwatch | |||
---|---|---|---|
Port Name | Direction | Width | Description |
clk | Input | 1 | 100 MHz Input Clock |
reset | Input | 1 | Active-high reset |
run | Input | 1 | High when timer should be running, 0 when stopped |
digit0 | Output | 4 | The value of the ten-thousandths of a second digit |
digit1 | Output | 4 | The value of the thousandths of a second digit |
digit2 | Output | 4 | The value of the hundredths of a second digit |
digit3 | Output | 4 | The value of the tenths of a second digit |
digit4 | Output | 4 | The value of the seconds digit |
digit5 | Output | 4 | The value of the tens of seconds digit |
digit6 | Output | 4 | The value of the minutes digit |
digit7 | Output | 4 | The value of the tens of minutes digit |
Create a tcl simulation script to simulate the behavior of your stopwatch
module. You will likely need to simulate for several milliseconds to check that the lower digits are functioning correctly. It will take too long to simulate the upper digits, so you will have to wait until next exercise to test it on the board. In your simulation, make sure to check that:
run
input is high.Include your Tcl simulation script in your lab report.
Include a screenshot of your simulation that verifies that it works.
Pass-Off: Nothing to pass off in person.
In this exercise you will create the top-level module and test your stopwatch on the board.
Create the top-level module as follows:
Module Name = stopwatch_top | |||
---|---|---|---|
Port Name | Direction | Width | Description |
clk | Input | 1 | 100 MHz Input Clock |
CPU_RESETN | Input | 1 | Active-low reset |
sw | Input | 1 | High when stopwatch should be running, 0 when stopped |
anode | Output | 8 | Seven-segment anode values, from Seven Segment Controller |
segment | Output | 8 | Seven-segment segment values, from Seven Segment Controller |
Your top module should:
stopwatch
module, as well as a SevenSegmentControl module.stopwatch
module to the dataIn
input of the SevenSegmentControl
.0
when pressed and a 1
otherwise. You will need to invert the signal when connecting it to your stopwatch
and SevenSegmentControl
modules.Be sure to include an appropriate constraints file:
clk
pin, you should also uncomment two lines near the top that refer to the clock. One connects the clock, the line after it tells informs Vivado that the clock runs at 100MHz.Exercise #3 Pass-off: Nothing for this.
Submit your SystemVerilog modules as part of the lab report on Learning Suite. (Make sure your SystemVerilog conforms to the lab SystemVerilog coding standards).
Attach a video (narrated) describing how your design operates. Time it to show that it really is counting seconds at the correct rate. Show how you can clear it at well and how you can start and stop it at will. Also, describe how long it will take for the counter to completely roll over and show that happening if it is feasible to do so.
How long (in hours) did you work on this lab?
List the pitfalls you encountered in this lab. What made it take longer than it should have (in your mind)?