Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

145 lines
3.5 KiB

//
// ptrary.cpp
//
// CPtrArray
//
#include "private.h"
#include "ptrary.h"
#include "mem.h"
//+---------------------------------------------------------------------------
//
// Insert(int iIndex, int cElems)
//
// Grows the array to accomodate cElems at offset iIndex.
//
// The new cells are NOT initialized!
//
//----------------------------------------------------------------------------
BOOL CVoidPtrArray::Insert(int iIndex, int cElems)
{
void **ppv;
int iSizeNew;
Assert(iIndex >= 0);
Assert(iIndex <= _cElems);
Assert(cElems >= 0);
if (cElems == 0)
return TRUE;
// allocate space if necessary
if (_iSize < _cElems + cElems)
{
// allocate 1.5x what we need to avoid future allocs
iSizeNew = max(_cElems + cElems, _cElems + _cElems / 2);
if ((ppv = (_rgpv == NULL) ? (void **)cicMemAlloc(iSizeNew*sizeof(void *)) :
(void **)cicMemReAlloc(_rgpv, iSizeNew*sizeof(void *)))
== NULL)
{
return FALSE;
}
_rgpv = ppv;
_iSize = iSizeNew;
}
if (iIndex < _cElems)
{
// make room for the new addition
memmove(&_rgpv[iIndex + cElems], &_rgpv[iIndex], (_cElems - iIndex)*sizeof(void *));
}
_cElems += cElems;
Assert(_iSize >= _cElems);
return TRUE;
}
//+---------------------------------------------------------------------------
//
// Remove(int Index, int cElems)
//
// Removes cElems at offset iIndex.
//
//----------------------------------------------------------------------------
void CVoidPtrArray::Remove(int iIndex, int cElems)
{
int iSizeNew;
Assert(cElems > 0);
Assert(iIndex >= 0);
Assert(iIndex + cElems <= _cElems);
if (iIndex + cElems < _cElems)
{
// shift following eles left
memmove(&_rgpv[iIndex], &_rgpv[iIndex + cElems], (_cElems - iIndex - cElems)*sizeof(void *));
}
_cElems -= cElems;
// free mem when array contents uses less than half alloc'd mem
iSizeNew = _iSize / 2;
if (iSizeNew > _cElems)
{
CompactSize(iSizeNew);
}
}
//+---------------------------------------------------------------------------
//
// Move
//
// Move an entry from one position to another, shifting other entries as
// appropriate to maintain the array size.
//
// The entry currently at iIndexNew will follow the moved entry on return.
//
// Returns the new index, which will be iIndexNew or iIndexNew - 1 if
// iIndexOld < iIndexNew.
//----------------------------------------------------------------------------
int CVoidPtrArray::Move(int iIndexNew, int iIndexOld)
{
int iSrc;
int iDst;
int iActualNew;
void *pv;
int c;
Assert(iIndexOld >= 0);
Assert(iIndexOld < _cElems);
Assert(iIndexNew >= 0);
if (iIndexOld == iIndexNew)
return iIndexOld;
pv = _rgpv[iIndexOld];
if (iIndexOld < iIndexNew)
{
c = iIndexNew - iIndexOld - 1;
iSrc = iIndexOld + 1;
iDst = iIndexOld;
iActualNew = iIndexNew - 1;
}
else
{
c = iIndexOld - iIndexNew;
iSrc = iIndexOld - c;
iDst = iIndexOld - c + 1;
iActualNew = iIndexNew;
}
Assert(iActualNew >= 0);
Assert(iActualNew < _cElems);
memmove(&_rgpv[iDst], &_rgpv[iSrc], c*sizeof(void *));
_rgpv[iActualNew] = pv;
return iActualNew;
}