replace : iotivity -> iotivity-sec
[platform/upstream/iotivity.git] / resource / c_common / octhread / src / posix / octhread.c
@@ -37,6 +37,7 @@
 #endif
 
 #include "iotivity_config.h"
+#include "octhread.h"
 #ifdef HAVE_STRING_H
 #include <string.h>
 #endif
 #ifdef HAVE_SYS_TIME_H
 #include <sys/time.h>
 #endif
-#ifdef HAVE_WINSOCK2_H
-#include <winsock2.h>
-#endif
 #include <stdio.h>
 #include <errno.h>
 #include <assert.h>
 #include <oic_malloc.h>
-#include "camutex.h"
 #include "logger.h"
 
 /**
@@ -90,45 +87,128 @@ static const uint64_t NANOSECS_PER_SEC      = 1000000000L;
 
 typedef struct _tagMutexInfo_t
 {
-#if defined(_WIN32)
-    CRITICAL_SECTION mutex;
-#else
     pthread_mutex_t mutex;
-#endif
-} ca_mutex_internal;
+} oc_mutex_internal;
 
 typedef struct _tagEventInfo_t
 {
-#if defined(_WIN32)
-    CONDITION_VARIABLE cond;
-#else
     pthread_cond_t cond;
     pthread_condattr_t condattr;
+} oc_cond_internal;
+
+typedef struct _tagThreadInfo_t
+{
+    pthread_t thread;
+    pthread_attr_t  threadattr;
+} oc_thread_internal;
+
+#ifndef __TIZENRT__
+OCThreadResult_t oc_thread_new(oc_thread *t, void *(*start_routine)(void *), void *arg)
+#else
+OCThreadResult_t oc_thread_new(oc_thread *t, void *(*start_routine)(void *), void *arg,
+                                   const char *task_name, int stack_size)
+#endif
+{
+    OCThreadResult_t res = OC_THREAD_SUCCESS;
+    oc_thread_internal *threadInfo = (oc_thread_internal*)OICMalloc(sizeof(oc_thread_internal));
+    if (NULL != threadInfo)
+    {
+#ifdef __TIZENRT__
+        pthread_attr_t attr;
+        pthread_attr_init(&attr);
+        struct sched_param prio;
+        prio.sched_priority = 90;
+        (void)pthread_attr_setschedparam(&attr, &prio);
+        (void)pthread_attr_setstacksize(&attr, stack_size);
+        int result = pthread_create(&threadInfo->thread, &attr, start_routine, arg);
+        pthread_setname_np(threadInfo->thread, task_name);
+#else
+        int result = pthread_create(&threadInfo->thread, NULL, start_routine, arg);
+#endif
+        if (result != 0)
+        {
+            res = OC_THREAD_CREATE_FAILURE;
+            *t = NULL;
+            OICFree(threadInfo);
+            OIC_LOG_V(ERROR, TAG, "%s: pthread_create failed", __func__);
+        }
+        else
+        {
+            *t = (oc_thread)threadInfo;
+        }
+    }
+    else
+    {
+        OIC_LOG_V(ERROR, TAG, "%s Failed to allocate thread!", __func__);
+        *t = NULL;
+        res = OC_THREAD_ALLOCATION_FAILURE;
+    }
+    return res;
+}
+
+OCThreadResult_t oc_thread_free(oc_thread t)
+{
+    OCThreadResult_t res = OC_THREAD_SUCCESS;
+    oc_thread_internal *threadInfo = (oc_thread_internal*) t;
+    if (threadInfo)
+    {
+        OICFree(threadInfo);
+    }
+    else
+    {
+        OIC_LOG_V(ERROR, TAG, "%s Invalid thread !", __func__);
+        res = OC_THREAD_INVALID;
+    }
+    return res;
+}
+
+OCThreadResult_t oc_thread_wait(oc_thread t)
+{
+    OCThreadResult_t res = OC_THREAD_SUCCESS;
+    oc_thread_internal *threadInfo = (oc_thread_internal*) t;
+    int joinres = pthread_join(threadInfo->thread, NULL);
+    if (0 != joinres)
+    {
+        OIC_LOG_V(ERROR, TAG, "Failed to join thread with error %d", joinres);
+        res = OC_THREAD_WAIT_FAILURE;
+    }
+
+    return res;
+}
+
+#ifdef __TIZEN__
+OCThreadResult_t oc_thread_cancel(oc_thread t)
+{
+    OCThreadResult_t res = OC_THREAD_SUCCESS;
+    oc_thread_internal *threadInfo = (oc_thread_internal*) t;
+    int ret = pthread_cancel(threadInfo->thread);
+    if (0 != ret)
+    {
+        OIC_LOG_V(ERROR, TAG, "Failed to cancel thread with error %d", ret);
+        res = OC_THREAD_CANCEL_FAILURE;
+    }
+
+    return res;
+}
 #endif
-} ca_cond_internal;
 
-ca_mutex ca_mutex_new(void)
+oc_mutex oc_mutex_new(void)
 {
-    ca_mutex retVal = NULL;
-    ca_mutex_internal *mutexInfo = (ca_mutex_internal*) OICMalloc(sizeof(ca_mutex_internal));
+    oc_mutex retVal = NULL;
+    oc_mutex_internal *mutexInfo = (oc_mutex_internal*) OICMalloc(sizeof(oc_mutex_internal));
     if (NULL != mutexInfo)
     {
-#if defined(_WIN32)
-        InitializeCriticalSection(&mutexInfo->mutex);
-        retVal = (ca_mutex)mutexInfo;
-#else
         // create the mutex with the attributes set
         int ret=pthread_mutex_init(&(mutexInfo->mutex), PTHREAD_MUTEX_DEFAULT);
         if (0 == ret)
         {
-            retVal = (ca_mutex) mutexInfo;
+            retVal = (oc_mutex) mutexInfo;
         }
         else
         {
             OIC_LOG_V(ERROR, TAG, "%s Failed to initialize mutex !", __func__);
             OICFree(mutexInfo);
         }
-#endif
     }
     else
     {
@@ -138,18 +218,12 @@ ca_mutex ca_mutex_new(void)
     return retVal;
 }
 
-bool ca_mutex_free(ca_mutex mutex)
+bool oc_mutex_free(oc_mutex mutex)
 {
     bool bRet=false;
-
-    ca_mutex_internal *mutexInfo = (ca_mutex_internal*) mutex;
+    oc_mutex_internal *mutexInfo = (oc_mutex_internal*) mutex;
     if (mutexInfo)
     {
-#if defined(_WIN32)
-        DeleteCriticalSection(&mutexInfo->mutex);
-        OICFree(mutexInfo);
-        bRet=true;
-#else
         int ret = pthread_mutex_destroy(&mutexInfo->mutex);
         if (0 == ret)
         {
@@ -160,7 +234,6 @@ bool ca_mutex_free(ca_mutex mutex)
         {
             OIC_LOG_V(ERROR, TAG, "%s Failed to free mutex !", __func__);
         }
-#endif
     }
     else
     {
@@ -170,63 +243,54 @@ bool ca_mutex_free(ca_mutex mutex)
     return bRet;
 }
 
-void ca_mutex_lock(ca_mutex mutex)
+void oc_mutex_lock(oc_mutex mutex)
 {
-    ca_mutex_internal *mutexInfo = (ca_mutex_internal*) mutex;
+    oc_mutex_internal *mutexInfo = (oc_mutex_internal*) mutex;
     if (mutexInfo)
     {
-#if defined(_WIN32)
-        EnterCriticalSection(&mutexInfo->mutex);
-#else
         int ret = pthread_mutex_lock(&mutexInfo->mutex);
         if(ret != 0)
         {
             OIC_LOG_V(ERROR, TAG, "Pthread Mutex lock failed: %d", ret);
             exit(ret);
         }
-#endif
     }
     else
     {
         OIC_LOG_V(ERROR, TAG, "%s Invalid mutex !", __func__);
-        return;
     }
 }
 
-void ca_mutex_unlock(ca_mutex mutex)
+void oc_mutex_unlock(oc_mutex mutex)
 {
-    ca_mutex_internal *mutexInfo = (ca_mutex_internal*) mutex;
+    oc_mutex_internal *mutexInfo = (oc_mutex_internal*) mutex;
     if (mutexInfo)
     {
-#if defined(_WIN32)
-        LeaveCriticalSection(&mutexInfo->mutex);
-#else
+#if defined(__TIZENRT__)
+        if (mutexInfo->mutex.pid == 0)
+        {
+            return;
+        }
+#endif
         int ret = pthread_mutex_unlock(&mutexInfo->mutex);
-        if(ret != 0)
+        if (ret != 0)
         {
             OIC_LOG_V(ERROR, TAG, "Pthread Mutex unlock failed: %d", ret);
             exit(ret);
         }
-        (void)ret;
-#endif
     }
     else
     {
         OIC_LOG_V(ERROR, TAG, "%s: Invalid mutex !", __func__);
-        return;
     }
 }
 
-ca_cond ca_cond_new(void)
+oc_cond oc_cond_new(void)
 {
-    ca_cond retVal = NULL;
-    ca_cond_internal *eventInfo = (ca_cond_internal*) OICMalloc(sizeof(ca_cond_internal));
+    oc_cond retVal = NULL;
+    oc_cond_internal *eventInfo = (oc_cond_internal*) OICMalloc(sizeof(oc_cond_internal));
     if (NULL != eventInfo)
     {
-#if defined(_WIN32)
-        InitializeConditionVariable(&eventInfo->cond);
-        retVal = (ca_cond) eventInfo;
-#else
         int ret = pthread_condattr_init(&(eventInfo->condattr));
         if(0 != ret)
         {
@@ -258,7 +322,7 @@ ca_cond ca_cond_new(void)
         ret = pthread_cond_init(&(eventInfo->cond), &(eventInfo->condattr));
         if (0 == ret)
         {
-            retVal = (ca_cond) eventInfo;
+            retVal = (oc_cond) eventInfo;
         }
         else
         {
@@ -266,7 +330,6 @@ ca_cond ca_cond_new(void)
             pthread_condattr_destroy(&(eventInfo->condattr));
             OICFree(eventInfo);
         }
-#endif
     }
     else
     {
@@ -276,14 +339,11 @@ ca_cond ca_cond_new(void)
     return retVal;
 }
 
-void ca_cond_free(ca_cond cond)
+void oc_cond_free(oc_cond cond)
 {
-    ca_cond_internal *eventInfo = (ca_cond_internal*) cond;
+    oc_cond_internal *eventInfo = (oc_cond_internal*) cond;
     if (eventInfo != NULL)
     {
-#if defined(_WIN32)
-        OICFree(cond);
-#else
         int ret = pthread_cond_destroy(&(eventInfo->cond));
         int ret2 = pthread_condattr_destroy(&(eventInfo->condattr));
         if (0 == ret && 0 == ret2)
@@ -295,7 +355,6 @@ void ca_cond_free(ca_cond cond)
             OIC_LOG_V(ERROR, TAG, "%s: Failed to destroy condition variable %d, %d",
                     __func__, ret, ret2);
         }
-#endif
     }
     else
     {
@@ -303,20 +362,16 @@ void ca_cond_free(ca_cond cond)
     }
 }
 
-void ca_cond_signal(ca_cond cond)
+void oc_cond_signal(oc_cond cond)
 {
-    ca_cond_internal *eventInfo = (ca_cond_internal*) cond;
+    oc_cond_internal *eventInfo = (oc_cond_internal*) cond;
     if (eventInfo != NULL)
     {
-#if defined(_WIN32)
-        WakeConditionVariable(&eventInfo->cond);
-#else
         int ret = pthread_cond_signal(&(eventInfo->cond));
         if (0 != ret)
         {
             OIC_LOG_V(ERROR, TAG, "%s: Failed to signal condition variable", __func__);
         }
-#endif
     }
     else
     {
@@ -324,20 +379,16 @@ void ca_cond_signal(ca_cond cond)
     }
 }
 
-void ca_cond_broadcast(ca_cond cond)
+void oc_cond_broadcast(oc_cond cond)
 {
-    ca_cond_internal* eventInfo = (ca_cond_internal*) cond;
+    oc_cond_internal* eventInfo = (oc_cond_internal*) cond;
     if (eventInfo != NULL)
     {
-#if defined(_WIN32)
-        WakeAllConditionVariable(&eventInfo->cond);
-#else
         int ret = pthread_cond_broadcast(&(eventInfo->cond));
         if (0 != ret)
         {
             OIC_LOG_V(ERROR, TAG, "%s: failed to signal condition variable", __func__);
         }
-#endif
     }
     else
     {
@@ -345,9 +396,9 @@ void ca_cond_broadcast(ca_cond cond)
     }
 }
 
-void ca_cond_wait(ca_cond cond, ca_mutex mutex)
+void oc_cond_wait(oc_cond cond, oc_mutex mutex)
 {
-    ca_cond_wait_for(cond, mutex, 0L);
+    oc_cond_wait_for(cond, mutex, 0L);
 }
 
 #ifndef TIMEVAL_TO_TIMESPEC
@@ -357,8 +408,7 @@ void ca_cond_wait(ca_cond cond, ca_mutex mutex)
 }
 #endif
 
-#if !defined(_WIN32)
-struct timespec ca_get_current_time()
+struct timespec oc_get_current_time()
 {
 #if defined(__ANDROID__) || _POSIX_TIMERS > 0
     struct timespec ts;
@@ -373,7 +423,7 @@ struct timespec ca_get_current_time()
 #endif
 }
 
-void ca_add_microseconds_to_timespec(struct timespec* ts, uint64_t microseconds)
+void oc_add_microseconds_to_timespec(struct timespec* ts, uint64_t microseconds)
 {
     time_t secPart = microseconds/USECS_PER_SEC;
     uint64_t nsecPart = (microseconds % USECS_PER_SEC) * NANOSECS_PER_USECS;
@@ -383,48 +433,28 @@ void ca_add_microseconds_to_timespec(struct timespec* ts, uint64_t microseconds)
     ts->tv_nsec = (totalNs)% NANOSECS_PER_SEC;
     ts->tv_sec += secPart + secOfNs;
 }
-#endif
 
-CAWaitResult_t ca_cond_wait_for(ca_cond cond, ca_mutex mutex, uint64_t microseconds)
+OCWaitResult_t oc_cond_wait_for(oc_cond cond, oc_mutex mutex, uint64_t microseconds)
 {
-    CAWaitResult_t retVal = CA_WAIT_INVAL;
+    OCWaitResult_t retVal = OC_WAIT_INVAL;
 
-    ca_cond_internal *eventInfo = (ca_cond_internal*) cond;
-    ca_mutex_internal *mutexInfo = (ca_mutex_internal*) mutex;
+    oc_cond_internal *eventInfo = (oc_cond_internal*) cond;
+    oc_mutex_internal *mutexInfo = (oc_mutex_internal*) mutex;
 
     if (NULL == mutexInfo)
     {
         OIC_LOG_V(ERROR, TAG, "%s: Invalid mutex", __func__);
-        return CA_WAIT_INVAL;
+        return OC_WAIT_INVAL;
     }
 
     if (NULL == eventInfo)
     {
         OIC_LOG_V(ERROR, TAG, "%s: Invalid condition", __func__);
-        return CA_WAIT_INVAL;
+        return OC_WAIT_INVAL;
     }
 
     if (microseconds > 0)
     {
-#if defined(_WIN32)
-        // Wait for the given time
-        DWORD milli = (DWORD)(microseconds / 1000);
-        if (!SleepConditionVariableCS(&eventInfo->cond, &mutexInfo->mutex, milli))
-        {
-            if (GetLastError() == ERROR_TIMEOUT)
-            {
-                retVal = CA_WAIT_TIMEDOUT;
-            }
-            else
-            {
-                OIC_LOG_V(ERROR, TAG, "SleepConditionVariableCS() with Timeout failed %i", GetLastError());
-                retVal = CA_WAIT_INVAL;
-            }
-        }else
-        {
-            retVal = CA_WAIT_SUCCESS;
-        }
-#else
         int ret = 0;
         struct timespec abstime = { .tv_sec = 0 };
 
@@ -438,8 +468,8 @@ CAWaitResult_t ca_cond_wait_for(ca_cond cond, ca_mutex mutex, uint64_t microseco
         } else
 #endif
         {
-             abstime = ca_get_current_time();
-            ca_add_microseconds_to_timespec(&abstime, microseconds);
+             abstime = oc_get_current_time();
+            oc_add_microseconds_to_timespec(&abstime, microseconds);
 
             //Wait for the given time
             ret = pthread_cond_timedwait(&(eventInfo->cond), &(mutexInfo->mutex), &abstime);
@@ -449,39 +479,26 @@ CAWaitResult_t ca_cond_wait_for(ca_cond cond, ca_mutex mutex, uint64_t microseco
         {
             case 0:
                 // Success
-                retVal = CA_WAIT_SUCCESS;
+                retVal = OC_WAIT_SUCCESS;
                 break;
             case ETIMEDOUT:
-                retVal = CA_WAIT_TIMEDOUT;
+                retVal = OC_WAIT_TIMEDOUT;
                 break;
             case EINVAL:
                 OIC_LOG_V(ERROR, TAG, "%s: condition, mutex, or abstime is Invalid", __func__);
-                retVal = CA_WAIT_INVAL;
+                retVal = OC_WAIT_INVAL;
                 break;
             default:
                 OIC_LOG_V(ERROR, TAG, "%s: pthread_cond_timedwait returned %d", __func__, retVal);
-                retVal = CA_WAIT_INVAL;
+                retVal = OC_WAIT_INVAL;
                 break;
         }
-#endif
     }
     else
     {
-#if defined(_WIN32)
-        // Wait forever
-        if (!SleepConditionVariableCS(&eventInfo->cond, &mutexInfo->mutex, INFINITE))
-        {
-            OIC_LOG_V(ERROR, TAG, "SleepConditionVariableCS() w/o Timeout failed %i", GetLastError());
-            retVal = CA_WAIT_INVAL;
-        }else
-        {
-            retVal = CA_WAIT_SUCCESS;
-        }
-#else
         // Wait forever
         int ret = pthread_cond_wait(&eventInfo->cond, &mutexInfo->mutex);
-        retVal = ret == 0 ? CA_WAIT_SUCCESS : CA_WAIT_INVAL;
-#endif
+        retVal = ret == 0 ? OC_WAIT_SUCCESS : OC_WAIT_INVAL;
     }
     return retVal;
 }