added QSE_SECNSEC_TO_USEC()
removed qse_mtx_trylock() and added the waiting_time parameter to qse_mtx_lock()
This commit is contained in:
		| @ -30,6 +30,7 @@ | ||||
| #if (!defined(__unix__) && !defined(__unix)) || defined(HAVE_PTHREAD) | ||||
|  | ||||
| #if defined(_WIN32) | ||||
| 	#include <windows.h> | ||||
| 	#include <process.h> | ||||
| #elif defined(__OS2__) | ||||
| 	/* implement this */ | ||||
| @ -73,7 +74,7 @@ int qse_cnd_init (qse_cnd_t* cnd, qse_mmgr_t* mmgr) | ||||
| 	QSE_MEMSET (cnd, 0, QSE_SIZEOF(*cnd)); | ||||
| 	cnd->mmgr = mmgr; | ||||
|  | ||||
| #ifdef _WIN32 | ||||
| #if defined(_WIN32) | ||||
| 	cnd->gone    = 0; | ||||
| 	cnd->blocked = 0; | ||||
| 	cnd->waiting = 0; | ||||
| @ -86,8 +87,6 @@ int qse_cnd_init (qse_cnd_t* cnd, qse_mmgr_t* mmgr) | ||||
| 	    cnd->queue == QSE_NULL ||  | ||||
| 	    cnd->mutex == QSE_NULL)  | ||||
| 	{ | ||||
| 		int num = qse_maperrno (GetLastError()); | ||||
|  | ||||
| 		if (cnd->gate) CloseHandle (cnd->gate); | ||||
| 		if (cnd->queue) CloseHandle (cnd->queue); | ||||
| 		if (cnd->mutex) CloseHandle (cnd->mutex); | ||||
| @ -107,7 +106,7 @@ int qse_cnd_init (qse_cnd_t* cnd, qse_mmgr_t* mmgr) | ||||
|  | ||||
| void qse_cnd_fini (qse_cnd_t* cnd) | ||||
| { | ||||
| #ifdef _WIN32 | ||||
| #if defined(_WIN32) | ||||
| 	CloseHandle (cnd->gate); | ||||
| 	CloseHandle (cnd->queue); | ||||
| 	CloseHandle (cnd->mutex); | ||||
| @ -122,7 +121,7 @@ void qse_cnd_fini (qse_cnd_t* cnd) | ||||
|  | ||||
| void qse_cnd_signal (qse_cnd_t* cnd) | ||||
| { | ||||
| #ifdef _WIN32 | ||||
| #if defined(_WIN32) | ||||
| 	unsigned int signals = 0; | ||||
|  | ||||
| 	WaitForSingleObject ((HANDLE)cnd->mutex, INFINITE); | ||||
| @ -166,7 +165,7 @@ void qse_cnd_signal (qse_cnd_t* cnd) | ||||
|  | ||||
| void qse_cnd_broadcast (qse_cnd_t* cnd) | ||||
| { | ||||
| #ifdef _WIN32 | ||||
| #if defined(_WIN32) | ||||
| 	unsigned int signals = 0; | ||||
|  | ||||
| 	WaitForSingleObject ((HANDLE)cnd->mutex, INFINITE); | ||||
| @ -210,7 +209,7 @@ void qse_cnd_broadcast (qse_cnd_t* cnd) | ||||
|  | ||||
| void qse_cnd_wait (qse_cnd_t* cnd, qse_mtx_t* mutex, qse_ntime_t* waiting_time) | ||||
| { | ||||
| #ifdef _WIN32 | ||||
| #if defined(_WIN32) | ||||
| 	unsigned int was_waiting, was_gone; | ||||
| 	int signaled; | ||||
|  | ||||
| @ -222,7 +221,10 @@ void qse_cnd_wait (qse_cnd_t* cnd, qse_mtx_t* mutex, qse_ntime_t* waiting_time) | ||||
|  | ||||
| 	if (waiting_time) | ||||
| 	{ | ||||
| 		signaled = (WaitForSingleObject((HANDLE)cnd->queue, (DWORD)waiting_time) == WAIT_OBJECT_0); | ||||
| 		DWORD msec; | ||||
|  | ||||
| 		msec = QSE_SECNSEC_TO_MSEC (waiting_time->sec, waiting_time->nsec); | ||||
| 		signaled = (WaitForSingleObject((HANDLE)cnd->queue, msec) == WAIT_OBJECT_0); | ||||
| 	} | ||||
| 	else | ||||
| 	{ | ||||
| @ -279,7 +281,7 @@ void qse_cnd_wait (qse_cnd_t* cnd, qse_mtx_t* mutex, qse_ntime_t* waiting_time) | ||||
| 		ReleaseSemaphore ((HANDLE)cnd->gate, 1, QSE_NULL); | ||||
| 	} | ||||
|  | ||||
| 	qse_mtx_lock (mutex); | ||||
| 	qse_mtx_lock (mutex, QSE_NULL); | ||||
| #else | ||||
| 	if (waiting_time) | ||||
| 	{ | ||||
| @ -302,82 +304,4 @@ void qse_cnd_wait (qse_cnd_t* cnd, qse_mtx_t* mutex, qse_ntime_t* waiting_time) | ||||
| #endif | ||||
| } | ||||
|  | ||||
| #if 0 | ||||
| void qse_cnd_twait ( | ||||
| 	qse_cnd_t* cnd, qse_mtx_t* mutex, qse_time_t waiting_time) | ||||
| { | ||||
| #ifdef _WIN32 | ||||
| 	qse_bool_t signaled; | ||||
| 	unsigned int was_waiting, was_gone; | ||||
|  | ||||
| 	WaitForSingleObject ((HANDLE)cnd->gate, INFINITE); | ||||
| 	++cnd->blocked; | ||||
| 	ReleaseSemaphore ((HANDLE)cnd->gate, 1, QSE_NULL); | ||||
|  | ||||
| 	qse_mtx_unlock (mutex); | ||||
|  | ||||
| 	signaled = (WaitForSingleObject((HANDLE)cnd->queue, (DWORD)waiting_time) == WAIT_OBJECT_0); | ||||
|  | ||||
| 	was_waiting = 0;  | ||||
| 	was_gone = 0; | ||||
|  | ||||
| 	WaitForSingleObject ((HANDLE)cnd->mutex, INFINITE); | ||||
|  | ||||
| 	was_waiting = cnd->waiting; | ||||
| 	was_gone = cnd->gone; | ||||
|  | ||||
| 	if (was_waiting != 0)  | ||||
| 	{ | ||||
| 		if (!signaled)  | ||||
| 		{ /* timed out */ | ||||
| 			if (cnd->blocked != 0) --(cnd->blocked); | ||||
| 			else ++(cnd->gone); | ||||
| 		} | ||||
| 		if (--(cnd->waiting) == 0)  | ||||
| 		{ | ||||
| 			if (cnd->blocked != 0)  | ||||
| 			{ | ||||
| 				ReleaseSemaphore ((HANDLE)cnd->gate, 1, QSE_NULL); | ||||
| 				was_waiting = 0; | ||||
| 			} | ||||
| 			else if (cnd->gone != 0) cnd->gone = 0; | ||||
| 		} | ||||
| 	} | ||||
| 	else if (++(cnd->gone) == QSE_TYPE_MAX(unsigned int) / 2)  | ||||
| 	{ | ||||
| 		WaitForSingleObject ((HANDLE)cnd->gate, INFINITE); | ||||
| 		cnd->blocked -= cnd->gone; | ||||
| 		ReleaseSemaphore ((HANDLE)cnd->gate, 1, QSE_NULL); | ||||
| 		cnd->gone = 0; | ||||
| 	} | ||||
|  | ||||
| 	ReleaseMutex ((HANDLE)cnd->mutex); | ||||
|  | ||||
| 	if (was_waiting == 1)  | ||||
| 	{ | ||||
| 		for (;was_gone; --was_gone)  | ||||
| 		{ | ||||
| 			WaitForSingleObject ((HANDLE)cnd->queue, INFINITE); | ||||
| 		} | ||||
| 		ReleaseSemaphore ((HANDLE)cnd->gate, 1, QSE_NULL); | ||||
| 	} | ||||
|  | ||||
| 	qse_mtx_lock (mutex); | ||||
| #else | ||||
| 	qse_time_t now; | ||||
| 	qse_timespec_t timeout; | ||||
|  | ||||
| 	qse_gettime (&now); | ||||
| 	now += waiting_time; | ||||
|  | ||||
| 	QSE_TIME_TO_TIMESPEC (now, &timeout); | ||||
|  | ||||
| 	QSE_ASSERT (QSE_SIZEOF(timeout) == QSE_SIZEOF(struct timespec)); | ||||
| 	pthread_cond_timedwait (&cnd->hnd, &mutex->hnd, &timeout); | ||||
| #endif | ||||
| } | ||||
|  | ||||
| #endif | ||||
|  | ||||
|  | ||||
| #endif | ||||
|  | ||||
| @ -30,19 +30,25 @@ | ||||
| #if (!defined(__unix__) && !defined(__unix)) || defined(HAVE_PTHREAD) | ||||
|  | ||||
| #if defined(_WIN32) | ||||
| 	#include <process.h> | ||||
| #	include <windows.h> | ||||
| #	include <process.h> | ||||
| #elif defined(__OS2__) | ||||
| 	/* implement this */ | ||||
|  | ||||
| #	define INCL_DOSSEMAPHORES | ||||
| #	include <os2.h> | ||||
|  | ||||
| #elif defined(__DOS__) | ||||
| 	/* implement this */ | ||||
|  | ||||
| #elif defined(__BEOS__) | ||||
| 	#include <be/kernel/OS.h> | ||||
| #	include <be/kernel/OS.h> | ||||
|  | ||||
| #else | ||||
| 	#if defined(AIX) && defined(__GNUC__) | ||||
| #	if defined(AIX) && defined(__GNUC__) | ||||
| 		typedef int crid_t; | ||||
| 		typedef unsigned int class_id_t; | ||||
| 	#endif | ||||
| 	#include <pthread.h> | ||||
| #	endif | ||||
| #	include <pthread.h> | ||||
| #endif | ||||
|  | ||||
| qse_mtx_t* qse_mtx_open (qse_mmgr_t* mmgr, qse_size_t xtnsize) | ||||
| @ -79,7 +85,17 @@ int qse_mtx_init (qse_mtx_t* mtx, qse_mmgr_t* mmgr) | ||||
| 	if (mtx->hnd == QSE_NULL) return -1; | ||||
|  | ||||
| #elif defined(__OS2__) | ||||
| #	error not implemented | ||||
|  | ||||
| 	{ | ||||
| 		APIRET rc; | ||||
| 		HMTX m; | ||||
|  | ||||
| 		rc = DosCreateMutexSem (QSE_NULL, &m, DC_SEM_SHARED, FALSE); | ||||
| 		if (rc != NO_ERROR) return -1; | ||||
|  | ||||
| 		mtx->hnd = m; | ||||
| 		return 0; | ||||
| 	} | ||||
|  | ||||
| #elif defined(__DOS__) | ||||
| #	error not implemented | ||||
| @ -114,7 +130,7 @@ void qse_mtx_fini (qse_mtx_t* mtx) | ||||
| 	CloseHandle (mtx->hnd); | ||||
|  | ||||
| #elif defined(__OS2__) | ||||
| #	error not implemented | ||||
| 	DosCloseMutexSem (mtx->hnd); | ||||
|  | ||||
| #elif defined(__DOS__) | ||||
| #	error not implemented | ||||
| @ -138,7 +154,7 @@ void* qse_mtx_getxtn (qse_mtx_t* mtx) | ||||
| 	return QSE_XTN (mtx); | ||||
| } | ||||
|  | ||||
| int qse_mtx_lock (qse_mtx_t* mtx) | ||||
| int qse_mtx_lock (qse_mtx_t* mtx, qse_ntime_t* waiting_time) | ||||
| { | ||||
| #if defined(_WIN32) | ||||
| 	/*  | ||||
| @ -153,15 +169,61 @@ int qse_mtx_lock (qse_mtx_t* mtx) | ||||
| 	 *                  state is nonsignaled.  | ||||
| 	 *   WAIT_FAILED    An error occurred | ||||
| 	 */ | ||||
| 	if (WaitForSingleObject (mtx->hnd, INFINITE) == WAIT_FAILED)  | ||||
| 	if (waiting_time) | ||||
| 	{ | ||||
| 		qse_seterrno (qse_maperrno(GetLastError())); | ||||
| 		return -1; | ||||
| 		DWORD msec; | ||||
| 		msec = QSE_SECNSEC_TO_MSEC (waiting_time->sec, waiting_time->nsec); | ||||
| 		if (WaitForSingleObject(mtx->hnd, msec) != WAIT_OBJECT_0)  return -1; | ||||
| 	} | ||||
| 	else | ||||
| 	{ | ||||
| 		if (WaitForSingleObject (mtx->hnd, INFINITE) == WAIT_FAILED) return -1; | ||||
| 	} | ||||
|  | ||||
| #elif defined(__OS2__) | ||||
| 	if (waiting_time) | ||||
| 	{ | ||||
| 		ULONG msec; | ||||
| 		msec = QSE_SECNSEC_TO_MSEC (waiting_time->sec, waiting_time->nsec); | ||||
| 		if (DosRequestMutexSem (mtx->hnd, msec) != NO_ERROR) return -1; | ||||
| 	} | ||||
| 	else | ||||
| 	{ | ||||
| 		if (DosRequestMutexSem (mtx->hnd, SEM_INDEFINITE_WAIT) != NO_ERROR) return -1; | ||||
| 	} | ||||
|  | ||||
| #elif defined(__DOS__) | ||||
|  | ||||
| 	/* nothing to do */ | ||||
|  | ||||
| #elif defined(__BEOS__) | ||||
| 	if (acquire_sem(mtx->hnd) != B_NO_ERROR) return -1; | ||||
| 	if (waiting_time) | ||||
| 	{ | ||||
| 		/* TODO: check for B_WOULD_BLOCK */ | ||||
| 		/*if (acquire_sem_etc(mtx->hnd, 1, B_ABSOLUTE_TIMEOUT, 0) != B_NO_ERROR) return -1;*/ | ||||
| 		bigtime_t usec; | ||||
|  | ||||
| 		usec = QSE_SECNSEC_TO_USEC (waiting_time->sec, waiting_time->nsec); | ||||
| 		if (acquire_sem_etc(mtx->hnd, 1, B_TIMEOUT, 0) != B_NO_ERROR) return -1; | ||||
| 	} | ||||
| 	else | ||||
| 	{ | ||||
| 		if (acquire_sem(mtx->hnd) != B_NO_ERROR) return -1; | ||||
| 	} | ||||
| #else | ||||
| 	if (pthread_mutex_lock ((pthread_mutex_t*)&mtx->hnd) != 0) return -1; | ||||
|  | ||||
| 	if (waiting_time) | ||||
| 	{ | ||||
| 		struct timespec ts; | ||||
|  | ||||
| 		ts.tv_sec = waiting_time->sec; | ||||
| 		ts.tv_nsec = waiting_time->nsec; | ||||
| 		if (pthread_mutex_timedlock ((pthread_mutex_t*)&mtx->hnd, &ts) != 0) return -1; | ||||
| 	} | ||||
| 	else | ||||
| 	{ | ||||
| 		if (pthread_mutex_lock ((pthread_mutex_t*)&mtx->hnd) != 0) return -1; | ||||
| 	} | ||||
| #endif | ||||
| 	return 0; | ||||
| } | ||||
| @ -170,28 +232,21 @@ int qse_mtx_unlock (qse_mtx_t* mtx) | ||||
| { | ||||
| #if defined(_WIN32) | ||||
| 	if (ReleaseMutex (mtx->hnd) == FALSE) return -1; | ||||
|  | ||||
| #elif defined(__OS2__) | ||||
| 	if (DosReleaseMutexSem (mtx->hnd) != NO_ERROR) return -1; | ||||
|  | ||||
| #elif defined(__DOS__) | ||||
|  | ||||
| 	/* nothing to do */ | ||||
|  | ||||
| #elif defined(__BEOS__) | ||||
| 	if (release_sem(mtx->hnd) != B_NO_ERROR) return -1; | ||||
|  | ||||
| #else | ||||
| 	if (pthread_mutex_unlock ((pthread_mutex_t*)&mtx->hnd) != 0) return -1; | ||||
| #endif | ||||
| 	return 0; | ||||
| } | ||||
|  | ||||
| int qse_mtx_trylock (qse_mtx_t* mtx) | ||||
| { | ||||
| #if defined(_WIN32) | ||||
| 	if (WaitForSingleObject(mtx->hnd, 0) != WAIT_OBJECT_0)  return -1; | ||||
| #elif defined(__BEOS__) | ||||
| 	if (acquire_sem_etc(mtx->hnd, 1, B_ABSOLUTE_TIMEOUT, 0) != B_NO_ERROR)  | ||||
| 	{ | ||||
| 		/* TODO: check for B_WOULD_BLOCK */ | ||||
| 		return -1; | ||||
| 	} | ||||
| #else | ||||
| 	if (pthread_mutex_trylock((pthread_mutex_t*)&mtx->hnd) != 0) return -1; | ||||
| #endif | ||||
| 	return 0; | ||||
| } | ||||
|  | ||||
| #endif | ||||
|  | ||||
| @ -33,6 +33,7 @@ | ||||
| #if (!defined(__unix__) && !defined(__unix)) || defined(HAVE_PTHREAD) | ||||
|  | ||||
| #if defined(_WIN32) | ||||
| #	include <windows.h> | ||||
| #	include <process.h> | ||||
| #	define QSE_THR_HND_INVALID INVALID_HANDLE_VALUE | ||||
| #elif defined(__OS2__) | ||||
|  | ||||
		Reference in New Issue
	
	Block a user