/***********************************************************************
 * 
 *  Copyright (C) 2006 Novell, Inc. All Rights Reserved.
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License as published by the Free Software Foundation; version 2.1
 *  of the License.
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Library Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; if not, Novell, Inc.
 * 
 *  To contact Novell about this file by physical or electronic mail, 
 *  you may find current contact information at www.novell.com.
 * 
 *  Author: Juan Carlos Luciani <jluciani@novell.com>
 *
 ***********************************************************************/

//===[ Include files ]=====================================================

#include "internal.h"

//===[ Type definitions ]==================================================

//
// Platform Mutex structure
//
typedef struct _PlatformMutex
{
   pthread_mutex_t   mutex;

} PlatformMutex, *PPlatformMutex;

//===[ Function prototypes ]===============================================

//===[ Global variables ]==================================================

// Path separator
char  pathCharString[] = "/";

// Modules configuration folder path
char  moduleConfigFolderPath[] = "/etc/CASA/authtoken/modules";

//
// Module synchronization mutex
// 
pthread_mutex_t   g_hModuleMutex = PTHREAD_MUTEX_INITIALIZER;

//
// Ipc client library path
//
#ifdef _LIB64
char  IpcClientLibraryPath[] = "/usr/lib64/libcasa_c_ipc.so";
#else
char  IpcClientLibraryPath[] = "/usr/lib/libcasa_c_ipc.so";
#endif


//++=======================================================================
HANDLE
PlatAllocMutex(void)
//
//  Arguments: 
//
//  Returns:   
//
//  Abstract:  
//
//  Notes:
//
//  Environment:
//
// L2
//=======================================================================--
{
   PlatformMutex        *pPlatMutex;
   pthread_mutexattr_t  mutexAttr;

   DbgTrace(2, "-PlatAllocMutex- Start\n", 0);

   // Allocate space for our mutex structure
   pPlatMutex = malloc(sizeof(*pPlatMutex));
   if (pPlatMutex)
   {
      // Finish initializing the mutex
      if (pthread_mutexattr_init(&mutexAttr) == 0)
      {
         if (pthread_mutexattr_settype(&mutexAttr, PTHREAD_MUTEX_RECURSIVE) == 0)
         {
            if (pthread_mutex_init(&pPlatMutex->mutex, &mutexAttr) != 0)
            {
               DbgTrace(0, "-PlatAllocMutex- Error %d initing mutex\n", errno);
               free(pPlatMutex);
               pPlatMutex = NULL;
            }
         }
         else
         {
            DbgTrace(0, "-PlatAllocMutex- Error %d setting mutex type\n", errno);
            free(pPlatMutex);
            pPlatMutex = NULL;
         }
      }
      else
      {
         DbgTrace(0, "-PlatAllocMutex- Error %d initing mutexattr\n", errno);
         free(pPlatMutex);
         pPlatMutex = NULL;
      }
   }
   else
   {
      DbgTrace(0, "-PlatAllocMutex- Memory allocation failure\n", 0);
   }

   DbgTrace(2, "-PlatAllocMutex- End, retHandle = %0X\n", (unsigned int) pPlatMutex);

   return (HANDLE) pPlatMutex;
}


//++=======================================================================
void
PlatDestroyMutex(HANDLE hMutex)
//
//  Arguments: 
//
//  Returns:   
//
//  Abstract:  
//
//  Notes:
//
//  Environment:
//
// L2
//=======================================================================--
{
   PlatformMutex  *pPlatMutex = (PlatformMutex*) hMutex;

   DbgTrace(2, "-PlatDestroyMutex- Start\n", 0);

   // Free the resources associated with the mutex
   pthread_mutex_destroy(&pPlatMutex->mutex);
   free(pPlatMutex);

   DbgTrace(2, "-PlatDestroyMutex- End\n", 0);
}


//++=======================================================================
void
PlatAcquireMutex(HANDLE hMutex)
//
//  Arguments: 
//
//  Returns:   
//
//  Abstract:  
//
//  Notes:
//
//  Environment:
//
// L2
//=======================================================================--
{
   PlatformMutex  *pPlatMutex = (PlatformMutex*) hMutex;

   DbgTrace(2, "-PlatAcquireMutex- Start\n", 0);

   // Acquire the mutex
   pthread_mutex_lock(&pPlatMutex->mutex);

   DbgTrace(2, "-PlatAcquireMutex- End\n", 0);
}


//++=======================================================================
void
PlatReleaseMutex(HANDLE hMutex)
//
//  Arguments: 
//
//  Returns:   
//
//  Abstract:  
//
//  Notes:
//
//  Environment:
//
// L2
//=======================================================================--
{
   PlatformMutex  *pPlatMutex = (PlatformMutex*) hMutex;

   DbgTrace(2, "-PlatReleaseMutex- Start\n", 0);

   // Release the mutex
   pthread_mutex_unlock(&pPlatMutex->mutex);

   DbgTrace(2, "-PlatRelease- End\n", 0);
}


//++=======================================================================
LIB_HANDLE
OpenLibrary(
   IN    char *pFileName)
//
//  Arguments: 
//
//  Returns:   
//
//  Abstract:  
//
//  Notes:
//
// L2
//=======================================================================--
{
   LIB_HANDLE  libHandle;

   DbgTrace(1, "-OpenLibrary- Start\n", 0);

   libHandle = dlopen(pFileName, RTLD_LAZY);
   if (libHandle == NULL)
   {
      DbgTrace(0, "-OpenLibrary- Not able to load library, error = %s\n", dlerror());
   }

   DbgTrace(1, "-OpenLibrary- End, handle = %0lX\n", (long) libHandle);

   return libHandle;
}


//++=======================================================================
void
CloseLibrary(
   IN    LIB_HANDLE libHandle)
//
//  Arguments: 
//
//  Returns:   
//
//  Abstract:  
//
//  Notes:
//
// L2
//=======================================================================--
{
   DbgTrace(1, "-CloseLibrary- Start\n", 0);

   dlclose(libHandle);

   DbgTrace(1, "-CloseLibrary- End\n", 0);
}


//++=======================================================================
void*
GetFunctionPtr(
   IN    LIB_HANDLE libHandle,
   IN    char *pFunctionName)
//
//  Arguments: 
//
//  Returns:   
//
//  Abstract:  
//
//  Notes:
//
// L2
//=======================================================================--
{
   void  *pFuncPtr;

   DbgTrace(1, "-GetFunctionPtr- Start\n", 0);

   pFuncPtr = dlsym(libHandle, pFunctionName);
   if (pFuncPtr == NULL)
   {
      DbgTrace(0, "-GetFunctionPtr- Not able to obtain func ptr, error = %s\n", dlerror());
   }

   DbgTrace(1, "-GetFunctionPtr- End, pFuncPtr = %0lX\n", (long) pFuncPtr);

   return pFuncPtr;
}


//++=======================================================================
//++=======================================================================
//++=======================================================================