From cde63164e7f952ed0980fe62877796b81f749310 Mon Sep 17 00:00:00 2001 From: rpj Date: Thu, 7 Jun 2001 08:27:44 +0000 Subject: * semaphore.h (sem_t): Is now an opaque pointer; moved actual definition to implement.h. * implement.h (sem_t_): Move here from semaphore.h; was the definition of sem_t. * semaphore.c: Wherever necessary, changed use of sem from that of a pointer to a pointer-pointer; added extra checks for a valid sem_t; NULL sem_t when it is destroyed; added extra checks when creating and destroying sem_t elements in the NEED_SEM code branches; changed from using a pthread_mutex_t ((*sem)->mutex) to CRITICAL_SECTION ((*sem)->sem_lock_cs) in NEED_SEM branches for access serialisation. --- semaphore.c | 139 ++++++++++++++++++++++++++++++++++-------------------------- 1 file changed, 78 insertions(+), 61 deletions(-) (limited to 'semaphore.c') diff --git a/semaphore.c b/semaphore.c index 15441e8..0f06c4b 100644 --- a/semaphore.c +++ b/semaphore.c @@ -9,18 +9,6 @@ * * POSIX 1003.1b-1993 (POSIX.1b) * - * Contents: - * Public Methods Author - * -------------- ------ - * sem_init John E. Bossom Mar 1998 - * sem_destroy John E. Bossom Mar 1998 - * sem_trywait John E. Bossom Mar 1998 - * sem_wait John E. Bossom Mar 1998 - * sem_post John E. Bossom Mar 1998 - * - * Private Methods - * --------------- - * * ------------------------------------------------------------- * * Pthreads-win32 - POSIX Threads Library for Win32 @@ -104,29 +92,46 @@ sem_init (sem_t * sem, int pshared, unsigned int value) #ifdef NEED_SEM - sem->value = value; - pthread_mutex_init(&sem->mutex, NULL); - sem->event = CreateEvent (NULL, - FALSE, /* manual reset */ - FALSE, /* initial state */ - NULL); - if (value != 0) + sem_t s = (sem_t) calloc (1, sizeof (*sem_t)); + + if (s == NULL) { - SetEvent(sem->event); + result = ENOMEM; } + else + { + s->value = value; + s->event = CreateEvent (NULL, + FALSE, /* manual reset */ + FALSE, /* initial state */ + NULL); + if (s->Event == 0) + { + result = ENOSPC; + } + else + { + if (value != 0) + { + SetEvent(s->event); + } + InitializeCriticalSection(&s->sem_lock_cs); + + *sem = s; + } #else /* NEED_SEM */ /* * NOTE: Taking advantage of the fact that - * sem_t is a simple structure with one entry; - * We don't have to allocate it... + * sem_t is a simple structure with one entry; + * We don't have to allocate it... */ *sem = CreateSemaphore ( - 0, - value, - 0x7FFFFFF, - NULL); + 0, + value, + 0x7FFFFFF, + NULL); if (*sem == 0) { @@ -175,34 +180,42 @@ sem_destroy (sem_t * sem) */ { int result = 0; + sem_t s = *sem; - if (sem == NULL) + if (sem == NULL || *sem == NULL) { result = EINVAL; } + else + { + *sem = NULL; #ifdef NEED_SEM - else - { - pthread_mutex_destroy(&sem->mutex); - if (!CloseHandle(sem->event)) + if (! CloseHandle(s->event)) { result = EINVAL; } - } + else + { + DeleteCriticalSection(&s->sem_lock_cs); + free(s); + } #else /* NEED_SEM */ - else if (! CloseHandle (*sem)) - { - result = EINVAL; - } + if (! CloseHandle (s)) + { + result = EINVAL; + } #endif /* NEED_SEM */ + } + if (result != 0) { + *sem = s; errno = result; return -1; } @@ -242,28 +255,27 @@ sem_trywait (sem_t * sem) * ------------------------------------------------------ */ { - int result = 0; - - if (sem == NULL) - { - result = EINVAL; - } - #ifdef NEED_SEM - /* not yet implemented! */ - result = EINVAL; + /* + * not yet implemented! + */ + int result = EINVAL; return -1; #else /* NEED_SEM */ + int result = 0; + + if (sem == NULL || *sem == NULL) + { + result = EINVAL; + } else if (WaitForSingleObject (*sem, 0) == WAIT_TIMEOUT) { result = EAGAIN; } -#endif /* NEED_SEM */ - if (result != 0) { errno = result; @@ -272,6 +284,8 @@ sem_trywait (sem_t * sem) return 0; +#endif /* NEED_SEM */ + } /* sem_trywait */ @@ -280,14 +294,16 @@ sem_trywait (sem_t * sem) void ptw32_decrease_semaphore(sem_t * sem) { - pthread_mutex_lock(&sem->mutex); + register sem_t s = *sem; + + EnterCriticalSection(&s->sem_lock_cs); - if (sem->value != 0) + if (s->value != 0) { - sem->value--; - if (sem->value != 0) + s->value--; + if (s->value != 0) { - SetEvent(sem->event); + SetEvent(s->event); } } else @@ -295,20 +311,21 @@ ptw32_decrease_semaphore(sem_t * sem) /* this case should not happen! */ } - pthread_mutex_unlock(&sem->mutex); + LeaveCriticalSection(&s->sem_lock_cs); } BOOL ptw32_increase_semaphore(sem_t * sem, unsigned int n) { BOOL result; + register sem_t s = *sem; - pthread_mutex_lock(&sem->mutex); + EnterCriticalSection(&s->sem_lock_cs); - if (sem->value + n > sem->value) + if (s->value + n > s->value) { - sem->value += n; - SetEvent(sem->event); + s->value += n; + SetEvent(s->event); result = TRUE; } else @@ -316,7 +333,7 @@ ptw32_increase_semaphore(sem_t * sem, unsigned int n) result = FALSE; } - pthread_mutex_unlock(&sem->mutex); + LeaveCriticalSection(&s->sem_lock_cs); return result; } @@ -355,7 +372,7 @@ sem_wait (sem_t * sem) { int result = 0; - if (sem == NULL) + if (sem == NULL || *sem == NULL) { result = EINVAL; } @@ -364,7 +381,7 @@ sem_wait (sem_t * sem) #ifdef NEED_SEM - result = pthreadCancelableWait (sem->event); + result = pthreadCancelableWait ((*sem)->event); #else /* NEED_SEM */ @@ -419,7 +436,7 @@ sem_post (sem_t * sem) { int result = 0; - if (sem == NULL) + if (sem == NULL || *sem == NULL) { result = EINVAL; } -- cgit v1.2.3