Re: Problem with simple VHDL piece of code
- From: Jonathan Bromley <jonathan.bromley@xxxxxxxxxxxxx>
- Date: Thu, 12 Jul 2007 21:14:15 +0100
On Thu, 12 Jul 2007 11:18:18 -0700, Jaco
Naude <naude.jaco@xxxxxxxxx> wrote:
I'm wondering if any VHDL expert out there can tell me why the
following piece of code isn't working. It should be a simple clock
divider, enabling the CE signal on every counter'th pulse. However the
counter increase line counter := 1+ counter does not increment the
variable. If I change the 1 to for example 20 it stays 20 throughout
the simulation. I'm sure the input signals are correct... Any
suggestions would be helpful.
I'm fairly sure that it's the <= comparisons that are breaking
your design, but while we have the code in front of us there
are a few design style issues that might be worth pursuing.
Would it be fair to guess that you are by habit a software
person, moving into hardware? :-)
process (clk)
variable counter : integer :=0;
Initialisation doesn't usually work in hardware. Better
to use an explicit reset of some kind (as you have done).
begin
if (clk'event and clk = '1') then
counter_out <= counter;
I'm guessing this is just a diagnostic output, so that you
can easily see what "counter" is doing? Note that it lags
behind "counter" by one clock cycle.
if rst <= '1' then
counter := 0;
ce_out <= '1';
end if;
OK. Synchronous reset; I'm sure that's what you intended,
but it's worth checking...
if start <= '1' and rst <= '0' then
if rst='1' then
....reset actions
elsif start='1' then
....main code body
end if
would perhaps have been neater, and easier to follow.
if counter < counter_top + 1 then
Again I'm guessing. counter_top is an incoming signal, perhaps
the contents of a writeable register? This comparison is rather
expensive in hardware, since you are building an incrementer
and a magnitude comparator. For dividers like this, it's
almost always better to preset the counter to the limit
value and then count it down until it reaches a constant
(1 or 0, in most situations).
ce_out <= '0';
counter := 1 + counter;
Are you happy for ce_out to freeze at '1' if someone drops the
'start' signal at an inopportune moment? It may be better to
default ce_out to '0' and set it to '1' only for a single clock
when the wraparound occurs.
else
counter := 0;
ce_out <= '1';
end if;
else
ce_out <= '1';
end if;
end if;
end process;
Finally, your integer counter seems to be unconstrained;
consequently, it will probably be synthesised to 32 bits.
There are various opinions about this, but my own practice
is always to use the numeric_std UNSIGNED or SIGNED vector
types rather than integers.
If I take all my own advice, I end up with something like
this:
constant counter_bits: positive := 16; -- or maybe a generic
signal counter_top: unsigned(counter_bits-1 downto 0);
signal ce_out, start, rst: std_logic;
....
process (clk)
variable counter: unsigned(counter_top'range);
begin
if rising_edge(clk) then
ce_out <= '0';
if rst = '1' then
ce_out <= '1';
counter := counter_top;
elsif start = '1' then
if counter = 0 then
ce_out <= '1';
counter := counter_top;
else
counter := counter - 1;
end if;
end if;
end process;
Note that this generates ce_out with a period of
(counter_top + 1) cycles. If you want the period
to be exactly (counter_top) then you should test
"if counter=1" for the wraparound. The limit
comparator is now trivial, and involves no arithmetic.
Also, note that ce_out will be asserted for the whole
time that rst is asserted. If you don't want that, it
might be better to reset the counter to 1 so that ce_out
is asserted on the first clock after reset is released.
I hope it's clear from the above that you have a lot of
choices, and my suggestions may or may not be useful
depending on what else is happening in your system.
HTH
--
Jonathan Bromley, Consultant
DOULOS - Developing Design Know-how
VHDL * Verilog * SystemC * e * Perl * Tcl/Tk * Project Services
Doulos Ltd., 22 Market Place, Ringwood, BH24 1AW, UK
jonathan.bromley@xxxxxxxxxxxxx
http://www.MYCOMPANY.com
The contents of this message may contain personal views which
are not the views of Doulos Ltd., unless specifically stated.
.
- Follow-Ups:
- Re: Problem with simple VHDL piece of code
- From: Andy
- Re: Problem with simple VHDL piece of code
- From: Jonathan Bromley
- Re: Problem with simple VHDL piece of code
- References:
- Problem with simple VHDL piece of code
- From: Jaco Naude
- Problem with simple VHDL piece of code
- Prev by Date: Re: Problem with simple VHDL piece of code
- Next by Date: Re: Problem with simple VHDL piece of code
- Previous by thread: Re: Problem with simple VHDL piece of code
- Next by thread: Re: Problem with simple VHDL piece of code
- Index(es):
Relevant Pages
|