作者在 2010-10-26 14:13:38 发布以下内容
// Socketmap.h: interface for the CSocketmap class.
//
//////////////////////////////////////////////////////////////////////
//
//////////////////////////////////////////////////////////////////////
#ifndef _SOCKETMAP_H_
#define _SOCKETMAP_H_
#define _SOCKETMAP_H_
template<class VALUE>
class CSocketQueue
{
public:
CSocketQueue();
~CSocketQueue();
int GetCount(){return m_nCount;};
bool InitQueue(int nCount);
void DestroyQueue();
VALUE* AllocItem();
bool FreeItem(VALUE *pItem);
bool GetItem(VALUE **pItem);//取得第一个项,并不释放
VALUE& operator[](int index)const;
LPCRITICAL_SECTION GetSync(){return &m_Sync;};
protected:
int m_nCount;
VALUE* m_ValueArray;
VALUE** m_ValueQueue;
unsigned int m_iHeadIndex;
//unsigned int m_iGetIndex;
unsigned int m_iTailIndex;
int m_iFreeCount;
CRITICAL_SECTION m_Sync;
};
template<class VALUE>
CSocketQueue<VALUE>::CSocketQueue()
{
m_nCount = 0;
m_ValueArray = NULL;
m_ValueQueue = NULL;
m_iHeadIndex = 0;
m_iTailIndex = 0;
m_iFreeCount = 0;
//m_iGetIndex = 0;
}
template<class VALUE>
CSocketQueue<VALUE>::~CSocketQueue()
{
DestroyQueue();
}
template<class VALUE>
VALUE& CSocketQueue<VALUE>::operator[](int index)const
{
return m_ValueArray[index];
}
template<class VALUE>
bool CSocketQueue<VALUE>::InitQueue(int nCount)
{
m_ValueArray = (VALUE*)LocalAlloc(LMEM_FIXED|LMEM_ZEROINIT,sizeof(VALUE)*nCount);
m_ValueQueue = (VALUE**)LocalAlloc(LMEM_FIXED|LMEM_ZEROINIT,sizeof(VALUE*)*nCount);
if(m_ValueArray == NULL || m_ValueQueue == NULL)
{
if(m_ValueArray != NULL)
LocalFree(m_ValueArray);
if(m_ValueQueue != NULL)
LocalFree(m_ValueQueue);
m_ValueArray = NULL;
m_ValueQueue = NULL;
return false;
}
InitializeCriticalSection(&m_Sync);
m_nCount = nCount;
for(int i = 0; i < m_nCount; i++)
{
m_ValueQueue[i] = &m_ValueArray[i];
}
m_iHeadIndex = 0;
m_iTailIndex = 0;
// m_iGetIndex = 0;
m_iFreeCount = m_nCount;
return true;
}
template<class VALUE>
void CSocketQueue<VALUE>::DestroyQueue()
{
if(m_nCount == 0)return;
EnterCriticalSection(&m_Sync);
__try
{
LocalFree(m_ValueArray);
LocalFree(m_ValueQueue);
m_ValueArray = NULL;
m_ValueQueue = NULL;
m_nCount = 0;
m_iHeadIndex = m_iTailIndex = 0;
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
DeleteCriticalSection(&m_Sync);
}
template<class VALUE>
VALUE* CSocketQueue<VALUE>::AllocItem()
{
VALUE* pItem = NULL;
EnterCriticalSection(&m_Sync);
__try
{
if(m_iFreeCount == 0)
__leave;
pItem = m_ValueQueue[m_iHeadIndex ++];
m_iHeadIndex %= m_nCount;
m_iFreeCount --;
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
return pItem;
}
template<class VALUE>
bool CSocketQueue<VALUE>::FreeItem(VALUE *pItem)
{
EnterCriticalSection(&m_Sync);
__try
{
if(m_iFreeCount == m_nCount )
__leave;
unsigned int index = 0;
//先判断释放的项是否存在
for(index=m_iTailIndex;index<m_iTailIndex+m_nCount-m_iFreeCount;index++)
{
if(m_ValueQueue[index%m_nCount] == pItem)
break;
}
//如果不存在直接返回
if(index == m_iTailIndex+m_nCount-m_iFreeCount)
__leave;
VALUE* pTemp = m_ValueQueue[m_iTailIndex];
m_ValueQueue[m_iTailIndex] = pItem;
m_ValueQueue[index%m_nCount] = pTemp;
m_iTailIndex ++;
m_iTailIndex %= m_nCount;
m_iFreeCount ++;
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
return true;
}
class CSocketQueue
{
public:
CSocketQueue();
~CSocketQueue();
int GetCount(){return m_nCount;};
bool InitQueue(int nCount);
void DestroyQueue();
VALUE* AllocItem();
bool FreeItem(VALUE *pItem);
bool GetItem(VALUE **pItem);//取得第一个项,并不释放
VALUE& operator[](int index)const;
LPCRITICAL_SECTION GetSync(){return &m_Sync;};
protected:
int m_nCount;
VALUE* m_ValueArray;
VALUE** m_ValueQueue;
unsigned int m_iHeadIndex;
//unsigned int m_iGetIndex;
unsigned int m_iTailIndex;
int m_iFreeCount;
CRITICAL_SECTION m_Sync;
};
template<class VALUE>
CSocketQueue<VALUE>::CSocketQueue()
{
m_nCount = 0;
m_ValueArray = NULL;
m_ValueQueue = NULL;
m_iHeadIndex = 0;
m_iTailIndex = 0;
m_iFreeCount = 0;
//m_iGetIndex = 0;
}
template<class VALUE>
CSocketQueue<VALUE>::~CSocketQueue()
{
DestroyQueue();
}
template<class VALUE>
VALUE& CSocketQueue<VALUE>::operator[](int index)const
{
return m_ValueArray[index];
}
template<class VALUE>
bool CSocketQueue<VALUE>::InitQueue(int nCount)
{
m_ValueArray = (VALUE*)LocalAlloc(LMEM_FIXED|LMEM_ZEROINIT,sizeof(VALUE)*nCount);
m_ValueQueue = (VALUE**)LocalAlloc(LMEM_FIXED|LMEM_ZEROINIT,sizeof(VALUE*)*nCount);
if(m_ValueArray == NULL || m_ValueQueue == NULL)
{
if(m_ValueArray != NULL)
LocalFree(m_ValueArray);
if(m_ValueQueue != NULL)
LocalFree(m_ValueQueue);
m_ValueArray = NULL;
m_ValueQueue = NULL;
return false;
}
InitializeCriticalSection(&m_Sync);
m_nCount = nCount;
for(int i = 0; i < m_nCount; i++)
{
m_ValueQueue[i] = &m_ValueArray[i];
}
m_iHeadIndex = 0;
m_iTailIndex = 0;
// m_iGetIndex = 0;
m_iFreeCount = m_nCount;
return true;
}
template<class VALUE>
void CSocketQueue<VALUE>::DestroyQueue()
{
if(m_nCount == 0)return;
EnterCriticalSection(&m_Sync);
__try
{
LocalFree(m_ValueArray);
LocalFree(m_ValueQueue);
m_ValueArray = NULL;
m_ValueQueue = NULL;
m_nCount = 0;
m_iHeadIndex = m_iTailIndex = 0;
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
DeleteCriticalSection(&m_Sync);
}
template<class VALUE>
VALUE* CSocketQueue<VALUE>::AllocItem()
{
VALUE* pItem = NULL;
EnterCriticalSection(&m_Sync);
__try
{
if(m_iFreeCount == 0)
__leave;
pItem = m_ValueQueue[m_iHeadIndex ++];
m_iHeadIndex %= m_nCount;
m_iFreeCount --;
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
return pItem;
}
template<class VALUE>
bool CSocketQueue<VALUE>::FreeItem(VALUE *pItem)
{
EnterCriticalSection(&m_Sync);
__try
{
if(m_iFreeCount == m_nCount )
__leave;
unsigned int index = 0;
//先判断释放的项是否存在
for(index=m_iTailIndex;index<m_iTailIndex+m_nCount-m_iFreeCount;index++)
{
if(m_ValueQueue[index%m_nCount] == pItem)
break;
}
//如果不存在直接返回
if(index == m_iTailIndex+m_nCount-m_iFreeCount)
__leave;
VALUE* pTemp = m_ValueQueue[m_iTailIndex];
m_ValueQueue[m_iTailIndex] = pItem;
m_ValueQueue[index%m_nCount] = pTemp;
m_iTailIndex ++;
m_iTailIndex %= m_nCount;
m_iFreeCount ++;
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
return true;
}
template<class VALUE>
bool CSocketQueue<VALUE>::GetItem(VALUE **pItem)
{
bool bResult = true;
EnterCriticalSection(&m_Sync);
__try
{
if(m_iTailIndex == m_iHeadIndex )
{
*pItem = NULL;
bResult = false;
__leave;
}
*pItem = m_ValueQueue[m_iTailIndex];
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
return bResult;
}
bool CSocketQueue<VALUE>::GetItem(VALUE **pItem)
{
bool bResult = true;
EnterCriticalSection(&m_Sync);
__try
{
if(m_iTailIndex == m_iHeadIndex )
{
*pItem = NULL;
bResult = false;
__leave;
}
*pItem = m_ValueQueue[m_iTailIndex];
}
__finally
{
LeaveCriticalSection(&m_Sync);
}
return bResult;
}
#endif // !defined(AFX_SOCKETMAP_H__0EBB7372_60BB_42AF_8AF4_0E961630C7C7__INCLUDED_)