mirror of
https://github.com/dashr9230/SA-MP.git
synced 2024-12-23 06:57:31 +08:00
254 lines
4.4 KiB
C++
254 lines
4.4 KiB
C++
|
|
#pragma once
|
|
|
|
#include <stdio.h>
|
|
|
|
class CAbstractStream
|
|
{
|
|
public:
|
|
enum eSeek
|
|
{
|
|
SeekStart,
|
|
SeekCurrent,
|
|
SeekEnd,
|
|
};
|
|
|
|
CAbstractStream() {}
|
|
|
|
virtual ~CAbstractStream() {}
|
|
|
|
virtual unsigned int Read(void *pbBuffer, int nNumberOfBytes) = 0;
|
|
|
|
virtual unsigned int Read(void *pbBuffer, int nElementSize, int nNumberOfElements)
|
|
{
|
|
return Read(pbBuffer, nNumberOfElements * nElementSize);
|
|
}
|
|
|
|
virtual unsigned int Write(const void *pbBuffer, int nNumberOfBytes) = 0;
|
|
|
|
virtual unsigned int Write(const void *pbBuffer, int nElementSize, int nNumberOfElements)
|
|
{
|
|
return Write(pbBuffer, nNumberOfElements * nElementSize);
|
|
}
|
|
|
|
virtual void Seek(int nOffset, eSeek seekMode) = 0;
|
|
|
|
virtual void Seek(int nOffset)
|
|
{
|
|
Seek(nOffset, SeekStart);
|
|
}
|
|
|
|
virtual unsigned int Tell() = 0;
|
|
};
|
|
|
|
class CFileStream :
|
|
public CAbstractStream
|
|
{
|
|
protected:
|
|
FILE *m_fiFile;
|
|
|
|
public:
|
|
enum eMode
|
|
{
|
|
ModeRead,
|
|
ModeReadWrite,
|
|
ModeAppend,
|
|
ModeWrite,
|
|
};
|
|
|
|
enum eType
|
|
{
|
|
TypeText,
|
|
TypeBinary,
|
|
};
|
|
|
|
CFileStream()
|
|
{
|
|
m_fiFile = NULL;
|
|
}
|
|
|
|
CFileStream(const char *szFilename, eType type, eMode mode)
|
|
{
|
|
m_fiFile = NULL;
|
|
Open(szFilename, type, mode);
|
|
}
|
|
|
|
virtual ~CFileStream()
|
|
{
|
|
if (m_fiFile)
|
|
Close();
|
|
}
|
|
|
|
virtual bool Open(const char *szFilename, eType type, eMode mode)
|
|
{
|
|
if (m_fiFile)
|
|
Close();
|
|
|
|
char szMode[4];
|
|
int nPos = 0;
|
|
szMode[0] = szMode[1] = szMode[2] = szMode[3] = 0;
|
|
|
|
switch(mode)
|
|
{
|
|
case ModeRead:
|
|
szMode[nPos++] = 'r'; break;
|
|
case ModeWrite:
|
|
szMode[nPos++] = 'w'; break;
|
|
case ModeReadWrite:
|
|
szMode[nPos++] = 'r'; szMode[nPos++] = '+'; break;
|
|
case ModeAppend:
|
|
szMode[nPos++] = 'a'; break;
|
|
}
|
|
|
|
switch(type)
|
|
{
|
|
case TypeText:
|
|
szMode[nPos++] = 't'; break;
|
|
case TypeBinary:
|
|
szMode[nPos++] = 'b'; break;
|
|
}
|
|
|
|
m_fiFile = fopen(szFilename, szMode);
|
|
if (!m_fiFile)
|
|
return false;
|
|
|
|
return true;
|
|
}
|
|
|
|
virtual bool IsOpen()
|
|
{
|
|
return (m_fiFile != NULL);
|
|
}
|
|
|
|
virtual void Close()
|
|
{
|
|
if (m_fiFile)
|
|
{
|
|
fclose(m_fiFile);
|
|
m_fiFile = NULL;
|
|
}
|
|
}
|
|
|
|
virtual unsigned int Read(void *pbBuffer, int nNumberOfBytes)
|
|
{
|
|
return (unsigned int)fread(pbBuffer, 1, nNumberOfBytes, m_fiFile);
|
|
}
|
|
|
|
virtual unsigned int Read(void *pbBuffer, int nElementSize, int nNumberOfElements)
|
|
{
|
|
return (unsigned int)fread(pbBuffer, nElementSize, nNumberOfElements, m_fiFile);
|
|
}
|
|
|
|
virtual unsigned int Write(const void *pbBuffer, int nNumberOfBytes)
|
|
{
|
|
return (unsigned int)fwrite(pbBuffer, 1, nNumberOfBytes, m_fiFile);
|
|
}
|
|
|
|
virtual unsigned int Write(const void *pbBuffer, int nElementSize, int nNumberOfElements)
|
|
{
|
|
return (unsigned int)fwrite(pbBuffer, nElementSize, nNumberOfElements, m_fiFile);
|
|
}
|
|
|
|
virtual void Seek(int nOffset, eSeek seekMode)
|
|
{
|
|
int mode = 0;
|
|
switch (seekMode)
|
|
{
|
|
case SeekCurrent:
|
|
mode = SEEK_CUR; break;
|
|
case SeekStart:
|
|
mode = SEEK_SET; break;
|
|
case SeekEnd:
|
|
mode = SEEK_END; break;
|
|
}
|
|
|
|
fseek(m_fiFile, nOffset, seekMode);
|
|
}
|
|
|
|
virtual unsigned int Tell()
|
|
{
|
|
return (unsigned int)ftell(m_fiFile);
|
|
}
|
|
|
|
};
|
|
|
|
class CMemoryStream :
|
|
public CAbstractStream
|
|
{
|
|
protected:
|
|
unsigned char *m_pbBuffer;
|
|
unsigned int m_nOffset;
|
|
unsigned int m_nLength;
|
|
bool m_bCopy;
|
|
|
|
public:
|
|
CMemoryStream(unsigned char *pbBuffer, unsigned int nLength, bool bCopy = true)
|
|
{
|
|
m_bCopy = bCopy;
|
|
m_nOffset = 0;
|
|
m_nLength = nLength;
|
|
|
|
if (bCopy)
|
|
{
|
|
m_pbBuffer = (unsigned char *)malloc(nLength);
|
|
memcpy(m_pbBuffer, pbBuffer, nLength);
|
|
}
|
|
else
|
|
{
|
|
m_pbBuffer = pbBuffer;
|
|
}
|
|
}
|
|
|
|
virtual ~CMemoryStream()
|
|
{
|
|
if (m_bCopy && m_pbBuffer)
|
|
{
|
|
free(m_pbBuffer);
|
|
}
|
|
}
|
|
|
|
virtual unsigned int Read(void *pbBuffer, int nNumberOfBytes)
|
|
{
|
|
if (m_nOffset + nNumberOfBytes > m_nLength)
|
|
nNumberOfBytes = m_nLength - m_nOffset;
|
|
|
|
memcpy(pbBuffer, m_pbBuffer + m_nOffset, nNumberOfBytes);
|
|
m_nOffset += nNumberOfBytes;
|
|
|
|
return nNumberOfBytes;
|
|
}
|
|
|
|
virtual unsigned int Write(const void *pbBuffer, int nNumberOfBytes)
|
|
{
|
|
if (m_nOffset + nNumberOfBytes > m_nLength)
|
|
nNumberOfBytes = m_nLength - m_nOffset;
|
|
|
|
memcpy(m_pbBuffer + m_nOffset, pbBuffer, nNumberOfBytes);
|
|
m_nOffset += nNumberOfBytes;
|
|
|
|
return nNumberOfBytes;
|
|
}
|
|
|
|
virtual void Seek(int nOffset, eSeek seekMode)
|
|
{
|
|
switch(seekMode)
|
|
{
|
|
case SeekStart:
|
|
m_nOffset = nOffset; break;
|
|
case SeekCurrent:
|
|
m_nOffset += nOffset; break;
|
|
case SeekEnd:
|
|
m_nOffset = m_nLength + nOffset; break;
|
|
}
|
|
|
|
if (m_nOffset > m_nLength)
|
|
m_nOffset = m_nLength;
|
|
}
|
|
|
|
virtual unsigned int Tell()
|
|
{
|
|
return m_nOffset;
|
|
}
|
|
|
|
};
|