I am at the very beginning of Learning VHDL and I am have a lot of insecurity on how to procede.
I am not sure if I am doing it right or if there is something wrong because my understanding of the topic is still very partial. I am trying to learn.
MY PROBLEM:
I am trying to make a pulse counter in VHDL with:
I need to count the number of pulses (counting rising edges) that appear at the Pulse_In input. On the Pulse_sec output, I will have the number of pulses in one seconds, while on Pulse_min, the number of pulses in the last minute. And the output needs to be updated at the end of every second.
MY ATTEMPT (MAYBE WRONG I DO NOT KNOW):
-- clock --
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity clock_gen is
port(clock: out bit);
end entity
architecture behav of clock_gen is
constant frequency: integer:= 1000;
constant period: time:= 1000ms/frequency;
begin
clock: process
begin
clock <= ‘0’,’1’ after period/2;
wait for period;
end process clock;
end architecture;
-- counter --
entity PulseCounter is
port(Pulse_in: in bit;
Clock: in bit;
Pulse_sec, Pulse_min: out integer range 15 to 0);
end entity
architecture my_counter of PulseCounter is
begin
process
var seconds: integer:=0;
begin
if (Clock='1' and Clock'last_value='0') then
if (Pulse_in='1' and seconds/=59) then
Pulse_sec = Pulse_sec + 1;
Pulse_min = Pulse_min + Pulse_sec;
seconds = seconds + 1;
end if;
end if;
wait on Clock;
end process;
end architecture;
-- I am not sure if the entity is correct, given the data above --
-- I do not know if my process is correct --
When writing vhdl you have the actual entity that you want to write and a "testbench" for that entity. The testbench is another vhdl entity with the only purpose to act as a test environment for the entity that you want to write. Without the testbench you end up asking questions like this on SO because you do not have a way of verifying yourself if your design does what it is supposed to do.
The part of your attempt that generates the clock belongs into the testbench entity since in a real-world example the clock is supplied by some oscillator to the FPGA/ASIC where your vhdl design is implemented. In the testbench entity, you only simulate the existence of this clock. Statements like "period: time:= 1000ms/frequency;" and "clock <= ‘0’,’1’ after period/2;" will not be synthesisable since there is no concept of "1000ms" anymore once you want to actually implement this in an FPGA/ASIC. (synthesisable vhdl is a subset of legal vhdl. In testbenches you can use everything that is legal vhdl since it will never be implemented on a device. For the entity under test you should stick to synthesisable vhdl)
You should start with 2 separate files. The testbench and your PulseCounter
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity my_counter_tb is
end entity;
architecture rtl of my_counter_tb is
constant frequency: integer:= 1000;
constant period: time:= 1000 ms/frequency;
signal clock : std_logic := '0';
signal Pulse_in : std_logic;
signal Pulse_sec, Pulse_min : std_logic_vector(15 downto 0);
begin
label_that_is_not_clock_since_clock_is_already_a_signal: process
begin
clock <= '0','1' after period/2;
wait for period;
end process;
pulsecounter_inst: entity work.PulseCounter
port map (
Pulse_in => Pulse_in,
Clock => Clock,
Pulse_sec => Pulse_sec,
Pulse_min => Pulse_min
);
-- write a process here that does something with Pulse_in
end architecture;
and
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity PulseCounter is
port(Pulse_in: in std_logic;
Clock: in bit;
Pulse_sec, Pulse_min: out integer range 15 to 0);
end entity;
architecture rtl of PulseCounter is
begin
-- your counter implementation
end architecture;
Then you plug these two files into some vhdl simulator and can test the behaviour of your vhdl design yourself, find out where the syntax errors are and so on. (For example Modelsim, ghdl, Questa, Aldec, edaplayground, ... whatever is used in your class)
A few obvious problems with your code from above: