Source code of Windows XP (NT5)
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.
 
 
 
 
 
 

426 lines
9.8 KiB

/***************************************************************************
*
* File: queue.c
*
* INTEL Corporation Proprietary Information
* Copyright (c) 1996 Intel Corporation.
*
* This listing is supplied under the terms of a license agreement
* with INTEL Corporation and may not be used, copied, nor disclosed
* except in accordance with the terms of that agreement.
*
***************************************************************************
*
* $Workfile: queue.c $
* $Revision: 1.8 $
* $Modtime: 13 Dec 1996 11:48:16 $
* $Log: S:\sturgeon\src\h245ws\vcs\queue.c_v $
*
* Rev 1.8 13 Dec 1996 12:13:12 SBELL1
* moved ifdef _cplusplus to after includes
*
* Rev 1.7 May 28 1996 10:39:00 plantz
* Change QFree to not free objects on the queue; instead it insists that
* the queue be empty.
*
* Rev 1.6 21 May 1996 16:21:36 EHOWARDX
* Added DeleteCriticalSection to QFree().
*
* Rev 1.5 Apr 24 1996 16:18:58 plantz
* Removed include winsock2.h and incommon.h
*
* Rev 1.3.1.0 Apr 24 1996 16:16:42 plantz
* Removed include winsock2.h and callcont.h
*
* Rev 1.3 01 Apr 1996 14:53:28 EHOWARDX
* Changed pQUEUE to PQUEUE.
*
* Rev 1.1 09 Mar 1996 21:12:34 EHOWARDX
* Fixes as result of testing.
*
* Rev 1.0 08 Mar 1996 20:22:38 unknown
* Initial revision.
*
***************************************************************************/
#ifndef STRICT
#define STRICT
#endif // not defined STRICT
#pragma warning ( disable : 4115 4201 4214 4514 )
#include <nt.h>
#include <ntrtl.h>
#include <nturtl.h>
#include <windows.h>
#include "queue.h"
#include "linkapi.h"
#include "h245ws.h"
#include "provider.h"
#if defined(__cplusplus)
extern "C"
{
#endif // (__cplusplus)
/*-*-------------------------------------------------------------------------
Function Name:
QCreate
Syntax:
PQUEUE QCreate(void);
Parameters:
None.
Summary:
Allocates and initializes a new queue.
Returns:
NULL - Allocation of memory for new queue failed.
Otherwise - Address of new queue created.
-------------------------------------------------------------------------*-*/
PQUEUE QCreate(void)
{
register PQUEUE pQueue; /* pointer to the new queue */
/* Allocate a new queue */
pQueue = (PQUEUE)HWSMALLOC(sizeof(QUEUE));
if (pQueue != NULL)
{
/* Initialize the new queue */
pQueue->nHead = pQueue->nTail = Q_NULL;
__try {
// initialize lock (and allocate event immediately)
InitializeCriticalSectionAndSpinCount(&pQueue->CriticalSection,H323_SPIN_COUNT);
} __except ((GetExceptionCode() == STATUS_NO_MEMORY)
? EXCEPTION_EXECUTE_HANDLER
: EXCEPTION_CONTINUE_SEARCH
) {
// free queue
HWSFREE(pQueue);
// re-initialize
pQueue = NULL;
}
}
return pQueue;
} /* QCreate */
void QLock(PQUEUE pQueue)
{
EnterCriticalSection(&pQueue->CriticalSection);
}
void QUnlock(PQUEUE pQueue)
{
LeaveCriticalSection(&pQueue->CriticalSection);
}
LPVOID QFirstItem(PQUEUE pQueue)
{
HWSASSERT(pQueue != NULL);
if (pQueue->nHead == Q_NULL)
{
/* If the queue is empty, we will return NULL */
return NULL;
}
pQueue->nCursor = pQueue->nHead;
return pQueue->apObjects[pQueue->nHead];
}
LPVOID QNextItem(PQUEUE pQueue)
{
pQueue->nCursor = (pQueue->nCursor + 1) % MAX_QUEUE_SIZE;
if (pQueue->nCursor == ((pQueue->nTail + 1) % MAX_QUEUE_SIZE))
{
return NULL;
}
return pQueue->apObjects[pQueue->nCursor];
} /* QNextItem */
LPVOID QRemoveCurrentItem(PQUEUE pQueue)
{
register LPVOID pElem; /* pointer to the new queue */
HWSASSERT(pQueue->nHead != Q_NULL);
pElem = pQueue->apObjects[pQueue->nCursor];
// copy the head element to the current slot and remove the first element.
pQueue->apObjects[pQueue->nCursor] = pQueue->apObjects[pQueue->nHead];
pQueue->apObjects[pQueue->nHead] = NULL;
/* Check to see if we've just emptied the queue; if so, set */
/* the nHead and nTail indices to Q_NULL. If not, set the nHead */
/* index to the right value. */
if (pQueue->nHead == pQueue->nTail)
{
pQueue->nHead = pQueue->nTail = Q_NULL;
}
else
{
pQueue->nHead = (pQueue->nHead + 1) % MAX_QUEUE_SIZE;
}
return pElem;
} /* QRemoveCurrentItem */
/*-*-------------------------------------------------------------------------
Function Name:
QFree
Syntax:
void QFree(PQUEUE pQueue);
Parameters:
pQueue -pointer to the queue to free
Summary:
Deallocates a queue that was allocated by QCreate.
-------------------------------------------------------------------------*-*/
void QFree(PQUEUE pQueue)
{
/* The queue must be empty before it is freed. */
HWSASSERT(pQueue->nHead == Q_NULL);
/* Free the queue. */
DeleteCriticalSection(&pQueue->CriticalSection);
HWSFREE(pQueue);
} /* QFree */
/*
* NAME
* QRemove - remove object from head of queue
*
* ARGUMENTS
* pQueue Pointer to queue
*
* RETURN VALUE
* Pointer to object dequeued or NULL of queue empty
*/
/*-*-------------------------------------------------------------------------
Function Name:
QRemove
Syntax:
LPVOID QRemove(PQUEUE pQueue);
Parameters:
pQueue - Pointer to queue.
Summary:
Removes and returns object from head of queue.
Returns:
NULL - Queue was empty.
Otherwise - Address of object dequeued.
-------------------------------------------------------------------------*-*/
LPVOID QRemove(PQUEUE pQueue)
{
register LPVOID pObject; /* pointer to the object to remove */
EnterCriticalSection(&pQueue->CriticalSection);
if (pQueue->nHead == Q_NULL)
{
/* If the queue is empty, we will return NULL */
pObject = NULL;
}
else
{
/* Get the pointer, NULL it in the apObjects array. */
pObject = pQueue->apObjects[pQueue->nHead];
pQueue->apObjects[pQueue->nHead] = NULL;
/* Check to see if we've just emptied the queue; if so, set */
/* the nHead and nTail indices to Q_NULL. If not, set the nHead */
/* index to the right value. */
if (pQueue->nHead == pQueue->nTail)
{
pQueue->nHead = pQueue->nTail = Q_NULL;
}
else
{
pQueue->nHead = (pQueue->nHead + 1) % MAX_QUEUE_SIZE;
}
}
LeaveCriticalSection(&pQueue->CriticalSection);
return pObject;
} /* QRemove */
/*-*-------------------------------------------------------------------------
Function Name:
QInsert
Syntax:
BOOL QInsert(PQUEUE pQueue, LPVOID pObject);
Parameters:
pQueue - Pointer to queue to insert object into.
pObject - Pointer to object to insert into queue.
Summary:
Inserts an object at tail of queue.
Returns:
TRUE - Object successfully added to queue.
FALSE - Queue full; object could not be added.
-------------------------------------------------------------------------*-*/
BOOL QInsert(PQUEUE pQueue, LPVOID pObject)
{
register int iTemp;
EnterCriticalSection(&pQueue->CriticalSection);
/* If the queue is full, set the return value to FALSE and do */
/* nothing; if not, update the indices appropriately and set the */
/* return value to TRUE. */
if (pQueue->nHead == Q_NULL)
{
/* Queue is empty */
pQueue->apObjects[0] = pObject;
pQueue->nHead = pQueue->nTail = 0;
iTemp = TRUE;
}
else
{
iTemp = (pQueue->nTail + 1) % MAX_QUEUE_SIZE;
if (iTemp == pQueue->nHead)
{
/* Queue is full */
iTemp = FALSE;
}
else
{
pQueue->apObjects[iTemp] = pObject;
pQueue->nTail = iTemp;
iTemp = TRUE;
}
}
LeaveCriticalSection(&pQueue->CriticalSection);
return (BOOL) iTemp;
}
/*-*-------------------------------------------------------------------------
Function Name:
QInsertAtHead
Syntax:
BOOL QInsertAtHead(PQUEUE pQueue, LPVOID pObject);
Parameters:
pQueue - Pointer to queue to insert object into.
pObject - Pointer to object to insert into queue.
Summary:
Inserts an object at head of queue.
Returns:
TRUE - Object successfully added to queue.
FALSE - Queue full; object could not be added.
-------------------------------------------------------------------------*-*/
BOOL QInsertAtHead(PQUEUE pQueue, LPVOID pObject)
{
register int iTemp;
EnterCriticalSection(&pQueue->CriticalSection);
if (pQueue->nHead == Q_NULL)
{
/* Queue is empty */
pQueue->apObjects[0] = pObject;
pQueue->nHead = pQueue->nTail = 0;
iTemp = TRUE;
}
else
{
iTemp = (pQueue->nHead + (MAX_QUEUE_SIZE - 1)) % MAX_QUEUE_SIZE;
if (iTemp == pQueue->nTail)
{
/* Queue is full */
iTemp = FALSE;
}
else
{
pQueue->apObjects[iTemp] = pObject;
pQueue->nHead = iTemp;
iTemp = TRUE;
}
}
LeaveCriticalSection(&pQueue->CriticalSection);
return (BOOL) iTemp;
} /* QInsertAtHead */
/*-*-------------------------------------------------------------------------
Function Name:
IsQEmpty
Syntax:
BOOL IsQEmpty(PQUEUE pQueue);
Parameters:
pQueue - Pointer to queue to check.
Summary:
Checks if a queue is empty.
Returns:
TRUE - Queue is empty.
FALSE - Queue contains at least one object.
-------------------------------------------------------------------------*-*/
BOOL IsQEmpty(PQUEUE pQueue)
{
return (pQueue->nHead == Q_NULL ? TRUE : FALSE);
} /* IsQEmpty */
#if defined(__cplusplus)
}
#endif // (__cplusplus)