📄 sbtrd.cpp
字号:
/****************License************************************************ * * Copyright 2000-2003. ScanSoft, Inc. * * Use of this software is subject to notices and obligations set forth * in the SpeechWorks Public License - Software Version 1.2 which is * included with this software. * * ScanSoft is a registered trademark of ScanSoft, Inc., and OpenSpeech, * SpeechWorks and the SpeechWorks logo are registered trademarks or * trademarks of SpeechWorks International, Inc. in the United States * and other countries. * ***********************************************************************/ /***************************************************************************** ***************************************************************************** * * SBtrd API implementation * * This provides the Win32 implementation of the VXItrd API for basic * thread operations and locks. Unlike most of the other VXI APIs, * this is implemented in a library (on Windows a DLL with a specific * name, on other operating systems as a static, shared, or dynamic * library). Implementations of this API are operating system * dependant. * * To avoid cyclic dependancies, this does not perform logging. Clients * must do error logging themselves based on passed return codes. * ***************************************************************************** *****************************************************************************/ // -----1=0-------2=0-------3=0-------4=0-------5=0-------6=0-------7=0-------8 #ifndef WIN32 #error This file is intended only for use with the Microsoft Windows API. #endif #include <stdlib.h> #define WIN32_LEAN_AND_MEAN #include <windows.h> #include <process.h> #define VXITRD_EXPORTS #include "VXItrd.h" // Header for this API #if ( ! defined(NDEBUG) ) && ( ! defined(VXITRD_RECURSIVE_MUTEX) ) #include <assert.h> /* Suppress/disable warnings triggered by asserts below */ #pragma warning(4 : 4130) /* logical operation on address of string constant */ #endif extern "C" struct VXItrdMutex { #ifdef VXITRD_KERNEL_MUTEX HANDLE mutex; #else CRITICAL_SECTION critSection; #endif #if ( ! defined(NDEBUG) ) && ( ! defined(VXITRD_RECURSIVE_MUTEX) ) volatile bool locked; #endif }; extern "C" struct VXItrdThread { HANDLE threadHandle; unsigned int threadID; }; extern "C" struct VXItrdTimer { HANDLE timerEvent; }; static VXIint32 g_threadStackSize = 0; // -----1=0-------2=0-------3=0-------4=0-------5=0-------6=0-------7=0-------8 /** * Creates a new mutex initialized to the unlocked state. If the calling * thread terminates, the created mutex is not automatically deallocated as * it may be shared among multiple threads. * * @return Fatal error (ex: system lacks necessary resources for creation) * Success; valid mutex has been created */ VXITRD_API VXItrdResult VXItrdMutexCreate(VXItrdMutex **mutex) { VXItrdResult rc = VXItrd_RESULT_SUCCESS; if (mutex == NULL) return VXItrd_RESULT_INVALID_ARGUMENT; *mutex = NULL; // Create the wrapper object VXItrdMutex *result = new VXItrdMutex; if (result == NULL) return VXItrd_RESULT_OUT_OF_MEMORY; #if ( ! defined(NDEBUG) ) && ( ! defined(VXITRD_RECURSIVE_MUTEX) ) result->locked = false; #endif // Create the critical section or mutex, use Win32 exception // handling to catch predicatable problems __try { #ifdef VXITRD_KERNEL_MUTEX result->mutex = CreateMutex(NULL, FALSE, NULL); if (result->mutex == NULL) rc = VXItrd_RESULT_SYSTEM_ERROR; #else InitializeCriticalSection(&result->critSection); #endif } __except (GetExceptionCode() == STATUS_NO_MEMORY ? EXCEPTION_EXECUTE_HANDLER : EXCEPTION_CONTINUE_SEARCH ) { rc = VXItrd_RESULT_OUT_OF_MEMORY; } if (rc == VXItrd_RESULT_SUCCESS) *mutex = result; else if (result) delete result; return rc; } /** * Deletes an existing mutex. It is illegal to delete a locked mutex. * * @return Fatal error (ex: invalid mutex) * Success; mutex has been destroyed * Mutex is locked */ VXITRD_API VXItrdResult VXItrdMutexDestroy(VXItrdMutex **mutex) { VXItrdResult rc = VXItrd_RESULT_SUCCESS; if ((! mutex) || (! *mutex)) return VXItrd_RESULT_INVALID_ARGUMENT; #if ( ! defined(NDEBUG) ) && ( ! defined(VXITRD_RECURSIVE_MUTEX) ) // Check the lock state if ( (*mutex)->locked ) { assert ("VXItrdMutexDestroy( ) on locked mutex" == NULL); return VXItrd_RESULT_FATAL_ERROR; } #endif // Are no predictable problems, so no Win32 exception handling #ifdef VXITRD_KERNEL_MUTEX if (CloseHandle((*mutex)->mutex) == FALSE) rc = VXItrd_RESULT_SYSTEM_ERROR; #else DeleteCriticalSection(&(*mutex)->critSection); #endif delete *mutex; *mutex = NULL; return rc; } /** * Locks an existing mutex. If the mutex is already locked, the thread waits * for the mutex to become available. * * @return: Fatal error (ex: invalid mutex or deadlock detected) * Success; mutex is now locked * Mutex already locked by current thread. */ VXITRD_API VXItrdResult VXItrdMutexLock(VXItrdMutex *mutex) { if (mutex == NULL) return VXItrd_RESULT_INVALID_ARGUMENT; __try { #ifdef VXITRD_KERNEL_MUTEX int result = WaitForSingleObject(mutex->mutex, INFINITE); if (result == WAIT_FAILED) return VXItrd_RESULT_SYSTEM_ERROR; #else EnterCriticalSection(&mutex->critSection); #endif } __except (GetExceptionCode() == STATUS_INVALID_HANDLE ? EXCEPTION_EXECUTE_HANDLER : EXCEPTION_CONTINUE_SEARCH ) { // Yes, Microsoft says STATUS_INVALID_HANDLE is returned on low memory return VXItrd_RESULT_OUT_OF_MEMORY; } #if ( ! defined(NDEBUG) ) && ( ! defined(VXITRD_RECURSIVE_MUTEX) ) // Check the lock state if ( mutex->locked ) { // Should not be locking the same mutex twice, very OS dependant // (Win32 says the behavior is undefined) and not gauranteed by // VXItrdMutex assert ("VXItrdMutexLock( ) on already locked mutex" == NULL); return VXItrd_RESULT_FATAL_ERROR; } else { mutex->locked = true; } #endif return VXItrd_RESULT_SUCCESS; } /** * Unlocks a mutex owned by the thread. * * @return: Fatal error (ex: invalid mutex) * Success; mutex no longer owned by calling thread * Mutex not owned by thread. */ VXITRD_API VXItrdResult VXItrdMutexUnlock(VXItrdMutex *mutex) { if (mutex == NULL) return VXItrd_RESULT_INVALID_ARGUMENT; #if ( ! defined(NDEBUG) ) && ( ! defined(VXITRD_RECURSIVE_MUTEX) ) // Check the lock state if ( ! mutex->locked ) { // Unlocking a mutex that wasn't locked assert ("VXItrdMutexUnlock( ) on unlocked mutex" == NULL); return VXItrd_RESULT_FATAL_ERROR; } else { mutex->locked = false; } #endif #ifdef VXITRD_KERNEL_MUTEX int result = ReleaseMutex(mutex->mutex); if (result == FALSE) return VXItrd_RESULT_FATAL_ERROR; #else LeaveCriticalSection(&mutex->critSection); #endif return VXItrd_RESULT_SUCCESS; } /** * Purpose Create a thread. Note thread values are not supported on OS/2. * execution starts on the thread immediately. To pause execution * use a Mutex between the thread and the thread creator. * * @param thread the thread object to be created * @param start_func the function for the thread to start execution on * @param arg the arguments to the thread function * @return VXItrdResult of operation. Return SUCCESS if thread has been * created and started. * */ VXITRD_API VXItrdResult VXItrdThreadCreate(VXItrdThread **thread, VXItrdThreadStartFunc thread_function, VXItrdThreadArg thread_arg) { if ((thread == NULL) || (thread_function == NULL)) return VXItrd_RESULT_INVALID_ARGUMENT; *thread = NULL; // Create the wrapper object VXItrdThread *result = new VXItrdThread; if (result == NULL) return VXItrd_RESULT_OUT_OF_MEMORY;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -