I just want to know what below function is doing
static int myfunc(int val) { return *(volatile int *)val; }
The volatile keyword is intended to prevent the compiler from applying any optimizations on objects that can change in ways that cannot be determined by the compiler. Objects declared as volatile are omitted from optimization because their values can be changed by code outside the scope of current code at any time.
Volatile is used in C programming when we need to go and read the value stored by the pointer at the address pointed by the pointer. If you need to change anything in your code that is out of compiler reach you can use this volatile keyword before the variable for which you want to change the value.
volatile int* p; is a pointer to an int that the compiler will treat as volatile . This means that the compiler will assume that it is possible for the variable that p is pointing at to have changed even if there is nothing in the source code to suggest that this might occur.
If val is a pointer when you pass it to this function, it makes sure that the value pointed by this pointer is read and returned to the caller.
I suspect this might be a trick for embedded devices, where sometimes the operation of reading a value at an address has some effect on the hardware.
For instance, reading from an hardware FIFO will pop the read value from the FIFO.
Marking here the pointer as volatile make the compiler not optimize the read if it detects that the value is not used.
Example:
#define FIFO_ADDRESS 0x800050 static int myfunc(int val) { return *(volatile int *)val; // the address *will* be read } static int bad( int val ) { return *(int*)val; // might be optimized to nop() // by the compiler if the value // is not used by the caller } int main(){ bad( FIFO_ADDRESS ); // could be NOP since return value is not used myfunc( FIFO_ADDRESS ); // *WILL* perform a READ operation on the FIFO, // even though the result is not used, because // of the volatile keyword }
Note that I would do it differently, probably with a smartly named macro:
#define FORCE_INT_PTR_READ( address ) *(volatile int *)address
Could you give us an example of usage in your case?
It appears to be trying to confuse the optimiser (and possibly the user). It is taking an integer, treating it as a pointer to an integer, and dereferencing it. The 'volatile' ensures that the optimiser will generate code for that dereference at that point and won't let the optimiser omit the fetch from memory. This is usually used for accessing memory mapped hardware registers,
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With