advisor-annotate.h 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525
  1. #if !defined(TORCH_STABLE_ONLY) && !defined(TORCH_TARGET_VERSION)
  2. /*
  3. * Copyright (C) 2005-2019 Intel Corporation
  4. * SPDX-License-Identifier: GPL-2.0-only OR BSD-3-Clause
  5. */
  6. /* This file defines macros and inline functions used by
  7. * the Intel(R) Advisor XE "Dependencies Modeling" and
  8. * "Suitability Modeling" analysis, and are in described
  9. * in the "Annotations" section of the help.
  10. *
  11. * Expansion Options
  12. *
  13. * There are several options you can used to control how advisor-annotate.h
  14. * is included. To use these, define the option prior to including
  15. * advisor-annotate.h. e.g.
  16. * #define ANNOTATE_DECLARE
  17. * #include "advisor-annotate.h"
  18. *
  19. * Controlling inclusion of windows.h
  20. *
  21. * windows.h is included for declarations for LoadLibrary, GetProcSymbol,
  22. * but this can have interactions with user code, such as conflicting
  23. * definitions of types. There are two general approaches to work around
  24. * this if this triggers problems building your application:
  25. *
  26. * 1. Reduce the amount declared by windows.h by using the following:
  27. * #define NOMINMAX
  28. * #define WIN32_LEAN_AND_MEAN
  29. * prior to including advisor-annotate.h in your code.
  30. * The first avoids problems with STL min/max in particular
  31. * This is sufficient in some cases, and may be the easiest.
  32. *
  33. * 2. Use a declaration/definition approach, where all uses of advisor-annotate.h
  34. * other than one, generate a set of declarations, and windows.h is only
  35. * needed in a single implementation module. In this model, all includes
  36. * of advisor-annotate.h except one specify ANNOTATE_DECLARE, which causes
  37. * advisor-annotate.h to declare an external routine, and not include
  38. * windows.h. A final include of advisor-annotate.h than specifies
  39. * ANNOTATE_DEFINE, to actually define the global routine to resolve
  40. * the external reference. This one include is the only one that winds up
  41. * using windows.h. If necessary, this can be placed in a file by itself.
  42. *
  43. * An example using this mechanism:
  44. *
  45. * ...
  46. * // Some header(s) used in places in your system where you want
  47. * // to be able to use annotations
  48. * #define ANNOTATE_DECLARE
  49. * #include "advisor-annotate.h"
  50. * ...
  51. * // annotation uses
  52. * ANNOTATE_SITE_BEGIN(MySite1)
  53. * ...
  54. * ANNOTATE_SITE_END(MySite1)
  55. * ...
  56. *
  57. * ...
  58. * // A single implementation file (.cpp/.cxx) causes windows.h
  59. * // to be included, and the support routine to be defined as a
  60. * // global routine called from the various annotation uses.
  61. * #define ANNOTATE_DEFINE
  62. * #include "advisor-annotate.h"
  63. * ...
  64. *
  65. * Null expansion of annotations
  66. *
  67. * Some people may find it useful to have no expansion for annotations,
  68. * if you have a project that you want to build without any annotation
  69. * effects at all. (e.g. if you have a project where you want to have
  70. * some annotations in a shared source pool, but only particular
  71. * developers are actually building with the annotations enabled.)
  72. * Defining ANNOTATE_EXPAND_NULL avoids declaring comdat routines,
  73. * and avoids any textual expansion for annotation macros.
  74. */
  75. #ifndef _ADVISOR_ANNOTATE_H_
  76. #define _ADVISOR_ANNOTATE_H_
  77. /* Version of the annotations.
  78. * The presence of this macro serves to idetify the annotation definition
  79. * file and the form of annotations.
  80. */
  81. #define INTEL_ADVISOR_ANNOTATION_VERSION 1.0
  82. #ifdef ANNOTATE_EXPAND_NULL
  83. #define ANNOTATE_SITE_BEGIN(_SITE)
  84. #define ANNOTATE_SITE_END(...)
  85. #define ANNOTATE_TASK_BEGIN(_TASK)
  86. #define ANNOTATE_TASK_END(...)
  87. #define ANNOTATE_ITERATION_TASK(_TASK)
  88. #define ANNOTATE_LOCK_ACQUIRE(_ADDR)
  89. #define ANNOTATE_LOCK_RELEASE(_ADDR)
  90. #define ANNOTATE_RECORD_ALLOCATION(_ADDR, _SIZE)
  91. #define ANNOTATE_RECORD_DEALLOCATION(_ADDR)
  92. #define ANNOTATE_INDUCTION_USES(_ADDR, _SIZE)
  93. #define ANNOTATE_REDUCTION_USES(_ADDR, _SIZE)
  94. #define ANNOTATE_OBSERVE_USES(_ADDR, _SIZE)
  95. #define ANNOTATE_CLEAR_USES(_ADDR)
  96. #define ANNOTATE_DISABLE_OBSERVATION_PUSH
  97. #define ANNOTATE_DISABLE_OBSERVATION_POP
  98. #define ANNOTATE_DISABLE_COLLECTION_PUSH
  99. #define ANNOTATE_DISABLE_COLLECTION_POP
  100. #define ANNOTATE_AGGREGATE_TASK(_COUNT)
  101. #else /* ANNOTATE_EXPAND_NULL */
  102. #if defined(WIN32) || defined(_WIN32)
  103. #define ANNOTATEAPI __cdecl
  104. #ifndef ANNOTATE_DECLARE
  105. #include <windows.h>
  106. typedef HMODULE lib_t;
  107. #define __itt_get_proc(lib, name) GetProcAddress(lib, name)
  108. #define __itt_load_lib(name) LoadLibraryA(name)
  109. #define __itt_unload_lib(handle) FreeLibrary(handle)
  110. #define __itt_system_error() (int)GetLastError()
  111. #endif /* ANNOTATE_DECLARE */
  112. #else /* defined(WIN32) || defined(_WIN32) */
  113. #if defined _M_IX86 || __i386__
  114. # define ANNOTATEAPI __attribute__ ((cdecl))
  115. #else
  116. # define ANNOTATEAPI /* actual only on x86 platform */
  117. #endif
  118. #ifndef ANNOTATE_DECLARE
  119. #include <pthread.h>
  120. #include <dlfcn.h>
  121. #include <errno.h>
  122. typedef void* lib_t;
  123. #define __itt_get_proc(lib, name) dlsym(lib, name)
  124. #define __itt_load_lib(name) dlopen(name, RTLD_LAZY)
  125. #define __itt_unload_lib(handle) dlclose(handle)
  126. #define __itt_system_error() errno
  127. #endif /* ANNOTATE_DECLARE */
  128. #endif /* defined(WIN32) || defined(_WIN32) */
  129. #include <stdlib.h>
  130. #ifdef __cplusplus
  131. extern "C" {
  132. #endif /* __cplusplus */
  133. #ifndef _ITTNOTIFY_H_
  134. /* Handles for sites and tasks.
  135. */
  136. typedef void* __itt_model_site; /* handle for lexical site */
  137. typedef void* __itt_model_site_instance; /* handle for dynamic instance */
  138. typedef void* __itt_model_task; /* handle for lexical site */
  139. typedef void* __itt_model_task_instance; /* handle for dynamic instance */
  140. typedef enum {
  141. __itt_model_disable_observation,
  142. __itt_model_disable_collection
  143. } __itt_model_disable;
  144. #endif /* _ITTNOTIFY_H_ */
  145. /*** Use the routines in libittnotify.dll. ***/
  146. /* Basic approach:
  147. * For the case of calling the dll, there is an __annotate_routine function
  148. * declared as a comdat in each compilation unit with annotations present.
  149. * That routine in turn has an internal static structure that is initialized
  150. * once to contain the address of functions occuring in libittnotify.dll.
  151. * Each time an annotation macro is invoked, that causes a call to the
  152. * __annotate_routine function to get addresses of the routines, followed
  153. * by calling the specific routine, provided the address is non-null.
  154. */
  155. /* This set of macros generates calls that are part of application images,
  156. * which call the __itt_model_xxx routines in the dynamically loaded
  157. * libittnotify.dll.
  158. */
  159. #ifndef _ITTNOTIFY_H_
  160. #define ITT_NOTIFY_DECL(_text) _text
  161. #else
  162. #define ITT_NOTIFY_DECL(_text)
  163. #endif
  164. /* For C++, a static initialization is used */
  165. #if defined(__cplusplus) && defined(WIN32)
  166. #define _ANNOTATE_ROUTINES_ADDR __annotate_routines_s
  167. #else
  168. #define _ANNOTATE_ROUTINES_ADDR __annotate_routines_init( __annotate_routines() )
  169. #endif /* __cplusplus */
  170. #define _ANNOTATE_DECLARE_0(_BASENAME) \
  171. typedef void (ANNOTATEAPI * __annotate_##_BASENAME##_t)(); \
  172. static __inline void ANNOTATEAPI __annotate_##_BASENAME##_t_nop() { }; \
  173. ITT_NOTIFY_DECL( extern void ANNOTATEAPI __itt_model_##_BASENAME(); )
  174. #define _ANNOTATE_DECLARE_0_INT(_BASENAME) \
  175. typedef int (ANNOTATEAPI * __annotate_##_BASENAME##_t)(); \
  176. static __inline int ANNOTATEAPI __annotate_##_BASENAME##_t_nop() { return 0; }; \
  177. ITT_NOTIFY_DECL( extern void ANNOTATEAPI __itt_model_##_BASENAME(); )
  178. #define _ANNOTATE_CALL_0(_BASENAME) { _ANNOTATE_ROUTINES_ADDR->_BASENAME(); }
  179. #define _ANNOTATE_DECLARE_1(_BASENAME, _P1TYPE) \
  180. typedef void (ANNOTATEAPI * __annotate_##_BASENAME##_t)(_P1TYPE p1); \
  181. static __inline void ANNOTATEAPI __annotate_##_BASENAME##_t_nop(_P1TYPE p1) { (void)p1; }; \
  182. ITT_NOTIFY_DECL( extern void ANNOTATEAPI __itt_model_##_BASENAME(_P1TYPE p1); )
  183. #define _ANNOTATE_CALL_1(_BASENAME, _P1) { _ANNOTATE_ROUTINES_ADDR->_BASENAME(_P1); }
  184. #define _ANNOTATE_DECLARE_2(_BASENAME, _P1TYPE, _P2TYPE) \
  185. typedef void (ANNOTATEAPI * __annotate_##_BASENAME##_t)(_P1TYPE p1, _P2TYPE p2); \
  186. static __inline void ANNOTATEAPI __annotate_##_BASENAME##_t_nop(_P1TYPE p1, _P2TYPE p2) { (void)p1; (void)p2; }; \
  187. ITT_NOTIFY_DECL( extern void ANNOTATEAPI __itt_model_##_BASENAME(_P1TYPE p1, _P2TYPE p2); )
  188. #define _ANNOTATE_CALL_2(_BASENAME, _P1, _P2) { _ANNOTATE_ROUTINES_ADDR->_BASENAME((_P1), (_P2)); }
  189. /*** Declare routines appropriately based on usage style ***/
  190. /* Depending on above, this will either expand to comdats that are
  191. * used directly, or comdats that call routines in libittnotify.dll
  192. */
  193. _ANNOTATE_DECLARE_1(site_beginA, const char *)
  194. _ANNOTATE_DECLARE_0(site_end_2)
  195. _ANNOTATE_DECLARE_1(task_beginA, const char *)
  196. _ANNOTATE_DECLARE_0(task_end_2)
  197. _ANNOTATE_DECLARE_1(iteration_taskA, const char *)
  198. _ANNOTATE_DECLARE_1(lock_acquire_2, void *)
  199. _ANNOTATE_DECLARE_1(lock_release_2, void *)
  200. _ANNOTATE_DECLARE_2(record_allocation, void *, size_t)
  201. _ANNOTATE_DECLARE_1(record_deallocation, void *)
  202. _ANNOTATE_DECLARE_2(induction_uses, void *, size_t)
  203. _ANNOTATE_DECLARE_2(reduction_uses, void *, size_t)
  204. _ANNOTATE_DECLARE_2(observe_uses, void *, size_t)
  205. _ANNOTATE_DECLARE_1(clear_uses, void *)
  206. _ANNOTATE_DECLARE_1(disable_push, __itt_model_disable)
  207. _ANNOTATE_DECLARE_0(disable_pop)
  208. _ANNOTATE_DECLARE_1(aggregate_task, size_t)
  209. _ANNOTATE_DECLARE_0_INT(is_collection_disabled)
  210. /* All of the symbols potentially in the library
  211. */
  212. struct __annotate_routines {
  213. volatile int initialized;
  214. __annotate_site_beginA_t site_beginA;
  215. __annotate_site_end_2_t site_end_2;
  216. __annotate_task_beginA_t task_beginA;
  217. __annotate_task_end_2_t task_end_2;
  218. __annotate_iteration_taskA_t iteration_taskA;
  219. __annotate_lock_acquire_2_t lock_acquire_2;
  220. __annotate_lock_release_2_t lock_release_2;
  221. __annotate_record_allocation_t record_allocation;
  222. __annotate_record_deallocation_t record_deallocation;
  223. __annotate_induction_uses_t induction_uses;
  224. __annotate_reduction_uses_t reduction_uses;
  225. __annotate_observe_uses_t observe_uses;
  226. __annotate_clear_uses_t clear_uses;
  227. __annotate_disable_push_t disable_push;
  228. __annotate_disable_pop_t disable_pop;
  229. __annotate_aggregate_task_t aggregate_task;
  230. __annotate_is_collection_disabled_t is_collection_disabled;
  231. };
  232. /* This comdat-ed routine means there is a single instance of the function pointer
  233. * structure per image
  234. */
  235. static __inline struct __annotate_routines* __annotate_routines()
  236. {
  237. static struct __annotate_routines __annotate_routines;
  238. return &__annotate_routines;
  239. }
  240. /* This routine is called to get the address of an initialized
  241. * set of function pointers for the annotation routines.
  242. */
  243. #ifdef ANNOTATE_DECLARE
  244. extern struct __annotate_routines* ANNOTATEAPI __annotate_routines_init(struct __annotate_routines* itt);
  245. #else
  246. #ifdef ANNOTATE_DEFINE
  247. /* */
  248. #else
  249. static __inline
  250. #endif
  251. struct __annotate_routines*
  252. ANNOTATEAPI
  253. __annotate_routines_init(struct __annotate_routines* itt) {
  254. if (itt->initialized) {
  255. return itt;
  256. } else {
  257. /* Initialized by first invocation
  258. * This assumes that the code here can be executed successfully
  259. * by multiple threads, should that ever happen.
  260. */
  261. int do_disable_pop = 0;
  262. char* lib_name = NULL;
  263. lib_t itt_notify = 0;
  264. if (sizeof(void*) > 4) {
  265. lib_name = getenv("INTEL_LIBITTNOTIFY64");
  266. } else {
  267. lib_name = getenv("INTEL_LIBITTNOTIFY32");
  268. }
  269. if (lib_name) {
  270. itt_notify = __itt_load_lib(lib_name);
  271. } else {
  272. #if defined(WIN32) || defined(_WIN32)
  273. itt_notify = __itt_load_lib("libittnotify.dll");
  274. #elif defined(__APPLE__)
  275. itt_notify = __itt_load_lib("libittnotify.dylib");
  276. #else
  277. itt_notify = __itt_load_lib("libittnotify.so");
  278. #endif
  279. }
  280. if (itt_notify != NULL) {
  281. /* The static variables initialized and itt are reported as race conditions
  282. * or inconsistent lock usage by Dependencies Modeling in some obscure cases
  283. * involving multiple dlls. Ignoring this initialization phase gets rid of
  284. * this problem.
  285. */
  286. __annotate_disable_push_t disable_push;
  287. __annotate_is_collection_disabled_t is_collection_disabled;
  288. disable_push = (__annotate_disable_push_t) __itt_get_proc(itt_notify, "__itt_model_disable_push");
  289. is_collection_disabled = (__annotate_is_collection_disabled_t) __itt_get_proc(itt_notify, "__itt_model_is_collection_disabled");
  290. if (disable_push) {
  291. if ( ! (is_collection_disabled && is_collection_disabled()) )
  292. {
  293. // disable collection only if it is not disabled already (for example, started paused)
  294. disable_push(__itt_model_disable_observation);
  295. do_disable_pop = 1;
  296. }
  297. }
  298. itt->site_beginA = (__annotate_site_beginA_t) __itt_get_proc(itt_notify, "__itt_model_site_beginA");
  299. itt->site_end_2 = (__annotate_site_end_2_t) __itt_get_proc(itt_notify, "__itt_model_site_end_2");
  300. itt->task_beginA = (__annotate_task_beginA_t) __itt_get_proc(itt_notify, "__itt_model_task_beginA");
  301. itt->task_end_2 = (__annotate_task_end_2_t) __itt_get_proc(itt_notify, "__itt_model_task_end_2");
  302. itt->iteration_taskA = (__annotate_iteration_taskA_t) __itt_get_proc(itt_notify, "__itt_model_iteration_taskA");
  303. itt->lock_acquire_2 = (__annotate_lock_acquire_2_t) __itt_get_proc(itt_notify, "__itt_model_lock_acquire_2");
  304. itt->lock_release_2 = (__annotate_lock_release_2_t) __itt_get_proc(itt_notify, "__itt_model_lock_release_2");
  305. itt->record_allocation = (__annotate_record_allocation_t) __itt_get_proc(itt_notify, "__itt_model_record_allocation");
  306. itt->record_deallocation = (__annotate_record_deallocation_t)__itt_get_proc(itt_notify, "__itt_model_record_deallocation");
  307. itt->induction_uses = (__annotate_induction_uses_t) __itt_get_proc(itt_notify, "__itt_model_induction_uses");
  308. itt->reduction_uses = (__annotate_reduction_uses_t) __itt_get_proc(itt_notify, "__itt_model_reduction_uses");
  309. itt->observe_uses = (__annotate_observe_uses_t) __itt_get_proc(itt_notify, "__itt_model_observe_uses");
  310. itt->clear_uses = (__annotate_clear_uses_t) __itt_get_proc(itt_notify, "__itt_model_clear_uses");
  311. itt->disable_push = disable_push;
  312. itt->disable_pop = (__annotate_disable_pop_t) __itt_get_proc(itt_notify, "__itt_model_disable_pop");
  313. itt->aggregate_task = (__annotate_aggregate_task_t) __itt_get_proc(itt_notify, "__itt_model_aggregate_task");
  314. itt->is_collection_disabled = is_collection_disabled;
  315. }
  316. /* No-op routine for any that didn't get resolved */
  317. if (!itt->site_beginA) itt->site_beginA = __annotate_site_beginA_t_nop;
  318. if (!itt->site_end_2) itt->site_end_2 = __annotate_site_end_2_t_nop;
  319. if (!itt->task_beginA) itt->task_beginA = __annotate_task_beginA_t_nop;
  320. if (!itt->task_end_2) itt->task_end_2 = __annotate_task_end_2_t_nop;
  321. if (!itt->iteration_taskA) itt->iteration_taskA = __annotate_iteration_taskA_t_nop;
  322. if (!itt->lock_acquire_2) itt->lock_acquire_2 = __annotate_lock_acquire_2_t_nop;
  323. if (!itt->lock_release_2) itt->lock_release_2 = __annotate_lock_release_2_t_nop;
  324. if (!itt->record_allocation) itt->record_allocation = __annotate_record_allocation_t_nop;
  325. if (!itt->record_deallocation) itt->record_deallocation=__annotate_record_deallocation_t_nop;
  326. if (!itt->induction_uses) itt->induction_uses = __annotate_induction_uses_t_nop;
  327. if (!itt->reduction_uses) itt->reduction_uses = __annotate_reduction_uses_t_nop;
  328. if (!itt->observe_uses) itt->observe_uses = __annotate_observe_uses_t_nop;
  329. if (!itt->clear_uses) itt->clear_uses = __annotate_clear_uses_t_nop;
  330. if (!itt->disable_push) itt->disable_push = __annotate_disable_push_t_nop;
  331. if (!itt->disable_pop) itt->disable_pop = __annotate_disable_pop_t_nop;
  332. if (!itt->aggregate_task) itt->aggregate_task = __annotate_aggregate_task_t_nop;
  333. if (!itt->is_collection_disabled) itt->is_collection_disabled = __annotate_is_collection_disabled_t_nop;
  334. itt->initialized = 1;
  335. if (do_disable_pop) {
  336. itt->disable_pop();
  337. }
  338. }
  339. return itt;
  340. }
  341. #endif /* ANNOTATE_DECLARE */
  342. /* For C++ only, use a class to force initialization */
  343. #if defined(__cplusplus) && defined(WIN32)
  344. /* Force one-shot initialization so individual calls don't need it */
  345. static struct __annotate_routines* __annotate_routines_s = __annotate_routines_init( __annotate_routines() );
  346. #endif
  347. /* For C++, allow the Annotate::SiteBegin(x) form. For Windows CLR, this is the default
  348. * expansion for the macros (with no-inline) to get the best call stacks in the tools. */
  349. #if defined(__cplusplus)
  350. /* Ensure this code is managed and non-inlinable */
  351. #if defined(WIN32) && defined(__CLR_VER)
  352. #pragma managed(push, on)
  353. #define ANNOTATE_CLR_NOINLINE __declspec(noinline)
  354. #else
  355. #define ANNOTATE_CLR_NOINLINE
  356. #endif
  357. class Annotate {
  358. public:
  359. static ANNOTATE_CLR_NOINLINE void SiteBegin(const char* site) { _ANNOTATE_ROUTINES_ADDR->site_beginA(site); }
  360. static ANNOTATE_CLR_NOINLINE void SiteEnd() { _ANNOTATE_ROUTINES_ADDR->site_end_2(); }
  361. static ANNOTATE_CLR_NOINLINE void TaskBegin(const char* task) { _ANNOTATE_ROUTINES_ADDR->task_beginA(task); }
  362. static ANNOTATE_CLR_NOINLINE void TaskEnd() { _ANNOTATE_ROUTINES_ADDR->task_end_2(); }
  363. static ANNOTATE_CLR_NOINLINE void IterationTask(const char* task) { _ANNOTATE_ROUTINES_ADDR->iteration_taskA(task); }
  364. static ANNOTATE_CLR_NOINLINE void LockAcquire(void* lockId) { _ANNOTATE_ROUTINES_ADDR->lock_acquire_2(lockId); }
  365. static ANNOTATE_CLR_NOINLINE void LockRelease(void* lockId) { _ANNOTATE_ROUTINES_ADDR->lock_release_2(lockId); }
  366. static ANNOTATE_CLR_NOINLINE void RecordAllocation(void *p, size_t s) { _ANNOTATE_ROUTINES_ADDR->record_allocation(p, s); }
  367. static ANNOTATE_CLR_NOINLINE void RecordDeallocation(void *p) { _ANNOTATE_ROUTINES_ADDR->record_deallocation(p); }
  368. static ANNOTATE_CLR_NOINLINE void InductionUses(void *p, size_t s) { _ANNOTATE_ROUTINES_ADDR->induction_uses(p, s); }
  369. static ANNOTATE_CLR_NOINLINE void ReductionUses(void *p, size_t s) { _ANNOTATE_ROUTINES_ADDR->reduction_uses(p, s); }
  370. static ANNOTATE_CLR_NOINLINE void ObserveUses(void *p, size_t s) { _ANNOTATE_ROUTINES_ADDR->observe_uses(p, s); }
  371. static ANNOTATE_CLR_NOINLINE void ClearUses(void *p) { _ANNOTATE_ROUTINES_ADDR->clear_uses(p); }
  372. static ANNOTATE_CLR_NOINLINE void DisablePush(__itt_model_disable d) { _ANNOTATE_ROUTINES_ADDR->disable_push(d); }
  373. static ANNOTATE_CLR_NOINLINE void DisablePop() { _ANNOTATE_ROUTINES_ADDR->disable_pop(); }
  374. static ANNOTATE_CLR_NOINLINE void AggregateTask(size_t c) { _ANNOTATE_ROUTINES_ADDR->aggregate_task(c); }
  375. };
  376. #if defined(WIN32) && defined(__CLR_VER)
  377. #pragma managed(pop)
  378. #endif
  379. #undef ANNOTATE_CLR_NOINLINE
  380. #endif
  381. #if defined(__cplusplus) && defined(WIN32) && defined(__CLR_VER)
  382. #define ANNOTATE_SITE_BEGIN(_SITE) Annotate::SiteBegin(#_SITE)
  383. #define ANNOTATE_SITE_END(...) Annotate::SiteEnd()
  384. #define ANNOTATE_TASK_BEGIN(_TASK) Annotate::TaskBegin(#_TASK)
  385. #define ANNOTATE_TASK_END(...) Annotate::TaskEnd()
  386. #define ANNOTATE_ITERATION_TASK(_TASK) Annotate::IterationTask(#_TASK)
  387. #define ANNOTATE_LOCK_ACQUIRE(_ADDR) Annotate::LockAcquire(_ADDR)
  388. #define ANNOTATE_LOCK_RELEASE(_ADDR) Annotate::LockRelease(_ADDR)
  389. #define ANNOTATE_RECORD_ALLOCATION(_ADDR, _SIZE) Annotate::RecordAllocation((_ADDR), (_SIZE))
  390. #define ANNOTATE_RECORD_DEALLOCATION(_ADDR) Annotate::RecordDeallocation(_ADDR)
  391. #define ANNOTATE_INDUCTION_USES(_ADDR, _SIZE) Annotate::InductionUses((_ADDR), (_SIZE))
  392. #define ANNOTATE_REDUCTION_USES(_ADDR, _SIZE) Annotate::ReductionUses((_ADDR), (_SIZE))
  393. #define ANNOTATE_OBSERVE_USES(_ADDR, _SIZE) Annotate::ObserveUses((_ADDR), (_SIZE))
  394. #define ANNOTATE_CLEAR_USES(_ADDR) Annotate::ClearUses(_ADDR)
  395. #define ANNOTATE_DISABLE_OBSERVATION_PUSH Annotate::DisablePush(itt_model_disable_observation)
  396. #define ANNOTATE_DISABLE_OBSERVATION_POP Annotate::DisablePop()
  397. #define ANNOTATE_DISABLE_COLLECTION_PUSH Annotate::DisablePush(__itt_model_disable_collection)
  398. #define ANNOTATE_DISABLE_COLLECTION_POP Annotate::DisablePop()
  399. #define ANNOTATE_AGGREGATE_TASK(_COUNT) Annotate::AggregateTask(_COUNT)
  400. #else
  401. /* Mark the start of a site (region) to be analyzed by the tool */
  402. #define ANNOTATE_SITE_BEGIN(_SITE) _ANNOTATE_CALL_1(site_beginA, #_SITE)
  403. /* Mark the end of a site (region) to be analyzed by the tool and
  404. * indicate a WaitForAll task synchronization */
  405. #define ANNOTATE_SITE_END(...) _ANNOTATE_CALL_0(site_end_2)
  406. /* Mark the beginning of a region of code that constitutes a task */
  407. #define ANNOTATE_TASK_BEGIN(_TASK) _ANNOTATE_CALL_1(task_beginA, #_TASK)
  408. /* Mark the end of a region of code that constitutes a task */
  409. #define ANNOTATE_TASK_END(...) _ANNOTATE_CALL_0(task_end_2)
  410. /* Mark the break between one task and the next task (a "split" description model
  411. * rather than a "begin/end" description model. */
  412. #define ANNOTATE_ITERATION_TASK(_TASK) _ANNOTATE_CALL_1(iteration_taskA, #_TASK)
  413. /* Acquire a lock identified by lockId */
  414. #define ANNOTATE_LOCK_ACQUIRE(_ADDR) _ANNOTATE_CALL_1(lock_acquire_2, (_ADDR))
  415. /* Release a lock identified by lockId */
  416. #define ANNOTATE_LOCK_RELEASE(_ADDR) _ANNOTATE_CALL_1(lock_release_2, (_ADDR))
  417. /* Record user allocation of memory */
  418. #define ANNOTATE_RECORD_ALLOCATION(_ADDR, _SIZE) _ANNOTATE_CALL_2(record_allocation, (_ADDR), (_SIZE))
  419. /* Record user deallocation of memory */
  420. #define ANNOTATE_RECORD_DEALLOCATION(_ADDR) _ANNOTATE_CALL_1(record_deallocation, (_ADDR))
  421. /* Denote storage as an inductive value */
  422. #define ANNOTATE_INDUCTION_USES(_ADDR, _SIZE) _ANNOTATE_CALL_2(induction_uses, (_ADDR), (_SIZE))
  423. /* Denote storage as a reduction */
  424. #define ANNOTATE_REDUCTION_USES(_ADDR, _SIZE) _ANNOTATE_CALL_2(reduction_uses, (_ADDR), (_SIZE))
  425. /* Record all observations of uses */
  426. #define ANNOTATE_OBSERVE_USES(_ADDR, _SIZE) _ANNOTATE_CALL_2(observe_uses, (_ADDR), (_SIZE))
  427. /* Clear handling of values */
  428. #define ANNOTATE_CLEAR_USES(_ADDR) _ANNOTATE_CALL_1(clear_uses, (_ADDR))
  429. /* Push disable of observations */
  430. #define ANNOTATE_DISABLE_OBSERVATION_PUSH _ANNOTATE_CALL_1(disable_push, __itt_model_disable_observation)
  431. /* Pop disable of observations */
  432. #define ANNOTATE_DISABLE_OBSERVATION_POP _ANNOTATE_CALL_0(disable_pop)
  433. /* Push disable of collection */
  434. #define ANNOTATE_DISABLE_COLLECTION_PUSH _ANNOTATE_CALL_1(disable_push, __itt_model_disable_collection)
  435. /* Pop disable of collection */
  436. #define ANNOTATE_DISABLE_COLLECTION_POP _ANNOTATE_CALL_0(disable_pop)
  437. /* Task aggregation */
  438. #define ANNOTATE_AGGREGATE_TASK(_COUNT) _ANNOTATE_CALL_1(aggregate_task, (_COUNT))
  439. #endif
  440. #ifdef __cplusplus
  441. }
  442. #endif /* __cplusplus */
  443. #endif /* ANNOTATE_EXPAND_NULL */
  444. #endif /* _ADVISOR_ANNOTATE_H_ */
  445. #else
  446. #error "This file should not be included when either TORCH_STABLE_ONLY or TORCH_TARGET_VERSION is defined."
  447. #endif // !defined(TORCH_STABLE_ONLY) && !defined(TORCH_TARGET_VERSION)