FPGARelated.com
Forums

Jumps in FPGA implemented integrator

Started by Helen October 26, 2006
Hello

I am fairly new to this FPGA game, and well am having a few teething
problems with my code.  I am using an Actel ProAsic Plus Evaluation
board.

I am trying to clock in a single bit stream (called compout) at 8MHz
(clock on global clock line), and then put the bit stream through a
comb decimation filter to eventually get it to 8 bit, 125kHz data.
However, at the integrator stage of the code (which is at 8MHz), I get
jumps in the output (combacc, read out using a DAQ card on the falling
edge of the 8MHz clock), because I am only adding or subtracting 1 in
this integrator, it is a clocked process, and relatively slow (at 8MHz)
I am at a bit of a loss as to what could be causing jumps of 2, 4 and
sometimes 50 or 60 - not all power of 2) in combacc.  combacc is a
signed, 8 bit signal, which I transfer into a std_logic_vector to be
read out.

process (Clk8MHz) is
begin
  if rising_edge(Clk8MHz) then
    feedbackbit<=compout;
    if compout ='1' then
         combacc1<=combacc1 + 1;
    else
         combacc1<=combacc1 - 1;
    end if;
  end if;
end process;

Interestingly, if I remove the else clause from the process (so 1 is
added if compout is 1, but nothing happens if compout is 0) then I
don't get the jump problem - but this causes problems for me further
down the line, so I would really like to be able to add or subtract 1
at this stage!

I don't get the problem when I use the simulator on the code
(pre-synthesis), and the timing analysis tells me (i think) that the
addition/subtraction only takes 30nS (much less than 1/2 an 8MHz clock
period of 62nS), so I don't think it can be a timing problem?

Any ideas would be gratefully received, 

Cheers
Helen

Hi,

Helen schrieb:

> I am fairly new to this FPGA game, and well am having a few teething
[..]
> I am trying to clock in a single bit stream (called compout) at 8MHz
[..]
> process (Clk8MHz) is > begin > if rising_edge(Clk8MHz) then > feedbackbit<=compout; > if compout ='1' then > combacc1<=combacc1 + 1; > else > combacc1<=combacc1 - 1;
Am I right, that compout is driven from outside the fpga without having a register between the input pin and the counter? Then you have a timing problem as compout may be switching from 0 to 1 or vice versa while calculating combacc1. This will lead to situations where some of you register think they have to add and some think they have to subtract at the rising clock edge. This could be easily overcome by clocking in compout (and any other input) before using it. if rising_edge(Clk8MHz) then compout_reg <= compout; if compout_reg='1' then ..... would be the simplest sollution. In general it would be better to use at least a two stage shift register at each asynchronous input either from outside the fpga or from different clock domains. bye Thomas
Thomas,

Many thanks for your input!  Yes you are right, compout is driven
outside the FPGA and is not synchronous.  I have tried out your
suggestion (see below), and it does definitely improve things (removes
most of the jumps :-), but I still have something going wrong as there
are still some occasional jumps in the data.  I have staggered the
integrator sum to a falling edge of the clock. (see below).  Is this
what you meant by 2-stage shift register?  Is there anything else I can
try?

sigdelfeedback: process (Clk8MHz) is
begin
  if rising_edge(Clk8MHz) then
    feedbackbit<=compout;
  end if;
end process sigdelfeedback;

integrator: process (Clk8MHz) is
begin
  if falling_edge(Clk8MHz) then
    if feedbackbit ='1' then
         combacc1<=combacc1 + 1;
    else
         combacc1<=combacc1 - 1;
    end if;
  end if;
end process integrator;

Thanks again, 
Helen

Hi Helen,

Helen schrieb:
> Many thanks for your input! Yes you are right, compout is driven > outside the FPGA and is not synchronous. I have tried out your > suggestion (see below), and it does definitely improve things (removes > most of the jumps :-), but I still have something going wrong as there > are still some occasional jumps in the data. I have staggered the > integrator sum to a falling edge of the clock. (see below). Is this > what you meant by 2-stage shift register?
No *g*
> Is there anything else I can > try?
Yes. Two stage shift register means two FF in serial clocking in the signal with your clock and you use the 2nd register. This should do for most cases, but could be improved by using 3 FF (as below). process (Clk, Rst) signal Compout_Reg_Sr : std_ulogic_vector(2 downto 0); -- shift if Rst=RESET_ACTIVE then Compout_Sr <= (others => '0'); -- all bits to '0' elsif Rising_edge(Clk) then Compout_Sr <= Compout_Sr(1 downto 0) & Compout; if Compout_Sr(2)='1' then -- do something end if; end if; This helps you eliminating effects of metastability (should be no problem for a 8MHz clk anyway), and allows you to have stable signal crossings between two timing domains. You should use such technique for every asynchronous signal when changeing clock domains. bye Thomas
Thanks Thomas - I will try this!

This is clearly Metastabilty issue. Thomas is correct.
I was also having such kind of problem.
There is an interesting article in cadence on Metastability & Cross
Clock domain.
If you have time, go through it
http://www.cadence.com/whitepapers/cdc_wp.pdf

Regards,
Krishna Janumanchi


Helen wrote:
> Thanks Thomas - I will try this!
krishna.janumanchi@gmail.com schrieb:

> This is clearly Metastabilty issue. Thomas is correct. > I was also having such kind of problem. > There is an interesting article in cadence on Metastability & Cross > Clock domain. > If you have time, go through it > http://www.cadence.com/whitepapers/cdc_wp.pdf
Just to be clearl I expect this to be _no_ metastability problem. APA at 8 MHz needs extrem curios HW to have any issue regarding metastability. As a rule of thumb which is valid for any actual devices from Actel (and which I would also use for any other Fpgas), you could say that 1 ns settling time is enough to say that this device will have no more than _one_ effect due to metastability before it crumbles to dust. The problem is a timing issue regarding asynchronous inputs. The only point I said, is that a circuitry removing this timing issue for sure also removes the problem of metastability [1]. In fact it is enough to guarantee that each input feeds only one FF, but as some synthesiser uses register doubling for load balancing, it is not enough to have only one FF in rtl, so it is safe to use 2-3 serial FF in rtl to be safe against doubling of the FF at the input. bye Thomas [1] To be precise it can't be fully removed, but i consider MTBF
>10^100 years as safe enough to use the term "removed" under any reasonable circumstances.
thanks both for your input,

Thomas's 2-stage shift register seems to have fixed the jumping problem
 :)

krishna.janumanchi@gmail.com wrote:
> This is clearly Metastabilty issue. Thomas is correct. > I was also having such kind of problem. > There is an interesting article in cadence on Metastability & Cross > Clock domain. > If you have time, go through it > http://www.cadence.com/whitepapers/cdc_wp.pdf > > Regards, > Krishna Janumanchi > > > Helen wrote: > >>Thanks Thomas - I will try this! > >
No, in fact I'd say clearly not a metastability problem, rather a race condition caused by an async input going to more than one flip-flop. The only way to get metastability to consistently show up is to force the issue by having a synchronous system with a delay between flip-flops that is exactly adjusted to land the output transition of the first flip flop right at the very small metastability window of the second flip-flop. In a system with a matastability problem at an input or otherwise crossing clock domains, using modern FPGAs, you are likely not going to see any evidence of a metastability in the lab, and even if you do, you are not likely to repeat it sufficiently frequently to observe it. The problem is surely a synchronization issue. If you have an asynchronous input to a synchronous machine feeding more than one flip-flop in the machine, unless the delay from the input to every flip-flop, as well as the delay of the clock to each flip-flop it feeds is precisely matched (impossible to do), then there is some point where a change in the input is detected on different clock cycles by the two flip-flops. For example, consider a simple system where an async signal is just fed to the D inputs of two flip-flops. The flip flops are clocked by a clock signal with a period of 10ns. Assume the clocks arrive at both flip-flops at the same instant. The delay from the input to the first flip flop is 4ns, and the delay from the async input to the second flip-flop is 6ns. If the input changes within 4ns before or after the clock edge, both flip-flops will register the change on the same clock. However, if the input changes 5ns after the clock edge, it will arrive at the first flip-flop just before the next clock edge, but will arrive at the second flip-flop just AFTER the next clock edge. The result is the first flip-flop changes a clock ahead of the second flip-flop. The same effect happens if the input delays are identical but the clock is delayed to one of the flip-flops relative to the other. For an asynchronous input, there is no set relationship of the arrival of the input change to the timing of the clock pulse, so eventually you will have a case like the one described above where two flip-flops sense the same input event on different clock edges. The only way to avoid that is to ensure that any asynchronous event is sensed by one, and only one flip-flop in the design. The usual approach is to synchronize the event using a flip-flop and then distributing that synchronized event rather than the event itself to the rest of the design. Special care has to be taken with asynchronous inputs that are more than one bit wide, as such an input feeds more than one flip flop by definition. In that case, you need to use hold the data stable while a strobe signal is used to signal the arrival of good data to the system and then transfer that latched good data.
I agree with Ray, and since I had just posted a longish explanation of
the same subject, please allow me to copy it here:

To paraphrase Karl Marx:
A spectre is haunting this newsgroup, the spectre of metastability.
Whenever something works unreliably, metastability gets the blame. But
the problem is usually elsewhere.

Metastability causes a non-deterministic extra output delay, when a
flip-flop's D input changes asynchronously, and happens to change
within an extremely narrow capture window (a tiny fraction of a
femtosecond !). This capture window is located at an unknown (and
unstable) point somewhere within the set-up time window specified in
the data sheet. The capture window is billions of times smaller than
the specified set-up time window. The likelihood of a flip-flop going
metastable is thus extremely small. The likelihood of a metastable
delay longer than 3 ns is even less.
As an example, a 1 MHz asynchronous signal, synchronized by a 100 MHz
clock, causes an extra 3 ns delay statistically once every billion
years. If the asynchronous event is at 10 MHz, the 3 ns delay occurs
ten times more often, once every 100 million years.
But a 2.5 ns delay happens a million times more often !
See the Xilinx application note XAPP094
You should worry about metastability only when the clock frequency is
so high that a few ns of extra delay out of the synchronizer flip-flop
might causes failure. The recommended standard procedure,
double-synchronizing in two close-by flip-flops, solves those cases.
Try to avoid clocking synchronizers at 500 MHz or more...
So much about metastability.

The real cause of problems is often the typical mistake, when a
designer feeds an asynchronous input signal to more than one
synchronizer flip-flop in parallel, (or an asynchronous byte to a
register, without additional handshake) in the mistaken believe that
all these flip-flops will synchronize the input on the same identical
clock edge.
This might work occasionally, but sooner or later subtle difference in
routing delay or set-up times will make one flip-flop use one clock
edge, and another flip-flop use the next clock edge. Depending on the
specific design, this might cause a severe malfunction.
Rule #1: Never feed an asynchronous input into more than one
synchronizer flip-flop. Never ever.

Peter Alfke
==============================
On Oct 30, 7:45 am, Ray Andraka <r...@andraka.com> wrote:
> krishna.januman...@gmail.com wrote: > > This is clearly Metastabilty issue. Thomas is correct. > > I was also having such kind of problem. > > There is an interesting article in cadence on Metastability & Cross > > Clock domain. > > If you have time, go through it > >http://www.cadence.com/whitepapers/cdc_wp.pdf > > > Regards, > > Krishna Janumanchi > > > Helen wrote: > > >>Thanks Thomas - I will try this!No, in fact I'd say clearly not a metastability problem, rather a race > condition caused by an async input going to more than one flip-flop. > The only way to get metastability to consistently show up is to force > the issue by having a synchronous system with a delay between flip-flops > that is exactly adjusted to land the output transition of the first flip > flop right at the very small metastability window of the second > flip-flop. In a system with a matastability problem at an input or > otherwise crossing clock domains, using modern FPGAs, you are likely not > going to see any evidence of a metastability in the lab, and even if you > do, you are not likely to repeat it sufficiently frequently to observe it. > > The problem is surely a synchronization issue. If you have an > asynchronous input to a synchronous machine feeding more than one > flip-flop in the machine, unless the delay from the input to every > flip-flop, as well as the delay of the clock to each flip-flop it feeds > is precisely matched (impossible to do), then there is some point where > a change in the input is detected on different clock cycles by the two > flip-flops. > > For example, consider a simple system where an async signal is just fed > to the D inputs of two flip-flops. The flip flops are clocked by a > clock signal with a period of 10ns. Assume the clocks arrive at both > flip-flops at the same instant. The delay from the input to the first > flip flop is 4ns, and the delay from the async input to the second > flip-flop is 6ns. If the input changes within 4ns before or after the > clock edge, both flip-flops will register the change on the same clock. > However, if the input changes 5ns after the clock edge, it will arrive > at the first flip-flop just before the next clock edge, but will arrive > at the second flip-flop just AFTER the next clock edge. The result is > the first flip-flop changes a clock ahead of the second flip-flop. The > same effect happens if the input delays are identical but the clock is > delayed to one of the flip-flops relative to the other. > > For an asynchronous input, there is no set relationship of the arrival > of the input change to the timing of the clock pulse, so eventually you > will have a case like the one described above where two flip-flops sense > the same input event on different clock edges. The only way to avoid > that is to ensure that any asynchronous event is sensed by one, and only > one flip-flop in the design. The usual approach is to synchronize the > event using a flip-flop and then distributing that synchronized event > rather than the event itself to the rest of the design. > > Special care has to be taken with asynchronous inputs that are more than > one bit wide, as such an input feeds more than one flip flop by > definition. In that case, you need to use hold the data stable while a > strobe signal is used to signal the arrival of good data to the system > and then transfer that latched good data.