avr-gcc-list
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [avr-gcc-list] generic queue library for AVR GCC?


From: David Brown
Subject: Re: [avr-gcc-list] generic queue library for AVR GCC?
Date: Tue, 16 Nov 2004 10:36:07 +0100

> Bruce D. Lightner wrote:
>
> >
> > How about this...
> >
> >     #include <avr/io.h>
> >     #include <avr/interrupt.h>
> >     #include <inttypes.h>
> >     #define begin_critical_section()  SREG; cli()
> >     #define end_critical_section(val) SREG = val
> >     ....
> >     {
> >         unsigned char sreg = begin_critical_section();
> >         sm_qin = sm_qout = 0;   // reset queue pointers
> >         end_critical_section(sreg);
> >     }
> >
> > This gets you the same, optimally efficient AVR code.
>
> but be careful
> this will not work:
>
>         unsigned char cr;
>         if (bSomeFlag) cr = begin_critical_section();
>         sm_qin = sm_qout = 0;   // reset queue pointers
>         if (bSomeFlag) end_critical_section(cr);
>
> cli() will get executed even if bSomeFlag is 0.
> maybe an inline function will do the job.

Yes, an inline function would work fine:
    static inline unsigned char begin_critical_section(void) {
        unsigned char s = SREG;
        cli();
        return SREG;
    }

In modern C programming, you should normally use static inline functions
rather than macros - they provide far better type and syntax checking, and
you can avoid such intensly ugly hacks such as "do { ... } while (0)" fake
loops.

Additionally, it makes sense to impose some basic rules in your C
programming as workarounds for some of the more idiotic "features" of C,
such as by always including scope brackets in if statements:

    if (bSomeFlags) {
        cr = begin_critical_section();
    }

A few extra brackets don't do any harm - and they can avoid such
hard-to-spot errors.


>
> -Bjarne
>





reply via email to

[Prev in Thread] Current Thread [Next in Thread]