⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 smartbuffer.h

📁 用UDP写的可靠传输程序源代码,非常有借鉴意义,适合互连网通讯
💻 H
字号:
// SmartBuffer - Buffer for handy network packets arrangement
// Declaration file
//
// (c) Lev Naumov, CAMEL Laboratory
// E-mail: camellab@mail.ru
// For more information see http://camel.ifmo.ru or
// http://www.codeproject.com/internet/ctp.asp
/////////////////////////////////////////////////////////////////////////////

class SmartBuffer
{
public:
    // Constructor. Parameters:
    // +) datasize - amount of data to be used;
    // +) autodel - if true then this buffer will be freed automatically by
    //    protocol's implementation after it will be sent and confirmed if
    //    needed. So, working with such buffer, you will have to create it with
    //    operator new, but do not to delete it. If this parameter equals false
    //    you will have to do new and delete manually
    // +) headsize - size of header of each packet;
    // +) maxdatasize - maximum size of data in single packet (without header)
    SmartBuffer(unsigned int datasize=0, bool autodel=true, unsigned int headsize=25, unsigned int maxdatasize=65400);

    // Constructor. Parameters:
    // +) fname - name of file to be stored in internal buffer as data;
    // +) datasize - amount of data to be stroed just before the file;
    // +) autodel - if true then this buffer will be freed automatically by
    //    protocol's implementation after it will be sent and confirmed if
    //    needed. So, working with such buffer, you will have to create it with
    //    operator new, but do not to delete it. If this parameter equals false
    //    you will have to do new and delete manually
    // +) headsize - size of header of each packet;
    // +) maxdatasize - maximum size of data in single packet (without header)
    SmartBuffer(LPCTSTR fname, unsigned int datasize=0, bool autodel=true, unsigned int headsize=25, unsigned int maxdatasize=65400);

    // Destructor
    virtual ~SmartBuffer() {delete[] m_pBuffer;};

// Access to key values
    // Header size
    inline unsigned int GetHeadSize() {return m_uHeadSize;};

    // Data size
    inline unsigned int GetDataSize() {return m_uDataSize;};
    void SetDataSize(unsigned int datasize);

    // Maximum data size for single packet
    inline unsigned int GetMaxDataSize() {return m_uMaxDataSize;};

    // Allocated buffer size
    inline unsigned int GetBufferSize() {return m_uBufferSize;};

    // Auto deleting
    inline bool GetAutoDel() {return m_bAutoDel;}
    inline void SetAutoDel(bool autodel) {m_bAutoDel=autodel;}

// Access to key pointers
    // Returns begining of the buffer
    inline char* GetBufferBegin() {return m_pBuffer;};

    // Returns current pointer
    inline void* GetCurPtr() {return m_pCurPtr;};

    // Sets current pointer to pointer to data of i-th packet (i from zero to
    // GetPacketsCount()-1). Result false if index i is out of bounds
    inline bool CurPtrToDataPtr(unsigned int i) {char* res=GetDataPtr(i); if (res) {m_pCurPtr=res; return true;} else return false;};
    
    // Sets current pointer to the begining of data
    inline void CurPtrToDataBegin() {m_pCurPtr=m_pBuffer+m_uHeadSize;};

// Access to packets
    // Returns amount of packets
    inline unsigned int GetPacketsCount() {return m_uBufferSize/(m_uHeadSize+m_uMaxDataSize)+((m_uBufferSize%(m_uHeadSize+m_uMaxDataSize))?1:0);};

    // Returns pointer to header of i-th packet (i from zero to
    // GetPacketsCount()-1). Result is zero if index i is out of bounds
    inline char* GetHeadPtr(unsigned int i) {char* res=i*(m_uHeadSize+m_uMaxDataSize)+m_pBuffer; if (res>m_pBuffer+m_uBufferSize) return NULL; else return res;};

    // Returns pointer to data of i-th packet (i from zero to
    // GetPacketsCount()-1). Result is zero if index i is out of bounds
    inline char* GetDataPtr(unsigned int i) {char* res=GetHeadPtr(i); if (res) return res+m_uHeadSize; else return NULL;};

    // Returns size of i-th packet (i from zero to GetPacketsCount()-1),
    // including header. Only last packet's size can differ from header's size
    // plus maximum data size. Result is zero if index i is out of bounds
    inline unsigned int GetPacketSize(unsigned int i) {if (i<(m_uBufferSize)/(m_uHeadSize+m_uMaxDataSize)) return m_uHeadSize+m_uMaxDataSize; else if (i==(m_uBufferSize)/(m_uHeadSize+m_uMaxDataSize)) return (m_uBufferSize)%(m_uHeadSize+m_uMaxDataSize); else return 0;};

// Data and header access routines
    // Put data of size GetHeadSize() from src to the are of i-th header.
    // Returns true if data was copied successfully to the existing header etc
    // and false otherwise
    bool PutHead(void* src, unsigned int i);

    // Put byte of data bt to internal buffer from current pointer (if dest is
    // negative) or from dest-th byte.. Current pointer will be moved to the
    // end of put data (skipping headers) if movecur equals true. Returns true
    // if data was copied successfully
    bool PutDataByte(unsigned char bt, bool movecur=true, int dest=-1);

    // Put data of size size from src to internal buffer from current pointer
    // (if dest is negative) or from dest-th byte. Current pointer will be
    // moved to the end of put data (skipping headers) if movecur equals true.
    // Returns true if data was copied successfully, without truncation etc and
    // false otherwise
    bool PutData(void* src, unsigned int size, bool movecur=true, int dest=-1);

    // Put string to internal buffer from current pointer (if dest is negative)
    // or from dest-th byte. Current pointer will be moved to the end of put
    // data (skipping headers) if movecur equals true. Returns true if data was
    // copied successfully, without truncation etc and false otherwise
    inline bool PutDataString(char* str, bool movecur=true, int dest=-1) {return PutData(str,strlen(str)+1,movecur,dest);};

    // Put data from file fname to internal buffer from current pointer
    // (if dest is negative) or from dest-th byte. Current pointer will be
    // moved to the end of put data (skipping headers) if movecur equals true.
    // Returns true if data was copied successfully, without truncation etc and
    // false otherwise
    bool PutDataFile(LPCTSTR fname, bool movecur=true, int dest=-1);

    // Trim the buffer, by cutting the content, excluding the part of buffer
    // from current pointer to the end. It is strongly to perform this
    // operation only after all buffer's modifications
    void Trim();

protected:
    // Calculates needed buffer size
    inline unsigned int GetNeededBufferSize(unsigned int datasize, unsigned int headsize, unsigned int maxdatasize) {return datasize?(datasize/maxdatasize*(headsize+maxdatasize)+((datasize%maxdatasize>0)?(datasize%maxdatasize+headsize):0)):headsize;};

    // Calculate pointer by dest (if negative - then by m_pCurPtr). Result
    // pointer will be put to ptr. If prtnsize is not NULL then portion size
    // will be also calculated and put to variable, pointed by prtnsize
    inline void DestToPtr(int dest, char*& ptr, unsigned int* prtnsize);

// Data members
    bool m_bAutoDel; // Detele it automatically or not
    unsigned int m_uHeadSize; // Size of header
    unsigned int m_uDataSize; // Size of data
    unsigned int m_uMaxDataSize; // Maximum size of data in single packet

    unsigned int m_uBufferSize; // Size of allocated internal buffer
    char* m_pBuffer; // Pointer to internal buffer
    char* m_pCurPtr; // Current pointer
};

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -