| 52 | |
| 53 | template<class T, int HashCount> |
| 54 | typename CNetBan::CBan<T> *CNetBan::CBanPool<T, HashCount>::Add(const T *pData, const CBanInfo *pInfo, const CNetHash *pNetHash) |
| 55 | { |
| 56 | if(!m_pFirstFree) |
| 57 | return 0; |
| 58 | |
| 59 | // create new ban |
| 60 | CBan<T> *pBan = m_pFirstFree; |
| 61 | pBan->m_Data = *pData; |
| 62 | pBan->m_Info = *pInfo; |
| 63 | pBan->m_NetHash = *pNetHash; |
| 64 | if(pBan->m_pNext) |
| 65 | pBan->m_pNext->m_pPrev = pBan->m_pPrev; |
| 66 | if(pBan->m_pPrev) |
| 67 | pBan->m_pPrev->m_pNext = pBan->m_pNext; |
| 68 | else |
| 69 | m_pFirstFree = pBan->m_pNext; |
| 70 | |
| 71 | // add it to the hash list |
| 72 | if(m_paaHashList[pNetHash->m_HashIndex][pNetHash->m_Hash]) |
| 73 | m_paaHashList[pNetHash->m_HashIndex][pNetHash->m_Hash]->m_pHashPrev = pBan; |
| 74 | pBan->m_pHashPrev = 0; |
| 75 | pBan->m_pHashNext = m_paaHashList[pNetHash->m_HashIndex][pNetHash->m_Hash]; |
| 76 | m_paaHashList[pNetHash->m_HashIndex][pNetHash->m_Hash] = pBan; |
| 77 | |
| 78 | // insert it into the used list |
| 79 | if(m_pFirstUsed) |
| 80 | { |
| 81 | for(CBan<T> *p = m_pFirstUsed; ; p = p->m_pNext) |
| 82 | { |
| 83 | if(p->m_Info.m_Expires == CBanInfo::EXPIRES_NEVER || (pInfo->m_Expires != CBanInfo::EXPIRES_NEVER && pInfo->m_Expires <= p->m_Info.m_Expires)) |
| 84 | { |
| 85 | // insert before |
| 86 | pBan->m_pNext = p; |
| 87 | pBan->m_pPrev = p->m_pPrev; |
| 88 | if(p->m_pPrev) |
| 89 | p->m_pPrev->m_pNext = pBan; |
| 90 | else |
| 91 | m_pFirstUsed = pBan; |
| 92 | p->m_pPrev = pBan; |
| 93 | break; |
| 94 | } |
| 95 | |
| 96 | if(!p->m_pNext) |
| 97 | { |
| 98 | // last entry |
| 99 | p->m_pNext = pBan; |
| 100 | pBan->m_pPrev = p; |
| 101 | pBan->m_pNext = 0; |
| 102 | break; |
| 103 | } |
| 104 | } |
| 105 | } |
| 106 | else |
| 107 | { |
| 108 | m_pFirstUsed = pBan; |
| 109 | pBan->m_pNext = pBan->m_pPrev = 0; |
| 110 | } |
| 111 | |