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

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

RE: [avr-gcc-list] volatile...


From: Eric Weddington
Subject: RE: [avr-gcc-list] volatile...
Date: Thu, 14 Dec 2006 09:01:41 -0700

 

> -----Original Message-----
> From: 
> address@hidden 
> [mailto:address@hidden
> org] On Behalf Of Larry Barello
> Sent: Thursday, December 14, 2006 7:43 AM
> To: address@hidden; address@hidden
> Subject: RE: [avr-gcc-list] volatile...
> 
> This is somewhat a compiler issue since it is both a 
> necessary keyword, yet
> insufficient to write correct code.  It is a problem that vexes many
> newcomers (and old farts like me who forget every now and then) and is
> discussed in the FAQ, but is worth burning space here as well.
> 
> The GCC compiler is very smart.  Global or local (e.g. 
> static) variables are
> stuffed into SRAM.  In a function the compiler will often 
> read the variable
> into registers and work on it there, stuffing it back out to 
> SRAM later on.
> Depending upon the routine, e.g. a forever() loop in main(), 
> it may *never*
> write it back.
> 
> This model, although very efficient, breaks if you have an 
> interrupt handler
> asynchronously modifying the same variable while it is in 
> registers in the
> function.
> 
> The "volatile" keyword tells the compiler that *every* access to the
> variable has to be done in place, no caching or optimization. 
>  A related,
> but very important, is protecting the operation on the 
> variable with cli/sei
> instructions.  Access and operations typically take multiple 
> instructions.
> e.g. foo++;  Takes three or more instructions.  If the 
> interrupt handler
> interrupts between the read & write, well, bad things happen.  So, in
> reality not only do you have to say "volatile" you must also protect
> operations with the cli/sei instruction.  
 
This is an explanation. There is one other area that explains the keyword
"volatile" and that is in register definitions. It is true what Larry said
that "The 'volatile' keyword tellst the compiler that *every* access to the
variable has to be done in place, no caching or optimization." Another way
of saying this is that the variable can be accessed (i.e. written to) by an
entity outside the mainline code. There are mainly two areas where this can
happen:
- A variable shared between mainline code and an ISR. This is the situation
described by Larry above.
- And a memory location that can be updated by hardware (i.e. outside the
mainline code). If you take a look at avr-libc, in the macros that define
all the registers, you will see that a register is defined as a number
(address) typecast as a pointer to a *volatile* uint8_t (or uint16_t for 2
byte registers). This is very important as many of these memory-mapped
registers  can be written by the hardware in addition to the mainline code.
This scenario is similar to the mainline/ISR scenario above.

Eric Weddington





reply via email to

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