

#ifndef _JL_UNIVERSAL_THREADS_H_
#define _JL_UNIVERSAL_THREADS_H_


/*
 * define UNIV_SEMA_IRIX or UNIV_SEMA_PTHREAD before including this file
 */


#ifdef UNIV_SEMA_IRIX

#include <stdlib.h>
#include <ulocks.h>

#define UNIV_THREAD					int
#define UNIV_THREAD_CREATE(t,f,a)	sproc(f, PR_SADDR, (a));

#define UNIV_SEMAHANDLE				usptr_t*
#define UNIV_SEMA					usptr_t*

#define UNIV_SEMA_VALID(s) (s)

#define UNIV_INIT_HANDLE(h,fname)	h = usinit(fname)
#define UNIV_NEW_SEMA(s,h)			s = usnewsema(h,1)

#define UNIV_HOLD_SEMA(s)			uspsema(s)
#define UNIV_RELEASE_SEMA(s)		usvsema(s)

#define UNIV_FREE_HANDLE(h)			usdetach(h)
#define UNIV_FREE_SEMA(s,h)			usfreesema(s,h)

#define UNIV_THREAD_RETURN_TYPE		void
#define UNIV_THREAD_RETURN_COMMAND	

#endif // ifdef UNIV_SEMA_IRIX



#ifdef UNIV_SEMA_PTHREAD

#include <stdlib.h>
#include <pthread.h>
#include <semaphore.h>

#define UNIV_THREAD					pthread_t
#define UNIV_THREAD_CREATE(t,f,a)	pthread_create(&(t), NULL, f, (a));

#define UNIV_SEMAHANDLE				int
#define UNIV_SEMA				sem_t

#define UNIV_SEMA_VALID(s) (1)

#define UNIV_INIT_HANDLE(h,fname)	0;
#define UNIV_NEW_SEMA(s,h)			sem_init (&(s), 0, 1)

#define UNIV_HOLD_SEMA(s)			sem_wait (&(s))
#define UNIV_RELEASE_SEMA(s)		sem_post(&(s))

#define UNIV_FREE_HANDLE(h)			h = 0;
#define UNIV_FREE_SEMA(s,h)			sem_destroy (&(s));

#define UNIV_THREAD_RETURN_TYPE		void*
#define UNIV_THREAD_RETURN_COMMAND	return NULL

#endif // ifdef UNIV_SEMA_PTHREAD

#ifdef UNIV_SEMA_PTHREAD_MUTEX

#include <stdlib.h>
#include <pthread.h>

#define UNIV_THREAD					pthread_t
#define UNIV_THREAD_CREATE(t,f,a)	pthread_create(&(t), NULL, f, (a));

#define UNIV_SEMAHANDLE				pthread_mutexattr_t
#define UNIV_SEMA				pthread_mutex_t

#define UNIV_SEMA_VALID(s) (1)

#define UNIV_INIT_HANDLE(h,fname)     pthread_mutexattr_init(&h)
#define UNIV_NEW_SEMA(s,h)                    pthread_mutex_init(&(s),&h)


#define UNIV_HOLD_SEMA(s)                     pthread_mutex_lock(&(s))
#define UNIV_RELEASE_SEMA(s)          pthread_mutex_unlock(&(s))

#define UNIV_FREE_HANDLE(h)                   pthread_mutexattr_destroy(&h)
#define UNIV_FREE_SEMA(s,h)                   pthread_mutex_destroy(&(s))

#define UNIV_THREAD_RETURN_TYPE		void*
#define UNIV_THREAD_RETURN_COMMAND	return NULL
#endif

#ifdef UNIV_SEMA_SOLARIS

#include <stdlib.h>
#include <thread.h>
#include <sched.h>


#define UNIV_THREAD					thread_t
#define UNIV_THREAD_CREATE(t,f,a)	thr_create(NULL, NULL, f, (a), NULL, &t);

#define UNIV_SEMAHANDLE				int
#define UNIV_SEMA				sema_t

#define UNIV_SEMA_VALID(s) (1)

#define UNIV_INIT_HANDLE(h,fname)	0;
#define UNIV_NEW_SEMA(s,h)			sema_init (&(s), 0, 0)

#define UNIV_HOLD_SEMA(s)			sema_wait (&(s))
#define UNIV_RELEASE_SEMA(s)		sema_post(&(s))

#define UNIV_FREE_HANDLE(h)			h = 0;
#define UNIV_FREE_SEMA(s,h)			sema_destroy (&(s));

#define UNIV_THREAD_RETURN_TYPE		void*
#define UNIV_THREAD_RETURN_COMMAND	return NULL

#endif


#ifdef UNIV_SEMA_CLONE

#include <stdlib.h>
#include <ulocks.h>

#define UNIV_THREAD					int
#define UNIV_THREAD_CREATE(t,f,a)	sproc(f, PR_SADDR, (a));

#define UNIV_SEMAHANDLE				int
#define UNIV_SEMA					int
#define UNIV_SEMA_VALID(s) (1)

#define UNIV_INIT_HANDLE(h,fname)	h = 1
#define UNIV_NEW_SEMA(s,h)			s = h

#define UNIV_HOLD_SEMA(s)			s = 1
#define UNIV_RELEASE_SEMA(s)		s = 1

#define UNIV_FREE_HANDLE(h)			h = 0
#define UNIV_FREE_SEMA(s,h)			s = h

#endif // ifdef UNIV_SEMA_CLONE



#ifdef UNIV_SEMA_NONE

#define UNIV_THREAD                               int
#define UNIV_THREAD_RETURN_TYPE void *

#define UNIV_SEMAHANDLE				int
#define UNIV_SEMA					int

#define UNIV_INIT_HANDLE(h,fname)	h = 1
#define UNIV_NEW_SEMA(s,h)			s = h
#define UNIV_SEMA_VALID(s) (1)

#define UNIV_HOLD_SEMA(s)			s = 1
#define UNIV_RELEASE_SEMA(s)		s = 1

#define UNIV_FREE_HANDLE(h)			h = 0
#define UNIV_FREE_SEMA(s,h)			s = h

#endif // ifdef UNIV_SEMA_NONE

#ifdef UNIV_SEMA_WINDOWS

#include <stdlib.h>
#include <pthread.h>

#define UNIV_THREAD					pthread_t
#define UNIV_THREAD_CREATE(t,f,a)	pthread_create(&(t), NULL, f, (a));

#define UNIV_SEMAHANDLE				pthread_mutexattr_t
#define UNIV_SEMA				pthread_mutex_t

#define UNIV_SEMA_VALID(s) (1)

#define UNIV_INIT_HANDLE(h,fname)     pthread_mutexattr_init(&h)
#define UNIV_NEW_SEMA(s,h)                    pthread_mutex_init(&(s),&h)

#define UNIV_HOLD_SEMA(s)                     pthread_mutex_lock(&(s))
#define UNIV_RELEASE_SEMA(s)          pthread_mutex_unlock(&(s))

#define UNIV_FREE_HANDLE(h)                   pthread_mutexattr_destroy(&h)
#define UNIV_FREE_SEMA(s,h)                   pthread_mutex_destroy(&(s))

#define UNIV_THREAD_RETURN_TYPE		void*
#define UNIV_THREAD_RETURN_COMMAND	return NULL
#endif


#endif // ifndef _JL_UNIVERSAL_SEMAPHORES_H_
