move mutexImpl etc. from pandaexpress

This commit is contained in:
David Rose 2006-02-21 23:11:05 +00:00
parent ab65fe0cfe
commit 8ab0b63fd0
20 changed files with 905 additions and 28 deletions

View File

@ -15,8 +15,14 @@
interrogateManifest.h interrogateType.I interrogateType.h \ interrogateManifest.h interrogateType.I interrogateType.h \
interrogate_datafile.I interrogate_datafile.h \ interrogate_datafile.I interrogate_datafile.h \
interrogate_interface.h interrogate_request.h \ interrogate_interface.h interrogate_request.h \
mutexImpl.h \
mutexDummyImpl.h mutexDummyImpl.I \
mutexNsprImpl.h mutexNsprImpl.I \
mutexPosixImpl.h mutexPosixImpl.I \
mutexWin32Impl.h mutexWin32Impl.I \
py_panda.h \ py_panda.h \
register_type.I register_type.h \ register_type.I register_type.h \
selectThreadImpl.h \
typedObject.I typedObject.h \ typedObject.I typedObject.h \
typeHandle.I typeHandle.h \ typeHandle.I typeHandle.h \
typeRegistry.I typeRegistry.h \ typeRegistry.I typeRegistry.h \
@ -32,6 +38,10 @@
interrogateFunctionWrapper.cxx interrogateManifest.cxx \ interrogateFunctionWrapper.cxx interrogateManifest.cxx \
interrogateType.cxx interrogate_datafile.cxx \ interrogateType.cxx interrogate_datafile.cxx \
interrogate_interface.cxx interrogate_request.cxx \ interrogate_interface.cxx interrogate_request.cxx \
mutexDummyImpl.cxx \
mutexNsprImpl.cxx \
mutexPosixImpl.cxx \
mutexWin32Impl.cxx \
py_panda.cxx \ py_panda.cxx \
register_type.cxx \ register_type.cxx \
typedObject.cxx \ typedObject.cxx \
@ -41,8 +51,15 @@
#define INSTALL_HEADERS \ #define INSTALL_HEADERS \
interrogate_interface.h interrogate_request.h vector_int.h \ interrogate_interface.h interrogate_request.h vector_int.h \
config_interrogatedb.h py_panda.h \ config_interrogatedb.h \
mutexImpl.h \
mutexDummyImpl.h mutexDummyImpl.I \
mutexNsprImpl.h mutexNsprImpl.I \
mutexPosixImpl.h mutexPosixImpl.I \
mutexWin32Impl.h mutexWin32Impl.I \
py_panda.h \
register_type.I register_type.h \ register_type.I register_type.h \
selectThreadImpl.h \
typedObject.I typedObject.h \ typedObject.I typedObject.h \
typeHandle.I typeHandle.h \ typeHandle.I typeHandle.h \
typeRegistry.I typeRegistry.h \ typeRegistry.I typeRegistry.h \

View File

@ -1,4 +1,3 @@
#include "vector_int.cxx" #include "vector_int.cxx"
#include "dtool_super_base.cxx" #include "dtool_super_base.cxx"
#include "config_interrogatedb.cxx" #include "config_interrogatedb.cxx"
@ -9,5 +8,7 @@
#include "interrogateFunctionWrapper.cxx" #include "interrogateFunctionWrapper.cxx"
#include "interrogate_datafile.cxx" #include "interrogate_datafile.cxx"
#include "interrogate_interface.cxx" #include "interrogate_interface.cxx"
#include "interrogateDatabase.cxx"
#include "interrogateManifest.cxx"

View File

@ -1,8 +1,9 @@
#include "interrogateDatabase.cxx"
#include "interrogateManifest.cxx"
#include "interrogateType.cxx" #include "interrogateType.cxx"
#include "interrogate_request.cxx" #include "interrogate_request.cxx"
#include "mutexDummyImpl.cxx"
#include "mutexNsprImpl.cxx"
#include "mutexPosixImpl.cxx"
#include "mutexWin32Impl.cxx"
#include "py_panda.cxx" #include "py_panda.cxx"
#include "register_type.cxx" #include "register_type.cxx"
#include "typedObject.cxx" #include "typedObject.cxx"

View File

@ -0,0 +1,54 @@
// Filename: mutexDummyImpl.I
// Created by: drose (08Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////
// Function: MutexDummyImpl::Constructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexDummyImpl::
MutexDummyImpl() {
}
////////////////////////////////////////////////////////////////////
// Function: MutexDummyImpl::Destructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexDummyImpl::
~MutexDummyImpl() {
}
////////////////////////////////////////////////////////////////////
// Function: MutexDummyImpl::lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexDummyImpl::
lock() {
}
////////////////////////////////////////////////////////////////////
// Function: MutexDummyImpl::release
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexDummyImpl::
release() {
}

View File

@ -0,0 +1,25 @@
// Filename: mutexDummyImpl.cxx
// Created by: drose (08Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#include "selectThreadImpl.h"
#ifdef THREAD_DUMMY_IMPL
#include "mutexDummyImpl.h"
#endif // THREAD_DUMMY_IMPL

View File

@ -0,0 +1,48 @@
// Filename: mutexDummyImpl.h
// Created by: drose (08Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#ifndef MUTEXDUMMYIMPL_H
#define MUTEXDUMMYIMPL_H
#include "dtoolbase.h"
#include "selectThreadImpl.h"
#ifdef THREAD_DUMMY_IMPL
#include "notify.h"
////////////////////////////////////////////////////////////////////
// Class : MutexDummyImpl
// Description : A fake mutex implementation for single-threaded
// applications that don't need any synchronization
// control. This does nothing at all.
////////////////////////////////////////////////////////////////////
class EXPCL_DTOOLCONFIG MutexDummyImpl {
public:
INLINE MutexDummyImpl();
INLINE ~MutexDummyImpl();
INLINE void lock();
INLINE void release();
};
#include "mutexDummyImpl.I"
#endif // THREAD_DUMMY_IMPL
#endif

View File

@ -0,0 +1,57 @@
// Filename: mutexImpl.h
// Created by: drose (08Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#ifndef MUTEXIMPL_H
#define MUTEXIMPL_H
#include "dtoolbase.h"
#include "selectThreadImpl.h"
#if defined(THREAD_DUMMY_IMPL)
#include "mutexDummyImpl.h"
typedef MutexDummyImpl MutexImpl;
typedef MutexDummyImpl ReMutexImpl;
#define HAVE_REMUTEXIMPL 1
#elif defined(THREAD_WIN32_IMPL)
#include "mutexWin32Impl.h"
typedef MutexWin32Impl MutexImpl;
typedef MutexWin32Impl ReMutexImpl; // Win32 Mutexes are always reentrant.
#define HAVE_REMUTEXIMPL 1
#elif defined(THREAD_POSIX_IMPL)
#include "mutexPosixImpl.h"
typedef MutexPosixImpl MutexImpl;
typedef ReMutexPosixImpl ReMutexImpl;
#define HAVE_REMUTEXIMPL 1
#elif defined(THREAD_NSPR_IMPL)
#include "mutexNsprImpl.h"
typedef MutexNsprImpl MutexImpl;
#undef HAVE_REMUTEXIMPL // NSPR doesn't provide a reentrant mutex.
#endif
#endif

View File

@ -0,0 +1,72 @@
// Filename: mutexNsprImpl.I
// Created by: drose (08Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////
// Function: MutexNsprImpl::Constructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexNsprImpl::
MutexNsprImpl() {
_lock = PR_NewLock();
nassertv(_lock != (PRLock *)NULL);
}
////////////////////////////////////////////////////////////////////
// Function: MutexNsprImpl::Destructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexNsprImpl::
~MutexNsprImpl() {
PR_DestroyLock(_lock);
}
////////////////////////////////////////////////////////////////////
// Function: MutexNsprImpl::lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexNsprImpl::
lock() {
PR_Lock(_lock);
}
////////////////////////////////////////////////////////////////////
// Function: MutexNsprImpl::try_lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE bool MutexNsprImpl::
try_lock() {
// NSPR doesn't define a try_lock function. Too bad. We just
// report that it would always block (since we don't know).
return false;
}
////////////////////////////////////////////////////////////////////
// Function: MutexNsprImpl::release
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexNsprImpl::
release() {
int status = PR_Unlock(_lock);
nassertv(status == PR_SUCCESS);
}

View File

@ -0,0 +1,25 @@
// Filename: mutexNsprImpl.cxx
// Created by: drose (09Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#include "selectThreadImpl.h"
#ifdef THREAD_NSPR_IMPL
#include "mutexNsprImpl.h"
#endif // THREAD_NSPR_IMPL

View File

@ -0,0 +1,55 @@
// Filename: mutexNsprImpl.h
// Created by: drose (08Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#ifndef MUTEXNSPRIMPL_H
#define MUTEXNSPRIMPL_H
#include "dtoolbase.h"
#include "selectThreadImpl.h"
#ifdef THREAD_NSPR_IMPL
#include "notify.h"
#include <prlock.h>
#undef MUTEX_DEFINES_TRYLOCK
////////////////////////////////////////////////////////////////////
// Class : MutexNsprImpl
// Description : Uses NSPR to implement a mutex.
////////////////////////////////////////////////////////////////////
class EXPCL_DTOOLCONFIG MutexNsprImpl {
public:
INLINE MutexNsprImpl();
INLINE ~MutexNsprImpl();
INLINE void lock();
INLINE bool try_lock();
INLINE void release();
private:
PRLock *_lock;
friend class ConditionVarNsprImpl;
};
#include "mutexNsprImpl.I"
#endif // THREAD_NSPR_IMPL
#endif

View File

@ -0,0 +1,138 @@
// Filename: mutexPosixImpl.I
// Created by: drose (10Feb06)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////
// Function: MutexPosixImpl::Constructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexPosixImpl::
MutexPosixImpl() {
pthread_mutexattr_t attr;
pthread_mutexattr_init(&attr);
pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_NORMAL);
int result = pthread_mutex_init(&_lock, &attr);
pthread_mutexattr_destroy(&attr);
nassertv(result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: MutexPosixImpl::Destructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexPosixImpl::
~MutexPosixImpl() {
int result = pthread_mutex_destroy(&_lock);
nassertv(result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: MutexPosixImpl::lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexPosixImpl::
lock() {
int result = pthread_mutex_lock(&_lock);
nassertv(result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: MutexPosixImpl::try_lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE bool MutexPosixImpl::
try_lock() {
int result = pthread_mutex_trylock(&_lock);
nassertr(result == 0 || result == EBUSY, false);
return (result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: MutexPosixImpl::release
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexPosixImpl::
release() {
int result = pthread_mutex_unlock(&_lock);
nassertv(result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: ReMutexPosixImpl::Constructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE ReMutexPosixImpl::
ReMutexPosixImpl() {
pthread_mutexattr_t attr;
pthread_mutexattr_init(&attr);
pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE);
int result = pthread_mutex_init(&_lock, &attr);
pthread_mutexattr_destroy(&attr);
nassertv(result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: ReMutexPosixImpl::Destructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE ReMutexPosixImpl::
~ReMutexPosixImpl() {
int result = pthread_mutex_destroy(&_lock);
nassertv(result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: ReMutexPosixImpl::lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void ReMutexPosixImpl::
lock() {
int result = pthread_mutex_lock(&_lock);
nassertv(result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: ReMutexPosixImpl::try_lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE bool ReMutexPosixImpl::
try_lock() {
int result = pthread_mutex_trylock(&_lock);
nassertr(result == 0 || result == EBUSY, false);
return (result == 0);
}
////////////////////////////////////////////////////////////////////
// Function: ReMutexPosixImpl::release
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void ReMutexPosixImpl::
release() {
int result = pthread_mutex_unlock(&_lock);
nassertv(result == 0);
}

View File

@ -0,0 +1,25 @@
// Filename: mutexPosixImpl.cxx
// Created by: drose (10Feb06)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#include "selectThreadImpl.h"
#ifdef THREAD_POSIX_IMPL
#include "mutexPosixImpl.h"
#endif // THREAD_POSIX_IMPL

View File

@ -0,0 +1,73 @@
// Filename: mutexPosixImpl.h
// Created by: drose (10Feb06)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#ifndef MUTEXPOSIXIMPL_H
#define MUTEXPOSIXIMPL_H
#include "dtoolbase.h"
#include "selectThreadImpl.h"
#ifdef THREAD_POSIX_IMPL
#include "notify.h"
#include <pthread.h>
#include <errno.h>
#define MUTEX_DEFINES_TRYLOCK 1
////////////////////////////////////////////////////////////////////
// Class : MutexPosixImpl
// Description : Uses Posix threads to implement a mutex.
////////////////////////////////////////////////////////////////////
class EXPCL_DTOOLCONFIG MutexPosixImpl {
public:
INLINE MutexPosixImpl();
INLINE ~MutexPosixImpl();
INLINE void lock();
INLINE bool try_lock();
INLINE void release();
private:
pthread_mutex_t _lock;
friend class ConditionVarPosixImpl;
};
////////////////////////////////////////////////////////////////////
// Class : ReMutexPosixImpl
// Description : Uses Posix threads to implement a reentrant mutex.
////////////////////////////////////////////////////////////////////
class EXPCL_DTOOLCONFIG ReMutexPosixImpl {
public:
INLINE ReMutexPosixImpl();
INLINE ~ReMutexPosixImpl();
INLINE void lock();
INLINE bool try_lock();
INLINE void release();
private:
pthread_mutex_t _lock;
};
#include "mutexPosixImpl.I"
#endif // THREAD_POSIX_IMPL
#endif

View File

@ -0,0 +1,68 @@
// Filename: mutexWin32Impl.I
// Created by: drose (07Feb06)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////
// Function: MutexWin32Impl::Constructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexWin32Impl::
MutexWin32Impl() {
InitializeCriticalSection(&_lock);
}
////////////////////////////////////////////////////////////////////
// Function: MutexWin32Impl::Destructor
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE MutexWin32Impl::
~MutexWin32Impl() {
DeleteCriticalSection(&_lock);
}
////////////////////////////////////////////////////////////////////
// Function: MutexWin32Impl::lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexWin32Impl::
lock() {
EnterCriticalSection(&_lock);
}
////////////////////////////////////////////////////////////////////
// Function: MutexWin32Impl::try_lock
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE bool MutexWin32Impl::
try_lock() {
return (TryEnterCriticalSection(&_lock) != 0);
}
////////////////////////////////////////////////////////////////////
// Function: MutexWin32Impl::release
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
INLINE void MutexWin32Impl::
release() {
LeaveCriticalSection(&_lock);
}

View File

@ -0,0 +1,25 @@
// Filename: mutexWin32Impl.cxx
// Created by: drose (07Feb06)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#include "selectThreadImpl.h"
#ifdef THREAD_WIN32_IMPL
#include "mutexWin32Impl.h"
#endif // THREAD_WIN32_IMPL

View File

@ -0,0 +1,55 @@
// Filename: mutexWin32Impl.h
// Created by: drose (07Feb06)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#ifndef MUTEXWIN32IMPL_H
#define MUTEXWIN32IMPL_H
#include "dtoolbase.h"
#include "selectThreadImpl.h"
#ifdef THREAD_WIN32_IMPL
#include "notify.h"
#include <windows.h>
#define MUTEX_DEFINES_TRYLOCK 1
////////////////////////////////////////////////////////////////////
// Class : MutexWin32Impl
// Description : Uses Windows native calls to implement a mutex.
////////////////////////////////////////////////////////////////////
class EXPCL_DTOOLCONFIG MutexWin32Impl {
public:
INLINE MutexWin32Impl();
INLINE ~MutexWin32Impl();
INLINE void lock();
INLINE bool try_lock();
INLINE void release();
private:
CRITICAL_SECTION _lock;
friend class ConditionVarWin32Impl;
};
#include "mutexWin32Impl.I"
#endif // THREAD_WIN32_IMPL
#endif

View File

@ -17,6 +17,7 @@
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
#include "py_panda.h" #include "py_panda.h"
#include "config_interrogatedb.h"
#ifdef HAVE_PYTHON #ifdef HAVE_PYTHON

View File

@ -0,0 +1,71 @@
// Filename: selectThreadImpl.h
// Created by: drose (09Aug02)
//
////////////////////////////////////////////////////////////////////
//
// PANDA 3D SOFTWARE
// Copyright (c) 2001 - 2004, Disney Enterprises, Inc. All rights reserved
//
// All use of this software is subject to the terms of the Panda 3d
// Software license. You should have received a copy of this license
// along with this source code; you will also find a current copy of
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
//
// To contact the maintainers of this program write to
// panda3d-general@lists.sourceforge.net .
//
////////////////////////////////////////////////////////////////////
#ifndef SELECTTHREADIMPL_H
#define SELECTTHREADIMPL_H
#include "dtoolbase.h"
////////////////////////////////////////////////////////////////////
// This file decides which of the core implementations of the various
// threading and locking implementations we should use, based on
// platform and/or available libraries.
//
// This file, along with mutexImpl.h and the various Mutex
// implementation classes, are defined in dtool so that some form of
// critical-section protection will be available to view low-level
// classes like TypeRegistry. Most of the rest of the threading and
// synchronization classes are defined in panda/src/express.
////////////////////////////////////////////////////////////////////
#if !defined(HAVE_THREADS)
// With threading disabled, use the do-nothing implementation.
#define THREAD_DUMMY_IMPL 1
#elif defined(WIN32_VC)
// In Windows, use the native threading library.
#define THREAD_WIN32_IMPL 1
#elif defined(HAVE_POSIX_THREADS)
// Posix threads are nice.
#define THREAD_POSIX_IMPL 1
#elif defined(HAVE_NSPR)
// If NSPR is available, use that.
#define THREAD_NSPR_IMPL 1
#else
// This is a configuration error. For some reason, HAVE_THREADS is
// defined but we don't have any way to implement it.
#error No thread implementation defined for platform.
#endif
// Let's also factor out some of the other configuration variables.
#if defined(DO_PIPELINING) && defined(HAVE_THREADS)
#define THREADED_PIPELINE 1
#else
#undef THREADED_PIPELINE
#endif
#endif

View File

@ -31,6 +31,7 @@
// static init time, and we must use the arrow syntax to force // static init time, and we must use the arrow syntax to force
// initialization of the interrogatedb_cat category. // initialization of the interrogatedb_cat category.
MutexImpl TypeRegistry::_lock;
TypeRegistry *TypeRegistry::_global_pointer = NULL; TypeRegistry *TypeRegistry::_global_pointer = NULL;
@ -47,12 +48,15 @@ TypeRegistry *TypeRegistry::_global_pointer = NULL;
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
bool TypeRegistry:: bool TypeRegistry::
register_type(TypeHandle &type_handle, const string &name) { register_type(TypeHandle &type_handle, const string &name) {
_lock.lock();
if (type_handle != TypeHandle::none()) { if (type_handle != TypeHandle::none()) {
// Here's a type that was already registered. Just make sure // Here's a type that was already registered. Just make sure
// everything's still kosher. // everything's still kosher.
TypeRegistryNode *rnode = look_up(type_handle, NULL); TypeRegistryNode *rnode = look_up(type_handle, NULL);
if (&type_handle == &rnode->_ref) { if (&type_handle == &rnode->_ref) {
// No problem. // No problem.
_lock.release();
nassertr(rnode->_name == name, false); nassertr(rnode->_name == name, false);
return false; return false;
} }
@ -82,6 +86,7 @@ register_type(TypeHandle &type_handle, const string &name) {
_derivations_fresh = false; _derivations_fresh = false;
type_handle = new_handle; type_handle = new_handle;
_lock.release();
return true; return true;
} }
TypeRegistryNode *rnode = (*ri).second; TypeRegistryNode *rnode = (*ri).second;
@ -97,6 +102,7 @@ register_type(TypeHandle &type_handle, const string &name) {
if (type_handle == rnode->_handle) { if (type_handle == rnode->_handle) {
// No problem. // No problem.
_lock.release();
return false; return false;
} }
// But wait--the type_handle has changed! We kept a reference to // But wait--the type_handle has changed! We kept a reference to
@ -107,6 +113,7 @@ register_type(TypeHandle &type_handle, const string &name) {
interrogatedb_cat->error() interrogatedb_cat->error()
<< "Reregistering " << name << "\n"; << "Reregistering " << name << "\n";
type_handle == rnode->_handle; type_handle == rnode->_handle;
_lock.release();
return false; return false;
} }
@ -122,6 +129,7 @@ register_type(TypeHandle &type_handle, const string &name) {
type_handle = rnode->_handle; type_handle = rnode->_handle;
} }
_lock.release();
return false; return false;
} }
@ -136,6 +144,8 @@ register_type(TypeHandle &type_handle, const string &name) {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
TypeHandle TypeRegistry:: TypeHandle TypeRegistry::
register_dynamic_type(const string &name) { register_dynamic_type(const string &name) {
_lock.lock();
NameRegistry::iterator ri; NameRegistry::iterator ri;
ri = _name_registry.find(name); ri = _name_registry.find(name);
@ -162,12 +172,15 @@ register_dynamic_type(const string &name) {
_name_registry[name] = rnode; _name_registry[name] = rnode;
_derivations_fresh = false; _derivations_fresh = false;
_lock.release();
return *new_handle; return *new_handle;
} }
// Return the TypeHandle previously obtained. // Return the TypeHandle previously obtained.
TypeRegistryNode *rnode = (*ri).second; TypeRegistryNode *rnode = (*ri).second;
return rnode->_handle; TypeHandle handle = rnode->_handle;
_lock.release();
return handle;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -180,6 +193,8 @@ register_dynamic_type(const string &name) {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
void TypeRegistry:: void TypeRegistry::
record_derivation(TypeHandle child, TypeHandle parent) { record_derivation(TypeHandle child, TypeHandle parent) {
_lock.lock();
TypeRegistryNode *cnode = look_up(child, NULL); TypeRegistryNode *cnode = look_up(child, NULL);
nassertv(cnode != (TypeRegistryNode *)NULL); nassertv(cnode != (TypeRegistryNode *)NULL);
TypeRegistryNode *pnode = look_up(parent, NULL); TypeRegistryNode *pnode = look_up(parent, NULL);
@ -196,6 +211,8 @@ record_derivation(TypeHandle child, TypeHandle parent) {
pnode->_child_classes.push_back(cnode); pnode->_child_classes.push_back(cnode);
_derivations_fresh = false; _derivations_fresh = false;
} }
_lock.release();
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -209,6 +226,8 @@ record_derivation(TypeHandle child, TypeHandle parent) {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
void TypeRegistry:: void TypeRegistry::
record_alternate_name(TypeHandle type, const string &name) { record_alternate_name(TypeHandle type, const string &name) {
_lock.lock();
TypeRegistryNode *rnode = look_up(type, (TypedObject *)NULL); TypeRegistryNode *rnode = look_up(type, (TypedObject *)NULL);
if (rnode != (TypeRegistryNode *)NULL) { if (rnode != (TypeRegistryNode *)NULL) {
NameRegistry::iterator ri = NameRegistry::iterator ri =
@ -219,6 +238,8 @@ record_alternate_name(TypeHandle type, const string &name) {
<< rnode->_name << "; cannot reassign to " << type << "\n"; << rnode->_name << "; cannot reassign to " << type << "\n";
} }
} }
_lock.release();
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -230,13 +251,17 @@ record_alternate_name(TypeHandle type, const string &name) {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
TypeHandle TypeRegistry:: TypeHandle TypeRegistry::
find_type(const string &name) const { find_type(const string &name) const {
_lock.lock();
TypeHandle handle;
NameRegistry::const_iterator ri; NameRegistry::const_iterator ri;
ri = _name_registry.find(name); ri = _name_registry.find(name);
if (ri == _name_registry.end()) { if (ri != _name_registry.end()) {
return TypeHandle::none(); handle = (*ri).second->_handle;
} else {
return (*ri).second->_handle;
} }
_lock.release();
return handle;
} }
@ -252,9 +277,13 @@ find_type(const string &name) const {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
string TypeRegistry:: string TypeRegistry::
get_name(TypeHandle type, TypedObject *object) const { get_name(TypeHandle type, TypedObject *object) const {
_lock.lock();
TypeRegistryNode *rnode = look_up(type, object); TypeRegistryNode *rnode = look_up(type, object);
nassertr(rnode != (TypeRegistryNode *)NULL, ""); nassertr(rnode != (TypeRegistryNode *)NULL, "");
return rnode->_name; string name = rnode->_name;
_lock.release();
return name;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -278,12 +307,17 @@ get_name(TypeHandle type, TypedObject *object) const {
bool TypeRegistry:: bool TypeRegistry::
is_derived_from(TypeHandle child, TypeHandle base, is_derived_from(TypeHandle child, TypeHandle base,
TypedObject *child_object) { TypedObject *child_object) {
_lock.lock();
const TypeRegistryNode *child_node = look_up(child, child_object); const TypeRegistryNode *child_node = look_up(child, child_object);
const TypeRegistryNode *base_node = look_up(base, (TypedObject *)NULL); const TypeRegistryNode *base_node = look_up(base, (TypedObject *)NULL);
nassertr(child_node != (TypeRegistryNode *)NULL && nassertr(child_node != (TypeRegistryNode *)NULL &&
base_node != (TypeRegistryNode *)NULL, false); base_node != (TypeRegistryNode *)NULL, false);
freshen_derivations(); freshen_derivations();
return TypeRegistryNode::is_derived_from(child_node, base_node);
bool result = TypeRegistryNode::is_derived_from(child_node, base_node);
_lock.release();
return result;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -295,8 +329,11 @@ is_derived_from(TypeHandle child, TypeHandle base,
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
int TypeRegistry:: int TypeRegistry::
get_num_root_classes() { get_num_root_classes() {
_lock.lock();
freshen_derivations(); freshen_derivations();
return _root_classes.size(); int num_roots = _root_classes.size();
_lock.release();
return num_roots;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -307,9 +344,15 @@ get_num_root_classes() {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
TypeHandle TypeRegistry:: TypeHandle TypeRegistry::
get_root_class(int n) { get_root_class(int n) {
_lock.lock();
freshen_derivations(); freshen_derivations();
nassertr(n >= 0 && n < get_num_root_classes(), TypeHandle::none()); TypeHandle handle;
return _root_classes[n]->_handle; if (n >= 0 && n < get_num_root_classes()) {
handle = _root_classes[n]->_handle;
}
_lock.release();
return handle;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -330,9 +373,12 @@ get_root_class(int n) {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
int TypeRegistry:: int TypeRegistry::
get_num_parent_classes(TypeHandle child, TypedObject *child_object) const { get_num_parent_classes(TypeHandle child, TypedObject *child_object) const {
_lock.lock();
TypeRegistryNode *rnode = look_up(child, child_object); TypeRegistryNode *rnode = look_up(child, child_object);
nassertr(rnode != (TypeRegistryNode *)NULL, 0); nassertr(rnode != (TypeRegistryNode *)NULL, 0);
return rnode->_parent_classes.size(); int num_parents = rnode->_parent_classes.size();
_lock.release();
return num_parents;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -344,11 +390,15 @@ get_num_parent_classes(TypeHandle child, TypedObject *child_object) const {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
TypeHandle TypeRegistry:: TypeHandle TypeRegistry::
get_parent_class(TypeHandle child, int index) const { get_parent_class(TypeHandle child, int index) const {
_lock.lock();
TypeHandle handle;
TypeRegistryNode *rnode = look_up(child, (TypedObject *)NULL); TypeRegistryNode *rnode = look_up(child, (TypedObject *)NULL);
nassertr(rnode != (TypeRegistryNode *)NULL, TypeHandle::none()); nassertr(rnode != (TypeRegistryNode *)NULL, TypeHandle::none());
nassertr(index >= 0 && index < (int)rnode->_parent_classes.size(), if (index >= 0 && index < (int)rnode->_parent_classes.size()) {
TypeHandle::none()); handle = rnode->_parent_classes[index]->_handle;
return rnode->_parent_classes[index]->_handle; }
_lock.release();
return handle;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -365,9 +415,12 @@ get_parent_class(TypeHandle child, int index) const {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
int TypeRegistry:: int TypeRegistry::
get_num_child_classes(TypeHandle child, TypedObject *child_object) const { get_num_child_classes(TypeHandle child, TypedObject *child_object) const {
_lock.lock();
TypeRegistryNode *rnode = look_up(child, child_object); TypeRegistryNode *rnode = look_up(child, child_object);
nassertr(rnode != (TypeRegistryNode *)NULL, 0); nassertr(rnode != (TypeRegistryNode *)NULL, 0);
return rnode->_child_classes.size(); int num_children = rnode->_child_classes.size();
_lock.release();
return num_children;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -379,11 +432,15 @@ get_num_child_classes(TypeHandle child, TypedObject *child_object) const {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
TypeHandle TypeRegistry:: TypeHandle TypeRegistry::
get_child_class(TypeHandle child, int index) const { get_child_class(TypeHandle child, int index) const {
_lock.lock();
TypeHandle handle;
TypeRegistryNode *rnode = look_up(child, (TypedObject *)NULL); TypeRegistryNode *rnode = look_up(child, (TypedObject *)NULL);
nassertr(rnode != (TypeRegistryNode *)NULL, TypeHandle::none()); nassertr(rnode != (TypeRegistryNode *)NULL, TypeHandle::none());
nassertr(index >= 0 && index < (int)rnode->_child_classes.size(), if (index >= 0 && index < (int)rnode->_child_classes.size()) {
TypeHandle::none()); handle = rnode->_child_classes[index]->_handle;
return rnode->_child_classes[index]->_handle; }
_lock.release();
return handle;
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -403,12 +460,16 @@ get_child_class(TypeHandle child, int index) const {
TypeHandle TypeRegistry:: TypeHandle TypeRegistry::
get_parent_towards(TypeHandle child, TypeHandle base, get_parent_towards(TypeHandle child, TypeHandle base,
TypedObject *child_object) { TypedObject *child_object) {
_lock.lock();
TypeHandle handle;
const TypeRegistryNode *child_node = look_up(child, child_object); const TypeRegistryNode *child_node = look_up(child, child_object);
const TypeRegistryNode *base_node = look_up(base, NULL); const TypeRegistryNode *base_node = look_up(base, NULL);
nassertr(child_node != (TypeRegistryNode *)NULL && nassertr(child_node != (TypeRegistryNode *)NULL &&
base_node != (TypeRegistryNode *)NULL, TypeHandle::none()); base_node != (TypeRegistryNode *)NULL, TypeHandle::none());
freshen_derivations(); freshen_derivations();
return TypeRegistryNode::get_parent_towards(child_node, base_node); handle = TypeRegistryNode::get_parent_towards(child_node, base_node);
_lock.release();
return handle;
} }
@ -425,6 +486,7 @@ get_parent_towards(TypeHandle child, TypeHandle base,
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
void TypeRegistry:: void TypeRegistry::
reregister_types() { reregister_types() {
_lock.lock();
HandleRegistry::iterator ri; HandleRegistry::iterator ri;
TypeRegistry *reg = ptr(); TypeRegistry *reg = ptr();
for (ri = reg->_handle_registry.begin(); for (ri = reg->_handle_registry.begin();
@ -436,6 +498,7 @@ reregister_types() {
<< "Reregistering " << rnode->_name << "\n"; << "Reregistering " << rnode->_name << "\n";
} }
} }
_lock.release();
} }
@ -448,6 +511,7 @@ reregister_types() {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
void TypeRegistry:: void TypeRegistry::
write(ostream &out) const { write(ostream &out) const {
_lock.lock();
// Recursively write out the tree, starting from each node that has // Recursively write out the tree, starting from each node that has
// no parent. // no parent.
HandleRegistry::const_iterator hi; HandleRegistry::const_iterator hi;
@ -459,6 +523,7 @@ write(ostream &out) const {
write_node(out, 2, root); write_node(out, 2, root);
} }
} }
_lock.release();
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -469,6 +534,7 @@ write(ostream &out) const {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
TypeRegistry *TypeRegistry:: TypeRegistry *TypeRegistry::
ptr() { ptr() {
_lock.lock();
if (_global_pointer == NULL) { if (_global_pointer == NULL) {
#ifdef NOTIFY_DEBUG #ifdef NOTIFY_DEBUG
if (interrogatedb_cat->is_spam()) { if (interrogatedb_cat->is_spam()) {
@ -478,6 +544,7 @@ ptr() {
#endif #endif
init_global_pointer(); init_global_pointer();
} }
_lock.release();
return _global_pointer; return _global_pointer;
} }
@ -500,9 +567,7 @@ TypeRegistry() {
// Function: TypeRegistry::init_global_pointer // Function: TypeRegistry::init_global_pointer
// Access: Private, Static // Access: Private, Static
// Description: Constructs the TypeRegistry object for the first // Description: Constructs the TypeRegistry object for the first
// time. It is initially created on the local heap, // time.
// then as soon as shared memory becomes available, it
// should be moved into shared memory.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
void TypeRegistry:: void TypeRegistry::
init_global_pointer() { init_global_pointer() {

View File

@ -20,7 +20,7 @@
#define TYPEREGISTRY_H #define TYPEREGISTRY_H
#include "dtoolbase.h" #include "dtoolbase.h"
#include "mutexImpl.h"
#include "notify.h" #include "notify.h"
#include "pvector.h" #include "pvector.h"
#include "pmap.h" #include "pmap.h"
@ -106,6 +106,7 @@ private:
bool _derivations_fresh; bool _derivations_fresh;
static MutexImpl _lock;
static TypeRegistry *_global_pointer; static TypeRegistry *_global_pointer;
}; };