Reputation: 268
I am trying to write a C function that reads the first line of text from a file, then uses fseek()
and ftell()
to get the size of the remainder of the file (the file minus the first line).
My idea was to use a second FILE *fp1
to grab the position of the original FILE *fp
, and send fp1
to the end of the file with fseek()
, so that I wouldn't have to move my original fp
and lose its position.
Here's my code. The compiler is telling me I can't assign fp1
to fp
because fp1
is a FILE*
and fp
is a struct FILE*
.
Can I achieve what I'm trying to do this way?
FILE *fp, fp1;
fp = fopen(filename, "r");
if (!fp)
return 0;
fscanf(fp, "%1d", m); //Lines 15-18 read the first line of the file
fscanf(fp, "%*1c");
fscanf(fp, "%1d", n);
fscanf(fp, "%*1c");
fp1 = fp; //<---------- This is my problem.
//how do I set fp1 to the same place in the
//file as fp?
fseek(fp1, 0, SEEK_END);
*file_size = ftell(fp1);
Upvotes: 0
Views: 2380
Reputation: 144695
Your definition does not define 2 FILE *
pointers:
FILE *fp, fp1;
fp
is a FILE *
, but fp1
is defined as a FILE
type.
You cannot define FILE
objects this way, they should only be obtained from fopen()
. Their state cannot be saved by making a copy of the FILE
object, it is way too complex for this and uses other resources in addition to the FILE
object, which may be an incomplete type.
The good news is you can save the current offset in fp
with ftell()
and seek to the end to attempt to get the file size, and then restore the stream position with another call to fseek()
:
long saved = ftell(fp);
*file_size = -1; // file size may be impossible to retrieve
if (fseek(fp, 0, SEEK_END) != -1) {
*file_size = ftell(fp);
}
fseek(fp, saved, SEEK_SET);
But you should note that this method is not reliable:
You should try and modify your method so it does not need to know the file size.
Upvotes: 2
Reputation: 726
This just copies the pointer to file handle. The proper way is to save ftell result before you move, and after moving to end of file - move back again.
So:
long saved = ftell(fp);
fseek(fp, 0, SEEK_END);
*file_size = ftell(fp);
fseek(fp, saved, SEEK_SET);
Upvotes: 5