I spend a sleepless night yesterday trying to track down a bug in my test case. My interface looks something like this:
image read_image(FILE *file) {
if (file == nullptr) {
//throw exception
}
//call ftell and fread on the file
//but not fclose
...
//return an image
}
Turns out one of my test cases tested whether my code can handle reading from a file that was first opened (so the file pointer was not nullptr), but closed before I pass it to my function, something like this:
FILE *img_file = fopen("existing_image.png", "r");
REQUIRE(img_file != nullptr); //this passes!
fclose(img_file);
auto my_image = image_read(file);
//... then somewhere down in completely
//unrelated test cases I get segfaults,
//double free errors and the like
Then I spent hours trying to track down segfaults, double frees in completely unrelated parts of my code until I removed that particular test case. This seemed to solve it.
My questions are:
- I know calling
fread/ftellon a closed file is a dumb idea but could it really cause that kind of memory corruption? I looked around on e.g. cppreference but it was never explicitly specified that passing a closed stream is undefined behavior... - Is there any way of finding out if a file was closed before reading from it? (I looked on SO, but the answer seems: no.)
Additional Info
I am using C++17 and gcc 9.3.0 to compile. The reason I have to deal with FILE * at all is because I am receiving these pointers from an external C API.