Tools/NetTest - TCP stack testing, going well
[tpg/acess2.git] / Tools / nativelib / threads_int.c
index 2274eea..87c60b1 100644 (file)
@@ -4,26 +4,52 @@
  *
  * threads_int.c
  * - Internal threading functions
+ *
+ * POSIX Mutex/Semaphore management
+ * Wait state
  */
+#define DEBUG  1
 #include <stddef.h>
 #include <stdlib.h>
 #include <stdint.h>
+#include <stdio.h>     // printf debugging
 #include <acess_logging.h>
 #include <threads_int.h>
 #include <pthread_weak.h>
+#include <shortlock.h>
 
 // === TYPES ===
-typedef struct sThread tThread;
 struct sThreadIntMutex { int lock; };
 struct sThreadIntSem { int val; };
 
+// === PROTOTYPES ===
+
 // === CODE ===
+int Threads_int_ThreadingEnabled(void)
+{
+       return !!pthread_create;
+}
+
+tThreadIntMutex *Threads_int_MutexCreate(void)
+{
+       if( Threads_int_ThreadingEnabled() )
+       {
+               tThreadIntMutex *ret = malloc(sizeof(pthread_mutex_t));
+               pthread_mutex_init( (void*)ret, NULL );
+               return ret;
+       }
+       else
+       {
+               return calloc(sizeof(tThreadIntMutex), 1);
+       }
+}
+
 void Threads_int_MutexLock(tThreadIntMutex *Mutex)
 {
        if( !Mutex ) {
                return ;
        }
-       if( pthread_mutex_lock )
+       if( Threads_int_ThreadingEnabled() )
        {
                pthread_mutex_lock( (void*)Mutex );
        }
@@ -41,7 +67,7 @@ void Threads_int_MutexRelease(tThreadIntMutex *Mutex)
                return ;
        }
 
-       if( pthread_mutex_unlock )
+       if( Threads_int_ThreadingEnabled() )
        {
                pthread_mutex_unlock( (void*)Mutex );
        }
@@ -53,11 +79,25 @@ void Threads_int_MutexRelease(tThreadIntMutex *Mutex)
        }
 }
 
+tThreadIntSem *Threads_int_SemCreate(void)
+{
+       if( Threads_int_ThreadingEnabled() )
+       {
+               tThreadIntSem *ret = malloc(sizeof(sem_t));
+               sem_init( (void*)ret, 0, 0 );
+               return ret;
+       }
+       else
+       {
+               return calloc(sizeof(tThreadIntSem), 1);
+       }
+}
+
 void Threads_int_SemSignal(tThreadIntSem *Sem)
 {
-       if( sem_wait )
+       if( Threads_int_ThreadingEnabled() )
        {
-               sem_wait( (void*)Sem );
+               sem_post( (void*)Sem );
        }
        else
        {
@@ -67,9 +107,15 @@ void Threads_int_SemSignal(tThreadIntSem *Sem)
 
 void Threads_int_SemWaitAll(tThreadIntSem *Sem)
 {
-       if( sem_post )
+       if( Threads_int_ThreadingEnabled() )
        {
-               sem_post( (void*)Sem );
+               // TODO: Handle multiples
+               LOG("Waiting on %p", Sem);
+               sem_wait( (void*)Sem );
+               LOG("Wait 1 done, cleaning up");
+               while( sem_trywait((void*)Sem) == 0 )
+                       ;
+               LOG("Wait over");
        }
        else
        {
@@ -82,17 +128,19 @@ void Threads_int_SemWaitAll(tThreadIntSem *Sem)
 void *Threads_int_ThreadRoot(void *ThreadPtr)
 {
        tThread *thread = ThreadPtr;
+       lpThreads_This = thread;
+       Log_Debug("Threads", "SpawnFcn: %p, SpawnData: %p", thread->SpawnFcn, thread->SpawnData);
        thread->SpawnFcn(thread->SpawnData);
        return NULL;
 }
 
 int Threads_int_CreateThread(tThread *Thread)
 {
-       if( pthread_create )
+       if( Threads_int_ThreadingEnabled() )
        {
                pthread_t *pthread = malloc(sizeof(pthread_t));
                Thread->ThreadHandle = pthread;
-               return pthread_create(pthread, NULL, Threads_int_ThreadRoot, Thread);
+               return pthread_create(pthread, NULL, &Threads_int_ThreadRoot, Thread);
        }
        else
        {
@@ -101,3 +149,48 @@ int Threads_int_CreateThread(tThread *Thread)
        }
 }
 
+void SHORTLOCK(tShortSpinlock *Lock)
+{
+       if( Threads_int_ThreadingEnabled() )
+       {
+               if( !*Lock ) {
+                       *Lock = malloc(sizeof(pthread_mutex_t));
+                       pthread_mutex_init(*Lock, NULL);
+               }
+//             printf("%p: SHORTLOCK wait\n", lpThreads_This);
+               pthread_mutex_lock(*Lock);
+//             printf("%p: SHORTLOCK held %p\n", lpThreads_This, __builtin_return_address(0));
+       }
+       else
+       {
+               if(*Lock)       Log_KernelPanic("---", "Double short lock");
+               *Lock = (void*)1;
+       }
+}
+
+void SHORTREL(tShortSpinlock *Lock)
+{
+       if( Threads_int_ThreadingEnabled() )
+       {
+               pthread_mutex_unlock(*Lock);
+//             printf("%p: SHORTLOCK rel\n", lpThreads_This);
+       }
+       else
+       {
+               if(!*Lock)      Log_Notice("---", "Short release when not held");
+               *Lock = NULL;
+       }
+}
+
+int CPU_HAS_LOCK(tShortSpinlock *Lock)
+{
+       if( Threads_int_ThreadingEnabled() )
+       {
+               Log_KernelPanic("---", "TODO: CPU_HAS_LOCK with threading enabled");
+               return 0;
+       }
+       else
+       {
+               return 0;
+       }
+}

UCC git Repository :: git.ucc.asn.au