Re: Shared Data Problem

From: Lanarcam (lanarcam1_at_yahoo.fr)
Date: 03/19/05


Date: 19 Mar 2005 11:05:11 -0800

Ian Bell wrote:
> Lanarcam wrote:
> >
> > An alternative:
> > There is no problem when the ISR writes a variable whose size is
equal
> > to the data bus length (word). In this case you can perform an
atomic
> > read in a background task. (supposing no virtual memory)
>
> That's fine as long as there is no need to indicate to the background
that
> there is new data. In that case the ISR also needs to set a flag
(signal)
> that there is new data. The background checks the flag and if there
is new
> data, reads it and *finally* resets the flag. Similarly the ISR needs
to
> check the flag before updating the data and reseting the flag.

A counter can be used to signal new data. the background task does not
need to modify the counter. This works of course if the background task
runs periodicaly or constantly. If the background task is suspended
you must signal new data by using a semaphore or an equivalent.

> This means the ISR can detect when data will be lost because the
> background has not
> read it. To avoid this you can use a queue with head and tail
pointers
> instead of the flag.

I agree with your solution, but it depends on the needs of the
application.
If you must ensure no data is ever lost, the queue is necessary.
On the other hand if you have real time constraints, you must sometimes
read the most recent data. In this case you are better off without
a queue. Otherwise you need to time stamp your data.

> > There is a problem when the ISR updates two or more words. There
you
> > can devise a protocol, such as:
> > The ISR updates the data structure and then increments a counter
> > (word).
> > the background task reads the counter, reads the data structure and
> > reads the counter again.
> > If both readings of the counter yield the same result the operation
> > was successful. Otherwise start again.
>
> You need to take care not to start again too much but again a queue
can
> avoid this.
>

It depends on the timing of the interrupt. If the interrupt is
periodic you should need to start again once at most.

If the interrupt is sporadic the ISR must check for new data before
reenabling the interrupt. If interrupts occur too frequently the
system should be designed to take care of that.

Anyhow I agree again that a queue is unavoidable when the sequence
of data is critical. This is the case in data acquisition systems
such as RTUs. But for control equipment where timing is critical
you cannot use old data. In this case the sytem must be designed
in order to avoid tasks delays. Rate monotonic scheduling can be
used for that purpose.



Relevant Pages

  • Re: writing ISR for UART
    ... i add "case" in side ISR? ... most compilers have an _interrupt_ keyword or similar ... so if the interrupt handler adds a character to the queue while ... c)The interrupt runs and overwrites the character that was to be retrieved. ...
    (comp.arch.embedded)
  • Re: writing ISR for UART
    ... i add "case" in side ISR? ... most compilers have an _interrupt_ keyword or similar ... so if the interrupt handler adds a character to the queue while ... c)The interrupt runs and overwrites the character that was to be retrieved. ...
    (comp.arch.embedded)
  • Re: PCI interrupt response time
    ... Because of PCI interrupt nature, ... your ISR will only be entered once. ... >>together it is possible that you queue a DPC and before the DPC is run ...
    (microsoft.public.win32.programmer.kernel)
  • Re: PCI interrupt response time
    ... >together it is possible that you queue a DPC and before the DPC is run ... >the next interrupt occurs and you attempt to insert it on the DPC ... separate DPCs and not do any of the copying in the ISR (as Slobodan ...
    (microsoft.public.win32.programmer.kernel)
  • Re: Shared Data Problem
    ... >> if the ISR that also changes it occurs part way through the access. ... > interrupts around the non-atomic variable access. ... read in a background task. ... The ISR updates the data structure and then increments a counter ...
    (comp.arch.embedded)