ITT_EXTERN_C void _N_(fini_ittlib)(void) { __itt_api_fini_t* __itt_api_fini_ptr; static volatile TIDT current_thread = 0; if (__itt_ittapi_global.api_initialized) { __itt_mutex_lock(&__itt_ittapi_global.mutex); if (__itt_ittapi_global.api_initialized) { if (current_thread == 0) { current_thread = __itt_thread_id(); __itt_api_fini_ptr = (__itt_api_fini_t*)__itt_get_proc(__itt_ittapi_global.lib, "__itt_api_fini"); if (__itt_api_fini_ptr) __itt_api_fini_ptr(&__itt_ittapi_global); __itt_nullify_all_pointers(); /* TODO: !!! not safe !!! don't support unload so far. * if (__itt_ittapi_global.lib != NULL) * __itt_unload_lib(__itt_ittapi_global.lib); * __itt_ittapi_global.lib = NULL; */ __itt_ittapi_global.api_initialized = 0; current_thread = 0; } } __itt_mutex_unlock(&__itt_ittapi_global.mutex); } }
static void ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(thread_ignore),_init))(void) { TIDT tid = __itt_thread_id(); __itt_thread_info *h_tail, *h; if (!__itt_ittapi_global.api_initialized && __itt_ittapi_global.thread_list->tid == 0) { __itt_init_ittlib_name(NULL, __itt_group_all); if (ITTNOTIFY_NAME(thread_ignore) && ITTNOTIFY_NAME(thread_ignore) != ITT_VERSIONIZE(ITT_JOIN(_N_(thread_ignore),_init))) { ITTNOTIFY_NAME(thread_ignore)(); return; } } __itt_mutex_lock(&__itt_ittapi_global.mutex); for (h_tail = NULL, h = __itt_ittapi_global.thread_list; h != NULL; h_tail = h, h = h->next) if (h->tid == tid) break; if (h == NULL) { static const char* name = "unknown"; NEW_THREAD_INFO_A(&__itt_ittapi_global, h, h_tail, tid, __itt_thread_ignored, name); } else { h->state = __itt_thread_ignored; } __itt_mutex_unlock(&__itt_ittapi_global.mutex); }
static void ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_nameW),_init))(const wchar_t* name) { TIDT tid = __itt_thread_id(); __itt_thread_info *h_tail, *h; if (!__itt_ittapi_global.api_initialized && __itt_ittapi_global.thread_list->tid == 0) { __itt_init_ittlib_name(NULL, __itt_group_all); if (ITTNOTIFY_NAME(thread_set_nameW) && ITTNOTIFY_NAME(thread_set_nameW) != ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_nameW),_init))) { ITTNOTIFY_NAME(thread_set_nameW)(name); return; } } __itt_mutex_lock(&__itt_ittapi_global.mutex); for (h_tail = NULL, h = __itt_ittapi_global.thread_list; h != NULL; h_tail = h, h = h->next) if (h->tid == tid) break; if (h == NULL) { NEW_THREAD_INFO_W(&__itt_ittapi_global, h, h_tail, tid, __itt_thread_normal, name); } else { h->nameW = name ? _wcsdup(name) : NULL; } __itt_mutex_unlock(&__itt_ittapi_global.mutex); }
/* -------------------------------------------------------------------------- */ static void ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(pause),_init))(void) { if (!__itt_ittapi_global.api_initialized && __itt_ittapi_global.thread_list->tid == 0) { __itt_init_ittlib_name(NULL, __itt_group_all); if (ITTNOTIFY_NAME(pause) && ITTNOTIFY_NAME(pause) != ITT_VERSIONIZE(ITT_JOIN(_N_(pause),_init))) { ITTNOTIFY_NAME(pause)(); return; } } __itt_ittapi_global.state = __itt_collection_paused; } static void ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(resume),_init))(void) { if (!__itt_ittapi_global.api_initialized && __itt_ittapi_global.thread_list->tid == 0) { __itt_init_ittlib_name(NULL, __itt_group_all); if (ITTNOTIFY_NAME(resume) && ITTNOTIFY_NAME(resume) != ITT_VERSIONIZE(ITT_JOIN(_N_(resume),_init))) { ITTNOTIFY_NAME(resume)(); return; } } __itt_ittapi_global.state = __itt_collection_normal; } #if ITT_PLATFORM==ITT_PLATFORM_WIN static void ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_nameW),_init))(const wchar_t* name) { TIDT tid = __itt_thread_id(); __itt_thread_info *h_tail, *h; if (!__itt_ittapi_global.api_initialized && __itt_ittapi_global.thread_list->tid == 0) { __itt_init_ittlib_name(NULL, __itt_group_all); if (ITTNOTIFY_NAME(thread_set_nameW) && ITTNOTIFY_NAME(thread_set_nameW) != ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_nameW),_init))) { ITTNOTIFY_NAME(thread_set_nameW)(name); return; } } __itt_mutex_lock(&__itt_ittapi_global.mutex); for (h_tail = NULL, h = __itt_ittapi_global.thread_list; h != NULL; h_tail = h, h = h->next) if (h->tid == tid) break; if (h == NULL) { NEW_THREAD_INFO_W(&__itt_ittapi_global, h, h_tail, tid, __itt_thread_normal, name); } else { h->nameW = name ? _wcsdup(name) : NULL; } __itt_mutex_unlock(&__itt_ittapi_global.mutex); } static int ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(thr_name_setW),_init))(const wchar_t* name, int namelen) { namelen = namelen; ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_nameW),_init))(name); return 0; } static void ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_nameA),_init))(const char* name) #else /* ITT_PLATFORM==ITT_PLATFORM_WIN */ static void ITTAPI ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_name),_init))(const char* name) #endif /* ITT_PLATFORM==ITT_PLATFORM_WIN */ { TIDT tid = __itt_thread_id(); __itt_thread_info *h_tail, *h; if (!__itt_ittapi_global.api_initialized && __itt_ittapi_global.thread_list->tid == 0) { __itt_init_ittlib_name(NULL, __itt_group_all); #if ITT_PLATFORM==ITT_PLATFORM_WIN if (ITTNOTIFY_NAME(thread_set_nameA) && ITTNOTIFY_NAME(thread_set_nameA) != ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_nameA),_init))) { ITTNOTIFY_NAME(thread_set_nameA)(name); return; } #else /* ITT_PLATFORM==ITT_PLATFORM_WIN */ if (ITTNOTIFY_NAME(thread_set_name) && ITTNOTIFY_NAME(thread_set_name) != ITT_VERSIONIZE(ITT_JOIN(_N_(thread_set_name),_init))) { ITTNOTIFY_NAME(thread_set_name)(name); return; } #endif /* ITT_PLATFORM==ITT_PLATFORM_WIN */ } __itt_mutex_lock(&__itt_ittapi_global.mutex); for (h_tail = NULL, h = __itt_ittapi_global.thread_list; h != NULL; h_tail = h, h = h->next) if (h->tid == tid) break; if (h == NULL) { NEW_THREAD_INFO_A(&__itt_ittapi_global, h, h_tail, tid, __itt_thread_normal, name); } else { h->nameA = name ? __itt_fstrdup(name) : NULL; } __itt_mutex_unlock(&__itt_ittapi_global.mutex); }
ITT_EXTERN_C int _N_(init_ittlib)(const char* lib_name, __itt_group_id init_groups) { register int i; __itt_group_id groups; #ifdef ITT_COMPLETE_GROUP __itt_group_id zero_group = __itt_group_none; #endif /* ITT_COMPLETE_GROUP */ static volatile TIDT current_thread = 0; if (!__itt_ittapi_global.api_initialized) { #ifndef ITT_SIMPLE_INIT ITT_MUTEX_INIT_AND_LOCK(__itt_ittapi_global); #endif /* ITT_SIMPLE_INIT */ if (!__itt_ittapi_global.api_initialized) { if (current_thread == 0) { current_thread = __itt_thread_id(); __itt_ittapi_global.thread_list->tid = current_thread; if (lib_name == NULL) lib_name = __itt_get_lib_name(); groups = __itt_get_groups(); if (groups != __itt_group_none || lib_name != NULL) { __itt_ittapi_global.lib = __itt_load_lib((lib_name == NULL) ? ittnotify_lib_name : lib_name); if (__itt_ittapi_global.lib != NULL) { __itt_api_init_t* __itt_api_init_ptr; int lib_version = __itt_lib_version(__itt_ittapi_global.lib); switch (lib_version) { case 0: groups = __itt_group_legacy; case 1: /* Fill all pointers from dynamic library */ for (i = 0; __itt_ittapi_global.api_list_ptr[i].name != NULL; i++) { if (__itt_ittapi_global.api_list_ptr[i].group & groups & init_groups) { *__itt_ittapi_global.api_list_ptr[i].func_ptr = (void*)__itt_get_proc(__itt_ittapi_global.lib, __itt_ittapi_global.api_list_ptr[i].name); if (*__itt_ittapi_global.api_list_ptr[i].func_ptr == NULL) { /* Restore pointers for function with static implementation */ *__itt_ittapi_global.api_list_ptr[i].func_ptr = __itt_ittapi_global.api_list_ptr[i].null_func; __itt_report_error(__itt_error_no_symbol, lib_name, __itt_ittapi_global.api_list_ptr[i].name); #ifdef ITT_COMPLETE_GROUP zero_group = (__itt_group_id)(zero_group | __itt_ittapi_global.api_list_ptr[i].group); #endif /* ITT_COMPLETE_GROUP */ } } else *__itt_ittapi_global.api_list_ptr[i].func_ptr = __itt_ittapi_global.api_list_ptr[i].null_func; } if (groups == __itt_group_legacy) { /* Compatibility with legacy tools */ ITTNOTIFY_NAME(thread_ignore) = ITTNOTIFY_NAME(thr_ignore); #if ITT_PLATFORM==ITT_PLATFORM_WIN ITTNOTIFY_NAME(sync_createA) = ITTNOTIFY_NAME(sync_set_nameA); ITTNOTIFY_NAME(sync_createW) = ITTNOTIFY_NAME(sync_set_nameW); #else /* ITT_PLATFORM!=ITT_PLATFORM_WIN */ ITTNOTIFY_NAME(sync_create) = ITTNOTIFY_NAME(sync_set_name); #endif /* ITT_PLATFORM==ITT_PLATFORM_WIN */ ITTNOTIFY_NAME(sync_prepare) = ITTNOTIFY_NAME(notify_sync_prepare); ITTNOTIFY_NAME(sync_cancel) = ITTNOTIFY_NAME(notify_sync_cancel); ITTNOTIFY_NAME(sync_acquired) = ITTNOTIFY_NAME(notify_sync_acquired); ITTNOTIFY_NAME(sync_releasing) = ITTNOTIFY_NAME(notify_sync_releasing); } #ifdef ITT_COMPLETE_GROUP for (i = 0; __itt_ittapi_global.api_list_ptr[i].name != NULL; i++) if (__itt_ittapi_global.api_list_ptr[i].group & zero_group) *__itt_ittapi_global.api_list_ptr[i].func_ptr = __itt_ittapi_global.api_list_ptr[i].null_func; #endif /* ITT_COMPLETE_GROUP */ break; case 2: __itt_api_init_ptr = (__itt_api_init_t*)__itt_get_proc(__itt_ittapi_global.lib, "__itt_api_init"); if (__itt_api_init_ptr) __itt_api_init_ptr(&__itt_ittapi_global, init_groups); break; } } else { __itt_nullify_all_pointers(); __itt_report_error(__itt_error_no_module, lib_name, #if ITT_PLATFORM==ITT_PLATFORM_WIN __itt_system_error() #else /* ITT_PLATFORM==ITT_PLATFORM_WIN */ dlerror() #endif /* ITT_PLATFORM==ITT_PLATFORM_WIN */ ); } } else { __itt_nullify_all_pointers(); } __itt_ittapi_global.api_initialized = 1; current_thread = 0; /* !!! Just to avoid unused code elimination !!! */ if (__itt_fini_ittlib_ptr == _N_(fini_ittlib)) current_thread = 0; } } #ifndef ITT_SIMPLE_INIT __itt_mutex_unlock(&__itt_ittapi_global.mutex); #endif /* ITT_SIMPLE_INIT */ } /* Evaluating if any function ptr is non empty and it's in init_groups */ for (i = 0; __itt_ittapi_global.api_list_ptr[i].name != NULL; i++) if (*__itt_ittapi_global.api_list_ptr[i].func_ptr != __itt_ittapi_global.api_list_ptr[i].null_func && __itt_ittapi_global.api_list_ptr[i].group & init_groups) return 1; return 0; }
static int _N_(init_ittlib)(const char* lib_name, __itt_group_id groups) { int i, ret = 0; static volatile TIDT current_thread = 0; if (!ittnotify_init) { #ifndef ITT_SIMPLE_INIT static mutex_t mutex; static volatile int inter_counter = 0; static volatile int mutex_initialized = 0; if (!mutex_initialized) { if (__itt_interlocked_increment(&inter_counter) == 1) { __itt_mutex_init(&mutex); mutex_initialized = 1; } else while (!mutex_initialized) __itt_thread_yield(); } __itt_mutex_lock(&mutex); #endif /* ITT_SIMPLE_INIT */ if (!ittnotify_init) { if (current_thread == 0) { current_thread = __itt_thread_id(); if (groups == __itt_group_none) groups = __itt_get_groups(); if (groups == __itt_group_none) { // Clear all pointers for (i = 0; func_map[i].name != NULL; i++ ) *func_map[i].func_ptr = NULL; } else { __itt_group_id zero_group = __itt_group_none; if (lib_name == NULL) lib_name = __itt_get_lib_name(); ittnotify_lib = __itt_load_lib(lib_name); if (ittnotify_lib != NULL) { if (__itt_is_legacy_lib(ittnotify_lib)) groups = __itt_group_legacy; for (i = 0; func_map[i].name != NULL; i++) { if (func_map[i].group & groups) { *func_map[i].func_ptr = (void*)__itt_get_proc(ittnotify_lib, func_map[i].name); if (*func_map[i].func_ptr == NULL) { __itt_report_error(__itt_error_no_symbol, lib_name, func_map[i].name ); zero_group = (__itt_group_id)(zero_group | func_map[i].group); } } else *func_map[i].func_ptr = NULL; } if (groups == __itt_group_legacy) { // Compatibility with legacy tools ITTNOTIFY_NAME(sync_prepare) = ITTNOTIFY_NAME(notify_sync_prepare); ITTNOTIFY_NAME(sync_cancel) = ITTNOTIFY_NAME(notify_sync_cancel); ITTNOTIFY_NAME(sync_acquired) = ITTNOTIFY_NAME(notify_sync_acquired); ITTNOTIFY_NAME(sync_releasing) = ITTNOTIFY_NAME(notify_sync_releasing); } } else { // Clear all pointers for (i = 0; func_map[i].name != NULL; i++) *func_map[i].func_ptr = NULL; __itt_report_error(__itt_error_no_module, lib_name, #if ITT_PLATFORM==ITT_PLATFORM_WIN __itt_system_error() #else /* ITT_PLATFORM==ITT_PLATFORM_WIN */ dlerror() #endif /* ITT_PLATFORM==ITT_PLATFORM_WIN */ ); } #ifdef ITT_COMPLETE_GROUP for (i = 0; func_map[i].name != NULL; i++) if (func_map[i].group & zero_group) *func_map[i].func_ptr = NULL; #endif /* ITT_COMPLETE_GROUP */ /* evaluating if any function ptr is non empty */ for (i = 0; func_map[i].name != NULL; i++) { if (*func_map[i].func_ptr != NULL) { ret = 1; break; } } } ittnotify_init = 1; current_thread = 0; } } #ifndef ITT_SIMPLE_INIT __itt_mutex_unlock(&mutex); #endif /* ITT_SIMPLE_INIT */ } return ret; }