From 0621a8e08a6b0130b8f51782f4b75b2fe6a299da Mon Sep 17 00:00:00 2001 From: Brecht Van Lommel Date: Fri, 29 Jan 2010 11:26:17 +0000 Subject: Fix for lack of basic error checking in writing compressed .blend files (which is enabled by default). If there was a problem reading or writing in the compression process, the original .blend file could get lost. Now errors are checked, and writing is done as follows: write .blend@ -> compress .blend@ to .blend@.gz -> rename .blend@.gz to .blend -> remove .blend@ We've had blender crash here, lose the original .blend and leave an empty .blend@. It is not clear to me where this would happen in practice if there is enough disk space and permissions are correct, so the actual crash is likely not fixed by this commit. --- source/blender/blenlib/intern/fileops.c | 36 +++++++++++++++++++++------------ 1 file changed, 23 insertions(+), 13 deletions(-) (limited to 'source/blender/blenlib') diff --git a/source/blender/blenlib/intern/fileops.c b/source/blender/blenlib/intern/fileops.c index ae20eda5a59..52ebab9b1ff 100644 --- a/source/blender/blenlib/intern/fileops.c +++ b/source/blender/blenlib/intern/fileops.c @@ -153,29 +153,39 @@ int BLI_gzip(char *from, char *to) { char buffer[10240]; int file; int readsize = 0; + int rval= 0, err; + gzFile gzfile; - gzFile gzfile = gzopen(to,"wb"); - if (NULL == gzfile) return -1; + gzfile = gzopen(to, "wb"); + if(gzfile == NULL) + return -1; - file = open(from,O_BINARY|O_RDONLY); - - if (file < 0) return -2; + file = open(from, O_BINARY|O_RDONLY); + if(file < 0) + return -2; - while ( 1 ) - { + while(1) { readsize = read(file, buffer, 10240); + + if(readsize < 0) { + rval= -2; /* error happened in reading */ + fprintf(stderr, "Error reading file %s: %s.\n", from, strerror(errno)); + break; + } + else if(readsize == 0) + break; /* done reading */ - if (readsize <= 0) break; - - gzwrite(gzfile,buffer,readsize); + if(gzwrite(gzfile, buffer, readsize) <= 0) { + rval= -1; /* error happened in writing */ + fprintf(stderr, "Error writing gz file %s: %s.\n", to, gzerror(gzfile, &err)); + break; + } } gzclose(gzfile); close(file); - - remove(from); - return 0; + return rval; } /* return 1 when file can be written */ -- cgit v1.2.3