static TA_RetCode TA_SystemGlobalInit( void **globalToAlloc ) { TA_PROLOG TA_RetCode retCode; TA_SystemGlobal *global; TA_TRACE_BEGIN( TA_SystemGlobalInit ); TA_ASSERT( globalToAlloc != NULL ); *globalToAlloc = NULL; global = (TA_SystemGlobal *)TA_Malloc( sizeof( TA_SystemGlobal ) ); if( !global ) { TA_TRACE_RETURN( TA_ALLOC_ERR ); } memset( global, 0, sizeof( TA_SystemGlobal ) ); retCode = TA_StringCacheAlloc( &global->dirnameCache ); if( retCode != TA_SUCCESS ) { TA_Free( global ); TA_TRACE_RETURN( TA_ALLOC_ERR ); } retCode = TA_StringCacheAlloc( &global->filenameCache ); if( retCode != TA_SUCCESS ) { TA_StringCacheFree( global->dirnameCache ); TA_Free( global ); TA_TRACE_RETURN( TA_ALLOC_ERR ); } /* Success! Return the global to the caller. */ *globalToAlloc = global; TA_TRACE_RETURN( TA_SUCCESS ); }
TA_RetCode TA_Initialize( const TA_InitializeParam *param ) { /* Note: Keep that function simple. * No tracing, no stdio and no assert. */ TA_RetCode retCode; #if !defined( TA_SINGLE_THREAD ) unsigned int again; /* Boolean */ unsigned int i; #endif /* Allocate the "global variable" used to manage the global * variables of all other modules... */ memset( TA_Globals, 0, sizeof( TA_LibcPriv ) ); TA_Globals->magicNb = TA_LIBC_PRIV_MAGIC_NB; if( param ) { if( param->logOutput ) { /* Override someone intention to use stdin!? */ if( param->logOutput == stdin ) TA_Globals->stdioFile = stdout; else TA_Globals->stdioFile = param->logOutput; TA_Globals->stdioEnabled = 1; } if( param->userLocalDrive ) TA_Globals->localCachePath = param->userLocalDrive; } #if !defined( TA_SINGLE_THREAD ) /* For multithread, allocate all semaphores * protecting the module's globals. */ again = 1; for( i=0; i < TA_NB_GLOBAL_ID && again; i++ ) { retCode = TA_SemaInit( &(TA_Globals->moduleControl[i].sema), 1 ); if( retCode != TA_SUCCESS ) again = 0; } if( again == 0 ) { /* Clean-up and exit. */ for( i=0; i < TA_NB_GLOBAL_ID; i++ ) TA_SemaDestroy( &(TA_Globals->moduleControl[i].sema) ); memset( TA_Globals, 0, sizeof( TA_LibcPriv ) ); return TA_INTERNAL_ERROR(4); } #endif /* Force immediatly the initialization of the memory module. * Note: No call to the tracing capability are allowed in TA_MemInit. */ retCode = TA_MemInit( sizeof( TA_LibcPriv ) ); /* Force immediatly the initialization of the tracing module. */ if( retCode == TA_SUCCESS ) retCode = TA_TraceInit(); if( retCode != TA_SUCCESS ) { /* Clean-up and exit. */ #if !defined( TA_SINGLE_THREAD ) for( i=0; i < TA_NB_GLOBAL_ID; i++ ) TA_SemaDestroy( &(TA_Globals->moduleControl[i].sema) ); #endif memset( TA_Globals, 0, sizeof( TA_LibcPriv ) ); return TA_INTERNAL_ERROR(5); } /* Tracing can now be safely used by the memory module until * shutdown in TA_Shutdown. */ TA_Globals->traceEnabled = 1; /*** At this point, TA_Shutdown can be called to clean-up. ***/ /* Allocate the default string cache used throughout the library. */ retCode = TA_StringCacheAlloc( &(TA_Globals->dfltCache) ); if( retCode != TA_SUCCESS ) { TA_Shutdown(); return retCode; } return TA_SUCCESS; }