최종완료보고 버전
This commit is contained in:
@@ -0,0 +1,397 @@
|
||||
#ifndef BLOCK_LIST_BUFFER__H_
|
||||
#define BLOCK_LIST_BUFFER__H_
|
||||
|
||||
#ifdef _WIN32
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
|
||||
struct _TBinaryBlock
|
||||
{
|
||||
char * pData;
|
||||
char * pDataOffset;
|
||||
int nSize;
|
||||
};
|
||||
typedef struct _TBinaryBlock TBinaryBlock;
|
||||
|
||||
|
||||
class HBlockListBuffer : public HObject
|
||||
{
|
||||
public:
|
||||
HBlockListBuffer(int nBlockSize)
|
||||
{
|
||||
m_nBlockSize = nBlockSize;
|
||||
m_nTotalSize = 0; //...
|
||||
}
|
||||
|
||||
~HBlockListBuffer()
|
||||
{
|
||||
RemoveAll();
|
||||
}
|
||||
|
||||
inline size_t GetCount() { return listBinaryBlock.size(); }
|
||||
|
||||
inline int GetTotalSize()
|
||||
{
|
||||
int nTotalSize = 0;
|
||||
for (std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
iter != listBinaryBlock.end(); iter++)
|
||||
{
|
||||
if (iter->nSize > 0)
|
||||
nTotalSize += iter->nSize;
|
||||
}
|
||||
|
||||
return nTotalSize;
|
||||
}
|
||||
|
||||
inline bool Enqueue(const char * pData, int nSize)
|
||||
{
|
||||
if (nSize <= 0) //... command, -1 = end mark
|
||||
{
|
||||
TBinaryBlock blockNew;
|
||||
blockNew.nSize = nSize;
|
||||
listBinaryBlock.push_back(blockNew);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (listBinaryBlock.empty() == false)
|
||||
{
|
||||
#if 1
|
||||
std::list<TBinaryBlock>::iterator iter = listBinaryBlock.end();
|
||||
iter--;
|
||||
|
||||
if (iter->nSize <= 0)
|
||||
return false;
|
||||
|
||||
int nRemainBufer = m_nBlockSize - iter->nSize - (iter->pDataOffset - iter->pData);
|
||||
if (nRemainBufer > nSize)
|
||||
{
|
||||
memcpy(iter->pDataOffset + iter->nSize, pData, nSize);
|
||||
iter->nSize += nSize;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (nRemainBufer > 0)
|
||||
{
|
||||
memcpy(iter->pDataOffset + iter->nSize, pData, nRemainBufer);
|
||||
iter->nSize += nRemainBufer;
|
||||
pData += nRemainBufer;
|
||||
nSize -= nRemainBufer;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
while (nSize > 0)
|
||||
{
|
||||
TBinaryBlock blockNew;
|
||||
blockNew.pData = (char *)malloc(m_nBlockSize);
|
||||
blockNew.pDataOffset = blockNew.pData;
|
||||
|
||||
if (nSize <= m_nBlockSize)
|
||||
{
|
||||
memcpy(blockNew.pDataOffset, pData, nSize);
|
||||
blockNew.nSize = nSize;
|
||||
nSize = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(blockNew.pDataOffset, pData, m_nBlockSize);
|
||||
blockNew.nSize = m_nBlockSize;
|
||||
pData += m_nBlockSize;
|
||||
nSize -= m_nBlockSize;
|
||||
}
|
||||
|
||||
listBinaryBlock.push_back(blockNew);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
inline bool Dequeue(char * pDst, int nCount)
|
||||
{
|
||||
if (nCount > GetTotalSize())
|
||||
return false;
|
||||
|
||||
int nRemainSize = nCount;
|
||||
|
||||
std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
while (iter != listBinaryBlock.end())
|
||||
{
|
||||
if (iter->nSize < 0)
|
||||
return false;
|
||||
|
||||
if (nRemainSize < nCount)
|
||||
{
|
||||
if (iter->nSize < nRemainSize)
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset, iter->nSize);
|
||||
pDst += iter->nSize;
|
||||
nRemainSize -= iter->nSize;
|
||||
free(iter->pData);
|
||||
iter = listBinaryBlock.erase(iter);
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset, nRemainSize);
|
||||
|
||||
if (iter->nSize == nRemainSize)
|
||||
{
|
||||
free(iter->pData);
|
||||
listBinaryBlock.erase(iter);
|
||||
}
|
||||
else
|
||||
{
|
||||
iter->pDataOffset += nRemainSize;
|
||||
iter->nSize -= nRemainSize;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (iter->nSize > 0)
|
||||
{
|
||||
if (iter->nSize < nCount)
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset, iter->nSize);
|
||||
pDst += iter->nSize;
|
||||
nRemainSize -= iter->nSize;
|
||||
free(iter->pData);
|
||||
iter = listBinaryBlock.erase(iter);
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset, nCount);
|
||||
|
||||
if (iter->nSize == nCount)
|
||||
{
|
||||
free(iter->pData);
|
||||
listBinaryBlock.erase(iter);
|
||||
}
|
||||
else
|
||||
{
|
||||
iter->pDataOffset += nCount;
|
||||
iter->nSize -= nCount;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool DequeueAll(char * pDst)
|
||||
{
|
||||
std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
while (iter != listBinaryBlock.end())
|
||||
{
|
||||
if (iter->nSize <= 0) //...
|
||||
return false;
|
||||
|
||||
memcpy(pDst, iter->pDataOffset, iter->nSize);
|
||||
pDst += iter->nSize;
|
||||
free(iter->pData);
|
||||
iter = listBinaryBlock.erase(iter);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
inline bool GetFront(char ** ppData, int * pnSize)
|
||||
{
|
||||
std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
if (iter == listBinaryBlock.end())
|
||||
return false;
|
||||
|
||||
if (iter->nSize > 0)
|
||||
*ppData = iter->pDataOffset;
|
||||
|
||||
*pnSize = iter->nSize;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
inline void PopFront()
|
||||
{
|
||||
std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
if (iter == listBinaryBlock.end())
|
||||
return;
|
||||
|
||||
if (iter->nSize > 0)
|
||||
free(iter->pData);
|
||||
listBinaryBlock.erase(iter);
|
||||
}
|
||||
|
||||
inline bool ReduceFront(int nSize)
|
||||
{
|
||||
if (nSize > m_nBlockSize)
|
||||
return false;
|
||||
|
||||
std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
if (iter == listBinaryBlock.end())
|
||||
return false;
|
||||
|
||||
if (iter->nSize <= 0)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else if (nSize > iter->nSize)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else if (nSize == iter->nSize)
|
||||
{
|
||||
free(iter->pData);
|
||||
listBinaryBlock.erase(iter);
|
||||
return true;
|
||||
}
|
||||
|
||||
iter->pDataOffset += nSize;
|
||||
iter->nSize -= nSize;
|
||||
return true;
|
||||
}
|
||||
|
||||
inline void RemoveAll()
|
||||
{
|
||||
for (std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
iter != listBinaryBlock.end(); iter++)
|
||||
{
|
||||
if (iter->nSize > 0)
|
||||
free(iter->pData);
|
||||
}
|
||||
listBinaryBlock.clear();
|
||||
}
|
||||
|
||||
HDynamicArray<char> ChangeAndClear(int * pnSize, int nExtra)
|
||||
{
|
||||
*pnSize = GetTotalSize();
|
||||
if (*pnSize <= 0)
|
||||
return (char *)NULL;
|
||||
|
||||
char * pBuffer = (char *)malloc(*pnSize + nExtra);
|
||||
char * pOffset = pBuffer;
|
||||
|
||||
for (std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
iter != listBinaryBlock.end(); iter++)
|
||||
{
|
||||
if (iter->nSize > 0) //...
|
||||
{
|
||||
memcpy(pOffset, iter->pDataOffset, iter->nSize);
|
||||
pOffset += iter->nSize;
|
||||
}
|
||||
|
||||
free(iter->pData);
|
||||
}
|
||||
listBinaryBlock.clear();
|
||||
|
||||
return pBuffer;
|
||||
}
|
||||
|
||||
inline bool Copy(char * pDst, int nStartPos, int nCount)
|
||||
{
|
||||
int nRemainSize = nCount;
|
||||
int i = 0;
|
||||
for (std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
iter != listBinaryBlock.end(); iter++)
|
||||
{
|
||||
if (iter->nSize < 0)
|
||||
return false;
|
||||
|
||||
i += iter->nSize;
|
||||
|
||||
if (nRemainSize < nCount)
|
||||
{
|
||||
if (iter->nSize < nRemainSize)
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset, iter->nSize);
|
||||
pDst += iter->nSize;
|
||||
nRemainSize -= iter->nSize;
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset, nRemainSize);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (i > nStartPos) //...
|
||||
{
|
||||
int nBlockRemain = i - nStartPos;
|
||||
int nBlockStartIndex = iter->nSize - nBlockRemain;
|
||||
|
||||
if (nBlockRemain < nCount)
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset + nBlockStartIndex, nBlockRemain);
|
||||
pDst += nBlockRemain;
|
||||
nRemainSize -= nBlockRemain;
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(pDst, iter->pDataOffset + nBlockStartIndex, nCount);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
int SearchChr(int nStartPos, char ch)
|
||||
{
|
||||
int i = 0, j;
|
||||
for (std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
iter != listBinaryBlock.end(); iter++)
|
||||
{
|
||||
if (iter->nSize < 0)
|
||||
return -1;
|
||||
|
||||
if (i + iter->nSize > nStartPos)
|
||||
{
|
||||
for (j = 0; j < iter->nSize; j++)
|
||||
{
|
||||
if (i >= nStartPos && iter->pDataOffset[j] == ch)
|
||||
return i;
|
||||
|
||||
i++;
|
||||
}
|
||||
}
|
||||
else
|
||||
i += iter->nSize;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
#ifdef _DEBUG
|
||||
void Print()
|
||||
{
|
||||
printf("Print, count = %d\n", listBinaryBlock.size());
|
||||
|
||||
int i = 0;
|
||||
for (std::list<TBinaryBlock>::iterator iter = listBinaryBlock.begin();
|
||||
iter != listBinaryBlock.end(); iter++)
|
||||
{
|
||||
printf("%d, ", i++);
|
||||
|
||||
if (iter->nSize > 0)
|
||||
{
|
||||
for (int j = 0; j < iter->nSize; j++)
|
||||
putchar(iter->pDataOffset[j]);
|
||||
}
|
||||
|
||||
putchar('\n');
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
protected:
|
||||
std::list<TBinaryBlock> listBinaryBlock;
|
||||
int m_nBlockSize;
|
||||
int m_nTotalSize;
|
||||
};
|
||||
|
||||
#endif // BLOCK_LIST_BUFFER__H_
|
||||
Reference in New Issue
Block a user