From 0cc8fcdbacba7e8ca60d6f4c4d915e707c13fa5f Mon Sep 17 00:00:00 2001 From: csoler Date: Tue, 18 May 2010 21:15:22 +0000 Subject: [PATCH] improved the security of size determination for file lists (suppresses a small bug that caused a chain reaction ending in crash of client peers when downloading file lists) git-svn-id: http://svn.code.sf.net/p/retroshare/code/trunk@2945 b45a01b8-16f6-495d-af2f-9b41ad6348cc --- libretroshare/src/dbase/findex.cc | 36 +++++++++++++++++++------------ 1 file changed, 22 insertions(+), 14 deletions(-) diff --git a/libretroshare/src/dbase/findex.cc b/libretroshare/src/dbase/findex.cc index 7bb2be399..2d2a7d846 100644 --- a/libretroshare/src/dbase/findex.cc +++ b/libretroshare/src/dbase/findex.cc @@ -33,6 +33,8 @@ #include #include #include +#include +#include #include #include @@ -920,21 +922,11 @@ int FileIndex::saveIndex(std::string filename, std::string &fileHash, uint64_t & { unsigned char sha_buf[SHA_DIGEST_LENGTH]; std::string filenametmp = filename + ".tmp" ; - std::ofstream file (filenametmp.c_str(), std::ofstream::binary); std::ostringstream oss; size = 0 ; fileHash = "" ; - if (!file) - { -#ifdef FI_DEBUG - std::cerr << "FileIndex::saveIndex error opening file: " << filename; - std::cerr << std::endl; -#endif - return 0; - } - /* print version and header */ oss << "# FileIndex version 0.1" << std::endl; oss << "# Dir: d name, path, parent, size, modtime, pop, updtime;" << std::endl; @@ -985,17 +977,33 @@ int FileIndex::saveIndex(std::string filename, std::string &fileHash, uint64_t & fileHash = tmpout.str(); /* finally, save to file */ - file << oss.str(); - /* get the size out */ - size=file.tellp(); - file.close(); + FILE *file = fopen(filenametmp.c_str(), "wb"); + if (file == NULL) + { + std::cerr << "FileIndex::saveIndex error opening file for writting: " << filename << ". Giving up." << std::endl; + return 0; + } + fprintf(file,"%s",oss.str().c_str()) ; + + fclose(file); // Use a temp file name so that the file is never half saved. // if(!RsDirUtil::renameFile(filenametmp,filename)) return false ; + /* get the size out */ + struct stat64 buf; + + if(-1 == stat64(filename.c_str(), &buf)) + { + std::cerr << "Can't determine size of file " << filename << ": errno = " << errno << std::endl ; + return false ; + } + + size=buf.st_size; + return true; }