ENH: Add compression support

This commit is contained in:
Andy Cedilnik 2005-01-27 10:14:24 -05:00
parent 197ba0bdd6
commit 14477cee6e
2 changed files with 86 additions and 11 deletions

View File

@ -26,6 +26,10 @@
# include <sys/stat.h>
#endif
#if defined(CMAKE_BUILD_WITH_CMAKE)
# include <cmzlib/zlib.h>
#endif
//----------------------------------------------------------------------------
cmGeneratedFileStream::cmGeneratedFileStream():
cmGeneratedFileStreamBase(), Stream()
@ -81,12 +85,19 @@ void cmGeneratedFileStream::SetCopyIfDifferent(bool copy_if_different)
m_CopyIfDifferent = copy_if_different;
}
//----------------------------------------------------------------------------
void cmGeneratedFileStream::SetCompression(bool compression)
{
m_Compress = compression;
}
//----------------------------------------------------------------------------
cmGeneratedFileStreamBase::cmGeneratedFileStreamBase():
m_Name(),
m_TempName(),
m_CopyIfDifferent(false),
m_Okay(false)
m_Okay(false),
m_Compress(false)
{
}
@ -95,7 +106,8 @@ cmGeneratedFileStreamBase::cmGeneratedFileStreamBase(const char* name):
m_Name(name),
m_TempName(name),
m_CopyIfDifferent(false),
m_Okay(false)
m_Okay(false),
m_Compress(false)
{
// Create the name of the temporary file.
m_TempName += ".tmp";
@ -107,22 +119,39 @@ cmGeneratedFileStreamBase::cmGeneratedFileStreamBase(const char* name):
//----------------------------------------------------------------------------
cmGeneratedFileStreamBase::~cmGeneratedFileStreamBase()
{
std::string resname = m_Name;
if ( m_Compress )
{
resname += ".gz";
}
// Only consider replacing the destination file if no error
// occurred.
if(m_Okay &&
(!m_CopyIfDifferent ||
cmSystemTools::FilesDiffer(m_TempName.c_str(), m_Name.c_str())))
(!m_CopyIfDifferent ||
cmSystemTools::FilesDiffer(m_TempName.c_str(), resname.c_str())))
{
// The destination is to be replaced. Rename the temporary to the
// destination atomically.
this->RenameFile(m_TempName.c_str(), m_Name.c_str());
}
else
{
// The destination was not replaced. Just delete the temporary
// file.
cmSystemTools::RemoveFile(m_TempName.c_str());
if ( m_Compress )
{
std::string gzname = m_TempName + ".temp.gz";
if ( this->CompressFile(m_TempName.c_str(), gzname.c_str()) )
{
this->RenameFile(gzname.c_str(), resname.c_str());
}
cmSystemTools::RemoveFile(gzname.c_str());
}
else
{
this->RenameFile(m_TempName.c_str(), resname.c_str());
}
}
// Else, the destination was not replaced.
//
// Always delete the temporary file. We never want it to stay around.
cmSystemTools::RemoveFile(m_TempName.c_str());
}
//----------------------------------------------------------------------------
@ -139,6 +168,41 @@ void cmGeneratedFileStreamBase::Open(const char* name)
cmSystemTools::RemoveFile(m_TempName.c_str());
}
//----------------------------------------------------------------------------
int cmGeneratedFileStreamBase::CompressFile(const char* oldname,
const char* newname)
{
#ifdef CMAKE_BUILD_WITH_CMAKE
gzFile gf = cm_zlib_gzopen(newname, "w");
if ( !gf )
{
return 0;
}
FILE* ifs = fopen(oldname, "r");
if ( !ifs )
{
return 0;
}
size_t res;
const size_t BUFFER_SIZE = 1024;
char buffer[BUFFER_SIZE];
while ( (res = fread(buffer, 1, BUFFER_SIZE, ifs)) > 0 )
{
if ( !cm_zlib_gzwrite(gf, buffer, res) )
{
fclose(ifs);
cm_zlib_gzclose(gf);
return 0;
}
}
fclose(ifs);
cm_zlib_gzclose(gf);
return 1;
#else
return 0;
#endif
}
//----------------------------------------------------------------------------
int cmGeneratedFileStreamBase::RenameFile(const char* oldname,
const char* newname)

View File

@ -41,6 +41,9 @@ protected:
// Internal file replacement implementation.
int RenameFile(const char* oldname, const char* newname);
// Internal file compression implementation.
int CompressFile(const char* oldname, const char* newname);
// The name of the final destination file for the output.
std::string m_Name;
@ -52,6 +55,9 @@ protected:
// Whether the destination file should be replaced.
bool m_Okay;
// Whether the destionation file is compressed
bool m_Compress;
};
/** \class cmGeneratedFileStream
@ -103,6 +109,11 @@ public:
* Set whether copy-if-different is done.
*/
void SetCopyIfDifferent(bool copy_if_different);
/**
* Set whether compression is done.
*/
void SetCompression(bool compression);
};
#endif