Replace tabs with 4 spaces in all remaining OST code, since this inconsistency can now result in 'misleading indentation' warnings in GCC 6.0+.

This commit is contained in:
Brian Cox 2016-04-23 00:33:17 -07:00
parent 5819201c68
commit 728795af3d
370 changed files with 27186 additions and 27186 deletions

316
src/core/archive.cpp Executable file → Normal file
View File

@ -32,10 +32,10 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// archive.cpp -- classes that abstract a raw byte archive // archive.cpp -- classes that abstract a raw byte archive
// //
// cArchive -- interface for single-direction (one pass) reads and writes // cArchive -- interface for single-direction (one pass) reads and writes
// cBidirArchive -- interface for a random-access archive // cBidirArchive -- interface for a random-access archive
// cMemArchive -- implementation of a bidirectional archive in memory // cMemArchive -- implementation of a bidirectional archive in memory
// cFileArchive -- implementation of a bidirectional archive as a file // cFileArchive -- implementation of a bidirectional archive as a file
#include "stdcore.h" #include "stdcore.h"
#include "archive.h" #include "archive.h"
@ -219,34 +219,34 @@ void cArchive::WriteBlob(const void* pBlob, int count) // throw(eArchive)
int32 cArchive::GetStorageSize(const TSTRING& str) int32 cArchive::GetStorageSize(const TSTRING& str)
{ {
int32 size = sizeof(int32); // the length is always stored int32 size = sizeof(int32); // the length is always stored
// //
// after the length, all of the characters in the string are written as 16-bit values, // after the length, all of the characters in the string are written as 16-bit values,
// except for the null character // except for the null character
// //
size += ( str.length() * 2 ); size += ( str.length() * 2 );
return size; return size;
} }
int64 cArchive::Copy(cArchive* pFrom, int64 amt) int64 cArchive::Copy(cArchive* pFrom, int64 amt)
{ {
enum { BUF_SIZE = 2048 }; enum { BUF_SIZE = 2048 };
int8 buf[BUF_SIZE]; int8 buf[BUF_SIZE];
int64 amtLeft = amt; int64 amtLeft = amt;
while(amtLeft > 0) while(amtLeft > 0)
{ {
int64 amtToRead = amtLeft > (int64)BUF_SIZE ? (int64)BUF_SIZE : amtLeft; int64 amtToRead = amtLeft > (int64)BUF_SIZE ? (int64)BUF_SIZE : amtLeft;
int64 amtRead = pFrom->ReadBlob(buf, static_cast<int>( amtToRead ) ); int64 amtRead = pFrom->ReadBlob(buf, static_cast<int>( amtToRead ) );
amtLeft -= amtRead; amtLeft -= amtRead;
WriteBlob(buf, static_cast<int>( amtRead ) ); WriteBlob(buf, static_cast<int>( amtRead ) );
if(amtRead < amtToRead) if(amtRead < amtToRead)
break; break;
} }
// return the amount copied ... // return the amount copied ...
return (amt - amtLeft); return (amt - amtLeft);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -429,7 +429,7 @@ void cMemoryArchive::AllocateMemory(int len) // throw(eArchive)
if (len > mAllocatedLen) if (len > mAllocatedLen)
{ {
// grow the buffer // grow the buffer
// only error if we are in debug mode // only error if we are in debug mode
#ifdef _DEBUG #ifdef _DEBUG
if (len > mMaxAllocatedLen) if (len > mMaxAllocatedLen)
ThrowAndAssert(eArchiveOutOfMem()); ThrowAndAssert(eArchiveOutOfMem());
@ -486,9 +486,9 @@ class cFixedMemArchive : public cBidirArchive
{ {
public: public:
int8* mpMemory; int8* mpMemory;
int32 mSize; int32 mSize;
int32 mReadHead; int32 mReadHead;
}; };
*/ */
@ -496,18 +496,18 @@ public:
// cFixedMemArchive // cFixedMemArchive
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
cFixedMemArchive::cFixedMemArchive() cFixedMemArchive::cFixedMemArchive()
: mpMemory (0), : mpMemory (0),
mSize (0), mSize (0),
mReadHead (0) mReadHead (0)
{ {
} }
cFixedMemArchive::cFixedMemArchive( int8* pMem, int32 size ) cFixedMemArchive::cFixedMemArchive( int8* pMem, int32 size )
: mpMemory (0), : mpMemory (0),
mSize (0), mSize (0),
mReadHead (0) mReadHead (0)
{ {
Attach( pMem, size ); Attach( pMem, size );
} }
cFixedMemArchive::~cFixedMemArchive() cFixedMemArchive::~cFixedMemArchive()
@ -516,9 +516,9 @@ cFixedMemArchive::~cFixedMemArchive()
void cFixedMemArchive::Attach( int8* pMem, int32 size ) void cFixedMemArchive::Attach( int8* pMem, int32 size )
{ {
mpMemory = pMem; mpMemory = pMem;
mSize = size; mSize = size;
mReadHead = 0; mReadHead = 0;
} }
void cFixedMemArchive::Seek(int64 offset, SeekFrom from) // throw(eArchive) void cFixedMemArchive::Seek(int64 offset, SeekFrom from) // throw(eArchive)
@ -545,28 +545,28 @@ void cFixedMemArchive::Seek(int64 offset, SeekFrom from) // throw(eArchive)
int64 cFixedMemArchive::CurrentPos() const int64 cFixedMemArchive::CurrentPos() const
{ {
return mReadHead; return mReadHead;
} }
int64 cFixedMemArchive::Length() const int64 cFixedMemArchive::Length() const
{ {
return mSize; return mSize;
} }
bool cFixedMemArchive::EndOfFile() bool cFixedMemArchive::EndOfFile()
{ {
return (mReadHead >= mSize); return (mReadHead >= mSize);
} }
int cFixedMemArchive::Read(void* pDest, int count) // throw(eArchive) int cFixedMemArchive::Read(void* pDest, int count) // throw(eArchive)
{ {
ASSERT( pDest ); ASSERT( pDest );
if (mReadHead + count > mSize) if (mReadHead + count > mSize)
{ {
count = static_cast<int>( mSize - mReadHead ); count = static_cast<int>( mSize - mReadHead );
if (count <= 0) if (count <= 0)
return 0; return 0;
} }
if (pDest != 0) if (pDest != 0)
memcpy(pDest, mpMemory + mReadHead, count); memcpy(pDest, mpMemory + mReadHead, count);
@ -576,12 +576,12 @@ int cFixedMemArchive::Read(void* pDest, int count) // throw(eArchive)
return count; return count;
} }
int cFixedMemArchive::Write(const void* pDest, int count) // throw(eArchive) int cFixedMemArchive::Write(const void* pDest, int count) // throw(eArchive)
{ {
if (mReadHead + count > mSize) if (mReadHead + count > mSize)
{ {
ASSERT( false ); ASSERT( false );
throw eArchiveWrite(); throw eArchiveWrite();
} }
memcpy(mpMemory + mReadHead, pDest, count); memcpy(mpMemory + mReadHead, pDest, count);
@ -598,9 +598,9 @@ int cFixedMemArchive::Write(const void* pDest, int count) // throw(eArchive)
//Ctor -- Initialize member variables to 0 or NULL equivalents. //Ctor -- Initialize member variables to 0 or NULL equivalents.
cFileArchive::cFileArchive() : cFileArchive::cFileArchive() :
mFileSize(0), mFileSize(0),
mReadHead(0), mReadHead(0),
isWritable(false) isWritable(false)
{} {}
cFileArchive::~cFileArchive() cFileArchive::~cFileArchive()
@ -609,7 +609,7 @@ cFileArchive::~cFileArchive()
bool cFileArchive::EndOfFile() bool cFileArchive::EndOfFile()
{ {
return ( mReadHead >= mFileSize ); return ( mReadHead >= mFileSize );
} }
//////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////
@ -618,38 +618,38 @@ bool cFileArchive::EndOfFile()
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
void cFileArchive::Seek( int64 offset, SeekFrom from) // throw(eArchive) void cFileArchive::Seek( int64 offset, SeekFrom from) // throw(eArchive)
{ {
try try
{ {
switch (from) switch (from)
{ {
case cBidirArchive::BEGINNING: case cBidirArchive::BEGINNING:
break; break;
case cBidirArchive::CURRENT: case cBidirArchive::CURRENT:
offset = mReadHead + offset; offset = mReadHead + offset;
break; break;
case cBidirArchive::END: case cBidirArchive::END:
offset = mFileSize + offset; offset = mFileSize + offset;
break; break;
default: default:
throw eArchiveSeek( mCurrentFilename, iFSServices::GetInstance()->GetErrString() ) ; throw eArchiveSeek( mCurrentFilename, iFSServices::GetInstance()->GetErrString() ) ;
} }
if ( offset > mFileSize ) if ( offset > mFileSize )
throw eArchiveSeek( mCurrentFilename, iFSServices::GetInstance()->GetErrString() ) ; throw eArchiveSeek( mCurrentFilename, iFSServices::GetInstance()->GetErrString() ) ;
mReadHead = offset; mReadHead = offset;
mCurrentFile.Seek(mReadHead, cFile::SEEK_BEGIN); mCurrentFile.Seek(mReadHead, cFile::SEEK_BEGIN);
//This is where the actual read/writehead is set!! //This is where the actual read/writehead is set!!
}//try }//try
catch( eFile& fileError ) catch( eFile& fileError )
{ {
throw( eArchiveSeek( mCurrentFilename, fileError.GetDescription() ) ); throw( eArchiveSeek( mCurrentFilename, fileError.GetDescription() ) );
} }
} }
int64 cFileArchive::CurrentPos(void) const int64 cFileArchive::CurrentPos(void) const
{ {
return mReadHead; return mReadHead;
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
@ -657,14 +657,14 @@ int64 cFileArchive::CurrentPos(void) const
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
int64 cFileArchive::Length(void) const int64 cFileArchive::Length(void) const
{ {
try try
{ {
return mCurrentFile.GetSize(); return mCurrentFile.GetSize();
} }
catch(eFile& fileError) catch(eFile& fileError)
{ {
throw( eArchiveSeek( mCurrentFilename, fileError.GetDescription() ) ); throw( eArchiveSeek( mCurrentFilename, fileError.GetDescription() ) );
} }
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
@ -672,25 +672,25 @@ int64 cFileArchive::Length(void) const
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
void cFileArchive::OpenRead(const TCHAR* filename, uint32 openFlags) void cFileArchive::OpenRead(const TCHAR* filename, uint32 openFlags)
{ {
try try
{ {
// set up open flags // set up open flags
uint32 flags = cFile::OPEN_READ; uint32 flags = cFile::OPEN_READ;
flags |= ( ( openFlags & FA_OPEN_TRUNCATE ) ? cFile::OPEN_TRUNCATE : 0 ); flags |= ( ( openFlags & FA_OPEN_TRUNCATE ) ? cFile::OPEN_TRUNCATE : 0 );
flags |= ( ( openFlags & FA_OPEN_TEXT ) ? cFile::OPEN_TEXT : 0 ); flags |= ( ( openFlags & FA_OPEN_TEXT ) ? cFile::OPEN_TEXT : 0 );
flags |= ( ( openFlags & FA_NONBLOCKING ) ? cFile::OPEN_NONBLOCKING :0 ); flags |= ( ( openFlags & FA_NONBLOCKING ) ? cFile::OPEN_NONBLOCKING :0 );
mCurrentFilename = filename; mCurrentFilename = filename;
mCurrentFile.Open( filename, flags ); mCurrentFile.Open( filename, flags );
isWritable = false; isWritable = false;
mFileSize = mCurrentFile.GetSize(); mFileSize = mCurrentFile.GetSize();
mReadHead = mCurrentFile.Seek( 0, cFile::SEEK_BEGIN ); mReadHead = mCurrentFile.Seek( 0, cFile::SEEK_BEGIN );
} }
catch(eFile& fileError) catch(eFile& fileError)
{ {
throw(eArchiveOpen( mCurrentFilename, fileError.GetDescription() ) ); throw(eArchiveOpen( mCurrentFilename, fileError.GetDescription() ) );
} }
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
@ -698,34 +698,34 @@ void cFileArchive::OpenRead(const TCHAR* filename, uint32 openFlags)
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
void cFileArchive::OpenReadWrite(const TCHAR* filename, uint32 openFlags) void cFileArchive::OpenReadWrite(const TCHAR* filename, uint32 openFlags)
{ {
try try
{ {
// set up open flags // set up open flags
uint32 flags = cFile::OPEN_WRITE; uint32 flags = cFile::OPEN_WRITE;
flags |= ( ( openFlags & FA_OPEN_TRUNCATE ) ? cFile::OPEN_TRUNCATE : 0 ); flags |= ( ( openFlags & FA_OPEN_TRUNCATE ) ? cFile::OPEN_TRUNCATE : 0 );
flags |= ( ( openFlags & FA_OPEN_TEXT ) ? cFile::OPEN_TEXT : 0 ); flags |= ( ( openFlags & FA_OPEN_TEXT ) ? cFile::OPEN_TEXT : 0 );
flags |= ( ( openFlags & FA_NONBLOCKING ) ? cFile::OPEN_NONBLOCKING :0 ); flags |= ( ( openFlags & FA_NONBLOCKING ) ? cFile::OPEN_NONBLOCKING :0 );
mCurrentFilename = filename; mCurrentFilename = filename;
mCurrentFile.Open( filename, flags ); mCurrentFile.Open( filename, flags );
isWritable = true; isWritable = true;
mFileSize = mCurrentFile.GetSize(); mFileSize = mCurrentFile.GetSize();
mReadHead = mCurrentFile.Seek( 0, cFile::SEEK_BEGIN ); mReadHead = mCurrentFile.Seek( 0, cFile::SEEK_BEGIN );
} }
catch(eFile& fileError) catch(eFile& fileError)
{ {
throw( eArchiveOpen( mCurrentFilename, fileError.GetDescription() ) ); throw( eArchiveOpen( mCurrentFilename, fileError.GetDescription() ) );
} }
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
// GetCurrentFilename -- Returns the name of the file currently associated // GetCurrentFilename -- Returns the name of the file currently associated
// with the FileArchive. // with the FileArchive.
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
TSTRING cFileArchive::GetCurrentFilename(void) const TSTRING cFileArchive::GetCurrentFilename(void) const
{ {
return mCurrentFilename; return mCurrentFilename;
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
@ -733,18 +733,18 @@ TSTRING cFileArchive::GetCurrentFilename(void) const
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
void cFileArchive::Close() void cFileArchive::Close()
{ {
try try
{ {
mCurrentFile.Close(); mCurrentFile.Close();
mFileSize = 0; mFileSize = 0;
mReadHead = 0; mReadHead = 0;
mCurrentFilename = _T(""); mCurrentFilename = _T("");
} }
catch(eFile& fileError) catch(eFile& fileError)
{ {
throw( eArchive( mCurrentFilename, fileError.GetDescription() ) ); throw( eArchive( mCurrentFilename, fileError.GetDescription() ) );
} }
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
@ -753,22 +753,22 @@ void cFileArchive::Close()
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
int cFileArchive::Read(void* pDest, int count) int cFileArchive::Read(void* pDest, int count)
{ {
try try
{ {
if ( mReadHead + count > mFileSize ) if ( mReadHead + count > mFileSize )
count = static_cast<int>( mFileSize - mReadHead ); count = static_cast<int>( mFileSize - mReadHead );
if ( pDest != NULL ) if ( pDest != NULL )
{ {
int nbRead = int nbRead =
static_cast<int>( mCurrentFile.Read( pDest, count ) ); static_cast<int>( mCurrentFile.Read( pDest, count ) );
// 'count' may not be equal to 'nbRead' if the file is open in // 'count' may not be equal to 'nbRead' if the file is open in
// text mode. // text mode.
count = nbRead; count = nbRead;
if(count < 0) count = 0; if(count < 0) count = 0;
} }
else else
{ {
int i; int i;
int32 dummy; int32 dummy;
@ -777,20 +777,20 @@ int cFileArchive::Read(void* pDest, int count)
if (i < (int)sizeof(int32)) if (i < (int)sizeof(int32))
{ {
if (i > 0) if (i > 0)
mCurrentFile.Read( &dummy, i ); mCurrentFile.Read( &dummy, i );
break; break;
} }
mCurrentFile.Read( &dummy, i ); mCurrentFile.Read( &dummy, i );
} }
} }
mReadHead += count; mReadHead += count;
return count; return count;
} }
catch( eFile& fileError ) catch( eFile& fileError )
{ {
throw( eArchiveRead( mCurrentFilename, fileError.GetDescription() ) ); throw( eArchiveRead( mCurrentFilename, fileError.GetDescription() ) );
} }
} }
@ -841,20 +841,20 @@ int cFileArchive::Write(const void* pDest, int count) // throw(eArchive)
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
void cFileArchive::Truncate() // throw(eArchive) void cFileArchive::Truncate() // throw(eArchive)
{ {
ASSERT( mCurrentFile.IsOpen() ); ASSERT( mCurrentFile.IsOpen() );
ASSERT( mCurrentFile.isWritable ); ASSERT( mCurrentFile.isWritable );
try try
{ {
mCurrentFile.Truncate ( mReadHead ); mCurrentFile.Truncate ( mReadHead );
} }
catch( eFile& fileError ) catch( eFile& fileError )
{ {
//TODO: create an error number for truncate... //TODO: create an error number for truncate...
throw( eArchiveWrite( mCurrentFilename, fileError.GetDescription() ) ); throw( eArchiveWrite( mCurrentFilename, fileError.GetDescription() ) );
} }
mFileSize = mReadHead; mFileSize = mReadHead;
} }
@ -871,8 +871,8 @@ void cLockedTemporaryFileArchive::OpenReadWrite( const TCHAR* filename, uint32 o
try { try {
ASSERT( !mCurrentFile.IsOpen() ); // shouldn't be able to create a new file when we're already open ASSERT( !mCurrentFile.IsOpen() ); // shouldn't be able to create a new file when we're already open
if ( mCurrentFile.IsOpen() ) if ( mCurrentFile.IsOpen() )
throw( eArchive( mCurrentFilename, _T("Internal Error") ) ); throw( eArchive( mCurrentFilename, _T("Internal Error") ) );
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////

182
src/core/archive.h Executable file → Normal file
View File

@ -32,10 +32,10 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// archive.h -- classes that abstract a raw byte archive // archive.h -- classes that abstract a raw byte archive
// //
// cArchive -- interface for single-direction (one pass) reads and writes // cArchive -- interface for single-direction (one pass) reads and writes
// cBidirArchive -- interface for a random-access archive // cBidirArchive -- interface for a random-access archive
// cMemArchive -- implementation of a bidirectional archive in memory // cMemArchive -- implementation of a bidirectional archive in memory
// cFileArchive -- implementation of a bidirectional archive as a file // cFileArchive -- implementation of a bidirectional archive as a file
#ifndef __ARCHIVE_H #ifndef __ARCHIVE_H
#define __ARCHIVE_H #define __ARCHIVE_H
@ -56,26 +56,26 @@
//============================================================================= //=============================================================================
// eArchive exception classes // eArchive exception classes
//============================================================================= //=============================================================================
TSS_FILE_EXCEPTION( eArchive, eFileError ); TSS_FILE_EXCEPTION( eArchive, eFileError );
TSS_FILE_EXCEPTION( eArchiveOpen, eArchive ); TSS_FILE_EXCEPTION( eArchiveOpen, eArchive );
TSS_FILE_EXCEPTION( eArchiveWrite, eArchive ); TSS_FILE_EXCEPTION( eArchiveWrite, eArchive );
TSS_FILE_EXCEPTION( eArchiveRead, eArchive ); TSS_FILE_EXCEPTION( eArchiveRead, eArchive );
TSS_FILE_EXCEPTION( eArchiveEOF, eArchive ); TSS_FILE_EXCEPTION( eArchiveEOF, eArchive );
TSS_FILE_EXCEPTION( eArchiveSeek, eArchive ); TSS_FILE_EXCEPTION( eArchiveSeek, eArchive );
TSS_FILE_EXCEPTION( eArchiveMemmap, eArchive ); TSS_FILE_EXCEPTION( eArchiveMemmap, eArchive );
TSS_FILE_EXCEPTION( eArchiveOutOfMem, eArchive ); TSS_FILE_EXCEPTION( eArchiveOutOfMem, eArchive );
TSS_FILE_EXCEPTION( eArchiveInvalidOp, eArchive ); TSS_FILE_EXCEPTION( eArchiveInvalidOp, eArchive );
TSS_FILE_EXCEPTION( eArchiveFormat, eArchive ); TSS_FILE_EXCEPTION( eArchiveFormat, eArchive );
TSS_FILE_EXCEPTION( eArchiveNotRegularFile, eArchive ); TSS_FILE_EXCEPTION( eArchiveNotRegularFile, eArchive );
TSS_BEGIN_EXCEPTION( eArchiveCrypto, eArchive ) TSS_BEGIN_EXCEPTION( eArchiveCrypto, eArchive )
virtual TSTRING GetMsg() const; virtual TSTRING GetMsg() const;
// eCryptoArchive appends a special string to the end of // eCryptoArchive appends a special string to the end of
// all exception messages // all exception messages
TSS_END_EXCEPTION() TSS_END_EXCEPTION()
TSS_EXCEPTION( eArchiveStringTooLong, eArchive ); TSS_EXCEPTION( eArchiveStringTooLong, eArchive );
// throw( eArchiveOpen( cErrorUtil::MakeFileError( fileError.GetMsg(), strTempFile ) ) ); // throw( eArchiveOpen( cErrorUtil::MakeFileError( fileError.GetMsg(), strTempFile ) ) );
//============================================================================= //=============================================================================
@ -87,7 +87,7 @@ class cArchive
public: public:
virtual ~cArchive() {} virtual ~cArchive() {}
// convenience methods // convenience methods
// //
// Specific Read functions throw(eArchive) if EOF is reached because // Specific Read functions throw(eArchive) if EOF is reached because
// if the caller is requesting a certain amount of data to be present, // if the caller is requesting a certain amount of data to be present,
@ -101,33 +101,33 @@ public:
// All write functions throw exceptions for unexpected events like // All write functions throw exceptions for unexpected events like
// running out of memory or disk space. // running out of memory or disk space.
// //
void ReadInt16(int16& ret); // throw(eArchive) void ReadInt16(int16& ret); // throw(eArchive)
void ReadInt32(int32& ret); // throw(eArchive) void ReadInt32(int32& ret); // throw(eArchive)
void ReadInt64(int64& ret); // throw(eArchive) void ReadInt64(int64& ret); // throw(eArchive)
void ReadString(TSTRING& ret); // throw(eArchive) void ReadString(TSTRING& ret); // throw(eArchive)
int ReadBlob(void* pBlob, int count); int ReadBlob(void* pBlob, int count);
void WriteInt16(int16 i); // throw(eArchive) void WriteInt16(int16 i); // throw(eArchive)
void WriteInt32(int32 i); // throw(eArchive) void WriteInt32(int32 i); // throw(eArchive)
void WriteInt64(int64 i); // throw(eArchive) void WriteInt64(int64 i); // throw(eArchive)
void WriteString(TSTRING s); // throw(eArchive) void WriteString(TSTRING s); // throw(eArchive)
void WriteBlob(const void* pBlob, int count); // throw(eArchive) void WriteBlob(const void* pBlob, int count); // throw(eArchive)
static int32 GetStorageSize(const TSTRING& str); static int32 GetStorageSize(const TSTRING& str);
// this method calculates how many bytes the given string will take up in the archive and returns // this method calculates how many bytes the given string will take up in the archive and returns
// that value // that value
// NOTE -- if the implementation of ReadString() or WriteString() ever changes, this method will also // NOTE -- if the implementation of ReadString() or WriteString() ever changes, this method will also
// need to change. // need to change.
int64 Copy(cArchive* pFrom, int64 amt); // throw(eArchive) int64 Copy(cArchive* pFrom, int64 amt); // throw(eArchive)
// this method copies amt bytes from pFrom to itself, throwing an eArchive if anything goes wrong. // this method copies amt bytes from pFrom to itself, throwing an eArchive if anything goes wrong.
// only makes sense to call for reading archives // only makes sense to call for reading archives
virtual bool EndOfFile() = 0; virtual bool EndOfFile() = 0;
protected: protected:
// overrides // overrides
virtual int Read(void* pDest, int count) = 0; virtual int Read(void* pDest, int count) = 0;
virtual int Write(const void* pDest, int count) = 0; // throw(eArchive); virtual int Write(const void* pDest, int count) = 0; // throw(eArchive);
}; };
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -202,7 +202,7 @@ public:
void Truncate(); // set the length to the current pos void Truncate(); // set the length to the current pos
int8* GetMemory() const { return mpMemory; } int8* GetMemory() const { return mpMemory; }
protected: protected:
int8* mpMemory; int8* mpMemory;
@ -211,50 +211,50 @@ protected:
int mLogicalSize; int mLogicalSize;
int mReadHead; int mReadHead;
virtual int Read(void* pDest, int count); virtual int Read(void* pDest, int count);
virtual int Write(const void* pDest, int count); // throw(eArchive) virtual int Write(const void* pDest, int count); // throw(eArchive)
virtual void AllocateMemory(int len); // throw(eArchive) virtual void AllocateMemory(int len); // throw(eArchive)
}; };
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// cFixedMemArchive -- a memory archive that operates on a fixed-sized block of // cFixedMemArchive -- a memory archive that operates on a fixed-sized block of
// memory that has already been allocated // memory that has already been allocated
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
class cFixedMemArchive : public cBidirArchive class cFixedMemArchive : public cBidirArchive
{ {
public: public:
cFixedMemArchive(); cFixedMemArchive();
cFixedMemArchive( int8* pMem, int32 size ); cFixedMemArchive( int8* pMem, int32 size );
virtual ~cFixedMemArchive(); virtual ~cFixedMemArchive();
void Attach( int8* pMem, int32 size ); void Attach( int8* pMem, int32 size );
// this method associates the archive with pMem and sets the size of the // this method associates the archive with pMem and sets the size of the
// archive. Unlike cMemoryArchive, this may never grow or shrink in size. // archive. Unlike cMemoryArchive, this may never grow or shrink in size.
//----------------------------------- //-----------------------------------
// cBidirArchive interface // cBidirArchive interface
//----------------------------------- //-----------------------------------
virtual void Seek (int64 offset, SeekFrom from) ; // throw(eArchive); virtual void Seek (int64 offset, SeekFrom from) ; // throw(eArchive);
virtual int64 CurrentPos () const ; virtual int64 CurrentPos () const ;
virtual int64 Length () const ; virtual int64 Length () const ;
virtual bool EndOfFile(); virtual bool EndOfFile();
protected: protected:
//----------------------------------- //-----------------------------------
// cArchive interface // cArchive interface
//----------------------------------- //-----------------------------------
virtual int Read(void* pDest, int count); // throw(eArchive) virtual int Read(void* pDest, int count); // throw(eArchive)
virtual int Write(const void* pDest, int count); // throw(eArchive) virtual int Write(const void* pDest, int count); // throw(eArchive)
int8* mpMemory; int8* mpMemory;
int32 mSize; int32 mSize;
int32 mReadHead; int32 mReadHead;
}; };
class cFileArchive : public cBidirArchive class cFileArchive : public cBidirArchive
{ {
public: public:
cFileArchive(); cFileArchive();
virtual ~cFileArchive(); virtual ~cFileArchive();
enum OpenFlags enum OpenFlags
{ {
@ -264,34 +264,34 @@ public:
}; };
// TODO: Open should throw // TODO: Open should throw
virtual void OpenRead(const TCHAR* filename, uint32 openFlags = 0 ); virtual void OpenRead(const TCHAR* filename, uint32 openFlags = 0 );
virtual void OpenReadWrite(const TCHAR* filename, uint32 openFlags = FA_OPEN_TRUNCATE ); virtual void OpenReadWrite(const TCHAR* filename, uint32 openFlags = FA_OPEN_TRUNCATE );
// opens a file for reading or writing; the file is always created if it doesn't exist, // opens a file for reading or writing; the file is always created if it doesn't exist,
// and is truncated to zero length if truncateFile is set to true; // and is truncated to zero length if truncateFile is set to true;
TSTRING GetCurrentFilename(void) const; TSTRING GetCurrentFilename(void) const;
virtual void Close(void); virtual void Close(void);
void Truncate(); // throw(eArchive) // set the length to the current pos void Truncate(); // throw(eArchive) // set the length to the current pos
//----------------------------------- //-----------------------------------
// cBidirArchive interface // cBidirArchive interface
//----------------------------------- //-----------------------------------
virtual bool EndOfFile(); virtual bool EndOfFile();
virtual void Seek(int64 offset, SeekFrom from); // throw(eArchive) virtual void Seek(int64 offset, SeekFrom from); // throw(eArchive)
virtual int64 CurrentPos() const; virtual int64 CurrentPos() const;
virtual int64 Length() const; virtual int64 Length() const;
protected: protected:
int64 mFileSize; //Size of FileArchive int64 mFileSize; //Size of FileArchive
int64 mReadHead; //Current position of read/write head int64 mReadHead; //Current position of read/write head
//----------------------------------- //-----------------------------------
// cArchive interface // cArchive interface
//----------------------------------- //-----------------------------------
virtual int Read(void* pDest, int count); virtual int Read(void* pDest, int count);
virtual int Write(const void* pDest, int count); //throw(eArchive) virtual int Write(const void* pDest, int count); //throw(eArchive)
bool isWritable; bool isWritable;
cFile mCurrentFile; cFile mCurrentFile;
TSTRING mCurrentFilename; //current file TSTRING mCurrentFilename; //current file
}; };
/////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////
@ -305,15 +305,15 @@ protected:
class cLockedTemporaryFileArchive : public cFileArchive class cLockedTemporaryFileArchive : public cFileArchive
{ {
public: public:
virtual void OpenReadWrite ( const TCHAR* filename = NULL, uint32 openFlags = FA_OPEN_TRUNCATE ); virtual void OpenReadWrite ( const TCHAR* filename = NULL, uint32 openFlags = FA_OPEN_TRUNCATE );
// creates the file. filename must not exist on the file system. // creates the file. filename must not exist on the file system.
// if filename is NULL, the class will create and use a temporary file. // if filename is NULL, the class will create and use a temporary file.
// truncateFile has no meaning // truncateFile has no meaning
//virtual void OpenReadWriteThrow ( const TCHAR* filename = NULL, bool truncateFile = true ) throw (eArchive); //virtual void OpenReadWriteThrow ( const TCHAR* filename = NULL, bool truncateFile = true ) throw (eArchive);
// this is the same as OpenReadWrite, except an exception is thrown on error (of type // this is the same as OpenReadWrite, except an exception is thrown on error (of type
// cArchive::ERR_OPEN_FAILED) // cArchive::ERR_OPEN_FAILED)
virtual void Close(); virtual void Close();
// close and delete the file // close and delete the file
private: private:
// open for read only makes no sense if we're always creating the file, // open for read only makes no sense if we're always creating the file,

View File

@ -63,19 +63,19 @@ int util_tlen( const TCHAR* cur, size_t count )
*/ */
// //
// finds the next whole character in string identified by ['cur'-'end') // finds the next whole character in string identified by ['cur'-'end')
// identifies beginning of char in 'first', then end of character in 'last' // identifies beginning of char in 'first', then end of character in 'last'
// returns number of TCHARs that make up the next character // returns number of TCHARs that make up the next character
// if there are no more characters, will return 0 and first = last = end // if there are no more characters, will return 0 and first = last = end
// POSTCONDITIONS: // POSTCONDITIONS:
// //
// RETURNS: // RETURNS:
// //
// THROWS: // THROWS:
// //
// COMPLEXITY: // COMPLEXITY:
// //
// //
/* static */ /* static */
@ -159,19 +159,19 @@ int cCharUtil::PeekNextChar( const TSTRING::const_iterator& cur,
// TSTRING::const_iterator& last ) // TSTRING::const_iterator& last )
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// REQUIRES: // REQUIRES:
// //
// EFFECTS: // EFFECTS:
// //
// same as PeekNextChar but increments 'cur' to 'last' // same as PeekNextChar but increments 'cur' to 'last'
// //
// POSTCONDITIONS: // POSTCONDITIONS:
// //
// RETURNS: // RETURNS:
// //
// THROWS: // THROWS:
// //
// COMPLEXITY: // COMPLEXITY:
// //
// //
/* static */ /* static */

View File

@ -39,8 +39,8 @@
// ctor, dotr // ctor, dotr
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
cCmdLineParser::cCmdLineParser() : cCmdLineParser::cCmdLineParser() :
mArgTable(HASH_VERY_SMALL), mArgTable(HASH_VERY_SMALL),
mLastArgInfo(-1, PARAM_NONE) mLastArgInfo(-1, PARAM_NONE)
{ {
} }
@ -53,26 +53,26 @@ cCmdLineParser::~cCmdLineParser()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cCmdLineParser::AddArg(int argId, const TSTRING& arg, const TSTRING& alias, ParamCount numParams, bool multipleAllowed) void cCmdLineParser::AddArg(int argId, const TSTRING& arg, const TSTRING& alias, ParamCount numParams, bool multipleAllowed)
{ {
if(arg.empty() && alias.empty()) if(arg.empty() && alias.empty())
{ {
// this refers to the list of parameters that comes after all the cmd line switches // this refers to the list of parameters that comes after all the cmd line switches
mLastArgInfo.mId = argId; mLastArgInfo.mId = argId;
mLastArgInfo.mNumParams = numParams; mLastArgInfo.mNumParams = numParams;
return ; return ;
} }
if(! arg.empty()) if(! arg.empty())
mArgTable.Insert(arg, cArgInfo(argId, numParams)); mArgTable.Insert(arg, cArgInfo(argId, numParams));
if(! alias.empty()) if(! alias.empty())
{ {
// put the alias in the table with a '-' prepended to it so it matches '--' // put the alias in the table with a '-' prepended to it so it matches '--'
TSTRING str(_T("-")); TSTRING str(_T("-"));
str += alias; str += alias;
mArgTable.Insert(str, cArgInfo(argId, numParams)); mArgTable.Insert(str, cArgInfo(argId, numParams));
} }
// This argument can appear more than once on the command line. // This argument can appear more than once on the command line.
if( multipleAllowed ) if( multipleAllowed )
mMultipleAllowed.insert( argId ); mMultipleAllowed.insert( argId );
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -80,11 +80,11 @@ void cCmdLineParser::AddArg(int argId, const TSTRING& arg, const TSTRING& alias,
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cCmdLineParser::Clear() void cCmdLineParser::Clear()
{ {
mLastArgInfo.mId = -1; mLastArgInfo.mId = -1;
mLastArgInfo.mNumParams = PARAM_INVALID; mLastArgInfo.mNumParams = PARAM_INVALID;
mArgTable.Clear(); mArgTable.Clear();
mArgData.clear(); mArgData.clear();
mMutExList.clear(); mMutExList.clear();
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -92,54 +92,54 @@ void cCmdLineParser::Clear()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cCmdLineParser::Parse(int argc, const TCHAR *const * argv) void cCmdLineParser::Parse(int argc, const TCHAR *const * argv)
{ {
// clear out any existing data // clear out any existing data
mArgData.clear(); mArgData.clear();
const TCHAR* pCurArg = 0; const TCHAR* pCurArg = 0;
bool bProcessedFinalParams = false; // gets set to true when the parameters to the command line are processed bool bProcessedFinalParams = false; // gets set to true when the parameters to the command line are processed
// I assume argv[0] is the executable name... // I assume argv[0] is the executable name...
for(int i=1; i < argc; i++) for(int i=1; i < argc; i++)
{ {
if(argv[i][0] == _T('-')) if(argv[i][0] == _T('-'))
{ {
pCurArg = argv[i]; pCurArg = argv[i];
// this is a switch; find it in the table... // this is a switch; find it in the table...
cArgInfo argInfo; cArgInfo argInfo;
if ( !mArgTable.Lookup( TSTRING(&argv[i][1] ), argInfo ) ) if ( !mArgTable.Lookup( TSTRING(&argv[i][1] ), argInfo ) )
{ {
// unknown switch! // unknown switch!
throw eCmdLineInvalidArg( throw eCmdLineInvalidArg(
TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS ) TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS )
+ pCurArg ); + pCurArg );
} }
// //
// make sure this hasn't been specified yet... // make sure this hasn't been specified yet...
// //
if( ArgInList( argInfo.mId ) ) if( ArgInList( argInfo.mId ) )
{ {
// Make sure it isn't okay for this one to appear more than once... // Make sure it isn't okay for this one to appear more than once...
std::set<int>::iterator it = mMultipleAllowed.find( argInfo.mId ); std::set<int>::iterator it = mMultipleAllowed.find( argInfo.mId );
if( it == mMultipleAllowed.end() ) if( it == mMultipleAllowed.end() )
{ {
// It wasn't in our list of allowed params, so error. // It wasn't in our list of allowed params, so error.
throw eCmdLineMultiArg( throw eCmdLineMultiArg(
TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS ) TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS )
+ argv[i] ); + argv[i] );
} }
} }
// //
// add it to the list.. // add it to the list..
// //
mArgData.push_back(cArgData(argInfo.mId, TSTRING(argv[i]))); mArgData.push_back(cArgData(argInfo.mId, TSTRING(argv[i])));
cArgData& curArg = mArgData.back(); cArgData& curArg = mArgData.back();
switch( argInfo.mNumParams ) switch( argInfo.mNumParams )
{ {
case PARAM_NONE: case PARAM_NONE:
// make sure there are no parameters to this, but be careful because // make sure there are no parameters to this, but be careful because
// it is legal to start the parameters to the executable here. // it is legal to start the parameters to the executable here.
if((i+1 < argc) && (argv[i+1][0] != _T('-'))) if((i+1 < argc) && (argv[i+1][0] != _T('-')))
{ {
// search for any more parameters // search for any more parameters
// TODO: In the future we may want to support a '--' switch that specifies the start // TODO: In the future we may want to support a '--' switch that specifies the start
@ -147,121 +147,121 @@ void cCmdLineParser::Parse(int argc, const TCHAR *const * argv)
for (int j = i + 2; j < argc; ++j ) for (int j = i + 2; j < argc; ++j )
{ {
if (argv[j][0] == _T('-')) if (argv[j][0] == _T('-'))
{ {
// >0 parameter passed ! // >0 parameter passed !
throw eCmdLineBadParam( throw eCmdLineBadParam(
TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS ) TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS )
+ pCurArg ); + pCurArg );
} }
} }
} }
break;
case PARAM_ONE:
// get the next parameter...
i++;
if ( (i >= argc) || (argv[i][0] == _T('-')) )
{
// zero parameters passed to something that needed one param
throw eCmdLineBadParam(
TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS )
+ pCurArg );
}
curArg.mParams.push_back( TSTRING(argv[i]) );
break; break;
case PARAM_MANY: case PARAM_ONE:
i++; // get the next parameter...
while((i < argc) && (argv[i][0] != _T('-'))) i++;
{ if ( (i >= argc) || (argv[i][0] == _T('-')) )
curArg.mParams.push_back(TSTRING(argv[i])); {
i++; // zero parameters passed to something that needed one param
} throw eCmdLineBadParam(
i--; // since we have gone too far at this point TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS )
break; + pCurArg );
}
curArg.mParams.push_back( TSTRING(argv[i]) );
break;
case PARAM_MANY:
i++;
while((i < argc) && (argv[i][0] != _T('-')))
{
curArg.mParams.push_back(TSTRING(argv[i]));
i++;
}
i--; // since we have gone too far at this point
break;
default: default:
ASSERTMSG( false, "Unknown number of arguments to parser" ); ASSERTMSG( false, "Unknown number of arguments to parser" );
} }
} }
else else
{ {
bProcessedFinalParams = true; bProcessedFinalParams = true;
// this must be the final "unnamed" arg // this must be the final "unnamed" arg
// first, make sure it is consistent with the current info... // first, make sure it is consistent with the current info...
bool bResult = true; bool bResult = true;
switch(mLastArgInfo.mNumParams) switch(mLastArgInfo.mNumParams)
{ {
case PARAM_NONE: case PARAM_NONE:
// this is an error; they didn't want any command line parameters... // this is an error; they didn't want any command line parameters...
bResult = false; bResult = false;
break; break;
case PARAM_ONE: case PARAM_ONE:
if(i+1 != argc) if(i+1 != argc)
// there is >1 final parameter; it is an error // there is >1 final parameter; it is an error
bResult = false; bResult = false;
break; break;
case PARAM_MANY: case PARAM_MANY:
// we'll catch errors below // we'll catch errors below
break; break;
default: default:
ASSERT(false); ASSERT(false);
} }
if(! bResult) if(! bResult)
{ {
throw eCmdLineBadParam( ); throw eCmdLineBadParam( );
} }
// ok, we can push the final parameter info onto the list... // ok, we can push the final parameter info onto the list...
mArgData.push_back(cArgData(mLastArgInfo.mId)); mArgData.push_back(cArgData(mLastArgInfo.mId));
cArgData& curArg = mArgData.back(); cArgData& curArg = mArgData.back();
while ( i < argc ) while ( i < argc )
{ {
if ( argv[i][0] == _T('-') ) if ( argv[i][0] == _T('-') )
{ {
if ( ! pCurArg ) if ( ! pCurArg )
{ {
throw eCmdLineBadSwitchPos( throw eCmdLineBadSwitchPos(
TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS ) TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS )
+ argv[i] ); + argv[i] );
} }
else else
{ {
// there was an extra parameter passed somewhere! // there was an extra parameter passed somewhere!
throw eCmdLineBadArgParam( throw eCmdLineBadArgParam(
TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS ) TSS_GetString( cCore, core::STR_ERR2_BAD_ARG_PARAMS )
+ pCurArg ); + pCurArg );
} }
} }
// add this param to the list // add this param to the list
curArg.mParams.push_back(TSTRING(argv[i])); curArg.mParams.push_back(TSTRING(argv[i]));
i++; i++;
} }
} }
} }
// it is possible not to process the final command line parameters in the "else" case above // it is possible not to process the final command line parameters in the "else" case above
// (this only occurs if there are no command line parameters specified) so let's make sure that // (this only occurs if there are no command line parameters specified) so let's make sure that
// is consistent with what we are configured with... // is consistent with what we are configured with...
// NOTE -- it is ok to have no cmd line parameters if they specified PARAM_NONE or PARAM_MANY // NOTE -- it is ok to have no cmd line parameters if they specified PARAM_NONE or PARAM_MANY
if(! bProcessedFinalParams) if(! bProcessedFinalParams)
{ {
if(mLastArgInfo.mNumParams == PARAM_ONE) if(mLastArgInfo.mNumParams == PARAM_ONE)
{ {
throw eCmdLineBadParam( ); throw eCmdLineBadParam( );
} }
} }
// Check for "relationship errors": // Check for "relationship errors":
TestMutEx(); TestMutEx();
TestDependency(); TestDependency();
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -269,27 +269,27 @@ void cCmdLineParser::Parse(int argc, const TCHAR *const * argv)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cCmdLineParser::TestMutEx() void cCmdLineParser::TestMutEx()
{ {
std::list<std::pair<int,int> >::const_iterator i; std::list<std::pair<int,int> >::const_iterator i;
cCmdLineIter iter1(*this), iter2(*this); cCmdLineIter iter1(*this), iter2(*this);
for(i = mMutExList.begin(); i != mMutExList.end(); i++) for(i = mMutExList.begin(); i != mMutExList.end(); i++)
{ {
//TODO -- there is a much more efficent way to do this (using cFCOPropVector, for example) //TODO -- there is a much more efficent way to do this (using cFCOPropVector, for example)
// the command line is presumably small enough, tho, that it probably isn't a big // the command line is presumably small enough, tho, that it probably isn't a big
// deal to do it this way. // deal to do it this way.
iter1.SeekToArg(i->first); iter1.SeekToArg(i->first);
if(! iter1.Done()) if(! iter1.Done())
{ {
iter2.SeekToArg(i->second); iter2.SeekToArg(i->second);
if(! iter2.Done()) if(! iter2.Done())
{ {
// we have a mutual exclusion violation! // we have a mutual exclusion violation!
throw eCmdLineMutEx( throw eCmdLineMutEx(
iter1.ActualParam() iter1.ActualParam()
+ _T(", ") + _T(", ")
+ iter2.ActualParam() ); + iter2.ActualParam() );
} }
} }
} }
} }
@ -298,55 +298,55 @@ void cCmdLineParser::TestMutEx()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cCmdLineParser::TestDependency() void cCmdLineParser::TestDependency()
{ {
std::list< std::pair< std::pair< int, int>, bool > >::const_iterator i; std::list< std::pair< std::pair< int, int>, bool > >::const_iterator i;
cCmdLineIter iter1(*this), iter2(*this); cCmdLineIter iter1(*this), iter2(*this);
for( i = mDependencyList.begin(); i != mDependencyList.end(); ++i) for( i = mDependencyList.begin(); i != mDependencyList.end(); ++i)
{ {
iter1.SeekToArg( i->first.first ); iter1.SeekToArg( i->first.first );
// was it on the command line? // was it on the command line?
if( !iter1.Done() ) if( !iter1.Done() )
{ {
// it was, is the corresponding arg on the command line? // it was, is the corresponding arg on the command line?
iter2.SeekToArg( i->first.second ); iter2.SeekToArg( i->first.second );
if( iter2.Done() ) // it wasn't, dependency error if( iter2.Done() ) // it wasn't, dependency error
{ {
TSTRING arg1, arg2, alias1, alias2; TSTRING arg1, arg2, alias1, alias2;
cCmdLineParser::LookupArgInfo( i->first.first, arg1, alias1 ); cCmdLineParser::LookupArgInfo( i->first.first, arg1, alias1 );
cCmdLineParser::LookupArgInfo( i->first.second, arg2, alias2 ); cCmdLineParser::LookupArgInfo( i->first.second, arg2, alias2 );
// determine in which form the user passed the arguments, // determine in which form the user passed the arguments,
// and construct the error message in the same form // and construct the error message in the same form
if ( iter1.ActualParam().length() == 2 ) if ( iter1.ActualParam().length() == 2 )
throw eCmdLineDependency( _T("The switch -") + arg1 + _T(" requires -") + arg2 +_T(".") ); throw eCmdLineDependency( _T("The switch -") + arg1 + _T(" requires -") + arg2 +_T(".") );
else else
throw eCmdLineDependency( _T("The switch --") + alias1 + _T(" requires --") + alias2 + _T(".") ); throw eCmdLineDependency( _T("The switch --") + alias1 + _T(" requires --") + alias2 + _T(".") );
} }
} }
else if( i->second ) else if( i->second )
// only make this second check if the dependencies are MUTUAL, // only make this second check if the dependencies are MUTUAL,
// as indicated (or not) by the bool value. // as indicated (or not) by the bool value.
{ {
iter2.SeekToArg( i->first.second ); iter2.SeekToArg( i->first.second );
// the first arg in the pair was not on the command line, // the first arg in the pair was not on the command line,
// so just make sure the second isn't there... // so just make sure the second isn't there...
if( !iter2.Done() ) if( !iter2.Done() )
{ {
// arg2 appeared without arg1, so dependency error. // arg2 appeared without arg1, so dependency error.
TSTRING arg1, arg2, alias1, alias2; TSTRING arg1, arg2, alias1, alias2;
cCmdLineParser::LookupArgInfo( i->first.first, arg1, alias1 ); cCmdLineParser::LookupArgInfo( i->first.first, arg1, alias1 );
cCmdLineParser::LookupArgInfo( i->first.second, arg2, alias2 ); cCmdLineParser::LookupArgInfo( i->first.second, arg2, alias2 );
// determine in which form the user passed the arguments, // determine in which form the user passed the arguments,
// and construct the error message in the same form // and construct the error message in the same form
if ( iter1.ActualParam().length() == 2 ) if ( iter1.ActualParam().length() == 2 )
throw eCmdLineDependency( _T("The switch -") + arg2 + _T(" requires -") + arg1 +_T(".") ); throw eCmdLineDependency( _T("The switch -") + arg2 + _T(" requires -") + arg1 +_T(".") );
else else
throw eCmdLineDependency( _T("The switch --") + alias2 + _T(" requires --") + alias1 + _T(".") ); throw eCmdLineDependency( _T("The switch --") + alias2 + _T(" requires --") + alias1 + _T(".") );
} }
} }
} //end for } //end for
} }
@ -355,10 +355,10 @@ void cCmdLineParser::TestDependency()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cCmdLineParser::AddMutEx(int argId1, int argId2) void cCmdLineParser::AddMutEx(int argId1, int argId2)
{ {
// note that I do no checking for duplicates here... // note that I do no checking for duplicates here...
std::pair<int, int> mutEx(argId1, argId2); std::pair<int, int> mutEx(argId1, argId2);
ASSERT(argId1 != argId2); ASSERT(argId1 != argId2);
mMutExList.push_back(mutEx); mMutExList.push_back(mutEx);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -366,13 +366,13 @@ void cCmdLineParser::AddMutEx(int argId1, int argId2)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cCmdLineParser::AddDependency(int argId1, int argId2, bool mutual ) void cCmdLineParser::AddDependency(int argId1, int argId2, bool mutual )
{ {
// again, no checking for duplicates... would a set // again, no checking for duplicates... would a set
// prove to be a better container for this operation? // prove to be a better container for this operation?
std::pair< int, int > Args( argId1, argId2 ); std::pair< int, int > Args( argId1, argId2 );
std::pair< std::pair< int, int >, bool > Dep( Args, mutual ); std::pair< std::pair< int, int >, bool > Dep( Args, mutual );
ASSERT(argId1 != argId2); ASSERT(argId1 != argId2);
mDependencyList.push_back( Dep); mDependencyList.push_back( Dep);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -381,29 +381,29 @@ void cCmdLineParser::AddDependency(int argId1, int argId2, bool mutual )
#ifdef _DEBUG #ifdef _DEBUG
void cCmdLineParser::TraceContents(int dl) void cCmdLineParser::TraceContents(int dl)
{ {
cDebug d("cCmdLineParser::TraceContents"); cDebug d("cCmdLineParser::TraceContents");
if(dl == -1) if(dl == -1)
dl = cDebug::D_DEBUG; dl = cDebug::D_DEBUG;
std::list<cArgData>::const_iterator i; std::list<cArgData>::const_iterator i;
for(i = mArgData.begin(); i != mArgData.end(); i++) for(i = mArgData.begin(); i != mArgData.end(); i++)
{ {
d.Trace(dl, "* Item id:%d\n", i->mId); d.Trace(dl, "* Item id:%d\n", i->mId);
for(std::vector<TSTRING>::const_iterator vi = i->mParams.begin(); vi != i->mParams.end(); vi++) for(std::vector<TSTRING>::const_iterator vi = i->mParams.begin(); vi != i->mParams.end(); vi++)
{ {
d.Trace(dl, "\t%s\n", vi->c_str()); d.Trace(dl, "\t%s\n", vi->c_str());
} }
} }
d.Trace(dl, "--- Switch id table ---\n"); d.Trace(dl, "--- Switch id table ---\n");
cHashTableIter<TSTRING, cArgInfo> iter(mArgTable); cHashTableIter<TSTRING, cArgInfo> iter(mArgTable);
for(iter.SeekBegin(); ! iter.Done(); iter.Next()) for(iter.SeekBegin(); ! iter.Done(); iter.Next())
{ {
d.Trace(dl, "[%d] %s\n", iter.Val().mId, iter.Key().c_str()); d.Trace(dl, "[%d] %s\n", iter.Val().mId, iter.Key().c_str());
} }
d.Trace(dl, "[%d] Final Param List\n", mLastArgInfo.mId); d.Trace(dl, "[%d] Final Param List\n", mLastArgInfo.mId);
} }
#endif #endif
@ -412,28 +412,28 @@ void cCmdLineParser::TraceContents(int dl)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cCmdLineParser::LookupArgInfo(int argId, TSTRING& arg, TSTRING& alias) const bool cCmdLineParser::LookupArgInfo(int argId, TSTRING& arg, TSTRING& alias) const
{ {
arg = _T(""); arg = _T("");
alias = _T(""); alias = _T("");
cHashTableIter<TSTRING, cArgInfo> iter(mArgTable); cHashTableIter<TSTRING, cArgInfo> iter(mArgTable);
for(iter.SeekBegin(); ! iter.Done(); iter.Next()) for(iter.SeekBegin(); ! iter.Done(); iter.Next())
{ {
if(iter.Val().mId == argId) if(iter.Val().mId == argId)
{ {
TSTRING str = iter.Key(); TSTRING str = iter.Key();
if((str.length() > 0) && (str[0] == _T('-'))) if((str.length() > 0) && (str[0] == _T('-')))
{ {
// this is the alias! // this is the alias!
alias = (str.c_str() + 1); alias = (str.c_str() + 1);
} }
else else
{ {
// this is the arg... // this is the arg...
arg = str; arg = str;
} }
} }
} }
return ((! arg.empty()) || (! alias.empty())); return ((! arg.empty()) || (! alias.empty()));
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -441,13 +441,13 @@ bool cCmdLineParser::LookupArgInfo(int argId, TSTRING& arg, TSTRING& alias) cons
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cCmdLineParser::ArgInList(int argId) bool cCmdLineParser::ArgInList(int argId)
{ {
std::list<cArgData>::iterator i; std::list<cArgData>::iterator i;
for( i = mArgData.begin(); i != mArgData.end(); i++ ) for( i = mArgData.begin(); i != mArgData.end(); i++ )
{ {
if( i->mId == argId ) if( i->mId == argId )
return true; return true;
} }
return false; return false;
} }
@ -458,15 +458,15 @@ bool cCmdLineParser::ArgInList(int argId)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// SeekToArg // SeekToArg
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cCmdLineIter::SeekToArg(int argId) const bool cCmdLineIter::SeekToArg(int argId) const
{ {
for(SeekBegin(); ! Done(); Next()) for(SeekBegin(); ! Done(); Next())
{ {
if(ArgId() == argId) if(ArgId() == argId)
return true; return true;
} }
return false; return false;
} }

View File

@ -49,39 +49,39 @@
//============================================================================= //=============================================================================
// eCmdLine // eCmdLine
//============================================================================= //=============================================================================
TSS_EXCEPTION( eCmdLine, eError ) TSS_EXCEPTION( eCmdLine, eError )
TSS_EXCEPTION( eCmdLineInvalidArg, eCmdLine ) // an arg on the command line is not recognized TSS_EXCEPTION( eCmdLineInvalidArg, eCmdLine ) // an arg on the command line is not recognized
TSS_EXCEPTION( eCmdLineBadArgParam, eCmdLine ) // wrong number of parameters to an argument TSS_EXCEPTION( eCmdLineBadArgParam, eCmdLine ) // wrong number of parameters to an argument
TSS_EXCEPTION( eCmdLineBadParam, eCmdLine ) // wrong number of paramters to the executable (not associated with any arguments) TSS_EXCEPTION( eCmdLineBadParam, eCmdLine ) // wrong number of paramters to the executable (not associated with any arguments)
TSS_EXCEPTION( eCmdLineBadSwitchPos,eCmdLine ) // a '-' arg appeared after the final parameter list TSS_EXCEPTION( eCmdLineBadSwitchPos,eCmdLine ) // a '-' arg appeared after the final parameter list
TSS_EXCEPTION( eCmdLineMutEx, eCmdLine ) // a mutual exclusion error has occured TSS_EXCEPTION( eCmdLineMutEx, eCmdLine ) // a mutual exclusion error has occured
TSS_EXCEPTION( eCmdLineDependency, eCmdLine ) // a dependency error has occurred. TSS_EXCEPTION( eCmdLineDependency, eCmdLine ) // a dependency error has occurred.
TSS_EXCEPTION( eCmdLineMultiArg, eCmdLine ) // an arg was found twice in the command line TSS_EXCEPTION( eCmdLineMultiArg, eCmdLine ) // an arg was found twice in the command line
/* /*
// cCmdLineParser owns errors 600-699 // cCmdLineParser owns errors 600-699
// these can be turned into a string by using cErrorTable // these can be turned into a string by using cErrorTable
enum ErrorType enum ErrorType
{ {
ERR_NONE = 601, // no error ERR_NONE = 601, // no error
ERR_INVALID_ARG = 602, // an arg on the command line is not recognized ERR_INVALID_ARG = 602, // an arg on the command line is not recognized
ERR_BAD_ARG_PARAMS = 603, // wrong number of parameters to an argument ERR_BAD_ARG_PARAMS = 603, // wrong number of parameters to an argument
ERR_BAD_PARAMS = 604, // wrong number of paramters to the executable (not associated with any arguments) ERR_BAD_PARAMS = 604, // wrong number of paramters to the executable (not associated with any arguments)
ERR_SWITCH_AFTER_FINAL_LIST = 605, // a '-' arg appeared after the final paramter list ERR_SWITCH_AFTER_FINAL_LIST = 605, // a '-' arg appeared after the final paramter list
ERR_MUTUAL_EXCLUSION = 606, // a mutual exclusion error has occured ERR_MUTUAL_EXCLUSION = 606, // a mutual exclusion error has occured
ERR_MULTIPLE_ARG = 607, // an arg was found twice in the command line ERR_MULTIPLE_ARG = 607, // an arg was found twice in the command line
ERR_INVALID // top of enum ERR_INVALID // top of enum
}; };
// for storing error information // for storing error information
ErrorType mCurError; ErrorType mCurError;
TSTRING mCurErrorString; TSTRING mCurErrorString;
void GetErrorInfo(ErrorType& et, TSTRING& errorData) const; void GetErrorInfo(ErrorType& et, TSTRING& errorData) const;
// returns information on the type of error that occured in a Parse() command. Only // returns information on the type of error that occured in a Parse() command. Only
// returns valid information if Parse() had just been called and returned false. A // returns valid information if Parse() had just been called and returned false. A
// second call to Parse() might alter existing error info // second call to Parse() might alter existing error info
*/ */
//============================================================================= //=============================================================================
@ -90,176 +90,176 @@ TSS_EXCEPTION( eCmdLineMultiArg, eCmdLine ) // an arg was found twice in the com
class cCmdLineParser class cCmdLineParser
{ {
public: public:
cCmdLineParser(); cCmdLineParser();
~cCmdLineParser(); ~cCmdLineParser();
enum ParamCount enum ParamCount
{ {
PARAM_NONE, // no parameters to arg PARAM_NONE, // no parameters to arg
PARAM_ONE, // one parameter to arg PARAM_ONE, // one parameter to arg
PARAM_MANY, // zero or more paramters to arg PARAM_MANY, // zero or more paramters to arg
PARAM_INVALID // top of enum PARAM_INVALID // top of enum
}; };
void AddArg(int argId, const TSTRING& arg, const TSTRING& alias, ParamCount numParams, bool multipleAllowed = false); void AddArg(int argId, const TSTRING& arg, const TSTRING& alias, ParamCount numParams, bool multipleAllowed = false);
// this method should be called for each argument that can appear on the // this method should be called for each argument that can appear on the
// command line. // command line.
// argId -- a number that uniquely identifies the argument; no two arguments // argId -- a number that uniquely identifies the argument; no two arguments
// may have the same id (ASSERT-enforced) // may have the same id (ASSERT-enforced)
// arg -- string that comes after the '-'. can be _T("") if there is only // arg -- string that comes after the '-'. can be _T("") if there is only
// a string representation // a string representation
// alias -- string that comes after '--' which has the same meaning. Can be _T("") // alias -- string that comes after '--' which has the same meaning. Can be _T("")
// if there is no alias. If both arg and alias are empty strings, then this arg // if there is no alias. If both arg and alias are empty strings, then this arg
// represents the list of arguments that comes at the end of the command line // represents the list of arguments that comes at the end of the command line
// numParams -- number of parameters that this argument needs // numParams -- number of parameters that this argument needs
void AddMutEx(int argId1, int argId2); void AddMutEx(int argId1, int argId2);
// this adds a mutual exclusion constraint. When Parse() is called, if argId1 and // this adds a mutual exclusion constraint. When Parse() is called, if argId1 and
// argId2 both exist on the command line, then the parse will fail and the error // argId2 both exist on the command line, then the parse will fail and the error
// value ERR_MUTUAL_EXCLUSION will be set. // value ERR_MUTUAL_EXCLUSION will be set.
void AddDependency(int argId1, int argId2, bool mutual = false ); void AddDependency(int argId1, int argId2, bool mutual = false );
// This adds a dependency constraint. When Parse() is called, if argId1 // This adds a dependency constraint. When Parse() is called, if argId1
// exists on the command line independent from argId2, then the parse will fail. // exists on the command line independent from argId2, then the parse will fail.
// If the default param mutual is true, then the command parser will check for // If the default param mutual is true, then the command parser will check for
// argId1 if argId2 is passed. We do this, since it is possible for one arg to // argId1 if argId2 is passed. We do this, since it is possible for one arg to
// depend on another, but have the other arg alone on the command line, legally. // depend on another, but have the other arg alone on the command line, legally.
void Parse(int argc, const TCHAR *const * argv); // throw eCmdLine void Parse(int argc, const TCHAR *const * argv); // throw eCmdLine
// after AddArg() has been called for every argument that could be processed by the // after AddArg() has been called for every argument that could be processed by the
// command line, call this to tokenize argv. If the return value is false, then // command line, call this to tokenize argv. If the return value is false, then
// the input was invalid in some way; the actual error can be determined by calling // the input was invalid in some way; the actual error can be determined by calling
// GetErrorInfo() below. // GetErrorInfo() below.
void Clear(); void Clear();
// clear out all information that this class contains // clear out all information that this class contains
bool LookupArgInfo(int argId, TSTRING& arg, TSTRING& alias) const; bool LookupArgInfo(int argId, TSTRING& arg, TSTRING& alias) const;
// given an argId, fill out the strings with the argument and alias strings. Returns false // given an argId, fill out the strings with the argument and alias strings. Returns false
// if the argId cannot be found. This method is not very fast, so don't use it often. // if the argId cannot be found. This method is not very fast, so don't use it often.
#ifdef _DEBUG #ifdef _DEBUG
void TraceContents(int dl = -1) ; void TraceContents(int dl = -1) ;
#endif #endif
private: private:
void TestMutEx(); void TestMutEx();
// tests for mutual exclusion violations; if it fails, the current error is set and false // tests for mutual exclusion violations; if it fails, the current error is set and false
// is returned. // is returned.
void TestDependency(); void TestDependency();
// tests for all dependency violations. // tests for all dependency violations.
bool ArgInList(int argId); bool ArgInList(int argId);
// returns true if an argument with the specified id already exists in the list; this is used // returns true if an argument with the specified id already exists in the list; this is used
// to make sure the same arg doesn't appear >1 time on the command line // to make sure the same arg doesn't appear >1 time on the command line
// for storing information on paramers // for storing information on paramers
struct cArgInfo struct cArgInfo
{ {
int mId; int mId;
ParamCount mNumParams; ParamCount mNumParams;
cArgInfo(int i = -1, ParamCount p = PARAM_INVALID) : mId(i), mNumParams(p) {} cArgInfo(int i = -1, ParamCount p = PARAM_INVALID) : mId(i), mNumParams(p) {}
}; };
// for storing parsed argv information // for storing parsed argv information
struct cArgData struct cArgData
{ {
int mId; int mId;
std::vector<TSTRING> mParams; std::vector<TSTRING> mParams;
TSTRING mActualParam; // a string representation of what was actually on the command line TSTRING mActualParam; // a string representation of what was actually on the command line
cArgData(int id = -1, const TSTRING& actualParam = TSTRING(_T(""))) : mId(id), mActualParam(actualParam) {} cArgData(int id = -1, const TSTRING& actualParam = TSTRING(_T(""))) : mId(id), mActualParam(actualParam) {}
}; };
cHashTable<TSTRING, cArgInfo> mArgTable; cHashTable<TSTRING, cArgInfo> mArgTable;
cArgInfo mLastArgInfo; // info on the argument that comes at the end of the command line (with no associated '-x' or '--x') cArgInfo mLastArgInfo; // info on the argument that comes at the end of the command line (with no associated '-x' or '--x')
std::list<cArgData> mArgData; std::list<cArgData> mArgData;
std::list<std::pair<int,int> > mMutExList; // all of the mutual exclusions std::list<std::pair<int,int> > mMutExList; // all of the mutual exclusions
std::list< std::pair < std::pair<int,int>, bool > > mDependencyList; // all of the dependencies std::list< std::pair < std::pair<int,int>, bool > > mDependencyList; // all of the dependencies
std::set< int > mMultipleAllowed; std::set< int > mMultipleAllowed;
friend class cCmdLineIter; friend class cCmdLineIter;
}; };
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// cCmdLineIter -- used to iterate over the tokenized command line parameters; // cCmdLineIter -- used to iterate over the tokenized command line parameters;
// is only useful after cCmdLineParser::Parse() has been called. // is only useful after cCmdLineParser::Parse() has been called.
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
class cCmdLineIter class cCmdLineIter
{ {
public: public:
cCmdLineIter(const cCmdLineParser& parser); cCmdLineIter(const cCmdLineParser& parser);
// iteration // iteration
void SeekBegin() const; void SeekBegin() const;
bool Done() const; bool Done() const;
bool IsEmpty() const; bool IsEmpty() const;
void Next() const; void Next() const;
bool SeekToArg(int argId) const; bool SeekToArg(int argId) const;
// seeks to the argument with the given argId. returns // seeks to the argument with the given argId. returns
// false and Done() == true if it couldn't find it. // false and Done() == true if it couldn't find it.
// access to the argument data // access to the argument data
int ArgId() const; int ArgId() const;
// returns the id of this arg; ASSERTs if Done() == true // returns the id of this arg; ASSERTs if Done() == true
int NumParams() const; int NumParams() const;
// returns the number of parameters this argument has // returns the number of parameters this argument has
const TSTRING& ActualParam() const; const TSTRING& ActualParam() const;
// returns exactly what was passed on the command line (ie -- what the user typed) // returns exactly what was passed on the command line (ie -- what the user typed)
const TSTRING& ParamAt(int index) const; const TSTRING& ParamAt(int index) const;
// returns the parameter at the specified index. ASSERTs if // returns the parameter at the specified index. ASSERTs if
// the index is out of range. // the index is out of range.
private: private:
const std::list<cCmdLineParser::cArgData>& mList; const std::list<cCmdLineParser::cArgData>& mList;
mutable std::list<cCmdLineParser::cArgData>::const_iterator mIter; mutable std::list<cCmdLineParser::cArgData>::const_iterator mIter;
}; };
//############################################################################# //#############################################################################
// inline implementation // inline implementation
//############################################################################# //#############################################################################
inline cCmdLineIter::cCmdLineIter(const cCmdLineParser& parser) : inline cCmdLineIter::cCmdLineIter(const cCmdLineParser& parser) :
mList(parser.mArgData) mList(parser.mArgData)
{ {
SeekBegin(); SeekBegin();
} }
inline void cCmdLineIter::SeekBegin() const inline void cCmdLineIter::SeekBegin() const
{ {
mIter = mList.begin(); mIter = mList.begin();
} }
inline bool cCmdLineIter::Done() const inline bool cCmdLineIter::Done() const
{ {
return (mIter == mList.end()); return (mIter == mList.end());
} }
inline bool cCmdLineIter::IsEmpty() const inline bool cCmdLineIter::IsEmpty() const
{ {
return (mList.size() == 0); return (mList.size() == 0);
} }
inline void cCmdLineIter::Next() const inline void cCmdLineIter::Next() const
{ {
mIter++; mIter++;
} }
inline int cCmdLineIter::ArgId() const inline int cCmdLineIter::ArgId() const
{ {
ASSERT(! Done()); ASSERT(! Done());
return mIter->mId; return mIter->mId;
} }
inline int cCmdLineIter::NumParams() const inline int cCmdLineIter::NumParams() const
{ {
ASSERT(! Done()); ASSERT(! Done());
return mIter->mParams.size(); return mIter->mParams.size();
} }
inline const TSTRING& cCmdLineIter::ActualParam() const inline const TSTRING& cCmdLineIter::ActualParam() const
{ {
ASSERT(! Done()); ASSERT(! Done());
return mIter->mActualParam; return mIter->mActualParam;
} }
inline const TSTRING& cCmdLineIter::ParamAt(int index) const inline const TSTRING& cCmdLineIter::ParamAt(int index) const
{ {
ASSERT((index >= 0) && (index < NumParams())); ASSERT((index >= 0) && (index < NumParams()));
return mIter->mParams[index]; return mIter->mParams[index];
} }

View File

@ -84,9 +84,9 @@ TSS_EXCEPTION( eConverterUnknownCodepage, eConverter );
* or a byte value is not a character, it is cast to a reserved * or a byte value is not a character, it is cast to a reserved
* region of UCS2 ( 0xE000 - 0xE0FF ). * region of UCS2 ( 0xE000 - 0xE0FF ).
* CONSTRAINTS: * CONSTRAINTS:
* *
* INVARIANTS: * INVARIANTS:
* *
*/ */
class iCodeConverter class iCodeConverter
{ {

View File

@ -46,7 +46,7 @@ TSS_ImplementPackage( cCore )
cCore::cCore() cCore::cCore()
{ {
TSS_REGISTER_PKG_ERRORS( core ); TSS_REGISTER_PKG_ERRORS( core );
// NOTE: Initialize code converter when cCore is a dependency // NOTE: Initialize code converter when cCore is a dependency
// of another package (created on first call to GetInstance(), // of another package (created on first call to GetInstance(),

View File

@ -43,17 +43,17 @@
//--Requirements //--Requirements
#include "package.h" // for: Packaging Abstraction #include "package.h" // for: Packaging Abstraction
//--Classes //--Classes
TSS_BeginPackage( cCore ) TSS_BeginPackage( cCore )
TSS_DECLARE_STRINGTABLE; TSS_DECLARE_STRINGTABLE;
public: public:
cCore(); cCore();
TSS_EndPackage( cCore ) TSS_EndPackage( cCore )

View File

@ -68,34 +68,34 @@ TSS_REGISTER_ERROR( eBadCmdLine(), _T("Command line error.") );
/// Archive /// Archive
TSS_REGISTER_ERROR( eArchive(), _T("Archive error.") ) TSS_REGISTER_ERROR( eArchive(), _T("Archive error.") )
TSS_REGISTER_ERROR( eArchiveOpen(), _T("File could not be opened.") ) TSS_REGISTER_ERROR( eArchiveOpen(), _T("File could not be opened.") )
TSS_REGISTER_ERROR( eArchiveWrite(), _T("File could not be written.") ) TSS_REGISTER_ERROR( eArchiveWrite(), _T("File could not be written.") )
TSS_REGISTER_ERROR( eArchiveRead(), _T("File could not be read.") ) TSS_REGISTER_ERROR( eArchiveRead(), _T("File could not be read.") )
TSS_REGISTER_ERROR( eArchiveEOF(), _T("End of file reached.") ) TSS_REGISTER_ERROR( eArchiveEOF(), _T("End of file reached.") )
TSS_REGISTER_ERROR( eArchiveSeek(), _T("File seek failed.") ) TSS_REGISTER_ERROR( eArchiveSeek(), _T("File seek failed.") )
TSS_REGISTER_ERROR( eArchiveMemmap(), _T("Memory mapped archive file invalid.") ) TSS_REGISTER_ERROR( eArchiveMemmap(), _T("Memory mapped archive file invalid.") )
TSS_REGISTER_ERROR( eArchiveOutOfMem(), _T("Archive ran out of memory.") ) TSS_REGISTER_ERROR( eArchiveOutOfMem(), _T("Archive ran out of memory.") )
TSS_REGISTER_ERROR( eArchiveInvalidOp(),_T("Archive logic error.") ) TSS_REGISTER_ERROR( eArchiveInvalidOp(),_T("Archive logic error.") )
TSS_REGISTER_ERROR( eArchiveFormat(), _T("Archive file format invalid.") ) TSS_REGISTER_ERROR( eArchiveFormat(), _T("Archive file format invalid.") )
TSS_REGISTER_ERROR( eArchiveNotRegularFile(), _T("File is not a regular file.") ) TSS_REGISTER_ERROR( eArchiveNotRegularFile(), _T("File is not a regular file.") )
TSS_REGISTER_ERROR( eArchiveCrypto(), _T("File could not be decrypted.") ) TSS_REGISTER_ERROR( eArchiveCrypto(), _T("File could not be decrypted.") )
TSS_REGISTER_ERROR( eArchiveStringTooLong(), _T("String was too long.") ) TSS_REGISTER_ERROR( eArchiveStringTooLong(), _T("String was too long.") )
/// File /// File
TSS_REGISTER_ERROR( eFile(), _T("File error.") ) TSS_REGISTER_ERROR( eFile(), _T("File error.") )
TSS_REGISTER_ERROR( eFileOpen(), _T("File could not be opened.") ) TSS_REGISTER_ERROR( eFileOpen(), _T("File could not be opened.") )
TSS_REGISTER_ERROR( eFileWrite(), _T("File could not be written.") ) TSS_REGISTER_ERROR( eFileWrite(), _T("File could not be written.") )
TSS_REGISTER_ERROR( eFileRead(), _T("File could not be read.") ) TSS_REGISTER_ERROR( eFileRead(), _T("File could not be read.") )
TSS_REGISTER_ERROR( eFileEOF(), _T("End of file reached.") ) TSS_REGISTER_ERROR( eFileEOF(), _T("End of file reached.") )
TSS_REGISTER_ERROR( eFileSeek(), _T("File seek failed.") ) TSS_REGISTER_ERROR( eFileSeek(), _T("File seek failed.") )
TSS_REGISTER_ERROR( eFileInvalidOp(), _T("File logic error.") ) TSS_REGISTER_ERROR( eFileInvalidOp(), _T("File logic error.") )
TSS_REGISTER_ERROR( eFileTrunc(), _T("File could not be truncated.") ) TSS_REGISTER_ERROR( eFileTrunc(), _T("File could not be truncated.") )
TSS_REGISTER_ERROR( eFileClose(), _T("File could not be closed.") ) TSS_REGISTER_ERROR( eFileClose(), _T("File could not be closed.") )
TSS_REGISTER_ERROR( eFileFlush(), _T("File could not be flushed.") ) TSS_REGISTER_ERROR( eFileFlush(), _T("File could not be flushed.") )
TSS_REGISTER_ERROR( eFileRewind(), _T("File could not be rewound.") ) TSS_REGISTER_ERROR( eFileRewind(), _T("File could not be rewound.") )
/// Win32 /// Win32
@ -106,32 +106,32 @@ TSS_REGISTER_ERROR(eUnix(), _T("Unix API failure.") )
/// FSServices /// FSServices
TSS_REGISTER_ERROR( eFSServices(), _T("File system error.") ) TSS_REGISTER_ERROR( eFSServices(), _T("File system error.") )
TSS_REGISTER_ERROR( eFSServicesGeneric(),_T("File system error.") ) TSS_REGISTER_ERROR( eFSServicesGeneric(),_T("File system error.") )
/// Serializer /// Serializer
TSS_REGISTER_ERROR( eSerializerUnknownType(), _T("Unknown type encountered in file.\nFile format may not be valid for this platform.") ) TSS_REGISTER_ERROR( eSerializerUnknownType(), _T("Unknown type encountered in file.\nFile format may not be valid for this platform.") )
TSS_REGISTER_ERROR( eSerializerInputStreamFmt(), _T("Invalid input stream format.") ) TSS_REGISTER_ERROR( eSerializerInputStreamFmt(), _T("Invalid input stream format.") )
TSS_REGISTER_ERROR( eSerializerOutputStreamFmt(), _T("Invalid output stream format.") ) TSS_REGISTER_ERROR( eSerializerOutputStreamFmt(), _T("Invalid output stream format.") )
TSS_REGISTER_ERROR( eSerializerInputStremTypeArray(), _T("A bad index was encountered in file.") ) TSS_REGISTER_ERROR( eSerializerInputStremTypeArray(), _T("A bad index was encountered in file.") )
TSS_REGISTER_ERROR( eSerializerArchive(), _T("File read encountered an archive error.") ) TSS_REGISTER_ERROR( eSerializerArchive(), _T("File read encountered an archive error.") )
TSS_REGISTER_ERROR( eSerializerVersionMismatch(), _T("File version mismatch.") ) TSS_REGISTER_ERROR( eSerializerVersionMismatch(), _T("File version mismatch.") )
TSS_REGISTER_ERROR( eSerializerEncryption(), _T("File encryption error.") ) TSS_REGISTER_ERROR( eSerializerEncryption(), _T("File encryption error.") )
TSS_REGISTER_ERROR( eSerializer(), _T("File format error.") ) TSS_REGISTER_ERROR( eSerializer(), _T("File format error.") )
/// Command Line /// Command Line
TSS_REGISTER_ERROR( eCmdLine(), _T("Command line parsing error.") ) TSS_REGISTER_ERROR( eCmdLine(), _T("Command line parsing error.") )
TSS_REGISTER_ERROR( eCmdLineInvalidArg(), _T("Invalid argument passed on command line.") ) TSS_REGISTER_ERROR( eCmdLineInvalidArg(), _T("Invalid argument passed on command line.") )
TSS_REGISTER_ERROR( eCmdLineBadArgParam(), _T("Incorrect number of parameters to a command line argument.") ) TSS_REGISTER_ERROR( eCmdLineBadArgParam(), _T("Incorrect number of parameters to a command line argument.") )
TSS_REGISTER_ERROR( eCmdLineBadParam(), _T("Incorrect number of parameters on command line.") ) TSS_REGISTER_ERROR( eCmdLineBadParam(), _T("Incorrect number of parameters on command line.") )
TSS_REGISTER_ERROR( eCmdLineBadSwitchPos(), _T("Switch appears after final command line parameter.") ) TSS_REGISTER_ERROR( eCmdLineBadSwitchPos(), _T("Switch appears after final command line parameter.") )
TSS_REGISTER_ERROR( eCmdLineMutEx(), _T("Specified command line switches are mutually exclusive.") ) TSS_REGISTER_ERROR( eCmdLineMutEx(), _T("Specified command line switches are mutually exclusive.") )
TSS_REGISTER_ERROR( eCmdLineDependency(), _T("Command line parameter missing.") ) TSS_REGISTER_ERROR( eCmdLineDependency(), _T("Command line parameter missing.") )
TSS_REGISTER_ERROR( eCmdLineMultiArg(), _T("Command line argument specified more than once.") ) TSS_REGISTER_ERROR( eCmdLineMultiArg(), _T("Command line argument specified more than once.") )
/// TWLocale /// TWLocale

View File

@ -42,7 +42,7 @@
#include "core/errortable.h" #include "core/errortable.h"
TSS_DECLARE_ERROR_REGISTRATION( core ) TSS_DECLARE_ERROR_REGISTRATION( core )
#endif//__COREERRORS_H #endif//__COREERRORS_H

View File

@ -51,11 +51,11 @@ TSS_BeginStringtable( cCore )
TSS_StringEntry( core::STR_ERROR_CONTINUING, _T("Continuing...") ), TSS_StringEntry( core::STR_ERROR_CONTINUING, _T("Continuing...") ),
TSS_StringEntry( core::STR_ERR2_FILENAME, _T("Filename: ") ), TSS_StringEntry( core::STR_ERR2_FILENAME, _T("Filename: ") ),
TSS_StringEntry( core::STR_ERROR_FILENAME, _T("Filename: ") ), TSS_StringEntry( core::STR_ERROR_FILENAME, _T("Filename: ") ),
TSS_StringEntry( core::STR_UNKNOWN, _T("Unknown") ), TSS_StringEntry( core::STR_UNKNOWN, _T("Unknown") ),
TSS_StringEntry( core::STR_NUMBER_TOO_BIG, _T("Number too big") ), TSS_StringEntry( core::STR_NUMBER_TOO_BIG, _T("Number too big") ),
TSS_StringEntry( core::STR_SIGNAL, _T("Software interrupt forced exit:") ), TSS_StringEntry( core::STR_SIGNAL, _T("Software interrupt forced exit:") ),
TSS_StringEntry( core::STR_NEWLINE, _T("\n") ), TSS_StringEntry( core::STR_NEWLINE, _T("\n") ),
TSS_StringEntry( core::STR_MEMARCHIVE_FILENAME, _T("Error occured in internal memory file") ), TSS_StringEntry( core::STR_MEMARCHIVE_FILENAME, _T("Error occured in internal memory file") ),
TSS_StringEntry( core::STR_MEMARCHIVE_ERRSTR, _T("") ), TSS_StringEntry( core::STR_MEMARCHIVE_ERRSTR, _T("") ),
TSS_StringEntry( core::STR_ENDOFTIME, _T("Tripwire is not designed to run past the year 2038.\nNow exiting...") ), TSS_StringEntry( core::STR_ENDOFTIME, _T("Tripwire is not designed to run past the year 2038.\nNow exiting...") ),
TSS_StringEntry( core::STR_UNKNOWN_TIME, _T("Unknown time") ), TSS_StringEntry( core::STR_UNKNOWN_TIME, _T("Unknown time") ),

View File

@ -59,7 +59,7 @@ TSS_BeginStringIds( core )
STR_ERROR_FILENAME, STR_ERROR_FILENAME,
STR_NUMBER_TOO_BIG, STR_NUMBER_TOO_BIG,
STR_UNKNOWN, STR_UNKNOWN,
STR_SIGNAL, STR_SIGNAL,
STR_NEWLINE, STR_NEWLINE,
STR_MEMARCHIVE_FILENAME, STR_MEMARCHIVE_FILENAME,
STR_MEMARCHIVE_ERRSTR, STR_MEMARCHIVE_ERRSTR,

View File

@ -33,7 +33,7 @@
* *
* *
* Copyright (c) 1991, 1993 * Copyright (c) 1991, 1993
* The Regents of the University of California. All rights reserved. * The Regents of the University of California. All rights reserved.
* *
* This code is derived from software contributed to Berkeley by * This code is derived from software contributed to Berkeley by
* James W. Williams of NASA Goddard Space Flight Center. * James W. Williams of NASA Goddard Space Flight Center.
@ -48,8 +48,8 @@
* documentation and/or other materials provided with the distribution. * documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software * 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement: * must display the following acknowledgement:
* This product includes software developed by the University of * This product includes software developed by the University of
* California, Berkeley and its contributors. * California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors * 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software * may be used to endorse or promote products derived from this software
* without specific prior written permission. * without specific prior written permission.
@ -85,58 +85,58 @@
#define BUFSIZE 4096 #define BUFSIZE 4096
static uint32 crctab[] = { static uint32 crctab[] = {
0x0, 0x0,
0x04c11db7, 0x09823b6e, 0x0d4326d9, 0x130476dc, 0x17c56b6b, 0x04c11db7, 0x09823b6e, 0x0d4326d9, 0x130476dc, 0x17c56b6b,
0x1a864db2, 0x1e475005, 0x2608edb8, 0x22c9f00f, 0x2f8ad6d6, 0x1a864db2, 0x1e475005, 0x2608edb8, 0x22c9f00f, 0x2f8ad6d6,
0x2b4bcb61, 0x350c9b64, 0x31cd86d3, 0x3c8ea00a, 0x384fbdbd, 0x2b4bcb61, 0x350c9b64, 0x31cd86d3, 0x3c8ea00a, 0x384fbdbd,
0x4c11db70, 0x48d0c6c7, 0x4593e01e, 0x4152fda9, 0x5f15adac, 0x4c11db70, 0x48d0c6c7, 0x4593e01e, 0x4152fda9, 0x5f15adac,
0x5bd4b01b, 0x569796c2, 0x52568b75, 0x6a1936c8, 0x6ed82b7f, 0x5bd4b01b, 0x569796c2, 0x52568b75, 0x6a1936c8, 0x6ed82b7f,
0x639b0da6, 0x675a1011, 0x791d4014, 0x7ddc5da3, 0x709f7b7a, 0x639b0da6, 0x675a1011, 0x791d4014, 0x7ddc5da3, 0x709f7b7a,
0x745e66cd, 0x9823b6e0, 0x9ce2ab57, 0x91a18d8e, 0x95609039, 0x745e66cd, 0x9823b6e0, 0x9ce2ab57, 0x91a18d8e, 0x95609039,
0x8b27c03c, 0x8fe6dd8b, 0x82a5fb52, 0x8664e6e5, 0xbe2b5b58, 0x8b27c03c, 0x8fe6dd8b, 0x82a5fb52, 0x8664e6e5, 0xbe2b5b58,
0xbaea46ef, 0xb7a96036, 0xb3687d81, 0xad2f2d84, 0xa9ee3033, 0xbaea46ef, 0xb7a96036, 0xb3687d81, 0xad2f2d84, 0xa9ee3033,
0xa4ad16ea, 0xa06c0b5d, 0xd4326d90, 0xd0f37027, 0xddb056fe, 0xa4ad16ea, 0xa06c0b5d, 0xd4326d90, 0xd0f37027, 0xddb056fe,
0xd9714b49, 0xc7361b4c, 0xc3f706fb, 0xceb42022, 0xca753d95, 0xd9714b49, 0xc7361b4c, 0xc3f706fb, 0xceb42022, 0xca753d95,
0xf23a8028, 0xf6fb9d9f, 0xfbb8bb46, 0xff79a6f1, 0xe13ef6f4, 0xf23a8028, 0xf6fb9d9f, 0xfbb8bb46, 0xff79a6f1, 0xe13ef6f4,
0xe5ffeb43, 0xe8bccd9a, 0xec7dd02d, 0x34867077, 0x30476dc0, 0xe5ffeb43, 0xe8bccd9a, 0xec7dd02d, 0x34867077, 0x30476dc0,
0x3d044b19, 0x39c556ae, 0x278206ab, 0x23431b1c, 0x2e003dc5, 0x3d044b19, 0x39c556ae, 0x278206ab, 0x23431b1c, 0x2e003dc5,
0x2ac12072, 0x128e9dcf, 0x164f8078, 0x1b0ca6a1, 0x1fcdbb16, 0x2ac12072, 0x128e9dcf, 0x164f8078, 0x1b0ca6a1, 0x1fcdbb16,
0x018aeb13, 0x054bf6a4, 0x0808d07d, 0x0cc9cdca, 0x7897ab07, 0x018aeb13, 0x054bf6a4, 0x0808d07d, 0x0cc9cdca, 0x7897ab07,
0x7c56b6b0, 0x71159069, 0x75d48dde, 0x6b93dddb, 0x6f52c06c, 0x7c56b6b0, 0x71159069, 0x75d48dde, 0x6b93dddb, 0x6f52c06c,
0x6211e6b5, 0x66d0fb02, 0x5e9f46bf, 0x5a5e5b08, 0x571d7dd1, 0x6211e6b5, 0x66d0fb02, 0x5e9f46bf, 0x5a5e5b08, 0x571d7dd1,
0x53dc6066, 0x4d9b3063, 0x495a2dd4, 0x44190b0d, 0x40d816ba, 0x53dc6066, 0x4d9b3063, 0x495a2dd4, 0x44190b0d, 0x40d816ba,
0xaca5c697, 0xa864db20, 0xa527fdf9, 0xa1e6e04e, 0xbfa1b04b, 0xaca5c697, 0xa864db20, 0xa527fdf9, 0xa1e6e04e, 0xbfa1b04b,
0xbb60adfc, 0xb6238b25, 0xb2e29692, 0x8aad2b2f, 0x8e6c3698, 0xbb60adfc, 0xb6238b25, 0xb2e29692, 0x8aad2b2f, 0x8e6c3698,
0x832f1041, 0x87ee0df6, 0x99a95df3, 0x9d684044, 0x902b669d, 0x832f1041, 0x87ee0df6, 0x99a95df3, 0x9d684044, 0x902b669d,
0x94ea7b2a, 0xe0b41de7, 0xe4750050, 0xe9362689, 0xedf73b3e, 0x94ea7b2a, 0xe0b41de7, 0xe4750050, 0xe9362689, 0xedf73b3e,
0xf3b06b3b, 0xf771768c, 0xfa325055, 0xfef34de2, 0xc6bcf05f, 0xf3b06b3b, 0xf771768c, 0xfa325055, 0xfef34de2, 0xc6bcf05f,
0xc27dede8, 0xcf3ecb31, 0xcbffd686, 0xd5b88683, 0xd1799b34, 0xc27dede8, 0xcf3ecb31, 0xcbffd686, 0xd5b88683, 0xd1799b34,
0xdc3abded, 0xd8fba05a, 0x690ce0ee, 0x6dcdfd59, 0x608edb80, 0xdc3abded, 0xd8fba05a, 0x690ce0ee, 0x6dcdfd59, 0x608edb80,
0x644fc637, 0x7a089632, 0x7ec98b85, 0x738aad5c, 0x774bb0eb, 0x644fc637, 0x7a089632, 0x7ec98b85, 0x738aad5c, 0x774bb0eb,
0x4f040d56, 0x4bc510e1, 0x46863638, 0x42472b8f, 0x5c007b8a, 0x4f040d56, 0x4bc510e1, 0x46863638, 0x42472b8f, 0x5c007b8a,
0x58c1663d, 0x558240e4, 0x51435d53, 0x251d3b9e, 0x21dc2629, 0x58c1663d, 0x558240e4, 0x51435d53, 0x251d3b9e, 0x21dc2629,
0x2c9f00f0, 0x285e1d47, 0x36194d42, 0x32d850f5, 0x3f9b762c, 0x2c9f00f0, 0x285e1d47, 0x36194d42, 0x32d850f5, 0x3f9b762c,
0x3b5a6b9b, 0x0315d626, 0x07d4cb91, 0x0a97ed48, 0x0e56f0ff, 0x3b5a6b9b, 0x0315d626, 0x07d4cb91, 0x0a97ed48, 0x0e56f0ff,
0x1011a0fa, 0x14d0bd4d, 0x19939b94, 0x1d528623, 0xf12f560e, 0x1011a0fa, 0x14d0bd4d, 0x19939b94, 0x1d528623, 0xf12f560e,
0xf5ee4bb9, 0xf8ad6d60, 0xfc6c70d7, 0xe22b20d2, 0xe6ea3d65, 0xf5ee4bb9, 0xf8ad6d60, 0xfc6c70d7, 0xe22b20d2, 0xe6ea3d65,
0xeba91bbc, 0xef68060b, 0xd727bbb6, 0xd3e6a601, 0xdea580d8, 0xeba91bbc, 0xef68060b, 0xd727bbb6, 0xd3e6a601, 0xdea580d8,
0xda649d6f, 0xc423cd6a, 0xc0e2d0dd, 0xcda1f604, 0xc960ebb3, 0xda649d6f, 0xc423cd6a, 0xc0e2d0dd, 0xcda1f604, 0xc960ebb3,
0xbd3e8d7e, 0xb9ff90c9, 0xb4bcb610, 0xb07daba7, 0xae3afba2, 0xbd3e8d7e, 0xb9ff90c9, 0xb4bcb610, 0xb07daba7, 0xae3afba2,
0xaafbe615, 0xa7b8c0cc, 0xa379dd7b, 0x9b3660c6, 0x9ff77d71, 0xaafbe615, 0xa7b8c0cc, 0xa379dd7b, 0x9b3660c6, 0x9ff77d71,
0x92b45ba8, 0x9675461f, 0x8832161a, 0x8cf30bad, 0x81b02d74, 0x92b45ba8, 0x9675461f, 0x8832161a, 0x8cf30bad, 0x81b02d74,
0x857130c3, 0x5d8a9099, 0x594b8d2e, 0x5408abf7, 0x50c9b640, 0x857130c3, 0x5d8a9099, 0x594b8d2e, 0x5408abf7, 0x50c9b640,
0x4e8ee645, 0x4a4ffbf2, 0x470cdd2b, 0x43cdc09c, 0x7b827d21, 0x4e8ee645, 0x4a4ffbf2, 0x470cdd2b, 0x43cdc09c, 0x7b827d21,
0x7f436096, 0x7200464f, 0x76c15bf8, 0x68860bfd, 0x6c47164a, 0x7f436096, 0x7200464f, 0x76c15bf8, 0x68860bfd, 0x6c47164a,
0x61043093, 0x65c52d24, 0x119b4be9, 0x155a565e, 0x18197087, 0x61043093, 0x65c52d24, 0x119b4be9, 0x155a565e, 0x18197087,
0x1cd86d30, 0x029f3d35, 0x065e2082, 0x0b1d065b, 0x0fdc1bec, 0x1cd86d30, 0x029f3d35, 0x065e2082, 0x0b1d065b, 0x0fdc1bec,
0x3793a651, 0x3352bbe6, 0x3e119d3f, 0x3ad08088, 0x2497d08d, 0x3793a651, 0x3352bbe6, 0x3e119d3f, 0x3ad08088, 0x2497d08d,
0x2056cd3a, 0x2d15ebe3, 0x29d4f654, 0xc5a92679, 0xc1683bce, 0x2056cd3a, 0x2d15ebe3, 0x29d4f654, 0xc5a92679, 0xc1683bce,
0xcc2b1d17, 0xc8ea00a0, 0xd6ad50a5, 0xd26c4d12, 0xdf2f6bcb, 0xcc2b1d17, 0xc8ea00a0, 0xd6ad50a5, 0xd26c4d12, 0xdf2f6bcb,
0xdbee767c, 0xe3a1cbc1, 0xe760d676, 0xea23f0af, 0xeee2ed18, 0xdbee767c, 0xe3a1cbc1, 0xe760d676, 0xea23f0af, 0xeee2ed18,
0xf0a5bd1d, 0xf464a0aa, 0xf9278673, 0xfde69bc4, 0x89b8fd09, 0xf0a5bd1d, 0xf464a0aa, 0xf9278673, 0xfde69bc4, 0x89b8fd09,
0x8d79e0be, 0x803ac667, 0x84fbdbd0, 0x9abc8bd5, 0x9e7d9662, 0x8d79e0be, 0x803ac667, 0x84fbdbd0, 0x9abc8bd5, 0x9e7d9662,
0x933eb0bb, 0x97ffad0c, 0xafb010b1, 0xab710d06, 0xa6322bdf, 0x933eb0bb, 0x97ffad0c, 0xafb010b1, 0xab710d06, 0xa6322bdf,
0xa2f33668, 0xbcb4666d, 0xb8757bda, 0xb5365d03, 0xb1f740b4 0xa2f33668, 0xbcb4666d, 0xb8757bda, 0xb5365d03, 0xb1f740b4
}; };
/* /*
@ -145,8 +145,8 @@ static uint32 crctab[] = {
* locations to store the crc and the number of bytes read. It returns 0 on * locations to store the crc and the number of bytes read. It returns 0 on
* success and 1 on failure. Errno is set on failure. * success and 1 on failure. Errno is set on failure.
*/ */
#define COMPUTE(var, ch) (var) = ((var) << 8) ^ \ #define COMPUTE(var, ch) (var) = ((var) << 8) ^ \
crctab[0xff & (unsigned)((var) >> 24 ^ (ch))] crctab[0xff & (unsigned)((var) >> 24 ^ (ch))]
void crcInit( CRC_INFO& crcInfo ) void crcInit( CRC_INFO& crcInfo )
{ {
@ -156,22 +156,22 @@ void crcInit( CRC_INFO& crcInfo )
void crcUpdate( CRC_INFO& crcInfo, const uint8* pbData, int cbDataLen ) void crcUpdate( CRC_INFO& crcInfo, const uint8* pbData, int cbDataLen )
{ {
for( int i = 0; i < cbDataLen; i++, pbData++ ) for( int i = 0; i < cbDataLen; i++, pbData++ )
{ {
COMPUTE( crcInfo.crc, *pbData ); COMPUTE( crcInfo.crc, *pbData );
} }
crcInfo.cbTotalLen += cbDataLen; crcInfo.cbTotalLen += cbDataLen;
} }
void crcFinit( CRC_INFO& crcInfo ) void crcFinit( CRC_INFO& crcInfo )
{ {
// include the length // include the length
// //
uint32 len = crcInfo.cbTotalLen; uint32 len = crcInfo.cbTotalLen;
for(; len != 0; len >>= 8) for(; len != 0; len >>= 8)
COMPUTE( crcInfo.crc, len & 0xff ); COMPUTE( crcInfo.crc, len & 0xff );
crcInfo.crc = ~(crcInfo.crc) & 0xFFFFFFFF; crcInfo.crc = ~(crcInfo.crc) & 0xFFFFFFFF;
} }

View File

@ -48,7 +48,7 @@ void crcUpdate( CRC_INFO& crcInfo, const uint8* pbData, int cbDataLen );
void crcFinit ( CRC_INFO& crcInfo ); void crcFinit ( CRC_INFO& crcInfo );
// calculates the crc for len bytes starting at pBuf // calculates the crc for len bytes starting at pBuf
//Wrapper function for CRC32 in crc32.cpp //Wrapper function for CRC32 in crc32.cpp
#endif //__CRC32_H #endif //__CRC32_H

View File

@ -44,10 +44,10 @@
#include <fstream> #include <fstream>
#include <cstdio> #include <cstdio>
int cDebug::mDebugLevel(10); int cDebug::mDebugLevel(10);
uint32 cDebug::mOutMask(cDebug::OUT_TRACE); uint32 cDebug::mOutMask(cDebug::OUT_TRACE);
std::ofstream cDebug::logfile; std::ofstream cDebug::logfile;
//mDebugLevel default == 10, mOutMask default == OUT_TRACE. //mDebugLevel default == 10, mOutMask default == OUT_TRACE.
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// Constructors and Destructor // Constructors and Destructor
@ -63,13 +63,13 @@ cDebug::cDebug(const char* label)
cDebug::cDebug(const cDebug &rhs) cDebug::cDebug(const cDebug &rhs)
{ {
strcpy(mLabel, rhs.mLabel); strcpy(mLabel, rhs.mLabel);
} }
cDebug::~cDebug() cDebug::~cDebug()
{ {
if(logfile) if(logfile)
logfile.close(); logfile.close();
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -79,38 +79,38 @@ cDebug::~cDebug()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cDebug::Trace(int levelNum, const char* format, ...) void cDebug::Trace(int levelNum, const char* format, ...)
{ {
if (levelNum > mDebugLevel) if (levelNum > mDebugLevel)
return; return;
// create the output buffer // create the output buffer
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::Trace(int levelNum, const wchar_t* format, ...) void cDebug::Trace(int levelNum, const wchar_t* format, ...)
{ {
if (levelNum > mDebugLevel) if (levelNum > mDebugLevel)
return; return;
// create the output buffer // create the output buffer
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// DoTrace() // DoTrace()
// internal helper function -- does the actual printing to logfile, // internal helper function -- does the actual printing to logfile,
// console, etc... // console, etc...
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cDebug::DoTrace(const char *format, va_list &args) void cDebug::DoTrace(const char *format, va_list &args)
{ {
size_t guard1 = 0xBABABABA; size_t guard1 = 0xBABABABA;
char out[2048]; char out[2048];
size_t guard2 = 0xBABABABA; size_t guard2 = 0xBABABABA;
vsprintf(out, format, args); vsprintf(out, format, args);
@ -118,32 +118,32 @@ void cDebug::DoTrace(const char *format, va_list &args)
ASSERT(guard1 == 0xBABABABA && guard2 == 0xBABABABA); // string was too long ASSERT(guard1 == 0xBABABABA && guard2 == 0xBABABABA); // string was too long
ASSERT(strlen(out) < 1024); ASSERT(strlen(out) < 1024);
std::ostringstream ostr; std::ostringstream ostr;
ostr.setf(std::ios::left); ostr.setf(std::ios::left);
ostr.width(40); ostr.width(40);
ostr << mLabel; ostr << mLabel;
ostr.width(0); ostr.width(0);
ostr << out; ostr << out;
if ((mOutMask & OUT_STDOUT) != 0) if ((mOutMask & OUT_STDOUT) != 0)
{ {
std::cout << ostr.str().c_str(); std::cout << ostr.str().c_str();
std::cout.flush(); std::cout.flush();
} }
// //
//make it output to log file! //make it output to log file!
// //
if ((mOutMask & OUT_FILE) != 0) if ((mOutMask & OUT_FILE) != 0)
{ {
// the logfile is narrow chars only... // the logfile is narrow chars only...
logfile.setf(std::ios::left); logfile.setf(std::ios::left);
logfile.width(40); logfile.width(40);
logfile << mLabel; logfile << mLabel;
logfile.width(0); logfile.width(0);
logfile << out; logfile << out;
logfile.flush(); logfile.flush();
} }
} }
@ -156,42 +156,42 @@ void cDebug::DoTrace(const wchar_t *format, va_list &args)
#else #else
size_t guard1 = 0xBABABABA; size_t guard1 = 0xBABABABA;
wchar_t out[2048]; wchar_t out[2048];
size_t guard2 = 0xBABABABA; size_t guard2 = 0xBABABABA;
vswprintf(out, format, args); vswprintf(out, format, args);
ASSERT(guard1 == 0xBABABABA && guard2 == 0xBABABABA); // string was too long ASSERT(guard1 == 0xBABABABA && guard2 == 0xBABABABA); // string was too long
char nout[1024]; char nout[1024];
if (wcstombs(nout, out, 1024) == -1) if (wcstombs(nout, out, 1024) == -1)
strcpy(nout, "XXX Unconvertable wide char detected in cDebug::DoTrace()\n"); strcpy(nout, "XXX Unconvertable wide char detected in cDebug::DoTrace()\n");
std::ostringstream ostr; std::ostringstream ostr;
ostr.setf(std::ios::left); ostr.setf(std::ios::left);
ostr.width(40); ostr.width(40);
ostr << mLabel; ostr << mLabel;
ostr.width(0); ostr.width(0);
ostr << nout; ostr << nout;
if ((mOutMask & OUT_STDOUT) != 0) if ((mOutMask & OUT_STDOUT) != 0)
{ {
std::cout << ostr.str().c_str(); std::cout << ostr.str().c_str();
std::cout.flush(); std::cout.flush();
} }
// //
//make it output to log file! //make it output to log file!
// //
if ((mOutMask & OUT_FILE) != 0) if ((mOutMask & OUT_FILE) != 0)
{ {
// the logfile is narrow chars only... // the logfile is narrow chars only...
logfile.setf(std::ios::left); logfile.setf(std::ios::left);
logfile.width(40); logfile.width(40);
logfile << mLabel; logfile << mLabel;
logfile.width(0); logfile.width(0);
logfile << out; logfile << out;
logfile.flush(); logfile.flush();
} }
#endif // IS_UNIX #endif // IS_UNIX
} }
@ -200,151 +200,151 @@ void cDebug::DoTrace(const wchar_t *format, va_list &args)
// //
// wrappers around Trace() that requires less typing // wrappers around Trace() that requires less typing
// TODO: this is quick and dirty, but lets me check in all these files right away. --ghk // TODO: this is quick and dirty, but lets me check in all these files right away. --ghk
// //
void cDebug::TraceAlways(const char *format, ...) void cDebug::TraceAlways(const char *format, ...)
{ {
if (D_ALWAYS > mDebugLevel) if (D_ALWAYS > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceError(const char *format, ...) void cDebug::TraceError(const char *format, ...)
{ {
if (D_ERROR > mDebugLevel) if (D_ERROR > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceWarning(const char *format, ...) void cDebug::TraceWarning(const char *format, ...)
{ {
if (D_WARNING > mDebugLevel) if (D_WARNING > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceDebug(const char *format, ...) void cDebug::TraceDebug(const char *format, ...)
{ {
if (D_DEBUG > mDebugLevel) if (D_DEBUG > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceDetail(const char *format, ...) void cDebug::TraceDetail(const char *format, ...)
{ {
if (D_DETAIL > mDebugLevel) if (D_DETAIL > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceNever(const char *format, ...) void cDebug::TraceNever(const char *format, ...)
{ {
if (D_NEVER > mDebugLevel) if (D_NEVER > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceAlways(const wchar_t *format, ...) void cDebug::TraceAlways(const wchar_t *format, ...)
{ {
if (D_ALWAYS > mDebugLevel) if (D_ALWAYS > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceError(const wchar_t *format, ...) void cDebug::TraceError(const wchar_t *format, ...)
{ {
if (D_ERROR > mDebugLevel) if (D_ERROR > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceWarning(const wchar_t *format, ...) void cDebug::TraceWarning(const wchar_t *format, ...)
{ {
if (D_WARNING > mDebugLevel) if (D_WARNING > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceDebug(const wchar_t *format, ...) void cDebug::TraceDebug(const wchar_t *format, ...)
{ {
if (D_DEBUG > mDebugLevel) if (D_DEBUG > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceDetail(const wchar_t *format, ...) void cDebug::TraceDetail(const wchar_t *format, ...)
{ {
if (D_DETAIL > mDebugLevel) if (D_DETAIL > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceNever(const wchar_t *format, ...) void cDebug::TraceNever(const wchar_t *format, ...)
{ {
if (D_NEVER > mDebugLevel) if (D_NEVER > mDebugLevel)
return; return;
// fill up arglist, and pass to printing routine // fill up arglist, and pass to printing routine
va_list args; va_list args;
va_start(args, format); va_start(args, format);
DoTrace(format, args); DoTrace(format, args);
va_end(args); va_end(args);
} }
void cDebug::TraceVaArgs( int iDebugLevel, const char *format, va_list &args ) void cDebug::TraceVaArgs( int iDebugLevel, const char *format, va_list &args )
@ -367,15 +367,15 @@ void cDebug::TraceVaArgs( int iDebugLevel, const wchar_t *format, va_list &args
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cDebug::AddOutTarget(OutTarget target) bool cDebug::AddOutTarget(OutTarget target)
{ {
if (target == OUT_STDOUT) if (target == OUT_STDOUT)
mOutMask |= OUT_STDOUT; mOutMask |= OUT_STDOUT;
if (target == OUT_TRACE) if (target == OUT_TRACE)
mOutMask |= OUT_TRACE; mOutMask |= OUT_TRACE;
if (target == OUT_FILE) { if (target == OUT_FILE) {
mOutMask |= OUT_FILE; mOutMask |= OUT_FILE;
return false; return false;
} }
return true; return true;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -383,15 +383,15 @@ bool cDebug::AddOutTarget(OutTarget target)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cDebug::RemoveOutTarget(OutTarget target) bool cDebug::RemoveOutTarget(OutTarget target)
{ {
if (!HasOutTarget(target)) if (!HasOutTarget(target))
return true; return true;
if (target == OUT_STDOUT) if (target == OUT_STDOUT)
mOutMask ^= OUT_STDOUT; mOutMask ^= OUT_STDOUT;
if (target == OUT_TRACE) if (target == OUT_TRACE)
mOutMask ^= OUT_TRACE; mOutMask ^= OUT_TRACE;
if (target == OUT_FILE) if (target == OUT_FILE)
mOutMask ^= OUT_FILE; mOutMask ^= OUT_FILE;
return true; return true;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -399,15 +399,15 @@ bool cDebug::RemoveOutTarget(OutTarget target)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cDebug::HasOutTarget(OutTarget target) bool cDebug::HasOutTarget(OutTarget target)
{ {
if (target == OUT_STDOUT) if (target == OUT_STDOUT)
return ((mOutMask & OUT_STDOUT) != 0); return ((mOutMask & OUT_STDOUT) != 0);
else if (target == OUT_TRACE) else if (target == OUT_TRACE)
return ((mOutMask & OUT_TRACE) != 0); return ((mOutMask & OUT_TRACE) != 0);
else if (target == OUT_FILE) else if (target == OUT_FILE)
return ((mOutMask & OUT_FILE) != 0); return ((mOutMask & OUT_FILE) != 0);
else //ambiguous input, or too many bits set in target else //ambiguous input, or too many bits set in target
return false; return false;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -416,22 +416,22 @@ bool cDebug::HasOutTarget(OutTarget target)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cDebug::SetOutputFile(const char* filename) bool cDebug::SetOutputFile(const char* filename)
{ {
// TODO -- make sure this does the right thing if a log file is // TODO -- make sure this does the right thing if a log file is
// already open! // already open!
// TODO -- make this work with wide chars // TODO -- make this work with wide chars
if (!logfile) if (!logfile)
logfile.open(filename, std::ios_base::out | std::ios_base::ate | std::ios_base::app); logfile.open(filename, std::ios_base::out | std::ios_base::ate | std::ios_base::app);
else else
logfile.setf(std::ios_base::hex, std::ios_base::basefield); logfile.setf(std::ios_base::hex, std::ios_base::basefield);
//make sure info. will not be clobbered. //make sure info. will not be clobbered.
//Should be open now- if not, abort. //Should be open now- if not, abort.
if (!logfile) { if (!logfile) {
mOutMask ^= OUT_FILE; mOutMask ^= OUT_FILE;
return false; return false;
} else } else
mOutMask |= OUT_FILE; mOutMask |= OUT_FILE;
return true; return true;
} }
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
@ -440,7 +440,7 @@ bool cDebug::SetOutputFile(const char* filename)
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
void cDebug::DebugOut( const char* lpOutputString, ... ) void cDebug::DebugOut( const char* lpOutputString, ... )
{ {
char buf[2048]; char buf[2048];
// create the output buffer // create the output buffer
va_list args; va_list args;
va_start(args, lpOutputString); va_start(args, lpOutputString);
@ -449,25 +449,25 @@ void cDebug::DebugOut( const char* lpOutputString, ... )
#ifdef _UNICODE #ifdef _UNICODE
wchar_t wbuf[2048]; wchar_t wbuf[2048];
if (mbstowcs(wbuf, buf, strlen(buf)+1) == -1) if (mbstowcs(wbuf, buf, strlen(buf)+1) == -1)
wcscpy(wbuf, _T("XXX Unconvertable mb character detected in cDebug::DebugOut()\n") ); wcscpy(wbuf, _T("XXX Unconvertable mb character detected in cDebug::DebugOut()\n") );
#if !USE_OUTPUT_DEBUG_STRING #if !USE_OUTPUT_DEBUG_STRING
#ifdef _DEBUG #ifdef _DEBUG
TCERR << wbuf; TCERR << wbuf;
#endif //_DEBUG #endif //_DEBUG
#else // USE_OUTPUT_DEBUG_STRING #else // USE_OUTPUT_DEBUG_STRING
::OutputDebugString(wbuf); ::OutputDebugString(wbuf);
#endif // USE_OUTPUT_DEBUG_STRING #endif // USE_OUTPUT_DEBUG_STRING
#else // _UNICODE #else // _UNICODE
#if !USE_OUTPUT_DEBUG_STRING #if !USE_OUTPUT_DEBUG_STRING
#ifdef _DEBUG #ifdef _DEBUG
TCERR << buf; TCERR << buf;
#endif //_DEBUG #endif //_DEBUG
#else // USE_OUTPUT_DEBUG_STRING #else // USE_OUTPUT_DEBUG_STRING
::OutputDebugString(buf); ::OutputDebugString(buf);
#endif // USE_OUTPUT_DEBUG_STRING #endif // USE_OUTPUT_DEBUG_STRING
#endif // _UNICODE #endif // _UNICODE
TCOUT.flush(); TCOUT.flush();
} }
@ -480,7 +480,7 @@ void cDebug::DebugOut( const wchar_t* lpOutputString, ... )
#if IS_UNIX #if IS_UNIX
char mbformatbuf[1024]; char mbformatbuf[1024];
char buf[1024]; char buf[1024];
// if (wcstombs(mbformatbuf, lpOutputString, wcslen(lpOutputString)) == -1) // if (wcstombs(mbformatbuf, lpOutputString, wcslen(lpOutputString)) == -1)
// strcpy(mbformatbuf, "XXX Unconvertable wide char detected in cDebug::DebugOut()\n"); // strcpy(mbformatbuf, "XXX Unconvertable wide char detected in cDebug::DebugOut()\n");
vsprintf(buf, mbformatbuf, args); vsprintf(buf, mbformatbuf, args);
@ -495,26 +495,26 @@ void cDebug::DebugOut( const wchar_t* lpOutputString, ... )
#if !USE_OUTPUT_DEBUG_STRING #if !USE_OUTPUT_DEBUG_STRING
#ifdef _DEBUG #ifdef _DEBUG
TCERR << buf; TCERR << buf;
#endif //_DEBUG #endif //_DEBUG
#else // USE_OUTPUT_DEBUG_STRING #else // USE_OUTPUT_DEBUG_STRING
::OutputDebugString(buf); ::OutputDebugString(buf);
#endif // USE_OUTPUT_DEBUG_STRING #endif // USE_OUTPUT_DEBUG_STRING
#else #else
char nbuf[1024]; char nbuf[1024];
#if IS_UNIX #if IS_UNIX
strcpy(nbuf, buf); strcpy(nbuf, buf);
#else #else
if (wcstombs(nbuf, buf, wcslen(buf)+1) == -1) if (wcstombs(nbuf, buf, wcslen(buf)+1) == -1)
strcpy(nbuf, "XXX Unconvertable wide char detected in cDebug::DebugOut()\n"); strcpy(nbuf, "XXX Unconvertable wide char detected in cDebug::DebugOut()\n");
#endif #endif
#if !USE_OUTPUT_DEBUG_STRING #if !USE_OUTPUT_DEBUG_STRING
#ifdef _DEBUG #ifdef _DEBUG
TCERR << nbuf; TCERR << nbuf;
#endif //_DEBUG #endif //_DEBUG
#else // USE_OUTPUT_DEBUG_STRING #else // USE_OUTPUT_DEBUG_STRING
::OutputDebugString(nbuf); ::OutputDebugString(nbuf);
#endif // USE_OUTPUT_DEBUG_STRING #endif // USE_OUTPUT_DEBUG_STRING
#endif #endif
TCOUT.flush(); TCOUT.flush();

View File

@ -61,7 +61,7 @@
// When compiling with MFC, these are already defined and we get error msgs // When compiling with MFC, these are already defined and we get error msgs
// every time this file is included. Since these behave the same as the MFC // every time this file is included. Since these behave the same as the MFC
// version, it is OK to always undef them here.... // version, it is OK to always undef them here....
// -- 20 Aug 99 mdb // -- 20 Aug 99 mdb
// //
#undef ASSERT #undef ASSERT
#undef TRACE #undef TRACE
@ -78,90 +78,90 @@
class cDebug class cDebug
{ {
public: public:
enum OutTarget enum OutTarget
{ {
OUT_STDOUT = 1, OUT_STDOUT = 1,
OUT_TRACE = 2, OUT_TRACE = 2,
OUT_FILE = 4 OUT_FILE = 4
}; };
enum DebugLevel enum DebugLevel
{ {
D_ALWAYS = 0, D_ALWAYS = 0,
D_ERROR = 1, D_ERROR = 1,
D_WARNING = 4, D_WARNING = 4,
D_DEBUG = 8, D_DEBUG = 8,
D_DETAIL = 16, D_DETAIL = 16,
D_NEVER = 1000 D_NEVER = 1000
}; };
cDebug(const char* pLabel); cDebug(const char* pLabel);
~cDebug(); ~cDebug();
cDebug(const cDebug& rhs); cDebug(const cDebug& rhs);
// These are the preferred tracing interfaces, because you don't need to know // These are the preferred tracing interfaces, because you don't need to know
// the DebugLevel enums. // the DebugLevel enums.
// Wide/Narrow Chars Issues: If you include a %s in your format string and you // Wide/Narrow Chars Issues: If you include a %s in your format string and you
// wish to print out a TCHAR (which might be a natural thing to do) you should // wish to print out a TCHAR (which might be a natural thing to do) you should
// encompas the format string with a _T("") macro, i.e. make it a TSTRING. // encompas the format string with a _T("") macro, i.e. make it a TSTRING.
// The wide character overloads of these functions will expect wide strings // The wide character overloads of these functions will expect wide strings
// for %s options. // for %s options.
// //
void TraceAlways (const char *format, ...); void TraceAlways (const char *format, ...);
void TraceError (const char *format, ...); void TraceError (const char *format, ...);
void TraceWarning (const char *format, ...); void TraceWarning (const char *format, ...);
void TraceDebug (const char *format, ...); void TraceDebug (const char *format, ...);
void TraceDetail (const char *format, ...); void TraceDetail (const char *format, ...);
void TraceNever (const char *format, ...); void TraceNever (const char *format, ...);
void TraceAlways (const wchar_t *format, ...); void TraceAlways (const wchar_t *format, ...);
void TraceError (const wchar_t *format, ...); void TraceError (const wchar_t *format, ...);
void TraceWarning (const wchar_t *format, ...); void TraceWarning (const wchar_t *format, ...);
void TraceDebug (const wchar_t *format, ...); void TraceDebug (const wchar_t *format, ...);
void TraceDetail (const wchar_t *format, ...); void TraceDetail (const wchar_t *format, ...);
void TraceNever (const wchar_t *format, ...); void TraceNever (const wchar_t *format, ...);
// these are of use if you are inside a function with a "..." as an argument // these are of use if you are inside a function with a "..." as an argument
// and you want to trace those args // and you want to trace those args
void TraceVaArgs (int iDebugLevel, const char *format, va_list &args); void TraceVaArgs (int iDebugLevel, const char *format, va_list &args);
void TraceVaArgs (int iDebugLevel, const wchar_t *format, va_list &args); void TraceVaArgs (int iDebugLevel, const wchar_t *format, va_list &args);
// ...but you can still choose to use this interface... // ...but you can still choose to use this interface...
void Trace(int levelNum, const char* format, ...); void Trace(int levelNum, const char* format, ...);
void Trace(int levelNum, const wchar_t* format, ...); void Trace(int levelNum, const wchar_t* format, ...);
// Outputs based on levelnum. If levelnum <= global debug, print. // Outputs based on levelnum. If levelnum <= global debug, print.
public: public:
static bool AddOutTarget (OutTarget target); static bool AddOutTarget (OutTarget target);
static bool RemoveOutTarget (OutTarget target); static bool RemoveOutTarget (OutTarget target);
// used to specify the out target.... // used to specify the out target....
static bool HasOutTarget (OutTarget target); static bool HasOutTarget (OutTarget target);
static bool SetOutputFile (const char* filename); static bool SetOutputFile (const char* filename);
// specifies the output file name used when OUT_FILE is set // specifies the output file name used when OUT_FILE is set
static void SetDebugLevel (int level); static void SetDebugLevel (int level);
static int GetDebugLevel (void); static int GetDebugLevel (void);
// gets and sets the global debug level. Trace output at or below this // gets and sets the global debug level. Trace output at or below this
// level will be output. // level will be output.
static void DebugOut ( const char* lpOutputString, ... ); static void DebugOut ( const char* lpOutputString, ... );
static void DebugOut ( const wchar_t* lpOutputString, ... ); static void DebugOut ( const wchar_t* lpOutputString, ... );
// Works just like TRACE // Works just like TRACE
// note: there is an internal buffer size of 1024; traces larger // note: there is an internal buffer size of 1024; traces larger
// than that will have unpredictable and probably bad results // than that will have unpredictable and probably bad results
private: private:
#ifdef DEBUG #ifdef DEBUG
enum { MAX_LABEL = 128 }; enum { MAX_LABEL = 128 };
static int mDebugLevel; static int mDebugLevel;
static uint32 mOutMask; static uint32 mOutMask;
static std::ofstream logfile; static std::ofstream logfile;
char mLabel[MAX_LABEL]; char mLabel[MAX_LABEL];
// helper functions // helper functions
void DoTrace(const char *format, va_list &args); void DoTrace(const char *format, va_list &args);
void DoTrace(const wchar_t *format, va_list &args); void DoTrace(const wchar_t *format, va_list &args);
#endif #endif
}; };
@ -180,12 +180,12 @@ private:
inline void cDebug::SetDebugLevel(int level) inline void cDebug::SetDebugLevel(int level)
{ {
mDebugLevel = level; mDebugLevel = level;
} }
inline int cDebug::GetDebugLevel() inline int cDebug::GetDebugLevel()
{ {
return mDebugLevel; return mDebugLevel;
} }
#else // DEBUG #else // DEBUG
@ -193,30 +193,30 @@ inline int cDebug::GetDebugLevel()
inline cDebug::cDebug (const char *) {} inline cDebug::cDebug (const char *) {}
inline cDebug::~cDebug () {} inline cDebug::~cDebug () {}
inline cDebug::cDebug (const cDebug&) {} inline cDebug::cDebug (const cDebug&) {}
inline void cDebug::TraceAlways (const char *, ...) {} inline void cDebug::TraceAlways (const char *, ...) {}
inline void cDebug::TraceError (const char *, ...) {} inline void cDebug::TraceError (const char *, ...) {}
inline void cDebug::TraceWarning (const char *, ...) {} inline void cDebug::TraceWarning (const char *, ...) {}
inline void cDebug::TraceDebug (const char *, ...) {} inline void cDebug::TraceDebug (const char *, ...) {}
inline void cDebug::TraceDetail (const char *, ...) {} inline void cDebug::TraceDetail (const char *, ...) {}
inline void cDebug::TraceNever (const char *, ...) {} inline void cDebug::TraceNever (const char *, ...) {}
inline void cDebug::TraceAlways (const wchar_t *, ...) {} inline void cDebug::TraceAlways (const wchar_t *, ...) {}
inline void cDebug::TraceError (const wchar_t *, ...) {} inline void cDebug::TraceError (const wchar_t *, ...) {}
inline void cDebug::TraceWarning (const wchar_t *, ...) {} inline void cDebug::TraceWarning (const wchar_t *, ...) {}
inline void cDebug::TraceDebug (const wchar_t *, ...) {} inline void cDebug::TraceDebug (const wchar_t *, ...) {}
inline void cDebug::TraceDetail (const wchar_t *, ...) {} inline void cDebug::TraceDetail (const wchar_t *, ...) {}
inline void cDebug::TraceNever (const wchar_t *, ...) {} inline void cDebug::TraceNever (const wchar_t *, ...) {}
inline void cDebug::TraceVaArgs (int, const char *, va_list &) {} inline void cDebug::TraceVaArgs (int, const char *, va_list &) {}
inline void cDebug::TraceVaArgs (int, const wchar_t *, va_list &) {} inline void cDebug::TraceVaArgs (int, const wchar_t *, va_list &) {}
inline void cDebug::Trace (int, const char*, ...) {} inline void cDebug::Trace (int, const char*, ...) {}
inline void cDebug::Trace (int, const wchar_t*, ...) {} inline void cDebug::Trace (int, const wchar_t*, ...) {}
inline bool cDebug::AddOutTarget (OutTarget) { return false; } inline bool cDebug::AddOutTarget (OutTarget) { return false; }
inline bool cDebug::RemoveOutTarget (OutTarget) { return false; } inline bool cDebug::RemoveOutTarget (OutTarget) { return false; }
inline bool cDebug::HasOutTarget (OutTarget) { return false; } inline bool cDebug::HasOutTarget (OutTarget) { return false; }
inline bool cDebug::SetOutputFile (const char*) { return false; } inline bool cDebug::SetOutputFile (const char*) { return false; }
inline void cDebug::SetDebugLevel (int) {} inline void cDebug::SetDebugLevel (int) {}
inline int cDebug::GetDebugLevel (void) { return 0; } inline int cDebug::GetDebugLevel (void) { return 0; }
inline void cDebug::DebugOut ( const char*, ... ) {} inline void cDebug::DebugOut ( const char*, ... ) {}
inline void cDebug::DebugOut ( const wchar_t*, ... ) {} inline void cDebug::DebugOut ( const wchar_t*, ... ) {}
#endif // DEBUG #endif // DEBUG
@ -229,9 +229,9 @@ inline void cDebug::DebugOut ( const wchar_t*, ... ) {}
#if IS_UNIX #if IS_UNIX
#define ASSERTMSG( exp, s ) assert( (exp) != 0 ) #define ASSERTMSG( exp, s ) assert( (exp) != 0 )
#define ASSERT( exp ) assert( (exp) != 0 ) #define ASSERT( exp ) assert( (exp) != 0 )
// if we are not windows we will just use the standard assert() // if we are not windows we will just use the standard assert()
#define TSS_DebugBreak() ASSERT( false ); #define TSS_DebugBreak() ASSERT( false );
#endif// IS_UNIX #endif// IS_UNIX

View File

@ -829,7 +829,7 @@ bool cEncoder::OnlyOneCatagoryPerChar() const
ach[0] = ch; ach[0] = ch;
for( sack_type::const_iterator atE = m_encodings.begin(); atE != m_encodings.end(); atE++ ) for( sack_type::const_iterator atE = m_encodings.begin(); atE != m_encodings.end(); atE++ )
{ {
if( (*atE)->NeedsEncoding( ach.begin(), ach.end() ) ) if( (*atE)->NeedsEncoding( ach.begin(), ach.end() ) )
{ {
if( fFailedATest ) if( fFailedATest )
return false; // each char can only fail one test return false; // each char can only fail one test

View File

@ -41,11 +41,11 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
uint32 eError::CalcHash( const char* name ) uint32 eError::CalcHash( const char* name )
{ {
CRC_INFO crc; CRC_INFO crc;
crcInit( crc ); crcInit( crc );
crcUpdate( crc, (const uint8*)name, strlen( name ) ); crcUpdate( crc, (const uint8*)name, strlen( name ) );
crcFinit( crc ); crcFinit( crc );
return crc.crc; return crc.crc;
} }

View File

@ -43,55 +43,55 @@ class eError
{ {
public: public:
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Construction and Assignment // Construction and Assignment
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
eError( const TSTRING& msg, uint32 flags = 0 ); eError( const TSTRING& msg, uint32 flags = 0 );
explicit eError( const eError& rhs ); explicit eError( const eError& rhs );
explicit eError(); explicit eError();
void operator=( const eError& rhs ); void operator=( const eError& rhs );
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Destruction // Destruction
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
virtual ~eError(); virtual ~eError();
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Data Access // Data Access
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
virtual uint32 GetID() const = 0; virtual uint32 GetID() const = 0;
// returns a system wide unique identifier for this exception. See the // returns a system wide unique identifier for this exception. See the
// macro below for the typical implementation of this method. // macro below for the typical implementation of this method.
// This is used to associate the error with a string description of the // This is used to associate the error with a string description of the
// error via the global error table. // error via the global error table.
virtual TSTRING GetMsg() const; virtual TSTRING GetMsg() const;
// returns specific information about the error that occured. Provides // returns specific information about the error that occured. Provides
// additional information about the error described by GetID(). It should // additional information about the error described by GetID(). It should
// not provide any information redundant with GetID(). // not provide any information redundant with GetID().
// //
// The string passed to the constructor should be formated properly to // The string passed to the constructor should be formated properly to
// be displayed as the "Second" part of an error message, or the derived // be displayed as the "Second" part of an error message, or the derived
// class should override GetMsg() and return a string appropriate for display. // class should override GetMsg() and return a string appropriate for display.
uint32 GetFlags() const; uint32 GetFlags() const;
// Flags are defined below. Currently, these only have an impact on how errors are // Flags are defined below. Currently, these only have an impact on how errors are
// displayed. // displayed.
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Flags // Flags
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
enum Flag enum Flag
{ {
NON_FATAL = 0x00000001, // displays "Error" or "Warning" ? NON_FATAL = 0x00000001, // displays "Error" or "Warning" ?
SUPRESS_THIRD_MSG = 0x00000002 // supresses the "continuing" or "exiting" message SUPRESS_THIRD_MSG = 0x00000002 // supresses the "continuing" or "exiting" message
}; };
void SetFlags( uint32 flags ); void SetFlags( uint32 flags );
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Flag Convenience Methods // Flag Convenience Methods
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
void SetFatality(bool fatal); void SetFatality(bool fatal);
bool IsFatal() const; bool IsFatal() const;
// Fatality is set to true by default when eError is constructed. But when an error // Fatality is set to true by default when eError is constructed. But when an error
@ -101,19 +101,19 @@ public:
void SetSupressThird(bool supressThird); void SetSupressThird(bool supressThird);
bool SupressThird() const; bool SupressThird() const;
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Utility Methods // Utility Methods
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
static uint32 CalcHash( const char* name ); static uint32 CalcHash( const char* name );
// calculates the CRC32 of the string passed in as name. This methods // calculates the CRC32 of the string passed in as name. This methods
// asserts that name is non null. This is used to generate unique IDs // asserts that name is non null. This is used to generate unique IDs
// for errors. // for errors.
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Private Implementation // Private Implementation
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
protected: protected:
TSTRING mMsg; TSTRING mMsg;
uint32 mFlags; uint32 mFlags;
}; };
@ -125,7 +125,7 @@ protected:
// TSS_BEGIN_EXCEPTION / TSS_END_EXCEPTION // TSS_BEGIN_EXCEPTION / TSS_END_EXCEPTION
// //
// Serves the same purpose as TSS_EXCEPTION but allows custom data and methods // Serves the same purpose as TSS_EXCEPTION but allows custom data and methods
// to be added to the exception class. // to be added to the exception class.
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
#if HAVE_GCC #if HAVE_GCC
@ -135,22 +135,22 @@ protected:
#endif #endif
#define TSS_BEGIN_EXCEPTION( except, base ) \ #define TSS_BEGIN_EXCEPTION( except, base ) \
class except : public base \ class except : public base \
{\ {\
public:\ public:\
except( const TSTRING& msg, uint32 flags = 0 ) \ except( const TSTRING& msg, uint32 flags = 0 ) \
: base( msg, flags ) {} \ : base( msg, flags ) {} \
TSS_BEGIN_EXCEPTION_EXPLICIT except( const except& rhs ) \ TSS_BEGIN_EXCEPTION_EXPLICIT except( const except& rhs ) \
: base( rhs ) {} \ : base( rhs ) {} \
explicit except() : base() {} \ explicit except() : base() {} \
\ \
virtual uint32 GetID() const \ virtual uint32 GetID() const \
{\ {\
return CalcHash( #except ); \ return CalcHash( #except ); \
}\ }\
#define TSS_END_EXCEPTION( ) \ #define TSS_END_EXCEPTION( ) \
}; };
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// TSS_BEGIN_EXCEPTION_NO_CTOR // TSS_BEGIN_EXCEPTION_NO_CTOR
@ -158,29 +158,29 @@ protected:
// Same as TSS_BEGIN_EXCEPTION, but doesn't define any ctors. // Same as TSS_BEGIN_EXCEPTION, but doesn't define any ctors.
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
#define TSS_BEGIN_EXCEPTION_NO_CTOR( except, base ) \ #define TSS_BEGIN_EXCEPTION_NO_CTOR( except, base ) \
class except : public base \ class except : public base \
{\ {\
public:\ public:\
explicit except() : base() {} \ explicit except() : base() {} \
\ \
virtual uint32 GetID() const \ virtual uint32 GetID() const \
{\ {\
return CalcHash( #except ); \ return CalcHash( #except ); \
}\ }\
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// TSS_EXCEPTION // TSS_EXCEPTION
// //
// This is a convenience define for quickly defining an exception class. After // This is a convenience define for quickly defining an exception class. After
// defining a new exception, don't forget to add it to the package's error // defining a new exception, don't forget to add it to the package's error
// string file! // string file!
// //
// TODO (mdb) -- do we want to cache the CRC? if we store it in a class static // TODO (mdb) -- do we want to cache the CRC? if we store it in a class static
// variable, then we will need to define it in the cpp file as well ... // variable, then we will need to define it in the cpp file as well ...
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
#define TSS_EXCEPTION( except, base ) \ #define TSS_EXCEPTION( except, base ) \
TSS_BEGIN_EXCEPTION( except, base ) \ TSS_BEGIN_EXCEPTION( except, base ) \
TSS_END_EXCEPTION() TSS_END_EXCEPTION()
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// Inline Implementation // Inline Implementation
@ -190,30 +190,30 @@ protected:
// eError // eError
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline eError::eError( const TSTRING& msg, uint32 flags ) inline eError::eError( const TSTRING& msg, uint32 flags )
: mMsg ( msg ), : mMsg ( msg ),
mFlags ( flags ) mFlags ( flags )
{ {
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// eError // eError
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline eError::eError( const eError& rhs ) inline eError::eError( const eError& rhs )
: mMsg ( rhs.mMsg ), : mMsg ( rhs.mMsg ),
mFlags ( rhs.mFlags ) mFlags ( rhs.mFlags )
{ {
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// eError // eError
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline eError::eError( ) inline eError::eError( )
: mMsg ( _T("") ), : mMsg ( _T("") ),
mFlags ( 0 ) mFlags ( 0 )
{ {
} }
@ -222,8 +222,8 @@ inline eError::eError( )
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline void eError::operator=( const eError& rhs ) inline void eError::operator=( const eError& rhs )
{ {
mMsg = rhs.mMsg; mMsg = rhs.mMsg;
mFlags = rhs.mFlags; mFlags = rhs.mFlags;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -231,7 +231,7 @@ inline void eError::operator=( const eError& rhs )
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline eError::~eError() inline eError::~eError()
{ {
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -239,7 +239,7 @@ inline eError::~eError()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline TSTRING eError::GetMsg() const inline TSTRING eError::GetMsg() const
{ {
return mMsg; return mMsg;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -247,7 +247,7 @@ inline TSTRING eError::GetMsg() const
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline uint32 eError::GetFlags() const inline uint32 eError::GetFlags() const
{ {
return mFlags; return mFlags;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -255,7 +255,7 @@ inline uint32 eError::GetFlags() const
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline void eError::SetFlags( uint32 flags ) inline void eError::SetFlags( uint32 flags )
{ {
mFlags = flags; mFlags = flags;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////

View File

@ -47,32 +47,32 @@ class eError;
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// cErrorBucket -- contains an interface that handles error reporting, and // cErrorBucket -- contains an interface that handles error reporting, and
// contains a link to a child bucket. Each concrete implementation of the // contains a link to a child bucket. Each concrete implementation of the
// cErrorBucket interface will perform its own specific task related to the // cErrorBucket interface will perform its own specific task related to the
// error's occurence (print to stderr, store in a queue, etc) and then forward // error's occurence (print to stderr, store in a queue, etc) and then forward
// the error on to its child link. The parent bucket does not own the destruction // the error on to its child link. The parent bucket does not own the destruction
// of the pointer to the child bucket. // of the pointer to the child bucket.
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
class cErrorBucket class cErrorBucket
{ {
public: public:
cErrorBucket(); cErrorBucket();
virtual ~cErrorBucket() {} virtual ~cErrorBucket() {}
virtual void AddError(const eError& error); virtual void AddError(const eError& error);
// add an error to the bucket // add an error to the bucket
cErrorBucket* GetChild(); cErrorBucket* GetChild();
// returns the bucket that the current bucket is chained to, or // returns the bucket that the current bucket is chained to, or
// NULL if nothing is attached to it. // NULL if nothing is attached to it.
cErrorBucket* SetChild(cErrorBucket* pNewChild); cErrorBucket* SetChild(cErrorBucket* pNewChild);
// sets the child link of this bucket; returns the old link value // sets the child link of this bucket; returns the old link value
protected: protected:
virtual void HandleError(const eError& error) = 0; virtual void HandleError(const eError& error) = 0;
// override this to implement error handling functionality specific to // override this to implement error handling functionality specific to
// the derived class // the derived class
cErrorBucket* mpChild; cErrorBucket* mpChild;
}; };
//############################################################################# //#############################################################################
@ -82,20 +82,20 @@ protected:
// cErrorBucket // cErrorBucket
/////////////////// ///////////////////
inline cErrorBucket::cErrorBucket() : inline cErrorBucket::cErrorBucket() :
mpChild(0) mpChild(0)
{ {
} }
inline cErrorBucket* cErrorBucket::GetChild() inline cErrorBucket* cErrorBucket::GetChild()
{ {
return mpChild; return mpChild;
} }
inline cErrorBucket* cErrorBucket::SetChild(cErrorBucket* pNewChild) inline cErrorBucket* cErrorBucket::SetChild(cErrorBucket* pNewChild)
{ {
cErrorBucket* pOldChild = mpChild; cErrorBucket* pOldChild = mpChild;
mpChild = pNewChild; mpChild = pNewChild;
return pOldChild; return pOldChild;
} }
#endif #endif

View File

@ -42,9 +42,9 @@
//############################################################################# //#############################################################################
void cErrorBucket::AddError(const eError& error) void cErrorBucket::AddError(const eError& error)
{ {
HandleError(error); HandleError(error);
if(mpChild) if(mpChild)
mpChild->AddError(error); mpChild->AddError(error);
} }
//############################################################################# //#############################################################################
@ -55,14 +55,14 @@ void cErrorReporter::PrintErrorMsg(const eError& error, const TSTRING& strExtra)
cDisplayEncoder e( cDisplayEncoder e(
(cDisplayEncoder::Flags) ( cDisplayEncoder::NON_ROUNDTRIP | (cDisplayEncoder::Flags) ( cDisplayEncoder::NON_ROUNDTRIP |
cDisplayEncoder::ALLOW_WHITESPACE ) ); cDisplayEncoder::ALLOW_WHITESPACE ) );
TSTRING errStr; TSTRING errStr;
// //
// if the ID is zero, just return. // if the ID is zero, just return.
// this should only occur at the top level of a program (ie -- twcmdline.cpp) and // this should only occur at the top level of a program (ie -- twcmdline.cpp) and
// indicates that an error occurred and an error message has already been printed out. // indicates that an error occurred and an error message has already been printed out.
// Therefore, we will do nothing here but return. // Therefore, we will do nothing here but return.
// //
// TODO: Having an error with an ID of 0 is legacy. The only place it happens at this // TODO: Having an error with an ID of 0 is legacy. The only place it happens at this
// point is when we throw ePoly() with no constructor arguments. At some point we want // point is when we throw ePoly() with no constructor arguments. At some point we want
@ -70,8 +70,8 @@ void cErrorReporter::PrintErrorMsg(const eError& error, const TSTRING& strExtra)
// But we don't want to break any release code, thus we return on the next line - June 2, 1999 DMB. // But we don't want to break any release code, thus we return on the next line - June 2, 1999 DMB.
ASSERT( error.GetID() != 0 ); ASSERT( error.GetID() != 0 );
if( error.GetID() == 0 ) if( error.GetID() == 0 )
return; return;
// "First Part" header // "First Part" header
errStr = TSS_GetString( cCore, error.IsFatal() ? core::STR_ERROR_ERROR errStr = TSS_GetString( cCore, error.IsFatal() ? core::STR_ERROR_ERROR
@ -94,7 +94,7 @@ void cErrorReporter::PrintErrorMsg(const eError& error, const TSTRING& strExtra)
// #pragma message("errorbucketimpl.cpp needs a little help in the mb arena, with the findfirst/last and such") // #pragma message("errorbucketimpl.cpp needs a little help in the mb arena, with the findfirst/last and such")
errStr = cErrorTable::GetInstance()->Get( error.GetID() ); errStr = cErrorTable::GetInstance()->Get( error.GetID() );
if(! errStr.empty()) if(! errStr.empty())
{ {
// If the first part has a '\n' in it, we take everything following and prepend it to the // If the first part has a '\n' in it, we take everything following and prepend it to the
// second part. This was added to allow specifing a verbose string as the second part // second part. This was added to allow specifing a verbose string as the second part
@ -109,7 +109,7 @@ void cErrorReporter::PrintErrorMsg(const eError& error, const TSTRING& strExtra)
ASSERT(errStr.length() + len + 6 < 80); // line too big for terminal? ASSERT(errStr.length() + len + 6 < 80); // line too big for terminal?
// Add 6 to account for "### ' and ': ' // Add 6 to account for "### ' and ': '
TCERR << TSS_GetString( cCore, core::STR_ERROR_COLON ) << _T(" ") << errStr; TCERR << TSS_GetString( cCore, core::STR_ERROR_COLON ) << _T(" ") << errStr;
TCERR << std::endl; TCERR << std::endl;
} }
// "Second Part" error string // "Second Part" error string
@ -160,22 +160,22 @@ void cErrorReporter::PrintErrorMsg(const eError& error, const TSTRING& strExtra)
} }
// "Third Part" print 'exiting' or 'continuing' // "Third Part" print 'exiting' or 'continuing'
// note that we supress this part if the appropriate flag is set... // note that we supress this part if the appropriate flag is set...
// //
if( (error.GetFlags() & eError::SUPRESS_THIRD_MSG) == 0 ) if( (error.GetFlags() & eError::SUPRESS_THIRD_MSG) == 0 )
{ {
TCERR << TSS_GetString( cCore, core::STR_ERROR_HEADER) TCERR << TSS_GetString( cCore, core::STR_ERROR_HEADER)
<< TSS_GetString( << TSS_GetString(
cCore, cCore,
error.IsFatal() error.IsFatal()
? core::STR_ERROR_EXITING ? core::STR_ERROR_EXITING
: core::STR_ERROR_CONTINUING ) << std::endl; : core::STR_ERROR_CONTINUING ) << std::endl;
} }
} }
void cErrorReporter::HandleError(const eError& error) void cErrorReporter::HandleError(const eError& error)
{ {
PrintErrorMsg(error); PrintErrorMsg(error);
} }
//############################################################################# //#############################################################################
@ -183,11 +183,11 @@ void cErrorReporter::HandleError(const eError& error)
//############################################################################# //#############################################################################
void cErrorTracer::HandleError(const eError& error) void cErrorTracer::HandleError(const eError& error)
{ {
cDebug d("cErrorTracer::HandleError"); cDebug d("cErrorTracer::HandleError");
d.TraceError( _T("%s : %s\n"), d.TraceError( _T("%s : %s\n"),
cErrorTable::GetInstance()->Get( error.GetID() ).c_str(), cErrorTable::GetInstance()->Get( error.GetID() ).c_str(),
error.GetMsg().c_str() ); error.GetMsg().c_str() );
} }
//############################################################################# //#############################################################################
@ -197,51 +197,51 @@ IMPLEMENT_TYPEDSERIALIZABLE(cErrorQueue, _T("cErrorQueue"), 0, 1);
void cErrorQueue::Clear() void cErrorQueue::Clear()
{ {
mList.clear(); mList.clear();
} }
int cErrorQueue::GetNumErrors() const int cErrorQueue::GetNumErrors() const
{ {
return mList.size(); return mList.size();
} }
void cErrorQueue::HandleError(const eError& error) void cErrorQueue::HandleError(const eError& error)
{ {
mList.push_back( ePoly( error ) ); mList.push_back( ePoly( error ) );
} }
cErrorQueueIter::cErrorQueueIter(cErrorQueue& queue) : cErrorQueueIter::cErrorQueueIter(cErrorQueue& queue) :
mList(queue.mList) mList(queue.mList)
{ {
SeekBegin(); SeekBegin();
} }
cErrorQueueIter::cErrorQueueIter(const cErrorQueue& queue) cErrorQueueIter::cErrorQueueIter(const cErrorQueue& queue)
: mList( ((cErrorQueue*)&queue)->mList ) : mList( ((cErrorQueue*)&queue)->mList )
{ {
SeekBegin(); SeekBegin();
} }
void cErrorQueueIter::SeekBegin() void cErrorQueueIter::SeekBegin()
{ {
mIter = mList.begin(); mIter = mList.begin();
} }
void cErrorQueueIter::Next() void cErrorQueueIter::Next()
{ {
++mIter; ++mIter;
} }
bool cErrorQueueIter::Done() const bool cErrorQueueIter::Done() const
{ {
return (mIter == mList.end()); return (mIter == mList.end());
} }
const ePoly& cErrorQueueIter::GetError() const const ePoly& cErrorQueueIter::GetError() const
{ {
ASSERT(! Done()); ASSERT(! Done());
return (*mIter); return (*mIter);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -249,25 +249,25 @@ const ePoly& cErrorQueueIter::GetError() const
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cErrorQueue::Read(iSerializer* pSerializer, int32 version) void cErrorQueue::Read(iSerializer* pSerializer, int32 version)
{ {
if (version > Version()) if (version > Version())
ThrowAndAssert(eSerializerVersionMismatch(_T("ErrorQueue Read"))); ThrowAndAssert(eSerializerVersionMismatch(_T("ErrorQueue Read")));
int32 size; int32 size;
mList.clear(); mList.clear();
pSerializer->ReadInt32(size); pSerializer->ReadInt32(size);
for(int i = 0; i < size; ++i) for(int i = 0; i < size; ++i)
{ {
int32 errorNumber; int32 errorNumber;
TSTRING errorString; TSTRING errorString;
int32 flags; int32 flags;
pSerializer->ReadInt32 (errorNumber); pSerializer->ReadInt32 (errorNumber);
pSerializer->ReadString (errorString); pSerializer->ReadString (errorString);
pSerializer->ReadInt32 (flags); pSerializer->ReadInt32 (flags);
mList.push_back( ePoly( errorNumber, errorString, flags ) ); mList.push_back( ePoly( errorNumber, errorString, flags ) );
} }
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -275,15 +275,15 @@ void cErrorQueue::Read(iSerializer* pSerializer, int32 version)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cErrorQueue::Write(iSerializer* pSerializer) const void cErrorQueue::Write(iSerializer* pSerializer) const
{ {
pSerializer->WriteInt32(mList.size()); pSerializer->WriteInt32(mList.size());
ListType::const_iterator i; ListType::const_iterator i;
for( i = mList.begin(); i != mList.end(); ++i) for( i = mList.begin(); i != mList.end(); ++i)
{ {
pSerializer->WriteInt32 ((*i).GetID()); pSerializer->WriteInt32 ((*i).GetID());
pSerializer->WriteString((*i).GetMsg()); pSerializer->WriteString((*i).GetMsg());
pSerializer->WriteInt32 ((*i).GetFlags()); pSerializer->WriteInt32 ((*i).GetFlags());
} }
} }
@ -292,15 +292,15 @@ void cErrorQueue::Write(iSerializer* pSerializer) const
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cErrorQueue::TraceContents(int dl) const void cErrorQueue::TraceContents(int dl) const
{ {
if(dl < 0) if(dl < 0)
dl = cDebug::D_DEBUG; dl = cDebug::D_DEBUG;
cDebug d("cFCOErrorQueue::TraceContents"); cDebug d("cFCOErrorQueue::TraceContents");
ListType::const_iterator i; ListType::const_iterator i;
int counter = 0; int counter = 0;
for(i = mList.begin(); i != mList.end(); i++, counter++) for(i = mList.begin(); i != mList.end(); i++, counter++)
{ {
d.Trace(dl, _T("Error[%d]: num = %x string = %s\n") , counter, (*i).GetID(), (*i).GetMsg().c_str()); d.Trace(dl, _T("Error[%d]: num = %x string = %s\n") , counter, (*i).GetID(), (*i).GetMsg().c_str());
} }
} }

View File

@ -61,111 +61,111 @@
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
// cErrorReporter -- sends all error messages to // cErrorReporter -- sends all error messages to
// stderr // stderr
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
class cErrorReporter : public cErrorBucket class cErrorReporter : public cErrorBucket
{ {
public: public:
static void PrintErrorMsg(const eError& error, const TSTRING& strExtra = _T("")); static void PrintErrorMsg(const eError& error, const TSTRING& strExtra = _T(""));
// function that HandleError() uses to print the error messages to stderr. // function that HandleError() uses to print the error messages to stderr.
// this function uses the current authoritative format for error reporting, so // this function uses the current authoritative format for error reporting, so
// other functions needing to display errors to the user should use this. // other functions needing to display errors to the user should use this.
// //
// NOTE:bam 5/7/99 -- I don't think the below is true anymore? // NOTE:bam 5/7/99 -- I don't think the below is true anymore?
// NOTE:mdb -- if the error has an ID of zero, nothing will be printed. This // NOTE:mdb -- if the error has an ID of zero, nothing will be printed. This
// is a way to throw a fatal error where the error reporting has already // is a way to throw a fatal error where the error reporting has already
// occurred. // occurred.
protected: protected:
virtual void HandleError(const eError& error); virtual void HandleError(const eError& error);
}; };
/////////////////////////////////////////////////////// ///////////////////////////////////////////////////////
// cErrorTracer -- traces all errors with the D_ERROR debug // cErrorTracer -- traces all errors with the D_ERROR debug
// level // level
/////////////////////////////////////////////////////// ///////////////////////////////////////////////////////
class cErrorTracer : public cErrorBucket class cErrorTracer : public cErrorBucket
{ {
protected: protected:
virtual void HandleError(const eError& error); virtual void HandleError(const eError& error);
}; };
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
// cErrorQueue -- keeps track of all the errors that // cErrorQueue -- keeps track of all the errors that
// are reported to it, providing an interface for // are reported to it, providing an interface for
// retrieving them at a later time // retrieving them at a later time
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
class cErrorQueue : public cErrorBucket, public iTypedSerializable class cErrorQueue : public cErrorBucket, public iTypedSerializable
{ {
friend class cErrorQueueIter; friend class cErrorQueueIter;
public: public:
void Clear(); void Clear();
// remove all errors from the queue // remove all errors from the queue
int GetNumErrors() const; int GetNumErrors() const;
// returns how many errors are in the queue // returns how many errors are in the queue
// //
// iSerializable interface // iSerializable interface
// //
virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive) virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive)
virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive) virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive)
// //
// Debugging // Debugging
// //
void TraceContents(int dl = -1) const; void TraceContents(int dl = -1) const;
protected: protected:
virtual void HandleError(const eError& error); virtual void HandleError(const eError& error);
private: private:
typedef std::list<ePoly> ListType; typedef std::list<ePoly> ListType;
ListType mList; ListType mList;
DECLARE_TYPEDSERIALIZABLE() DECLARE_TYPEDSERIALIZABLE()
}; };
class cErrorQueueIter class cErrorQueueIter
{ {
public: public:
cErrorQueueIter(cErrorQueue& queue); cErrorQueueIter(cErrorQueue& queue);
cErrorQueueIter(const cErrorQueue& queue); cErrorQueueIter(const cErrorQueue& queue);
~cErrorQueueIter() {} ~cErrorQueueIter() {}
// iteration methods // iteration methods
void SeekBegin(); void SeekBegin();
void Next(); void Next();
bool Done() const; bool Done() const;
// access to the error // access to the error
const ePoly& GetError() const; const ePoly& GetError() const;
// both of these return results are undefined if the iterator // both of these return results are undefined if the iterator
// is not valid (ie - IsDone() == true) // is not valid (ie - IsDone() == true)
private: private:
cErrorQueue::ListType& mList; cErrorQueue::ListType& mList;
cErrorQueue::ListType::iterator mIter; cErrorQueue::ListType::iterator mIter;
}; };
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
// cErrorBucketNull -- an error bucket that plays the // cErrorBucketNull -- an error bucket that plays the
// role of /dev/null // role of /dev/null
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
class cErrorBucketNull : public cErrorBucket class cErrorBucketNull : public cErrorBucket
{ {
virtual void AddError(const eError& ) {} virtual void AddError(const eError& ) {}
protected: protected:
virtual void HandleError(const eError& ) {} virtual void HandleError(const eError& ) {}
}; };
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
// cErrorBucketPassThru -- does nothing with errors; // cErrorBucketPassThru -- does nothing with errors;
// just passes them on to its children // just passes them on to its children
////////////////////////////////////////////////////// //////////////////////////////////////////////////////
class cErrorBucketPassThru : public cErrorBucket class cErrorBucketPassThru : public cErrorBucket
{ {
protected: protected:
virtual void HandleError(const eError& ) {} virtual void HandleError(const eError& ) {}
}; };

View File

@ -45,8 +45,8 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
cErrorTable* cErrorTable::GetInstance() cErrorTable* cErrorTable::GetInstance()
{ {
static cErrorTable gErrorTable; static cErrorTable gErrorTable;
return &gErrorTable; return &gErrorTable;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////

View File

@ -34,8 +34,8 @@
// Date: 30 April 99 // Date: 30 April 99
// Creator: mdb // Creator: mdb
// //
// cErrorTable -- singleton derived from Resource_<> that serves as the global // cErrorTable -- singleton derived from Resource_<> that serves as the global
// error id to string mapping // error id to string mapping
// //
#ifndef __ERRORTABLE_H #ifndef __ERRORTABLE_H
#define __ERRORTABLE_H #define __ERRORTABLE_H
@ -54,16 +54,16 @@ class eError;
class cErrorTable : public cMessages_<uint32, TCHAR> class cErrorTable : public cMessages_<uint32, TCHAR>
{ {
public: public:
typedef cMessages_<uint32, TCHAR> inherited; typedef cMessages_<uint32, TCHAR> inherited;
// //
// Convenience Methods // Convenience Methods
// //
void Put( const eError& e, const TCHAR* msg ); void Put( const eError& e, const TCHAR* msg );
// //
// Singleton Interface // Singleton Interface
// //
static cErrorTable* GetInstance(); static cErrorTable* GetInstance();
private: private:
#ifdef _DEBUG #ifdef _DEBUG
@ -85,55 +85,55 @@ inline void cErrorTable::Put( const eError& e, const TCHAR* msg )
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// //
// These macros make it easy for a module to register errors with the global // These macros make it easy for a module to register errors with the global
// error table. Them like this: // error table. Them like this:
// //
// // animalerrors.h // // animalerrors.h
// // // //
// TSS_DECLARE_ERROR_REGISTRATION( animal ) // TSS_DECLARE_ERROR_REGISTRATION( animal )
// //
// // animalerrors.cpp // // animalerrors.cpp
// // // //
// TSS_BEGIN_ERROR_REGISTRATION( animal ) // TSS_BEGIN_ERROR_REGISTRATION( animal )
// TSS_REGISTER_ERROR( eDog, _T("Dog error") ) // TSS_REGISTER_ERROR( eDog, _T("Dog error") )
// TSS_REGISTER_ERROR( eDogBark, _T("Barking error") ) // TSS_REGISTER_ERROR( eDogBark, _T("Barking error") )
// TSS_END_ERROR_REGISTRATION() // TSS_END_ERROR_REGISTRATION()
// //
// // pkg.h // // pkg.h
// TSS_DeclarePackage( cWorld ) // TSS_DeclarePackage( cWorld )
// //
// // pkg.cpp // // pkg.cpp
// cWorld::cWorld() // cWorld::cWorld()
// { // {
// TSS_REGISTER_PKG_ERRORS( animal ) // TSS_REGISTER_PKG_ERRORS( animal )
// //
//=================== //===================
// cpp file macros // cpp file macros
//=================== //===================
#define TSS_BEGIN_ERROR_REGISTRATION( pkgName ) \ #define TSS_BEGIN_ERROR_REGISTRATION( pkgName ) \
RegisterErrors##pkgName::RegisterErrors##pkgName() \ RegisterErrors##pkgName::RegisterErrors##pkgName() \
{ {
#define TSS_REGISTER_ERROR( err, str ) \ #define TSS_REGISTER_ERROR( err, str ) \
cErrorTable::GetInstance()->Put \ cErrorTable::GetInstance()->Put \
( err, str ); ( err, str );
#define TSS_END_ERROR_REGISTRATION() \ #define TSS_END_ERROR_REGISTRATION() \
} }
//=================== //===================
// h file macros // h file macros
//=================== //===================
#define TSS_DECLARE_ERROR_REGISTRATION( pkgName ) \ #define TSS_DECLARE_ERROR_REGISTRATION( pkgName ) \
struct RegisterErrors##pkgName \ struct RegisterErrors##pkgName \
{\ {\
RegisterErrors##pkgName(); \ RegisterErrors##pkgName(); \
}; };
//=================== //===================
// package init macros // package init macros
//=================== //===================
#define TSS_REGISTER_PKG_ERRORS( pkgName ) \ #define TSS_REGISTER_PKG_ERRORS( pkgName ) \
RegisterErrors##pkgName register##pkgName; RegisterErrors##pkgName register##pkgName;
#endif //__ERRORTABLE_H #endif //__ERRORTABLE_H

16
src/core/errorutil.cpp Executable file → Normal file
View File

@ -43,11 +43,11 @@
#if IS_UNIX #if IS_UNIX
namespace //unique namespace //unique
{ {
TCHAR* tw_itot( int value, TCHAR* string, int radix) TCHAR* tw_itot( int value, TCHAR* string, int radix)
{ {
_stprintf( string, "%d", value ); _stprintf( string, "%d", value );
return string; return string;
} }
} }
#else #else
#define tw_itot _itot #define tw_itot _itot
@ -73,7 +73,7 @@ eInternal::eInternal(TCHAR* sourceFile, int lineNum)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
TSTRING cErrorUtil::MakeFileError( const TSTRING& msg, const TSTRING& fileName ) TSTRING cErrorUtil::MakeFileError( const TSTRING& msg, const TSTRING& fileName )
{ {
TSTRING ret; TSTRING ret;
ret = TSS_GetString( cCore, core::STR_ERR2_FILENAME ); ret = TSS_GetString( cCore, core::STR_ERR2_FILENAME );
ret.append( fileName ); ret.append( fileName );
ret.append( 1, _T('\n') ); ret.append( 1, _T('\n') );
@ -82,7 +82,7 @@ TSTRING cErrorUtil::MakeFileError( const TSTRING& msg, const TSTRING& fileName )
{ {
ret.append(msg); ret.append(msg);
} }
return ret; return ret;
} }

View File

@ -36,10 +36,10 @@
// Company: TSS // Company: TSS
// Desc: contains useful eError derived classes // Desc: contains useful eError derived classes
// //
// eInternal -- internal logic errors ( ie -- programming mistakes ) // eInternal -- internal logic errors ( ie -- programming mistakes )
// ePoly -- "polymorphic" error that takes its ID as input instead // ePoly -- "polymorphic" error that takes its ID as input instead
// of from its class name // of from its class name
// ThrowAndAssert -- asserts false and throws the specified exception // ThrowAndAssert -- asserts false and throws the specified exception
// //
#ifndef __ERRORUTIL_H #ifndef __ERRORUTIL_H
#define __ERRORUTIL_H #define __ERRORUTIL_H
@ -55,22 +55,22 @@
class ePoly : public eError class ePoly : public eError
{ {
public: public:
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// Construction and Assignment // Construction and Assignment
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
ePoly( uint32 id, const TSTRING& msg, uint32 flags = 0 ); ePoly( uint32 id, const TSTRING& msg, uint32 flags = 0 );
explicit ePoly( const eError& rhs ); explicit ePoly( const eError& rhs );
explicit ePoly(); explicit ePoly();
void operator=( const eError& rhs ); void operator=( const eError& rhs );
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
// ID manipulation // ID manipulation
//------------------------------------------------------------------------- //-------------------------------------------------------------------------
virtual uint32 GetID() const; virtual uint32 GetID() const;
void SetID( uint32 id ); void SetID( uint32 id );
private: private:
uint32 mID; uint32 mID;
}; };
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -78,7 +78,7 @@ private:
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
TSS_BEGIN_EXCEPTION( eInternal, eError ) TSS_BEGIN_EXCEPTION( eInternal, eError )
public: public:
eInternal( TCHAR* file, int lineNum ); eInternal( TCHAR* file, int lineNum );
TSS_END_EXCEPTION() TSS_END_EXCEPTION()
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -87,11 +87,11 @@ TSS_END_EXCEPTION()
class cErrorUtil class cErrorUtil
{ {
public: public:
static TSTRING MakeFileError( const TSTRING& msg, const TSTRING& fileName ); static TSTRING MakeFileError( const TSTRING& msg, const TSTRING& fileName );
// constructs an error message of the form: // constructs an error message of the form:
// File: <fileName> \n <msg> // File: <fileName> \n <msg>
// This is useful for constructing strings to pass as the msg parameter // This is useful for constructing strings to pass as the msg parameter
// to eError constructors. // to eError constructors.
}; };
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -99,15 +99,15 @@ public:
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// //
// NOTE -- we require the developer to supply the file name instead of using // NOTE -- we require the developer to supply the file name instead of using
// __FILE__ because that includes the full path to the file, which we // __FILE__ because that includes the full path to the file, which we
// would not like to display to the user. // would not like to display to the user.
// //
#define INTERNAL_ERROR(filename) eInternal((TCHAR*)_T(filename), __LINE__) #define INTERNAL_ERROR(filename) eInternal((TCHAR*)_T(filename), __LINE__)
#define THROW_INTERNAL(filename) throw eInternal((TCHAR*)_T(filename), __LINE__) #define THROW_INTERNAL(filename) throw eInternal((TCHAR*)_T(filename), __LINE__)
// TODO: ASSERT is always fatal in Unix, perhaps we could #ifdef the ASSERT // TODO: ASSERT is always fatal in Unix, perhaps we could #ifdef the ASSERT
// to echo to cout the line number the exception occured at? // to echo to cout the line number the exception occured at?
#define ThrowAndAssert(exception) { ASSERT(false); throw exception; } #define ThrowAndAssert(exception) { ASSERT(false); throw exception; }
@ -119,10 +119,10 @@ public:
// ePoly // ePoly
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline ePoly::ePoly( uint32 id, const TSTRING& msg, uint32 flags ) inline ePoly::ePoly( uint32 id, const TSTRING& msg, uint32 flags )
: eError( msg, flags ), : eError( msg, flags ),
mID( id ) mID( id )
{ {
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -137,10 +137,10 @@ inline ePoly::ePoly( const eError& rhs )
// ePoly // ePoly
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline ePoly::ePoly() inline ePoly::ePoly()
: eError( _T("") ), : eError( _T("") ),
mID( 0 ) mID( 0 )
{ {
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -150,7 +150,7 @@ inline void ePoly::operator=( const eError& rhs )
{ {
mMsg = rhs.GetMsg(); mMsg = rhs.GetMsg();
mFlags = rhs.GetFlags(); mFlags = rhs.GetFlags();
mID = rhs.GetID(); mID = rhs.GetID();
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -158,7 +158,7 @@ inline void ePoly::operator=( const eError& rhs )
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline uint32 ePoly::GetID() const inline uint32 ePoly::GetID() const
{ {
return mID; return mID;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -166,7 +166,7 @@ inline uint32 ePoly::GetID() const
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline void ePoly::SetID( uint32 id ) inline void ePoly::SetID( uint32 id )
{ {
mID = id; mID = id;
} }
#endif //__ERRORUTIL_H #endif //__ERRORUTIL_H

112
src/core/file.h Executable file → Normal file
View File

@ -30,7 +30,7 @@
// info@tripwire.org or www.tripwire.org. // info@tripwire.org or www.tripwire.org.
// //
// file.h : Interface for cFile class, which abstracts file operations across // file.h : Interface for cFile class, which abstracts file operations across
// different platforms (currently just Windows and Unix...) // different platforms (currently just Windows and Unix...)
#ifndef __FILE_H #ifndef __FILE_H
#define __FILE_H #define __FILE_H
@ -55,17 +55,17 @@
// eFile exception class // eFile exception class
//============================================================================= //=============================================================================
TSS_FILE_EXCEPTION( eFile, eFileError ); TSS_FILE_EXCEPTION( eFile, eFileError );
TSS_FILE_EXCEPTION( eFileOpen, eFile ); TSS_FILE_EXCEPTION( eFileOpen, eFile );
TSS_FILE_EXCEPTION( eFileWrite, eFile ); TSS_FILE_EXCEPTION( eFileWrite, eFile );
TSS_FILE_EXCEPTION( eFileRead, eFile ); TSS_FILE_EXCEPTION( eFileRead, eFile );
TSS_FILE_EXCEPTION( eFileEOF, eFile ); // never used! TSS_FILE_EXCEPTION( eFileEOF, eFile ); // never used!
TSS_FILE_EXCEPTION( eFileSeek, eFile ); TSS_FILE_EXCEPTION( eFileSeek, eFile );
TSS_FILE_EXCEPTION( eFileInvalidOp, eFile ); // never used! TSS_FILE_EXCEPTION( eFileInvalidOp, eFile ); // never used!
TSS_FILE_EXCEPTION( eFileTrunc, eFile ); TSS_FILE_EXCEPTION( eFileTrunc, eFile );
TSS_FILE_EXCEPTION( eFileClose, eFile ); // never used! TSS_FILE_EXCEPTION( eFileClose, eFile ); // never used!
TSS_FILE_EXCEPTION( eFileFlush, eFile ); TSS_FILE_EXCEPTION( eFileFlush, eFile );
TSS_FILE_EXCEPTION( eFileRewind, eFile ); TSS_FILE_EXCEPTION( eFileRewind, eFile );
//============================================================================= //=============================================================================
// cFile // cFile
@ -81,64 +81,64 @@ public:
#endif // IS_UNIX #endif // IS_UNIX
enum SeekFrom enum SeekFrom
{ {
SEEK_BEGIN = 0, SEEK_BEGIN = 0,
SEEK_CURRENT, SEEK_CURRENT,
SEEK_EOF SEEK_EOF
}; };
enum OpenFlags enum OpenFlags
{ {
// note that reading from the file is implicit // note that reading from the file is implicit
OPEN_READ = 0x00000001, // not needed, but makes calls nice... OPEN_READ = 0x00000001, // not needed, but makes calls nice...
OPEN_WRITE = 0x00000002, // we will be writing to the file OPEN_WRITE = 0x00000002, // we will be writing to the file
OPEN_LOCKED_TEMP = 0x00000004, // the file should not be readable by other processes and should be removed when closed OPEN_LOCKED_TEMP = 0x00000004, // the file should not be readable by other processes and should be removed when closed
OPEN_TRUNCATE = 0x00000008, // opens an empty file. creates it if it doesn't exist. Doesn't make much sense without OF_WRITE OPEN_TRUNCATE = 0x00000008, // opens an empty file. creates it if it doesn't exist. Doesn't make much sense without OF_WRITE
OPEN_CREATE = 0x00000010, // create the file if it doesn't exist; this is implicit if OF_TRUNCATE is set OPEN_CREATE = 0x00000010, // create the file if it doesn't exist; this is implicit if OF_TRUNCATE is set
OPEN_TEXT = 0x00000020, OPEN_TEXT = 0x00000020,
OPEN_EXCLUSIVE = 0x00000040, // Use O_CREAT | O_EXCL OPEN_EXCLUSIVE = 0x00000040, // Use O_CREAT | O_EXCL
OPEN_NONBLOCKING = 0x00000080, // Use non-blocking i/o [Unix] OPEN_NONBLOCKING = 0x00000080, // Use non-blocking i/o [Unix]
}; };
//Ctor, Dtor, CpyCtor, Operator=: //Ctor, Dtor, CpyCtor, Operator=:
cFile ( void ); cFile ( void );
~cFile ( void ); ~cFile ( void );
/************ User Interface **************************/ /************ User Interface **************************/
// Both Open methods ALWAYS open files in BINARY mode! // Both Open methods ALWAYS open files in BINARY mode!
void Open ( const TSTRING& sFileName, uint32 flags = OPEN_READ ); //throw(eFile) void Open ( const TSTRING& sFileName, uint32 flags = OPEN_READ ); //throw(eFile)
void Close ( void ); //throw(eFile) void Close ( void ); //throw(eFile)
bool IsOpen ( void ) const; bool IsOpen ( void ) const;
File_t Seek ( File_t offset, SeekFrom From ) const; //throw(eFile) File_t Seek ( File_t offset, SeekFrom From ) const; //throw(eFile)
// Seek returns the current offset after completion // Seek returns the current offset after completion
File_t Read ( void* buffer, File_t nBytes ) const; //throw(eFile) File_t Read ( void* buffer, File_t nBytes ) const; //throw(eFile)
// Read returns the number of bytes that are actually read. If the nBytes // Read returns the number of bytes that are actually read. If the nBytes
// parameter is 0, 0 bytes will be read and buffer will remain untouched. // parameter is 0, 0 bytes will be read and buffer will remain untouched.
// If the read head is at EOF, no bytes will be read and 0 will be returned. // If the read head is at EOF, no bytes will be read and 0 will be returned.
File_t Write ( const void* buffer, File_t nBytes ); //throw(eFile) File_t Write ( const void* buffer, File_t nBytes ); //throw(eFile)
// Write returns the number of bytes that are actually written. // Write returns the number of bytes that are actually written.
File_t Tell ( void ) const; File_t Tell ( void ) const;
// Tell returns the current offset. // Tell returns the current offset.
bool Flush ( void ); //throw(eFile) bool Flush ( void ); //throw(eFile)
// Flush returns 0 if the currently defined stream is successfully flushed. // Flush returns 0 if the currently defined stream is successfully flushed.
void Rewind ( void ) const; //throw(eFile) void Rewind ( void ) const; //throw(eFile)
// Sets the offset to 0. // Sets the offset to 0.
File_t GetSize ( void ) const; File_t GetSize ( void ) const;
// Returns the size of the current file in bytes. Returns -1 if no file is defined. // Returns the size of the current file in bytes. Returns -1 if no file is defined.
void Truncate ( File_t offset ); // throw(eFile) void Truncate ( File_t offset ); // throw(eFile)
private: private:
cFile ( const cFile& rhs ); //not impl. cFile ( const cFile& rhs ); //not impl.
cFile& operator= ( const cFile& rhs); //not impl. cFile& operator= ( const cFile& rhs); //not impl.
//Pointer to the insulated implementation //Pointer to the insulated implementation
cFile_i* mpData; cFile_i* mpData;
public: public:
bool isWritable; bool isWritable;
}; };
@ -146,8 +146,8 @@ public:
class cArosPath class cArosPath
{ {
public: public:
static TSTRING AsPosix(const TSTRING& in); static TSTRING AsPosix(const TSTRING& in);
static TSTRING AsNative(const TSTRING& in); static TSTRING AsNative(const TSTRING& in);
}; };
#endif #endif

326
src/core/file_unix.cpp Executable file → Normal file
View File

@ -56,14 +56,14 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
/*static TSTRING util_GetErrnoString() /*static TSTRING util_GetErrnoString()
{ {
TSTRING ret; TSTRING ret;
char* pErrorStr = strerror(errno); char* pErrorStr = strerror(errno);
#ifdef _UNICODE #ifdef _UNICODE
#error We dont currently support unicode on unix #error We dont currently support unicode on unix
#else #else
ret = pErrorStr; ret = pErrorStr;
#endif #endif
return ret; return ret;
}*/ }*/
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
@ -73,26 +73,26 @@
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
struct cFile_i struct cFile_i
{ {
cFile_i(); cFile_i();
~cFile_i(); ~cFile_i();
FILE* mpCurrStream; //currently defined file stream FILE* mpCurrStream; //currently defined file stream
TSTRING mFileName; //the name of the file we are currently referencing. TSTRING mFileName; //the name of the file we are currently referencing.
}; };
//Ctor //Ctor
cFile_i::cFile_i() : cFile_i::cFile_i() :
mpCurrStream(NULL) mpCurrStream(NULL)
{} {}
//Dtor //Dtor
cFile_i::~cFile_i() cFile_i::~cFile_i()
{ {
if (mpCurrStream != NULL) if (mpCurrStream != NULL)
fclose( mpCurrStream ); fclose( mpCurrStream );
mpCurrStream = NULL; mpCurrStream = NULL;
mFileName.empty(); mFileName.empty();
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
@ -102,18 +102,18 @@ cFile_i::~cFile_i()
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
cFile::cFile() : cFile::cFile() :
mpData(NULL), isWritable(false) mpData(NULL), isWritable(false)
{ {
mpData = new cFile_i; mpData = new cFile_i;
} }
cFile::~cFile() cFile::~cFile()
{ {
if( mpData != NULL) if( mpData != NULL)
{ {
delete mpData; delete mpData;
mpData = NULL; mpData = NULL;
} }
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -126,44 +126,44 @@ void cFile::Open( const TSTRING& sFileName, uint32 flags )
#else #else
void cFile::Open( const TSTRING& sFileNameC, uint32 flags ) void cFile::Open( const TSTRING& sFileNameC, uint32 flags )
{ {
TSTRING sFileName = cArosPath::AsNative(sFileNameC); TSTRING sFileName = cArosPath::AsNative(sFileNameC);
#endif #endif
mode_t openmode = 0664; mode_t openmode = 0664;
if ( mpData->mpCurrStream != NULL ) if ( mpData->mpCurrStream != NULL )
Close(); Close();
// //
// set up the sopen permissions // set up the sopen permissions
// //
int perm = 0; int perm = 0;
TSTRING mode; TSTRING mode;
if( flags & OPEN_WRITE ) if( flags & OPEN_WRITE )
{ {
perm |= O_RDWR; perm |= O_RDWR;
isWritable = true; isWritable = true;
mode = _T("rb"); mode = _T("rb");
if( flags & OPEN_TRUNCATE ) if( flags & OPEN_TRUNCATE )
{ {
perm |= O_TRUNC; perm |= O_TRUNC;
perm |= O_CREAT; perm |= O_CREAT;
mode = _T("w+b"); mode = _T("w+b");
} }
else else
mode = _T("r+b"); mode = _T("r+b");
} }
else else
{ {
perm |= O_RDONLY; perm |= O_RDONLY;
isWritable = false; isWritable = false;
mode = _T("rb"); mode = _T("rb");
} }
if ( flags & OPEN_EXCLUSIVE ) { if ( flags & OPEN_EXCLUSIVE ) {
perm |= O_CREAT | O_EXCL; perm |= O_CREAT | O_EXCL;
openmode = (mode_t) 0600; // Make sure only root can read the file openmode = (mode_t) 0600; // Make sure only root can read the file
} }
if ( flags & OPEN_CREATE ) if ( flags & OPEN_CREATE )
perm |= O_CREAT; perm |= O_CREAT;
@ -172,83 +172,83 @@ void cFile::Open( const TSTRING& sFileNameC, uint32 flags )
if( flags & OPEN_NONBLOCKING ) if( flags & OPEN_NONBLOCKING )
perm |= O_NONBLOCK; perm |= O_NONBLOCK;
#endif #endif
// //
// actually open the file // actually open the file
// //
int fh = _topen( sFileName.c_str(), perm, openmode ); int fh = _topen( sFileName.c_str(), perm, openmode );
if( fh == -1 ) if( fh == -1 )
{ {
throw( eFileOpen( sFileName, iFSServices::GetInstance()->GetErrString() ) ); throw( eFileOpen( sFileName, iFSServices::GetInstance()->GetErrString() ) );
} }
#ifndef __AROS__ #ifndef __AROS__
if( flags & OPEN_LOCKED_TEMP ) if( flags & OPEN_LOCKED_TEMP )
{ {
// unlink this file // unlink this file
if( 0 != unlink( sFileName.c_str() ) ) if( 0 != unlink( sFileName.c_str() ) )
{ {
// we weren't able to unlink file, so close handle and fail // we weren't able to unlink file, so close handle and fail
close( fh ); close( fh );
throw( eFileOpen( sFileName, iFSServices::GetInstance()->GetErrString() ) ); throw( eFileOpen( sFileName, iFSServices::GetInstance()->GetErrString() ) );
} }
} }
#endif #endif
// //
// turn the file handle into a FILE* // turn the file handle into a FILE*
// //
mpData->mpCurrStream = _tfdopen(fh, mode.c_str()); mpData->mpCurrStream = _tfdopen(fh, mode.c_str());
mpData->mFileName = sFileName; //Set mFileName to the newly opened file. mpData->mFileName = sFileName; //Set mFileName to the newly opened file.
cFile::Rewind(); cFile::Rewind();
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// Close -- Closes mpCurrStream and sets the pointer to NULL // Close -- Closes mpCurrStream and sets the pointer to NULL
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
void cFile::Close() //throw(eFile) void cFile::Close() //throw(eFile)
{ {
if(mpData->mpCurrStream != NULL) if(mpData->mpCurrStream != NULL)
{ {
fclose( mpData->mpCurrStream ); fclose( mpData->mpCurrStream );
mpData->mpCurrStream = NULL; mpData->mpCurrStream = NULL;
} }
mpData->mFileName.empty(); mpData->mFileName.empty();
} }
bool cFile::IsOpen( void ) const bool cFile::IsOpen( void ) const
{ {
return( mpData->mpCurrStream != NULL ); return( mpData->mpCurrStream != NULL );
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// Seek -- Positions the read/write offset in mpCurrStream. Returns the // Seek -- Positions the read/write offset in mpCurrStream. Returns the
// current offset upon completion. Returns 0 if no stream is defined. // current offset upon completion. Returns 0 if no stream is defined.
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
cFile::File_t cFile::Seek( File_t offset, SeekFrom From) const //throw(eFile) cFile::File_t cFile::Seek( File_t offset, SeekFrom From) const //throw(eFile)
{ {
//Check to see if a file as been opened yet... //Check to see if a file as been opened yet...
ASSERT( mpData->mpCurrStream != 0); ASSERT( mpData->mpCurrStream != 0);
int apiFrom; int apiFrom;
switch( From ) switch( From )
{ {
case cFile::SEEK_BEGIN: case cFile::SEEK_BEGIN:
apiFrom = SEEK_SET; apiFrom = SEEK_SET;
break; break;
case cFile::SEEK_CURRENT: case cFile::SEEK_CURRENT:
apiFrom = SEEK_CUR; apiFrom = SEEK_CUR;
break; break;
case cFile::SEEK_EOF: case cFile::SEEK_EOF:
apiFrom = SEEK_END; apiFrom = SEEK_END;
break; break;
default: default:
//An invalid SeekFrom parameter was passed. //An invalid SeekFrom parameter was passed.
throw( eInternal( _T("file_unix") ) ); throw( eInternal( _T("file_unix") ) );
} }
// this is a hack to simulate running out of disk space // this is a hack to simulate running out of disk space
#if 0 #if 0
@ -276,98 +276,98 @@ cFile::File_t cFile::Seek( File_t offset, SeekFrom From) const //throw(eFile)
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// Read -- Returns the actual bytes read from mpCurrStream. Returns 0 if // Read -- Returns the actual bytes read from mpCurrStream. Returns 0 if
// mpCurrStream is undefined. // mpCurrStream is undefined.
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
cFile::File_t cFile::Read( void* buffer, File_t nBytes ) const //throw(eFile) cFile::File_t cFile::Read( void* buffer, File_t nBytes ) const //throw(eFile)
{ {
File_t iBytesRead; File_t iBytesRead;
// Has a file been opened? // Has a file been opened?
ASSERT( mpData->mpCurrStream != NULL ); ASSERT( mpData->mpCurrStream != NULL );
// Is the nBytes parameter 0? If so, return without touching buffer: // Is the nBytes parameter 0? If so, return without touching buffer:
if( nBytes == 0 ) if( nBytes == 0 )
return 0; return 0;
iBytesRead = fread( buffer, sizeof(byte), nBytes, mpData->mpCurrStream ); iBytesRead = fread( buffer, sizeof(byte), nBytes, mpData->mpCurrStream );
if( ferror( mpData->mpCurrStream ) != 0 ) if( ferror( mpData->mpCurrStream ) != 0 )
throw eFileRead( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ) ; throw eFileRead( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ) ;
else else
return iBytesRead; return iBytesRead;
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// Write -- Returns the actual number of bytes written to mpCurrStream // Write -- Returns the actual number of bytes written to mpCurrStream
// Returns 0 if no file has been opened. // Returns 0 if no file has been opened.
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
cFile::File_t cFile::Write( const void* buffer, File_t nBytes ) //throw(eFile) cFile::File_t cFile::Write( const void* buffer, File_t nBytes ) //throw(eFile)
{ {
File_t actual_count = 0; File_t actual_count = 0;
// Has a file been opened? Is it writable? // Has a file been opened? Is it writable?
ASSERT( mpData->mpCurrStream != NULL ); ASSERT( mpData->mpCurrStream != NULL );
ASSERT( isWritable ); ASSERT( isWritable );
if( ( actual_count = fwrite( buffer, sizeof(byte), nBytes, mpData->mpCurrStream ) ) < nBytes ) if( ( actual_count = fwrite( buffer, sizeof(byte), nBytes, mpData->mpCurrStream ) ) < nBytes )
throw eFileWrite( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ); throw eFileWrite( mpData->mFileName, iFSServices::GetInstance()->GetErrString() );
else else
return actual_count; return actual_count;
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// Tell -- Returns the current file offset. Returns 0 if no file has been // Tell -- Returns the current file offset. Returns 0 if no file has been
// opened. // opened.
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
cFile::File_t cFile::Tell() const cFile::File_t cFile::Tell() const
{ {
ASSERT( mpData->mpCurrStream != 0); ASSERT( mpData->mpCurrStream != 0);
return ftell( mpData->mpCurrStream ); return ftell( mpData->mpCurrStream );
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// Flush -- Flushes the current stream. // Flush -- Flushes the current stream.
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
bool cFile::Flush() //throw(eFile) bool cFile::Flush() //throw(eFile)
{ {
if ( mpData->mpCurrStream == NULL ) if ( mpData->mpCurrStream == NULL )
throw eFileFlush( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ); throw eFileFlush( mpData->mFileName, iFSServices::GetInstance()->GetErrString() );
return ( fflush( mpData->mpCurrStream) == 0 ); return ( fflush( mpData->mpCurrStream) == 0 );
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// Rewind -- Sets the offset to the beginning of the file. If mpCurrStream // Rewind -- Sets the offset to the beginning of the file. If mpCurrStream
// is NULL, this method returns false. If the rewind operation fails, // is NULL, this method returns false. If the rewind operation fails,
// an exception is thrown. // an exception is thrown.
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
void cFile::Rewind() const //throw(eFile) void cFile::Rewind() const //throw(eFile)
{ {
ASSERT( mpData->mpCurrStream != 0); ASSERT( mpData->mpCurrStream != 0);
rewind( mpData->mpCurrStream ); rewind( mpData->mpCurrStream );
if( ftell( mpData->mpCurrStream ) != 0 ) if( ftell( mpData->mpCurrStream ) != 0 )
throw( eFileRewind( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ) ); throw( eFileRewind( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ) );
} }
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// GetSize -- Returns the size of the current stream, if one has been // GetSize -- Returns the size of the current stream, if one has been
// opened. If no stream has been opened, returns -1. // opened. If no stream has been opened, returns -1.
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
cFile::File_t cFile::GetSize() const cFile::File_t cFile::GetSize() const
{ {
File_t vCurrentOffset = Tell(); //for saving the current offset File_t vCurrentOffset = Tell(); //for saving the current offset
File_t ret; File_t ret;
//Has a file been opened? If not, return -1 //Has a file been opened? If not, return -1
if( mpData->mpCurrStream == NULL ) if( mpData->mpCurrStream == NULL )
return -1; return -1;
ret = Seek( 0, cFile::SEEK_EOF ); ret = Seek( 0, cFile::SEEK_EOF );
Seek( vCurrentOffset, cFile::SEEK_BEGIN ); Seek( vCurrentOffset, cFile::SEEK_BEGIN );
//return the offset to it's position prior to GetSize call. //return the offset to it's position prior to GetSize call.
return ret; return ret;
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
@ -375,39 +375,39 @@ cFile::File_t cFile::GetSize() const
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
void cFile::Truncate( File_t offset ) // throw(eFile) void cFile::Truncate( File_t offset ) // throw(eFile)
{ {
ASSERT( mpData->mpCurrStream != 0); ASSERT( mpData->mpCurrStream != 0);
ASSERT( isWritable ); ASSERT( isWritable );
ftruncate( fileno(mpData->mpCurrStream), offset ); ftruncate( fileno(mpData->mpCurrStream), offset );
if( GetSize() != offset ) if( GetSize() != offset )
throw( eFileTrunc( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ) ); throw( eFileTrunc( mpData->mFileName, iFSServices::GetInstance()->GetErrString() ) );
} }
#ifdef __AROS__ #ifdef __AROS__
TSTRING cArosPath::AsPosix( const TSTRING& in ) TSTRING cArosPath::AsPosix( const TSTRING& in )
{ {
if (in[0] == '/') if (in[0] == '/')
return in; return in;
TSTRING out = '/' + in; TSTRING out = '/' + in;
std::replace(out.begin(), out.end(), ':', '/'); std::replace(out.begin(), out.end(), ':', '/');
return out; return out;
} }
TSTRING cArosPath::AsNative( const TSTRING& in ) TSTRING cArosPath::AsNative( const TSTRING& in )
{ {
if (in[0] != '/') if (in[0] != '/')
return in; return in;
int x; int x;
for (x=1; in[x] == '/' && x<in.length(); x++); for (x=1; in[x] == '/' && x<in.length(); x++);
TSTRING out = in.substr(x); TSTRING out = in.substr(x);
TSTRING::size_type t = out.find_first_of('/'); TSTRING::size_type t = out.find_first_of('/');
out[t] = ':'; out[t] = ':';
return out; return out;
} }
#endif #endif

View File

@ -40,37 +40,37 @@
eFileError::eFileError( const TSTRING& filename, const TSTRING& description, uint32 flags ) eFileError::eFileError( const TSTRING& filename, const TSTRING& description, uint32 flags )
: eError( _T(""), flags ) : eError( _T(""), flags )
{ {
mFilename = filename; mFilename = filename;
mMsg = description; mMsg = description;
} }
TSTRING eFileError::GetFilename() const TSTRING eFileError::GetFilename() const
{ {
return mFilename; return mFilename;
} }
TSTRING eFileError::GetDescription() const TSTRING eFileError::GetDescription() const
{ {
return mMsg; return mMsg;
} }
/* virtual */ TSTRING eFileError::GetMsg() const /* virtual */ TSTRING eFileError::GetMsg() const
{ {
TSTRING ret; TSTRING ret;
if( ! mFilename.empty() ) if( ! mFilename.empty() )
{ {
ret = TSS_GetString( cCore, core::STR_ERROR_FILENAME ) + mFilename; ret = TSS_GetString( cCore, core::STR_ERROR_FILENAME ) + mFilename;
} }
if( ! mMsg.empty() ) if( ! mMsg.empty() )
{ {
if ( ! mFilename.empty() ) if ( ! mFilename.empty() )
ret += _T("\n"); ret += _T("\n");
ret += mMsg; ret += mMsg;
} }
return ret; return ret;
} }

View File

@ -53,28 +53,28 @@
//============================================================================= //=============================================================================
TSS_BEGIN_EXCEPTION_NO_CTOR( eFileError, eError ) TSS_BEGIN_EXCEPTION_NO_CTOR( eFileError, eError )
private: private:
TSTRING mFilename; TSTRING mFilename;
public: public:
eFileError( const TSTRING& filename, const TSTRING& description, uint32 flags = 0 ); eFileError( const TSTRING& filename, const TSTRING& description, uint32 flags = 0 );
explicit eFileError( const eFileError& rhs ) explicit eFileError( const eFileError& rhs )
: eError( rhs ) { mFilename = rhs.mFilename; } : eError( rhs ) { mFilename = rhs.mFilename; }
eFileError( const TSTRING& msg, uint32 flags = 0 ) eFileError( const TSTRING& msg, uint32 flags = 0 )
: eError( msg, flags ) {} : eError( msg, flags ) {}
TSTRING GetFilename() const; TSTRING GetFilename() const;
TSTRING GetDescription() const; TSTRING GetDescription() const;
virtual TSTRING GetMsg() const; virtual TSTRING GetMsg() const;
TSS_END_EXCEPTION() TSS_END_EXCEPTION()
#define TSS_FILE_EXCEPTION( except, base ) \ #define TSS_FILE_EXCEPTION( except, base ) \
TSS_BEGIN_EXCEPTION( except, base ) \ TSS_BEGIN_EXCEPTION( except, base ) \
except( const TSTRING& filename, const TSTRING& msg, uint32 flags = 0 ) \ except( const TSTRING& filename, const TSTRING& msg, uint32 flags = 0 ) \
: base( filename, msg, flags ) {} \ : base( filename, msg, flags ) {} \
TSS_END_EXCEPTION() TSS_END_EXCEPTION()
#endif #endif

14
src/core/fileheader.cpp Executable file → Normal file
View File

@ -110,17 +110,17 @@ int cFileHeaderID::operator==( const cFileHeaderID& rhs ) const
( ::memcmp( mID, rhs.mID, mIDLen * sizeof(char) ) == 0 ); ( ::memcmp( mID, rhs.mID, mIDLen * sizeof(char) ) == 0 );
} }
void cFileHeaderID::Read(iSerializer* pSerializer, int32 /*version*/ ) // throw (eSerializer, eArchive) void cFileHeaderID::Read(iSerializer* pSerializer, int32 /*version*/ ) // throw (eSerializer, eArchive)
{ {
int16 len; int16 len;
pSerializer->ReadInt16( len ); pSerializer->ReadInt16( len );
if ( (len < 0) || (len >= cFileHeaderID::MAXBYTES )) if ( (len < 0) || (len >= cFileHeaderID::MAXBYTES ))
{ {
// this is invalid! // this is invalid!
throw eSerializerInputStreamFmt( _T("File Header ID invalid") ); throw eSerializerInputStreamFmt( _T("File Header ID invalid") );
} }
pSerializer->ReadBlob(mID, len * sizeof(char)); pSerializer->ReadBlob(mID, len * sizeof(char));
mIDLen = len; mIDLen = len;
} }
void cFileHeaderID::Write(iSerializer* pSerializer) const // throw (eSerializer, eArchive) void cFileHeaderID::Write(iSerializer* pSerializer) const // throw (eSerializer, eArchive)

8
src/core/fileheader.h Executable file → Normal file
View File

@ -59,8 +59,8 @@ public:
int operator == (const cFileHeaderID& rhs) const; int operator == (const cFileHeaderID& rhs) const;
int operator != (const cFileHeaderID& rhs) const; int operator != (const cFileHeaderID& rhs) const;
virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive) virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive)
virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive) virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive)
private: private:
// For now we will store the id as a string. // For now we will store the id as a string.
@ -127,8 +127,8 @@ public:
cMemoryArchive& GetBaggage(); cMemoryArchive& GetBaggage();
const cMemoryArchive& GetBaggage() const; const cMemoryArchive& GetBaggage() const;
virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive) virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive)
virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive) virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive)
protected: protected:
cFileHeaderID mID; cFileHeaderID mID;

View File

@ -45,26 +45,26 @@
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// cGrowHeap -- a heap that can grow but never shrink // cGrowHeap -- a heap that can grow but never shrink
// All items alloced should be well below growBy in size // All items alloced should be well below growBy in size
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
class cGrowHeap_i; class cGrowHeap_i;
class cGrowHeap class cGrowHeap
{ {
public: public:
cGrowHeap( size_t initialSize, size_t growby, const TCHAR* name ); cGrowHeap( size_t initialSize, size_t growby, const TCHAR* name );
// creates a heap that is initially initialSize big, and increases the // creates a heap that is initially initialSize big, and increases the
// size by growBy every time there is no more room. // size by growBy every time there is no more room.
// initialSize and growby must be a multiple of BYTE_ALIGN // initialSize and growby must be a multiple of BYTE_ALIGN
~cGrowHeap(); ~cGrowHeap();
void* Malloc( size_t size ); void* Malloc( size_t size );
void Clear(); void Clear();
// resets the grow heap's state. // resets the grow heap's state.
size_t TotalMemUsage() const; size_t TotalMemUsage() const;
// returns the total memory usage of this heap // returns the total memory usage of this heap
private: private:
cGrowHeap_i* mpData; cGrowHeap_i* mpData;
}; };

View File

@ -36,7 +36,7 @@
// operator overloaded in order for this to work. TSTRINGS will always // operator overloaded in order for this to work. TSTRINGS will always
// work as the key value because of the overloaded-template-function // work as the key value because of the overloaded-template-function
// //
// Note: Any overloaded const byte*() operator must return an // Note: Any overloaded const byte*() operator must return an
// length of key as well. see cDefaultConvert // length of key as well. see cDefaultConvert
// //
// IMPORTANT -- cDefaultConvert only works for pointers to objects // IMPORTANT -- cDefaultConvert only works for pointers to objects
@ -63,18 +63,18 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// Comparison function objects ... these are used by the hash table to determine // Comparison function objects ... these are used by the hash table to determine
// equality. The one defined should work for objects that use op== to define // equality. The one defined should work for objects that use op== to define
// equality. There is also a specialization for TSTRINGS. If neither of these // equality. There is also a specialization for TSTRINGS. If neither of these
// fit your needs, you must pass the hash table your own fn pointer or class // fit your needs, you must pass the hash table your own fn pointer or class
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
template<class T> template<class T>
class cDefaultCompare class cDefaultCompare
{ {
public: public:
bool operator()(const T& lhs, const T& rhs) bool operator()(const T& lhs, const T& rhs)
{ {
return lhs == rhs; return lhs == rhs;
} }
}; };
///////////////////////////////////////////////////////// /////////////////////////////////////////////////////////
// specialization for TSTRINGS // specialization for TSTRINGS
@ -82,24 +82,24 @@ public:
template<> template<>
inline bool cDefaultCompare<TSTRING>::operator()(const TSTRING& lhs, const TSTRING& rhs) inline bool cDefaultCompare<TSTRING>::operator()(const TSTRING& lhs, const TSTRING& rhs)
{ {
return (lhs.compare(rhs) == 0); return (lhs.compare(rhs) == 0);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// Conversion function objects ... used by the hash table to locate the key in KEY_TYPE // Conversion function objects ... used by the hash table to locate the key in KEY_TYPE
// into a byte* and a key length (for hashing purposes). The default implementation // into a byte* and a key length (for hashing purposes). The default implementation
// just does a cast. A specialization is also provided for TSTRINGs. // just does a cast. A specialization is also provided for TSTRINGs.
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
template<class T> template<class T>
class cDefaultConvert class cDefaultConvert
{ {
public: public:
const byte* operator()(const T& obj, int* const pcbKeyLen) const byte* operator()(const T& obj, int* const pcbKeyLen)
{ {
// HACK! TODO: in the interest of time, I've left this as it is..... // HACK! TODO: in the interest of time, I've left this as it is.....
*pcbKeyLen = sizeof(TCHAR) * _tcslen(obj); *pcbKeyLen = sizeof(TCHAR) * _tcslen(obj);
return (byte*)obj; return (byte*)obj;
} }
}; };
///////////////////////////////////////////////////////// /////////////////////////////////////////////////////////
// specialization for TSTRINGS // specialization for TSTRINGS
@ -108,27 +108,27 @@ template<>
inline const byte* cDefaultConvert<TSTRING>::operator()(const TSTRING& obj, int* const pcbKeyLen ) inline const byte* cDefaultConvert<TSTRING>::operator()(const TSTRING& obj, int* const pcbKeyLen )
{ {
*pcbKeyLen = sizeof(TCHAR) * obj.length(); *pcbKeyLen = sizeof(TCHAR) * obj.length();
return (byte*)obj.c_str(); return (byte*)obj.c_str();
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// cHashTable<KEY, VAL, CMP, CONVERTER> // cHashTable<KEY, VAL, CMP, CONVERTER>
// KEY -- the key you are hashing on // KEY -- the key you are hashing on
// VAL -- the value you want associated with that key // VAL -- the value you want associated with that key
// CMP -- a function object that takes (KEY, KEY) and returns true if they // CMP -- a function object that takes (KEY, KEY) and returns true if they
// are equal. // are equal.
// CONVERTER -- function object that takes (KEY, int* pcbKeyLen) and returns a const byte* // CONVERTER -- function object that takes (KEY, int* pcbKeyLen) and returns a const byte*
// ( points to start of key ) and a byte length (in pcbKeyLen) that tells the hashtable // ( points to start of key ) and a byte length (in pcbKeyLen) that tells the hashtable
// how long the key is // how long the key is
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// these were moved outside of the class because it sucks to have to name the class with template parameters // these were moved outside of the class because it sucks to have to name the class with template parameters
// ie -- mTable(cHashTable<TSTRING, int>::MEDIUM // ie -- mTable(cHashTable<TSTRING, int>::MEDIUM
enum cHashTable_TableSize { enum cHashTable_TableSize {
HASH_VERY_SMALL = 17, HASH_VERY_SMALL = 17,
HASH_SMALL = 2007, HASH_SMALL = 2007,
HASH_MEDIUM = 6007, HASH_MEDIUM = 6007,
HASH_LARGE = 13007, HASH_LARGE = 13007,
HASH_VERY_LARGE = 49999 HASH_VERY_LARGE = 49999
}; };
// forward declaration // forward declaration
@ -141,48 +141,48 @@ class cHashTable
{ {
friend class cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>; friend class cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>;
public: public:
//structure for hash table nodes. //structure for hash table nodes.
struct node { struct node {
KEY_TYPE nKey; KEY_TYPE nKey;
VAL_TYPE nData; VAL_TYPE nData;
node* next; node* next;
}; };
cHashTable(int tblSize = HASH_MEDIUM); cHashTable(int tblSize = HASH_MEDIUM);
~cHashTable(); ~cHashTable();
bool Insert(KEY_TYPE key, VAL_TYPE data_in); bool Insert(KEY_TYPE key, VAL_TYPE data_in);
// The pointer, data_in, is stored in a node based on string_in's hashing. // The pointer, data_in, is stored in a node based on string_in's hashing.
// //
// if (key) already exists in the table, then it's value is replaced by (data_in) // if (key) already exists in the table, then it's value is replaced by (data_in)
// returns true if (key) already existed in table. otherwise, returns false // returns true if (key) already existed in table. otherwise, returns false
bool Lookup(KEY_TYPE key, VAL_TYPE& data_out) const; bool Lookup(KEY_TYPE key, VAL_TYPE& data_out) const;
//bool Lookup(TSTRING key, VAL_TYPE& data_out) const; //bool Lookup(TSTRING key, VAL_TYPE& data_out) const;
//Lookup returns true if a match is found for string_check. A reference //Lookup returns true if a match is found for string_check. A reference
//to the node in the table that matches string_check is passed back (by ref). //to the node in the table that matches string_check is passed back (by ref).
bool Remove(KEY_TYPE key); bool Remove(KEY_TYPE key);
//The node that matches string_out is de-allocated. //The node that matches string_out is de-allocated.
bool Clear(void); bool Clear(void);
//Clears the entire table and sets all node pointers to NULL //Clears the entire table and sets all node pointers to NULL
bool IsEmpty(void) const; bool IsEmpty(void) const;
uint32 Hash( const KEY_TYPE& key ) const; uint32 Hash( const KEY_TYPE& key ) const;
//The hashing function, taken from old Tripwire //The hashing function, taken from old Tripwire
int32 GetNumValues() const { return mValuesInTable; }; int32 GetNumValues() const { return mValuesInTable; };
// returns number of table entries filled // returns number of table entries filled
#ifdef _DEBUG #ifdef _DEBUG
void TraceDiagnostics() const; void TraceDiagnostics() const;
// traces hash table statistics // traces hash table statistics
#endif #endif
private: private:
cHashTable(const cHashTable& rhs); // not impl cHashTable(const cHashTable& rhs); // not impl
void operator=(const cHashTable& rhs); // not impl void operator=(const cHashTable& rhs); // not impl
node** mTable; node** mTable;
int mTableSize; int mTableSize;
int32 mValuesInTable; int32 mValuesInTable;
}; };
@ -194,23 +194,23 @@ template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
class cHashTableIter class cHashTableIter
{ {
public: public:
cHashTableIter(const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>& hashTbl); cHashTableIter(const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>& hashTbl);
void SeekBegin() const; void SeekBegin() const;
bool Done() const; bool Done() const;
void Next() const; void Next() const;
const KEY_TYPE& Key() const; const KEY_TYPE& Key() const;
const VAL_TYPE& Val() const; const VAL_TYPE& Val() const;
VAL_TYPE& Val(); VAL_TYPE& Val();
private: private:
mutable int mCurIndex; mutable int mCurIndex;
mutable typename cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::node* mpCurNode; mutable typename cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::node* mpCurNode;
const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>& mHashTable; const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>& mHashTable;
// helper function // helper function
void SeekNextValid() const; void SeekNextValid() const;
}; };
@ -223,61 +223,61 @@ private:
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::cHashTableIter( const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>& hashTbl) : inline cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::cHashTableIter( const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>& hashTbl) :
mHashTable(hashTbl) mHashTable(hashTbl)
{ {
SeekBegin(); SeekBegin();
} }
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline void cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::SeekBegin() const inline void cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::SeekBegin() const
{ {
mCurIndex = 0; mCurIndex = 0;
mpCurNode = mHashTable.mTable[0]; mpCurNode = mHashTable.mTable[0];
if(! mpCurNode) if(! mpCurNode)
SeekNextValid(); SeekNextValid();
} }
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline bool cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Done() const inline bool cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Done() const
{ {
return ((mCurIndex < 0) || (mCurIndex >= mHashTable.mTableSize)); return ((mCurIndex < 0) || (mCurIndex >= mHashTable.mTableSize));
} }
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline void cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Next() const inline void cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Next() const
{ {
SeekNextValid(); SeekNextValid();
} }
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline void cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::SeekNextValid() const inline void cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::SeekNextValid() const
{ {
if(mpCurNode) if(mpCurNode)
mpCurNode = mpCurNode->next; mpCurNode = mpCurNode->next;
//mCurIndex++; //mCurIndex++;
while((! mpCurNode) && (mCurIndex < mHashTable.mTableSize)) while((! mpCurNode) && (mCurIndex < mHashTable.mTableSize))
{ {
mpCurNode = mHashTable.mTable[++mCurIndex]; mpCurNode = mHashTable.mTable[++mCurIndex];
} }
} }
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline const KEY_TYPE& cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Key() const inline const KEY_TYPE& cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Key() const
{ {
ASSERT(! Done()); ASSERT(! Done());
return mpCurNode->nKey; return mpCurNode->nKey;
} }
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline const VAL_TYPE& cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Val() const inline const VAL_TYPE& cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Val() const
{ {
ASSERT(! Done()); ASSERT(! Done());
return mpCurNode->nData; return mpCurNode->nData;
} }
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
inline VAL_TYPE& cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Val() inline VAL_TYPE& cHashTableIter<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Val()
{ {
ASSERT(! Done()); ASSERT(! Done());
return mpCurNode->nData; return mpCurNode->nData;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -289,98 +289,98 @@ template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::cHashTable(int tblSize) cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::cHashTable(int tblSize)
{ {
mValuesInTable = 0; mValuesInTable = 0;
mTableSize = tblSize; mTableSize = tblSize;
mTable = new node*[mTableSize]; mTable = new node*[mTableSize];
for (int i=0; i < mTableSize; ++i) for (int i=0; i < mTableSize; ++i)
mTable[i] = NULL; mTable[i] = NULL;
} }
//Destructor steps through table and deallocates all dynamic memory //Destructor steps through table and deallocates all dynamic memory
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::~cHashTable() cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::~cHashTable()
{ {
for (int i=0; i<mTableSize; ++i) for (int i=0; i<mTableSize; ++i)
{ {
if (mTable[i] != NULL) if (mTable[i] != NULL)
{ {
//delete the entire chain: //delete the entire chain:
node* curr = mTable[i]; node* curr = mTable[i];
node* del; node* del;
while(curr != NULL) while(curr != NULL)
{ {
del = curr; del = curr;
curr=curr->next; curr=curr->next;
delete del; delete del;
} }
} }
} }
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
// Insert -- Hashes a const TCHAR* to a new index. Collisions are resolved // Insert -- Hashes a const TCHAR* to a new index. Collisions are resolved
// using seperate chaining (link lists). // using seperate chaining (link lists).
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
// General Version: // General Version:
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
bool cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Insert(KEY_TYPE key, VAL_TYPE d_in) bool cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Insert(KEY_TYPE key, VAL_TYPE d_in)
{ {
COMPARE_OP compare; COMPARE_OP compare;
int hindex = Hash( key ); int hindex = Hash( key );
if (mTable[hindex] == NULL) { if (mTable[hindex] == NULL) {
//open index, perform insert //open index, perform insert
mTable[hindex] = new node; mTable[hindex] = new node;
(mTable[hindex])->nKey = key; (mTable[hindex])->nKey = key;
(mTable[hindex])->next = NULL; (mTable[hindex])->next = NULL;
(mTable[hindex])->nData = d_in; (mTable[hindex])->nData = d_in;
mValuesInTable++; mValuesInTable++;
return false; return false;
} }
else //collision, do linked list insert else //collision, do linked list insert
{ {
// case 1: key already exists in list -- replace existing one // case 1: key already exists in list -- replace existing one
// case 2: key does not exist -- add to end of list // case 2: key does not exist -- add to end of list
node* nodeptr = mTable[hindex]; node* nodeptr = mTable[hindex];
bool found = false; bool found = false;
while (true) while (true)
{ {
if ( compare(nodeptr->nKey, key)) if ( compare(nodeptr->nKey, key))
{ {
// we found a duplicate! // we found a duplicate!
found = true; found = true;
break; break;
} }
// break if this is the last node in the list // break if this is the last node in the list
if(! nodeptr->next) if(! nodeptr->next)
break; break;
// otherwise, keep traversing // otherwise, keep traversing
nodeptr = nodeptr->next; nodeptr = nodeptr->next;
} }
// add a node if the key was not found // add a node if the key was not found
if (! found) if (! found)
{ {
node *prev = nodeptr; node *prev = nodeptr;
nodeptr = new node; nodeptr = new node;
nodeptr->nKey = key; nodeptr->nKey = key;
nodeptr->next = NULL; nodeptr->next = NULL;
prev->next = nodeptr; prev->next = nodeptr;
mValuesInTable++; mValuesInTable++;
} }
// whether it is a new node or not, set the data to this new value // whether it is a new node or not, set the data to this new value
nodeptr->nData = d_in; nodeptr->nData = d_in;
return found; return found;
} }
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -391,60 +391,60 @@ template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
bool bool
cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Lookup(KEY_TYPE key, VAL_TYPE& d_out) const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Lookup(KEY_TYPE key, VAL_TYPE& d_out) const
{ {
COMPARE_OP compare; COMPARE_OP compare;
int hindex = Hash( key ); int hindex = Hash( key );
if (mTable[hindex] == NULL) if (mTable[hindex] == NULL)
return false; return false;
else { else {
node* nodeptr = mTable[hindex]; node* nodeptr = mTable[hindex];
while (nodeptr != NULL) while (nodeptr != NULL)
{ {
if( compare(nodeptr->nKey, key)) { if( compare(nodeptr->nKey, key)) {
d_out = nodeptr->nData; d_out = nodeptr->nData;
return true; return true;
} }
nodeptr = nodeptr->next; nodeptr = nodeptr->next;
} }
} }
return false; //mTable entries exhausted without a match return false; //mTable entries exhausted without a match
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
// Remove -- Removes a single entry from the hash table. Returns false if // Remove -- Removes a single entry from the hash table. Returns false if
// the nKey is not found in the table. // the nKey is not found in the table.
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
// General Version - // General Version -
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
bool bool
cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Remove(KEY_TYPE key) cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Remove(KEY_TYPE key)
{ {
COMPARE_OP compare; COMPARE_OP compare;
int hindex = Hash( key ); int hindex = Hash( key );
if (mTable[hindex] == NULL) { if (mTable[hindex] == NULL) {
delete (mTable[hindex]); delete (mTable[hindex]);
mTable[hindex] = NULL; mTable[hindex] = NULL;
return true; return true;
} }
else { else {
node* nodeptr = mTable[hindex]; node* nodeptr = mTable[hindex];
node* prev; node* prev;
while(nodeptr != NULL) { while(nodeptr != NULL) {
prev = nodeptr; prev = nodeptr;
if(compare(mTable[hindex]->nKey, key)) if(compare(mTable[hindex]->nKey, key))
{ {
prev->next = nodeptr->next; prev->next = nodeptr->next;
delete nodeptr; delete nodeptr;
if (nodeptr == mTable[hindex]) if (nodeptr == mTable[hindex])
mTable[hindex] = NULL; mTable[hindex] = NULL;
nodeptr = NULL; nodeptr = NULL;
return true; return true;
}//end if }//end if
nodeptr = nodeptr->next; nodeptr = nodeptr->next;
}//end while }//end while
}//end else }//end else
return false; //match was not found, no node deleted return false; //match was not found, no node deleted
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -454,23 +454,23 @@ template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
bool bool
cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Clear(void) cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Clear(void)
{ {
for (int i=0; i<mTableSize; ++i) for (int i=0; i<mTableSize; ++i)
{ {
if (mTable[i] != NULL) { if (mTable[i] != NULL) {
node* curr = mTable[i]; node* curr = mTable[i];
node* del; node* del;
while(curr != NULL) { while(curr != NULL) {
del = curr; del = curr;
curr=curr->next; curr=curr->next;
delete del; delete del;
if (del == mTable[i]) if (del == mTable[i])
mTable[i] = NULL; mTable[i] = NULL;
del = NULL; del = NULL;
}//end delete chain loop }//end delete chain loop
}//end if mTable[i]!= NULL }//end if mTable[i]!= NULL
}//end for }//end for
return (IsEmpty()); return (IsEmpty());
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -480,10 +480,10 @@ template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
bool bool
cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::IsEmpty(void) const cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::IsEmpty(void) const
{ {
bool ret = true; bool ret = true;
for(int i=0; i< mTableSize; ++i) for(int i=0; i< mTableSize; ++i)
ret &= (mTable[i] == NULL); ret &= (mTable[i] == NULL);
return ret; return ret;
} }
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -495,10 +495,10 @@ uint32 cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Hash( const KEY_TY
CONVERTER converter; CONVERTER converter;
int len; int len;
const byte* pb = converter( key, &len ); //locates key const byte* pb = converter( key, &len ); //locates key
uint32 hindex; uint32 hindex;
hindex = *pb; hindex = *pb;
while (len-- > 0) while (len-- > 0)
hindex = ((hindex << 9) ^ *pb++) % mTableSize; hindex = ((hindex << 9) ^ *pb++) % mTableSize;
return hindex; return hindex;
} }
@ -508,34 +508,34 @@ uint32 cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::Hash( const KEY_TY
template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER> template <class KEY_TYPE, class VAL_TYPE, class COMPARE_OP, class CONVERTER>
void cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::TraceDiagnostics() const void cHashTable<KEY_TYPE, VAL_TYPE, COMPARE_OP, CONVERTER>::TraceDiagnostics() const
{ {
cDebug d("cHashTable::Diagnostics"); cDebug d("cHashTable::Diagnostics");
int slotsFilled = 0, numItems = 0, numMultiSlot = 0; int slotsFilled = 0, numItems = 0, numMultiSlot = 0;
node* pNode; node* pNode;
for(int i=0; i < mTableSize; i++) for(int i=0; i < mTableSize; i++)
{ {
if(mTable[i] != NULL) if(mTable[i] != NULL)
{ {
slotsFilled++; slotsFilled++;
numItems++; numItems++;
pNode = (mTable[i])->next; pNode = (mTable[i])->next;
if(pNode != NULL) if(pNode != NULL)
numMultiSlot++; numMultiSlot++;
while(pNode) while(pNode)
{ {
numItems++; numItems++;
pNode = pNode->next; pNode = pNode->next;
} }
} }
} }
d.TraceDebug("---------------Hash Table Statisics---------------\n"); d.TraceDebug("---------------Hash Table Statisics---------------\n");
d.TraceDebug("-- Number of slots: %d\n", mTableSize); d.TraceDebug("-- Number of slots: %d\n", mTableSize);
d.TraceDebug("-- Number of items: %d\n", numItems); d.TraceDebug("-- Number of items: %d\n", numItems);
d.TraceDebug("-- Slots filled: %d (%lf %%)\n",slotsFilled, ((double)slotsFilled / (double)mTableSize) * 100.0); d.TraceDebug("-- Slots filled: %d (%lf %%)\n",slotsFilled, ((double)slotsFilled / (double)mTableSize) * 100.0);
d.TraceDebug("-- Slots with >1 item: %d (%lf %%)\n",numMultiSlot, ((double)numMultiSlot / (double)slotsFilled) * 100.0); d.TraceDebug("-- Slots with >1 item: %d (%lf %%)\n",numMultiSlot, ((double)numMultiSlot / (double)slotsFilled) * 100.0);
d.TraceDebug("--------------------------------------------------\n"); d.TraceDebug("--------------------------------------------------\n");
} }
#endif // _DEBUG #endif // _DEBUG

View File

@ -71,10 +71,10 @@
/* /*
* Some comments on getting Haval into Tripwire: * Some comments on getting Haval into Tripwire:
* *
* - all #elif directives replaced by ugly #if/#else/#endif sequences. * - all #elif directives replaced by ugly #if/#else/#endif sequences.
* not all compilers support #elif (an ANSI construct). * not all compilers support #elif (an ANSI construct).
* - byte-order is discovered at compile time. we use the information * - byte-order is discovered at compile time. we use the information
* in "../../include/byteorder.h" to get this information. * in "../../include/byteorder.h" to get this information.
*/ */
#pragma GCC diagnostic ignored "-Wparentheses" #pragma GCC diagnostic ignored "-Wparentheses"
@ -90,7 +90,7 @@
#include "haval.h" #include "haval.h"
#include "debug.h" #include "debug.h"
#define HAVAL_VERSION 1 /* current version number */ #define HAVAL_VERSION 1 /* current version number */
/* Do not remove this line. Protyping depends on it! */ /* Do not remove this line. Protyping depends on it! */
#if defined(__STDC__) || defined(__cplusplus) #if defined(__STDC__) || defined(__cplusplus)

File diff suppressed because it is too large Load Diff

View File

@ -95,41 +95,41 @@ int echild();
/* /*
* define error codes * define error codes
*/ */
#define SE_NONE 0 /* no error */ #define SE_NONE 0 /* no error */
#define SE_NOMEM -1 /* no memory */ #define SE_NOMEM -1 /* no memory */
#define SE_NOPIPE -2 /* no pipes */ #define SE_NOPIPE -2 /* no pipes */
#define SE_NOVAR -3 /* variable not defined */ #define SE_NOVAR -3 /* variable not defined */
#define SE_BADFD -4 /* invalid file descriptor */ #define SE_BADFD -4 /* invalid file descriptor */
/* /*
* default security settings * default security settings
*/ */
#ifndef DEF_UMASK #ifndef DEF_UMASK
# define DEF_UMASK 077 /* only owner has privileges */ # define DEF_UMASK 077 /* only owner has privileges */
#endif #endif
#ifndef UID_RESET #ifndef UID_RESET
# define UID_RESET -2 /* reset EUID to RUID */ # define UID_RESET -2 /* reset EUID to RUID */
#endif #endif
#ifndef GID_RESET #ifndef GID_RESET
# define GID_RESET -2 /* reset EGID to RGID */ # define GID_RESET -2 /* reset EGID to RGID */
#endif #endif
#ifndef DEF_PATH #ifndef DEF_PATH
# ifdef __FreeBSD_cc_version # ifdef __FreeBSD_cc_version
# define DEF_PATH "PATH=/sbin:/usr/sbin:/bin:/usr/bin" /* default search path */ # define DEF_PATH "PATH=/sbin:/usr/sbin:/bin:/usr/bin" /* default search path */
# else # else
# define DEF_PATH "PATH=/bin:/usr/bin:/usr/ucb" /* default search path */ # define DEF_PATH "PATH=/bin:/usr/bin:/usr/ucb" /* default search path */
# endif # endif
#endif #endif
#ifndef DEF_SHELL #ifndef DEF_SHELL
# define DEF_SHELL "SHELL=/bin/sh" /* default shell */ # define DEF_SHELL "SHELL=/bin/sh" /* default shell */
#endif #endif
#ifndef DEF_IFS #ifndef DEF_IFS
# define DEF_IFS "IFS= \t\n" /* default IFS */ # define DEF_IFS "IFS= \t\n" /* default IFS */
#endif #endif
#ifndef DEF_TZ #ifndef DEF_TZ
# define DEF_TZ "TZ" /* default TZ */ # define DEF_TZ "TZ" /* default TZ */
#endif #endif
#ifndef NOSHELL #ifndef NOSHELL
# define NOSHELL "/bin/sh" /* use this if no shell */ # define NOSHELL "/bin/sh" /* use this if no shell */
#endif #endif

View File

@ -40,10 +40,10 @@
class cBlockLink class cBlockLink
{ {
public: public:
cBlockLink(cBlockLink* pNext) : mpNext(pNext) {} cBlockLink(cBlockLink* pNext) : mpNext(pNext) {}
cBlockLink* Next() { return mpNext; } cBlockLink* Next() { return mpNext; }
private: private:
cBlockLink* mpNext; // pointer to the next link, or NULL cBlockLink* mpNext; // pointer to the next link, or NULL
}; };
@ -55,13 +55,13 @@ private:
// ctor, dtor // ctor, dtor
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
cBlockList::cBlockList() : cBlockList::cBlockList() :
mpBlocks(0) mpBlocks(0)
{ {
} }
cBlockList::~cBlockList() cBlockList::~cBlockList()
{ {
Clear(); Clear();
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -69,9 +69,9 @@ cBlockList::~cBlockList()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void* cBlockList::Allocate(int size) void* cBlockList::Allocate(int size)
{ {
char* mem = new char[size + sizeof(cBlockLink)]; char* mem = new char[size + sizeof(cBlockLink)];
mpBlocks = new(mem) cBlockLink(mpBlocks); mpBlocks = new(mem) cBlockLink(mpBlocks);
return mem + sizeof(cBlockLink); return mem + sizeof(cBlockLink);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -79,13 +79,13 @@ void* cBlockList::Allocate(int size)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cBlockList::Clear() void cBlockList::Clear()
{ {
while(mpBlocks) while(mpBlocks)
{ {
cBlockLink* pLink = mpBlocks; cBlockLink* pLink = mpBlocks;
mpBlocks = mpBlocks->Next(); mpBlocks = mpBlocks->Next();
pLink->~cBlockLink(); pLink->~cBlockLink();
delete [] (char*)(pLink); delete [] (char*)(pLink);
} }
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -96,16 +96,16 @@ void cBlockList::Clear()
// ctor, dtor // ctor, dtor
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
cObjectPoolBase::cObjectPoolBase(int objSize, int chunkSize) : cObjectPoolBase::cObjectPoolBase(int objSize, int chunkSize) :
mObjectSize(objSize), mObjectSize(objSize),
mChunkSize(chunkSize), mChunkSize(chunkSize),
mpNextFree(0) mpNextFree(0)
{ {
} }
cObjectPoolBase::~cObjectPoolBase() cObjectPoolBase::~cObjectPoolBase()
{ {
//TODO -- assert that the number of instances left are 0. //TODO -- assert that the number of instances left are 0.
Clear(); Clear();
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -113,19 +113,19 @@ cObjectPoolBase::~cObjectPoolBase()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cObjectPoolBase::AllocNewChunk() void cObjectPoolBase::AllocNewChunk()
{ {
ASSERT(mpNextFree == 0); ASSERT(mpNextFree == 0);
int size = mObjectSize * mChunkSize; int size = mObjectSize * mChunkSize;
char* pBlock = (char*)mBlockList.Allocate(size); char* pBlock = (char*)mBlockList.Allocate(size);
char* pLast = pBlock + size - mObjectSize; char* pLast = pBlock + size - mObjectSize;
for(char* pc = pBlock; pc < pLast; pc += mObjectSize) for(char* pc = pBlock; pc < pLast; pc += mObjectSize)
{ {
((cLink*)pc)->mpNext = (cLink*)(pc + mObjectSize); ((cLink*)pc)->mpNext = (cLink*)(pc + mObjectSize);
} }
((cLink*)pLast)->mpNext = 0; ((cLink*)pLast)->mpNext = 0;
mpNextFree = (cLink*)pBlock; mpNextFree = (cLink*)pBlock;
} }

View File

@ -32,8 +32,8 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// objectpool.h // objectpool.h
// //
// cBlockList -- a linked list of blocks of memory // cBlockList -- a linked list of blocks of memory
// cObjectPoolBase -- a pool of equal-sized objects; constant time allocation // cObjectPoolBase -- a pool of equal-sized objects; constant time allocation
#ifndef __OBJECTPOOL_H #ifndef __OBJECTPOOL_H
#define __OBJECTPOOL_H #define __OBJECTPOOL_H
@ -45,13 +45,13 @@ class cBlockLink;
class cBlockList class cBlockList
{ {
public: public:
cBlockList(); cBlockList();
~cBlockList(); ~cBlockList();
void* Allocate(int size); void* Allocate(int size);
void Clear(); // releases everything in the block list void Clear(); // releases everything in the block list
private: private:
cBlockLink* mpBlocks; // linked list of blocks cBlockLink* mpBlocks; // linked list of blocks
}; };
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -60,44 +60,44 @@ private:
class cObjectPoolBase class cObjectPoolBase
{ {
public: public:
cObjectPoolBase(int objSize, int chunkSize); cObjectPoolBase(int objSize, int chunkSize);
~cObjectPoolBase(); ~cObjectPoolBase();
// NOTE -- dtor is not virtual; therefore it is potentially dangerous to delete a pointer to // NOTE -- dtor is not virtual; therefore it is potentially dangerous to delete a pointer to
// this class unless you know for sure the dynamic class type has nothing to clean up. // this class unless you know for sure the dynamic class type has nothing to clean up.
void* Alloc (); void* Alloc ();
void Free (void* pObj); void Free (void* pObj);
void Clear (); void Clear ();
//TODO -- add IsPointerValid() //TODO -- add IsPointerValid()
private: private:
void AllocNewChunk(); // get another chunk to use... void AllocNewChunk(); // get another chunk to use...
struct cLink struct cLink
{ {
cLink* mpNext; cLink* mpNext;
}; };
cBlockList mBlockList; cBlockList mBlockList;
const int mObjectSize; // how big are the objects? const int mObjectSize; // how big are the objects?
const int mChunkSize; // how big are the chunks we are allocating? const int mChunkSize; // how big are the chunks we are allocating?
cLink* mpNextFree; // the next free object cLink* mpNextFree; // the next free object
//int mInstanceCount; // number of objects that are currently allocated but not freed. //int mInstanceCount; // number of objects that are currently allocated but not freed.
}; };
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// cObjectPool // cObjectPool
// Note -- this template only works for classes that are constructed with their // Note -- this template only works for classes that are constructed with their
// default ctor; I don't know how to extend this model to work for non-default // default ctor; I don't know how to extend this model to work for non-default
// ctors... // ctors...
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
template <class T> template <class T>
class cObjectPool : public cObjectPoolBase class cObjectPool : public cObjectPoolBase
{ {
public: public:
cObjectPool(int chunkSize) : cObjectPoolBase(sizeof(T), chunkSize) {} cObjectPool(int chunkSize) : cObjectPoolBase(sizeof(T), chunkSize) {}
T* New () { return new(cObjectPoolBase::Alloc()) T(); } T* New () { return new(cObjectPoolBase::Alloc()) T(); }
void Delete (T* pObj) { pObj->~T(); Free(pObj); } void Delete (T* pObj) { pObj->~T(); Free(pObj); }
}; };
//############################################################################# //#############################################################################
@ -108,12 +108,12 @@ public:
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline void* cObjectPoolBase::Alloc() inline void* cObjectPoolBase::Alloc()
{ {
if(! mpNextFree) if(! mpNextFree)
AllocNewChunk(); AllocNewChunk();
cLink* pRtn = mpNextFree; cLink* pRtn = mpNextFree;
mpNextFree = mpNextFree->mpNext; mpNextFree = mpNextFree->mpNext;
return pRtn; return pRtn;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -121,9 +121,9 @@ inline void* cObjectPoolBase::Alloc()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline void cObjectPoolBase::Free(void* pObj) inline void cObjectPoolBase::Free(void* pObj)
{ {
cLink* pNew = (cLink*)pObj; cLink* pNew = (cLink*)pObj;
pNew->mpNext = mpNextFree; pNew->mpNext = mpNextFree;
mpNextFree = pNew; mpNextFree = pNew;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -131,8 +131,8 @@ inline void cObjectPoolBase::Free(void* pObj)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline void cObjectPoolBase::Clear() inline void cObjectPoolBase::Clear()
{ {
mBlockList.Clear(); mBlockList.Clear();
mpNextFree = 0; mpNextFree = 0;
} }

View File

@ -91,8 +91,8 @@
//--PACKAGE Helpers //--PACKAGE Helpers
#define TSS_Package( pkg ) \ #define TSS_Package( pkg ) \
pkg::GetInstance() // Access "the" Package obj pkg::GetInstance() // Access "the" Package obj
#define TSS_Dependency( pkg ) \ #define TSS_Dependency( pkg ) \
TSS_Package( pkg ) // Declare a Package Depend. TSS_Package( pkg ) // Declare a Package Depend.
@ -100,7 +100,7 @@
#define TSS_BeginPackage( pkg ) \ #define TSS_BeginPackage( pkg ) \
class pkg : public cPackageBase_< TCHAR > \ class pkg : public cPackageBase_< TCHAR > \
{ \ { \
public: \ public: \
static pkg& GetInstance(); static pkg& GetInstance();
@ -128,34 +128,34 @@
//--STRINGTABLE Helperfs //--STRINGTABLE Helperfs
#define TSS_GetString( pkg, id ) \ #define TSS_GetString( pkg, id ) \
TSS_Package( pkg ).GetString( id ) // Access the Message String TSS_Package( pkg ).GetString( id ) // Access the Message String
#define TSS_DECLARE_STRINGTABLE \ #define TSS_DECLARE_STRINGTABLE \
public: \ public: \
Messages::String \ Messages::String \
GetString( \ GetString( \
Messages::ConstKeyRef id ) const { \ Messages::ConstKeyRef id ) const { \
return m_messages.Get( id ); } \ return m_messages.Get( id ); } \
void LoadStrings(); \ void LoadStrings(); \
private: \ private: \
Messages m_messages // Decare a Stringtable Messages m_messages // Decare a Stringtable
#ifdef _DEBUG #ifdef _DEBUG
#define TSS_BeginStringtable( pkg ) \ #define TSS_BeginStringtable( pkg ) \
void pkg::LoadStrings() \ void pkg::LoadStrings() \
{ cDebug d( #pkg "::LoadStrings()" ); \ { cDebug d( #pkg "::LoadStrings()" ); \
d.TraceDebug("Loading strings for " #pkg " package.\n"); \ d.TraceDebug("Loading strings for " #pkg " package.\n"); \
Messages::Pair astr[] = { // Define a Stringtable Messages::Pair astr[] = { // Define a Stringtable
#else // _DEBUG #else // _DEBUG
#define TSS_BeginStringtable( pkg ) \ #define TSS_BeginStringtable( pkg ) \
void pkg::LoadStrings() \ void pkg::LoadStrings() \
{ Messages::Pair astr[] = { // Define a Stringtable { Messages::Pair astr[] = { // Define a Stringtable
#endif // _DEBUG #endif // _DEBUG
#define TSS_EndStringtable( pkg ) \ #define TSS_EndStringtable( pkg ) \
}; m_messages.Put( \ }; m_messages.Put( \
astr, astr + countof(astr) ); } // End define Strintable astr, astr + countof(astr) ); } // End define Strintable
@ -175,7 +175,7 @@
// cPackageBase_<CharT> -- Base class for all Package Resources // cPackageBase_<CharT> -- Base class for all Package Resources
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// SYNOPSIS: // SYNOPSIS:
// This class is the base class for all package representations // This class is the base class for all package representations
// and, thus, establishes the package contract. It's interface // and, thus, establishes the package contract. It's interface
// is relied on by the Package singleton wrapper, TSS_Package. // is relied on by the Package singleton wrapper, TSS_Package.
// Since part of its contract is that there is only one package // Since part of its contract is that there is only one package
@ -191,15 +191,15 @@
// //
// INVARIANTS: // INVARIANTS:
// m_nInstances <= 1 // m_nInstances <= 1
// //
// //
template< class CharT > template< class CharT >
class cPackageBase_ class cPackageBase_
{ {
public: public:
typedef cMessages_< int, CharT > Messages; typedef cMessages_< int, CharT > Messages;
void LoadStrings() void LoadStrings()
{ {

View File

@ -46,23 +46,23 @@
// For each of these "enumerations" we create unique integers identifying each // For each of these "enumerations" we create unique integers identifying each
// variation. We group similar items together, such as OS_REDHAT and OS_SLACKWARE // variation. We group similar items together, such as OS_REDHAT and OS_SLACKWARE
#define OS_UNKNOWN 0 #define OS_UNKNOWN 0
#define OS_WIN32 0x0101 #define OS_WIN32 0x0101
#define OS_AIX 0x0401 #define OS_AIX 0x0401
#define OS_HPUX 0x0501 #define OS_HPUX 0x0501
#define OS_IRIX 0x0601 #define OS_IRIX 0x0601
#define OS_OSF1 0x0701 #define OS_OSF1 0x0701
#define COMP_UNKNOWN 0 #define COMP_UNKNOWN 0
#define COMP_MSVC 0x0101 #define COMP_MSVC 0x0101
#define COMP_KAI_GCC 0x0201 #define COMP_KAI_GCC 0x0201
#define COMP_KAI_SUNPRO 0x0202 #define COMP_KAI_SUNPRO 0x0202
#define COMP_KAI_GLIBC 0x0203 #define COMP_KAI_GLIBC 0x0203
#define COMP_KAI_VISUALAGE 0x0204 #define COMP_KAI_VISUALAGE 0x0204
#define COMP_KAI_HPANSIC 0x0205 #define COMP_KAI_HPANSIC 0x0205
#define COMP_KAI_IRIX 0x0206 #define COMP_KAI_IRIX 0x0206
#define COMP_KAI_OSF1ALPHA 0x0207 #define COMP_KAI_OSF1ALPHA 0x0207
#define COMP_SUNPRO 0x0301 #define COMP_SUNPRO 0x0301
//============================================================================= //=============================================================================
// Platform detection // Platform detection
@ -93,34 +93,34 @@
#define COMP COMP_KAI_IRIX #define COMP COMP_KAI_IRIX
#elif defined(_ALPHA) #elif defined(_ALPHA)
#define OS OS_OSF1 #define OS OS_OSF1
#define COMP COMP_KAI_OSF1ALPHA #define COMP COMP_KAI_OSF1ALPHA
#elif defined (_HPUX) #elif defined (_HPUX)
#define OS OS_HPUX #define OS OS_HPUX
#define COMP COMP_KAI_HPANSIC #define COMP COMP_KAI_HPANSIC
#else #else
// OK for OS not to resolve, it's being phased out. // OK for OS not to resolve, it's being phased out.
// #error Unknown OS // #error Unknown OS
#endif #endif
#if !defined(OS) #if !defined(OS)
// OK for OS not to resolve, it's being phased out. // OK for OS not to resolve, it's being phased out.
// #error OS definition did not resolve. Check "platform.h". // #error OS definition did not resolve. Check "platform.h".
#endif #endif
/* XXX: COMP may now not resolve, because autoconf may /* XXX: COMP may now not resolve, because autoconf may
* detect GCC. This is done in the hopes that all * detect GCC. This is done in the hopes that all
* COMP detections, and indeed both OS & COMP detechtions * COMP detections, and indeed both OS & COMP detechtions
* will eventualy be done automatically. * will eventualy be done automatically.
* *
* This means, the former "#if !defined(COMP)" will * This means, the former "#if !defined(COMP)" will
* temporarily have to also check the HAVE_[compiler] * temporarily have to also check the HAVE_[compiler]
* #defines until all compilers are checked by autoconf, * #defines until all compilers are checked by autoconf,
* at which point this can be removed completely. * at which point this can be removed completely.
* *
* PH - 20010311 * PH - 20010311
*/ */
#if !defined(COMP) && !defined(HAVE_GCC) #if !defined(COMP) && !defined(HAVE_GCC)
#error COMP definition did not resolve. Check "platform.h". #error COMP definition did not resolve. Check "platform.h".
#endif #endif
@ -153,10 +153,10 @@
// OS detection // OS detection
// Note: Avoid using these if possible (see above) // Note: Avoid using these if possible (see above)
#define IS_WIN32 (OS == OS_WIN32) #define IS_WIN32 (OS == OS_WIN32)
#define IS_AIX (OS == OS_AIX) #define IS_AIX (OS == OS_AIX)
#define IS_HPUX (OS == OS_HPUX) #define IS_HPUX (OS == OS_HPUX)
#define IS_IRIX (OS == OS_IRIX) #define IS_IRIX (OS == OS_IRIX)
#define IS_OSF1 (OS == OS_OSF1) #define IS_OSF1 (OS == OS_OSF1)
// complier detection // complier detection
#define IS_KAI (COMP == COMP_KAI_GCC || COMP == COMP_KAI_SUNPRO || COMP == COMP_KAI_GLIBC || COMP == COMP_KAI_VISUALAGE || COMP == COMP_KAI_HPANSIC || COMP == COMP_KAI_IRIX || COMP == COMP_KAI_OSF1ALPHA) #define IS_KAI (COMP == COMP_KAI_GCC || COMP == COMP_KAI_SUNPRO || COMP == COMP_KAI_GLIBC || COMP == COMP_KAI_VISUALAGE || COMP == COMP_KAI_HPANSIC || COMP == COMP_KAI_IRIX || COMP == COMP_KAI_OSF1ALPHA)
@ -179,8 +179,8 @@
// Threading API // Threading API
// TODO:mdb -- this is not complete or rigorous on the unix side!!! // TODO:mdb -- this is not complete or rigorous on the unix side!!!
#define SUPPORTS_WIN32_THREADS IS_WIN32 #define SUPPORTS_WIN32_THREADS IS_WIN32
#define SUPPORTS_POSIX_THREADS (!SUPPORTS_WIN32_THREADS) #define SUPPORTS_POSIX_THREADS (!SUPPORTS_WIN32_THREADS)
// Miscellaneous // Miscellaneous
#define FSEEK_TAKES_INT32 IS_UNIX // True if fseek takes 32-bit offsets #define FSEEK_TAKES_INT32 IS_UNIX // True if fseek takes 32-bit offsets

View File

@ -54,18 +54,18 @@ RefSet* gpRefCountObj_Objects = 0;
// a way to see what hasn't been accounted for.... // a way to see what hasn't been accounted for....
struct cRefCountObj_Debug struct cRefCountObj_Debug
{ {
~cRefCountObj_Debug() ~cRefCountObj_Debug()
{ {
RefSet::iterator i; RefSet::iterator i;
cDebug d("cRefCountObj_Debug"); cDebug d("cRefCountObj_Debug");
if(gpRefCountObj_Objects) if(gpRefCountObj_Objects)
{ {
for(i = gpRefCountObj_Objects->begin(); i != gpRefCountObj_Objects->end(); i++) for(i = gpRefCountObj_Objects->begin(); i != gpRefCountObj_Objects->end(); i++)
{ {
d.TraceNever("Refrence Counted Object %p still exists\n", *i); d.TraceNever("Refrence Counted Object %p still exists\n", *i);
} }
} }
} }
} gRefCountObj_Debug; } gRefCountObj_Debug;
#endif // _DEBUG #endif // _DEBUG
@ -80,12 +80,12 @@ cRefCountObj::cRefCountObj()
++objectCounter; ++objectCounter;
++referenceCounter; ++referenceCounter;
cDebug d("cRefCountObj::cRefCountObj"); cDebug d("cRefCountObj::cRefCountObj");
d.TraceNever("Object Created[%p] %s\n", this, typeid(*this).name()); d.TraceNever("Object Created[%p] %s\n", this, typeid(*this).name());
if(! gpRefCountObj_Objects) if(! gpRefCountObj_Objects)
gpRefCountObj_Objects = new RefSet; gpRefCountObj_Objects = new RefSet;
gpRefCountObj_Objects->insert(this); gpRefCountObj_Objects->insert(this);
#endif #endif
} }
@ -97,20 +97,20 @@ cRefCountObj::~cRefCountObj()
#ifdef _DEBUG #ifdef _DEBUG
--objectCounter; --objectCounter;
cDebug d("cRefCountObj::~cRefCountObj"); cDebug d("cRefCountObj::~cRefCountObj");
d.TraceNever("Object Destroyed[%p] %s Objects Left = %d\n", this, typeid(*this).name(), objectCounter); d.TraceNever("Object Destroyed[%p] %s Objects Left = %d\n", this, typeid(*this).name(), objectCounter);
if(objectCounter == 0) if(objectCounter == 0)
{
d.TraceDebug("****** All Reference Counted Objects Destroyed! ******\n") ;
}
ASSERT(gpRefCountObj_Objects);
RefSet::const_iterator i = gpRefCountObj_Objects->find(this);
ASSERT(i != gpRefCountObj_Objects->end());
gpRefCountObj_Objects->erase(this);
if(gpRefCountObj_Objects->size() == 0)
{ {
delete gpRefCountObj_Objects; d.TraceDebug("****** All Reference Counted Objects Destroyed! ******\n") ;
}
ASSERT(gpRefCountObj_Objects);
RefSet::const_iterator i = gpRefCountObj_Objects->find(this);
ASSERT(i != gpRefCountObj_Objects->end());
gpRefCountObj_Objects->erase(this);
if(gpRefCountObj_Objects->size() == 0)
{
delete gpRefCountObj_Objects;
gpRefCountObj_Objects = 0; gpRefCountObj_Objects = 0;
} }
@ -135,7 +135,7 @@ void cRefCountObj::AddRef() const
void cRefCountObj::Release() const void cRefCountObj::Release() const
{ {
if (this == 0) if (this == 0)
return; return;
if (--mRefCount == 0) if (--mRefCount == 0)
@ -150,6 +150,6 @@ void cRefCountObj::Release() const
void cRefCountObj::Delete() const void cRefCountObj::Delete() const
{ {
delete this; delete this;
} }

View File

@ -67,13 +67,13 @@ public:
virtual void AddRef() const; virtual void AddRef() const;
virtual void Release() const; virtual void Release() const;
int GetRefCount() const { return mRefCount; } int GetRefCount() const { return mRefCount; }
// sometimes it is useful to know an object's refrence // sometimes it is useful to know an object's refrence
protected: protected:
virtual ~cRefCountObj(); virtual ~cRefCountObj();
virtual void Delete() const; virtual void Delete() const;
// override this if you don't want to be destroyed by "delete this"! // override this if you don't want to be destroyed by "delete this"!
private: private:
mutable int mRefCount; mutable int mRefCount;

View File

@ -67,13 +67,13 @@ template< class KEY, class CHR > class cMessages_;
// Used to maintain a table of resources that are indexed by KEY // Used to maintain a table of resources that are indexed by KEY
// type values. The <REZ> type can be any valid type that is // type values. The <REZ> type can be any valid type that is
// assignable. // assignable.
// //
// CONSTRAINTS: // CONSTRAINTS:
// <KEY> must be a valid key type for the std::map concept // <KEY> must be a valid key type for the std::map concept
// <REZ> must be a valid value type for the std::map concept. // <REZ> must be a valid value type for the std::map concept.
// //
// INVARIANTS: // INVARIANTS:
// //
// //
template< class KeyT, class RscT > template< class KeyT, class RscT >
class cResources_ class cResources_
@ -135,7 +135,7 @@ class cResources_
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// SYNOPSIS: // SYNOPSIS:
// Specialization of cResources_<KEY,REZ> to store message strings // Specialization of cResources_<KEY,REZ> to store message strings
// instead of generalized resource objects. In the future this can // instead of generalized resource objects. In the future this can
// be refactored to use message objects so that they can come from // be refactored to use message objects so that they can come from
// a dynamic source (i.e., not a string-literal) such as persistant // a dynamic source (i.e., not a string-literal) such as persistant
// storage or some algorithm based on the concatenation of elements. // storage or some algorithm based on the concatenation of elements.
@ -145,9 +145,9 @@ class cResources_
// not allowing the client to expect a specific character sequence // not allowing the client to expect a specific character sequence
// representation, such as the near ubiquitous const char*. For // representation, such as the near ubiquitous const char*. For
// example: // example:
// //
// const char* psz = messages.GetAnsi( IDS_SOMESTRING ); // const char* psz = messages.GetAnsi( IDS_SOMESTRING );
// //
// The above call requires the caller to be responsible for memory // The above call requires the caller to be responsible for memory
// resources in the case of a conversion. However, there is no // resources in the case of a conversion. However, there is no
// clear way to know up front how many bytes will be required. // clear way to know up front how many bytes will be required.
@ -155,14 +155,14 @@ class cResources_
// memory within cMessages and require the caller to release the // memory within cMessages and require the caller to release the
// the resources when they are done with the message. If we instead // the resources when they are done with the message. If we instead
// require calls in the following form: // require calls in the following form:
// //
// std::string str = messages.GetAnsi( IDS_SOMESTRING ); // std::string str = messages.GetAnsi( IDS_SOMESTRING );
// //
// We can allows assume proper resource use regardless of whether // We can allows assume proper resource use regardless of whether
// a simple character pointer is returned or newly allocated // a simple character pointer is returned or newly allocated
// resources used to convert the stored message. // resources used to convert the stored message.
// //
// //
// CONSTRAINTS: // CONSTRAINTS:
// As with all classes which manipulate character sequences, CHAR // As with all classes which manipulate character sequences, CHAR
// must be a valid character type as defined by the STDCPP standard. // must be a valid character type as defined by the STDCPP standard.
@ -425,7 +425,7 @@ Message_Class::GetWide( ConstKeyRef id ) const
// cMessages_<char & wchar_t> -- Specializations // cMessages_<char & wchar_t> -- Specializations
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// SYNOPSIS: // SYNOPSIS:
// MSVC does not yet support specializations. As a compromise, we fully // MSVC does not yet support specializations. As a compromise, we fully
// specialize on TCHR but assume a key type of "const int". // specialize on TCHR but assume a key type of "const int".
// //
@ -456,7 +456,7 @@ class cMessages_<ENUM_TYPE, char> :
{ {
Value msg = Resources::Get( id ); Value msg = Resources::Get( id );
return ( msg != DefaultValueRef() ) return ( msg != DefaultValueRef() )
? String( msg ) ? String( msg )
: String(); : String();
} }

View File

@ -78,9 +78,9 @@ class iSerializer;
class iSerializable class iSerializable
{ {
public: public:
virtual void Read (iSerializer* pSerializer, int32 version = 0) = 0; // throw (eSerializer, eArchive) virtual void Read (iSerializer* pSerializer, int32 version = 0) = 0; // throw (eSerializer, eArchive)
virtual void Write(iSerializer* pSerializer) const = 0; // throw (eSerializer, eArchive) virtual void Write(iSerializer* pSerializer) const = 0; // throw (eSerializer, eArchive)
// objects implement these methods to read and write themselves to a serializer. // objects implement these methods to read and write themselves to a serializer.
virtual ~iSerializable() {} virtual ~iSerializable() {}
}; };
@ -88,16 +88,16 @@ public:
class iTypedSerializable : public iTyped, public iSerializable class iTypedSerializable : public iTyped, public iSerializable
{ {
public: public:
typedef iTypedSerializable* (*CreateFunc)(); typedef iTypedSerializable* (*CreateFunc)();
// Pointer to a function that creates an empty version of each typed serializable object // Pointer to a function that creates an empty version of each typed serializable object
virtual int32 Version() const = 0; virtual int32 Version() const = 0;
// Return the current version of that this serializable object writes. // Return the current version of that this serializable object writes.
// As a convention version number should be (major_version << 16) | minor_version. // As a convention version number should be (major_version << 16) | minor_version.
static int32 MkVersion(int16 major, int16 minor) { return (int32)(((uint32)major << 16) | (uint32)minor); } static int32 MkVersion(int16 major, int16 minor) { return (int32)(((uint32)major << 16) | (uint32)minor); }
static int16 MajorVersion(int32 version) { return (int16)((uint32)version >> 16); } static int16 MajorVersion(int32 version) { return (int16)((uint32)version >> 16); }
static int16 MinorVersion(int32 version) { return (int16)version; } static int16 MinorVersion(int32 version) { return (int16)version; }
virtual ~iTypedSerializable() {} virtual ~iTypedSerializable() {}
}; };
@ -105,21 +105,21 @@ public:
////////////////////////////// //////////////////////////////
// convenience macros // convenience macros
#define DECLARE_TYPEDSERIALIZABLE() \ #define DECLARE_TYPEDSERIALIZABLE() \
DECLARE_TYPED() \ DECLARE_TYPED() \
public: \ public: \
static iTypedSerializable* Create(); \ static iTypedSerializable* Create(); \
virtual int32 Version() const; virtual int32 Version() const;
#define IMPLEMENT_TYPEDSERIALIZABLE(CLASS, TYPEDSTRING, VERSION_MAJOR, VERSION_MINOR) \ #define IMPLEMENT_TYPEDSERIALIZABLE(CLASS, TYPEDSTRING, VERSION_MAJOR, VERSION_MINOR) \
IMPLEMENT_TYPED(CLASS, TYPEDSTRING) \ IMPLEMENT_TYPED(CLASS, TYPEDSTRING) \
iTypedSerializable* CLASS::Create() \ iTypedSerializable* CLASS::Create() \
{ \ { \
return new CLASS; \ return new CLASS; \
} \ } \
int32 CLASS::Version() const \ int32 CLASS::Version() const \
{ \ { \
return iTypedSerializable::MkVersion(VERSION_MAJOR, VERSION_MINOR); \ return iTypedSerializable::MkVersion(VERSION_MAJOR, VERSION_MINOR); \
} }
#endif // __SERIALIZABLE_H #endif // __SERIALIZABLE_H

View File

@ -45,78 +45,78 @@
// eSerializer::GetMsg -- Overloaded method for returning an error message. // eSerializer::GetMsg -- Overloaded method for returning an error message.
/*virtual*/ TSTRING eSerializer::GetMsg() const /*virtual*/ TSTRING eSerializer::GetMsg() const
{ {
TSTRING ret; TSTRING ret;
if( !eSerializer::mDataSource.empty() ) if( !eSerializer::mDataSource.empty() )
{ {
ret = mMsg; ret = mMsg;
switch( eSerializer::mSourceType ) switch( eSerializer::mSourceType )
{ {
case TY_UNDEFINED: case TY_UNDEFINED:
ret.append( mDataSource ); ret.append( mDataSource );
break; break;
case TY_FILE: case TY_FILE:
ret.append( _T("\nFile: ") ); ret.append( _T("\nFile: ") );
ret.append( mDataSource ); ret.append( mDataSource );
break; break;
case TY_TEMPFILE: case TY_TEMPFILE:
ret.append( _T("\nTemporary File: ") ); ret.append( _T("\nTemporary File: ") );
ret.append( mDataSource ); ret.append( mDataSource );
break; break;
case TY_MEMORY: case TY_MEMORY:
ret.append( _T("\nMemory Block: ") ); //uhhh...?? ret.append( _T("\nMemory Block: ") ); //uhhh...??
ret.append( mDataSource ); ret.append( mDataSource );
break; break;
case TY_PIPE: case TY_PIPE:
ret.append( _T("\nNamed Pipe: ")); ret.append( _T("\nNamed Pipe: "));
ret.append( mDataSource ); ret.append( mDataSource );
break; break;
case TY_SOCKET: case TY_SOCKET:
ret.append( _T("\nNetwork Socket: ")); ret.append( _T("\nNetwork Socket: "));
ret.append( mDataSource ); ret.append( mDataSource );
break; break;
default: default:
ret.append( _T("\n")); ret.append( _T("\n"));
ret.append( mDataSource ); ret.append( mDataSource );
break; break;
} }
} }
else else
{ {
// Just use the base class method... // Just use the base class method...
ret = eError::GetMsg(); ret = eError::GetMsg();
} }
return ret; return ret;
} }
/* /*
eSerializer::eSerializer(ErrorNum errNum, const TSTRING& msg) : eSerializer::eSerializer(ErrorNum errNum, const TSTRING& msg) :
eError(errNum, msg) eError(errNum, msg)
{ {
} }
const TSTRING& eSerializer::GetMsg() const const TSTRING& eSerializer::GetMsg() const
{ {
if((mErrorNum < 0) || (mErrorNum >= E_NUMITEMS)) if((mErrorNum < 0) || (mErrorNum >= E_NUMITEMS))
{ {
// I don't know what this error number is; just use the base class implementation // I don't know what this error number is; just use the base class implementation
return eError::GetMsg(); return eError::GetMsg();
} }
static TSTRING message; static TSTRING message;
static const TCHAR* reasonStrings[] = { _T("The serializer encountered an unknown type"), static const TCHAR* reasonStrings[] = { _T("The serializer encountered an unknown type"),
_T("Invlaid input stream format for serializer"), _T("Invlaid input stream format for serializer"),
_T("Archive error"), _T("Archive error"),
_T("Version Mismatch"), _T("Version Mismatch"),
_T("Invalid Reason") }; _T("Invalid Reason") };
message = reasonStrings[mErrorNum]; message = reasonStrings[mErrorNum];
message += _T(" : "); message += _T(" : ");
message += mMsg; message += mMsg;
return message; return message;
} }

View File

@ -47,29 +47,29 @@ class iSerializable;
// Serializer Base Exception // Serializer Base Exception
//////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////
TSS_BEGIN_EXCEPTION_NO_CTOR( eSerializer, eError ) TSS_BEGIN_EXCEPTION_NO_CTOR( eSerializer, eError )
// TODO: What else to add to this enumeration? Locked File? Temp file? // TODO: What else to add to this enumeration? Locked File? Temp file?
enum DataSourceType { enum DataSourceType {
TY_UNDEFINED = 0, TY_UNDEFINED = 0,
TY_FILE, TY_FILE,
TY_TEMPFILE, TY_TEMPFILE,
TY_MEMORY, TY_MEMORY,
TY_PIPE, TY_PIPE,
TY_SOCKET TY_SOCKET
}; };
eSerializer( const TSTRING& msg, const TSTRING& dataSource = _T(""), DataSourceType paramType = TY_UNDEFINED ) eSerializer( const TSTRING& msg, const TSTRING& dataSource = _T(""), DataSourceType paramType = TY_UNDEFINED )
: eError( msg ), : eError( msg ),
mDataSource( dataSource ), mDataSource( dataSource ),
mSourceType( paramType ) mSourceType( paramType )
{} {}
virtual TSTRING GetMsg() const; virtual TSTRING GetMsg() const;
private: private:
TSTRING mDataSource; TSTRING mDataSource;
// TSTRING indentifier of the datasource associated with a particular error // TSTRING indentifier of the datasource associated with a particular error
// (if one exists) EX: a filename. // (if one exists) EX: a filename.
DataSourceType mSourceType; DataSourceType mSourceType;
TSS_END_EXCEPTION(); TSS_END_EXCEPTION();
//////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////
@ -94,67 +94,67 @@ TSS_SERIALIZER_EXCEPTION( eSerializerVersionMismatch );
TSS_SERIALIZER_EXCEPTION( eSerializerEncryption ); TSS_SERIALIZER_EXCEPTION( eSerializerEncryption );
/* /*
E_UNKNOWN_TYPE = 700, E_UNKNOWN_TYPE = 700,
E_INPUT_STREAM_FORMAT = 701, E_INPUT_STREAM_FORMAT = 701,
E_OUTPUT_STREAM_FORMAT = 706, E_OUTPUT_STREAM_FORMAT = 706,
E_INPUT_STR_TYPEARRAY = 702, // bad index in to type array E_INPUT_STR_TYPEARRAY = 702, // bad index in to type array
E_ARCHIVE = 703, E_ARCHIVE = 703,
E_VERSION_MISMATCH = 704, E_VERSION_MISMATCH = 704,
E_ENCRYPTION_ERROR = 705, E_ENCRYPTION_ERROR = 705,
*/ */
class iSerializer class iSerializer
{ {
public: public:
// Initializing and closing the archive // Initializing and closing the archive
virtual void Init() = 0; // throw eSerializer virtual void Init() = 0; // throw eSerializer
// initializes the serializer; must be called before any reading or writing is done // initializes the serializer; must be called before any reading or writing is done
virtual void Finit() = 0; virtual void Finit() = 0;
// called after a session of serialization is done; called implicitely by the destructor // called after a session of serialization is done; called implicitely by the destructor
// if not called explicitely before destruction // if not called explicitely before destruction
//Reading and writing objects Init() should have already been called or all these will fail. //Reading and writing objects Init() should have already been called or all these will fail.
virtual void WriteObjectDynCreate(const iTypedSerializable* pObj) = 0; // throw (eSerializer, eArchive) virtual void WriteObjectDynCreate(const iTypedSerializable* pObj) = 0; // throw (eSerializer, eArchive)
// writes an object such that it can be dynamically created when read back in with // writes an object such that it can be dynamically created when read back in with
// ReadObject. // ReadObject.
virtual iTypedSerializable* ReadObjectDynCreate() = 0; // throw (eSerializer, eArchive); virtual iTypedSerializable* ReadObjectDynCreate() = 0; // throw (eSerializer, eArchive);
// reads an object from the archive, returning a pointer to it. The caller is responsible for // reads an object from the archive, returning a pointer to it. The caller is responsible for
// deleteing or Release()ing it when done. // deleteing or Release()ing it when done.
virtual void WriteObject(const iTypedSerializable* pObj) = 0; // throw (eSerializer, eArchive) virtual void WriteObject(const iTypedSerializable* pObj) = 0; // throw (eSerializer, eArchive)
// writes an object to the archive that will not be dynamically created // writes an object to the archive that will not be dynamically created
virtual void ReadObject(iTypedSerializable* pObj) = 0; // throw (eSerializer, eArchive) virtual void ReadObject(iTypedSerializable* pObj) = 0; // throw (eSerializer, eArchive)
// reads an object that was written with WriteObject() // reads an object that was written with WriteObject()
// writing interface // writing interface
// all of these can throw eArchive // all of these can throw eArchive
virtual void ReadInt16(int16& ret) = 0; virtual void ReadInt16(int16& ret) = 0;
virtual void ReadInt32(int32& ret) = 0; virtual void ReadInt32(int32& ret) = 0;
virtual void ReadInt64(int64& ret) = 0; virtual void ReadInt64(int64& ret) = 0;
virtual void ReadString(TSTRING& ret) = 0; virtual void ReadString(TSTRING& ret) = 0;
virtual int ReadBlob(void* pBlob, int count) = 0; virtual int ReadBlob(void* pBlob, int count) = 0;
virtual void WriteInt16(int16 i) = 0; virtual void WriteInt16(int16 i) = 0;
virtual void WriteInt32(int32 i) = 0; virtual void WriteInt32(int32 i) = 0;
virtual void WriteInt64(int64 i) = 0; virtual void WriteInt64(int64 i) = 0;
virtual void WriteString(const TSTRING& s) = 0; virtual void WriteString(const TSTRING& s) = 0;
virtual void WriteBlob(const void* pBlob, int count) = 0; virtual void WriteBlob(const void* pBlob, int count) = 0;
virtual TSTRING GetFileName() const { return _T(""); } virtual TSTRING GetFileName() const { return _T(""); }
// derived classes can implement this to return the file name associated with the serializer. // derived classes can implement this to return the file name associated with the serializer.
// it is only used in error reporting. // it is only used in error reporting.
// the error enumeration: 700-799 // the error enumeration: 700-799
enum ErrorNum enum ErrorNum
{ {
E_UNKNOWN_TYPE = 700, E_UNKNOWN_TYPE = 700,
E_INPUT_STREAM_FORMAT = 701, E_INPUT_STREAM_FORMAT = 701,
E_INPUT_STR_TYPEARRAY = 702, // bad index in to type array E_INPUT_STR_TYPEARRAY = 702, // bad index in to type array
E_ARCHIVE = 703, E_ARCHIVE = 703,
E_VERSION_MISMATCH = 704, E_VERSION_MISMATCH = 704,
E_ENCRYPTION_ERROR = 705, E_ENCRYPTION_ERROR = 705,
E_OUTPUT_STREAM_FORMAT = 706, E_OUTPUT_STREAM_FORMAT = 706,
E_NUMITEMS E_NUMITEMS
}; };
virtual ~iSerializer() {} virtual ~iSerializer() {}
}; };

View File

@ -38,25 +38,25 @@
#include "crc32.h" #include "crc32.h"
// static members // static members
cSerializerImpl::SerMap cSerializerImpl::mSerCreateMap ; cSerializerImpl::SerMap cSerializerImpl::mSerCreateMap ;
cSerializerImpl::SerRefCountMap cSerializerImpl::mSerRefCountCreateMap ; cSerializerImpl::SerRefCountMap cSerializerImpl::mSerRefCountCreateMap ;
// RAD:09/01/99 -- No longer needed! // RAD:09/01/99 -- No longer needed!
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// util_TstrToStr -- converts the passed in tstring into a narrow string. maxSize // util_TstrToStr -- converts the passed in tstring into a narrow string. maxSize
// indicates the size of the narrow buffer // indicates the size of the narrow buffer
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// static inline void util_TstrToStr(char* pStr, const TCHAR* pTstr, int maxSize) // static inline void util_TstrToStr(char* pStr, const TCHAR* pTstr, int maxSize)
// { // {
// #ifdef _UNICODE // #ifdef _UNICODE
// ASSERT( maxSize >= wcstombs( 0, pTstr // ASSERT( maxSize >= wcstombs( 0, pTstr
// wcstombs(pStr, pTstr, maxSize); // wcstombs(pStr, pTstr, maxSize);
// #else // #else
// strncpy( pStr, pTstr, maxSize ); // strncpy( pStr, pTstr, maxSize );
// #endif // #endif
// } // }
// //
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -64,9 +64,9 @@ cSerializerImpl::SerRefCountMap cSerializerImpl::mSerRefCountCreateMap ;
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
static uint32 util_GetCRC( const cType& type ) static uint32 util_GetCRC( const cType& type )
{ {
// //
// convert this to narrow... // convert this to narrow...
// //
// NOTE:RAD -- Fixed bug when going from TCHAR is Wide to Multibyte // NOTE:RAD -- Fixed bug when going from TCHAR is Wide to Multibyte
// 09/01/99 - Increased performance by returning byte len instead of // 09/01/99 - Increased performance by returning byte len instead of
@ -77,7 +77,7 @@ static uint32 util_GetCRC( const cType& type )
#ifdef _UNICODE #ifdef _UNICODE
char sz[256]; char sz[256];
const uint8* pszType = (const uint8*)(&sz[0]); const uint8* pszType = (const uint8*)(&sz[0]);
const wchar_t* wsz = type.AsString(); const wchar_t* wsz = type.AsString();
ASSERT( countof(sz) >= ::wcstombs( 0, wsz, size_t(-1) ) ); ASSERT( countof(sz) >= ::wcstombs( 0, wsz, size_t(-1) ) );
@ -102,24 +102,24 @@ static uint32 util_GetCRC( const cType& type )
ASSERT( pszType && *pszType ); ASSERT( pszType && *pszType );
// //
// calculate the crc... // calculate the crc...
// //
CRC_INFO crc; CRC_INFO crc;
crcInit( crc ); crcInit( crc );
crcUpdate( crc, pszType, nBytes ); crcUpdate( crc, pszType, nBytes );
crcFinit( crc ); crcFinit( crc );
return crc.crc; return crc.crc;
} }
//############################################################################# //#############################################################################
// class cSerializerImpl // class cSerializerImpl
//############################################################################# //#############################################################################
cSerializerImpl::cSerializerImpl(cArchive& archive, Mode action, const TSTRING& fileName) : cSerializerImpl::cSerializerImpl(cArchive& archive, Mode action, const TSTRING& fileName) :
mpArchive(&archive), mpArchive(&archive),
mMode(action), mMode(action),
mbInit(false), mbInit(false),
mFileName( fileName ) mFileName( fileName )
{ {
} }
@ -129,13 +129,13 @@ cSerializerImpl::~cSerializerImpl()
bool cSerializerImpl::IsWriting() const bool cSerializerImpl::IsWriting() const
{ {
return (mMode == S_WRITE); return (mMode == S_WRITE);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// static object registration functions; Exactly one of these should be called for // static object registration functions; Exactly one of these should be called for
// every object that is to be serialized. // every object that is to be serialized.
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// TODO:dmb - following line doesn't do anything??? // TODO:dmb - following line doesn't do anything???
@ -143,49 +143,49 @@ bool cSerializerImpl::IsWriting() const
void cSerializerImpl::RegisterSerializable(const cType& type, iTypedSerializable::CreateFunc pFunc) void cSerializerImpl::RegisterSerializable(const cType& type, iTypedSerializable::CreateFunc pFunc)
{ {
uint32 crc = util_GetCRC( type ); uint32 crc = util_GetCRC( type );
if( cSerializerImpl::mSerCreateMap.find( crc ) != cSerializerImpl::mSerCreateMap.end() ) if( cSerializerImpl::mSerCreateMap.find( crc ) != cSerializerImpl::mSerCreateMap.end() )
{ {
// duplicate entry! // duplicate entry!
// //
ASSERT( false ); ASSERT( false );
TOSTRINGSTREAM str; TOSTRINGSTREAM str;
str << _T("Duplicate entry in type table: ") << type.AsString() << std::endl; str << _T("Duplicate entry in type table: ") << type.AsString() << std::endl;
throw eInternal(str.str()); throw eInternal(str.str());
} }
cSerializerImpl::mSerCreateMap[crc] = pFunc; cSerializerImpl::mSerCreateMap[crc] = pFunc;
} }
void cSerializerImpl::RegisterSerializableRefCt(const cType& type, iSerRefCountObj::CreateFunc pFunc) void cSerializerImpl::RegisterSerializableRefCt(const cType& type, iSerRefCountObj::CreateFunc pFunc)
{ {
uint32 crc = util_GetCRC( type ); uint32 crc = util_GetCRC( type );
if( cSerializerImpl::mSerRefCountCreateMap.find( crc ) != cSerializerImpl::mSerRefCountCreateMap.end() ) if( cSerializerImpl::mSerRefCountCreateMap.find( crc ) != cSerializerImpl::mSerRefCountCreateMap.end() )
{ {
// duplicate entry! // duplicate entry!
// //
ASSERT( false ); ASSERT( false );
TOSTRINGSTREAM str; TOSTRINGSTREAM str;
str << _T("Duplicate entry in type table: ") << type.AsString() << std::ends; str << _T("Duplicate entry in type table: ") << type.AsString() << std::ends;
throw eInternal(str.str()); throw eInternal(str.str());
} }
cSerializerImpl::mSerRefCountCreateMap[crc] = pFunc; cSerializerImpl::mSerRefCountCreateMap[crc] = pFunc;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// Init -- the job of init is to clear out the RefCountObj table, fill out the // Init -- the job of init is to clear out the RefCountObj table, fill out the
// mTypeArray, and and write the header information // mTypeArray, and and write the header information
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cSerializerImpl::Init() void cSerializerImpl::Init()
{ {
cDebug d("cSerializerImpl::Init"); cDebug d("cSerializerImpl::Init");
d.TraceDetail("Entering; IsWriting = %s\n", IsWriting() ? "true" : "false"); d.TraceDetail("Entering; IsWriting = %s\n", IsWriting() ? "true" : "false");
mRefCtObjTbl.Clear(); mRefCtObjTbl.Clear();
mbInit = true; mbInit = true;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -193,9 +193,9 @@ void cSerializerImpl::Init()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cSerializerImpl::Finit() void cSerializerImpl::Finit()
{ {
cDebug d("cSerializerImpl::Finit"); cDebug d("cSerializerImpl::Finit");
d.TraceDetail("Exiting; IsWriting = %s\n", IsWriting() ? "true" : "false"); d.TraceDetail("Exiting; IsWriting = %s\n", IsWriting() ? "true" : "false");
mbInit = false; mbInit = false;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -203,168 +203,168 @@ void cSerializerImpl::Finit()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cSerializerImpl::WriteObjectDynCreate(const iTypedSerializable* pObj) void cSerializerImpl::WriteObjectDynCreate(const iTypedSerializable* pObj)
{ {
ASSERT(mbInit); ASSERT(mbInit);
ASSERT(IsWriting()); ASSERT(IsWriting());
cDebug d("cSerializerImpl::WriteObjectDynCreate"); cDebug d("cSerializerImpl::WriteObjectDynCreate");
// CurrentPos() only works with bidir archive // CurrentPos() only works with bidir archive
//d.TraceDetail("Entering... Archive Offset = %d\n", mpArchive->CurrentPos()); //d.TraceDetail("Entering... Archive Offset = %d\n", mpArchive->CurrentPos());
d.TraceDetail(_T(" Object Type = %s\n"), pObj->GetType().AsString()); d.TraceDetail(_T(" Object Type = %s\n"), pObj->GetType().AsString());
// first, we write out the header, which consists of the following: // first, we write out the header, which consists of the following:
// uint32 crc of the object's type // uint32 crc of the object's type
// int32 version of stored data // int32 version of stored data
// int32 size of the chunk (counting from this point; not including the previous int32 // int32 size of the chunk (counting from this point; not including the previous int32
// int32 index into mRefCountObjTbl, or 0 if it isn't refrence counted. // int32 index into mRefCountObjTbl, or 0 if it isn't refrence counted.
// if the index already exists, then no data follows; a refrence // if the index already exists, then no data follows; a refrence
// should just be added to the existing object. // should just be added to the existing object.
ASSERT(mpArchive != 0); ASSERT(mpArchive != 0);
// get the ident for this class type // get the ident for this class type
// //
uint32 crc = util_GetCRC( pObj->GetType() ); uint32 crc = util_GetCRC( pObj->GetType() );
// //
// make sure this type is registered, and figure out if it is refrence counted // make sure this type is registered, and figure out if it is refrence counted
// //
SerRefCountMap::iterator i = mSerRefCountCreateMap.find( crc ); SerRefCountMap::iterator i = mSerRefCountCreateMap.find( crc );
bool bRefCount = true; bool bRefCount = true;
if( i == mSerRefCountCreateMap.end() ) if( i == mSerRefCountCreateMap.end() )
{ {
// //
// maybe it is not refrence counted... // maybe it is not refrence counted...
// //
SerMap::iterator si = mSerCreateMap.find( crc ); SerMap::iterator si = mSerCreateMap.find( crc );
if( si == mSerCreateMap.end() ) if( si == mSerCreateMap.end() )
{ {
d.TraceError("Attempt to serialize unregistered type : %s\n", pObj->GetType().AsString()); d.TraceError("Attempt to serialize unregistered type : %s\n", pObj->GetType().AsString());
ThrowAndAssert(eSerializerUnknownType( pObj->GetType().AsString(), mFileName, eSerializer::TY_FILE )); ThrowAndAssert(eSerializerUnknownType( pObj->GetType().AsString(), mFileName, eSerializer::TY_FILE ));
} }
bRefCount = false; bRefCount = false;
} }
mpArchive->WriteInt32(crc); mpArchive->WriteInt32(crc);
mpArchive->WriteInt32(pObj->Version()); mpArchive->WriteInt32(pObj->Version());
// write a placeholder for the size; we will come back and fill in the right value later... // write a placeholder for the size; we will come back and fill in the right value later...
mpArchive->WriteInt32(0xffffffff); mpArchive->WriteInt32(0xffffffff);
if(bRefCount) if(bRefCount)
{ {
// see if the object has already been serialized... // see if the object has already been serialized...
int idx; int idx;
if((idx = mRefCtObjTbl.Lookup(static_cast<const iSerRefCountObj*>(pObj))) == 0) if((idx = mRefCtObjTbl.Lookup(static_cast<const iSerRefCountObj*>(pObj))) == 0)
{ {
// it is not in the table yet; add it and serialize the object // it is not in the table yet; add it and serialize the object
idx = mRefCtObjTbl.Add(static_cast<const iSerRefCountObj*>(pObj)); idx = mRefCtObjTbl.Add(static_cast<const iSerRefCountObj*>(pObj));
d.TraceDetail("Object [%d] written for first time...\n", idx); d.TraceDetail("Object [%d] written for first time...\n", idx);
mpArchive->WriteInt32(idx); mpArchive->WriteInt32(idx);
pObj->Write(this); pObj->Write(this);
} }
else else
{ {
// since it is already in the table, just write the index number // since it is already in the table, just write the index number
d.TraceDetail("Object [%d] already serialized; incrementing refrence count.\n", idx); d.TraceDetail("Object [%d] already serialized; incrementing refrence count.\n", idx);
mpArchive->WriteInt32(idx); mpArchive->WriteInt32(idx);
} }
} }
else else
{ {
// not reference counted ... just write 0 // not reference counted ... just write 0
mpArchive->WriteInt32(0); mpArchive->WriteInt32(0);
// ... then write the object. // ... then write the object.
pObj->Write(this); pObj->Write(this);
} }
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// ReadObjectDynCreate // ReadObjectDynCreate
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
iTypedSerializable* cSerializerImpl::ReadObjectDynCreate() iTypedSerializable* cSerializerImpl::ReadObjectDynCreate()
{ {
cDebug d("cSerializerImpl::ReadObjectDynCreate"); cDebug d("cSerializerImpl::ReadObjectDynCreate");
//d.TraceDetail("Entering... archive offset = %d\n", mpArchive->CurrentPos()); //d.TraceDetail("Entering... archive offset = %d\n", mpArchive->CurrentPos());
int32 size, objIdx; int32 size, objIdx;
uint32 crc; uint32 crc;
// first, get the type... // first, get the type...
mpArchive->ReadInt32(reinterpret_cast<int32&>(crc)); mpArchive->ReadInt32(reinterpret_cast<int32&>(crc));
// read in the version // read in the version
int32 version; int32 version;
mpArchive->ReadInt32(version); mpArchive->ReadInt32(version);
// read in the size and the index... // read in the size and the index...
mpArchive->ReadInt32(size); mpArchive->ReadInt32(size);
// Save the position so we can seek correctly later on // Save the position so we can seek correctly later on
//int64 sizePos = mpArchive->CurrentPos(); //int64 sizePos = mpArchive->CurrentPos();
mpArchive->ReadInt32(objIdx); mpArchive->ReadInt32(objIdx);
if(objIdx == 0) if(objIdx == 0)
{ {
// the object is not reference counted; create and read in the object // the object is not reference counted; create and read in the object
// first, we need to create the object. // first, we need to create the object.
SerMap::iterator si; SerMap::iterator si;
si = mSerCreateMap.find(crc); si = mSerCreateMap.find(crc);
if(si == mSerCreateMap.end()) if(si == mSerCreateMap.end())
{ {
// unable to find the creation function... // unable to find the creation function...
d.TraceError("Unable to find creation function for non-ref counted object %d\n", crc); d.TraceError("Unable to find creation function for non-ref counted object %d\n", crc);
TOSTRINGSTREAM str; TOSTRINGSTREAM str;
#ifdef _DEBUG #ifdef _DEBUG
// Let's only report the actual crc in debug mode // Let's only report the actual crc in debug mode
str << (int32)crc << std::ends; str << (int32)crc << std::ends;
#endif #endif
ThrowAndAssert(eSerializerUnknownType(str.str(), mFileName, eSerializer::TY_FILE)); ThrowAndAssert(eSerializerUnknownType(str.str(), mFileName, eSerializer::TY_FILE));
} }
iTypedSerializable* pObj = ((*si).second)(); iTypedSerializable* pObj = ((*si).second)();
d.TraceDetail("Created non-ref counted object %s(%p)\n", pObj->GetType().AsString(), pObj); d.TraceDetail("Created non-ref counted object %s(%p)\n", pObj->GetType().AsString(), pObj);
pObj->Read(this, version); pObj->Read(this, version);
// seek past this object in case filepos is not correct! // seek past this object in case filepos is not correct!
//mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING); //mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING);
return pObj; return pObj;
} }
else else
{ {
// refrence counted... // refrence counted...
iSerRefCountObj* pObj; iSerRefCountObj* pObj;
pObj = mRefCtObjTbl.Lookup(objIdx); pObj = mRefCtObjTbl.Lookup(objIdx);
if(pObj == NULL) if(pObj == NULL)
{ {
// not in table yet...first find the creation function // not in table yet...first find the creation function
SerRefCountMap::iterator rci; SerRefCountMap::iterator rci;
rci = mSerRefCountCreateMap.find(crc); rci = mSerRefCountCreateMap.find(crc);
if(rci == mSerRefCountCreateMap.end()) if(rci == mSerRefCountCreateMap.end())
{ {
// unable to find the creation function... // unable to find the creation function...
d.TraceError("Unable to find creation function for ref counted object %d\n", crc); d.TraceError("Unable to find creation function for ref counted object %d\n", crc);
TOSTRINGSTREAM str; TOSTRINGSTREAM str;
str << (int32)crc << std::ends; str << (int32)crc << std::ends;
ThrowAndAssert(eSerializerUnknownType(str.str(), mFileName, eSerializer::TY_FILE)); ThrowAndAssert(eSerializerUnknownType(str.str(), mFileName, eSerializer::TY_FILE));
} }
pObj = ((*rci).second)(); pObj = ((*rci).second)();
d.TraceDetail("Creating Ref-Coutnted object [%d] %s(%p)\n", objIdx, pObj->GetType().AsString(), pObj); d.TraceDetail("Creating Ref-Coutnted object [%d] %s(%p)\n", objIdx, pObj->GetType().AsString(), pObj);
pObj->Read(this); pObj->Read(this);
mRefCtObjTbl.Add(pObj, objIdx); mRefCtObjTbl.Add(pObj, objIdx);
// seek past this object in case filepos is not correct! // seek past this object in case filepos is not correct!
//mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING); //mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING);
return pObj; return pObj;
} }
else else
{ {
// already serialized; just return this object. // already serialized; just return this object.
d.TraceDetail("Adding refrence to previously serialized object [%d] %s(%p)\n", objIdx, pObj->GetType().AsString(), pObj); d.TraceDetail("Adding refrence to previously serialized object [%d] %s(%p)\n", objIdx, pObj->GetType().AsString(), pObj);
pObj->AddRef(); pObj->AddRef();
} }
// seek past this object in case filepos is not correct! // seek past this object in case filepos is not correct!
//mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING); //mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING);
return pObj; return pObj;
} }
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -372,102 +372,102 @@ iTypedSerializable* cSerializerImpl::ReadObjectDynCreate()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cSerializerImpl::WriteObject(const iTypedSerializable* pObj) void cSerializerImpl::WriteObject(const iTypedSerializable* pObj)
{ {
ASSERT(pObj != 0); ASSERT(pObj != 0);
//ASSERT(mbInit); // this isn't needed if we are not writing the type array //ASSERT(mbInit); // this isn't needed if we are not writing the type array
ASSERT(IsWriting()); ASSERT(IsWriting());
cDebug d("cSerializerImpl::WriteObject"); cDebug d("cSerializerImpl::WriteObject");
//d.TraceDetail("Entering... Archive Offset = %d\n", mpArchive->CurrentPos()); //d.TraceDetail("Entering... Archive Offset = %d\n", mpArchive->CurrentPos());
d.TraceDetail(" Object Type = %s\n", pObj->GetType().AsString()); d.TraceDetail(" Object Type = %s\n", pObj->GetType().AsString());
// first, we write out the header, which consists of the following: // first, we write out the header, which consists of the following:
// int32 refrence into mTypeArray, indicating the object's type // int32 refrence into mTypeArray, indicating the object's type
// int32 version of stored data // int32 version of stored data
// int32 size of the chunk (counting from this point; not including the previous int32 // int32 size of the chunk (counting from this point; not including the previous int32
// data the object data // data the object data
ASSERT(mpArchive != 0); ASSERT(mpArchive != 0);
// 5Nov 98 mdb -- I am removing the read and write of type info for this method; it is never used, since // 5Nov 98 mdb -- I am removing the read and write of type info for this method; it is never used, since
// the object is already created when ReadObject() happens. The only good it might serve is in asserting that // the object is already created when ReadObject() happens. The only good it might serve is in asserting that
// the input stream is valid, but I can do that with the 0xffffffff size below (asserting that it is the same // the input stream is valid, but I can do that with the 0xffffffff size below (asserting that it is the same
// when it is read back in) // when it is read back in)
/* int i = 0; /* int i = 0;
for(; i < mTypeArray.size(); i++) for(; i < mTypeArray.size(); i++)
{ {
if(pObj->GetType() == *mTypeArray[i]) if(pObj->GetType() == *mTypeArray[i])
{ {
// aha! this is it! // aha! this is it!
break; break;
} }
} }
if(i == mTypeArray.size()) if(i == mTypeArray.size())
{ {
// the type was not registered; // the type was not registered;
// a debate exists in my mind as to whether this should be an exception or an assertion -- mdb // a debate exists in my mind as to whether this should be an exception or an assertion -- mdb
d.TraceError("Attempt to serialize unregistered type : %s\n", pObj->GetType().AsString()); d.TraceError("Attempt to serialize unregistered type : %s\n", pObj->GetType().AsString());
ThrowAndAssert(eSerializerUnknownType(pObj->GetType().AsString())); ThrowAndAssert(eSerializerUnknownType(pObj->GetType().AsString()));
} }
mpArchive->WriteInt32(i); mpArchive->WriteInt32(i);
*/ */
mpArchive->WriteInt32(0); // place holder for type array index mpArchive->WriteInt32(0); // place holder for type array index
mpArchive->WriteInt32(pObj->Version()); mpArchive->WriteInt32(pObj->Version());
// write a placeholder for the size; we will come back and fill in the right value later... // write a placeholder for the size; we will come back and fill in the right value later...
//int64 sizePos = mpArchive->CurrentPos(); //int64 sizePos = mpArchive->CurrentPos();
mpArchive->WriteInt32(0xffffffff); mpArchive->WriteInt32(0xffffffff);
// write out the object! // write out the object!
pObj->Write(this); pObj->Write(this);
// finally, we need to go back and patch up the size... // finally, we need to go back and patch up the size...
//int64 returnPos = mpArchive->CurrentPos(); //int64 returnPos = mpArchive->CurrentPos();
//mpArchive->Seek(sizePos, cBidirArchive::BEGINNING); //mpArchive->Seek(sizePos, cBidirArchive::BEGINNING);
//mpArchive->WriteInt32((int32)(returnPos - sizePos - sizeof(int32))); //mpArchive->WriteInt32((int32)(returnPos - sizePos - sizeof(int32)));
//mpArchive->Seek(returnPos, cBidirArchive::BEGINNING); //mpArchive->Seek(returnPos, cBidirArchive::BEGINNING);
} }
void cSerializerImpl::ReadObject(iTypedSerializable* pObj) void cSerializerImpl::ReadObject(iTypedSerializable* pObj)
{ {
cDebug d("cSerializerImpl::ReadObjectDynCreate"); cDebug d("cSerializerImpl::ReadObjectDynCreate");
//d.TraceDetail("Entering... archive offset = %d\n", mpArchive->CurrentPos()); //d.TraceDetail("Entering... archive offset = %d\n", mpArchive->CurrentPos());
// NOTE -- type index stuff is gone; see the comment in WriteObject() // NOTE -- type index stuff is gone; see the comment in WriteObject()
int32 /*typeIdx,*/ size; int32 /*typeIdx,*/ size;
// first, get the type... // first, get the type...
/* /*
mpArchive->ReadInt32(typeIdx); mpArchive->ReadInt32(typeIdx);
if((typeIdx < 0) || (typeIdx >= mTypeArray.size())) if((typeIdx < 0) || (typeIdx >= mTypeArray.size()))
{ {
// unknown type index! // unknown type index!
d.TraceError("Encountered bad index into TypeArray: %d\n", typeIdx); d.TraceError("Encountered bad index into TypeArray: %d\n", typeIdx);
ThrowAndAssert(eSerializerInputStremTypeArray()); ThrowAndAssert(eSerializerInputStremTypeArray());
} }
const cType* pType = mTypeArray[typeIdx]; const cType* pType = mTypeArray[typeIdx];
*/ */
// read in the version // read in the version
int32 dummy, version; int32 dummy, version;
mpArchive->ReadInt32(dummy); // old type array index mpArchive->ReadInt32(dummy); // old type array index
mpArchive->ReadInt32(version); mpArchive->ReadInt32(version);
// read in the size and the index... // read in the size and the index...
mpArchive->ReadInt32(size); mpArchive->ReadInt32(size);
// use the size to assert that the file format is correct // use the size to assert that the file format is correct
if(size != (int)0xffffffff) if(size != (int)0xffffffff)
{ {
// unknown type index! // unknown type index!
d.TraceError("Encountered bad size: %d\n", size); d.TraceError("Encountered bad size: %d\n", size);
ThrowAndAssert(eSerializerInputStremTypeArray(_T(""), mFileName, eSerializer::TY_FILE)); ThrowAndAssert(eSerializerInputStremTypeArray(_T(""), mFileName, eSerializer::TY_FILE));
} }
// remember current position // remember current position
//int64 sizePos = mpArchive->CurrentPos(); //int64 sizePos = mpArchive->CurrentPos();
// read in the object! // read in the object!
pObj->Read(this, version); pObj->Read(this, version);
// seek past this object in case filepos is not correct! // seek past this object in case filepos is not correct!
//mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING); //mpArchive->Seek(sizePos + size, cBidirArchive::BEGINNING);
} }
@ -476,52 +476,52 @@ void cSerializerImpl::ReadObject(iTypedSerializable* pObj)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cSerializerImpl::ReadInt16(int16& ret) void cSerializerImpl::ReadInt16(int16& ret)
{ {
mpArchive->ReadInt16(ret); mpArchive->ReadInt16(ret);
} }
void cSerializerImpl::ReadInt32(int32& ret) void cSerializerImpl::ReadInt32(int32& ret)
{ {
mpArchive->ReadInt32(ret); mpArchive->ReadInt32(ret);
} }
void cSerializerImpl::ReadInt64(int64& ret) void cSerializerImpl::ReadInt64(int64& ret)
{ {
mpArchive->ReadInt64(ret); mpArchive->ReadInt64(ret);
} }
void cSerializerImpl::ReadString(TSTRING& ret) void cSerializerImpl::ReadString(TSTRING& ret)
{ {
mpArchive->ReadString(ret); mpArchive->ReadString(ret);
} }
int cSerializerImpl::ReadBlob(void* pBlob, int count) int cSerializerImpl::ReadBlob(void* pBlob, int count)
{ {
return mpArchive->ReadBlob(pBlob, count); return mpArchive->ReadBlob(pBlob, count);
} }
void cSerializerImpl::WriteInt16(int16 i) void cSerializerImpl::WriteInt16(int16 i)
{ {
mpArchive->WriteInt16(i); mpArchive->WriteInt16(i);
} }
void cSerializerImpl::WriteInt32(int32 i) void cSerializerImpl::WriteInt32(int32 i)
{ {
mpArchive->WriteInt32(i); mpArchive->WriteInt32(i);
} }
void cSerializerImpl::WriteInt64(int64 i) void cSerializerImpl::WriteInt64(int64 i)
{ {
mpArchive->WriteInt64(i); mpArchive->WriteInt64(i);
} }
void cSerializerImpl::WriteString(const TSTRING& s) void cSerializerImpl::WriteString(const TSTRING& s)
{ {
mpArchive->WriteString(s); mpArchive->WriteString(s);
} }
void cSerializerImpl::WriteBlob(const void* pBlob, int count) void cSerializerImpl::WriteBlob(const void* pBlob, int count)
{ {
mpArchive->WriteBlob(pBlob, count); mpArchive->WriteBlob(pBlob, count);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -529,6 +529,6 @@ void cSerializerImpl::WriteBlob(const void* pBlob, int count)
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
TSTRING cSerializerImpl::GetFileName() const TSTRING cSerializerImpl::GetFileName() const
{ {
return mFileName; return mFileName;
} }

View File

@ -60,71 +60,71 @@ class cArchive;
class cSerializerImpl : public iSerializer class cSerializerImpl : public iSerializer
{ {
public: public:
enum Mode { S_READ, S_WRITE }; enum Mode { S_READ, S_WRITE };
cSerializerImpl (cArchive& archive, Mode action, const TSTRING& fileName = _T("") ); cSerializerImpl (cArchive& archive, Mode action, const TSTRING& fileName = _T("") );
// fileName is only used for error reporting purposes // fileName is only used for error reporting purposes
virtual ~cSerializerImpl(); virtual ~cSerializerImpl();
bool IsWriting() const; bool IsWriting() const;
// Initializing and closing the archive // Initializing and closing the archive
virtual void Init(); // throw eSerializer virtual void Init(); // throw eSerializer
// initializes the serializer; must be called before any reading or writing is done // initializes the serializer; must be called before any reading or writing is done
virtual void Finit(); virtual void Finit();
// called after a session of serialization is done; called implicitely by the destructor // called after a session of serialization is done; called implicitely by the destructor
// if not called explicitely before destruction // if not called explicitely before destruction
//Reading and writing objects Init() should have already been called or all these will fail. //Reading and writing objects Init() should have already been called or all these will fail.
virtual void WriteObjectDynCreate(const iTypedSerializable* pObj); // throw (eSerializer, eArchive) virtual void WriteObjectDynCreate(const iTypedSerializable* pObj); // throw (eSerializer, eArchive)
// writes an object such that it can be dynamically created when read back in with // writes an object such that it can be dynamically created when read back in with
// ReadObject. // ReadObject.
virtual iTypedSerializable* ReadObjectDynCreate(); // throw (eSerializer, eArchive); virtual iTypedSerializable* ReadObjectDynCreate(); // throw (eSerializer, eArchive);
// reads an object from the archive, returning a pointer to it. The caller is responsible for // reads an object from the archive, returning a pointer to it. The caller is responsible for
// deleteing or Release()ing it when done. // deleteing or Release()ing it when done.
virtual void WriteObject(const iTypedSerializable* pObj); // throw (eSerializer, eArchive) virtual void WriteObject(const iTypedSerializable* pObj); // throw (eSerializer, eArchive)
// writes an object to the archive that will not be dynamically created // writes an object to the archive that will not be dynamically created
virtual void ReadObject(iTypedSerializable* pObj); // throw (eSerializer, eArchive) virtual void ReadObject(iTypedSerializable* pObj); // throw (eSerializer, eArchive)
// reads an object that was written with WriteObject() // reads an object that was written with WriteObject()
// members for registering classes to be serialized. One of these must be called exactly once // members for registering classes to be serialized. One of these must be called exactly once
// for each class that is to be serialized. // for each class that is to be serialized.
static void RegisterSerializable (const cType& type, iTypedSerializable::CreateFunc pFunc); static void RegisterSerializable (const cType& type, iTypedSerializable::CreateFunc pFunc);
static void RegisterSerializableRefCt (const cType& type, iSerRefCountObj::CreateFunc pFunc); static void RegisterSerializableRefCt (const cType& type, iSerRefCountObj::CreateFunc pFunc);
// writing interface // writing interface
// TODO -- I am not sure if I want to keep these or just have the serializer expose the archive. Actually, // TODO -- I am not sure if I want to keep these or just have the serializer expose the archive. Actually,
// I think the best thing might be to have iSerializable only know about the archive // I think the best thing might be to have iSerializable only know about the archive
// Standard data read/write // Standard data read/write
// (All functions can throw eArchave exceptions). // (All functions can throw eArchave exceptions).
virtual void ReadInt16(int16& ret); virtual void ReadInt16(int16& ret);
virtual void ReadInt32(int32& ret); virtual void ReadInt32(int32& ret);
virtual void ReadInt64(int64& ret); virtual void ReadInt64(int64& ret);
virtual void ReadString(TSTRING& ret); virtual void ReadString(TSTRING& ret);
virtual int ReadBlob(void* pBlob, int count); virtual int ReadBlob(void* pBlob, int count);
virtual void WriteInt16(int16 i); virtual void WriteInt16(int16 i);
virtual void WriteInt32(int32 i); virtual void WriteInt32(int32 i);
virtual void WriteInt64(int64 i); virtual void WriteInt64(int64 i);
virtual void WriteString(const TSTRING& s); virtual void WriteString(const TSTRING& s);
virtual void WriteBlob(const void* pBlob, int count); virtual void WriteBlob(const void* pBlob, int count);
virtual TSTRING GetFileName() const; virtual TSTRING GetFileName() const;
private: private:
cArchive* mpArchive; // the archive we are serializing to cArchive* mpArchive; // the archive we are serializing to
Mode mMode; // are we writing or reading? Mode mMode; // are we writing or reading?
bool mbInit; // has init been called? bool mbInit; // has init been called?
cSerRefCountTable mRefCtObjTbl; // keeps track of all ref counted objects that cSerRefCountTable mRefCtObjTbl; // keeps track of all ref counted objects that
// have been read or written during serialization // have been read or written during serialization
TSTRING mFileName; TSTRING mFileName;
// creation function maps // creation function maps
typedef std::map<uint32, iTypedSerializable::CreateFunc> SerMap; typedef std::map<uint32, iTypedSerializable::CreateFunc> SerMap;
typedef std::map<uint32, iSerRefCountObj::CreateFunc> SerRefCountMap; typedef std::map<uint32, iSerRefCountObj::CreateFunc> SerRefCountMap;
static SerMap mSerCreateMap; static SerMap mSerCreateMap;
static SerRefCountMap mSerRefCountCreateMap; static SerRefCountMap mSerRefCountCreateMap;
static void InitSerializableMaps(); static void InitSerializableMaps();
static void FinitSerializableMaps(); static void FinitSerializableMaps();
}; };

View File

@ -39,35 +39,35 @@ namespace {
template<class FROM, class TO> template<class FROM, class TO>
int64 CopyImpl(TO* pTo, FROM* pFrom, int64 amt) int64 CopyImpl(TO* pTo, FROM* pFrom, int64 amt)
{ {
enum { BUF_SIZE = 8192 }; enum { BUF_SIZE = 8192 };
int8 buf[BUF_SIZE]; int8 buf[BUF_SIZE];
int64 amtLeft = amt; int64 amtLeft = amt;
while(amtLeft > 0) while(amtLeft > 0)
{ {
// NOTE: We use int's here rather than int64 because iSerializer and cArchive // NOTE: We use int's here rather than int64 because iSerializer and cArchive
// only take int's as their size parameter - dmb // only take int's as their size parameter - dmb
int amtToRead = amtLeft > BUF_SIZE ? BUF_SIZE : (int)amtLeft; int amtToRead = amtLeft > BUF_SIZE ? BUF_SIZE : (int)amtLeft;
int amtRead = pFrom->ReadBlob(buf, amtToRead ); int amtRead = pFrom->ReadBlob(buf, amtToRead );
amtLeft -= amtRead; amtLeft -= amtRead;
pTo->WriteBlob(buf, amtRead); pTo->WriteBlob(buf, amtRead);
if(amtRead < amtToRead) if(amtRead < amtToRead)
break; break;
} }
// return the amount copied ... // return the amount copied ...
return (amt - amtLeft); return (amt - amtLeft);
} }
} }
int64 cSerializerUtil::Copy( iSerializer* pDest, cArchive* pSrc, int64 amt ) int64 cSerializerUtil::Copy( iSerializer* pDest, cArchive* pSrc, int64 amt )
{ {
return CopyImpl( pDest, pSrc, amt ); return CopyImpl( pDest, pSrc, amt );
} }
int64 cSerializerUtil::Copy( cArchive* pDest, iSerializer* pSrc, int64 amt ) int64 cSerializerUtil::Copy( cArchive* pDest, iSerializer* pSrc, int64 amt )
{ {
return CopyImpl( pDest, pSrc, amt ); return CopyImpl( pDest, pSrc, amt );
} }

View File

@ -44,10 +44,10 @@ class iSerializer;
class cSerializerUtil class cSerializerUtil
{ {
public: public:
static int64 Copy( iSerializer* pDest, cArchive* pSrc, int64 amt ); // throw( eArchvie, eSerilaizer ) static int64 Copy( iSerializer* pDest, cArchive* pSrc, int64 amt ); // throw( eArchvie, eSerilaizer )
static int64 Copy( cArchive* pDest, iSerializer* pSrc, int64 amt ); // throw( eArchvie, eSerilaizer ) static int64 Copy( cArchive* pDest, iSerializer* pSrc, int64 amt ); // throw( eArchvie, eSerilaizer )
// these two methods copy data from archives to serializers and vice-versa. They // these two methods copy data from archives to serializers and vice-versa. They
// throw exceptions on error; the return value is the amount that was copied. // throw exceptions on error; the return value is the amount that was copied.
}; };
#endif #endif

View File

@ -57,8 +57,8 @@ public:
std::string mString; std::string mString;
virtual ~cSerializableNString() {}; virtual ~cSerializableNString() {};
virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive) virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive)
virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive) virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive)
DECLARE_TYPEDSERIALIZABLE() DECLARE_TYPEDSERIALIZABLE()
}; };
@ -72,8 +72,8 @@ public:
std::string mString; std::string mString;
virtual ~cSerializableWString() {}; virtual ~cSerializableWString() {};
virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive) virtual void Read (iSerializer* pSerializer, int32 version = 0); // throw (eSerializer, eArchive)
virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive) virtual void Write(iSerializer* pSerializer) const; // throw (eSerializer, eArchive)
DECLARE_TYPEDSERIALIZABLE() DECLARE_TYPEDSERIALIZABLE()
}; };

View File

@ -36,7 +36,7 @@
/* /*
* sha.c * sha.c
* *
* signature function hook for SHA. * signature function hook for SHA.
* *
* Gene Kim * Gene Kim
* Purdue University * Purdue University
@ -175,7 +175,7 @@ void shsTransform(SHS_INFO *shsInfo)
/* Step A. Copy the data buffer into the local work buffer */ /* Step A. Copy the data buffer into the local work buffer */
for( i = 0; i < 16; i++ ) for( i = 0; i < 16; i++ )
W[ i ] = shsInfo->data[ i ]; W[ i ] = shsInfo->data[ i ];
/* Step B. Expand the 16 words into 64 temporary data words */ /* Step B. Expand the 16 words into 64 temporary data words */
expand( 16 ); expand( 17 ); expand( 18 ); expand( 19 ); expand( 20 ); expand( 16 ); expand( 17 ); expand( 18 ); expand( 19 ); expand( 20 );
@ -244,10 +244,10 @@ static void byteReverse(uint32* buffer, int byteCount)
byteCount /= sizeof( uint32 ); byteCount /= sizeof( uint32 );
for( count = 0; count < byteCount; count++ ) for( count = 0; count < byteCount; count++ )
{ {
value = ( buffer[ count ] << 16 ) | ( buffer[ count ] >> 16 ); value = ( buffer[ count ] << 16 ) | ( buffer[ count ] >> 16 );
buffer[ count ] = ( ( value & 0xFF00FF00L ) >> 8 ) | ( ( value & 0x00FF00FFL ) << 8 ); buffer[ count ] = ( ( value & 0xFF00FF00L ) >> 8 ) | ( ( value & 0x00FF00FFL ) << 8 );
} }
} }
#endif /* #ifndef WORDS_BIGENDIAN */ #endif /* #ifndef WORDS_BIGENDIAN */
@ -260,21 +260,21 @@ void shsUpdate(SHS_INFO* shsInfo, uint8* buffer, int count)
{ {
/* Update bitcount */ /* Update bitcount */
if( ( shsInfo->countLo + ( ( uint32 ) count << 3 ) ) < shsInfo->countLo ) if( ( shsInfo->countLo + ( ( uint32 ) count << 3 ) ) < shsInfo->countLo )
shsInfo->countHi++; /* Carry from low to high bitCount */ shsInfo->countHi++; /* Carry from low to high bitCount */
shsInfo->countLo += ( ( uint32 ) count << 3 ); shsInfo->countLo += ( ( uint32 ) count << 3 );
shsInfo->countHi += ( ( uint32 ) count >> 29 ); shsInfo->countHi += ( ( uint32 ) count >> 29 );
/* Process data in SHS_BLOCKSIZE chunks */ /* Process data in SHS_BLOCKSIZE chunks */
while( count >= SHS_BLOCKSIZE ) while( count >= SHS_BLOCKSIZE )
{ {
memcpy( (char *) shsInfo->data, (char *) buffer, SHS_BLOCKSIZE ); memcpy( (char *) shsInfo->data, (char *) buffer, SHS_BLOCKSIZE );
#ifndef WORDS_BIGENDIAN #ifndef WORDS_BIGENDIAN
byteReverse( shsInfo->data, SHS_BLOCKSIZE ); byteReverse( shsInfo->data, SHS_BLOCKSIZE );
#endif /* #ifndef WORDS_BIGENDIAN */ #endif /* #ifndef WORDS_BIGENDIAN */
shsTransform( shsInfo ); shsTransform( shsInfo );
buffer += SHS_BLOCKSIZE; buffer += SHS_BLOCKSIZE;
count -= SHS_BLOCKSIZE; count -= SHS_BLOCKSIZE;
} }
/* Handle any remaining bytes of data. This should only happen once /* Handle any remaining bytes of data. This should only happen once
on the final lot of data */ on the final lot of data */
@ -295,20 +295,20 @@ void shsFinal(SHS_INFO *shsInfo)
/* Pad out to 56 mod 64 */ /* Pad out to 56 mod 64 */
if( count > 56 ) if( count > 56 )
{ {
/* Two lots of padding: Pad the first block to 64 bytes */ /* Two lots of padding: Pad the first block to 64 bytes */
memset( ( char * ) shsInfo->data + count, 0, 64 - count ); memset( ( char * ) shsInfo->data + count, 0, 64 - count );
#ifndef WORDS_BIGENDIAN #ifndef WORDS_BIGENDIAN
byteReverse( shsInfo->data, SHS_BLOCKSIZE ); byteReverse( shsInfo->data, SHS_BLOCKSIZE );
#endif /* #ifndef WORDS_BIGENDIAN */ #endif /* #ifndef WORDS_BIGENDIAN */
shsTransform( shsInfo ); shsTransform( shsInfo );
/* Now fill the next block with 56 bytes */ /* Now fill the next block with 56 bytes */
memset( (char *) shsInfo->data, 0, 56 ); memset( (char *) shsInfo->data, 0, 56 );
} }
else else
/* Pad block to 56 bytes */ /* Pad block to 56 bytes */
memset( ( char * ) shsInfo->data + count, 0, 56 - count ); memset( ( char * ) shsInfo->data + count, 0, 56 - count );
#ifndef WORDS_BIGENDIAN #ifndef WORDS_BIGENDIAN
byteReverse( shsInfo->data, SHS_BLOCKSIZE ); byteReverse( shsInfo->data, SHS_BLOCKSIZE );
#endif /* #ifndef WORDS_BIGENDIAN */ #endif /* #ifndef WORDS_BIGENDIAN */
@ -350,14 +350,14 @@ void main()
shsUpdate( &shsInfo, ( uint8 * ) "abc", 3 ); shsUpdate( &shsInfo, ( uint8 * ) "abc", 3 );
shsFinal( &shsInfo ); shsFinal( &shsInfo );
if( shsInfo.digest[ 0 ] != 0x0164B8A9L || if( shsInfo.digest[ 0 ] != 0x0164B8A9L ||
shsInfo.digest[ 1 ] != 0x14CD2A5EL || shsInfo.digest[ 1 ] != 0x14CD2A5EL ||
shsInfo.digest[ 2 ] != 0x74C4F7FFL || shsInfo.digest[ 2 ] != 0x74C4F7FFL ||
shsInfo.digest[ 3 ] != 0x082C4D97L || shsInfo.digest[ 3 ] != 0x082C4D97L ||
shsInfo.digest[ 4 ] != 0xF1EDF880L ) shsInfo.digest[ 4 ] != 0xF1EDF880L )
{ {
puts( "Error in SHS implementation" ); puts( "Error in SHS implementation" );
exit( -1 ); exit( -1 );
} }
/* Now perform time trial, generating MD for 10MB of data. First, /* Now perform time trial, generating MD for 10MB of data. First,
initialize the test data */ initialize the test data */
@ -370,7 +370,7 @@ void main()
/* Calculate SHS message digest in TEST_BLOCK_SIZE byte blocks */ /* Calculate SHS message digest in TEST_BLOCK_SIZE byte blocks */
shsInit( &shsInfo ); shsInit( &shsInfo );
for( i = TEST_BLOCKS; i > 0; i-- ) for( i = TEST_BLOCKS; i > 0; i-- )
shsUpdate( &shsInfo, data, TEST_BLOCK_SIZE ); shsUpdate( &shsInfo, data, TEST_BLOCK_SIZE );
shsFinal( &shsInfo ); shsFinal( &shsInfo );
/* Get finish time and time difference */ /* Get finish time and time difference */

View File

@ -46,10 +46,10 @@
/* The structure for storing SHS info */ /* The structure for storing SHS info */
typedef struct { typedef struct {
uint32 digest[ 5 ]; /* Message digest */ uint32 digest[ 5 ]; /* Message digest */
uint32 countLo, countHi; /* 64-bit bit count */ uint32 countLo, countHi; /* 64-bit bit count */
uint32 data[ 16 ]; /* SHS data buffer */ uint32 data[ 16 ]; /* SHS data buffer */
} SHS_INFO; } SHS_INFO;
/* Whether the machine is little-endian or not */ /* Whether the machine is little-endian or not */
@ -63,22 +63,22 @@ void shsFinal(SHS_INFO* shsInfo);
* formulation. Bruce Schneier described it thus in a posting to the * formulation. Bruce Schneier described it thus in a posting to the
* Cypherpunks mailing list on June 21, 1994 (as told to us by Steve Bellovin): * Cypherpunks mailing list on June 21, 1994 (as told to us by Steve Bellovin):
* *
* This is the fix to the Secure Hash Standard, NIST FIPS PUB 180: * This is the fix to the Secure Hash Standard, NIST FIPS PUB 180:
* *
* In Section 7 of FIPS 180 (page 9), the line which reads * In Section 7 of FIPS 180 (page 9), the line which reads
* *
* "b) For t=16 to 79 let Wt = Wt-3 XOR Wt-8 XOR Wt-14 XOR * "b) For t=16 to 79 let Wt = Wt-3 XOR Wt-8 XOR Wt-14 XOR
* Wt-16." * Wt-16."
* *
* is to be replaced by * is to be replaced by
* *
* "b) For t=16 to 79 let Wt = S1(Wt-3 XOR Wt-8 XOR Wt-14 XOR * "b) For t=16 to 79 let Wt = S1(Wt-3 XOR Wt-8 XOR Wt-14 XOR
* Wt-16)." * Wt-16)."
* *
* where S1 is a left circular shift by one bit as defined in * where S1 is a left circular shift by one bit as defined in
* Section 3 of FIPS 180 (page 6): * Section 3 of FIPS 180 (page 6):
* *
* S1(X) = (X<<1) OR (X>>31). * S1(X) = (X<<1) OR (X>>31).
* *
*/ */

View File

@ -54,8 +54,8 @@
class iSerRefCountObj : public cRefCountObj, public iTypedSerializable class iSerRefCountObj : public cRefCountObj, public iTypedSerializable
{ {
public: public:
// the creation function // the creation function
typedef iSerRefCountObj* (*CreateFunc)(void); typedef iSerRefCountObj* (*CreateFunc)(void);
protected: protected:
virtual ~iSerRefCountObj(); virtual ~iSerRefCountObj();
@ -65,21 +65,21 @@ protected:
////////////////////////////// //////////////////////////////
// convenience macros // convenience macros
#define DECLARE_SERREFCOUNT() \ #define DECLARE_SERREFCOUNT() \
DECLARE_TYPED() \ DECLARE_TYPED() \
public: \ public: \
static iSerRefCountObj* Create(); \ static iSerRefCountObj* Create(); \
virtual int32 Version() const; virtual int32 Version() const;
#define IMPLEMENT_SERREFCOUNT(CLASS, TYPEDSTRING, VERSION_MAJOR, VERSION_MINOR) \ #define IMPLEMENT_SERREFCOUNT(CLASS, TYPEDSTRING, VERSION_MAJOR, VERSION_MINOR) \
IMPLEMENT_TYPED(CLASS, TYPEDSTRING) \ IMPLEMENT_TYPED(CLASS, TYPEDSTRING) \
iSerRefCountObj* CLASS::Create() \ iSerRefCountObj* CLASS::Create() \
{ \ { \
return new CLASS; \ return new CLASS; \
} \ } \
int32 CLASS::Version() const \ int32 CLASS::Version() const \
{ \ { \
return iTypedSerializable::MkVersion(VERSION_MAJOR, VERSION_MINOR); \ return iTypedSerializable::MkVersion(VERSION_MAJOR, VERSION_MINOR); \
} }
#endif #endif

View File

@ -54,8 +54,8 @@ cSerRefCountTable::~cSerRefCountTable()
void cSerRefCountTable::Clear() void cSerRefCountTable::Clear()
{ {
mIDToObjTbl.clear(); mIDToObjTbl.clear();
mObjToIdTbl.clear(); mObjToIdTbl.clear();
} }
// find the table id for object. returns 0 if not in table. // find the table id for object. returns 0 if not in table.
@ -63,8 +63,8 @@ int cSerRefCountTable::Lookup(const iSerRefCountObj* pObj)
{ {
std::map<iSerRefCountObj*, int>::iterator itr; std::map<iSerRefCountObj*, int>::iterator itr;
// pay no attention to this cast :-) // pay no attention to this cast :-)
itr = mObjToIdTbl.find(const_cast<iSerRefCountObj*>(pObj)); itr = mObjToIdTbl.find(const_cast<iSerRefCountObj*>(pObj));
return (itr == mObjToIdTbl.end()) ? 0 : itr->second; return (itr == mObjToIdTbl.end()) ? 0 : itr->second;
} }
@ -86,8 +86,8 @@ int cSerRefCountTable::Add(iSerRefCountObj* pObj, int id)
{ {
if (Lookup(pObj) != 0) if (Lookup(pObj) != 0)
{ {
// this should be a programming error, but we will throw just to be safe... // this should be a programming error, but we will throw just to be safe...
ThrowAndAssert(eInternal(_T("cSerRefCountTable::Add() passed object already in table."))); ThrowAndAssert(eInternal(_T("cSerRefCountTable::Add() passed object already in table.")));
} }
if (id == 0) if (id == 0)
{ {
@ -96,8 +96,8 @@ int cSerRefCountTable::Add(iSerRefCountObj* pObj, int id)
} }
else if (Lookup(id) != NULL) else if (Lookup(id) != NULL)
{ {
// this should be a programming error, but we will throw just to be safe... // this should be a programming error, but we will throw just to be safe...
ThrowAndAssert(eInternal(_T("cSerRefCountTable::Add() passed ID already in table."))); ThrowAndAssert(eInternal(_T("cSerRefCountTable::Add() passed ID already in table.")));
} }
mIDToObjTbl.insert( MapIDTObj::value_type(id, pObj)); mIDToObjTbl.insert( MapIDTObj::value_type(id, pObj));
@ -108,8 +108,8 @@ int cSerRefCountTable::Add(iSerRefCountObj* pObj, int id)
int cSerRefCountTable::Add(const iSerRefCountObj* pObj, int id) int cSerRefCountTable::Add(const iSerRefCountObj* pObj, int id)
{ {
iSerRefCountObj* pNonConst = const_cast<iSerRefCountObj*>(pObj); iSerRefCountObj* pNonConst = const_cast<iSerRefCountObj*>(pObj);
return Add(pNonConst, id); return Add(pNonConst, id);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////

View File

@ -54,17 +54,17 @@ public:
// Add an object to the table, optionally specifying an ID. Returns a // Add an object to the table, optionally specifying an ID. Returns a
// unique ID for the object. ASSERTs and throws exception if object is // unique ID for the object. ASSERTs and throws exception if object is
// already in table or the ID is already taken. // already in table or the ID is already taken.
int Add( iSerRefCountObj* pObj, int id = 0); int Add( iSerRefCountObj* pObj, int id = 0);
int Add(const iSerRefCountObj* pObj, int id = 0); int Add(const iSerRefCountObj* pObj, int id = 0);
// TODO -- Note that this class is not really const-correct in that the const version of // TODO -- Note that this class is not really const-correct in that the const version of
// Add() just casts away the constness. The right thing to do is to make the serializer // Add() just casts away the constness. The right thing to do is to make the serializer
// use different versions of this class (const and non-const) depending on whether it is // use different versions of this class (const and non-const) depending on whether it is
// reading or writing and (maybe?) make this class a template class so that it can map // reading or writing and (maybe?) make this class a template class so that it can map
// to either const or non-const objects. // to either const or non-const objects.
// clears out the table // clears out the table
void Clear(); void Clear();
protected: protected:
typedef std::map<int, iSerRefCountObj*> MapIDTObj; typedef std::map<int, iSerRefCountObj*> MapIDTObj;

View File

@ -88,7 +88,7 @@ public:
const byte* operator()( const wc16_string& s, int* const pcbKeyLen ) const byte* operator()( const wc16_string& s, int* const pcbKeyLen )
{ {
*pcbKeyLen = sizeof(WCHAR16) * s.length(); *pcbKeyLen = sizeof(WCHAR16) * s.length();
return (byte*)s.c_str(); return (byte*)s.c_str();
} }
}; };
@ -97,7 +97,7 @@ class tss_hash_key_compare
public: public:
bool operator()( const wc16_string& lhs, const wc16_string& rhs ) bool operator()( const wc16_string& lhs, const wc16_string& rhs )
{ {
return ( lhs.compare( rhs ) == 0 ); return ( lhs.compare( rhs ) == 0 );
} }
}; };
@ -506,12 +506,12 @@ void cMBUCS2Cache::Add(mbchar_t* pMBchar, int mblen, dbchar_t ucs2)
static inline const byte* tss_hash_key_convert()( const TCHAR* psz, int* const pcbKeyLen ) static inline const byte* tss_hash_key_convert()( const TCHAR* psz, int* const pcbKeyLen )
{ {
*pcbKeyLen = sizeof(TCHAR) * _tcslen( psz ); *pcbKeyLen = sizeof(TCHAR) * _tcslen( psz );
return (byte*)psz; return (byte*)psz;
} }
static inline bool tss_hash_key_compare()( const TCHAR* lhs, const TCHAR* rhs ) static inline bool tss_hash_key_compare()( const TCHAR* lhs, const TCHAR* rhs )
{ {
return ( _tcscmp( lhs, rhs ) == 0 ); return ( _tcscmp( lhs, rhs ) == 0 );
} }
cHashTable< dbchar_t*, cHashTable< dbchar_t*,

View File

@ -55,9 +55,9 @@ inline
void TestStringUtil() void TestStringUtil()
{ {
#if USING_NTDBS_STUFF #if USING_NTDBS_STUFF
cDebug db("Test std::char_traits<dbchar_t>"); cDebug db("Test std::char_traits<dbchar_t>");
db.TraceAlways("Entering...\n"); db.TraceAlways("Entering...\n");
tss::dbstring a; tss::dbstring a;
tss::dbstring b; tss::dbstring b;
@ -143,7 +143,7 @@ void TestStringUtil()
//std::string TstrToStr( const TSTRING& tstr ); //std::string TstrToStr( const TSTRING& tstr );
//TSTRING StrToTstr( const std::string& str ); //TSTRING StrToTstr( const std::string& str );
//TSTRING WstrToTstr( const wc16_string& src ); //TSTRING WstrToTstr( const wc16_string& src );
//wc16_string TstrToWstr( const TSTRING& tstr ); //wc16_string TstrToWstr( const TSTRING& tstr );
// test Null assignments // test Null assignments
singleStr = cStringUtil::TstrToStr( tStrNull ); singleStr = cStringUtil::TstrToStr( tStrNull );

View File

@ -54,42 +54,42 @@ template<class TIME_FN, class TIME_TYPE>
class cTaskTimer class cTaskTimer
{ {
public: public:
cTaskTimer(const TSTRING& name) : mName(name), mTotalTime(0), mStartTime(0), mNumStarts(0) {} cTaskTimer(const TSTRING& name) : mName(name), mTotalTime(0), mStartTime(0), mNumStarts(0) {}
~cTaskTimer(); ~cTaskTimer();
void Start(); void Start();
void Stop(); void Stop();
bool IsRunning() { return (mStartTime != 0); } bool IsRunning() { return (mStartTime != 0); }
void Reset() { mNumStarts = mStartTime = mTotalTime = 0 } void Reset() { mNumStarts = mStartTime = mTotalTime = 0 }
int32 GetTotalTime() const; int32 GetTotalTime() const;
int32 GetNumTimesStarted() const; // returns the number of times start() was called int32 GetNumTimesStarted() const; // returns the number of times start() was called
const std::string& GetName() const; const std::string& GetName() const;
private: private:
TSTRING mName; TSTRING mName;
int32 mTotalTime; int32 mTotalTime;
TIME_TYPE mStartTime; TIME_TYPE mStartTime;
int32 mNumStarts; int32 mNumStarts;
}; };
#if IS_UNIX #if IS_UNIX
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// cUnixTimeFn -- Unix version, inserts proper function call and overloads // cUnixTimeFn -- Unix version, inserts proper function call and overloads
// operator() // operator()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
#include <ctime> #include <ctime>
class cUnixTimeFn class cUnixTimeFn
{ {
public: public:
typedef uint32 DataType; typedef uint32 DataType;
uint32 operator()() uint32 operator()()
{ {
return time( &dummy_var ); return time( &dummy_var );
} }
private: private:
time_t dummy_var; time_t dummy_var;
}; };
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -105,45 +105,45 @@ typedef cUnixTaskTimer cGenericTaskTimer;
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
template<class TIME_FN, class TIME_TYPE> template<class TIME_FN, class TIME_TYPE>
inline void cTaskTimer<TIME_FN, TIME_TYPE>::Start() inline void cTaskTimer<TIME_FN, TIME_TYPE>::Start()
{ {
ASSERT(! IsRunning()); ASSERT(! IsRunning());
TIME_FN GetTime; TIME_FN GetTime;
mStartTime = GetTime(); mStartTime = GetTime();
mNumStarts++; mNumStarts++;
} }
template<class TIME_FN, class TIME_TYPE> template<class TIME_FN, class TIME_TYPE>
inline void cTaskTimer<TIME_FN, TIME_TYPE>::Stop() inline void cTaskTimer<TIME_FN, TIME_TYPE>::Stop()
{ {
ASSERT(IsRunning()); ASSERT(IsRunning());
TIME_FN GetTime; TIME_FN GetTime;
mTotalTime += ( GetTime() - mStartTime ); mTotalTime += ( GetTime() - mStartTime );
mStartTime = 0; mStartTime = 0;
} }
template<class TIME_FN, class TIME_TYPE> template<class TIME_FN, class TIME_TYPE>
inline int32 cTaskTimer<TIME_FN, TIME_TYPE>::GetTotalTime() const inline int32 cTaskTimer<TIME_FN, TIME_TYPE>::GetTotalTime() const
{ {
return mTotalTime; return mTotalTime;
} }
template<class TIME_FN, class TIME_TYPE> template<class TIME_FN, class TIME_TYPE>
inline const std::string& cTaskTimer<TIME_FN, TIME_TYPE>::GetName() const inline const std::string& cTaskTimer<TIME_FN, TIME_TYPE>::GetName() const
{ {
return mName return mName
} }
template<class TIME_FN, class TIME_TYPE> template<class TIME_FN, class TIME_TYPE>
inline cTaskTimer<TIME_FN, TIME_TYPE>::~cTaskTimer() inline cTaskTimer<TIME_FN, TIME_TYPE>::~cTaskTimer()
{ {
// stop the timer if it is currently running // stop the timer if it is currently running
if(IsRunning()) if(IsRunning())
Stop(); Stop();
// trace out the time contents... // trace out the time contents...
cDebug d("cTaskTimer"); cDebug d("cTaskTimer");
d.TraceDebug("----- Time to execute %s: %d (started %d times)\n", mName.c_str(), mTotalTime, mNumStarts); d.TraceDebug("----- Time to execute %s: %d (started %d times)\n", mName.c_str(), mTotalTime, mNumStarts);
} }

View File

@ -114,12 +114,12 @@ typedef std::ifstream TIFSTREAM;
#define _tcsncmp strncmp #define _tcsncmp strncmp
// other abstractions // other abstractions
#define TUNLINK unlink #define TUNLINK unlink
// string representation // string representation
#if defined(_T) #if defined(_T)
// run it right over with a bulldozer, tripwire doesn't seem // run it right over with a bulldozer, tripwire doesn't seem
// to use ctype.h's _T -PH // to use ctype.h's _T -PH
#undef _T #undef _T
#endif #endif
#define _T(x) x #define _T(x) x

View File

@ -44,7 +44,7 @@
// //
bool TimeBombExploded() bool TimeBombExploded()
{ {
struct tm time_struct; struct tm time_struct;
/* /*
memset(&time_struct, 0, sizeof(time_struct)); memset(&time_struct, 0, sizeof(time_struct));

View File

@ -52,7 +52,7 @@
// METHOD CODE // METHOD CODE
//========================================================================= //=========================================================================
#define TIME_MAX 2147483647L // largest signed 32 bit number #define TIME_MAX 2147483647L // largest signed 32 bit number
#ifdef __AROS__ #ifdef __AROS__
#define tzset() #define tzset()

View File

@ -44,36 +44,36 @@ static void tw_psignal( int sig, const TCHAR* s );
tw_sighandler_t tw_signal(int sig, tw_sighandler_t pFunc) tw_sighandler_t tw_signal(int sig, tw_sighandler_t pFunc)
{ {
return signal(sig, pFunc); return signal(sig, pFunc);
} }
int tw_raise(int sig) int tw_raise(int sig)
{ {
return raise(sig); return raise(sig);
} }
tw_sighandler_t tw_sigign(int sig) tw_sighandler_t tw_sigign(int sig)
{ {
return signal(sig, SIG_IGN); return signal(sig, SIG_IGN);
} }
////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////
// tw_HandleSignal -- Take a given signal and install a handler for // tw_HandleSignal -- Take a given signal and install a handler for
// it, which will then exit with the supplied exit value // it, which will then exit with the supplied exit value
tw_sighandler_t tw_HandleSignal( int sig ) tw_sighandler_t tw_HandleSignal( int sig )
{ {
return signal( sig, util_SignalHandler ); return signal( sig, util_SignalHandler );
} }
void util_SignalHandler( int sig ) void util_SignalHandler( int sig )
{ {
//If we're on unix, let's print out a nice error message telling //If we're on unix, let's print out a nice error message telling
//the user which signal we've recieved. //the user which signal we've recieved.
#if IS_UNIX #if IS_UNIX
tw_psignal( sig, (TSS_GetString( cCore, core::STR_SIGNAL).c_str() ) ); tw_psignal( sig, (TSS_GetString( cCore, core::STR_SIGNAL).c_str() ) );
#endif #endif
exit( 8 ); exit( 8 );
} }
#if IS_UNIX #if IS_UNIX
@ -108,7 +108,7 @@ void tw_psignal(int sig, const TCHAR *str)
_T("Virtual Timer Expired"), _T("Virtual Timer Expired"),
_T("Profiling Timer Expired"), _T("Profiling Timer Expired"),
_T("Pollable Event"), _T("Pollable Event"),
_T("Window Size Change"), _T("Window Size Change"),
_T("Stopped (signal)"), _T("Stopped (signal)"),
_T("Stopped (user)"), _T("Stopped (user)"),
_T("Continued"), _T("Continued"),

View File

@ -31,7 +31,7 @@
// //
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// tw_signal.h -- a wrapper around signal(), needed because of linux // tw_signal.h -- a wrapper around signal(), needed because of linux
// build issues // build issues
// //
#ifndef __TW_SIGNAL_H #ifndef __TW_SIGNAL_H
#define __TW_SIGNAL_H #define __TW_SIGNAL_H
@ -39,7 +39,7 @@
#include <signal.h> #include <signal.h>
#ifdef HAVE_SIGNUM_H #ifdef HAVE_SIGNUM_H
#include <signum.h> // the signal number constants #include <signum.h> // the signal number constants
#endif #endif
#ifdef HAVE_BITS_SIGNUM_H #ifdef HAVE_BITS_SIGNUM_H
#include <bits/signum.h> #include <bits/signum.h>
@ -50,7 +50,7 @@ typedef void (*tw_sighandler_t)(int);
} }
tw_sighandler_t tw_signal(int sig, tw_sighandler_t pFunc); tw_sighandler_t tw_signal(int sig, tw_sighandler_t pFunc);
int tw_raise (int sig); int tw_raise (int sig);
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// tw_sigign -- wrapper around tw_signal(XXX, SIG_IGN) // tw_sigign -- wrapper around tw_signal(XXX, SIG_IGN)

View File

@ -172,7 +172,7 @@ public:
// Format( numT n, std::basic_string< CharT >& sBuf ) // Format( numT n, std::basic_string< CharT >& sBuf )
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// EFFECTS: Does all actual formatting for FormatNumber methods // EFFECTS: Does all actual formatting for FormatNumber methods
// //
static static
std::basic_string< CharT >& std::basic_string< CharT >&
Format( numT n, std::basic_string< CharT >& sBuf, bool fCStyleFormatting = false ) Format( numT n, std::basic_string< CharT >& sBuf, bool fCStyleFormatting = false )
@ -255,8 +255,8 @@ TSTRING& cTWLocale::FormatTime( int64 t, TSTRING& strBuf )
{ {
util_FormatTime( ptm, strBuf ); util_FormatTime( ptm, strBuf );
} }
else else
{ {
strBuf = TSS_GetString( cCore, core::STR_UNKNOWN_TIME ); strBuf = TSS_GetString( cCore, core::STR_UNKNOWN_TIME );
} }
@ -311,7 +311,7 @@ TSTRING& util_FormatTimeC( struct tm* ptm, TSTRING& strBuf )
TCHAR achTimeBuf[256]; TCHAR achTimeBuf[256];
/* XXX: This should check (#ifdef) for strftime - PH */ /* XXX: This should check (#ifdef) for strftime - PH */
size_t nbWritten = _tcsftime( achTimeBuf, countof( achTimeBuf ), size_t nbWritten = _tcsftime( achTimeBuf, countof( achTimeBuf ),
#if IS_MSVC // MSVC uses proprietary '#' #if IS_MSVC // MSVC uses proprietary '#'

View File

@ -38,7 +38,7 @@
enum Languages enum Languages
{ {
LANG_USENGLISH = 1 LANG_USENGLISH = 1
}; };
#endif #endif

View File

@ -44,23 +44,23 @@
class cType class cType
{ {
public: public:
cType(const TCHAR* name); cType(const TCHAR* name);
const TCHAR* AsString() const; const TCHAR* AsString() const;
bool operator==(const cType& rhs) const; bool operator==(const cType& rhs) const;
bool operator!=(const cType& rhs) const; bool operator!=(const cType& rhs) const;
private: private:
TSTRING mString; TSTRING mString;
}; };
class iTyped class iTyped
{ {
public: public:
virtual const cType& GetType() const = 0; virtual const cType& GetType() const = 0;
// the type of an FCO; classes that implement this interface need to // the type of an FCO; classes that implement this interface need to
// (a) declare a public static const cType member mType and // (a) declare a public static const cType member mType and
// (b) returning that object in their implementation of GetType() // (b) returning that object in their implementation of GetType()
// You can use the macros below to simplify the process // You can use the macros below to simplify the process
virtual ~iTyped() {} virtual ~iTyped() {}
}; };
@ -72,70 +72,70 @@ public:
public:\ public:\
static const cType mType;\ static const cType mType;\
virtual const cType& GetType() const; virtual const cType& GetType() const;
// put DECLARE_TYPED in the class definition // put DECLARE_TYPED in the class definition
#define IMPLEMENT_TYPED(CLASS, STRING)\ #define IMPLEMENT_TYPED(CLASS, STRING)\
const cType CLASS::mType(STRING);\ const cType CLASS::mType(STRING);\
const cType& CLASS::GetType() const\ const cType& CLASS::GetType() const\
{\ {\
return mType;\ return mType;\
} }
// put IMPLEMENT_TYPED in the .cpp file where the class is implemented // put IMPLEMENT_TYPED in the .cpp file where the class is implemented
#define CLASS_TYPE(CLASS) CLASS::mType #define CLASS_TYPE(CLASS) CLASS::mType
// a convienent way to specify a class's type // a convienent way to specify a class's type
/////////////////////////////////////////////// ///////////////////////////////////////////////
// iTyped Example // iTyped Example
/////////////////////////////////////////////// ///////////////////////////////////////////////
/* /*
(foo.h) (foo.h)
class cFoo : public iTyped class cFoo : public iTyped
{ {
public: public:
DECLARE_TYPED() DECLARE_TYPED()
} }
(foo.cpp) (foo.cpp)
DECLARE_TYPED(cFoo, "Foo"); DECLARE_TYPED(cFoo, "Foo");
(main.cpp) (main.cpp)
int main() int main()
{ {
iTyped* pi = Bar(); // returned a cFoo iTyped* pi = Bar(); // returned a cFoo
cout << "Encountered class " << pi->GetType().AsString() << endl; cout << "Encountered class " << pi->GetType().AsString() << endl;
// prints "Encountered class Foo" // prints "Encountered class Foo"
if(pi->GetType() == CLASS_TYPE(cFoo)) if(pi->GetType() == CLASS_TYPE(cFoo))
{ {
cFoo* pFoo = static_cast<cFoo*>(pi); cFoo* pFoo = static_cast<cFoo*>(pi);
// cast is always safe // cast is always safe
} }
} }
*/ */
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// inline implementation // inline implementation
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
inline cType::cType(const TCHAR* name) : inline cType::cType(const TCHAR* name) :
mString(name) mString(name)
{ {
ASSERT(!mString.empty()); ASSERT(!mString.empty());
} }
inline const TCHAR* cType::AsString() const inline const TCHAR* cType::AsString() const
{ {
return mString.c_str(); return mString.c_str();
} }
inline bool cType::operator==(const cType& rhs) const inline bool cType::operator==(const cType& rhs) const
{ {
return (this == &rhs); return (this == &rhs);
} }
inline bool cType::operator!=(const cType& rhs) const inline bool cType::operator!=(const cType& rhs) const
{ {
return (this != &rhs); return (this != &rhs);
} }

View File

@ -40,38 +40,38 @@
// standard TSS types // standard TSS types
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
typedef unsigned char byte ; // platform-independent typedef unsigned char byte ; // platform-independent
typedef signed char int8 ; typedef signed char int8 ;
typedef short int16 ; typedef short int16 ;
typedef float float32 ; typedef float float32 ;
typedef double float64 ; typedef double float64 ;
typedef unsigned char uint8 ; typedef unsigned char uint8 ;
typedef unsigned short uint16 ; typedef unsigned short uint16 ;
#if SIZEOF_INT == 4 #if SIZEOF_INT == 4
typedef int int32 ; typedef int int32 ;
typedef unsigned int uint32 ; typedef unsigned int uint32 ;
#elif SIZEOF_LONG == 4 #elif SIZEOF_LONG == 4
typedef long int32 ; typedef long int32 ;
typedef unsigned long uint32 ; typedef unsigned long uint32 ;
#else #else
# error "I don't seem to have a 32-bit integer type on this system." # error "I don't seem to have a 32-bit integer type on this system."
#endif #endif
#if SIZEOF_LONG == 8 #if SIZEOF_LONG == 8
typedef long int64 ; typedef long int64 ;
typedef unsigned long uint64 ; typedef unsigned long uint64 ;
#elif SIZEOF_LONG_LONG == 8 #elif SIZEOF_LONG_LONG == 8
typedef long long int64 ; typedef long long int64 ;
typedef unsigned long long uint64 ; typedef unsigned long long uint64 ;
#else #else
# error "I don't seem to have a 64-bit integer type on this system." # error "I don't seem to have a 64-bit integer type on this system."
#endif #endif
// other Win32 definitions // other Win32 definitions
//typedef uint16 UINT; //typedef uint16 UINT;
//typedef uint32 DWORD; //typedef uint32 DWORD;
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// Limits -- should be platform independent, right? ( assumes 2's complement numbers ) // Limits -- should be platform independent, right? ( assumes 2's complement numbers )

View File

@ -39,45 +39,45 @@
// TODO: JEB: make this look like eFileError // TODO: JEB: make this look like eFileError
eUnix::eUnix( const TCHAR* szFunctionName, const TCHAR* szObjectName, bool fCallGetLastError) eUnix::eUnix( const TCHAR* szFunctionName, const TCHAR* szObjectName, bool fCallGetLastError)
: eError( _T("")) : eError( _T(""))
{ {
#if IS_UNIX #if IS_UNIX
ASSERT( szFunctionName || szObjectName || fCallGetLastError ); ASSERT( szFunctionName || szObjectName || fCallGetLastError );
// //
// construct the error message: // construct the error message:
// //
// it will be of the form: FuncName() failed for Object: <FormatMessage output> // it will be of the form: FuncName() failed for Object: <FormatMessage output>
// //
if( szFunctionName ) if( szFunctionName )
{ {
mMsg = szFunctionName; mMsg = szFunctionName;
mMsg += _T(" failed"); mMsg += _T(" failed");
if( szObjectName ) if( szObjectName )
{ {
mMsg += _T(" for "); mMsg += _T(" for ");
mMsg += szObjectName; mMsg += szObjectName;
} }
} }
else if( szObjectName ) else if( szObjectName )
{ {
mMsg = szObjectName; mMsg = szObjectName;
} }
else else
{ {
mMsg = _T("Error"); mMsg = _T("Error");
} }
if( fCallGetLastError ) if( fCallGetLastError )
{ {
TSTRING strErr = strerror(errno); TSTRING strErr = strerror(errno);
if( ! strErr.empty() ) if( ! strErr.empty() )
{ {
mMsg += _T(": "); mMsg += _T(": ");
mMsg += strErr; mMsg += strErr;
} }
} }
#endif // IS_UNIX #endif // IS_UNIX
} }

View File

@ -43,12 +43,12 @@
TSS_BEGIN_EXCEPTION( eUnix, eError ) TSS_BEGIN_EXCEPTION( eUnix, eError )
eUnix( const TCHAR* functionName, const TCHAR* objectName, bool displayErrorNumber = true ); eUnix( const TCHAR* functionName, const TCHAR* objectName, bool displayErrorNumber = true );
// construct one of these to indicate a unix api failure. both functionName and // construct one of these to indicate a unix api failure. both functionName and
// objectName can be NULL. This method will construct a string to pass to eError // objectName can be NULL. This method will construct a string to pass to eError
// that contains all of the above information plus whatever errno returns if the dusplayErrorNumber // that contains all of the above information plus whatever errno returns if the dusplayErrorNumber
// parameter is true. // parameter is true.
TSS_END_EXCEPTION() TSS_END_EXCEPTION()

View File

@ -32,7 +32,7 @@
////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////
// unixfsservices.cpp // unixfsservices.cpp
// //
// Implements cUnixFSServices class in unixfsservices.h // Implements cUnixFSServices class in unixfsservices.h
// //
#include "core/stdcore.h" #include "core/stdcore.h"
@ -143,18 +143,18 @@ cUnixFSServices::~cUnixFSServices()
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// GetErrString // GetErrString
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
TSTRING cUnixFSServices::GetErrString() const TSTRING cUnixFSServices::GetErrString() const
{ {
TSTRING ret; TSTRING ret;
char* pErrorStr = strerror(errno); char* pErrorStr = strerror(errno);
#ifdef _UNICODE #ifdef _UNICODE
wchar_t pBuf[1024]; wchar_t pBuf[1024];
mbstowcs(pBuf, pErrorStr, 1024); mbstowcs(pBuf, pErrorStr, 1024);
ret = pBuf; ret = pBuf;
#else #else
ret = pErrorStr; ret = pErrorStr;
#endif #endif
return ret; return ret;
} }
@ -186,71 +186,71 @@ void cUnixFSServices::ReadDir(const TSTRING& strFilename, std::vector<TSTRING> &
#else #else
void cUnixFSServices::ReadDir(const TSTRING& strFilenameC, std::vector<TSTRING>& v, bool bFullPaths) const throw(eFSServices) void cUnixFSServices::ReadDir(const TSTRING& strFilenameC, std::vector<TSTRING>& v, bool bFullPaths) const throw(eFSServices)
{ {
TSTRING strFilename = cArosPath::AsNative(strFilenameC); TSTRING strFilename = cArosPath::AsNative(strFilenameC);
#endif #endif
//Get all the filenames //Get all the filenames
DIR* dp; DIR* dp;
dp = opendir( strFilename.c_str() ); dp = opendir( strFilename.c_str() );
if (dp == NULL) if (dp == NULL)
{ {
throw eFSServicesGeneric( strFilename, iFSServices::GetInstance()->GetErrString() ); throw eFSServicesGeneric( strFilename, iFSServices::GetInstance()->GetErrString() );
return; return;
} }
struct dirent* d; struct dirent* d;
while ((d = readdir(dp)) != NULL) while ((d = readdir(dp)) != NULL)
{ {
if ((strcmp(d->d_name, _T(".")) != 0) && (strcmp(d->d_name, _T("..")) != 0)) if ((strcmp(d->d_name, _T(".")) != 0) && (strcmp(d->d_name, _T("..")) != 0))
{ {
if( bFullPaths ) if( bFullPaths )
{ {
//Create the full pathname //Create the full pathname
TSTRING strNewName = strFilename; TSTRING strNewName = strFilename;
// get full path of dir entry // get full path of dir entry
util_TrailingSep( strNewName, true ); util_TrailingSep( strNewName, true );
strNewName += d->d_name; strNewName += d->d_name;
// save full path name // save full path name
v.push_back( strNewName ); v.push_back( strNewName );
} }
else else
v.push_back( d->d_name ); v.push_back( d->d_name );
} }
} }
//Close the directory //Close the directory
closedir( dp ); closedir( dp );
} }
/* needs to and with S_IFMT, check EQUALITY with S_*, and return more types /* needs to and with S_IFMT, check EQUALITY with S_*, and return more types
cFSStatArgs::FileType cUnixFSServices::GetFileType(const cFCOName &filename) throw(eFSServices) cFSStatArgs::FileType cUnixFSServices::GetFileType(const cFCOName &filename) throw(eFSServices)
{ {
cFSStatArgs stat; cFSStatArgs stat;
Stat(filename, stat); Stat(filename, stat);
return stat.mFileType; return stat.mFileType;
} }
*/ */
void cUnixFSServices::GetCurrentDir( TSTRING& strCurDir ) const throw(eFSServices) void cUnixFSServices::GetCurrentDir( TSTRING& strCurDir ) const throw(eFSServices)
{ {
TCHAR pathname[iFSServices::TW_MAX_PATH]; TCHAR pathname[iFSServices::TW_MAX_PATH];
pathname[0] = '\0'; pathname[0] = '\0';
TCHAR* ret = getcwd(pathname, sizeof(TCHAR)*iFSServices::TW_MAX_PATH); TCHAR* ret = getcwd(pathname, sizeof(TCHAR)*iFSServices::TW_MAX_PATH);
if (ret == NULL) if (ret == NULL)
throw eFSServicesGeneric( strCurDir, iFSServices::GetInstance()->GetErrString() ); throw eFSServicesGeneric( strCurDir, iFSServices::GetInstance()->GetErrString() );
strCurDir = pathname; strCurDir = pathname;
} }
void cUnixFSServices::ChangeDir( const TSTRING& strDir ) const throw(eFSServices) void cUnixFSServices::ChangeDir( const TSTRING& strDir ) const throw(eFSServices)
{ {
if( chdir( strDir.c_str() ) < 0 ) if( chdir( strDir.c_str() ) < 0 )
throw eFSServicesGeneric( strDir, iFSServices::GetInstance()->GetErrString() ); throw eFSServicesGeneric( strDir, iFSServices::GetInstance()->GetErrString() );
} }
@ -294,7 +294,7 @@ TSTRING& cUnixFSServices::MakeTempFilename( TSTRING& strName ) const throw(eFSSe
wchar_t wcsbuf[1024]; wchar_t wcsbuf[1024];
mbstowcs( wcsbuf, pchTempFileName, strlen( pchTempFileName ) + 1 )); mbstowcs( wcsbuf, pchTempFileName, strlen( pchTempFileName ) + 1 ));
strName = wcsbuf; strName = wcsbuf;
#else #else
strName = pchTempFileName; strName = pchTempFileName;
#endif #endif
@ -303,25 +303,25 @@ TSTRING& cUnixFSServices::MakeTempFilename( TSTRING& strName ) const throw(eFSSe
// So I'll always attempt to delete it -bam // So I'll always attempt to delete it -bam
FileDelete( strName ); FileDelete( strName );
return( strName ); return( strName );
} }
void cUnixFSServices::Mkdir( const TSTRING& strName ) const throw ( eFSServices ) void cUnixFSServices::Mkdir( const TSTRING& strName ) const throw ( eFSServices )
{ {
if( 0 != _tmkdir( strName.c_str(), 0777 ) ) if( 0 != _tmkdir( strName.c_str(), 0777 ) )
{ {
// if mkdir failed because the dir existed, that's OK // if mkdir failed because the dir existed, that's OK
if( errno != EEXIST ) if( errno != EEXIST )
throw eFSServicesGeneric( strName, iFSServices::GetInstance()->GetErrString() ); throw eFSServicesGeneric( strName, iFSServices::GetInstance()->GetErrString() );
} }
} }
bool cUnixFSServices::Rmdir( const TSTRING& strName ) const bool cUnixFSServices::Rmdir( const TSTRING& strName ) const
{ {
if( 0 == rmdir( strName.c_str() ) ) if( 0 == rmdir( strName.c_str() ) )
return true; return true;
return false; return false;
} }
void cUnixFSServices::GetTempDirName( TSTRING& strName ) const throw(eFSServices) void cUnixFSServices::GetTempDirName( TSTRING& strName ) const throw(eFSServices)
@ -341,19 +341,19 @@ void cUnixFSServices::Stat( const TSTRING& strName, cFSStatArgs &stat ) const th
#else #else
void cUnixFSServices::Stat( const TSTRING& strNameC, cFSStatArgs& stat) const throw(eFSServices) void cUnixFSServices::Stat( const TSTRING& strNameC, cFSStatArgs& stat) const throw(eFSServices)
{ {
TSTRING strName = cArosPath::AsNative(strNameC); TSTRING strName = cArosPath::AsNative(strNameC);
#endif #endif
//local variable for obtaining info on file. //local variable for obtaining info on file.
struct stat statbuf; struct stat statbuf;
int ret; int ret;
ret = lstat( strName.c_str(), &statbuf ); ret = lstat( strName.c_str(), &statbuf );
cDebug d( "cUnixFSServices::Stat" ); cDebug d( "cUnixFSServices::Stat" );
d.TraceDetail( "Executing on file %s (result=%d)\n", strName.c_str(), ret ); d.TraceDetail( "Executing on file %s (result=%d)\n", strName.c_str(), ret );
if( ret < 0 ) if( ret < 0 )
throw eFSServicesGeneric( strName, iFSServices::GetInstance()->GetErrString() ); throw eFSServicesGeneric( strName, iFSServices::GetInstance()->GetErrString() );
// new stuff 7/17/99 - BAM // new stuff 7/17/99 - BAM
// if the file is not a device set rdev to zero by hand (most OSs will // if the file is not a device set rdev to zero by hand (most OSs will
@ -365,46 +365,46 @@ void cUnixFSServices::Stat( const TSTRING& strNameC, cFSStatArgs& stat) const th
util_ZeroMemory( statbuf.st_rdev ); util_ZeroMemory( statbuf.st_rdev );
} }
//copy information returned by lstat call into the structure passed in //copy information returned by lstat call into the structure passed in
stat.gid = statbuf.st_gid; stat.gid = statbuf.st_gid;
stat.atime = statbuf.st_atime; stat.atime = statbuf.st_atime;
stat.ctime = statbuf.st_ctime; stat.ctime = statbuf.st_ctime;
stat.mtime = statbuf.st_mtime; stat.mtime = statbuf.st_mtime;
stat.dev = statbuf.st_dev; stat.dev = statbuf.st_dev;
stat.rdev = statbuf.st_rdev; stat.rdev = statbuf.st_rdev;
stat.ino = statbuf.st_ino; stat.ino = statbuf.st_ino;
stat.mode = statbuf.st_mode; stat.mode = statbuf.st_mode;
stat.nlink = statbuf.st_nlink; stat.nlink = statbuf.st_nlink;
stat.size = statbuf.st_size; stat.size = statbuf.st_size;
stat.uid = statbuf.st_uid; stat.uid = statbuf.st_uid;
stat.blksize = statbuf.st_blksize; stat.blksize = statbuf.st_blksize;
stat.blocks = statbuf.st_blocks; stat.blocks = statbuf.st_blocks;
// set the file type // set the file type
if(S_ISREG(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_FILE; if(S_ISREG(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_FILE;
else if(S_ISDIR(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_DIR; else if(S_ISDIR(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_DIR;
else if(S_ISLNK(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_SYMLINK; else if(S_ISLNK(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_SYMLINK;
else if(S_ISBLK(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_BLOCKDEV; else if(S_ISBLK(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_BLOCKDEV;
else if(S_ISCHR(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_CHARDEV; else if(S_ISCHR(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_CHARDEV;
else if(S_ISFIFO(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_FIFO; else if(S_ISFIFO(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_FIFO;
else if(S_ISSOCK(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_SOCK; else if(S_ISSOCK(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_SOCK;
#ifdef S_IFDOOR #ifdef S_IFDOOR
else if(S_ISDOOR(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_DOOR; else if(S_ISDOOR(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_DOOR;
#endif #endif
#ifdef S_IFPORT #ifdef S_IFPORT
else if(S_ISPORT(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_PORT; else if(S_ISPORT(statbuf.st_mode)) stat.mFileType = cFSStatArgs::TY_PORT;
#endif #endif
else stat.mFileType = cFSStatArgs::TY_INVALID; else stat.mFileType = cFSStatArgs::TY_INVALID;
} }
void cUnixFSServices::GetMachineName( TSTRING& strName ) const throw( eFSServices ) void cUnixFSServices::GetMachineName( TSTRING& strName ) const throw( eFSServices )
{ {
struct utsname namebuf; struct utsname namebuf;
if( uname( &namebuf ) == -1 ) if( uname( &namebuf ) == -1 )
throw eFSServicesGeneric( strName ); throw eFSServicesGeneric( strName );
else else
strName = namebuf.nodename; strName = namebuf.nodename;
} }
void cUnixFSServices::GetMachineNameFullyQualified( TSTRING& strName ) const void cUnixFSServices::GetMachineNameFullyQualified( TSTRING& strName ) const
@ -455,7 +455,7 @@ bool cUnixFSServices::GetCurrentUserName( TSTRING& strName ) const
fSuccess = true; fSuccess = true;
} }
else else
strName = _T(""); strName = _T("");
return( fSuccess ); return( fSuccess );
} }
@ -506,17 +506,17 @@ bool cUnixFSServices::GetIPAddress( uint32& uiIPAddress )
bool cUnixFSServices::IsCaseSensitive() const bool cUnixFSServices::IsCaseSensitive() const
{ {
return true; return true;
} }
bool cUnixFSServices::GetOwnerForFile( const TSTRING& tstrFilename, TSTRING& tstrUser ) const bool cUnixFSServices::GetOwnerForFile( const TSTRING& tstrFilename, TSTRING& tstrUser ) const
{ {
bool fSuccess = true; bool fSuccess = true;
struct stat statbuf; struct stat statbuf;
int ret = lstat(tstrFilename.c_str(), &statbuf); int ret = lstat(tstrFilename.c_str(), &statbuf);
if(ret < 0) if(ret < 0)
{ {
fSuccess = false; fSuccess = false;
} }
@ -525,11 +525,11 @@ bool cUnixFSServices::GetOwnerForFile( const TSTRING& tstrFilename, TSTRING& tst
{ {
struct passwd* pp = getpwuid( statbuf.st_uid ); struct passwd* pp = getpwuid( statbuf.st_uid );
//ASSERT( pp ); //ASSERT( pp );
// We shouldn't assert this, because it might be the case that a file // We shouldn't assert this, because it might be the case that a file
// is associated with some old user that no longer exists... we should // is associated with some old user that no longer exists... we should
// not fail this case. Instead, the method will just return false per // not fail this case. Instead, the method will just return false per
// the test below. // the test below.
if( pp == NULL ) if( pp == NULL )
{ {
fSuccess = false; fSuccess = false;
} }
@ -545,10 +545,10 @@ bool cUnixFSServices::GetOwnerForFile( const TSTRING& tstrFilename, TSTRING& tst
bool cUnixFSServices::GetGroupForFile( const TSTRING& tstrFilename, TSTRING& tstrGroup ) const bool cUnixFSServices::GetGroupForFile( const TSTRING& tstrFilename, TSTRING& tstrGroup ) const
{ {
bool fSuccess = true; bool fSuccess = true;
struct stat statbuf; struct stat statbuf;
int ret = lstat(tstrFilename.c_str(), &statbuf); int ret = lstat(tstrFilename.c_str(), &statbuf);
if(ret < 0) if(ret < 0)
{ {
fSuccess = false; fSuccess = false;
} }
@ -558,21 +558,21 @@ bool cUnixFSServices::GetGroupForFile( const TSTRING& tstrFilename, TSTRING& tst
struct group* pg = getgrgid( statbuf.st_gid ); struct group* pg = getgrgid( statbuf.st_gid );
//ASSERT( pg ); this assert stops everything in debug mode if we can't lookup a groupid //ASSERT( pg ); this assert stops everything in debug mode if we can't lookup a groupid
if( pg == NULL ) if( pg == NULL )
{ {
fSuccess = false; fSuccess = false;
tstrGroup = TSS_GetString(cCore, core::STR_UNKNOWN); tstrGroup = TSS_GetString(cCore, core::STR_UNKNOWN);
} }
else else
tstrGroup = pg->gr_name; tstrGroup = pg->gr_name;
} }
return( fSuccess ); return( fSuccess );
} }
//////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////
// Function name : cUnixFSServices::ConvertModeToString // Function name : cUnixFSServices::ConvertModeToString
// Description : takes a TSTRING and fills it with an "ls -l" representation // Description : takes a TSTRING and fills it with an "ls -l" representation
// of the object's permission bits ( e.g. "drwxr-x--x" ). // of the object's permission bits ( e.g. "drwxr-x--x" ).
// //
// Returns : void -- no errors are reported // Returns : void -- no errors are reported
@ -583,95 +583,95 @@ bool cUnixFSServices::GetGroupForFile( const TSTRING& tstrFilename, TSTRING& tst
void cUnixFSServices::ConvertModeToString( uint64 perm, TSTRING& tstrPerm ) const void cUnixFSServices::ConvertModeToString( uint64 perm, TSTRING& tstrPerm ) const
{ {
TCHAR szPerm[11]; //10 permission bits plus the NULL TCHAR szPerm[11]; //10 permission bits plus the NULL
_tcscpy( szPerm, _T("----------") ); _tcscpy( szPerm, _T("----------") );
ASSERT( sizeof(unsigned short) <= sizeof(uint32) ); ASSERT( sizeof(unsigned short) <= sizeof(uint32) );
// We do this in case an "unsigned short" is ever larger than the // We do this in case an "unsigned short" is ever larger than the
// value we are switching on, since the size of the mode parameter // value we are switching on, since the size of the mode parameter
// will be unsigned short (whatever that means, for the given platform...) // will be unsigned short (whatever that means, for the given platform...)
// check file type // check file type
switch ((uint32)perm & S_IFMT) //some versions of Unix don't like to switch on switch ((uint32)perm & S_IFMT) //some versions of Unix don't like to switch on
//64 bit values. //64 bit values.
{ {
case S_IFDIR: case S_IFDIR:
szPerm[0] = _T('d'); szPerm[0] = _T('d');
break; break;
case S_IFCHR: case S_IFCHR:
szPerm[0] = _T('c'); szPerm[0] = _T('c');
break; break;
case S_IFBLK: case S_IFBLK:
szPerm[0] = _T('b'); szPerm[0] = _T('b');
break; break;
case S_IFIFO: case S_IFIFO:
szPerm[0] = _T('p'); szPerm[0] = _T('p');
break; break;
case S_IFLNK: case S_IFLNK:
szPerm[0] = _T('l'); szPerm[0] = _T('l');
break; break;
#ifdef S_IFDOOR #ifdef S_IFDOOR
case S_IFDOOR: case S_IFDOOR:
szPerm[0] = _T('D'); szPerm[0] = _T('D');
break; break;
#endif #endif
#ifdef S_IFPORT #ifdef S_IFPORT
case S_IFPORT: case S_IFPORT:
szPerm[0] = _T('P'); szPerm[0] = _T('P');
break; break;
#endif #endif
break; break;
} }
// check owner read and write // check owner read and write
if (perm & S_IRUSR) if (perm & S_IRUSR)
szPerm[1] = _T('r'); szPerm[1] = _T('r');
if (perm & S_IWUSR) if (perm & S_IWUSR)
szPerm[2] = _T('w'); szPerm[2] = _T('w');
// check owner execute // check owner execute
if (perm & S_ISUID && perm & S_IXUSR) if (perm & S_ISUID && perm & S_IXUSR)
szPerm[3] = _T('s'); szPerm[3] = _T('s');
else if (perm & S_IXUSR) else if (perm & S_IXUSR)
szPerm[3] = _T('x'); szPerm[3] = _T('x');
else if (perm & S_ISUID) else if (perm & S_ISUID)
szPerm[3] = _T('S'); szPerm[3] = _T('S');
// check group read and write // check group read and write
if (perm & S_IRGRP) if (perm & S_IRGRP)
szPerm[4] = _T('r'); szPerm[4] = _T('r');
if (perm & S_IWGRP) if (perm & S_IWGRP)
szPerm[5] = _T('w'); szPerm[5] = _T('w');
// check group execute // check group execute
if (perm & S_ISGID && perm & S_IXGRP) if (perm & S_ISGID && perm & S_IXGRP)
szPerm[6] = _T('s'); szPerm[6] = _T('s');
else if (perm & S_IXGRP) else if (perm & S_IXGRP)
szPerm[6] = _T('x'); szPerm[6] = _T('x');
else if (perm & S_ISGID) else if (perm & S_ISGID)
szPerm[6] = _T('l'); szPerm[6] = _T('l');
// check other read and write // check other read and write
if (perm & S_IROTH) if (perm & S_IROTH)
szPerm[7] = _T('r'); szPerm[7] = _T('r');
if (perm & S_IWOTH) if (perm & S_IWOTH)
szPerm[8] = _T('w'); szPerm[8] = _T('w');
// check other execute // check other execute
if (perm & S_ISVTX && perm & S_IXOTH) if (perm & S_ISVTX && perm & S_IXOTH)
szPerm[9] = _T('t'); szPerm[9] = _T('t');
else if (perm & S_IXOTH) else if (perm & S_IXOTH)
szPerm[9] = _T('x'); szPerm[9] = _T('x');
else if (perm & S_ISVTX) else if (perm & S_ISVTX)
szPerm[9] = _T('T'); szPerm[9] = _T('T');
tstrPerm = szPerm; tstrPerm = szPerm;
return; return;
} }
//////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////
// Function name : cUnixFSServices::Rename // Function name : cUnixFSServices::Rename
// Description : Rename a file. Overwrites newname if it exists.and overwrite is true // Description : Rename a file. Overwrites newname if it exists.and overwrite is true
// //
// Returns : false if failure, true on success // Returns : false if failure, true on success
bool cUnixFSServices::Rename(const TSTRING& strOldName, const TSTRING& strNewName, bool overwrite) const bool cUnixFSServices::Rename(const TSTRING& strOldName, const TSTRING& strNewName, bool overwrite) const
@ -728,16 +728,16 @@ bool cUnixFSServices::GetExecutableFilename( TSTRING& strFullPath, const TSTRING
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// Function name : cUnixFSServices::FullPath // Function name : cUnixFSServices::FullPath
// Description : // Description :
// //
// Return type : bool // Return type : bool
// Argument : TSTRING& strFullPath // Argument : TSTRING& strFullPath
// Argument : const TSTRING& strRelPathC // Argument : const TSTRING& strRelPathC
// Argument : const TSTRING& pathRelFromC // Argument : const TSTRING& pathRelFromC
// //
// TODO -- is throwing an exception the more appropriate alternative to returning // TODO -- is throwing an exception the more appropriate alternative to returning
// a bool? I think it is ... mdb // a bool? I think it is ... mdb
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cUnixFSServices::FullPath( TSTRING& strFullPath, const TSTRING& strRelPathC, const TSTRING& pathRelFromC ) const bool cUnixFSServices::FullPath( TSTRING& strFullPath, const TSTRING& strRelPathC, const TSTRING& pathRelFromC ) const
{ {
@ -755,7 +755,7 @@ bool cUnixFSServices::FullPath( TSTRING& strFullPath, const TSTRING& strRelPathC
// //
if( strRelPath[0] == TW_SLASH ) // if is absolute path if( strRelPath[0] == TW_SLASH ) // if is absolute path
{ {
if( IsRoot( strRelPath ) ) // if it's root, don't monkey with it, just return it. if( IsRoot( strRelPath ) ) // if it's root, don't monkey with it, just return it.
{ {
strFullPath = strRelPath; strFullPath = strRelPath;
@ -763,26 +763,26 @@ bool cUnixFSServices::FullPath( TSTRING& strFullPath, const TSTRING& strRelPathC
} }
else else
{ {
strFullPath = _T(""); // push root, then add path elements from strRelPathC strFullPath = _T(""); // push root, then add path elements from strRelPathC
// one by one (in while loop below) // one by one (in while loop below)
} }
} }
else // is a relative path, so check pathRelFromC else // is a relative path, so check pathRelFromC
{ {
if( pathRelFromC.empty() ) // if we're relative to CWD... if( pathRelFromC.empty() ) // if we're relative to CWD...
{ {
// //
// get the current working directory // get the current working directory
// //
try try
{ {
GetCurrentDir( strFullPath ); GetCurrentDir( strFullPath );
util_TrailingSep( strFullPath, false ); util_TrailingSep( strFullPath, false );
} }
catch( eFSServices& ) catch( eFSServices& )
{ {
return false; return false;
} }
} }
else // we're relative to a given dir else // we're relative to a given dir
{ {
@ -850,8 +850,8 @@ int cUnixFSServices::CreateLockedTemporaryFile( const TCHAR* szFilename, int per
O_CREAT | O_EXCL; // only create a new file -- error if it exists already O_CREAT | O_EXCL; // only create a new file -- error if it exists already
// create file // create file
int fh = _topen( szFilename, oflags, 0666 ); int fh = _topen( szFilename, oflags, 0666 );
if( fh >= 0 ) if( fh >= 0 )
{ {
// file was created. Now unlink it // file was created. Now unlink it
if( 0 != unlink( szFilename ) ) if( 0 != unlink( szFilename ) )
@ -873,10 +873,10 @@ void cUnixFSServices::Sleep( int nSeconds ) const
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
// Function name : IsRoot // Function name : IsRoot
// Description : A root path is all '/'s // Description : A root path is all '/'s
// //
// Return type : bool // Return type : bool
// Argument : const TSTRING& strPath // Argument : const TSTRING& strPath
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool cUnixFSServices::IsRoot( const TSTRING& strPath ) const bool cUnixFSServices::IsRoot( const TSTRING& strPath ) const
@ -904,12 +904,12 @@ bool cUnixFSServices::IsRoot( const TSTRING& strPath ) const
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// Function name : util_PathFind // Function name : util_PathFind
// Description : // Description :
// takes single-element executible filename and looks in path env var for it // takes single-element executible filename and looks in path env var for it
// assumes path is colon-delimited string of directories. // assumes path is colon-delimited string of directories.
// //
// Return type : bool // Return type : bool
// Argument : TSTRING& strFullPath // Argument : TSTRING& strFullPath
// Argument : const TSTRING& strFilename // Argument : const TSTRING& strFilename
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -989,11 +989,11 @@ bool util_PathFind( TSTRING& strFullPath, const TSTRING& strFilename )
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
// Function name : util_FileIsExecutable // Function name : util_FileIsExecutable
// Description : file ( or file a link points to ) must be a regular // Description : file ( or file a link points to ) must be a regular
// file and executable by someone // file and executable by someone
// //
// Return type : bool // Return type : bool
// Argument : const TSTRING& strFile // Argument : const TSTRING& strFile
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
bool util_FileIsExecutable( const TSTRING& strFile ) bool util_FileIsExecutable( const TSTRING& strFile )
@ -1002,7 +1002,7 @@ bool util_FileIsExecutable( const TSTRING& strFile )
return false; return false;
struct stat s; struct stat s;
if( stat( strFile.c_str(), &s ) < 0 ) // this call handles links if( stat( strFile.c_str(), &s ) < 0 ) // this call handles links
return false; return false;
return( S_ISREG( s.st_mode ) && ( s.st_mode & ( S_IXUSR | S_IXGRP | S_IXOTH ) ) ); // can someone execute it? return( S_ISREG( s.st_mode ) && ( s.st_mode & ( S_IXUSR | S_IXGRP | S_IXOTH ) ) ); // can someone execute it?
@ -1010,13 +1010,13 @@ bool util_FileIsExecutable( const TSTRING& strFile )
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
// Function name : util_RemoveDuplicateSeps // Function name : util_RemoveDuplicateSeps
// Description : // Description :
// takes all adjacent slashes and replaces them with a single slash // takes all adjacent slashes and replaces them with a single slash
// ///root//foo -> /root/foo // ///root//foo -> /root/foo
// rel//foo/// -> rel/foo/ // rel//foo/// -> rel/foo/
// //
// Return type : void // Return type : void
// Argument : TSTRING& strPath // Argument : TSTRING& strPath
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void util_RemoveDuplicateSeps( TSTRING& strPath ) void util_RemoveDuplicateSeps( TSTRING& strPath )
@ -1051,15 +1051,15 @@ void util_RemoveDuplicateSeps( TSTRING& strPath )
////////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////////
// Function name : util_RemoveLastPathElement // Function name : util_RemoveLastPathElement
// Description : // Description :
// effectively pops off a path element from the end, except for the root dir, where it does nothing // effectively pops off a path element from the end, except for the root dir, where it does nothing
// it removes any slashes before and after the element // it removes any slashes before and after the element
// ///root//foo/ -> leaves "///root" ("foo" is strElem) // ///root//foo/ -> leaves "///root" ("foo" is strElem)
// ///root -> leaves "" ("root" is strElem) // ///root -> leaves "" ("root" is strElem)
// // -> leaves "" ("" is strElem) // // -> leaves "" ("" is strElem)
// //
// Return type : void // Return type : void
// Argument : TSTRING& strPath // Argument : TSTRING& strPath
// Argument : TSTRING& strElem // Argument : TSTRING& strElem
///////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////
@ -1091,8 +1091,8 @@ void util_RemoveLastPathElement( TSTRING& strPath, TSTRING& strElem )
//////////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////////
// Function name : util_GetNextPathElement // Function name : util_GetNextPathElement
// Description : // Description :
// starting from the left side of the path string, returns the index'th path element // starting from the left side of the path string, returns the index'th path element
// returns true if the element exists, false if there aren't <index + 1> many elements // returns true if the element exists, false if there aren't <index + 1> many elements
// //
@ -1101,7 +1101,7 @@ void util_RemoveLastPathElement( TSTRING& strPath, TSTRING& strElem )
// 2rd element of ABC/DEF/GH -> GH // 2rd element of ABC/DEF/GH -> GH
// 1st element of //ABC/DEF/GH -> DEF // 1st element of //ABC/DEF/GH -> DEF
// //
// Return type : bool : got path element? ( i.e. was there index path elements? ) // Return type : bool : got path element? ( i.e. was there index path elements? )
// Argument : const TSTRING& strPathC // Argument : const TSTRING& strPathC
// Argument : TSTRING& strElem // Argument : TSTRING& strElem
// Argument : int index // Argument : int index
@ -1146,10 +1146,10 @@ bool util_GetNextPathElement( const TSTRING& strPathC, TSTRING& strElem, int ind
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
// Function name : util_TrailingSep // Function name : util_TrailingSep
// Description : ensure that a path ( fLeaveSep ? "has" : "does not have" ) a trailing slash // Description : ensure that a path ( fLeaveSep ? "has" : "does not have" ) a trailing slash
// //
// Return type : bool : was there a trailing slash? // Return type : bool : was there a trailing slash?
// Argument : TSTRING& str // Argument : TSTRING& str
// Argument : bool fLeaveSep // Argument : bool fLeaveSep
///////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////
@ -1179,10 +1179,10 @@ bool util_TrailingSep( TSTRING& str, bool fLeaveSep )
} }
///////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////
// Function name : util_RemoveTrailingSeps // Function name : util_RemoveTrailingSeps
// Description : removes all trailing separators // Description : removes all trailing separators
// //
// Return type : void // Return type : void
// Argument : TSTRING& str // Argument : TSTRING& str
///////////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////////
void util_RemoveTrailingSeps( TSTRING& str ) void util_RemoveTrailingSeps( TSTRING& str )

View File

@ -44,7 +44,7 @@
// parameters of dissimilar types. Therefore, *FwdIter need not be // parameters of dissimilar types. Therefore, *FwdIter need not be
// the same type as CmpObjT. Uses a binary search algorithm. // the same type as CmpObjT. Uses a binary search algorithm.
// //
// Return type : FwdIterT : First element in the sequence [first, last) // Return type : FwdIterT : First element in the sequence [first, last)
// that is equal to or greater than 'obj' or // that is equal to or greater than 'obj' or
// 'last' if there is no such element. // 'last' if there is no such element.
// //
@ -60,12 +60,12 @@ template< class FwdIterT, class CmpObjT, class CmpFuncT > FwdIterT UpperBound( F
int nElemsInSet = 0; int nElemsInSet = 0;
FwdIterT iCur = first; FwdIterT iCur = first;
for (; iCur != last; ++iCur ) for (; iCur != last; ++iCur )
++nElemsInSet; ++nElemsInSet;
iCur = first; iCur = first;
while( 0 < nElemsInSet ) while( 0 < nElemsInSet )
{ {
// go to halfway point // go to halfway point
int iHalfWay = nElemsInSet/2; int iHalfWay = nElemsInSet/2;
FwdIterT iTemp = iCur; FwdIterT iTemp = iCur;
@ -75,15 +75,15 @@ template< class FwdIterT, class CmpObjT, class CmpFuncT > FwdIterT UpperBound( F
if( less( *iTemp, obj ) ) if( less( *iTemp, obj ) )
{ {
// start next search set at next elem with half of the last search set's elements // start next search set at next elem with half of the last search set's elements
iCur = ++iTemp; iCur = ++iTemp;
nElemsInSet -= iHalfWay + 1; // already searched ( iHalfway + 1 ) elems nElemsInSet -= iHalfWay + 1; // already searched ( iHalfway + 1 ) elems
} }
else else
{ {
// start next search set beginning with half of the last search set's elements // start next search set beginning with half of the last search set's elements
nElemsInSet = iHalfWay; nElemsInSet = iHalfWay;
} }
} }
return iCur; return iCur;
} }

View File

@ -49,7 +49,7 @@
iUserNotify* iUserNotify::mpInstance = 0; iUserNotify* iUserNotify::mpInstance = 0;
iUserNotify::iUserNotify(int verboseLevel) : iUserNotify::iUserNotify(int verboseLevel) :
mVerboseLevel(verboseLevel) mVerboseLevel(verboseLevel)
{ {
} }
@ -59,12 +59,12 @@ iUserNotify::~iUserNotify()
void iUserNotify::SetVerboseLevel(int level) void iUserNotify::SetVerboseLevel(int level)
{ {
mVerboseLevel = level; mVerboseLevel = level;
} }
int iUserNotify::GetVerboseLevel() const int iUserNotify::GetVerboseLevel() const
{ {
return mVerboseLevel; return mVerboseLevel;
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -74,8 +74,8 @@ void iUserNotify::NotifySilent( const TCHAR* format, ... )
{ {
va_list args; va_list args;
va_start(args, format); va_start(args, format);
HandleNotify( V_SILENT, format, args ); HandleNotify( V_SILENT, format, args );
va_end(args); va_end(args);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -85,8 +85,8 @@ void iUserNotify::NotifyNormal( const TCHAR* format, ... )
{ {
va_list args; va_list args;
va_start(args, format); va_start(args, format);
HandleNotify( V_NORMAL, format, args ); HandleNotify( V_NORMAL, format, args );
va_end(args); va_end(args);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -96,8 +96,8 @@ void iUserNotify::NotifyVerbose( const TCHAR* format, ... )
{ {
va_list args; va_list args;
va_start(args, format); va_start(args, format);
HandleNotify( V_VERBOSE, format, args ); HandleNotify( V_VERBOSE, format, args );
va_end(args); va_end(args);
} }
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -107,8 +107,8 @@ void iUserNotify::Notify(int verboseLevel, const TCHAR* format, ...)
{ {
va_list args; va_list args;
va_start(args, format); va_start(args, format);
HandleNotify( verboseLevel, format, args ); HandleNotify( verboseLevel, format, args );
va_end(args); va_end(args);
} }

View File

@ -46,48 +46,48 @@
class iUserNotify class iUserNotify
{ {
public: public:
// singleton interface; caller is responsible for deleting pointer; // singleton interface; caller is responsible for deleting pointer;
static iUserNotify* GetInstance(); static iUserNotify* GetInstance();
static void SetInstance(iUserNotify* pInst); static void SetInstance(iUserNotify* pInst);
virtual void Notify(int verboseLevel, const TCHAR* format, ...) ; virtual void Notify(int verboseLevel, const TCHAR* format, ...) ;
// notify the user that an event has occured. The outcome of this operation is // notify the user that an event has occured. The outcome of this operation is
// dependant on the type of object that is implementing this interface (for example, // dependant on the type of object that is implementing this interface (for example,
// a console application would want an iUserNotify that prints things to stdout) // a console application would want an iUserNotify that prints things to stdout)
// If the current verbosity level is less than verboseLevel, nothing will happen. // If the current verbosity level is less than verboseLevel, nothing will happen.
// All output should be sent through the cDisplayEncoder beforehand // All output should be sent through the cDisplayEncoder beforehand
// TODO:BAM -- enforce this somehow? // TODO:BAM -- enforce this somehow?
virtual void SetVerboseLevel(int level); virtual void SetVerboseLevel(int level);
virtual int GetVerboseLevel() const; virtual int GetVerboseLevel() const;
// get/set the current verbosity level. Notify()s that occur whose verbosity level // get/set the current verbosity level. Notify()s that occur whose verbosity level
// is greater than the current level will not be processed. // is greater than the current level will not be processed.
// a convenience enumeration; no one is bound by law to use these // a convenience enumeration; no one is bound by law to use these
enum VerboseLevel enum VerboseLevel
{ {
V_SILENT = 0, V_SILENT = 0,
V_NORMAL = 1, V_NORMAL = 1,
V_VERBOSE = 2 V_VERBOSE = 2
}; };
// //
// convenience methods for notifying at these three levels... // convenience methods for notifying at these three levels...
// //
void NotifySilent ( const TCHAR* format, ... ); void NotifySilent ( const TCHAR* format, ... );
void NotifyNormal ( const TCHAR* format, ... ); void NotifyNormal ( const TCHAR* format, ... );
void NotifyVerbose ( const TCHAR* format, ... ); void NotifyVerbose ( const TCHAR* format, ... );
iUserNotify(int verboseLevel = 0); iUserNotify(int verboseLevel = 0);
virtual ~iUserNotify(); virtual ~iUserNotify();
protected: protected:
virtual void HandleNotify( int level, const TCHAR* format, va_list& args ) = 0; virtual void HandleNotify( int level, const TCHAR* format, va_list& args ) = 0;
// this is implemented in derived classes to implement the specific type of // this is implemented in derived classes to implement the specific type of
// notification desired // notification desired
int mVerboseLevel; int mVerboseLevel;
private: private:
static iUserNotify* mpInstance; static iUserNotify* mpInstance;
}; };
@ -102,29 +102,29 @@ private:
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
#define TW_NOTIFY_SILENT\ #define TW_NOTIFY_SILENT\
if( iUserNotify::GetInstance()->GetVerboseLevel() >= iUserNotify::V_SILENT )\ if( iUserNotify::GetInstance()->GetVerboseLevel() >= iUserNotify::V_SILENT )\
iUserNotify::GetInstance()->NotifySilent iUserNotify::GetInstance()->NotifySilent
#define TW_NOTIFY_NORMAL\ #define TW_NOTIFY_NORMAL\
if( iUserNotify::GetInstance()->GetVerboseLevel() >= iUserNotify::V_NORMAL )\ if( iUserNotify::GetInstance()->GetVerboseLevel() >= iUserNotify::V_NORMAL )\
iUserNotify::GetInstance()->NotifyNormal iUserNotify::GetInstance()->NotifyNormal
#define TW_NOTIFY_VERBOSE\ #define TW_NOTIFY_VERBOSE\
if( iUserNotify::GetInstance()->GetVerboseLevel() >= iUserNotify::V_VERBOSE )\ if( iUserNotify::GetInstance()->GetVerboseLevel() >= iUserNotify::V_VERBOSE )\
iUserNotify::GetInstance()->NotifyVerbose iUserNotify::GetInstance()->NotifyVerbose
//############################################################################# //#############################################################################
// inline implementation // inline implementation
//############################################################################# //#############################################################################
inline iUserNotify* iUserNotify::GetInstance() inline iUserNotify* iUserNotify::GetInstance()
{ {
ASSERT(mpInstance != 0); ASSERT(mpInstance != 0);
return mpInstance; return mpInstance;
} }
inline void iUserNotify::SetInstance(iUserNotify* pInst) inline void iUserNotify::SetInstance(iUserNotify* pInst)
{ {
mpInstance = pInst; mpInstance = pInst;
} }

View File

@ -38,19 +38,19 @@
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void cUserNotifyStdout::HandleNotify( int level, const TCHAR* format, va_list& args ) void cUserNotifyStdout::HandleNotify( int level, const TCHAR* format, va_list& args )
{ {
if(GetVerboseLevel() < level) if(GetVerboseLevel() < level)
return; return;
// all verbose output now goes to stderr // all verbose output now goes to stderr
if(level < iUserNotify::V_VERBOSE) if(level < iUserNotify::V_VERBOSE)
{ {
_vtprintf(format, args); _vtprintf(format, args);
fflush( stdout ); fflush( stdout );
} }
else else
{ {
_vftprintf(stderr, format, args); _vftprintf(stderr, format, args);
fflush( stderr ); fflush( stderr );
} }
} }

View File

@ -43,10 +43,10 @@
class cUserNotifyStdout : public iUserNotify class cUserNotifyStdout : public iUserNotify
{ {
public: public:
virtual void HandleNotify( int level, const TCHAR* format, va_list& args ) ; virtual void HandleNotify( int level, const TCHAR* format, va_list& args ) ;
// formats the string and sends it to stdout // formats the string and sends it to stdout
// NOTE -- a little tripwire specific hack has been applied that makes all output // NOTE -- a little tripwire specific hack has been applied that makes all output
// at or above iUserNotify::V_VERBOSE go to stderr instead of stdout // at or above iUserNotify::V_VERBOSE go to stderr instead of stdout
}; };
#endif /* __USERNOTIFYSTDOUT_H */ #endif /* __USERNOTIFYSTDOUT_H */

View File

@ -61,7 +61,7 @@ public:
TCHAR* string; TCHAR* string;
}; };
// Select between the different localized string sets // Select between the different localized string sets
// for this product. Returns false if string not defined. // for this product. Returns false if string not defined.
virtual bool SelectStringSet(int setID) = 0; virtual bool SelectStringSet(int setID) = 0;
@ -83,11 +83,11 @@ public:
// Add a single string. The above rules apply. // Add a single string. The above rules apply.
virtual void AddString(int setID, int stringID, TCHAR* string) = 0; virtual void AddString(int setID, int stringID, TCHAR* string) = 0;
// singleton manipulation // singleton manipulation
static iUserString* GetInstance(); static iUserString* GetInstance();
static void SetInstance(iUserString* pInst); static void SetInstance(iUserString* pInst);
private: private:
static iUserString* mpInstance; static iUserString* mpInstance;
}; };
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -116,14 +116,14 @@ Example Use:
/////////////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////////////////////////
inline iUserString* iUserString::GetInstance() inline iUserString* iUserString::GetInstance()
{ {
ASSERT(mpInstance); ASSERT(mpInstance);
return mpInstance; return mpInstance;
} }
inline void iUserString::SetInstance(iUserString* pInst) inline void iUserString::SetInstance(iUserString* pInst)
{ {
mpInstance = pInst; mpInstance = pInst;
} }

View File

@ -73,7 +73,7 @@ const TCHAR* cUserStringMemBased::GetString(int stringID) const
{ {
// mCurrentStringSet is invallid // mCurrentStringSet is invallid
ASSERT(false); ASSERT(false);
return _T("<Bad String Set>"); return _T("<Bad String Set>");
} }
StringSet::const_iterator stringItr; StringSet::const_iterator stringItr;
@ -84,7 +84,7 @@ const TCHAR* cUserStringMemBased::GetString(int stringID) const
{ {
// string not found // string not found
ASSERT(false); ASSERT(false);
return _T("<Missing String>"); return _T("<Missing String>");
} }
return stringItr->second; return stringItr->second;

View File

@ -69,11 +69,11 @@ public:
~cUserStringMemBased(); ~cUserStringMemBased();
// the abstract interface // the abstract interface
virtual bool SelectStringSet (int setID); virtual bool SelectStringSet (int setID);
virtual const TCHAR* GetString (int stringID) const; virtual const TCHAR* GetString (int stringID) const;
virtual void ClearStringSet (int id); virtual void ClearStringSet (int id);
virtual void AddStringSet (int setID, const iUserString::tStringPair* pPairArray); virtual void AddStringSet (int setID, const iUserString::tStringPair* pPairArray);
virtual void AddString (int setID, int stringID, TCHAR* string); virtual void AddString (int setID, int stringID, TCHAR* string);
private: private:
typedef std::map<int, TCHAR*> StringSet; typedef std::map<int, TCHAR*> StringSet;

View File

@ -97,7 +97,7 @@ wchar_t* cUTF8::allocate( const char* in ) THROW( std::bad_alloc )
//--Convert //--Convert
out[0] = 0x00; // NOTE: Just in case we fail out[0] = 0x00; // NOTE: Just in case we fail
#ifdef _DEBUG #ifdef _DEBUG
//size_t nWritten = //size_t nWritten =
#endif #endif
@ -107,8 +107,8 @@ wchar_t* cUTF8::allocate( const char* in ) THROW( std::bad_alloc )
#ifdef _INTEG2 // Verify Output #ifdef _INTEG2 // Verify Output
if ( nWritten == 0 ) if ( nWritten == 0 )
{ {
cDebug d( "cUTF8::allocate" ); cDebug d( "cUTF8::allocate" );
d.TraceError( "MultiByteToWideChar failed with %x\n", ::GetLastError() ); d.TraceError( "MultiByteToWideChar failed with %x\n", ::GetLastError() );
} }
ASSERT( out && TSS_IsValidString( out, nWritten ) ); ASSERT( out && TSS_IsValidString( out, nWritten ) );
@ -119,7 +119,7 @@ wchar_t* cUTF8::allocate( const char* in ) THROW( std::bad_alloc )
char* cUTF8::allocate( const wchar_t* in ) THROW( std::bad_alloc ) char* cUTF8::allocate( const wchar_t* in ) THROW( std::bad_alloc )
{ {
ASSERT( in /*&& TSS_IsValidString( in ) */); // Verify Input ASSERT( in /*&& TSS_IsValidString( in ) */); // Verify Input
// Allocate required size // Allocate required size
size_t N = ::WideCharToMultiByte( CP_UTF8, 0, in, -1,0,0,0,0 ); size_t N = ::WideCharToMultiByte( CP_UTF8, 0, in, -1,0,0,0,0 );
@ -128,7 +128,7 @@ char* cUTF8::allocate( const wchar_t* in ) THROW( std::bad_alloc )
//--Convert //--Convert
out[0] = 0x00; // NOTE: Just in case we fail out[0] = 0x00; // NOTE: Just in case we fail
#ifdef _DEBUG #ifdef _DEBUG
//size_t nWritten = //size_t nWritten =
#endif #endif
@ -138,8 +138,8 @@ char* cUTF8::allocate( const wchar_t* in ) THROW( std::bad_alloc )
#ifdef _INTEG2 // Verify Output #ifdef _INTEG2 // Verify Output
if ( nWritten == 0 ) if ( nWritten == 0 )
{ {
cDebug d( "cUTF8::allocate" ); cDebug d( "cUTF8::allocate" );
d.TraceError( "WideCharToMultiByte failed with %x\n", ::GetLastError() ); d.TraceError( "WideCharToMultiByte failed with %x\n", ::GetLastError() );
} }
ASSERT( out /*&& TSS_IsValidString( out, nWritten ) */); ASSERT( out /*&& TSS_IsValidString( out, nWritten ) */);
@ -148,5 +148,5 @@ char* cUTF8::allocate( const wchar_t* in ) THROW( std::bad_alloc )
return out; return out;
} }
#endif //_UNICODE #endif //_UNICODE

View File

@ -61,12 +61,12 @@
// function to safely convert the string to something printable // function to safely convert the string to something printable
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
#ifdef _UNICODE #ifdef _UNICODE
# define TSS_UTF8( x ) cUTF8( x ).wstr() # define TSS_UTF8( x ) cUTF8( x ).wstr()
#else #else
# define TSS_UTF8( x ) x # define TSS_UTF8( x ) x
#endif #endif
#ifdef _UNICODE // this class is only needed in unicode builds... #ifdef _UNICODE // this class is only needed in unicode builds...
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// Entities Declared in this Module // Entities Declared in this Module

View File

@ -80,7 +80,7 @@ public:
~wc16_string_impl(); // call Release() to delete ~wc16_string_impl(); // call Release() to delete
private: private:
void operator = (const wc16_string_impl& rhs) { return; } // don't call void operator = (const wc16_string_impl& rhs) { return; } // don't call
}; };
static WCHAR16 NULL_WCHAR16 = 0; static WCHAR16 NULL_WCHAR16 = 0;
@ -119,8 +119,8 @@ void wc16_string::operator = (const wc16_string& rhs)
mpData = rhs.mpData; mpData = rhs.mpData;
if( mpData ) if( mpData )
mpData->AddRef(); mpData->AddRef();
} }

View File

@ -6,39 +6,39 @@ class Integer;
template <class T> class AbstractGroup template <class T> class AbstractGroup
{ {
public: public:
typedef T Element; typedef T Element;
virtual ~AbstractGroup() {} virtual ~AbstractGroup() {}
virtual bool Equal(const Element &a, const Element &b) const =0; virtual bool Equal(const Element &a, const Element &b) const =0;
virtual Element Zero() const =0; virtual Element Zero() const =0;
virtual Element Add(const Element &a, const Element &b) const =0; virtual Element Add(const Element &a, const Element &b) const =0;
virtual Element Inverse(const Element &a) const =0; virtual Element Inverse(const Element &a) const =0;
virtual Element Double(const Element &a) const; virtual Element Double(const Element &a) const;
virtual Element Subtract(const Element &a, const Element &b) const; virtual Element Subtract(const Element &a, const Element &b) const;
virtual Element& Accumulate(Element &a, const Element &b) const; virtual Element& Accumulate(Element &a, const Element &b) const;
virtual Element& Reduce(Element &a, const Element &b) const; virtual Element& Reduce(Element &a, const Element &b) const;
virtual Element IntMultiply(const Element &a, const Integer &e) const; virtual Element IntMultiply(const Element &a, const Integer &e) const;
virtual Element CascadeIntMultiply(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const; virtual Element CascadeIntMultiply(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const;
}; };
template <class T> class AbstractRing : public AbstractGroup<T> template <class T> class AbstractRing : public AbstractGroup<T>
{ {
public: public:
typedef T Element; typedef T Element;
virtual bool IsUnit(const Element &a) const =0; virtual bool IsUnit(const Element &a) const =0;
virtual Element One() const =0; virtual Element One() const =0;
virtual Element Multiply(const Element &a, const Element &b) const =0; virtual Element Multiply(const Element &a, const Element &b) const =0;
virtual Element MultiplicativeInverse(const Element &a) const =0; virtual Element MultiplicativeInverse(const Element &a) const =0;
virtual Element Square(const Element &a) const; virtual Element Square(const Element &a) const;
virtual Element Divide(const Element &a, const Element &b) const; virtual Element Divide(const Element &a, const Element &b) const;
virtual Element Exponentiate(const Element &a, const Integer &e) const; virtual Element Exponentiate(const Element &a, const Integer &e) const;
virtual Element CascadeExponentiate(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const; virtual Element CascadeExponentiate(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const;
}; };
// ******************************************************** // ********************************************************
@ -54,19 +54,19 @@ template <class Element, class Iterator> Element GeneralCascadeExponentiation(co
template <class T> class AbstractField : public AbstractRing<T> template <class T> class AbstractField : public AbstractRing<T>
{ {
public: public:
bool IsUnit(const typename T::Element &a) const bool IsUnit(const typename T::Element &a) const
{return !this->Equal(a, this->Zero());} {return !this->Equal(a, this->Zero());}
}; };
template <class T> class AbstractEuclideanDomain : public AbstractRing<T> template <class T> class AbstractEuclideanDomain : public AbstractRing<T>
{ {
public: public:
typedef T Element; typedef T Element;
virtual void DivisionAlgorithm(Element &r, Element &q, const Element &a, const Element &d) const =0; virtual void DivisionAlgorithm(Element &r, Element &q, const Element &a, const Element &d) const =0;
virtual Element Mod(const Element &a, const Element &b) const; virtual Element Mod(const Element &a, const Element &b) const;
virtual Element Gcd(const Element &a, const Element &b) const; virtual Element Gcd(const Element &a, const Element &b) const;
}; };
// ******************************************************** // ********************************************************
@ -74,153 +74,153 @@ public:
template <class T> class MultiplicativeGroup : public AbstractGroup<typename T::Element> template <class T> class MultiplicativeGroup : public AbstractGroup<typename T::Element>
{ {
public: public:
typedef T Ring; typedef T Ring;
MultiplicativeGroup(const Ring &m_ring) MultiplicativeGroup(const Ring &m_ring)
: m_ring(m_ring) {} : m_ring(m_ring) {}
const Ring & GetRing() const const Ring & GetRing() const
{return m_ring;} {return m_ring;}
bool Equal(const typename T::Element &a, const typename T::Element &b) const bool Equal(const typename T::Element &a, const typename T::Element &b) const
{return m_ring.Equal(a, b);} {return m_ring.Equal(a, b);}
typename T::Element Zero() const typename T::Element Zero() const
{return m_ring.One();} {return m_ring.One();}
typename T::Element Add(const typename T::Element &a, const typename T::Element &b) const typename T::Element Add(const typename T::Element &a, const typename T::Element &b) const
{return m_ring.Multiply(a, b);} {return m_ring.Multiply(a, b);}
typename T::Element& Accumulate(typename T::Element &a, const typename T::Element &b) const typename T::Element& Accumulate(typename T::Element &a, const typename T::Element &b) const
{return a = m_ring.Multiply(a, b);} {return a = m_ring.Multiply(a, b);}
typename T::Element Inverse(const typename T::Element &a) const typename T::Element Inverse(const typename T::Element &a) const
{return m_ring.MultiplicativeInverse(a);} {return m_ring.MultiplicativeInverse(a);}
typename T::Element Subtract(const typename T::Element &a, const typename T::Element &b) const typename T::Element Subtract(const typename T::Element &a, const typename T::Element &b) const
{return m_ring.Divide(a, b);} {return m_ring.Divide(a, b);}
typename T::Element& Reduce(typename T::Element &a, const typename T::Element &b) const typename T::Element& Reduce(typename T::Element &a, const typename T::Element &b) const
{return a = m_ring.Divide(a, b);} {return a = m_ring.Divide(a, b);}
typename T::Element Double(const typename T::Element &a) const typename T::Element Double(const typename T::Element &a) const
{return m_ring.Square(a);} {return m_ring.Square(a);}
protected: protected:
const Ring &m_ring; const Ring &m_ring;
}; };
template <class T> class EuclideanDomainOf : public AbstractEuclideanDomain<T> template <class T> class EuclideanDomainOf : public AbstractEuclideanDomain<T>
{ {
public: public:
typedef T Element; typedef T Element;
EuclideanDomainOf() {} EuclideanDomainOf() {}
bool Equal(const Element &a, const Element &b) const bool Equal(const Element &a, const Element &b) const
{return a==b;} {return a==b;}
Element Zero() const Element Zero() const
{return Element::Zero();} {return Element::Zero();}
Element Add(const Element &a, const Element &b) const Element Add(const Element &a, const Element &b) const
{return a+b;} {return a+b;}
Element& Accumulate(Element &a, const Element &b) const Element& Accumulate(Element &a, const Element &b) const
{return a+=b;} {return a+=b;}
Element Inverse(const Element &a) const Element Inverse(const Element &a) const
{return -a;} {return -a;}
Element Subtract(const Element &a, const Element &b) const Element Subtract(const Element &a, const Element &b) const
{return a-b;} {return a-b;}
Element& Reduce(Element &a, const Element &b) const Element& Reduce(Element &a, const Element &b) const
{return a-=b;} {return a-=b;}
Element Double(const Element &a) const Element Double(const Element &a) const
{return a.Doubled();} {return a.Doubled();}
Element One() const Element One() const
{return Element::One();} {return Element::One();}
Element Multiply(const Element &a, const Element &b) const Element Multiply(const Element &a, const Element &b) const
{return a*b;} {return a*b;}
Element Square(const Element &a) const Element Square(const Element &a) const
{return a.Squared();} {return a.Squared();}
bool IsUnit(const Element &a) const bool IsUnit(const Element &a) const
{return a.IsUnit();} {return a.IsUnit();}
Element MultiplicativeInverse(const Element &a) const Element MultiplicativeInverse(const Element &a) const
{return a.MultiplicativeInverse();} {return a.MultiplicativeInverse();}
Element Divide(const Element &a, const Element &b) const Element Divide(const Element &a, const Element &b) const
{return a/b;} {return a/b;}
Element Mod(const Element &a, const Element &b) const Element Mod(const Element &a, const Element &b) const
{return a%b;} {return a%b;}
void DivisionAlgorithm(Element &r, Element &q, const Element &a, const Element &d) const void DivisionAlgorithm(Element &r, Element &q, const Element &a, const Element &d) const
{Element::Divide(r, q, a, d);} {Element::Divide(r, q, a, d);}
}; };
template <class T> class QuotientRing : public AbstractRing<typename T::Element> template <class T> class QuotientRing : public AbstractRing<typename T::Element>
{ {
public: public:
typedef T EuclideanDomain; typedef T EuclideanDomain;
QuotientRing(const EuclideanDomain &domain, const typename T::Element &modulus) QuotientRing(const EuclideanDomain &domain, const typename T::Element &modulus)
: m_domain(domain), m_modulus(modulus) {} : m_domain(domain), m_modulus(modulus) {}
const EuclideanDomain & GetDomain() const const EuclideanDomain & GetDomain() const
{return m_domain;} {return m_domain;}
const typename T::Element & GetModulus() const const typename T::Element & GetModulus() const
{return m_modulus;} {return m_modulus;}
bool Equal(const typename T::Element &a, const typename T::Element &b) const bool Equal(const typename T::Element &a, const typename T::Element &b) const
{return m_domain.Equal(m_domain.Mod(m_domain.Subtract(a, b), m_modulus), m_domain.Zero());} {return m_domain.Equal(m_domain.Mod(m_domain.Subtract(a, b), m_modulus), m_domain.Zero());}
typename T::Element Zero() const typename T::Element Zero() const
{return m_domain.Zero();} {return m_domain.Zero();}
typename T::Element Add(const typename T::Element &a, const typename T::Element &b) const typename T::Element Add(const typename T::Element &a, const typename T::Element &b) const
{return m_domain.Add(a, b);} {return m_domain.Add(a, b);}
typename T::Element& Accumulate(typename T::Element &a, const typename T::Element &b) const typename T::Element& Accumulate(typename T::Element &a, const typename T::Element &b) const
{return m_domain.Accumulate(a, b);} {return m_domain.Accumulate(a, b);}
typename T::Element Inverse(const typename T::Element &a) const typename T::Element Inverse(const typename T::Element &a) const
{return m_domain.Inverse(a);} {return m_domain.Inverse(a);}
typename T::Element Subtract(const typename T::Element &a, const typename T::Element &b) const typename T::Element Subtract(const typename T::Element &a, const typename T::Element &b) const
{return m_domain.Subtract(a, b);} {return m_domain.Subtract(a, b);}
typename T::Element& Reduce(typename T::Element &a, const typename T::Element &b) const typename T::Element& Reduce(typename T::Element &a, const typename T::Element &b) const
{return m_domain.Reduce(a, b);} {return m_domain.Reduce(a, b);}
typename T::Element Double(const typename T::Element &a) const typename T::Element Double(const typename T::Element &a) const
{return m_domain.Double(a);} {return m_domain.Double(a);}
bool IsUnit(const typename T::Element &a) const bool IsUnit(const typename T::Element &a) const
{return m_domain.IsUnit(m_domain.Gcd(a, m_modulus));} {return m_domain.IsUnit(m_domain.Gcd(a, m_modulus));}
typename T::Element One() const typename T::Element One() const
{return m_domain.One();} {return m_domain.One();}
typename T::Element Multiply(const typename T::Element &a, const typename T::Element &b) const typename T::Element Multiply(const typename T::Element &a, const typename T::Element &b) const
{return m_domain.Mod(m_domain.Multiply(a, b), m_modulus);} {return m_domain.Mod(m_domain.Multiply(a, b), m_modulus);}
typename T::Element Square(const typename T::Element &a) const typename T::Element Square(const typename T::Element &a) const
{return m_domain.Mod(m_domain.Square(a), m_modulus);} {return m_domain.Mod(m_domain.Square(a), m_modulus);}
typename QuotientRing<T>::Element MultiplicativeInverse(const typename T::Element &a) const; typename QuotientRing<T>::Element MultiplicativeInverse(const typename T::Element &a) const;
protected: protected:
const EuclideanDomain &m_domain; const EuclideanDomain &m_domain;
typename T::Element m_modulus; typename T::Element m_modulus;
}; };
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
@ -233,256 +233,256 @@ protected:
template <class T> T AbstractGroup<T>::Double(const Element &a) const template <class T> T AbstractGroup<T>::Double(const Element &a) const
{ {
return Add(a, a); return Add(a, a);
} }
template <class T> T AbstractGroup<T>::Subtract(const Element &a, const Element &b) const template <class T> T AbstractGroup<T>::Subtract(const Element &a, const Element &b) const
{ {
return Add(a, Inverse(b)); return Add(a, Inverse(b));
} }
template <class T> T& AbstractGroup<T>::Accumulate(Element &a, const Element &b) const template <class T> T& AbstractGroup<T>::Accumulate(Element &a, const Element &b) const
{ {
return a = Add(a, b); return a = Add(a, b);
} }
template <class T> T& AbstractGroup<T>::Reduce(Element &a, const Element &b) const template <class T> T& AbstractGroup<T>::Reduce(Element &a, const Element &b) const
{ {
return a = Subtract(a, b); return a = Subtract(a, b);
} }
template <class T> T AbstractRing<T>::Square(const Element &a) const template <class T> T AbstractRing<T>::Square(const Element &a) const
{ {
return Multiply(a, a); return Multiply(a, a);
} }
template <class T> T AbstractRing<T>::Divide(const Element &a, const Element &b) const template <class T> T AbstractRing<T>::Divide(const Element &a, const Element &b) const
{ {
return Multiply(a, MultiplicativeInverse(b)); return Multiply(a, MultiplicativeInverse(b));
} }
template <class T> T AbstractEuclideanDomain<T>::Mod(const Element &a, const Element &b) const template <class T> T AbstractEuclideanDomain<T>::Mod(const Element &a, const Element &b) const
{ {
Element r, q; Element r, q;
DivisionAlgorithm(r, q, a, b); DivisionAlgorithm(r, q, a, b);
return r; return r;
} }
template <class T> T AbstractEuclideanDomain<T>::Gcd(const Element &a, const Element &b) const template <class T> T AbstractEuclideanDomain<T>::Gcd(const Element &a, const Element &b) const
{ {
Element g[3]={b, a}; Element g[3]={b, a};
unsigned int i0=0, i1=1, i2=2; unsigned int i0=0, i1=1, i2=2;
while (!this->Equal(g[i1], this->Zero())) while (!this->Equal(g[i1], this->Zero()))
{ {
g[i2] = Mod(g[i0], g[i1]); g[i2] = Mod(g[i0], g[i1]);
unsigned int t = i0; i0 = i1; i1 = i2; i2 = t; unsigned int t = i0; i0 = i1; i1 = i2; i2 = t;
} }
return g[i0]; return g[i0];
} }
template <class T> typename QuotientRing<T>::Element QuotientRing<T>::MultiplicativeInverse(const typename T::Element &a) const template <class T> typename QuotientRing<T>::Element QuotientRing<T>::MultiplicativeInverse(const typename T::Element &a) const
{ {
typename T::Element g[3]={m_modulus, a}; typename T::Element g[3]={m_modulus, a};
typename T::Element v[3]={m_domain.Zero(), m_domain.One()}; typename T::Element v[3]={m_domain.Zero(), m_domain.One()};
typename T::Element y; typename T::Element y;
unsigned int i0=0, i1=1, i2=2; unsigned int i0=0, i1=1, i2=2;
while (!this->Equal(g[i1], Zero())) while (!this->Equal(g[i1], Zero()))
{ {
// y = g[i0] / g[i1]; // y = g[i0] / g[i1];
// g[i2] = g[i0] % g[i1]; // g[i2] = g[i0] % g[i1];
m_domain.DivisionAlgorithm(g[i2], y, g[i0], g[i1]); m_domain.DivisionAlgorithm(g[i2], y, g[i0], g[i1]);
// v[i2] = v[i0] - (v[i1] * y); // v[i2] = v[i0] - (v[i1] * y);
v[i2] = m_domain.Subtract(v[i0], m_domain.Multiply(v[i1], y)); v[i2] = m_domain.Subtract(v[i0], m_domain.Multiply(v[i1], y));
unsigned int t = i0; i0 = i1; i1 = i2; i2 = t; unsigned int t = i0; i0 = i1; i1 = i2; i2 = t;
} }
return m_domain.IsUnit(g[i0]) ? m_domain.Divide(v[i0], g[i0]) : m_domain.Zero(); return m_domain.IsUnit(g[i0]) ? m_domain.Divide(v[i0], g[i0]) : m_domain.Zero();
} }
template <class T> T AbstractGroup<T>::IntMultiply(const Element &base, const Integer &exponent) const template <class T> T AbstractGroup<T>::IntMultiply(const Element &base, const Integer &exponent) const
{ {
unsigned int expLen = exponent.BitCount(); unsigned int expLen = exponent.BitCount();
if (expLen==0) if (expLen==0)
return Zero(); return Zero();
unsigned powerTableSize = (expLen <= 17 ? 1 : (expLen <= 24 ? 2 : (expLen <= 70 ? 4 : (expLen <= 197 ? 8 : (expLen <= 539 ? 16 : (expLen <= 1434 ? 32 : 64)))))); unsigned powerTableSize = (expLen <= 17 ? 1 : (expLen <= 24 ? 2 : (expLen <= 70 ? 4 : (expLen <= 197 ? 8 : (expLen <= 539 ? 16 : (expLen <= 1434 ? 32 : 64))))));
std::vector<Element> powerTable(powerTableSize); std::vector<Element> powerTable(powerTableSize);
powerTable[0] = base; powerTable[0] = base;
if (powerTableSize > 1) if (powerTableSize > 1)
{ {
Element temp = Double(base); Element temp = Double(base);
for (unsigned i=1; i<powerTableSize; i++) for (unsigned i=1; i<powerTableSize; i++)
powerTable[i] = Add(temp, powerTable[i-1]); powerTable[i] = Add(temp, powerTable[i-1]);
} }
Element result; Element result;
unsigned power = 0, prevPosition = expLen-1; unsigned power = 0, prevPosition = expLen-1;
bool firstTime = true; bool firstTime = true;
for (int i = expLen-1; i>=0; i--) for (int i = expLen-1; i>=0; i--)
{ {
power = 2*power + exponent.GetBit(i); power = 2*power + exponent.GetBit(i);
if (i==0 || power >= powerTableSize) if (i==0 || power >= powerTableSize)
{ {
unsigned squaresBefore = prevPosition-i; unsigned squaresBefore = prevPosition-i;
unsigned squaresAfter = 0; unsigned squaresAfter = 0;
prevPosition = i; prevPosition = i;
while (power && power%2 == 0) while (power && power%2 == 0)
{ {
power /= 2; power /= 2;
squaresBefore--; squaresBefore--;
squaresAfter++; squaresAfter++;
} }
if (firstTime) if (firstTime)
{ {
result = powerTable[(power-1)/2]; result = powerTable[(power-1)/2];
firstTime = false; firstTime = false;
} }
else else
{ {
while (squaresBefore--) while (squaresBefore--)
result = Double(result); result = Double(result);
if (power) if (power)
result = Add(powerTable[(power-1)/2], result); result = Add(powerTable[(power-1)/2], result);
} }
while (squaresAfter--) while (squaresAfter--)
result = Double(result); result = Double(result);
power = 0; power = 0;
} }
} }
return result; return result;
} }
template <class T> T AbstractGroup<T>::CascadeIntMultiply(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const template <class T> T AbstractGroup<T>::CascadeIntMultiply(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const
{ {
const unsigned expLen = STDMAX(e1.BitCount(), e2.BitCount()); const unsigned expLen = STDMAX(e1.BitCount(), e2.BitCount());
if (expLen==0) if (expLen==0)
return Zero(); return Zero();
const unsigned w = (expLen <= 46 ? 1 : (expLen <= 260 ? 2 : 3)); const unsigned w = (expLen <= 46 ? 1 : (expLen <= 260 ? 2 : 3));
const unsigned tableSize = 1<<w; const unsigned tableSize = 1<<w;
std::vector<Element> powerTable(tableSize << w); std::vector<Element> powerTable(tableSize << w);
powerTable[1] = x; powerTable[1] = x;
powerTable[tableSize] = y; powerTable[tableSize] = y;
if (w==1) if (w==1)
powerTable[3] = Add(x,y); powerTable[3] = Add(x,y);
else else
{ {
powerTable[2] = Double(x); powerTable[2] = Double(x);
powerTable[2*tableSize] = Double(y); powerTable[2*tableSize] = Double(y);
unsigned i, j; unsigned i, j;
for (i=3; i<tableSize; i+=2) for (i=3; i<tableSize; i+=2)
powerTable[i] = Add(powerTable[i-2], powerTable[2]); powerTable[i] = Add(powerTable[i-2], powerTable[2]);
for (i=1; i<tableSize; i+=2) for (i=1; i<tableSize; i+=2)
for (j=i+tableSize; j<(tableSize<<w); j+=tableSize) for (j=i+tableSize; j<(tableSize<<w); j+=tableSize)
powerTable[j] = Add(powerTable[j-tableSize], y); powerTable[j] = Add(powerTable[j-tableSize], y);
for (i=3*tableSize; i<(tableSize<<w); i+=2*tableSize) for (i=3*tableSize; i<(tableSize<<w); i+=2*tableSize)
powerTable[i] = Add(powerTable[i-2*tableSize], powerTable[2*tableSize]); powerTable[i] = Add(powerTable[i-2*tableSize], powerTable[2*tableSize]);
for (i=tableSize; i<(tableSize<<w); i+=2*tableSize) for (i=tableSize; i<(tableSize<<w); i+=2*tableSize)
for (j=i+2; j<i+tableSize; j+=2) for (j=i+2; j<i+tableSize; j+=2)
powerTable[j] = Add(powerTable[j-1], x); powerTable[j] = Add(powerTable[j-1], x);
} }
Element result; Element result;
unsigned power1 = 0, power2 = 0, prevPosition = expLen-1; unsigned power1 = 0, power2 = 0, prevPosition = expLen-1;
bool firstTime = true; bool firstTime = true;
for (int i = expLen-1; i>=0; i--) for (int i = expLen-1; i>=0; i--)
{ {
power1 = 2*power1 + e1.GetBit(i); power1 = 2*power1 + e1.GetBit(i);
power2 = 2*power2 + e2.GetBit(i); power2 = 2*power2 + e2.GetBit(i);
if (i==0 || 2*power1 >= tableSize || 2*power2 >= tableSize) if (i==0 || 2*power1 >= tableSize || 2*power2 >= tableSize)
{ {
unsigned squaresBefore = prevPosition-i; unsigned squaresBefore = prevPosition-i;
unsigned squaresAfter = 0; unsigned squaresAfter = 0;
prevPosition = i; prevPosition = i;
while ((power1 || power2) && power1%2 == 0 && power2%2==0) while ((power1 || power2) && power1%2 == 0 && power2%2==0)
{ {
power1 /= 2; power1 /= 2;
power2 /= 2; power2 /= 2;
squaresBefore--; squaresBefore--;
squaresAfter++; squaresAfter++;
} }
if (firstTime) if (firstTime)
{ {
result = powerTable[(power2<<w) + power1]; result = powerTable[(power2<<w) + power1];
firstTime = false; firstTime = false;
} }
else else
{ {
while (squaresBefore--) while (squaresBefore--)
result = Double(result); result = Double(result);
if (power1 || power2) if (power1 || power2)
result = Add(powerTable[(power2<<w) + power1], result); result = Add(powerTable[(power2<<w) + power1], result);
} }
while (squaresAfter--) while (squaresAfter--)
result = Double(result); result = Double(result);
power1 = power2 = 0; power1 = power2 = 0;
} }
} }
return result; return result;
} }
template <class Element, class Iterator> Element GeneralCascadeMultiplication(const AbstractGroup<Element> &group, Iterator begin, Iterator end) template <class Element, class Iterator> Element GeneralCascadeMultiplication(const AbstractGroup<Element> &group, Iterator begin, Iterator end)
{ {
if (end-begin == 1) if (end-begin == 1)
return group.IntMultiply((*begin).second, (*begin).first); return group.IntMultiply((*begin).second, (*begin).first);
else if (end-begin == 2) else if (end-begin == 2)
return group.CascadeIntMultiply((*begin).second, (*begin).first, (*(begin+1)).second, (*(begin+1)).first); return group.CascadeIntMultiply((*begin).second, (*begin).first, (*(begin+1)).second, (*(begin+1)).first);
else else
{ {
Integer q, r; Integer q, r;
Iterator last = end; Iterator last = end;
--last; --last;
make_heap(begin, end); make_heap(begin, end);
pop_heap(begin, end); pop_heap(begin, end);
while (!!(*begin).first) while (!!(*begin).first)
{ {
// (*last).first is largest exponent, (*begin).first is next largest // (*last).first is largest exponent, (*begin).first is next largest
Integer::Divide(r, q, (*last).first, (*begin).first); Integer::Divide(r, q, (*last).first, (*begin).first);
if (q == Integer::One()) if (q == Integer::One())
group.Accumulate((*begin).second, (*last).second); // avoid overhead of GeneralizedMultiplication() group.Accumulate((*begin).second, (*last).second); // avoid overhead of GeneralizedMultiplication()
else else
group.Accumulate((*begin).second, group.IntMultiply((*last).second, q)); group.Accumulate((*begin).second, group.IntMultiply((*last).second, q));
(*last).first = r; (*last).first = r;
push_heap(begin, end); push_heap(begin, end);
pop_heap(begin, end); pop_heap(begin, end);
} }
return group.IntMultiply((*last).second, (*last).first); return group.IntMultiply((*last).second, (*last).first);
} }
} }
template <class T> T AbstractRing<T>::Exponentiate(const Element &base, const Integer &exponent) const template <class T> T AbstractRing<T>::Exponentiate(const Element &base, const Integer &exponent) const
{ {
return MultiplicativeGroup<AbstractRing<T> >(*this).IntMultiply(base, exponent); return MultiplicativeGroup<AbstractRing<T> >(*this).IntMultiply(base, exponent);
} }
template <class T> T AbstractRing<T>::CascadeExponentiate(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const template <class T> T AbstractRing<T>::CascadeExponentiate(const Element &x, const Integer &e1, const Element &y, const Integer &e2) const
{ {
return MultiplicativeGroup<AbstractRing<T> >(*this).CascadeIntMultiply(x, e1, y, e2); return MultiplicativeGroup<AbstractRing<T> >(*this).CascadeIntMultiply(x, e1, y, e2);
} }
#if defined(BREAK_GCC34) #if defined(BREAK_GCC34)
template <class Element, class Iterator> Element GeneralCascadeExponentiation(const AbstractRing<Element> &ring, Iterator begin, Iterator end) template <class Element, class Iterator> Element GeneralCascadeExponentiation(const AbstractRing<Element> &ring, Iterator begin, Iterator end)
{ {
MultiplicativeGroup<AbstractRing<Element> > mg(field); MultiplicativeGroup<AbstractRing<Element> > mg(field);
return GeneralCascadeMultiplication<Element>(mg, begin, end); return GeneralCascadeMultiplication<Element>(mg, begin, end);
} }
#endif /* BREAK_GCC34 */ #endif /* BREAK_GCC34 */

View File

@ -6,100 +6,100 @@
unsigned int DERLengthEncode(unsigned int length, byte *output) unsigned int DERLengthEncode(unsigned int length, byte *output)
{ {
unsigned int i=0; unsigned int i=0;
if (length <= 0x7f) if (length <= 0x7f)
{ {
output[i++] = byte(length); output[i++] = byte(length);
} }
else else
{ {
output[i++] = byte(BytePrecision(length) | 0x80); output[i++] = byte(BytePrecision(length) | 0x80);
for (int j=BytePrecision(length); j; --j) for (int j=BytePrecision(length); j; --j)
{ {
output[i++] = byte (length >> (j-1)*8); output[i++] = byte (length >> (j-1)*8);
} }
} }
return i; return i;
} }
unsigned int DERLengthEncode(unsigned int length, BufferedTransformation &bt) unsigned int DERLengthEncode(unsigned int length, BufferedTransformation &bt)
{ {
byte buf[10]; // should be more than enough byte buf[10]; // should be more than enough
unsigned int i = DERLengthEncode(length, buf); unsigned int i = DERLengthEncode(length, buf);
assert(i <= 10); assert(i <= 10);
bt.Put(buf, i); bt.Put(buf, i);
return i; return i;
} }
bool BERLengthDecode(BufferedTransformation &bt, unsigned int &length) bool BERLengthDecode(BufferedTransformation &bt, unsigned int &length)
{ {
byte b; byte b;
if (!bt.Get(b)) if (!bt.Get(b))
BERDecodeError(); BERDecodeError();
if (!(b & 0x80)) if (!(b & 0x80))
length = b; length = b;
else else
{ {
unsigned int lengthBytes = b & 0x7f; unsigned int lengthBytes = b & 0x7f;
if (bt.MaxRetrieveable() < lengthBytes) if (bt.MaxRetrieveable() < lengthBytes)
BERDecodeError(); BERDecodeError();
bt.Get(b); bt.Get(b);
while (!b && lengthBytes>1) while (!b && lengthBytes>1)
{ {
bt.Get(b); bt.Get(b);
lengthBytes--; lengthBytes--;
} }
switch (lengthBytes) switch (lengthBytes)
{ {
case 0: case 0:
return false; // indefinite length return false; // indefinite length
case 1: case 1:
length = b; length = b;
break; break;
case 2: case 2:
length = b << 8; length = b << 8;
length |= (bt.Get(b), b); length |= (bt.Get(b), b);
break; break;
default: default:
BERDecodeError(); BERDecodeError();
} }
} }
return true; return true;
} }
BERSequenceDecoder::BERSequenceDecoder(BufferedTransformation &inQueue) BERSequenceDecoder::BERSequenceDecoder(BufferedTransformation &inQueue)
: inQueue(inQueue) : inQueue(inQueue)
{ {
byte b; byte b;
if (!inQueue.Get(b) || b != (SEQUENCE | CONSTRUCTED)) if (!inQueue.Get(b) || b != (SEQUENCE | CONSTRUCTED))
BERDecodeError(); BERDecodeError();
definiteLength = BERLengthDecode(inQueue, length); definiteLength = BERLengthDecode(inQueue, length);
} }
BERSequenceDecoder::~BERSequenceDecoder() BERSequenceDecoder::~BERSequenceDecoder()
{ {
if (!definiteLength) if (!definiteLength)
{ // remove end-of-content octects { // remove end-of-content octects
word16 i; word16 i;
if (!inQueue.GetShort(i) || (i!=0)) if (!inQueue.GetShort(i) || (i!=0))
BERDecodeError(); BERDecodeError();
} }
} }
DERSequenceEncoder::DERSequenceEncoder(BufferedTransformation &outQueue) DERSequenceEncoder::DERSequenceEncoder(BufferedTransformation &outQueue)
: outQueue(outQueue) : outQueue(outQueue)
{ {
} }
DERSequenceEncoder::~DERSequenceEncoder() DERSequenceEncoder::~DERSequenceEncoder()
{ {
unsigned int length = (unsigned int)CurrentSize(); unsigned int length = (unsigned int)CurrentSize();
outQueue.Put(SEQUENCE | CONSTRUCTED); outQueue.Put(SEQUENCE | CONSTRUCTED);
DERLengthEncode(length, outQueue); DERLengthEncode(length, outQueue);
TransferTo(outQueue); TransferTo(outQueue);
} }

View File

@ -24,34 +24,34 @@ bool BERLengthDecode(BufferedTransformation &, unsigned int &);
class BERSequenceDecoder : public BufferedTransformation class BERSequenceDecoder : public BufferedTransformation
{ {
public: public:
BERSequenceDecoder(BufferedTransformation &inQueue); BERSequenceDecoder(BufferedTransformation &inQueue);
~BERSequenceDecoder(); ~BERSequenceDecoder();
void Put(byte) {} void Put(byte) {}
void Put(const byte *, unsigned int) {} void Put(const byte *, unsigned int) {}
unsigned long MaxRetrieveable() unsigned long MaxRetrieveable()
{return inQueue.MaxRetrieveable();} {return inQueue.MaxRetrieveable();}
unsigned int Get(byte &outByte) unsigned int Get(byte &outByte)
{return inQueue.Get(outByte);} {return inQueue.Get(outByte);}
unsigned int Get(byte *outString, unsigned int getMax) unsigned int Get(byte *outString, unsigned int getMax)
{return inQueue.Get(outString, getMax);} {return inQueue.Get(outString, getMax);}
unsigned int Peek(byte &outByte) const unsigned int Peek(byte &outByte) const
{return inQueue.Peek(outByte);} {return inQueue.Peek(outByte);}
private: private:
BufferedTransformation &inQueue; BufferedTransformation &inQueue;
bool definiteLength; bool definiteLength;
unsigned int length; unsigned int length;
}; };
class DERSequenceEncoder : public ByteQueue class DERSequenceEncoder : public ByteQueue
{ {
public: public:
DERSequenceEncoder(BufferedTransformation &outQueue); DERSequenceEncoder(BufferedTransformation &outQueue);
~DERSequenceEncoder(); ~DERSequenceEncoder();
private: private:
BufferedTransformation &outQueue; BufferedTransformation &outQueue;
}; };
#endif #endif

View File

@ -105,31 +105,31 @@ typedef unsigned __int64 word64;
#elif defined(_KCC) #elif defined(_KCC)
#if defined(_ALPHA) #if defined(_ALPHA)
typedef unsigned int word; typedef unsigned int word;
typedef unsigned long dword; typedef unsigned long dword;
#define WORD64_AVAILABLE #define WORD64_AVAILABLE
typedef unsigned long word64; typedef unsigned long word64;
#define W64LIT(x) x##LL #define W64LIT(x) x##LL
#elif defined(_IRIX) #elif defined(_IRIX)
typedef unsigned long word; typedef unsigned long word;
typedef unsigned long long dword; typedef unsigned long long dword;
#define WORD64_AVAILABLE #define WORD64_AVAILABLE
typedef unsigned long long word64; typedef unsigned long long word64;
#define W64LIT(x) x##LL #define W64LIT(x) x##LL
#else #else
typedef unsigned long word; typedef unsigned long word;
typedef unsigned long long dword; typedef unsigned long long dword;
#define WORD64_AVAILABLE #define WORD64_AVAILABLE
typedef unsigned long long word64; typedef unsigned long long word64;
#define W64LIT(x) x##LL #define W64LIT(x) x##LL
#endif #endif
#elif defined(_SUNPRO) #elif defined(_SUNPRO)

View File

@ -6,39 +6,39 @@
unsigned int RandomNumberGenerator::GetBit() unsigned int RandomNumberGenerator::GetBit()
{ {
return Parity(GetByte()); return Parity(GetByte());
} }
void RandomNumberGenerator::GetBlock(byte *output, unsigned int size) void RandomNumberGenerator::GetBlock(byte *output, unsigned int size)
{ {
while (size--) while (size--)
*output++ = GetByte(); *output++ = GetByte();
} }
word32 RandomNumberGenerator::GetLong(word32 min, word32 max) word32 RandomNumberGenerator::GetLong(word32 min, word32 max)
{ {
word32 range = max-min; word32 range = max-min;
const int maxBytes = BytePrecision(range); const int maxBytes = BytePrecision(range);
const int maxBits = BitPrecision(range); const int maxBits = BitPrecision(range);
word32 value; word32 value;
do do
{ {
value = 0; value = 0;
for (int i=0; i<maxBytes; i++) for (int i=0; i<maxBytes; i++)
value = (value << 8) | GetByte(); value = (value << 8) | GetByte();
value = Crop(value, maxBits); value = Crop(value, maxBits);
} while (value > range); } while (value > range);
return value+min; return value+min;
} }
void StreamCipher::ProcessString(byte *outString, const byte *inString, unsigned int length) void StreamCipher::ProcessString(byte *outString, const byte *inString, unsigned int length)
{ {
while(length--) while(length--)
*outString++ = ProcessByte(*inString++); *outString++ = ProcessByte(*inString++);
} }
void StreamCipher::ProcessString(byte *inoutString, unsigned int length) void StreamCipher::ProcessString(byte *inoutString, unsigned int length)
@ -49,131 +49,131 @@ void StreamCipher::ProcessString(byte *inoutString, unsigned int length)
bool MessageAuthenticationCode::Verify(const byte *macIn) bool MessageAuthenticationCode::Verify(const byte *macIn)
{ {
SecByteBlock mac(DigestSize()); SecByteBlock mac(DigestSize());
Final(mac); Final(mac);
return memcmp(mac, macIn, DigestSize()) == 0; return memcmp(mac, macIn, DigestSize()) == 0;
} }
void BufferedTransformation::TransferTo(BufferedTransformation &target) void BufferedTransformation::TransferTo(BufferedTransformation &target)
{ {
SecByteBlock buf(256); SecByteBlock buf(256);
unsigned int l; unsigned int l;
while ((l=Get(buf, 256)) != 0) while ((l=Get(buf, 256)) != 0)
target.Put(buf, l); target.Put(buf, l);
} }
unsigned int BufferedTransformation::TransferTo(BufferedTransformation &target, unsigned int size) unsigned int BufferedTransformation::TransferTo(BufferedTransformation &target, unsigned int size)
{ {
SecByteBlock buf(256); SecByteBlock buf(256);
unsigned int l, total = 0; unsigned int l, total = 0;
while (size && (l=Get(buf, STDMIN(size, 256U)))) while (size && (l=Get(buf, STDMIN(size, 256U))))
{ {
target.Put(buf, l); target.Put(buf, l);
size -= l; size -= l;
total += l; total += l;
} }
return total; return total;
} }
void BufferedTransformation::PutShort(word16 value, bool highFirst) void BufferedTransformation::PutShort(word16 value, bool highFirst)
{ {
if (highFirst) if (highFirst)
{ {
Put(value>>8); Put(value>>8);
Put(byte(value)); Put(byte(value));
} }
else else
{ {
Put(byte(value)); Put(byte(value));
Put(value>>8); Put(value>>8);
} }
} }
void BufferedTransformation::PutLong(word32 value, bool highFirst) void BufferedTransformation::PutLong(word32 value, bool highFirst)
{ {
if (highFirst) if (highFirst)
{ {
for (int i=0; i<4; i++) for (int i=0; i<4; i++)
Put(byte(value>>((3-i)*8))); Put(byte(value>>((3-i)*8)));
} }
else else
{ {
for (int i=0; i<4; i++) for (int i=0; i<4; i++)
Put(byte(value>>(i*8))); Put(byte(value>>(i*8)));
} }
} }
int BufferedTransformation::GetShort(word16 &value, bool highFirst) int BufferedTransformation::GetShort(word16 &value, bool highFirst)
{ {
if (MaxRetrieveable()<2) if (MaxRetrieveable()<2)
return 0; return 0;
byte buf[2]; byte buf[2];
Get(buf, 2); Get(buf, 2);
if (highFirst) if (highFirst)
value = (buf[0] << 8) | buf[1]; value = (buf[0] << 8) | buf[1];
else else
value = (buf[1] << 8) | buf[0]; value = (buf[1] << 8) | buf[0];
return 2; return 2;
} }
int BufferedTransformation::GetLong(word32 &value, bool highFirst) int BufferedTransformation::GetLong(word32 &value, bool highFirst)
{ {
if (MaxRetrieveable()<4) if (MaxRetrieveable()<4)
return 0; return 0;
byte buf[4]; byte buf[4];
Get(buf, 4); Get(buf, 4);
if (highFirst) if (highFirst)
value = (buf[0] << 24) | (buf[1] << 16) | (buf[2] << 8) | buf [3]; value = (buf[0] << 24) | (buf[1] << 16) | (buf[2] << 8) | buf [3];
else else
value = (buf[3] << 24) | (buf[2] << 16) | (buf[1] << 8) | buf [0]; value = (buf[3] << 24) | (buf[2] << 16) | (buf[1] << 8) | buf [0];
return 4; return 4;
} }
unsigned int BufferedTransformation::Skip(unsigned int skipMax) unsigned int BufferedTransformation::Skip(unsigned int skipMax)
{ {
byte b; byte b;
unsigned int skipActual=0; unsigned int skipActual=0;
while (skipMax-- && Get(b)) while (skipMax-- && Get(b))
skipActual++; skipActual++;
return skipActual; return skipActual;
} }
unsigned int PK_FixedLengthCryptoSystem::MaxPlainTextLength(unsigned int cipherTextLength) const unsigned int PK_FixedLengthCryptoSystem::MaxPlainTextLength(unsigned int cipherTextLength) const
{ {
if (cipherTextLength == CipherTextLength()) if (cipherTextLength == CipherTextLength())
return MaxPlainTextLength(); return MaxPlainTextLength();
else else
return 0; return 0;
} }
unsigned int PK_FixedLengthCryptoSystem::CipherTextLength(unsigned int plainTextLength) const unsigned int PK_FixedLengthCryptoSystem::CipherTextLength(unsigned int plainTextLength) const
{ {
if (plainTextLength <= MaxPlainTextLength()) if (plainTextLength <= MaxPlainTextLength())
return CipherTextLength(); return CipherTextLength();
else else
return 0; return 0;
} }
unsigned int PK_FixedLengthDecryptor::Decrypt(const byte *cipherText, unsigned int cipherTextLength, byte *plainText) unsigned int PK_FixedLengthDecryptor::Decrypt(const byte *cipherText, unsigned int cipherTextLength, byte *plainText)
{ {
if (cipherTextLength != CipherTextLength()) if (cipherTextLength != CipherTextLength())
return 0; return 0;
return Decrypt(cipherText, plainText); return Decrypt(cipherText, plainText);
} }
bool PK_VerifierWithRecovery::Verify(const byte *message, unsigned int messageLength, const byte *signature) bool PK_VerifierWithRecovery::Verify(const byte *message, unsigned int messageLength, const byte *signature)
{ {
SecByteBlock recovered(MaxMessageLength()); SecByteBlock recovered(MaxMessageLength());
unsigned int rLen = Recover(signature, recovered); unsigned int rLen = Recover(signature, recovered);
return (rLen==messageLength && memcmp(recovered, message, rLen)==0); return (rLen==messageLength && memcmp(recovered, message, rLen)==0);
} }

View File

@ -14,53 +14,53 @@
class CryptlibException : public std::exception class CryptlibException : public std::exception
{ {
public: public:
explicit CryptlibException(const std::string& s) : m_what(s) {} explicit CryptlibException(const std::string& s) : m_what(s) {}
virtual ~CryptlibException() throw() {} virtual ~CryptlibException() throw() {}
const char *what() const throw() {return (m_what.c_str());} const char *what() const throw() {return (m_what.c_str());}
private: private:
std::string m_what; std::string m_what;
}; };
/// used to specify a direction for a cipher to operate in (encrypt or decrypt) /// used to specify a direction for a cipher to operate in (encrypt or decrypt)
enum CipherDir { enum CipherDir {
/// ///
ENCRYPTION, ENCRYPTION,
/// ///
DECRYPTION}; DECRYPTION};
/// abstract base class for block ciphers /// abstract base class for block ciphers
/** A particular derived class may change state as blocks are processed, /** A particular derived class may change state as blocks are processed,
so the ProcessBlock() functions are not specified to be const. so the ProcessBlock() functions are not specified to be const.
However, most classes derived from BlockTransformation are block ciphers However, most classes derived from BlockTransformation are block ciphers
in ECB mode (for example the DESEncryption class), which are stateless. in ECB mode (for example the DESEncryption class), which are stateless.
These classes should not be used directly, but only in combination with These classes should not be used directly, but only in combination with
a mode class (see \Ref{Mode}). However, if you know what you are doing, and a mode class (see \Ref{Mode}). However, if you know what you are doing, and
need to call ProcessBlock() on a const ECB cipher object, you can safely need to call ProcessBlock() on a const ECB cipher object, you can safely
cast away its constness. cast away its constness.
Note: BlockTransformation objects may assume that pointers to input and Note: BlockTransformation objects may assume that pointers to input and
output blocks are aligned on 32-bit word boundaries. output blocks are aligned on 32-bit word boundaries.
*/ */
class BlockTransformation class BlockTransformation
{ {
public: public:
/// ///
virtual ~BlockTransformation() {} virtual ~BlockTransformation() {}
/// encrypt or decrypt one block in place /// encrypt or decrypt one block in place
//* Precondition: size of inoutBlock == BlockSize(). //* Precondition: size of inoutBlock == BlockSize().
virtual void ProcessBlock(byte *inoutBlock) =0; virtual void ProcessBlock(byte *inoutBlock) =0;
/// encrypt or decrypt one block, may assume inBlock != outBlock /// encrypt or decrypt one block, may assume inBlock != outBlock
//* Precondition: size of inBlock and outBlock == BlockSize(). //* Precondition: size of inBlock and outBlock == BlockSize().
virtual void ProcessBlock(const byte *inBlock, byte *outBlock) =0; virtual void ProcessBlock(const byte *inBlock, byte *outBlock) =0;
/// block size of the cipher in bytes /// block size of the cipher in bytes
virtual unsigned int BlockSize() const =0; virtual unsigned int BlockSize() const =0;
}; };
@ -69,275 +69,275 @@ public:
class StreamCipher class StreamCipher
{ {
public: public:
/// ///
virtual ~StreamCipher() {} virtual ~StreamCipher() {}
/// encrypt or decrypt one byte /// encrypt or decrypt one byte
virtual byte ProcessByte(byte input) =0; virtual byte ProcessByte(byte input) =0;
/// encrypt or decrypt an array of bytes of specified length in place /// encrypt or decrypt an array of bytes of specified length in place
virtual void ProcessString(byte *inoutString, unsigned int length); virtual void ProcessString(byte *inoutString, unsigned int length);
/// encrypt or decrypt an array of bytes of specified length, may assume inString != outString /// encrypt or decrypt an array of bytes of specified length, may assume inString != outString
virtual void ProcessString(byte *outString, const byte *inString, unsigned int length); virtual void ProcessString(byte *outString, const byte *inString, unsigned int length);
}; };
/// abstract base class for random access stream ciphers /// abstract base class for random access stream ciphers
class RandomAccessStreamCipher : public virtual StreamCipher class RandomAccessStreamCipher : public virtual StreamCipher
{ {
public: public:
/// ///
virtual ~RandomAccessStreamCipher() {} virtual ~RandomAccessStreamCipher() {}
/*/ specify that the next byte to be processed is at absolute position n /*/ specify that the next byte to be processed is at absolute position n
in the plaintext/ciphertext stream */ in the plaintext/ciphertext stream */
virtual void Seek(unsigned long n) =0; virtual void Seek(unsigned long n) =0;
}; };
/// abstract base class for random number generators /// abstract base class for random number generators
/** All return values are uniformly distributed over the range specified. /** All return values are uniformly distributed over the range specified.
*/ */
class RandomNumberGenerator class RandomNumberGenerator
{ {
public: public:
/// ///
virtual ~RandomNumberGenerator() {} virtual ~RandomNumberGenerator() {}
/// generate new random byte and return it /// generate new random byte and return it
virtual byte GetByte() =0; virtual byte GetByte() =0;
/// generate new random bit and return it /// generate new random bit and return it
/** Default implementation is to call GetByte() and return its parity. */ /** Default implementation is to call GetByte() and return its parity. */
virtual unsigned int GetBit(); virtual unsigned int GetBit();
/// generate a random 32 bit word in the range min to max, inclusive /// generate a random 32 bit word in the range min to max, inclusive
virtual word32 GetLong(word32 a=0, word32 b=0xffffffffL); virtual word32 GetLong(word32 a=0, word32 b=0xffffffffL);
/// generate a random 16 bit word in the range min to max, inclusive /// generate a random 16 bit word in the range min to max, inclusive
virtual word16 GetShort(word16 a=0, word16 b=0xffff) virtual word16 GetShort(word16 a=0, word16 b=0xffff)
{return (word16)GetLong(a, b);} {return (word16)GetLong(a, b);}
/// generate random array of bytes /// generate random array of bytes
//* Default implementation is to call GetByte size times. //* Default implementation is to call GetByte size times.
virtual void GetBlock(byte *output, unsigned int size); virtual void GetBlock(byte *output, unsigned int size);
}; };
/// randomly shuffle the specified array, resulting permutation is uniformly distributed /// randomly shuffle the specified array, resulting permutation is uniformly distributed
template <class T> void Shuffle(RandomNumberGenerator &rng, T *array, unsigned int size) template <class T> void Shuffle(RandomNumberGenerator &rng, T *array, unsigned int size)
{ {
while (--size) while (--size)
swap(array[size], array[(unsigned int)rng.GetLong(0, size)]); swap(array[size], array[(unsigned int)rng.GetLong(0, size)]);
} }
/// abstract base class for hash functions /// abstract base class for hash functions
/** HashModule objects are stateful. They are created in an initial state, /** HashModule objects are stateful. They are created in an initial state,
change state as Update() is called, and return to the initial change state as Update() is called, and return to the initial
state when Final() is called. This interface allows a large message to state when Final() is called. This interface allows a large message to
be hashed in pieces by calling Update() on each piece followed by be hashed in pieces by calling Update() on each piece followed by
calling Final(). calling Final().
*/ */
class HashModule class HashModule
{ {
public: public:
/// ///
virtual ~HashModule() {} virtual ~HashModule() {}
/// process more input /// process more input
virtual void Update(const byte *input, unsigned int length) =0; virtual void Update(const byte *input, unsigned int length) =0;
/*/ calculate hash for the current message (the concatenation of all /*/ calculate hash for the current message (the concatenation of all
inputs passed in via Update()), then reinitialize the object */ inputs passed in via Update()), then reinitialize the object */
//* Precondition: size of digest == DigestSize(). //* Precondition: size of digest == DigestSize().
virtual void Final(byte *digest) =0; virtual void Final(byte *digest) =0;
/// size of the hash returned by Final() /// size of the hash returned by Final()
virtual unsigned int DigestSize() const =0; virtual unsigned int DigestSize() const =0;
/// use this if your input is short and you don't want to call Update() and Final() seperately /// use this if your input is short and you don't want to call Update() and Final() seperately
virtual void CalculateDigest(byte *digest, const byte *input, int length) virtual void CalculateDigest(byte *digest, const byte *input, int length)
{Update(input, length); Final(digest);} {Update(input, length); Final(digest);}
}; };
/// abstract base class for message authentication codes /// abstract base class for message authentication codes
/** The main differences between a MAC and an hash function (in terms of /** The main differences between a MAC and an hash function (in terms of
programmatic interface) is that a MAC is keyed, and that calculating programmatic interface) is that a MAC is keyed, and that calculating
a MAC for the same message twice may produce two different results so a MAC for the same message twice may produce two different results so
verifying a MAC may not be simply recalculating it and doing a bitwise verifying a MAC may not be simply recalculating it and doing a bitwise
comparison. comparison.
*/ */
class MessageAuthenticationCode : public virtual HashModule class MessageAuthenticationCode : public virtual HashModule
{ {
public: public:
/// ///
virtual ~MessageAuthenticationCode() {} virtual ~MessageAuthenticationCode() {}
/// verify that mac is a valid MAC for the current message, then reinitialize the object /// verify that mac is a valid MAC for the current message, then reinitialize the object
/** Default implementation is to call Final() and do a bitwise comparison /** Default implementation is to call Final() and do a bitwise comparison
between its output and mac. */ between its output and mac. */
virtual bool Verify(const byte *mac); virtual bool Verify(const byte *mac);
/// use this if your input is short and you don't want to call Update() and Verify() seperately /// use this if your input is short and you don't want to call Update() and Verify() seperately
virtual bool VerifyMAC(const byte *mac, const byte *input, int length) virtual bool VerifyMAC(const byte *mac, const byte *input, int length)
{Update(input, length); return Verify(mac);} {Update(input, length); return Verify(mac);}
}; };
/// abstract base class for buffered transformations /// abstract base class for buffered transformations
/** BufferedTransformation is a generalization of \Ref{BlockTransformation}, /** BufferedTransformation is a generalization of \Ref{BlockTransformation},
\Ref{StreamCipher}, and \Ref{HashModule}. \Ref{StreamCipher}, and \Ref{HashModule}.
A buffered transformation is an object that takes a stream of bytes A buffered transformation is an object that takes a stream of bytes
as input (this may be done in stages), does some computation on them, and as input (this may be done in stages), does some computation on them, and
then places the result into an internal buffer for later retrieval. Any then places the result into an internal buffer for later retrieval. Any
partial result already in the output buffer is not modified by further partial result already in the output buffer is not modified by further
input. input.
Computation is generally done as soon as possible, but some buffering Computation is generally done as soon as possible, but some buffering
on the input may be done for performance reasons. on the input may be done for performance reasons.
*/ */
class BufferedTransformation class BufferedTransformation
{ {
public: public:
/// ///
virtual ~BufferedTransformation() {} virtual ~BufferedTransformation() {}
//@Man: INPUT //@Man: INPUT
//@{ //@{
/// input a byte for processing /// input a byte for processing
virtual void Put(byte inByte) =0; virtual void Put(byte inByte) =0;
/// input multiple bytes /// input multiple bytes
virtual void Put(const byte *inString, unsigned int length) =0; virtual void Put(const byte *inString, unsigned int length) =0;
/// signal that no more input is available /// signal that no more input is available
virtual void InputFinished() {} virtual void InputFinished() {}
/// input a 16-bit word, big-endian or little-endian depending on highFirst /// input a 16-bit word, big-endian or little-endian depending on highFirst
void PutShort(word16 value, bool highFirst=true); void PutShort(word16 value, bool highFirst=true);
/// input a 32-bit word /// input a 32-bit word
void PutLong(word32 value, bool highFirst=true); void PutLong(word32 value, bool highFirst=true);
//@} //@}
//@Man: RETRIEVAL //@Man: RETRIEVAL
//@{ //@{
/// returns number of bytes that is currently ready for retrieval /// returns number of bytes that is currently ready for retrieval
/** All retrieval functions return the actual number of bytes /** All retrieval functions return the actual number of bytes
retrieved, which is the lesser of the request number and retrieved, which is the lesser of the request number and
MaxRetrieveable(). */ MaxRetrieveable(). */
virtual unsigned long MaxRetrieveable() =0; virtual unsigned long MaxRetrieveable() =0;
/// try to retrieve a single byte /// try to retrieve a single byte
virtual unsigned int Get(byte &outByte) =0; virtual unsigned int Get(byte &outByte) =0;
/// try to retrieve multiple bytes /// try to retrieve multiple bytes
virtual unsigned int Get(byte *outString, unsigned int getMax) =0; virtual unsigned int Get(byte *outString, unsigned int getMax) =0;
/// try to retrieve a 16-bit word, big-endian or little-endian depending on highFirst /// try to retrieve a 16-bit word, big-endian or little-endian depending on highFirst
int GetShort(word16 &value, bool highFirst=true); int GetShort(word16 &value, bool highFirst=true);
/// try to retrieve a 32-bit word /// try to retrieve a 32-bit word
int GetLong(word32 &value, bool highFirst=true); int GetLong(word32 &value, bool highFirst=true);
/// move all of the buffered output to target as input /// move all of the buffered output to target as input
virtual void TransferTo(BufferedTransformation &target); virtual void TransferTo(BufferedTransformation &target);
/// same as above but only transfer up to transferMax bytes /// same as above but only transfer up to transferMax bytes
virtual unsigned int TransferTo(BufferedTransformation &target, unsigned int transferMax); virtual unsigned int TransferTo(BufferedTransformation &target, unsigned int transferMax);
/// peek at the next byte without removing it from the output buffer /// peek at the next byte without removing it from the output buffer
virtual unsigned int Peek(byte &outByte) const =0; virtual unsigned int Peek(byte &outByte) const =0;
/// discard some bytes from the output buffer /// discard some bytes from the output buffer
unsigned int Skip(unsigned int skipMax); unsigned int Skip(unsigned int skipMax);
//@} //@}
//@Man: ATTACHMENT //@Man: ATTACHMENT
//@{ //@{
/** Some BufferedTransformation objects (e.g. \Ref{Filter} objects) /** Some BufferedTransformation objects (e.g. \Ref{Filter} objects)
allow other BufferedTransformation objects to be attached. When allow other BufferedTransformation objects to be attached. When
this is done, the first object instead of buffering its output, this is done, the first object instead of buffering its output,
sents that output to the attached object as input. See the sents that output to the attached object as input. See the
documentation for the \Ref{Filter} class for the details. documentation for the \Ref{Filter} class for the details.
*/ */
/// ///
virtual bool Attachable() {return false;} virtual bool Attachable() {return false;}
/// ///
virtual void Detach(BufferedTransformation *p = 0) {} // NULL is undefined at this point virtual void Detach(BufferedTransformation *p = 0) {} // NULL is undefined at this point
/// ///
virtual void Attach(BufferedTransformation *) {} virtual void Attach(BufferedTransformation *) {}
/// call InputFinished() for all attached objects /// call InputFinished() for all attached objects
virtual void Close() {InputFinished();} virtual void Close() {InputFinished();}
//@} //@}
}; };
/// abstract base class for public-key encryptors and decryptors /// abstract base class for public-key encryptors and decryptors
/** This class provides an interface common to encryptors and decryptors /** This class provides an interface common to encryptors and decryptors
for querying their plaintext and ciphertext lengths. for querying their plaintext and ciphertext lengths.
*/ */
class PK_CryptoSystem class PK_CryptoSystem
{ {
public: public:
/// ///
virtual ~PK_CryptoSystem() {} virtual ~PK_CryptoSystem() {}
/// maximum length of plaintext for a given ciphertext length /// maximum length of plaintext for a given ciphertext length
//* This function returns 0 if cipherTextLength is not valid (too long or too short). //* This function returns 0 if cipherTextLength is not valid (too long or too short).
virtual unsigned int MaxPlainTextLength(unsigned int cipherTextLength) const =0; virtual unsigned int MaxPlainTextLength(unsigned int cipherTextLength) const =0;
/// calculate length of ciphertext given length of plaintext /// calculate length of ciphertext given length of plaintext
//* This function returns 0 if plainTextLength is not valid (too long). //* This function returns 0 if plainTextLength is not valid (too long).
virtual unsigned int CipherTextLength(unsigned int plainTextLength) const =0; virtual unsigned int CipherTextLength(unsigned int plainTextLength) const =0;
}; };
/// abstract base class for public-key encryptors /// abstract base class for public-key encryptors
/** An encryptor is also a public encryption key. It contains both the /** An encryptor is also a public encryption key. It contains both the
key and the algorithm to perform the encryption. key and the algorithm to perform the encryption.
*/ */
class PK_Encryptor : public virtual PK_CryptoSystem class PK_Encryptor : public virtual PK_CryptoSystem
{ {
public: public:
/// encrypt a byte string /// encrypt a byte string
/** Preconditions: /** Preconditions:
\begin{itemize} \begin{itemize}
\item CipherTextLength(plainTextLength) != 0 (i.e., plainText isn't too long) \item CipherTextLength(plainTextLength) != 0 (i.e., plainText isn't too long)
\item size of cipherText == CipherTextLength(plainTextLength) \item size of cipherText == CipherTextLength(plainTextLength)
\end{itemize} \end{itemize}
*/ */
virtual void Encrypt(RandomNumberGenerator &rng, const byte *plainText, unsigned int plainTextLength, byte *cipherText) =0; virtual void Encrypt(RandomNumberGenerator &rng, const byte *plainText, unsigned int plainTextLength, byte *cipherText) =0;
}; };
/// abstract base class for public-key decryptors /// abstract base class for public-key decryptors
/** An decryptor is also a private decryption key. It contains both the /** An decryptor is also a private decryption key. It contains both the
key and the algorithm to perform the decryption. key and the algorithm to perform the decryption.
*/ */
class PK_Decryptor : public virtual PK_CryptoSystem class PK_Decryptor : public virtual PK_CryptoSystem
{ {
public: public:
/// decrypt a byte string, and return the length of plaintext /// decrypt a byte string, and return the length of plaintext
/** Precondition: size of plainText == MaxPlainTextLength(cipherTextLength) /** Precondition: size of plainText == MaxPlainTextLength(cipherTextLength)
bytes. bytes.
The function returns the actual length of the plaintext, or 0 The function returns the actual length of the plaintext, or 0
if decryption fails. if decryption fails.
*/ */
virtual unsigned int Decrypt(const byte *cipherText, unsigned int cipherTextLength, byte *plainText) =0; virtual unsigned int Decrypt(const byte *cipherText, unsigned int cipherTextLength, byte *plainText) =0;
}; };
/// abstract base class for encryptors and decryptors with fixed length ciphertext /// abstract base class for encryptors and decryptors with fixed length ciphertext
/** A simplified interface (as embodied in this /** A simplified interface (as embodied in this
class and its subclasses) is provided for crypto systems (such class and its subclasses) is provided for crypto systems (such
as RSA) whose ciphertext depend only on the key, not on the length as RSA) whose ciphertext depend only on the key, not on the length
of the plaintext. The maximum plaintext length also depend only on of the plaintext. The maximum plaintext length also depend only on
the key. the key.
*/ */
class PK_FixedLengthCryptoSystem : public virtual PK_CryptoSystem class PK_FixedLengthCryptoSystem : public virtual PK_CryptoSystem
{ {
public: public:
/// ///
virtual unsigned int MaxPlainTextLength() const =0; virtual unsigned int MaxPlainTextLength() const =0;
/// ///
virtual unsigned int CipherTextLength() const =0; virtual unsigned int CipherTextLength() const =0;
unsigned int MaxPlainTextLength(unsigned int cipherTextLength) const; unsigned int MaxPlainTextLength(unsigned int cipherTextLength) const;
unsigned int CipherTextLength(unsigned int plainTextLength) const; unsigned int CipherTextLength(unsigned int plainTextLength) const;
}; };
/// abstract base class for encryptors with fixed length ciphertext /// abstract base class for encryptors with fixed length ciphertext
@ -351,160 +351,160 @@ class PK_FixedLengthEncryptor : public virtual PK_Encryptor, public virtual PK_F
class PK_FixedLengthDecryptor : public virtual PK_Decryptor, public virtual PK_FixedLengthCryptoSystem class PK_FixedLengthDecryptor : public virtual PK_Decryptor, public virtual PK_FixedLengthCryptoSystem
{ {
public: public:
/// decrypt a byte string, and return the length of plaintext /// decrypt a byte string, and return the length of plaintext
/** Preconditions: /** Preconditions:
\begin{itemize} \begin{itemize}
\item length of cipherText == CipherTextLength() \item length of cipherText == CipherTextLength()
\item size of plainText == MaxPlainTextLength() \item size of plainText == MaxPlainTextLength()
\end{itemize} \end{itemize}
The function returns the actual length of the plaintext, or 0 The function returns the actual length of the plaintext, or 0
if decryption fails. if decryption fails.
*/ */
virtual unsigned int Decrypt(const byte *cipherText, byte *plainText) =0; virtual unsigned int Decrypt(const byte *cipherText, byte *plainText) =0;
unsigned int Decrypt(const byte *cipherText, unsigned int cipherTextLength, byte *plainText); unsigned int Decrypt(const byte *cipherText, unsigned int cipherTextLength, byte *plainText);
}; };
/// abstract base class for public-key signers and verifiers /// abstract base class for public-key signers and verifiers
/** This class provides an interface common to signers and verifiers /** This class provides an interface common to signers and verifiers
for querying their signature lengths and maximum message lengths. for querying their signature lengths and maximum message lengths.
The maximum message length is typically very low (less than 1000) The maximum message length is typically very low (less than 1000)
because it is intended that only message digests (see \Ref{HashModule}) because it is intended that only message digests (see \Ref{HashModule})
should be signed. should be signed.
*/ */
class PK_SignatureSystem class PK_SignatureSystem
{ {
public: public:
/// ///
virtual ~PK_SignatureSystem() {}; virtual ~PK_SignatureSystem() {};
/// maximum length of a message that can be signed or verified /// maximum length of a message that can be signed or verified
virtual unsigned int MaxMessageLength() const =0; virtual unsigned int MaxMessageLength() const =0;
/// signature length support by this object (as either input or output) /// signature length support by this object (as either input or output)
virtual unsigned int SignatureLength() const =0; virtual unsigned int SignatureLength() const =0;
}; };
/// abstract base class for public-key signers /// abstract base class for public-key signers
/** A signer is also a private signature key. It contains both the /** A signer is also a private signature key. It contains both the
key and the algorithm to perform the signature. key and the algorithm to perform the signature.
*/ */
class PK_Signer : public virtual PK_SignatureSystem class PK_Signer : public virtual PK_SignatureSystem
{ {
public: public:
/// sign a message /// sign a message
/** Preconditions: /** Preconditions:
\begin{itemize} \begin{itemize}
\item messageLen <= MaxMessageLength() \item messageLen <= MaxMessageLength()
\item size of signature == SignatureLength() \item size of signature == SignatureLength()
\end{itemize} \end{itemize}
*/ */
virtual void Sign(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature) =0; virtual void Sign(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature) =0;
}; };
/// abstract base class for public-key verifiers /// abstract base class for public-key verifiers
/** A verifier is also a public verification key. It contains both the /** A verifier is also a public verification key. It contains both the
key and the algorithm to perform the verification. key and the algorithm to perform the verification.
*/ */
class PK_Verifier : public virtual PK_SignatureSystem class PK_Verifier : public virtual PK_SignatureSystem
{ {
public: public:
/// check whether sig is a valid signature for message /// check whether sig is a valid signature for message
/** Preconditions: /** Preconditions:
\begin{itemize} \begin{itemize}
\item messageLen <= MaxMessageLength() \item messageLen <= MaxMessageLength()
\item length of signature == SignatureLength() \item length of signature == SignatureLength()
\end{itemize} \end{itemize}
*/ */
virtual bool Verify(const byte *message, unsigned int messageLen, const byte *sig) =0; virtual bool Verify(const byte *message, unsigned int messageLen, const byte *sig) =0;
}; };
/// abstract base class for public-key verifiers with recovery /// abstract base class for public-key verifiers with recovery
/** In a signature scheme with recovery, a verifier is able to extract /** In a signature scheme with recovery, a verifier is able to extract
a message from its valid signature. This saves space since a message from its valid signature. This saves space since
you don't need to store the message seperately. you don't need to store the message seperately.
*/ */
class PK_VerifierWithRecovery : public PK_Verifier class PK_VerifierWithRecovery : public PK_Verifier
{ {
public: public:
/// recover a message from its signature, return length of message, or 0 if signature is invalid /// recover a message from its signature, return length of message, or 0 if signature is invalid
/** Preconditions: /** Preconditions:
\begin{itemize} \begin{itemize}
\item length of signature == SignatureLength() \item length of signature == SignatureLength()
\item size of recoveredMessage == MaxMessageLength() \item size of recoveredMessage == MaxMessageLength()
\end{itemize} \end{itemize}
*/ */
virtual unsigned int Recover(const byte *signature, byte *recoveredMessage) =0; virtual unsigned int Recover(const byte *signature, byte *recoveredMessage) =0;
bool Verify(const byte *message, unsigned int messageLen, const byte *signature); bool Verify(const byte *message, unsigned int messageLen, const byte *signature);
}; };
/// abstract base class for key agreement protocols /// abstract base class for key agreement protocols
/** This class defines the interface for symmetric 2-pass key agreement /** This class defines the interface for symmetric 2-pass key agreement
protocols. It isn't very general and only basic Diffie-Hellman protocols. It isn't very general and only basic Diffie-Hellman
protocols fit the abstraction, so possibly a more general interface protocols fit the abstraction, so possibly a more general interface
is needed. is needed.
To use a KeyAgreementProtocol class, the two parties create matching To use a KeyAgreementProtocol class, the two parties create matching
KeyAgreementProtocol objects, call Setup() on these objects, KeyAgreementProtocol objects, call Setup() on these objects,
and send each other the public values produced. The objects are and send each other the public values produced. The objects are
responsible for remembering the corresponding secret values, and responsible for remembering the corresponding secret values, and
will produce a shared secret value when Agree() is called with the will produce a shared secret value when Agree() is called with the
other party's public value. other party's public value.
*/ */
class KeyAgreementProtocol class KeyAgreementProtocol
{ {
public: public:
/// ///
virtual ~KeyAgreementProtocol() {} virtual ~KeyAgreementProtocol() {}
/// ///
virtual unsigned int PublicValueLength() const =0; virtual unsigned int PublicValueLength() const =0;
/// ///
virtual unsigned int AgreedKeyLength() const =0; virtual unsigned int AgreedKeyLength() const =0;
/// produce public value /// produce public value
//* Precondition: size of publicValue == PublicValueLength() //* Precondition: size of publicValue == PublicValueLength()
virtual void Setup(RandomNumberGenerator &rng, byte *publicValue) =0; virtual void Setup(RandomNumberGenerator &rng, byte *publicValue) =0;
/// calculate agreed key given other party's public value /// calculate agreed key given other party's public value
/** Precondition: /** Precondition:
\begin{itemize} \begin{itemize}
\item Setup() was called previously on this object \item Setup() was called previously on this object
\item size of agreedKey == AgreedKeyLength() \item size of agreedKey == AgreedKeyLength()
\end{itemize} \end{itemize}
*/ */
virtual void Agree(const byte *otherPublicValue, byte *agreedKey) const =0; virtual void Agree(const byte *otherPublicValue, byte *agreedKey) const =0;
}; };
/// abstract base class for all objects that support precomputation /// abstract base class for all objects that support precomputation
/** The class defines a common interface for doing precomputation, /** The class defines a common interface for doing precomputation,
and loading and saving precomputation. and loading and saving precomputation.
*/ */
class PK_Precomputation class PK_Precomputation
{ {
public: public:
/// ///
virtual ~PK_Precomputation() {} virtual ~PK_Precomputation() {}
/// ///
/** The exact semantics of Precompute() is varies, but /** The exact semantics of Precompute() is varies, but
typically it means calculate a table of n objects typically it means calculate a table of n objects
that can be used later to speed up computation. that can be used later to speed up computation.
*/ */
virtual void Precompute(unsigned int n) =0; virtual void Precompute(unsigned int n) =0;
/// retrieve previously saved precomputation /// retrieve previously saved precomputation
virtual void LoadPrecomputation(BufferedTransformation &storedPrecomputation) =0; virtual void LoadPrecomputation(BufferedTransformation &storedPrecomputation) =0;
/// save precomputation for later use /// save precomputation for later use
virtual void SavePrecomputation(BufferedTransformation &storedPrecomputation) const =0; virtual void SavePrecomputation(BufferedTransformation &storedPrecomputation) const =0;
}; };
/// ///

View File

@ -29,187 +29,187 @@
#ifdef notdef #ifdef notdef
/* initial permutation IP */ /* initial permutation IP */
static byte ip[] = { static byte ip[] = {
58, 50, 42, 34, 26, 18, 10, 2, 58, 50, 42, 34, 26, 18, 10, 2,
60, 52, 44, 36, 28, 20, 12, 4, 60, 52, 44, 36, 28, 20, 12, 4,
62, 54, 46, 38, 30, 22, 14, 6, 62, 54, 46, 38, 30, 22, 14, 6,
64, 56, 48, 40, 32, 24, 16, 8, 64, 56, 48, 40, 32, 24, 16, 8,
57, 49, 41, 33, 25, 17, 9, 1, 57, 49, 41, 33, 25, 17, 9, 1,
59, 51, 43, 35, 27, 19, 11, 3, 59, 51, 43, 35, 27, 19, 11, 3,
61, 53, 45, 37, 29, 21, 13, 5, 61, 53, 45, 37, 29, 21, 13, 5,
63, 55, 47, 39, 31, 23, 15, 7 63, 55, 47, 39, 31, 23, 15, 7
}; };
/* final permutation IP^-1 */ /* final permutation IP^-1 */
static byte fp[] = { static byte fp[] = {
40, 8, 48, 16, 56, 24, 64, 32, 40, 8, 48, 16, 56, 24, 64, 32,
39, 7, 47, 15, 55, 23, 63, 31, 39, 7, 47, 15, 55, 23, 63, 31,
38, 6, 46, 14, 54, 22, 62, 30, 38, 6, 46, 14, 54, 22, 62, 30,
37, 5, 45, 13, 53, 21, 61, 29, 37, 5, 45, 13, 53, 21, 61, 29,
36, 4, 44, 12, 52, 20, 60, 28, 36, 4, 44, 12, 52, 20, 60, 28,
35, 3, 43, 11, 51, 19, 59, 27, 35, 3, 43, 11, 51, 19, 59, 27,
34, 2, 42, 10, 50, 18, 58, 26, 34, 2, 42, 10, 50, 18, 58, 26,
33, 1, 41, 9, 49, 17, 57, 25 33, 1, 41, 9, 49, 17, 57, 25
}; };
/* expansion operation matrix */ /* expansion operation matrix */
static byte ei[] = { static byte ei[] = {
32, 1, 2, 3, 4, 5, 32, 1, 2, 3, 4, 5,
4, 5, 6, 7, 8, 9, 4, 5, 6, 7, 8, 9,
8, 9, 10, 11, 12, 13, 8, 9, 10, 11, 12, 13,
12, 13, 14, 15, 16, 17, 12, 13, 14, 15, 16, 17,
16, 17, 18, 19, 20, 21, 16, 17, 18, 19, 20, 21,
20, 21, 22, 23, 24, 25, 20, 21, 22, 23, 24, 25,
24, 25, 26, 27, 28, 29, 24, 25, 26, 27, 28, 29,
28, 29, 30, 31, 32, 1 28, 29, 30, 31, 32, 1
}; };
/* The (in)famous S-boxes */ /* The (in)famous S-boxes */
static byte sbox[8][64] = { static byte sbox[8][64] = {
/* S1 */ /* S1 */
14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7, 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7,
0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8, 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8,
4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0, 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0,
15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13, 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13,
/* S2 */ /* S2 */
15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10, 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10,
3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5, 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5,
0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15, 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15,
13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9, 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9,
/* S3 */ /* S3 */
10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8, 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8,
13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1, 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1,
13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7, 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7,
1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12, 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12,
/* S4 */ /* S4 */
7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15, 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15,
13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9, 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9,
10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4, 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4,
3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14, 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14,
/* S5 */ /* S5 */
2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9, 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9,
14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6, 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6,
4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14, 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14,
11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3, 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3,
/* S6 */ /* S6 */
12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11, 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11,
10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8, 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8,
9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6, 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6,
4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13, 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13,
/* S7 */ /* S7 */
4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1, 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1,
13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6, 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6,
1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2, 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2,
6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12, 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12,
/* S8 */ /* S8 */
13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7, 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7,
1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2, 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2,
7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8, 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8,
2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11
}; };
/* 32-bit permutation function P used on the output of the S-boxes */ /* 32-bit permutation function P used on the output of the S-boxes */
static byte p32i[] = { static byte p32i[] = {
16, 7, 20, 21, 16, 7, 20, 21,
29, 12, 28, 17, 29, 12, 28, 17,
1, 15, 23, 26, 1, 15, 23, 26,
5, 18, 31, 10, 5, 18, 31, 10,
2, 8, 24, 14, 2, 8, 24, 14,
32, 27, 3, 9, 32, 27, 3, 9,
19, 13, 30, 6, 19, 13, 30, 6,
22, 11, 4, 25 22, 11, 4, 25
}; };
#endif #endif
/* permuted choice table (key) */ /* permuted choice table (key) */
static const byte pc1[] = { static const byte pc1[] = {
57, 49, 41, 33, 25, 17, 9, 57, 49, 41, 33, 25, 17, 9,
1, 58, 50, 42, 34, 26, 18, 1, 58, 50, 42, 34, 26, 18,
10, 2, 59, 51, 43, 35, 27, 10, 2, 59, 51, 43, 35, 27,
19, 11, 3, 60, 52, 44, 36, 19, 11, 3, 60, 52, 44, 36,
63, 55, 47, 39, 31, 23, 15, 63, 55, 47, 39, 31, 23, 15,
7, 62, 54, 46, 38, 30, 22, 7, 62, 54, 46, 38, 30, 22,
14, 6, 61, 53, 45, 37, 29, 14, 6, 61, 53, 45, 37, 29,
21, 13, 5, 28, 20, 12, 4 21, 13, 5, 28, 20, 12, 4
}; };
/* number left rotations of pc1 */ /* number left rotations of pc1 */
static const byte totrot[] = { static const byte totrot[] = {
1,2,4,6,8,10,12,14,15,17,19,21,23,25,27,28 1,2,4,6,8,10,12,14,15,17,19,21,23,25,27,28
}; };
/* permuted choice key (table) */ /* permuted choice key (table) */
static const byte pc2[] = { static const byte pc2[] = {
14, 17, 11, 24, 1, 5, 14, 17, 11, 24, 1, 5,
3, 28, 15, 6, 21, 10, 3, 28, 15, 6, 21, 10,
23, 19, 12, 4, 26, 8, 23, 19, 12, 4, 26, 8,
16, 7, 27, 20, 13, 2, 16, 7, 27, 20, 13, 2,
41, 52, 31, 37, 47, 55, 41, 52, 31, 37, 47, 55,
30, 40, 51, 45, 33, 48, 30, 40, 51, 45, 33, 48,
44, 49, 39, 56, 34, 53, 44, 49, 39, 56, 34, 53,
46, 42, 50, 36, 29, 32 46, 42, 50, 36, 29, 32
}; };
/* End of DES-defined tables */ /* End of DES-defined tables */
/* bit 0 is left-most in byte */ /* bit 0 is left-most in byte */
static const int bytebit[] = { static const int bytebit[] = {
0200,0100,040,020,010,04,02,01 0200,0100,040,020,010,04,02,01
}; };
/* Set key (initialize key schedule array) */ /* Set key (initialize key schedule array) */
DES::DES(const byte *key, CipherDir dir) DES::DES(const byte *key, CipherDir dir)
: k(32) : k(32)
{ {
SecByteBlock buffer(56+56+8); SecByteBlock buffer(56+56+8);
byte *const pc1m=buffer; /* place to modify pc1 into */ byte *const pc1m=buffer; /* place to modify pc1 into */
byte *const pcr=pc1m+56; /* place to rotate pc1 into */ byte *const pcr=pc1m+56; /* place to rotate pc1 into */
byte *const ks=pcr+56; byte *const ks=pcr+56;
register unsigned int i,j,l; register unsigned int i,j,l;
int m; int m;
for (j=0; j<56; j++) { /* convert pc1 to bits of key */ for (j=0; j<56; j++) { /* convert pc1 to bits of key */
l=pc1[j]-1; /* integer bit location */ l=pc1[j]-1; /* integer bit location */
m = l & 07; /* find bit */ m = l & 07; /* find bit */
pc1m[j]=(key[l>>3] & /* find which key byte l is in */ pc1m[j]=(key[l>>3] & /* find which key byte l is in */
bytebit[m]) /* and which bit of that byte */ bytebit[m]) /* and which bit of that byte */
? 1 : 0; /* and store 1-bit result */ ? 1 : 0; /* and store 1-bit result */
} }
for (i=0; i<16; i++) { /* key chunk for each iteration */ for (i=0; i<16; i++) { /* key chunk for each iteration */
memset(ks,0,8); /* Clear key schedule */ memset(ks,0,8); /* Clear key schedule */
for (j=0; j<56; j++) /* rotate pc1 the right amount */ for (j=0; j<56; j++) /* rotate pc1 the right amount */
pcr[j] = pc1m[(l=j+totrot[i])<(j<28? 28 : 56) ? l: l-28]; pcr[j] = pc1m[(l=j+totrot[i])<(j<28? 28 : 56) ? l: l-28];
/* rotate left and right halves independently */ /* rotate left and right halves independently */
for (j=0; j<48; j++){ /* select bits individually */ for (j=0; j<48; j++){ /* select bits individually */
/* check bit that goes to ks[j] */ /* check bit that goes to ks[j] */
if (pcr[pc2[j]-1]){ if (pcr[pc2[j]-1]){
/* mask it in if it's there */ /* mask it in if it's there */
l= j % 6; l= j % 6;
ks[j/6] |= bytebit[l] >> 2; ks[j/6] |= bytebit[l] >> 2;
} }
} }
/* Now convert to odd/even interleaved form for use in F */ /* Now convert to odd/even interleaved form for use in F */
k[2*i] = ((word32)ks[0] << 24) k[2*i] = ((word32)ks[0] << 24)
| ((word32)ks[2] << 16) | ((word32)ks[2] << 16)
| ((word32)ks[4] << 8) | ((word32)ks[4] << 8)
| ((word32)ks[6]); | ((word32)ks[6]);
k[2*i+1] = ((word32)ks[1] << 24) k[2*i+1] = ((word32)ks[1] << 24)
| ((word32)ks[3] << 16) | ((word32)ks[3] << 16)
| ((word32)ks[5] << 8) | ((word32)ks[5] << 8)
| ((word32)ks[7]); | ((word32)ks[7]);
} }
if (dir==DECRYPTION) // reverse key schedule order if (dir==DECRYPTION) // reverse key schedule order
for (i=0; i<16; i+=2) for (i=0; i<16; i+=2)
{ {
std::swap(k[i], k[32-2-i]); std::swap(k[i], k[32-2-i]);
std::swap(k[i+1], k[32-1-i]); std::swap(k[i+1], k[32-1-i]);
} }
} }
/* End of C code common to both versions */ /* End of C code common to both versions */
@ -219,47 +219,47 @@ DES::DES(const byte *key, CipherDir dir)
/* /*
inline void IPERM(word32 &left, word32 &right) inline void IPERM(word32 &left, word32 &right)
{ {
word32 work; word32 work;
work = ((left >> 4) ^ right) & 0x0f0f0f0f; work = ((left >> 4) ^ right) & 0x0f0f0f0f;
right ^= work; right ^= work;
left ^= work << 4; left ^= work << 4;
work = ((left >> 16) ^ right) & 0xffff; work = ((left >> 16) ^ right) & 0xffff;
right ^= work; right ^= work;
left ^= work << 16; left ^= work << 16;
work = ((right >> 2) ^ left) & 0x33333333; work = ((right >> 2) ^ left) & 0x33333333;
left ^= work; left ^= work;
right ^= (work << 2); right ^= (work << 2);
work = ((right >> 8) ^ left) & 0xff00ff; work = ((right >> 8) ^ left) & 0xff00ff;
left ^= work; left ^= work;
right ^= (work << 8); right ^= (work << 8);
right = rotl(right, 1); right = rotl(right, 1);
work = (left ^ right) & 0xaaaaaaaa; work = (left ^ right) & 0xaaaaaaaa;
left ^= work; left ^= work;
right ^= work; right ^= work;
left = rotl(left, 1); left = rotl(left, 1);
} }
inline void FPERM(word32 &left, word32 &right) inline void FPERM(word32 &left, word32 &right)
{ {
word32 work; word32 work;
right = rotr(right, 1); right = rotr(right, 1);
work = (left ^ right) & 0xaaaaaaaa; work = (left ^ right) & 0xaaaaaaaa;
left ^= work; left ^= work;
right ^= work; right ^= work;
left = rotr(left, 1); left = rotr(left, 1);
work = ((left >> 8) ^ right) & 0xff00ff; work = ((left >> 8) ^ right) & 0xff00ff;
right ^= work; right ^= work;
left ^= work << 8; left ^= work << 8;
work = ((left >> 2) ^ right) & 0x33333333; work = ((left >> 2) ^ right) & 0x33333333;
right ^= work; right ^= work;
left ^= work << 2; left ^= work << 2;
work = ((right >> 16) ^ left) & 0xffff; work = ((right >> 16) ^ left) & 0xffff;
left ^= work; left ^= work;
right ^= work << 16; right ^= work << 16;
work = ((right >> 4) ^ left) & 0x0f0f0f0f; work = ((right >> 4) ^ left) & 0x0f0f0f0f;
left ^= work; left ^= work;
right ^= work << 4; right ^= work << 4;
} }
*/ */
@ -268,153 +268,153 @@ inline void FPERM(word32 &left, word32 &right)
// (like in MSVC) // (like in MSVC)
inline void IPERM(word32 &left, word32 &right) inline void IPERM(word32 &left, word32 &right)
{ {
word32 work; word32 work;
right = rotl(right, 4U); right = rotl(right, 4U);
work = (left ^ right) & 0xf0f0f0f0; work = (left ^ right) & 0xf0f0f0f0;
left ^= work; left ^= work;
right = rotr(right^work, 20U); right = rotr(right^work, 20U);
work = (left ^ right) & 0xffff0000; work = (left ^ right) & 0xffff0000;
left ^= work; left ^= work;
right = rotr(right^work, 18U); right = rotr(right^work, 18U);
work = (left ^ right) & 0x33333333; work = (left ^ right) & 0x33333333;
left ^= work; left ^= work;
right = rotr(right^work, 6U); right = rotr(right^work, 6U);
work = (left ^ right) & 0x00ff00ff; work = (left ^ right) & 0x00ff00ff;
left ^= work; left ^= work;
right = rotl(right^work, 9U); right = rotl(right^work, 9U);
work = (left ^ right) & 0xaaaaaaaa; work = (left ^ right) & 0xaaaaaaaa;
left = rotl(left^work, 1U); left = rotl(left^work, 1U);
right ^= work; right ^= work;
} }
inline void FPERM(word32 &left, word32 &right) inline void FPERM(word32 &left, word32 &right)
{ {
word32 work; word32 work;
right = rotr(right, 1U); right = rotr(right, 1U);
work = (left ^ right) & 0xaaaaaaaa; work = (left ^ right) & 0xaaaaaaaa;
right ^= work; right ^= work;
left = rotr(left^work, 9U); left = rotr(left^work, 9U);
work = (left ^ right) & 0x00ff00ff; work = (left ^ right) & 0x00ff00ff;
right ^= work; right ^= work;
left = rotl(left^work, 6U); left = rotl(left^work, 6U);
work = (left ^ right) & 0x33333333; work = (left ^ right) & 0x33333333;
right ^= work; right ^= work;
left = rotl(left^work, 18U); left = rotl(left^work, 18U);
work = (left ^ right) & 0xffff0000; work = (left ^ right) & 0xffff0000;
right ^= work; right ^= work;
left = rotl(left^work, 20U); left = rotl(left^work, 20U);
work = (left ^ right) & 0xf0f0f0f0; work = (left ^ right) & 0xf0f0f0f0;
right ^= work; right ^= work;
left = rotr(left^work, 4U); left = rotr(left^work, 4U);
} }
// Encrypt or decrypt a block of data in ECB mode // Encrypt or decrypt a block of data in ECB mode
void DES::ProcessBlock(const byte *inBlock, byte * outBlock) void DES::ProcessBlock(const byte *inBlock, byte * outBlock)
{ {
word32 l,r,work; word32 l,r,work;
#ifdef WORDS_BIGENDIAN #ifdef WORDS_BIGENDIAN
l = *(word32 *)inBlock; l = *(word32 *)inBlock;
r = *(word32 *)(inBlock+4); r = *(word32 *)(inBlock+4);
#else #else
l = byteReverse(*(word32 *)inBlock); l = byteReverse(*(word32 *)inBlock);
r = byteReverse(*(word32 *)(inBlock+4)); r = byteReverse(*(word32 *)(inBlock+4));
#endif #endif
IPERM(l,r); IPERM(l,r);
const word32 *kptr=k; const word32 *kptr=k;
for (unsigned i=0; i<8; i++) for (unsigned i=0; i<8; i++)
{ {
work = rotr(r, 4U) ^ kptr[4*i+0]; work = rotr(r, 4U) ^ kptr[4*i+0];
l ^= Spbox[6][(work) & 0x3f] l ^= Spbox[6][(work) & 0x3f]
^ Spbox[4][(work >> 8) & 0x3f] ^ Spbox[4][(work >> 8) & 0x3f]
^ Spbox[2][(work >> 16) & 0x3f] ^ Spbox[2][(work >> 16) & 0x3f]
^ Spbox[0][(work >> 24) & 0x3f]; ^ Spbox[0][(work >> 24) & 0x3f];
work = r ^ kptr[4*i+1]; work = r ^ kptr[4*i+1];
l ^= Spbox[7][(work) & 0x3f] l ^= Spbox[7][(work) & 0x3f]
^ Spbox[5][(work >> 8) & 0x3f] ^ Spbox[5][(work >> 8) & 0x3f]
^ Spbox[3][(work >> 16) & 0x3f] ^ Spbox[3][(work >> 16) & 0x3f]
^ Spbox[1][(work >> 24) & 0x3f]; ^ Spbox[1][(work >> 24) & 0x3f];
work = rotr(l, 4U) ^ kptr[4*i+2]; work = rotr(l, 4U) ^ kptr[4*i+2];
r ^= Spbox[6][(work) & 0x3f] r ^= Spbox[6][(work) & 0x3f]
^ Spbox[4][(work >> 8) & 0x3f] ^ Spbox[4][(work >> 8) & 0x3f]
^ Spbox[2][(work >> 16) & 0x3f] ^ Spbox[2][(work >> 16) & 0x3f]
^ Spbox[0][(work >> 24) & 0x3f]; ^ Spbox[0][(work >> 24) & 0x3f];
work = l ^ kptr[4*i+3]; work = l ^ kptr[4*i+3];
r ^= Spbox[7][(work) & 0x3f] r ^= Spbox[7][(work) & 0x3f]
^ Spbox[5][(work >> 8) & 0x3f] ^ Spbox[5][(work >> 8) & 0x3f]
^ Spbox[3][(work >> 16) & 0x3f] ^ Spbox[3][(work >> 16) & 0x3f]
^ Spbox[1][(work >> 24) & 0x3f]; ^ Spbox[1][(work >> 24) & 0x3f];
} }
FPERM(l,r); FPERM(l,r);
#ifdef WORDS_BIGENDIAN #ifdef WORDS_BIGENDIAN
*(word32 *)outBlock = r; *(word32 *)outBlock = r;
*(word32 *)(outBlock+4) = l; *(word32 *)(outBlock+4) = l;
#else #else
*(word32 *)outBlock = byteReverse(r); *(word32 *)outBlock = byteReverse(r);
*(word32 *)(outBlock+4) = byteReverse(l); *(word32 *)(outBlock+4) = byteReverse(l);
#endif #endif
} }
void DES_EDE_Encryption::ProcessBlock(byte *inoutBlock) void DES_EDE_Encryption::ProcessBlock(byte *inoutBlock)
{ {
e.ProcessBlock(inoutBlock); e.ProcessBlock(inoutBlock);
d.ProcessBlock(inoutBlock); d.ProcessBlock(inoutBlock);
e.ProcessBlock(inoutBlock); e.ProcessBlock(inoutBlock);
} }
void DES_EDE_Encryption::ProcessBlock(const byte *inBlock, byte *outBlock) void DES_EDE_Encryption::ProcessBlock(const byte *inBlock, byte *outBlock)
{ {
e.ProcessBlock(inBlock, outBlock); e.ProcessBlock(inBlock, outBlock);
d.ProcessBlock(outBlock); d.ProcessBlock(outBlock);
e.ProcessBlock(outBlock); e.ProcessBlock(outBlock);
} }
void DES_EDE_Decryption::ProcessBlock(byte *inoutBlock) void DES_EDE_Decryption::ProcessBlock(byte *inoutBlock)
{ {
d.ProcessBlock(inoutBlock); d.ProcessBlock(inoutBlock);
e.ProcessBlock(inoutBlock); e.ProcessBlock(inoutBlock);
d.ProcessBlock(inoutBlock); d.ProcessBlock(inoutBlock);
} }
void DES_EDE_Decryption::ProcessBlock(const byte *inBlock, byte *outBlock) void DES_EDE_Decryption::ProcessBlock(const byte *inBlock, byte *outBlock)
{ {
d.ProcessBlock(inBlock, outBlock); d.ProcessBlock(inBlock, outBlock);
e.ProcessBlock(outBlock); e.ProcessBlock(outBlock);
d.ProcessBlock(outBlock); d.ProcessBlock(outBlock);
} }
void TripleDES_Encryption::ProcessBlock(byte *inoutBlock) void TripleDES_Encryption::ProcessBlock(byte *inoutBlock)
{ {
e1.ProcessBlock(inoutBlock); e1.ProcessBlock(inoutBlock);
d.ProcessBlock(inoutBlock); d.ProcessBlock(inoutBlock);
e2.ProcessBlock(inoutBlock); e2.ProcessBlock(inoutBlock);
} }
void TripleDES_Encryption::ProcessBlock(const byte *inBlock, byte *outBlock) void TripleDES_Encryption::ProcessBlock(const byte *inBlock, byte *outBlock)
{ {
e1.ProcessBlock(inBlock, outBlock); e1.ProcessBlock(inBlock, outBlock);
d.ProcessBlock(outBlock); d.ProcessBlock(outBlock);
e2.ProcessBlock(outBlock); e2.ProcessBlock(outBlock);
} }
void TripleDES_Decryption::ProcessBlock(byte *inoutBlock) void TripleDES_Decryption::ProcessBlock(byte *inoutBlock)
{ {
d1.ProcessBlock(inoutBlock); d1.ProcessBlock(inoutBlock);
e.ProcessBlock(inoutBlock); e.ProcessBlock(inoutBlock);
d2.ProcessBlock(inoutBlock); d2.ProcessBlock(inoutBlock);
} }
void TripleDES_Decryption::ProcessBlock(const byte *inBlock, byte *outBlock) void TripleDES_Decryption::ProcessBlock(const byte *inBlock, byte *outBlock)
{ {
d1.ProcessBlock(inBlock, outBlock); d1.ProcessBlock(inBlock, outBlock);
e.ProcessBlock(outBlock); e.ProcessBlock(outBlock);
d2.ProcessBlock(outBlock); d2.ProcessBlock(outBlock);
} }

View File

@ -7,99 +7,99 @@
class DES : public BlockTransformation class DES : public BlockTransformation
{ {
public: public:
DES(const byte *userKey, CipherDir); DES(const byte *userKey, CipherDir);
void ProcessBlock(const byte *inBlock, byte * outBlock); void ProcessBlock(const byte *inBlock, byte * outBlock);
void ProcessBlock(byte * inoutBlock) void ProcessBlock(byte * inoutBlock)
{DES::ProcessBlock(inoutBlock, inoutBlock);} {DES::ProcessBlock(inoutBlock, inoutBlock);}
enum {KEYLENGTH=8, BLOCKSIZE=8}; enum {KEYLENGTH=8, BLOCKSIZE=8};
unsigned int BlockSize() const {return BLOCKSIZE;} unsigned int BlockSize() const {return BLOCKSIZE;}
protected: protected:
static const word32 Spbox[8][64]; static const word32 Spbox[8][64];
SecBlock<word32> k; SecBlock<word32> k;
}; };
class DESEncryption : public DES class DESEncryption : public DES
{ {
public: public:
DESEncryption(const byte * userKey) DESEncryption(const byte * userKey)
: DES (userKey, ENCRYPTION) {} : DES (userKey, ENCRYPTION) {}
}; };
class DESDecryption : public DES class DESDecryption : public DES
{ {
public: public:
DESDecryption(const byte * userKey) DESDecryption(const byte * userKey)
: DES (userKey, DECRYPTION) {} : DES (userKey, DECRYPTION) {}
}; };
class DES_EDE_Encryption : public BlockTransformation class DES_EDE_Encryption : public BlockTransformation
{ {
public: public:
DES_EDE_Encryption(const byte * userKey) DES_EDE_Encryption(const byte * userKey)
: e(userKey, ENCRYPTION), d(userKey + DES::KEYLENGTH, DECRYPTION) {} : e(userKey, ENCRYPTION), d(userKey + DES::KEYLENGTH, DECRYPTION) {}
void ProcessBlock(const byte *inBlock, byte * outBlock); void ProcessBlock(const byte *inBlock, byte * outBlock);
void ProcessBlock(byte * inoutBlock); void ProcessBlock(byte * inoutBlock);
enum {KEYLENGTH=16, BLOCKSIZE=8}; enum {KEYLENGTH=16, BLOCKSIZE=8};
unsigned int BlockSize() const {return BLOCKSIZE;} unsigned int BlockSize() const {return BLOCKSIZE;}
private: private:
DES e, d; DES e, d;
}; };
class DES_EDE_Decryption : public BlockTransformation class DES_EDE_Decryption : public BlockTransformation
{ {
public: public:
DES_EDE_Decryption(const byte * userKey) DES_EDE_Decryption(const byte * userKey)
: d(userKey, DECRYPTION), e(userKey + DES::KEYLENGTH, ENCRYPTION) {} : d(userKey, DECRYPTION), e(userKey + DES::KEYLENGTH, ENCRYPTION) {}
void ProcessBlock(const byte *inBlock, byte * outBlock); void ProcessBlock(const byte *inBlock, byte * outBlock);
void ProcessBlock(byte * inoutBlock); void ProcessBlock(byte * inoutBlock);
enum {KEYLENGTH=16, BLOCKSIZE=8}; enum {KEYLENGTH=16, BLOCKSIZE=8};
unsigned int BlockSize() const {return BLOCKSIZE;} unsigned int BlockSize() const {return BLOCKSIZE;}
private: private:
DES d, e; DES d, e;
}; };
class TripleDES_Encryption : public BlockTransformation class TripleDES_Encryption : public BlockTransformation
{ {
public: public:
TripleDES_Encryption(const byte * userKey) TripleDES_Encryption(const byte * userKey)
: e1(userKey, ENCRYPTION), d(userKey + DES::KEYLENGTH, DECRYPTION), : e1(userKey, ENCRYPTION), d(userKey + DES::KEYLENGTH, DECRYPTION),
e2(userKey + 2*DES::KEYLENGTH, ENCRYPTION) {} e2(userKey + 2*DES::KEYLENGTH, ENCRYPTION) {}
void ProcessBlock(const byte *inBlock, byte * outBlock); void ProcessBlock(const byte *inBlock, byte * outBlock);
void ProcessBlock(byte * inoutBlock); void ProcessBlock(byte * inoutBlock);
enum {KEYLENGTH=24, BLOCKSIZE=8}; enum {KEYLENGTH=24, BLOCKSIZE=8};
unsigned int BlockSize() const {return BLOCKSIZE;} unsigned int BlockSize() const {return BLOCKSIZE;}
private: private:
DES e1, d, e2; DES e1, d, e2;
}; };
class TripleDES_Decryption : public BlockTransformation class TripleDES_Decryption : public BlockTransformation
{ {
public: public:
TripleDES_Decryption(const byte * userKey) TripleDES_Decryption(const byte * userKey)
: d1(userKey + 2*DES::KEYLENGTH, DECRYPTION), e(userKey + DES::KEYLENGTH, ENCRYPTION), : d1(userKey + 2*DES::KEYLENGTH, DECRYPTION), e(userKey + DES::KEYLENGTH, ENCRYPTION),
d2(userKey, DECRYPTION) {} d2(userKey, DECRYPTION) {}
void ProcessBlock(const byte *inBlock, byte * outBlock); void ProcessBlock(const byte *inBlock, byte * outBlock);
void ProcessBlock(byte * inoutBlock); void ProcessBlock(byte * inoutBlock);
enum {KEYLENGTH=24, BLOCKSIZE=8}; enum {KEYLENGTH=24, BLOCKSIZE=8};
unsigned int BlockSize() const {return BLOCKSIZE;} unsigned int BlockSize() const {return BLOCKSIZE;}
private: private:
DES d1, e, d2; DES d1, e, d2;
}; };
#endif #endif

View File

@ -5,8 +5,8 @@
#include "asn.h" #include "asn.h"
ElGamalCryptoPublicKey::ElGamalCryptoPublicKey(const Integer &p, const Integer &g, const Integer &y) ElGamalCryptoPublicKey::ElGamalCryptoPublicKey(const Integer &p, const Integer &g, const Integer &y)
: p(p), g(g), y(y), modulusLen(p.ByteCount()), : p(p), g(g), y(y), modulusLen(p.ByteCount()),
gpc(p, g, ExponentBitLength(), 1), ypc(p, y, ExponentBitLength(), 1) gpc(p, g, ExponentBitLength(), 1), ypc(p, y, ExponentBitLength(), 1)
{ {
} }
@ -18,99 +18,99 @@ ElGamalCryptoPublicKey::~ElGamalCryptoPublicKey()
ElGamalCryptoPublicKey::ElGamalCryptoPublicKey(BufferedTransformation &bt) ElGamalCryptoPublicKey::ElGamalCryptoPublicKey(BufferedTransformation &bt)
{ {
BERSequenceDecoder seq(bt); BERSequenceDecoder seq(bt);
p.BERDecode(seq); p.BERDecode(seq);
modulusLen=p.ByteCount(); modulusLen=p.ByteCount();
g.BERDecode(seq); g.BERDecode(seq);
y.BERDecode(seq); y.BERDecode(seq);
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
} }
void ElGamalCryptoPublicKey::DEREncode(BufferedTransformation &bt) const void ElGamalCryptoPublicKey::DEREncode(BufferedTransformation &bt) const
{ {
DERSequenceEncoder seq(bt); DERSequenceEncoder seq(bt);
p.DEREncode(seq); p.DEREncode(seq);
g.DEREncode(seq); g.DEREncode(seq);
y.DEREncode(seq); y.DEREncode(seq);
} }
void ElGamalCryptoPublicKey::Precompute(unsigned int precomputationStorage) void ElGamalCryptoPublicKey::Precompute(unsigned int precomputationStorage)
{ {
gpc.Precompute(p, g, ExponentBitLength(), precomputationStorage); gpc.Precompute(p, g, ExponentBitLength(), precomputationStorage);
ypc.Precompute(p, y, ExponentBitLength(), precomputationStorage); ypc.Precompute(p, y, ExponentBitLength(), precomputationStorage);
} }
void ElGamalCryptoPublicKey::LoadPrecomputation(BufferedTransformation &bt) void ElGamalCryptoPublicKey::LoadPrecomputation(BufferedTransformation &bt)
{ {
gpc.Load(p, bt); gpc.Load(p, bt);
ypc.Load(p, bt); ypc.Load(p, bt);
} }
void ElGamalCryptoPublicKey::SavePrecomputation(BufferedTransformation &bt) const void ElGamalCryptoPublicKey::SavePrecomputation(BufferedTransformation &bt) const
{ {
gpc.Save(bt); gpc.Save(bt);
ypc.Save(bt); ypc.Save(bt);
} }
void ElGamalCryptoPublicKey::Encrypt(RandomNumberGenerator &rng, const byte *plainText, unsigned int plainTextLength, byte *cipherText) void ElGamalCryptoPublicKey::Encrypt(RandomNumberGenerator &rng, const byte *plainText, unsigned int plainTextLength, byte *cipherText)
{ {
assert(plainTextLength <= MaxPlainTextLength()); assert(plainTextLength <= MaxPlainTextLength());
SecByteBlock block(modulusLen-1); SecByteBlock block(modulusLen-1);
rng.GetBlock(block, modulusLen-2-plainTextLength); rng.GetBlock(block, modulusLen-2-plainTextLength);
memcpy(block+modulusLen-2-plainTextLength, plainText, plainTextLength); memcpy(block+modulusLen-2-plainTextLength, plainText, plainTextLength);
block[modulusLen-2] = plainTextLength; block[modulusLen-2] = plainTextLength;
Integer m(block, modulusLen-1); Integer m(block, modulusLen-1);
Integer a,b; Integer a,b;
RawEncrypt(Integer(rng, ExponentBitLength()), m, a, b); RawEncrypt(Integer(rng, ExponentBitLength()), m, a, b);
a.Encode(cipherText, modulusLen); a.Encode(cipherText, modulusLen);
b.Encode(cipherText+modulusLen, modulusLen); b.Encode(cipherText+modulusLen, modulusLen);
} }
void ElGamalCryptoPublicKey::RawEncrypt(const Integer &k, const Integer &m, Integer &a, Integer &b) const void ElGamalCryptoPublicKey::RawEncrypt(const Integer &k, const Integer &m, Integer &a, Integer &b) const
{ {
// a = a_exp_b_mod_c(g, k, p); // a = a_exp_b_mod_c(g, k, p);
// b = m * a_exp_b_mod_c(y, k, p) % p; // b = m * a_exp_b_mod_c(y, k, p) % p;
a = gpc.Exponentiate(k); a = gpc.Exponentiate(k);
b = m * ypc.Exponentiate(k) % p; b = m * ypc.Exponentiate(k) % p;
} }
unsigned int ElGamalCryptoPublicKey::ExponentBitLength() const unsigned int ElGamalCryptoPublicKey::ExponentBitLength() const
{ {
return 2*DiscreteLogWorkFactor(p.BitCount()); return 2*DiscreteLogWorkFactor(p.BitCount());
} }
// ************************************************************* // *************************************************************
ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(const Integer &p, const Integer &g, const Integer &y, const Integer &x) ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(const Integer &p, const Integer &g, const Integer &y, const Integer &x)
: ElGamalCryptoPublicKey(p, g, y), x(x) : ElGamalCryptoPublicKey(p, g, y), x(x)
{ {
} }
ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, unsigned int pbits) ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, unsigned int pbits)
{ {
PrimeAndGenerator pg(1, rng, pbits); PrimeAndGenerator pg(1, rng, pbits);
p = pg.Prime(); p = pg.Prime();
modulusLen=p.ByteCount(); modulusLen=p.ByteCount();
g = pg.Generator(); g = pg.Generator();
x.Randomize(rng, ExponentBitLength()); x.Randomize(rng, ExponentBitLength());
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
y = gpc.Exponentiate(x); y = gpc.Exponentiate(x);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
} }
ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, const Integer &pIn, const Integer &gIn) ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, const Integer &pIn, const Integer &gIn)
{ {
p = pIn; p = pIn;
modulusLen=p.ByteCount(); modulusLen=p.ByteCount();
g = gIn; g = gIn;
x.Randomize(rng, ExponentBitLength()); x.Randomize(rng, ExponentBitLength());
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
y = gpc.Exponentiate(x); y = gpc.Exponentiate(x);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
} }
ElGamalCryptoPrivateKey::~ElGamalCryptoPrivateKey() ElGamalCryptoPrivateKey::~ElGamalCryptoPrivateKey()
@ -121,191 +121,191 @@ ElGamalCryptoPrivateKey::~ElGamalCryptoPrivateKey()
ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(BufferedTransformation &bt) ElGamalCryptoPrivateKey::ElGamalCryptoPrivateKey(BufferedTransformation &bt)
{ {
BERSequenceDecoder seq(bt); BERSequenceDecoder seq(bt);
p.BERDecode(seq); p.BERDecode(seq);
modulusLen=p.ByteCount(); modulusLen=p.ByteCount();
g.BERDecode(seq); g.BERDecode(seq);
y.BERDecode(seq); y.BERDecode(seq);
x.BERDecode(seq); x.BERDecode(seq);
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
} }
void ElGamalCryptoPrivateKey::DEREncode(BufferedTransformation &bt) const void ElGamalCryptoPrivateKey::DEREncode(BufferedTransformation &bt) const
{ {
DERSequenceEncoder seq(bt); DERSequenceEncoder seq(bt);
p.DEREncode(seq); p.DEREncode(seq);
g.DEREncode(seq); g.DEREncode(seq);
y.DEREncode(seq); y.DEREncode(seq);
x.DEREncode(seq); x.DEREncode(seq);
} }
unsigned int ElGamalCryptoPrivateKey::Decrypt(const byte *cipherText, byte *plainText) unsigned int ElGamalCryptoPrivateKey::Decrypt(const byte *cipherText, byte *plainText)
{ {
Integer a(cipherText, modulusLen); Integer a(cipherText, modulusLen);
Integer b(cipherText+modulusLen, modulusLen); Integer b(cipherText+modulusLen, modulusLen);
Integer m; Integer m;
RawDecrypt(a, b, m); RawDecrypt(a, b, m);
m.Encode(plainText, 1); m.Encode(plainText, 1);
unsigned int plainTextLength = plainText[0]; unsigned int plainTextLength = plainText[0];
if (plainTextLength > MaxPlainTextLength()) if (plainTextLength > MaxPlainTextLength())
return 0; return 0;
m >>= 8; m >>= 8;
m.Encode(plainText, plainTextLength); m.Encode(plainText, plainTextLength);
return plainTextLength; return plainTextLength;
} }
void ElGamalCryptoPrivateKey::RawDecrypt(const Integer &a, const Integer &b, Integer &m) const void ElGamalCryptoPrivateKey::RawDecrypt(const Integer &a, const Integer &b, Integer &m) const
{ {
if (x.BitCount()+20 < p.BitCount()) // if x is short if (x.BitCount()+20 < p.BitCount()) // if x is short
m = b * EuclideanMultiplicativeInverse(a_exp_b_mod_c(a, x, p), p) % p; m = b * EuclideanMultiplicativeInverse(a_exp_b_mod_c(a, x, p), p) % p;
else // save a multiplicative inverse calculation else // save a multiplicative inverse calculation
m = b * a_exp_b_mod_c(a, p-1-x, p) % p; m = b * a_exp_b_mod_c(a, p-1-x, p) % p;
} }
// ****************************************************************** // ******************************************************************
ElGamalSigPublicKey::ElGamalSigPublicKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y) ElGamalSigPublicKey::ElGamalSigPublicKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y)
: p(p), q(q), g(g), y(y), qLen(q.ByteCount()), : p(p), q(q), g(g), y(y), qLen(q.ByteCount()),
gpc(p, g, ExponentBitLength(), 1), ypc(p, y, ExponentBitLength(), 1) gpc(p, g, ExponentBitLength(), 1), ypc(p, y, ExponentBitLength(), 1)
{ {
} }
ElGamalSigPublicKey::ElGamalSigPublicKey(BufferedTransformation &bt) ElGamalSigPublicKey::ElGamalSigPublicKey(BufferedTransformation &bt)
{ {
BERSequenceDecoder seq(bt); BERSequenceDecoder seq(bt);
p.BERDecode(seq); p.BERDecode(seq);
q.BERDecode(seq); q.BERDecode(seq);
g.BERDecode(seq); g.BERDecode(seq);
y.BERDecode(seq); y.BERDecode(seq);
qLen = q.ByteCount(); qLen = q.ByteCount();
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
} }
void ElGamalSigPublicKey::DEREncode(BufferedTransformation &bt) const void ElGamalSigPublicKey::DEREncode(BufferedTransformation &bt) const
{ {
DERSequenceEncoder seq(bt); DERSequenceEncoder seq(bt);
p.DEREncode(seq); p.DEREncode(seq);
q.DEREncode(seq); q.DEREncode(seq);
g.DEREncode(seq); g.DEREncode(seq);
y.DEREncode(seq); y.DEREncode(seq);
} }
void ElGamalSigPublicKey::Precompute(unsigned int precomputationStorage) void ElGamalSigPublicKey::Precompute(unsigned int precomputationStorage)
{ {
gpc.Precompute(p, g, ExponentBitLength(), precomputationStorage); gpc.Precompute(p, g, ExponentBitLength(), precomputationStorage);
ypc.Precompute(p, y, ExponentBitLength(), precomputationStorage); ypc.Precompute(p, y, ExponentBitLength(), precomputationStorage);
} }
void ElGamalSigPublicKey::LoadPrecomputation(BufferedTransformation &bt) void ElGamalSigPublicKey::LoadPrecomputation(BufferedTransformation &bt)
{ {
gpc.Load(p, bt); gpc.Load(p, bt);
ypc.Load(p, bt); ypc.Load(p, bt);
} }
void ElGamalSigPublicKey::SavePrecomputation(BufferedTransformation &bt) const void ElGamalSigPublicKey::SavePrecomputation(BufferedTransformation &bt) const
{ {
gpc.Save(bt); gpc.Save(bt);
ypc.Save(bt); ypc.Save(bt);
} }
bool ElGamalSigPublicKey::Verify(const byte *message, unsigned int messageLen, const byte *signature) bool ElGamalSigPublicKey::Verify(const byte *message, unsigned int messageLen, const byte *signature)
{ {
assert(messageLen <= MaxMessageLength()); assert(messageLen <= MaxMessageLength());
Integer m(message, messageLen); Integer m(message, messageLen);
Integer r(signature, qLen); Integer r(signature, qLen);
Integer s(signature+qLen, qLen); Integer s(signature+qLen, qLen);
return RawVerify(m, r, s); return RawVerify(m, r, s);
} }
bool ElGamalSigPublicKey::RawVerify(const Integer &m, const Integer &r, const Integer &s) const bool ElGamalSigPublicKey::RawVerify(const Integer &m, const Integer &r, const Integer &s) const
{ {
// check r != 0 && r == (g^s * y^r + m) mod q // check r != 0 && r == (g^s * y^r + m) mod q
return !!r && r == (gpc.CascadeExponentiate(s, ypc, r) + m) % q; return !!r && r == (gpc.CascadeExponentiate(s, ypc, r) + m) % q;
} }
unsigned int ElGamalSigPublicKey::ExponentBitLength() const unsigned int ElGamalSigPublicKey::ExponentBitLength() const
{ {
return q.BitCount(); return q.BitCount();
} }
// ************************************************************* // *************************************************************
ElGamalSigPrivateKey::ElGamalSigPrivateKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y, const Integer &x) ElGamalSigPrivateKey::ElGamalSigPrivateKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y, const Integer &x)
: ElGamalSigPublicKey(p, q, g, y), x(x) : ElGamalSigPublicKey(p, q, g, y), x(x)
{ {
} }
ElGamalSigPrivateKey::ElGamalSigPrivateKey(RandomNumberGenerator &rng, unsigned int pbits) ElGamalSigPrivateKey::ElGamalSigPrivateKey(RandomNumberGenerator &rng, unsigned int pbits)
{ {
PrimeAndGenerator pg(1, rng, pbits, 2*DiscreteLogWorkFactor(pbits)); PrimeAndGenerator pg(1, rng, pbits, 2*DiscreteLogWorkFactor(pbits));
p = pg.Prime(); p = pg.Prime();
q = pg.SubPrime(); q = pg.SubPrime();
g = pg.Generator(); g = pg.Generator();
x.Randomize(rng, 2, q-2, Integer::ANY); x.Randomize(rng, 2, q-2, Integer::ANY);
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
y = gpc.Exponentiate(x); y = gpc.Exponentiate(x);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
qLen = q.ByteCount(); qLen = q.ByteCount();
} }
ElGamalSigPrivateKey::ElGamalSigPrivateKey(RandomNumberGenerator &rng, const Integer &pIn, const Integer &qIn, const Integer &gIn) ElGamalSigPrivateKey::ElGamalSigPrivateKey(RandomNumberGenerator &rng, const Integer &pIn, const Integer &qIn, const Integer &gIn)
{ {
p = pIn; p = pIn;
q = qIn; q = qIn;
g = gIn; g = gIn;
x.Randomize(rng, 2, q-2, Integer::ANY); x.Randomize(rng, 2, q-2, Integer::ANY);
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
y = gpc.Exponentiate(x); y = gpc.Exponentiate(x);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
qLen = q.ByteCount(); qLen = q.ByteCount();
} }
ElGamalSigPrivateKey::ElGamalSigPrivateKey(BufferedTransformation &bt) ElGamalSigPrivateKey::ElGamalSigPrivateKey(BufferedTransformation &bt)
{ {
BERSequenceDecoder seq(bt); BERSequenceDecoder seq(bt);
p.BERDecode(seq); p.BERDecode(seq);
q.BERDecode(seq); q.BERDecode(seq);
g.BERDecode(seq); g.BERDecode(seq);
y.BERDecode(seq); y.BERDecode(seq);
x.BERDecode(seq); x.BERDecode(seq);
gpc.Precompute(p, g, ExponentBitLength(), 1); gpc.Precompute(p, g, ExponentBitLength(), 1);
ypc.Precompute(p, y, ExponentBitLength(), 1); ypc.Precompute(p, y, ExponentBitLength(), 1);
qLen = q.ByteCount(); qLen = q.ByteCount();
} }
void ElGamalSigPrivateKey::DEREncode(BufferedTransformation &bt) const void ElGamalSigPrivateKey::DEREncode(BufferedTransformation &bt) const
{ {
DERSequenceEncoder seq(bt); DERSequenceEncoder seq(bt);
p.DEREncode(seq); p.DEREncode(seq);
q.DEREncode(seq); q.DEREncode(seq);
g.DEREncode(seq); g.DEREncode(seq);
y.DEREncode(seq); y.DEREncode(seq);
x.DEREncode(seq); x.DEREncode(seq);
} }
void ElGamalSigPrivateKey::Sign(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature) void ElGamalSigPrivateKey::Sign(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature)
{ {
assert(messageLen <= MaxMessageLength()); assert(messageLen <= MaxMessageLength());
Integer m(message, messageLen); Integer m(message, messageLen);
Integer r; Integer r;
Integer s; Integer s;
RawSign(rng, m, r, s); RawSign(rng, m, r, s);
r.Encode(signature, qLen); r.Encode(signature, qLen);
s.Encode(signature+qLen, qLen); s.Encode(signature+qLen, qLen);
} }
void ElGamalSigPrivateKey::RawSign(RandomNumberGenerator &rng, const Integer &m, Integer &r, Integer &s) const void ElGamalSigPrivateKey::RawSign(RandomNumberGenerator &rng, const Integer &m, Integer &r, Integer &s) const
{ {
do do
{ {
Integer k(rng, 2, q-2, Integer::ANY); Integer k(rng, 2, q-2, Integer::ANY);
r = (gpc.Exponentiate(k) + m) % q; r = (gpc.Exponentiate(k) + m) % q;
s = (k - x*r) % q; s = (k - x*r) % q;
} while (!r); // make sure r != 0 } while (!r); // make sure r != 0
} }

View File

@ -6,70 +6,70 @@
class ElGamalCryptoPublicKey : public PK_WithPrecomputation<PK_FixedLengthEncryptor> class ElGamalCryptoPublicKey : public PK_WithPrecomputation<PK_FixedLengthEncryptor>
{ {
public: public:
ElGamalCryptoPublicKey(const Integer &p, const Integer &g, const Integer &y); ElGamalCryptoPublicKey(const Integer &p, const Integer &g, const Integer &y);
ElGamalCryptoPublicKey(BufferedTransformation &bt); ElGamalCryptoPublicKey(BufferedTransformation &bt);
~ElGamalCryptoPublicKey(); ~ElGamalCryptoPublicKey();
void DEREncode(BufferedTransformation &bt) const; void DEREncode(BufferedTransformation &bt) const;
void Precompute(unsigned int precomputationStorage=16); void Precompute(unsigned int precomputationStorage=16);
void LoadPrecomputation(BufferedTransformation &storedPrecomputation); void LoadPrecomputation(BufferedTransformation &storedPrecomputation);
void SavePrecomputation(BufferedTransformation &storedPrecomputation) const; void SavePrecomputation(BufferedTransformation &storedPrecomputation) const;
void Encrypt(RandomNumberGenerator &rng, const byte *plainText, unsigned int plainTextLength, byte *cipherText); void Encrypt(RandomNumberGenerator &rng, const byte *plainText, unsigned int plainTextLength, byte *cipherText);
unsigned int MaxPlainTextLength() const {return STDMIN(255U, modulusLen-3);} unsigned int MaxPlainTextLength() const {return STDMIN(255U, modulusLen-3);}
unsigned int CipherTextLength() const {return 2*modulusLen;} unsigned int CipherTextLength() const {return 2*modulusLen;}
protected: protected:
ElGamalCryptoPublicKey() {} ElGamalCryptoPublicKey() {}
void RawEncrypt(const Integer &k, const Integer &m, Integer &a, Integer &b) const; void RawEncrypt(const Integer &k, const Integer &m, Integer &a, Integer &b) const;
unsigned int ExponentBitLength() const; unsigned int ExponentBitLength() const;
Integer p, g, y; Integer p, g, y;
unsigned int modulusLen; unsigned int modulusLen;
ModExpPrecomputation gpc, ypc; ModExpPrecomputation gpc, ypc;
}; };
class ElGamalCryptoPrivateKey : public ElGamalCryptoPublicKey, public PK_FixedLengthDecryptor class ElGamalCryptoPrivateKey : public ElGamalCryptoPublicKey, public PK_FixedLengthDecryptor
{ {
public: public:
ElGamalCryptoPrivateKey(const Integer &p, const Integer &g, const Integer &y, const Integer &x); ElGamalCryptoPrivateKey(const Integer &p, const Integer &g, const Integer &y, const Integer &x);
ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, unsigned int pbits); ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, unsigned int pbits);
// generate a random private key, given p and g // generate a random private key, given p and g
ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, const Integer &p, const Integer &g); ElGamalCryptoPrivateKey(RandomNumberGenerator &rng, const Integer &p, const Integer &g);
~ElGamalCryptoPrivateKey(); ~ElGamalCryptoPrivateKey();
ElGamalCryptoPrivateKey(BufferedTransformation &bt); ElGamalCryptoPrivateKey(BufferedTransformation &bt);
void DEREncode(BufferedTransformation &bt) const; void DEREncode(BufferedTransformation &bt) const;
unsigned int Decrypt(const byte *cipherText, byte *plainText); unsigned int Decrypt(const byte *cipherText, byte *plainText);
protected: protected:
void RawDecrypt(const Integer &a, const Integer &b, Integer &m) const; void RawDecrypt(const Integer &a, const Integer &b, Integer &m) const;
Integer x; Integer x;
}; };
class ElGamalSigPublicKey : public PK_WithPrecomputation<PK_Verifier> class ElGamalSigPublicKey : public PK_WithPrecomputation<PK_Verifier>
{ {
public: public:
ElGamalSigPublicKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y); ElGamalSigPublicKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y);
ElGamalSigPublicKey(BufferedTransformation &bt); ElGamalSigPublicKey(BufferedTransformation &bt);
void DEREncode(BufferedTransformation &bt) const; void DEREncode(BufferedTransformation &bt) const;
void Precompute(unsigned int precomputationStorage=16); void Precompute(unsigned int precomputationStorage=16);
void LoadPrecomputation(BufferedTransformation &storedPrecomputation); void LoadPrecomputation(BufferedTransformation &storedPrecomputation);
void SavePrecomputation(BufferedTransformation &storedPrecomputation) const; void SavePrecomputation(BufferedTransformation &storedPrecomputation) const;
bool Verify(const byte *message, unsigned int messageLen, const byte *signature); bool Verify(const byte *message, unsigned int messageLen, const byte *signature);
// message length for signature is unlimited, but only message digests should be signed // message length for signature is unlimited, but only message digests should be signed
unsigned int MaxMessageLength() const {return 0xffff;} unsigned int MaxMessageLength() const {return 0xffff;}
unsigned int SignatureLength() const {return 2*qLen;} unsigned int SignatureLength() const {return 2*qLen;}
const Integer& GetPrime() { return p; } const Integer& GetPrime() { return p; }
const Integer& GetParameterQ() { return q; } const Integer& GetParameterQ() { return q; }
@ -77,34 +77,34 @@ public:
const Integer& GetParameterY() { return y; } const Integer& GetParameterY() { return y; }
protected: protected:
ElGamalSigPublicKey() {} ElGamalSigPublicKey() {}
bool RawVerify(const Integer &m, const Integer &a, const Integer &b) const; bool RawVerify(const Integer &m, const Integer &a, const Integer &b) const;
unsigned int ExponentBitLength() const; unsigned int ExponentBitLength() const;
Integer p, q, g, y; Integer p, q, g, y;
unsigned int qLen; unsigned int qLen;
ModExpPrecomputation gpc, ypc; ModExpPrecomputation gpc, ypc;
}; };
class ElGamalSigPrivateKey : public ElGamalSigPublicKey, public PK_WithPrecomputation<PK_Signer> class ElGamalSigPrivateKey : public ElGamalSigPublicKey, public PK_WithPrecomputation<PK_Signer>
{ {
public: public:
ElGamalSigPrivateKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y, const Integer &x); ElGamalSigPrivateKey(const Integer &p, const Integer &q, const Integer &g, const Integer &y, const Integer &x);
ElGamalSigPrivateKey(RandomNumberGenerator &rng, unsigned int pbits); ElGamalSigPrivateKey(RandomNumberGenerator &rng, unsigned int pbits);
// generate a random private key, given p and g // generate a random private key, given p and g
ElGamalSigPrivateKey(RandomNumberGenerator &rng, const Integer &p, const Integer &q, const Integer &g); ElGamalSigPrivateKey(RandomNumberGenerator &rng, const Integer &p, const Integer &q, const Integer &g);
ElGamalSigPrivateKey(BufferedTransformation &bt); ElGamalSigPrivateKey(BufferedTransformation &bt);
void DEREncode(BufferedTransformation &bt) const; void DEREncode(BufferedTransformation &bt) const;
void Sign(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature); void Sign(RandomNumberGenerator &rng, const byte *message, unsigned int messageLen, byte *signature);
const Integer& GetParameterX() { return x; } const Integer& GetParameterX() { return x; }
protected: protected:
void RawSign(RandomNumberGenerator &rng, const Integer &m, Integer &a, Integer &b) const; void RawSign(RandomNumberGenerator &rng, const Integer &m, Integer &a, Integer &b) const;
Integer x; Integer x;
}; };
#endif #endif

View File

@ -7,58 +7,58 @@ USING_NAMESPACE(std)
template <class T> void ExponentiationPrecomputation<T>::Precompute(const Element &base, unsigned int maxExpBits) template <class T> void ExponentiationPrecomputation<T>::Precompute(const Element &base, unsigned int maxExpBits)
{ {
assert(storage <= maxExpBits); assert(storage <= maxExpBits);
exponentBase = Integer::Power2((maxExpBits+storage-1)/storage); exponentBase = Integer::Power2((maxExpBits+storage-1)/storage);
g[0] = base; g[0] = base;
for (unsigned i=1; i<storage; i++) for (unsigned i=1; i<storage; i++)
g[i] = group.IntMultiply(g[i-1], exponentBase); g[i] = group.IntMultiply(g[i-1], exponentBase);
} }
template <class T> typename ExponentiationPrecomputation<T>::Element ExponentiationPrecomputation<T>::Exponentiate(const Integer &exponent) const template <class T> typename ExponentiationPrecomputation<T>::Element ExponentiationPrecomputation<T>::Exponentiate(const Integer &exponent) const
{ {
vector<pair<Integer, Element> > eb(storage); // array of segments of the exponent and precalculated bases vector<pair<Integer, Element> > eb(storage); // array of segments of the exponent and precalculated bases
Integer temp, e = exponent; Integer temp, e = exponent;
unsigned i; unsigned i;
for (i=0; i+1<storage; i++) for (i=0; i+1<storage; i++)
{ {
Integer::Divide(eb[i].first, temp, e, exponentBase); Integer::Divide(eb[i].first, temp, e, exponentBase);
swap(temp, e); swap(temp, e);
eb[i].second = g[i]; eb[i].second = g[i];
} }
eb[i].first = e; eb[i].first = e;
eb[i].second = g[i]; eb[i].second = g[i];
return GeneralCascadeMultiplication<Element>(group, eb.begin(), eb.end()); return GeneralCascadeMultiplication<Element>(group, eb.begin(), eb.end());
} }
template <class T> typename ExponentiationPrecomputation<T>::Element template <class T> typename ExponentiationPrecomputation<T>::Element
ExponentiationPrecomputation<T>::CascadeExponentiate(const Integer &exponent, ExponentiationPrecomputation<T>::CascadeExponentiate(const Integer &exponent,
const ExponentiationPrecomputation<T> &pc2, const Integer &exponent2) const const ExponentiationPrecomputation<T> &pc2, const Integer &exponent2) const
{ {
vector<pair<Integer, Element> > eb(storage+pc2.storage); // array of segments of the exponent and precalculated bases vector<pair<Integer, Element> > eb(storage+pc2.storage); // array of segments of the exponent and precalculated bases
Integer temp, e = exponent; Integer temp, e = exponent;
unsigned i; unsigned i;
for (i=0; i+1<storage; i++) for (i=0; i+1<storage; i++)
{ {
Integer::Divide(eb[i].first, temp, e, exponentBase); Integer::Divide(eb[i].first, temp, e, exponentBase);
swap(temp, e); swap(temp, e);
eb[i].second = g[i]; eb[i].second = g[i];
} }
eb[i].first = e; eb[i].first = e;
eb[i].second = g[i]; eb[i].second = g[i];
e = exponent2; e = exponent2;
for (i=storage; i+1<storage+pc2.storage; i++) for (i=storage; i+1<storage+pc2.storage; i++)
{ {
Integer::Divide(eb[i].first, temp, e, exponentBase); Integer::Divide(eb[i].first, temp, e, exponentBase);
swap(temp, e); swap(temp, e);
eb[i].second = pc2.g[i-storage]; eb[i].second = pc2.g[i-storage];
} }
eb[i].first = e; eb[i].first = e;
eb[i].second = pc2.g[i-storage]; eb[i].second = pc2.g[i-storage];
return GeneralCascadeMultiplication<Element>(group, eb.begin(), eb.end()); return GeneralCascadeMultiplication<Element>(group, eb.begin(), eb.end());
} }

View File

@ -15,25 +15,25 @@
template <class T> class ExponentiationPrecomputation template <class T> class ExponentiationPrecomputation
{ {
public: public:
typedef T Group; typedef T Group;
typedef typename Group::Element Element; typedef typename Group::Element Element;
ExponentiationPrecomputation(const Group &group) : group(group) {} ExponentiationPrecomputation(const Group &group) : group(group) {}
ExponentiationPrecomputation(const Group &group, const Element &base, unsigned int maxExpBits, unsigned int storage) ExponentiationPrecomputation(const Group &group, const Element &base, unsigned int maxExpBits, unsigned int storage)
: group(group), storage(storage), g(storage) {Precompute(base, maxExpBits);} : group(group), storage(storage), g(storage) {Precompute(base, maxExpBits);}
ExponentiationPrecomputation(const Group &group, const ExponentiationPrecomputation &pc) ExponentiationPrecomputation(const Group &group, const ExponentiationPrecomputation &pc)
: group(group), storage(pc.storage), exponentBase(pc.exponentBase), g(pc.g) {} : group(group), storage(pc.storage), exponentBase(pc.exponentBase), g(pc.g) {}
void Precompute(const Element &base, unsigned int maxExpBits); void Precompute(const Element &base, unsigned int maxExpBits);
Element Exponentiate(const Integer &exponent) const; Element Exponentiate(const Integer &exponent) const;
Element CascadeExponentiate(const Integer &exponent, const ExponentiationPrecomputation<Group> &pc2, const Integer &exponent2) const; Element CascadeExponentiate(const Integer &exponent, const ExponentiationPrecomputation<Group> &pc2, const Integer &exponent2) const;
const Group &group; const Group &group;
unsigned int storage; // number of precalculated bases unsigned int storage; // number of precalculated bases
Integer exponentBase; // what base to represent the exponent in Integer exponentBase; // what base to represent the exponent in
std::vector<Element> g; // precalculated bases std::vector<Element> g; // precalculated bases
}; };
#endif #endif

View File

@ -6,92 +6,92 @@
#include <memory> #include <memory>
Filter::Filter(BufferedTransformation *outQ) Filter::Filter(BufferedTransformation *outQ)
: outQueue(outQ ? outQ : new ByteQueue) : outQueue(outQ ? outQ : new ByteQueue)
{ {
} }
Filter::Filter(const Filter &source) Filter::Filter(const Filter &source)
: outQueue(new ByteQueue) : outQueue(new ByteQueue)
{ {
} }
void Filter::Detach(BufferedTransformation *newOut) void Filter::Detach(BufferedTransformation *newOut)
{ {
std::auto_ptr<BufferedTransformation> out(newOut ? newOut : new ByteQueue); std::auto_ptr<BufferedTransformation> out(newOut ? newOut : new ByteQueue);
outQueue->Close(); outQueue->Close();
outQueue->TransferTo(*out); outQueue->TransferTo(*out);
outQueue.reset(out.release()); outQueue.reset(out.release());
} }
void Filter::Attach(BufferedTransformation *newOut) void Filter::Attach(BufferedTransformation *newOut)
{ {
if (outQueue->Attachable()) if (outQueue->Attachable())
outQueue->Attach(newOut); outQueue->Attach(newOut);
else else
Detach(newOut); Detach(newOut);
} }
BlockFilterBase::BlockFilterBase(BlockTransformation &c, BlockFilterBase::BlockFilterBase(BlockTransformation &c,
BufferedTransformation *outQ) BufferedTransformation *outQ)
: Filter(outQ), cipher(c), S(cipher.BlockSize()), inBuf(S) : Filter(outQ), cipher(c), S(cipher.BlockSize()), inBuf(S)
{ {
inBufSize=0; inBufSize=0;
} }
void BlockFilterBase::ProcessBuf() void BlockFilterBase::ProcessBuf()
{ {
cipher.ProcessBlock(inBuf); cipher.ProcessBlock(inBuf);
outQueue->Put(inBuf, S); outQueue->Put(inBuf, S);
inBufSize=0; inBufSize=0;
} }
void BlockFilterBase::Put(const byte *inString, unsigned int length) void BlockFilterBase::Put(const byte *inString, unsigned int length)
{ {
while (length--) while (length--)
BlockFilterBase::Put(*inString++); BlockFilterBase::Put(*inString++);
} }
void BlockEncryptionFilter::InputFinished() void BlockEncryptionFilter::InputFinished()
{ {
if (inBufSize == S) if (inBufSize == S)
ProcessBuf(); ProcessBuf();
// pad last block // pad last block
memset(inBuf+inBufSize, S-inBufSize, S-inBufSize); memset(inBuf+inBufSize, S-inBufSize, S-inBufSize);
ProcessBuf(); ProcessBuf();
} }
void BlockDecryptionFilter::InputFinished() void BlockDecryptionFilter::InputFinished()
{ {
cipher.ProcessBlock(inBuf); cipher.ProcessBlock(inBuf);
if (inBuf[S-1] > S) if (inBuf[S-1] > S)
inBuf[S-1] = 0; // something's wrong with the padding inBuf[S-1] = 0; // something's wrong with the padding
outQueue->Put(inBuf, S-inBuf[S-1]); outQueue->Put(inBuf, S-inBuf[S-1]);
inBufSize=0; inBufSize=0;
} }
void StreamCipherFilter::Put(const byte *inString, unsigned int length) void StreamCipherFilter::Put(const byte *inString, unsigned int length)
{ {
SecByteBlock temp(length); SecByteBlock temp(length);
cipher.ProcessString(temp, inString, length); cipher.ProcessString(temp, inString, length);
outQueue->Put(temp, length); outQueue->Put(temp, length);
} }
void HashFilter::InputFinished() void HashFilter::InputFinished()
{ {
SecByteBlock buf(hash.DigestSize()); SecByteBlock buf(hash.DigestSize());
hash.Final(buf); hash.Final(buf);
outQueue->Put(buf, hash.DigestSize()); outQueue->Put(buf, hash.DigestSize());
} }
BufferedTransformation *Insert(const byte *in, unsigned int length, BufferedTransformation *outQueue) BufferedTransformation *Insert(const byte *in, unsigned int length, BufferedTransformation *outQueue)
{ {
outQueue->Put(in, length); outQueue->Put(in, length);
return outQueue; return outQueue;
} }
unsigned int Extract(Source *source, byte *out, unsigned int length) unsigned int Extract(Source *source, byte *out, unsigned int length)
{ {
while (source->MaxRetrieveable() < length && source->Pump(1)); while (source->MaxRetrieveable() < length && source->Pump(1));
return source->Get(out, length); return source->Get(out, length);
} }

View File

@ -8,149 +8,149 @@
class Filter : public BufferedTransformation class Filter : public BufferedTransformation
{ {
public: public:
Filter(BufferedTransformation *outQ = NULL); Filter(BufferedTransformation *outQ = NULL);
Filter(const Filter &source); Filter(const Filter &source);
bool Attachable() {return true;} bool Attachable() {return true;}
void Detach(BufferedTransformation *newOut = NULL); void Detach(BufferedTransformation *newOut = NULL);
void Attach(BufferedTransformation *newOut); void Attach(BufferedTransformation *newOut);
void Close() void Close()
{InputFinished(); outQueue->Close();} {InputFinished(); outQueue->Close();}
unsigned long MaxRetrieveable() unsigned long MaxRetrieveable()
{return outQueue->MaxRetrieveable();} {return outQueue->MaxRetrieveable();}
unsigned int Get(byte &outByte) unsigned int Get(byte &outByte)
{return outQueue->Get(outByte);} {return outQueue->Get(outByte);}
unsigned int Get(byte *outString, unsigned int getMax) unsigned int Get(byte *outString, unsigned int getMax)
{return outQueue->Get(outString, getMax);} {return outQueue->Get(outString, getMax);}
unsigned int Peek(byte &outByte) const unsigned int Peek(byte &outByte) const
{return outQueue->Peek(outByte);} {return outQueue->Peek(outByte);}
BufferedTransformation *OutQueue() {return outQueue.get();} BufferedTransformation *OutQueue() {return outQueue.get();}
protected: protected:
member_ptr<BufferedTransformation> outQueue; member_ptr<BufferedTransformation> outQueue;
private: private:
void operator=(const Filter &); // assignment not allowed void operator=(const Filter &); // assignment not allowed
}; };
class BlockFilterBase : public Filter class BlockFilterBase : public Filter
{ {
public: public:
BlockFilterBase(BlockTransformation &cipher, BlockFilterBase(BlockTransformation &cipher,
BufferedTransformation *outQueue); BufferedTransformation *outQueue);
virtual ~BlockFilterBase() {} virtual ~BlockFilterBase() {}
void Put(byte inByte) void Put(byte inByte)
{ {
if (inBufSize == S) if (inBufSize == S)
ProcessBuf(); ProcessBuf();
inBuf[inBufSize++]=inByte; inBuf[inBufSize++]=inByte;
} }
void Put(const byte *inString, unsigned int length); void Put(const byte *inString, unsigned int length);
protected: protected:
void ProcessBuf(); void ProcessBuf();
BlockTransformation &cipher; BlockTransformation &cipher;
const unsigned int S; const unsigned int S;
SecByteBlock inBuf; SecByteBlock inBuf;
unsigned int inBufSize; unsigned int inBufSize;
}; };
class BlockEncryptionFilter : public BlockFilterBase class BlockEncryptionFilter : public BlockFilterBase
{ {
public: public:
BlockEncryptionFilter(BlockTransformation &cipher, BufferedTransformation *outQueue = NULL) BlockEncryptionFilter(BlockTransformation &cipher, BufferedTransformation *outQueue = NULL)
: BlockFilterBase(cipher, outQueue) {} : BlockFilterBase(cipher, outQueue) {}
protected: protected:
void InputFinished(); void InputFinished();
}; };
class BlockDecryptionFilter : public BlockFilterBase class BlockDecryptionFilter : public BlockFilterBase
{ {
public: public:
BlockDecryptionFilter(BlockTransformation &cipher, BufferedTransformation *outQueue = NULL) BlockDecryptionFilter(BlockTransformation &cipher, BufferedTransformation *outQueue = NULL)
: BlockFilterBase(cipher, outQueue) {} : BlockFilterBase(cipher, outQueue) {}
protected: protected:
void InputFinished(); void InputFinished();
}; };
class StreamCipherFilter : public Filter class StreamCipherFilter : public Filter
{ {
public: public:
StreamCipherFilter(StreamCipher &c, StreamCipherFilter(StreamCipher &c,
BufferedTransformation *outQueue = NULL) BufferedTransformation *outQueue = NULL)
: Filter(outQueue), cipher(c) {} : Filter(outQueue), cipher(c) {}
void Put(byte inByte) void Put(byte inByte)
{outQueue->Put(cipher.ProcessByte(inByte));} {outQueue->Put(cipher.ProcessByte(inByte));}
void Put(const byte *inString, unsigned int length); void Put(const byte *inString, unsigned int length);
private: private:
StreamCipher &cipher; StreamCipher &cipher;
}; };
class HashFilter : public Filter class HashFilter : public Filter
{ {
public: public:
HashFilter(HashModule &hm, BufferedTransformation *outQueue = NULL) HashFilter(HashModule &hm, BufferedTransformation *outQueue = NULL)
: Filter(outQueue), hash(hm) {} : Filter(outQueue), hash(hm) {}
void InputFinished(); void InputFinished();
void Put(byte inByte) void Put(byte inByte)
{hash.Update(&inByte, 1);} {hash.Update(&inByte, 1);}
void Put(const byte *inString, unsigned int length) void Put(const byte *inString, unsigned int length)
{hash.Update(inString, length);} {hash.Update(inString, length);}
private: private:
HashModule &hash; HashModule &hash;
}; };
class Source : public Filter class Source : public Filter
{ {
public: public:
Source(BufferedTransformation *outQ = NULL) Source(BufferedTransformation *outQ = NULL)
: Filter(outQ) {} : Filter(outQ) {}
void Put(byte) void Put(byte)
{Pump(1);} {Pump(1);}
void Put(const byte *, unsigned int length) void Put(const byte *, unsigned int length)
{Pump(length);} {Pump(length);}
void InputFinished() void InputFinished()
{PumpAll();} {PumpAll();}
virtual unsigned int Pump(unsigned int size) =0; virtual unsigned int Pump(unsigned int size) =0;
virtual unsigned long PumpAll() =0; virtual unsigned long PumpAll() =0;
}; };
class Sink : public BufferedTransformation class Sink : public BufferedTransformation
{ {
public: public:
unsigned long MaxRetrieveable() unsigned long MaxRetrieveable()
{return 0;} {return 0;}
unsigned int Get(byte &) unsigned int Get(byte &)
{return 0;} {return 0;}
unsigned int Get(byte *, unsigned int) unsigned int Get(byte *, unsigned int)
{return 0;} {return 0;}
unsigned int Peek(byte &) const unsigned int Peek(byte &) const
{return 0;} {return 0;}
}; };
class BitBucket : public Sink class BitBucket : public Sink
{ {
public: public:
void Put(byte) {} void Put(byte) {}
void Put(const byte *, unsigned int) {} void Put(const byte *, unsigned int) {}
}; };
BufferedTransformation *Insert(const byte *in, unsigned int length, BufferedTransformation *outQueue); BufferedTransformation *Insert(const byte *in, unsigned int length, BufferedTransformation *outQueue);

View File

@ -6,132 +6,132 @@
#include <memory> #include <memory>
Fork::Fork(int n, BufferedTransformation *const *givenOutPorts) Fork::Fork(int n, BufferedTransformation *const *givenOutPorts)
: numberOfPorts(n), outPorts(n) : numberOfPorts(n), outPorts(n)
{ {
currentPort = 0; currentPort = 0;
for (unsigned int i=0; i<numberOfPorts; i++) for (unsigned int i=0; i<numberOfPorts; i++)
outPorts[i].reset(givenOutPorts ? givenOutPorts[i] : new ByteQueue); outPorts[i].reset(givenOutPorts ? givenOutPorts[i] : new ByteQueue);
} }
void Fork::SelectOutPort(int portNumber) void Fork::SelectOutPort(int portNumber)
{ {
currentPort = portNumber; currentPort = portNumber;
} }
void Fork::Detach(BufferedTransformation *newOut) void Fork::Detach(BufferedTransformation *newOut)
{ {
std::auto_ptr<BufferedTransformation> out(newOut ? newOut : new ByteQueue); std::auto_ptr<BufferedTransformation> out(newOut ? newOut : new ByteQueue);
outPorts[currentPort]->Close(); outPorts[currentPort]->Close();
outPorts[currentPort]->TransferTo(*out); outPorts[currentPort]->TransferTo(*out);
outPorts[currentPort].reset(out.release()); outPorts[currentPort].reset(out.release());
} }
void Fork::Attach(BufferedTransformation *newOut) void Fork::Attach(BufferedTransformation *newOut)
{ {
if (outPorts[currentPort]->Attachable()) if (outPorts[currentPort]->Attachable())
outPorts[currentPort]->Attach(newOut); outPorts[currentPort]->Attach(newOut);
else else
Detach(newOut); Detach(newOut);
} }
void Fork::Close() void Fork::Close()
{ {
InputFinished(); InputFinished();
for (unsigned int i=0; i<numberOfPorts; i++) for (unsigned int i=0; i<numberOfPorts; i++)
outPorts[i]->Close(); outPorts[i]->Close();
} }
void Fork::Put(byte inByte) void Fork::Put(byte inByte)
{ {
for (unsigned int i=0; i<numberOfPorts; i++) for (unsigned int i=0; i<numberOfPorts; i++)
outPorts[i]->Put(inByte); outPorts[i]->Put(inByte);
} }
void Fork::Put(const byte *inString, unsigned int length) void Fork::Put(const byte *inString, unsigned int length)
{ {
for (unsigned int i=0; i<numberOfPorts; i++) for (unsigned int i=0; i<numberOfPorts; i++)
outPorts[i]->Put(inString, length); outPorts[i]->Put(inString, length);
} }
// ******************************************************** // ********************************************************
Join::Join(unsigned int n, BufferedTransformation *outQ) Join::Join(unsigned int n, BufferedTransformation *outQ)
: Filter(outQ), : Filter(outQ),
numberOfPorts(n), numberOfPorts(n),
inPorts(n), inPorts(n),
interfacesOpen(n), interfacesOpen(n),
interfaces(n) interfaces(n)
{ {
for (unsigned int i=0; i<numberOfPorts; i++) for (unsigned int i=0; i<numberOfPorts; i++)
{ {
inPorts[i].reset(new ByteQueue); inPorts[i].reset(new ByteQueue);
interfaces[i].reset(new Interface(*this, *inPorts[i], i)); interfaces[i].reset(new Interface(*this, *inPorts[i], i));
} }
} }
Interface * Join::ReleaseInterface(unsigned int i) Interface * Join::ReleaseInterface(unsigned int i)
{ {
return interfaces[i].release(); return interfaces[i].release();
} }
void Join::NotifyInput(unsigned int i, unsigned int /* length */) void Join::NotifyInput(unsigned int i, unsigned int /* length */)
{ {
AccessPort(i).TransferTo(*outQueue); AccessPort(i).TransferTo(*outQueue);
} }
void Join::NotifyClose(unsigned int /* id */) void Join::NotifyClose(unsigned int /* id */)
{ {
if ((--interfacesOpen) == 0) if ((--interfacesOpen) == 0)
outQueue->Close(); outQueue->Close();
} }
// ******************************************************** // ********************************************************
void Interface::Put(byte inByte) void Interface::Put(byte inByte)
{ {
bq.Put(inByte); bq.Put(inByte);
parent.NotifyInput(id, 1); parent.NotifyInput(id, 1);
} }
void Interface::Put(const byte *inString, unsigned int length) void Interface::Put(const byte *inString, unsigned int length)
{ {
bq.Put(inString, length); bq.Put(inString, length);
parent.NotifyInput(id, length); parent.NotifyInput(id, length);
} }
unsigned long Interface::MaxRetrieveable() unsigned long Interface::MaxRetrieveable()
{ {
return parent.MaxRetrieveable(); return parent.MaxRetrieveable();
} }
void Interface::Close() void Interface::Close()
{ {
parent.NotifyClose(id); parent.NotifyClose(id);
} }
void Interface::Detach(BufferedTransformation *bt) void Interface::Detach(BufferedTransformation *bt)
{ {
parent.Detach(bt); parent.Detach(bt);
} }
void Interface::Attach(BufferedTransformation *bt) void Interface::Attach(BufferedTransformation *bt)
{ {
parent.Attach(bt); parent.Attach(bt);
} }
unsigned int Interface::Get(byte &outByte) unsigned int Interface::Get(byte &outByte)
{ {
return parent.Get(outByte); return parent.Get(outByte);
} }
unsigned int Interface::Get(byte *outString, unsigned int getMax) unsigned int Interface::Get(byte *outString, unsigned int getMax)
{ {
return parent.Get(outString, getMax); return parent.Get(outString, getMax);
} }
unsigned int Interface::Peek(byte &outByte) const unsigned int Interface::Peek(byte &outByte) const
{ {
return parent.Peek(outByte); return parent.Peek(outByte);
} }

View File

@ -8,39 +8,39 @@
class Fork : public BufferedTransformation class Fork : public BufferedTransformation
{ {
public: public:
Fork(int number_of_outports, BufferedTransformation *const *outports = NULL); Fork(int number_of_outports, BufferedTransformation *const *outports = NULL);
void SelectOutPort(int portNumber); void SelectOutPort(int portNumber);
bool Attachable() {return true;} bool Attachable() {return true;}
void Detach(BufferedTransformation *newOut = NULL); void Detach(BufferedTransformation *newOut = NULL);
void Attach(BufferedTransformation *newOut); void Attach(BufferedTransformation *newOut);
virtual void Close(); virtual void Close();
unsigned long MaxRetrieveable() unsigned long MaxRetrieveable()
{return outPorts[currentPort]->MaxRetrieveable();} {return outPorts[currentPort]->MaxRetrieveable();}
// virtual void InputFinished() // virtual void InputFinished()
// {outPorts[currentPort]->InputFinished();} // {outPorts[currentPort]->InputFinished();}
unsigned int Get(byte &outByte) unsigned int Get(byte &outByte)
{return outPorts[currentPort]->Get(outByte);} {return outPorts[currentPort]->Get(outByte);}
unsigned int Get(byte *outString, unsigned int getMax) unsigned int Get(byte *outString, unsigned int getMax)
{return outPorts[currentPort]->Get(outString, getMax);} {return outPorts[currentPort]->Get(outString, getMax);}
unsigned int Peek(byte &outByte) const unsigned int Peek(byte &outByte) const
{return outPorts[currentPort]->Peek(outByte);} {return outPorts[currentPort]->Peek(outByte);}
virtual void Put(byte inByte); virtual void Put(byte inByte);
virtual void Put(const byte *inString, unsigned int length); virtual void Put(const byte *inString, unsigned int length);
protected: protected:
unsigned int NumberOfPorts() const {return numberOfPorts;} unsigned int NumberOfPorts() const {return numberOfPorts;}
BufferedTransformation& AccessPort(unsigned int i) {return *outPorts[i];} BufferedTransformation& AccessPort(unsigned int i) {return *outPorts[i];}
private: private:
Fork(const Fork &); // no copying allowed Fork(const Fork &); // no copying allowed
unsigned int numberOfPorts, currentPort; unsigned int numberOfPorts, currentPort;
vector_member_ptrs<BufferedTransformation> outPorts; vector_member_ptrs<BufferedTransformation> outPorts;
}; };
class Join; class Join;
@ -48,57 +48,57 @@ class Join;
class Interface : public BufferedTransformation class Interface : public BufferedTransformation
{ {
public: public:
Interface(Join &p, ByteQueue &b, int i) Interface(Join &p, ByteQueue &b, int i)
: parent(p), bq(b), id(i) {} : parent(p), bq(b), id(i) {}
unsigned long MaxRetrieveable(); unsigned long MaxRetrieveable();
void Close(); void Close();
bool Attachable() {return true;} bool Attachable() {return true;}
void Detach(BufferedTransformation *bt); void Detach(BufferedTransformation *bt);
void Attach(BufferedTransformation *bt); void Attach(BufferedTransformation *bt);
void Put(byte inByte); void Put(byte inByte);
void Put(const byte *inString, unsigned int length); void Put(const byte *inString, unsigned int length);
unsigned int Get(byte &outByte); unsigned int Get(byte &outByte);
unsigned int Get(byte *outString, unsigned int getMax); unsigned int Get(byte *outString, unsigned int getMax);
unsigned int Peek(byte &outByte) const; unsigned int Peek(byte &outByte) const;
private: private:
Join &parent; Join &parent;
ByteQueue &bq; ByteQueue &bq;
const int id; const int id;
}; };
class Join : public Filter class Join : public Filter
{ {
public: public:
Join(unsigned int number_of_inports, BufferedTransformation *outQ = NULL); Join(unsigned int number_of_inports, BufferedTransformation *outQ = NULL);
// Note that ReleaseInterface is similar but not completely compatible // Note that ReleaseInterface is similar but not completely compatible
// with SelectInterface of version 2.0. ReleaseInterface can be called // with SelectInterface of version 2.0. ReleaseInterface can be called
// only once for each interface, and if an interface is released, // only once for each interface, and if an interface is released,
// the caller will be responsible for deleting it. // the caller will be responsible for deleting it.
Interface *ReleaseInterface(unsigned int i); Interface *ReleaseInterface(unsigned int i);
virtual void NotifyInput(unsigned int interfaceId, unsigned int length); virtual void NotifyInput(unsigned int interfaceId, unsigned int length);
virtual void NotifyClose(unsigned int interfaceId); virtual void NotifyClose(unsigned int interfaceId);
void Put(byte inByte) {outQueue->Put(inByte);} void Put(byte inByte) {outQueue->Put(inByte);}
void Put(const byte *inString, unsigned int length) void Put(const byte *inString, unsigned int length)
{outQueue->Put(inString, length);} {outQueue->Put(inString, length);}
protected: protected:
unsigned int NumberOfPorts() const {return numberOfPorts;} unsigned int NumberOfPorts() const {return numberOfPorts;}
ByteQueue& AccessPort(unsigned int i) {return *inPorts[i];} ByteQueue& AccessPort(unsigned int i) {return *inPorts[i];}
unsigned int InterfacesOpen() const {return interfacesOpen;} unsigned int InterfacesOpen() const {return interfacesOpen;}
private: private:
Join(const Join &); // no copying allowed Join(const Join &); // no copying allowed
unsigned int numberOfPorts; unsigned int numberOfPorts;
vector_member_ptrs<ByteQueue> inPorts; vector_member_ptrs<ByteQueue> inPorts;
unsigned int interfacesOpen; unsigned int interfacesOpen;
vector_member_ptrs<Interface> interfaces; vector_member_ptrs<Interface> interfaces;
}; };
#endif #endif

File diff suppressed because it is too large Load Diff

Some files were not shown because too many files have changed in this diff Show More