Normally, C file I/O is done using FILE*
as this is what the standard library functions all take.
In C, one can also have a const pointer, where the address of the pointer cannot change (but the value it points to can be).
I wondered if this could be applied to FILE*
, so wrote this small program to test this:
#include <stdio.h>
int main(void) {
FILE* const file = fopen("somefile.txt", "w");
if (file != NULL) {
fprintf(file, "%s\n", "So this works? That's just swell!");
}
return 0;
}
This compiles fine and works as intended on Ubuntu/Linux 16.04 using GCC (the file contains exactly the string I expected), but I'm not sure if this idiom is such a good idea —the FILE
type is opaque by design and handling of it is implementation-specific.
Because there's no guarantee that any C library implementation won't try and change the address of the FILE
pointer, is it safer to not use this approach when doing I/O in C?
Converting comments into an answer as requested.
You can use
FILE * const
sanely; you cannot useconst FILE *
sanely. There's a guarantee that none of the functions in the C library will modify the pointer part of theFILE *
you pass to them in any way detectable by the calling code, because the pointer is always passed by value — never the address of the pointer. So there is no way for the calling code to modify your pointer — unless it goes to insanely complex steps in order to do so, and it won't because there is neither any need nor any benefit to doing so.It can't have any effect on the functions in the library; they are passed a copy of the value, and they won't modify the value, but won't be aware that the original value is non-modifiable anyway, and won't care. Using
FILE * const fp = fopen(…);
simply means you can't reuse that file pointer for anything else in the same function (or retry opening a different file name or calling a different 'open' function), and you can't reset it to NULL after youfclose()
it. Of course, if the pointer goes out of scope because it is inside a loop, it can be reused when the scope is re-entered.Otherwise, using
FILE * const
has no effect. I don't think it's useful. It isn't harmful except that it does nothing beneficial (and might confuse people). I recommend against usingFILE * const
.