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.
 
 
 
 
 
 

363 lines
8.7 KiB

/*
*
* NOTES:
*
* REVISIONS:
* pcy26Nov92: Removed windows.h debug stuff
* jod03Dec92: Changed the == tests to x.Equal in a couple of places.
* TSC11May93: In Equal(), cast theItemsInContainer as
* (int) theItemsInContainer
* TSC11May93: Changed operator ++ (INT) to always return a value,
* including *(NULL) !! This allows a clean compile,
* but is not a good solution. PCY SHOULD REVIEW.
* cad27Sep93: Return before delete moved
* rct01Feb94: List no longer inherits from Container
* pcy08Apr94: Trim size, use static iterators, dead code removal
* mwh05May94: #include file madness , part 2
* ajr24May94: Added some casts for Uware
* jps13Jul94: added stdlib.h for os2, changed include order
* ntf12Oct95: Added line to Next ListIterator::Next function to stop it
* bombing if theCurrentElement is NULL.
* cgm24Apr96: Current() returns NULL when theCurrentElement is NULL
*
* v-stebe 29Jul2000 Added checks for mem. alloc. failures
* (bugs #46329, #46330, #46331, #46332, #46333)
* v-stebe 29Jan2002 Removed List::Equals and ListIterator:operator++
* methods to resolve prefast errors.
*/
#define INCL_BASE
#define INCL_NOPM
#include "cdefine.h"
extern "C" {
#if (C_OS & C_OS2)
#include <stdlib.h>
#endif
#include <string.h>
#if (C_OS & C_NLM)
#include <process.h>
#endif
}
#include "list.h"
#include "node.h"
//------------------------------------------------------------------------
List::List() :
theItemsInContainer(0),
theHead((PNode)NULL),
theTail((PNode)NULL)
{
}
//------------------------------------------------------------------------
List::List(PList anOldList) :
theItemsInContainer(0),
theHead((PNode)NULL),
theTail((PNode)NULL)
{
INT err = ErrNO_ERROR;
INT items_in_list = anOldList->GetItemsInContainer();
if (items_in_list == 0)
{
err = ErrLIST_EMPTY;
}
else
{
PObj current_object = (PObj)anOldList->GetHead();
ListIterator list_iterator(*anOldList);
while ((current_object) && (err == ErrNO_ERROR))
{
if (theTail == theHead)
{
theTail = new Node(current_object);
if (theTail == NULL) {
// Memory allocation error
err = ErrMEMORY;
break;
}
if (theHead == (PNode)NULL)
{
theHead = theTail;
theHead->SetNext((PNode)NULL);
theHead->SetPrev((PNode)NULL);
}
else
{
theHead->SetNext(theTail);
theTail->SetPrev(theHead);
}
}
else
{
PNode temp = new Node(current_object);
theTail->SetNext(temp);
temp->SetPrev(theTail);
theTail = temp;
}
theItemsInContainer++;
current_object = (PObj)list_iterator.Next();
}
}
}
//------------------------------------------------------------------------
RObj List::PeekHead() const
{
return *(theHead->theNext->theData);
}
//------------------------------------------------------------------------
VOID List::Add( RObj anObject )
{
if (theHead == (PNode)NULL)
{
theHead = new Node( &anObject);
theTail = theHead;
theItemsInContainer++;
}
else
{
PNode temp = new Node( &anObject, theHead );
if (temp != NULL) {
theHead->SetPrev(temp);
temp->SetNext(theHead);
theHead = temp;
theItemsInContainer++;
}
}
}
//------------------------------------------------------------------------
VOID List::Append( PObj anObject )
{
if (theTail == theHead)
{
theTail = new Node(anObject);
if (theTail != NULL) {
if (theHead == (PNode)NULL)
{
theHead = theTail;
theHead->SetNext((PNode)NULL);
theHead->SetPrev((PNode)NULL);
}
else
{
theHead->SetNext(theTail);
theTail->SetPrev(theHead);
}
theItemsInContainer++;
}
}
else
{
PNode temp = new Node(anObject);
if (temp != NULL) {
theTail->SetNext(temp);
temp->SetPrev(theTail);
theTail = temp;
theItemsInContainer++;
}
}
}
//------------------------------------------------------------------------
PObj List::GetHead()
{
if (theHead != (PNode)NULL)
return theHead->GetData();
return (PObj)NULL;
}
//------------------------------------------------------------------------
PObj List::GetTail()
{
if (theTail != (PNode)NULL)
return theTail->GetData();
return (PObj)NULL;
}
//------------------------------------------------------------------------
PObj List::Find( PObj anObject )
{
PNode cursor = theHead;
while ( cursor != (PNode)NULL)
{
// if (*anObject == *(cursor->GetData()) )
if (anObject->Equal(*(cursor->GetData())) )
return cursor->GetData();
cursor = cursor->GetNext();
}
return (PObj)NULL;
}
//------------------------------------------------------------------------
PNode List::FindNode( PObj anObject )
{
PNode cursor = theHead;
while ( cursor != (PNode)NULL)
{
// if (*anObject == *(cursor->GetData()) )
if (anObject->Equal(*(cursor->GetData())) )
return cursor;
cursor = cursor->GetNext();
}
return (PNode)NULL;
}
//------------------------------------------------------------------------
VOID List::Detach( RObj anObject )
{
PNode thenode = FindNode( &anObject );
if (thenode == (PNode)NULL)
return; // Not in the List
PNode next = thenode->theNext;
PNode prev = thenode->thePrev;
if (prev) // If there is a previous node
prev->SetNext(thenode->GetNext()); // assign its next field
else
theHead = next;
if (next)
next->SetPrev(thenode->GetPrev());
else
theTail = prev;
theItemsInContainer--;
delete thenode;
thenode = NULL;
}
//------------------------------------------------------------------------
/*
C+
Name :FlushALL
Synop :Will delete all the NODES in the list along with the user objects
as well. The user objects in the list are held by the NODES.
*/
VOID List::FlushAll()
//c-
{
PNode current = theHead;
while( current != (PNode)NULL) //theTail )
{
PNode temp = current;
current = current->theNext;
// Delete the User Data. List is a friend of node
if(temp->theData) {
delete temp->theData;
}
delete temp; // Delete the Node now.
temp = NULL;
}
theHead = (PNode)NULL;
theTail = (PNode)NULL;
theItemsInContainer = 0;
}
VOID List::Flush()
{
// PNode current = theHead->theNext;
PNode current = theHead;
while( current != (PNode)NULL )
{
PNode temp = current;
current = current->theNext;
delete temp;
temp = NULL;
}
theHead = (PNode)NULL;
theTail = (PNode)NULL;
theItemsInContainer = 0;
}
// SRB: Removed method INT List::Equal( RObj anObject ) const
//------------------------------------------------------------------------
RListIterator List::InitIterator() const
{
return *( new ListIterator( (RList)*this ) );
}
//------------------------------------------------------------------------
ListIterator::ListIterator( RList aList )
{
theList = (PList)&aList;
theCurrentElement = theList->GetHeadNode();
}
//------------------------------------------------------------------------
RObj ListIterator::Current()
{
if (theCurrentElement)
return *(theCurrentElement->GetData());
else
return *((PObj)NULL);
}
// SRB: Removed method RObj ListIterator::operator ++ ( INT )
// SRB: Removed method RObj ListIterator::operator ++ ()
//------------------------------------------------------------------------
VOID ListIterator::Reset()
{
theCurrentElement = theList->GetHeadNode();
}
//------------------------------------------------------------------------
PObj ListIterator:: Next()
{
//ntf12Oct95: Added next line to stop this function bombing
if (theCurrentElement == NULL) return((PObj) NULL);
PNode tmp = theCurrentElement->GetNext(); //If above if not there, could bomb
if (tmp)
{
theCurrentElement = tmp;
return theCurrentElement->GetData();
}
return (PObj)NULL;
}