Where to use volatile keyword in C

I know that the volatile keyword prevents the compiler from optimizing the variable and reading it from memory whenever it is read. Apart from memory mapped registers, what are all the situations where we need to use mutability? Given a compatible compiler, is it necessary to declare test_var as volatile in both scenarios?

1.

In file1.c

int test_var=100;


void func1()
{
    test_var++;
}

      

In file2.c

extern int test_var;

void func2()
{
    if(test_var==100)
    {
      ....
    }
}

      

2.

In file1.c

int test_var=100;

void func1()
{

}

      

In file2.c

extern int test_var;

void func2()
{
    if(test_var==100)
    {
      ....
    }
}

      

+3


source to share


4 answers


memory mapped by I / O is only common use volatile

in C. *)

With POSIX signals, a volatile

can also be used in conjunction with a type sig_atomic_t

as follows:

volatile sig_atomic_t signal_occured = 0;

      

None of your scripts should require volatile

at all. If all you're interested in is guaranteeing that the value is updated between different compilation units, see tofro's comment extern

already guarantees that. In particular, volatile

not the correct tool for synchronizing threads in C. It will only introduce errors because, as you claim, it does , requires actual read and write access to the variable, but it does not enforce their correct ordering with respect to the streams (for there are no memory shortcomings, google).



Note that this differs from some other languages ​​where it is volatile

designed to work between threads.

On an embedded system, it volatile

can be good enough for communication between the ISR (Interrupt Service Service) and the main program, combined with a data type that is read / written atomically, just like sig_atomic_t

for POSIX signals.For this, refer to your compiler's documentation.


*). The C standard mentions this, along with the "asynchronously terminating functions" use case, only in a footnote, since memory mapped I / O is outside of the language. The language simply defines semantics volatile

in such a way as to make it suitable for memory mapped I / O.

+6


source


No need for any of your examples volatile

.

volatile

it is necessary:

  • anywhere a variable can be changed outside the control of one thread of execution,
  • wherever variable access is required, even if it is semantically ineffective.

Case 1 includes:



  • memory mapped I / O registers,
  • memory used for DMA transfers,
  • memory shared between interrupt and / or thread contexts,
  • memory shared between independent processors (for example, dual-port RAM)

Case 2 includes:

  • loop counters used for empty dwell loops where the entire loop can be fully optimized and will not take time,
  • Variables written but never readable for observation in the debugger.

The above examples may not be exhaustive, but semantics are key volatile

; the language should only do explicit access as stated in the source code.

+4


source


Apart from extensions such as memory mapped devices, volatile

there are two use cases in standard C : interacting with signal handlers and modifying objects using setjmp/longjmp

. In both cases, there is an unusual control flow that the optimizer may not be aware of.

+1


source


In microcontroller C applications using interrupts, the keyword is volatile

important to ensure that the value set in the interrupt is stored correctly in the interrupt and later has the correct value in the main loop processing. Failure to use volatile

is perhaps the single biggest reason why timer based interrupts or ADC (analog to digital conversion) interrupts, for example, will have a corrupted value when the control flow resumes after returning the processor state after an interrupt. Canonical template from Atmel and GCC:

volatile uint8_t flag = 0;

ISR(TIMER_whatever_interrupt)
{
    flag = 1;
}

while(1) // main loop
{
    if (flag == 1)
    {
        <do something>
        flag = 0;
    }
}

      

Without volatile

it, it will not guarantee that it will not work as expected.

0


source







All Articles