----- Original Message ----- From: "Rein Klazes" rklazes@xs4all.nl To: wine-patches@winehq.com Sent: Sunday, January 20, 2002 2:13 PM Subject: SetEndOfFile fix
hi,
This fixes office 97 MSword error (disk full or write protected) when saving files on a vfat partition. MSword calls SetEndOfFile() which uses ftruncate() that, in Linux, cannot grow files in this filesystem.
BTW. A google search shows that the ftruncate problem has been mentioned at least 3 times on c.e.m.w. in the last 6 months Since nobody entered a fix, I could be overlooking something...
This was a great catch. It was the reason Scandisk complained about OutlookExpress's files (see my message from 1/11/2001). However your fix still fails on my outdated kernel (2.2.12-20). The attached version seems to work better on this kernel.
Guy
On Sat, 26 Jan 2002 01:48:06 -0500, you wrote:
This was a great catch. It was the reason Scandisk complained about OutlookExpress's files (see my message from 1/11/2001). However your fix still fails on my outdated kernel (2.2.12-20). The attached version seems to work better on this kernel.
[...]
- if( (oldoff = lseek( fd, 0, SEEK_CUR)) == -1) return -1;
- if( lseek( fd, length - 1, SEEK_SET) == -1) return -1;
- /* write one byte, filepointer is back at the orig. position. */
- if( write( fd, &buf, 1) == -1) return -1;
- if( lseek( fd, oldoff, SEEK_SET) == -1) return -1;
You should not have to use the oldoff offset. When this function is entered the filepointer is already set to the desired length: length.
BTW, what goes wrong exactly? From the snippet above I understand that either ftruncate() moves the filepointer when it fails or that the sequence: lseek(fd,-1,SEEK_CUR);write(fd,&buf,1) moves the file pointer.
Rein.
Rein Klazes wrote:
BTW, what goes wrong exactly? From the snippet above I understand that either ftruncate() moves the filepointer when it fails or that the sequence: lseek(fd,-1,SEEK_CUR);write(fd,&buf,1) moves the file pointer.
For your perusal, codeweavers also had a reimplementation of this, so I split that out and posted it.
----- Original Message ----- From: "Rein Klazes" rklazes@xs4all.nl To: "Guy L. Albertelli" galberte@neo.lrun.com Cc: wine-devel@winehq.com Sent: Saturday, January 26, 2002 8:50 AM Subject: Re: SetEndOfFile fix
On Sat, 26 Jan 2002 01:48:06 -0500, you wrote:
BTW, what goes wrong exactly? From the snippet above I understand that either ftruncate() moves the filepointer when it fails or that the sequence: lseek(fd,-1,SEEK_CUR);write(fd,&buf,1) moves the file pointer.
All the following is on the 2.2.12-20 kernel:
"ftruncate" would return a 0. However Scandisk said that the file was bad. The length reported in the directory was larger than the allocated space. Errors were also reported on attempts to move or copy the file.
Since ftruncate did not return a error, the rest of your code was never executed. So the rewrite basically asked if the file was being extended, then use the lseek and write. Use ftruncate only if shortening the file. This process resulted in a "valid" file. The size in the directory seemed to match the allocated space.
The oldoff offset was just to put the current file pointer back to where it was on entry. I was not sure of the semantics of the SetEndOfFile and where it would leave the file pointer.
Guy
On Sat, 26 Jan 2002, Guy L. Albertelli wrote:
All the following is on the 2.2.12-20 kernel:
"ftruncate" would return a 0. However Scandisk said that the file was bad. The length reported in the directory was larger than the allocated space. Errors were also reported on attempts to move or copy the file.
Since ftruncate did not return a error, the rest of your code was never executed. So the rewrite basically asked if the file was being extended, then use the lseek and write. Use ftruncate only if shortening the file. This process resulted in a "valid" file. The size in the directory seemed to match the allocated space.
... Why don't we just eliminate the middleman and use lseek and write unconditionally? Just because ftruncate works on other than fat filsesystems doesn't mean we have to use it, does it? If we keep this up we will crack a walnut with a piledriver and 2 feather pilows.
Guy
Lawson
The Devil finds work for idle minds.
On Sat, 26 Jan 2002 22:48:42 -0500 (EST), you wrote:
On Sat, 26 Jan 2002, Guy L. Albertelli wrote:
All the following is on the 2.2.12-20 kernel:
"ftruncate" would return a 0. However Scandisk said that the file was bad. The length reported in the directory was larger than the allocated space. Errors were also reported on attempts to move or copy the file.
Since ftruncate did not return a error, the rest of your code was never executed. So the rewrite basically asked if the file was being extended, then use the lseek and write. Use ftruncate only if shortening the file. This process resulted in a "valid" file. The size in the directory seemed to match the allocated space.
... Why don't we just eliminate the middleman and use lseek and write unconditionally? Just because ftruncate works on other than fat filsesystems doesn't mean we have to use it, does it? If we keep this up we will crack a walnut with a piledriver and 2 feather pilows.
You still need ftruncate in case the file has to shrink. To do that without ftruncate takes a lot more work then an lseek and a write.
Rein.