#include
#include "std.h"
#include "api.h"
#include "list.h"
#include "stdmem.h"
#include "message.h"
typedef struct LNODE /* list node header */
{
struct LNODE* pprior; /* prior element */
struct LNODE* pnext; /* next element */
} lnode;
typedef struct LIST /* list header */
{
lnode* pfirst; /* first element */
lnode* pcur; /* current element */
lnode* plast; /* last element */
int size; /* size of elements */
int count; /* # of elements */
Bool managed; /* used by higher-order structures to 'own' lists */
} list;
/***********************************************************************\
* Description *
* Allocates a list. *
* *
* Return value: *
* Failure: 0 *
* Success: Handle of list *
* *
\***********************************************************************/
const int a_size) /* size of elements */
{
register list* l_plist; /* new list pointer */
assert(a_size>0);
l_plist=(list*)MemAlloc(poolDefault,sizeof(list)); /* allocate */
if (l_plist) /* sucess? */
{
l_plist->pfirst=0; /* empty list */
l_plist->pcur=0; /* no current */
l_plist->plast=0; /* empty list */
l_plist->size=a_size; /* record size */
l_plist->count=0; /* no elements */
l_plist->managed=False; /* not managed by default */
}
return (l_plist); /* return new list */
}
/***********************************************************************\
* Description *
* Determines whether a list is empty. *
* *
* Return value: *
* True: Empty *
* False: Not empty *
* *
\***********************************************************************/
Bool ListEmpty(const List a_hlist) /* handle of list */
{
register list* l_plist; /* list pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_result=False; /* default */
if (l_plist->pfirst==0) /* any elements? */
l_result=True; /* no */
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Determines the number of elements in the list. *
* *
* Return value: *
* # of elements *
* *
\***********************************************************************/
int ListSize(const List a_hlist)
{
register list* l_plist; /* list pointer */
register int l_size; /* return value */
assert(a_hlist!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_size=l_plist->count; /* get size */
return (l_size); /* done */
}
/***********************************************************************\
* Description *
* Marks the first element as the current. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListFindFirst(const List a_hlist) /* handle of list */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->pfirst; /* get first */
l_result=False; /* default */
if (l_pnode) /* node exists? */
{
l_plist->pcur=l_pnode; /* mark as current */
l_result=True; /* success */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Marks the previous element as the current. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListFindPrior(const List a_hlist) /* handle of list */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->pcur; /* get current */
l_result=False; /* default */
if (l_pnode) /* node exists? */
{
l_pnode=l_pnode->pprior; /* get previous */
if (l_pnode) /* node exists? */
{
l_plist->pcur=l_pnode; /* mark as current */
l_result=True; /* success */
}
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Marks the following element as the current. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListFindNext(const List a_hlist) /* handle of list */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->pcur; /* get current */
l_result=False; /* default */
if (l_pnode) /* node exists? */
{
l_pnode=l_pnode->pnext; /* get following */
if (l_pnode) /* node exists? */
{
l_plist->pcur=l_pnode; /* mark as current */
l_result=True; /* success */
}
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Marks the last element as the current. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListFindLast(const List a_hlist) /* handle of list */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->plast; /* get last */
l_result=False; /* default */
if (l_pnode) /* node exists? */
{
l_plist->pcur=l_pnode; /* mark as current */
l_result=True; /* success */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Searches the list for a specific element. *
* *
* Return value: *
* True: Found *
* False: Not found *
* *
\***********************************************************************/
Boo) ListFind(const List a_hlist, /* handle of list */
const void* a_pelement, /* element to find */
FComp* a_pfcomp) /* compare function */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pelement!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->pfirst; /* start with first */
l_result=False; /* default */
while (l_pnode) /* more nodes? */
{
if (a_pfcomp) /* comp function used? */
{
if (a_pfcomp(a_pelement,l_pnode+1)==0) /* equeal? */
l_result=True; /* success */
}
else
{
if (MemCompare(a_pelement,l_pnode+1,l_plist->size)==0)
l_result=True; /* success */
}
if (l_result) /* success? */
{
l_plist->pcur=l_pnode; /* mark as current */
break; /* done */
}
else l_pnode=l_pnode->pnext; /* next node */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Inserts an element at the beginning of the list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListInsertFirst(
const List a_hlist, /* handle of list */
const void* a_pelement) /* element to insert */
{
register list* l_plist; /* list pointer */
register int l_size; /* element size */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pelement!=0);
l_plist=(list*)a_hlist; /* convert handle */
/* debugger stop here? you tried to manipulate a managed list. */
assert(l_plist->managed==0);
l_size=l_plist->size; /* get size */
l_pnode=(lnode*)MemAlloc(poolDefault,sizeof(lnode)+l_size); /* allocate */
l_result=False; /* default */
if (l_pnode) /* success? */
{
l_pnode->pprior=0; /* no prior */
l_pnode->pnext=l_plist->pfirst; /* chain */
if (l_plist->pfirst) /* first exists? */
l_plist->pfirst->pprior=l_pnode; /* chain */
else
l_plist->plast=l_pnode; /* mark as last */
l_plist->pfirst=l_pnode; /* mark as first */
l_plist->pcur=l_pnode; /* mark as current */
(l_plist->count)++; /* one more */
MemCopy(l_pnode+1,a_pelement,l_size); /* copy */
l_result=True; /* success */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Inserts an element before the current in the list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListInsertPrior(
const List a_hlist, /* handle of list */
const void* a_pelement) /* element to insert */
{
register list* l_plist; /* list pointer */
register int l_size; /* element size */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pelement!=0);
l_plist=(list*)a_hlist; /* convert handle */
/* debugger stop here? you tried to mainpulate a managed list. */
assert(l_plist->managed==0);
if (l_plist->pcur==l_plist->pfirst) /* current is first? */
l_result=ListInsertFirst(a_hlist,a_pelement); /* insert first */
else
{
l_size=l_plist->size; /* get size */
l_pnode=(lnode*)MemAlloc(poolDefault,sizeof(lnode)+l_size); /* allocate */
l_result=False; /* default */
if (l_pnode) /* success? */
{
l_pnode->pprior=l_plist->pcur->pprior; /* chain */
l_pnode->pnext=l_plist->pcur; /* chain */
l_pnode->pprior->pnext=l_pnode; /* chain prior */
l_pnode->pnext->pprior=l_pnode; /* chain next */
l_plist->pcur=l_pnode; /* mark as current */
(l_plist->count)++; /* one more */
MemCopy(l_pnode+1,a_pelement,l_size); /* copy */
l_result=True; /* success */
}
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Inserts an element after the current in the list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListInsertNext(
const List a_hlist, /* handle of list */
const void* a_pelement) /* element to insert */
{
register list* l_plist; /* list pointer */
register int l_size; /* element size */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pelement!=0);
l_plist=(list*)a_hlist; /* convert handle */
/* debugger stop here? you tried to manipulate a managed list. */
assert(l_plist->managed==0);
if (l_plist->pcur==l_plist->plast) /* current is last? */
l_result=ListInsertLast(a_hlist,a_pelement); /* insert last */
else
{
l_size=l_plist->size; /* get size */
l_pnode=(lnode*)MemAlloc(poolDefault,sizeof(lnode)+l_size); /* allocate */
l_result=False; /* default */
if (l_pnode) /* success? */
{
l_pnode->pprior=l_plist->pcur; /* chain */
l_pnode->pnext=l_plist->pcur->pnext; /* chain */
l_pnode->pprior->pnext=l_pnode; /* chain prior */
l_pnode->pnext->pprior=l_pnode; /* chain next */
l_plist->pcur=l_pnode; /* mark as current */
(l_plist->count)++; /* one more */
MemCopy(l_pnode+1,a_pelement,l_size); /* copy */
l_result=True; /* success */
}
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Inserts an element at the end of the list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListInsertLast(
const List a_hlist, /* handle of list */
const void* a_pelement) /* element to insert */
{
register list* l_plist; /* list pointer */
register int l_size; /* element size */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pelement!=0);
l_plist=(list*)a_hlist; /* convert handle */
/* debugger stop here? you tried to manipulate a managed list. */
assert(l_plist->managed==0);
l_size=l_plist->size; /* get size */
l_pnode=(lnode*)MemAlloc(poolDefault,sizeof(lnode)+l_size); /* allocate */
l_result=False; /* default */
if (l_pnode) /* success? */
{
l_pnode->pprior=l_plist->plast; /* chain */
l_pnode->pnext=0; /* no next */
if (l_plist->plast) /* last exists? */
l_plist->plast->pnext=l_pnode; /* chain */
else
l_plist->pfirst=l_pnode; /* mark as first */
l_plist->plast=l_pnode; /* mark as last */
l_plist->pcur=l_pnode; /* mark as current */
(l_plist->count)++; /* one more */
MemCopy(l_pnode+1,a_pelement,l_size); /* copy */
l_result=True; /* success */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Retrieves the current element of the list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListRetrieve(
const List a_hlist, /* handle of list */
void* a_pelement) /* element pointer */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pelement!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->pcur; /* get current */
l_result=False; /* default */
if (l_pnode) /* node exists? */
{
MemCopy(a_pelement,l_pnode+1,l_plist->size); /* copy */
l_result=True; /* success */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Updates the current element of the list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListUpdate(
const List a_hlist, /* handle of list */
const void* a_pelement) /* new element */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pelement!=0);
l_plist=(list*)a_hlist; /* convert handle */
/* debugger stop here? you tried to manipulate a managed list. */
assert(l_plist->managed==0);
l_pnode=l_plist->pcur; /* get current */
l_result=False; /* default */
if (l_pnode) /* node exists? */
{
MemCopy(l_pnode+1,a_pelement,l_plist->size); /* copy */
l_result=True; /* success */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Removes the current element of the list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListRemove(
const List a_hlist, /* handle of list */
void* a_pelement) /* element pointer */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
l_plist=(list*)a_hlist; /* convert pointer */
/* debugger stop here? you tried to manipulate a managed list. */
assert(l_plist->managed==0);
l_pnode=l_plist->pcur; /* get current */
l_result=False; /* default */
if (l_pnode) /* node exists? */
{
if (l_pnode==l_plist->pfirst) /* is first? */
l_plist->pfirst=l_pnode->pnext; /* move first */
else
l_pnode->pprior->pnext=l_pnode->pnext; /* unchain */
if (l_pnode==l_plist->plast) /* is last? */
l_plist->plast=l_pnode->pprior; /* move last */
else
l_pnode->pnext->pprior=l_pnode->pprior; /* unchain */
l_plist->pcur=l_plist->pfirst; /* first is new current */
(l_plist->count)--; /* one less */
if (a_pelement) /* copy? */
MemCopy(a_pelement,l_pnode+1,l_plist->size); /* yes */
MemFree(l_pnode); /* free element */
l_result=True; /* success */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Maps a function onto each element of a list. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListMap(
const List a_hlist, /* handle of list */
FMap* a_pfmap, /* map function */
void* a_pcontext) /* context specific */
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pfmap!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->pfirst; /* start at first */
l_result=True; /* default */
while (l_pnode) /* more nodex? */
{
l_result=a_pfmap(l_pnode+1,a_pcontext); /* apply function */
if (!l_result) /* success? */
break; /* no */
l_pnode=l_pnode->pnext; /* next node */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* Maps a function onto each element of a list. *
* Mapping begins on the current node as opposed to the first *
* node. *
* *
* Return value: *
* True: Success *
* False: Failure *
* *
\***********************************************************************/
Bool ListMapPos(const List a_hlist, FMap* a_pfmap, void* a_pcontext)
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register Bool l_result; /* return value */
assert(a_hlist!=0);
assert(a_pfmap!=0);
l_plist=(list*)a_hlist; /* convert handle */
l_pnode=l_plist->pcur; /* start at first */
l_result=True; /* default */
while (l_pnode) /* more nodex? */
{
l_result=a_pfmap(l_pnode+1,a_pcontext); /* apply function */
if (!l_result) /* success? */
break; /* no */
l_pnode=l_pnode->pnext; /* next node */
}
return (l_result); /* done */
}
/***********************************************************************\
* Description *
* *
* Return value: *
* *
\***********************************************************************/
Bool ListFilterX(
const char *a_filename,
int a_linenumber,
const List a_hlist,
FFilter* a_pffilter,
void* a_pcontext
)
{
register list* l_plist; /* list pointer */
register lnode* l_pnode; /* node pointer */
register int l_temp; /* filter result */
register Bool l_result; /* return value */
Bool debug;
assert(a_hlist!=0);
assert(a_pffilter!=0);
l_plist=(list*)a_hlist; /* convert handle */
/* debugger stop here? you tried to manipulate a managed list. */
if (l_plist->managed != 0)
{
MessageError ("Managed list freed manually in file %s, line %d",a_filename,a_linenumber);
assert(False);
}
assert(l_plist->managed==0);
l_pnode=l_plist->pfirst; /* start at first */
l_result=True; /* default */
while (l_pnode) /* more nodex? */
{
l_plist->pcur=l_pnode; /* set as current */
l_temp=a_pffilter(l_pnode+1,a_pcontext); /* apply function */
l_pnode=l_pnode->pnext; /* next node */
if (l_temp<0 class="Apple-tab-span" span="" style="white-space: pre;"> 0>