FWRITE() function giving odd results

I've got a piece of code that is trying to use a file (not a DBF) in read/write mode.

I open it with FOPEN('name',12) so as to have read/write unbuffered access.

I then use FSEEK() to go to the end of the file and use FWRITE() to add some bytes to the end of it.

I then have to go back to the start of the file, again using FSEEK(), and read the first few bytes (they're a header, like in a DBF) with FREAD(). I have to change part of the header. I go back to the start, again with FSEEK(), and write, again with FWRITE().

My problem is that I have to do this twice in a particular part of my code - but it only works once!

I've looked at the number of bytes that FWRITE is reporting as having been written. They're correct.

I've tried using FFLUSH() at the end of each cycle, but that doesn't solve my problem.

Any suggestions?
LVL 1
IainMacbAsked:
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

x
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

pcelbaCommented:
All these low level functions were working without problems for me in all FoxPro and VFP versions so I am almost sure the problem is in your code... You can write the original bytes instead of changed ones, you can write at different offset etc. etc.

FFLUSH should not have any effect on the result in this case. You should check the current file pointer position by ? FSEEK(lnFH, 0, 1)  before each write operation.

You should post some code to allow better understanding what's going on.

Update: I suppose your file size is up to 2 GB.
IainMacbAuthor Commented:
I agree with you about the low-level functions. Most of the time I want to read data from these, or write it out - I think that this is the first time I've ever had to read and write to the same file.

And I agree with you about FFLUSH() - shouldn't have any effect in an unbuffered file.

File size is well below 2GB - one is 15,236 bytes long, the other 1,476.

Code is attached - I've given this a .TXT extension so as to get it past EE's limits.

What's happening here is that I'm writing a new record to a GIS .SHP shape file and its corresponding .SHX index file.

At the start, the .SHP file is 15,236 bytes long, the .SHX file 1,476 bytes.
The first call of the routine writes an extra 88 bytes to the SHP file, which makes it 15,324 bytes long. I can see that by looking in Windows Explorer at the file properties. Likewise, it writes an extra 8 bytes to the SHX file, making it 1,484 bytes long.

When the routine gets called for the second time, it sees the SHP file as being 15,236 bytes long - the original size. It doesn't seem to be able to see the extra 88 bytes. It then writes 88 bytes, making the file again 15,324 bytes long.

Same comment applies to the SHX file - the routine sees it as being the original length of 1,476 bytes.

I'm wondering if passing the handles as parameters might be confusing things...
temp.txt
IainMacbAuthor Commented:
I've just tried taking out the two parameters which pass the file handles - it still fails in exactly the same way.
Learn SQL Server Core 2016

This course will introduce you to SQL Server Core 2016, as well as teach you about SSMS, data tools, installation, server configuration, using Management Studio, and writing and executing queries.

pcelbaCommented:
Hmmm... The code seems to be OK.

How and when do you close your files?  Where are these files stored?  Some folders do not allow file changes (C:\Program Files, C:\Windows, etc. incl. subfolders) and Windows move all updates to some roaming user profile. Next file opening can read the original file again and again.
IainMacbAuthor Commented:
Attached is the calling code, or at least the significant parts of it.

Meanwhile, the files aren't in any special folder. It's named \PROJECTS\2015\QGIS and has all the usual read/write permissions. There's a DBF file that goes with the SHP and SHX ones, and I can write to this OK.
temp2.txt
pcelbaCommented:
Hmm, this seems to be a VFP bug... which I didn't expect at this place.

FSEEK() relative to the end of file does not reflect the file size change done by FWRITE() beyond the end of file.

You have two options:
1) Close and reopen the file after each size extension
2) Call FCHSIZE() before or after the FWRITE() and set the correct file size. It will also fix the FSEEK() behavior.

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
IainMacbAuthor Commented:
I've come to the same conclusion. I thought about closing and re-opening the file, but that's complicated by the need to know the name - not easy at this level of the subroutine calls.

However, I did try calling FCHSIZE() before FWRITE() and that has solved things.

My previous use of these functions has involved writing files using FCREATE() followed by FWRITE(). Presumably that has opened the file in a slightly different way. Here I'm using FOPEN() followed by FWRITE().
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
FoxPro

From novice to tech pro — start learning today.