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.
 
 
 
 
 
 

221 lines
6.3 KiB

/******************************Module*Header*******************************\
* Module Name: dl_init.c
*
* Display list initialization and sharing rountines.
*
* Copyright (c) 1995-96 Microsoft Corporation
\**************************************************************************/
/*
** Copyright 1991-1993, Silicon Graphics, Inc.
** All Rights Reserved.
**
** This is UNPUBLISHED PROPRIETARY SOURCE CODE of Silicon Graphics, Inc.;
** the contents of this file may not be disclosed to third parties, copied or
** duplicated in any form, in whole or in part, without the prior written
** permission of Silicon Graphics, Inc.
**
** RESTRICTED RIGHTS LEGEND:
** Use, duplication or disclosure by the Government is subject to restrictions
** as set forth in subdivision (c)(1)(ii) of the Rights in Technical Data
** and Computer Software clause at DFARS 252.227-7013, and/or in similar or
** successor clauses in the FAR, DOD or NASA FAR Supplement. Unpublished -
** rights reserved under the Copyright Laws of the United States.
**
** Display list init/destroy code.
**
** $Revision: 1.7 $
** $Date: 1993/09/29 00:44:06 $
*/
#include "precomp.h"
#pragma hdrstop
/*
** Empty data structure for display lists.
*/
static __GLdlist emptyDlist = {
2, /* refcount, two so that it can never die */
0 /* Everything else, some initialized later */
};
static __GLnamesArrayTypeInfo dlistTypeInfo =
{
&emptyDlist,
sizeof(__GLdlist),
__glDisposeDlist,
NULL
};
/*
** Used to share display lists between two different contexts.
*/
#ifdef NT_SERVER_SHARE_LISTS
GLboolean FASTCALL __glCanShareDlist(__GLcontext *gc, __GLcontext *shareMe)
{
GLboolean canShare = GL_TRUE;
if (gc->dlist.namesArray != NULL)
{
__glNamesLockArray(gc, gc->dlist.namesArray);
// Make sure we're not trying to replace a shared list
// The spec also says that it is illegal for the new context
// to have any display lists
canShare = gc->dlist.namesArray->refcount == 1 &&
gc->dlist.namesArray->tree == NULL &&
shareMe->dlist.namesArray != NULL;
__glNamesUnlockArray(gc, gc->dlist.namesArray);
}
return canShare;
}
#endif
void FASTCALL __glShareDlist(__GLcontext *gc, __GLcontext *shareMe)
{
#ifdef NT_SERVER_SHARE_LISTS
__glFreeDlistState(gc);
__glNamesLockArray(gc, shareMe->dlist.namesArray);
#endif
gc->dlist.namesArray = shareMe->dlist.namesArray;
gc->dlist.namesArray->refcount++;
#ifdef NT_SERVER_SHARE_LISTS
DBGLEVEL3(LEVEL_INFO, "Sharing dlists %p with %p, count %d\n", gc, shareMe,
gc->dlist.namesArray->refcount);
__glNamesUnlockArray(gc, shareMe->dlist.namesArray);
#endif
}
void FASTCALL __glInitDlistState(__GLcontext *gc)
{
__GLdlistMachine *dlist;
// This is required by the names management code
ASSERTOPENGL(offsetof(__GLdlist, refcount) == 0,
"Dlist refcount not at offset zero\n");
// Set empty dlist to contain no entries
emptyDlist.end = emptyDlist.head;
dlist = &gc->dlist;
dlist->nesting = 0;
dlist->currentList = 0;
dlist->listData = NULL;
dlist->beginRec = NULL;
ASSERTOPENGL(dlist->namesArray == NULL, "Dlist namesArray not NULL\n");
dlist->namesArray = __glNamesNewArray(gc, &dlistTypeInfo);
}
void FASTCALL __glFreeDlistState(__GLcontext *gc)
{
__GLnamesArray *narray;
narray = gc->dlist.namesArray;
if (narray == NULL)
{
return;
}
#ifdef NT_SERVER_SHARE_LISTS
__glNamesLockArray(gc, narray);
// Clean up any lists that this context may have locked
DlReleaseLocks(gc);
#endif
DBGLEVEL2(LEVEL_INFO, "Freeing dlists for %p, ref %d\n", gc,
narray->refcount);
narray->refcount--;
if (narray->refcount == 0)
{
// NULL the array pointer first, preventing its reuse
// after we unlock it. We need to unlock before we free it
// because the critical section will be cleaned up in the
// free
gc->dlist.namesArray = NULL;
// Decrement dlist refcounts and free them if they reach 0
__glNamesFreeArray(gc, narray);
}
else
{
__glNamesUnlockArray(gc, narray);
gc->dlist.namesArray = NULL;
}
if (gc->dlist.listData != NULL)
{
// We were in the middle of compiling a display list when this
// function is called! Free the display list data.
__glFreeDlist(gc, gc->dlist.listData);
gc->dlist.listData = NULL;
gc->dlist.currentList = 0;
}
}
/******************************Public*Routine******************************\
*
* glsrvShareLists
*
* Server side implementation of wglShareLists
*
* History:
* Tue Dec 13 17:14:18 1994 -by- Drew Bliss [drewb]
* Created
*
\**************************************************************************/
#ifdef NT_SERVER_SHARE_LISTS
ULONG APIENTRY glsrvShareLists(__GLcontext *gcShare, __GLcontext *gcSource)
{
if (!__glCanShareDlist(gcShare, gcSource) ||
!__glCanShareTextures(gcShare, gcSource))
{
return ERROR_INVALID_PARAMETER;
}
else
{
__glShareDlist(gcShare, gcSource);
__glShareTextures(gcShare, gcSource);
return ERROR_SUCCESS;
}
}
#endif
/******************************Public*Routine******************************\
*
* __glDlistThreadCleanup
*
* Performs thread-exit cleanup for dlist state
*
* History:
* Mon Dec 19 13:22:38 1994 -by- Drew Bliss [drewb]
* Created
*
\**************************************************************************/
#ifdef NT_SERVER_SHARE_LISTS
#if DBG
// Critical section check routine from usersrv
extern void APIENTRY CheckCritSectionOut(LPCRITICAL_SECTION pcs);
#endif
void __glDlistThreadCleanup(__GLcontext *gc)
{
#if DBG
// Make sure we're not holding the display list critical section
// We only hold this for short periods of time in our own code
// so we should never be holding it unless we have bugs
// In other words, it's ok to just assert this because no
// client action can cause us to hold it
CheckCritSectionOut(&gc->dlist.namesArray->critsec);
#endif
}
#endif