If a variable - an int, say, is declared as volatile, then the compilers knows it is volatile.It must honor volatile casts. Consider the following example: an interupt service routine(ISR) can in general access all memory, but usually you would designate a global variable that it will restrict it's modifications to. You could also make that variable a pointer, and make the ISR write to or read from the memory pointed to by that global pointer. The object pointed to by that pointer is only volatile when is pointing to it. When it is, all other pointers to that object must also be pointers to volatile, but only if they are actually dereferenced. The compiler has no way of knowing such complicated semantics. Instead, it must rely on the programmer to properly apply volatile casts to objects when they may be modified or read by the ISR, and only then.
Again: volatile mean external to the program. Therefore a complier cannot prove something it compiles is not actually volatile.
That variable can be accessed through pointers. Those pointers may or may not have casts. From what I've read (I've still to inspect the Standard - I will do so soon) the language of the Standard is such that *so long as the compiler can know the type of the underlying object being accessed, it can access that object using its type, regardless of the type of the pointers*.
If what I have read it true, then in the example you give above, the underlying object being referenced should be declared as volatile. If it is not, then regardless of the casts used on the pointers, the compiler is free to treat the variable as non-volatile, because it actually knows that it is. If it declared as non-volatile, but is expected to behave as volatile because the pointer used is volatile, a mistake has been made, for the Standard does not say this will happen - rather, it says if the compiler knows the type of the underlying object, it uses that type.
It may be a given compiler does support this behaviour, however. GCC I believe does.
Yes. This was the answer to the original question of this thread! =-)I took a look at the C standard wording. In my interpretation, what I said above holds true for variables that are not defined as volatile but are accessed through pointers. However, the standard also states:
6.7.3 par. 6: ... If an attempt is made to refer to an object defined with a volatile-qualified type through use of an lvalue with non-volatile-qualified type, the behavior is undefined.
Footnote:This applies to those objects that behave as if they were defined with qualified types, even if they are never actually defined as objects in the program (such as an object at a memory-mapped input/output
address).
In other words, you cannot cast away volatile for an object defined as volatile in your program. (unless you don't actually access the object through the non-volatile pointer).
Now though we talk about whether or not you can *add* volatile to a pointer and expect it to be honoured.