PIXEvents.h (22461B)
1 // Copyright (c) Microsoft Corporation. All rights reserved. 2 3 /*==========================================================================; 4 * 5 * Copyright (C) Microsoft Corporation. All Rights Reserved. 6 * 7 * File: PIXEvents.h 8 * Content: PIX include file 9 * Don't include this file directly - use pix3.h 10 * 11 ****************************************************************************/ 12 #pragma once 13 14 #ifndef _PixEvents_H_ 15 #define _PixEvents_H_ 16 17 #ifndef _PIX3_H_ 18 # error Do not include this file directly - use pix3.h 19 #endif 20 21 #include "PIXEventsCommon.h" 22 23 #if _MSC_VER < 1800 24 # error This version of pix3.h is only supported on Visual Studio 2013 or higher 25 #elif _MSC_VER < 1900 26 # ifndef constexpr // Visual Studio 2013 doesn't support constexpr 27 # define constexpr 28 # define PIX3__DEFINED_CONSTEXPR 29 # endif 30 #endif 31 32 // Xbox does not support CPU events for retail scenarios 33 #if defined(USE_PIX) || !defined(PIX_XBOX) 34 #define PIX_CONTEXT_EMIT_CPU_EVENTS 35 #endif 36 37 namespace PIXEventsDetail 38 { 39 template<typename... ARGS> 40 struct PIXEventTypeInferer 41 { 42 static constexpr PIXEventType Begin() { return PIXEvent_BeginEvent_VarArgs; } 43 static constexpr PIXEventType SetMarker() { return PIXEvent_SetMarker_VarArgs; } 44 static constexpr PIXEventType BeginOnContext() { return PIXEvent_BeginEvent_OnContext_VarArgs; } 45 static constexpr PIXEventType SetMarkerOnContext() { return PIXEvent_SetMarker_OnContext_VarArgs; } 46 47 // Xbox and Windows store different types of events for context events. 48 // On Xbox these include a context argument, while on Windows they do 49 // not. It is important not to change the event types used on the 50 // Windows version as there are OS components (eg debug layer & DRED) 51 // that decode event structs. 52 #ifdef PIX_XBOX 53 static constexpr PIXEventType GpuBeginOnContext() { return PIXEvent_BeginEvent_OnContext_VarArgs; } 54 static constexpr PIXEventType GpuSetMarkerOnContext() { return PIXEvent_SetMarker_OnContext_VarArgs; } 55 #else 56 static constexpr PIXEventType GpuBeginOnContext() { return PIXEvent_BeginEvent_VarArgs; } 57 static constexpr PIXEventType GpuSetMarkerOnContext() { return PIXEvent_SetMarker_VarArgs; } 58 #endif 59 }; 60 61 template<> 62 struct PIXEventTypeInferer<> 63 { 64 static constexpr PIXEventType Begin() { return PIXEvent_BeginEvent_NoArgs; } 65 static constexpr PIXEventType SetMarker() { return PIXEvent_SetMarker_NoArgs; } 66 static constexpr PIXEventType BeginOnContext() { return PIXEvent_BeginEvent_OnContext_NoArgs; } 67 static constexpr PIXEventType SetMarkerOnContext() { return PIXEvent_SetMarker_OnContext_NoArgs; } 68 69 #ifdef PIX_XBOX 70 static constexpr PIXEventType GpuBeginOnContext() { return PIXEvent_BeginEvent_OnContext_NoArgs; } 71 static constexpr PIXEventType GpuSetMarkerOnContext() { return PIXEvent_SetMarker_OnContext_NoArgs; } 72 #else 73 static constexpr PIXEventType GpuBeginOnContext() { return PIXEvent_BeginEvent_NoArgs; } 74 static constexpr PIXEventType GpuSetMarkerOnContext() { return PIXEvent_SetMarker_NoArgs; } 75 #endif 76 }; 77 78 inline void PIXCopyEventArguments(_Out_writes_to_ptr_(limit) UINT64*& destination, _In_ const UINT64* limit) 79 { 80 // nothing 81 UNREFERENCED_PARAMETER(destination); 82 UNREFERENCED_PARAMETER(limit); 83 } 84 85 template<typename ARG, typename... ARGS> 86 void PIXCopyEventArguments(_Out_writes_to_ptr_(limit) UINT64*& destination, _In_ const UINT64* limit, ARG const& arg, ARGS const&... args) 87 { 88 PIXCopyEventArgument(destination, limit, arg); 89 PIXCopyEventArguments(destination, limit, args...); 90 } 91 92 template<typename STR, typename... ARGS> 93 __declspec(noinline) void PIXBeginEventAllocate(PIXEventsThreadInfo* threadInfo, UINT64 color, STR formatString, ARGS... args) 94 { 95 #ifdef PIX_XBOX 96 UINT64 time = PIXEventsReplaceBlock(false); 97 #else 98 UINT64 time = PIXEventsReplaceBlock(threadInfo, false); 99 #endif 100 if (!time) 101 return; 102 103 UINT64* destination = threadInfo->destination; 104 UINT64* limit = threadInfo->biasedLimit; 105 if (destination >= limit) 106 return; 107 108 limit += PIXEventsSafeFastCopySpaceQwords; 109 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::Begin()); 110 *destination++ = color; 111 112 PIXCopyEventArguments(destination, limit, formatString, args...); 113 114 *destination = PIXEventsBlockEndMarker; 115 threadInfo->destination = destination; 116 } 117 118 template<typename STR, typename... ARGS> 119 void PIXBeginEvent(UINT64 color, STR formatString, ARGS... args) 120 { 121 PIXEventsThreadInfo* threadInfo = PIXGetThreadInfo(); 122 UINT64* limit = threadInfo->biasedLimit; 123 if (limit != nullptr) 124 { 125 UINT64* destination = threadInfo->destination; 126 if (destination < limit) 127 { 128 limit += PIXEventsSafeFastCopySpaceQwords; 129 UINT64 time = PIXGetTimestampCounter(); 130 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::Begin()); 131 *destination++ = color; 132 133 PIXCopyEventArguments(destination, limit, formatString, args...); 134 135 *destination = PIXEventsBlockEndMarker; 136 threadInfo->destination = destination; 137 } 138 else 139 { 140 PIXBeginEventAllocate(threadInfo, color, formatString, args...); 141 } 142 } 143 } 144 145 template<typename STR, typename... ARGS> 146 __declspec(noinline) void PIXSetMarkerAllocate(PIXEventsThreadInfo* threadInfo, UINT64 color, STR formatString, ARGS... args) 147 { 148 #ifdef PIX_XBOX 149 UINT64 time = PIXEventsReplaceBlock(false); 150 #else 151 UINT64 time = PIXEventsReplaceBlock(threadInfo, false); 152 #endif 153 if (!time) 154 return; 155 156 UINT64* destination = threadInfo->destination; 157 UINT64* limit = threadInfo->biasedLimit; 158 159 if (destination >= limit) 160 return; 161 162 limit += PIXEventsSafeFastCopySpaceQwords; 163 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::SetMarker()); 164 *destination++ = color; 165 166 PIXCopyEventArguments(destination, limit, formatString, args...); 167 168 *destination = PIXEventsBlockEndMarker; 169 threadInfo->destination = destination; 170 } 171 172 template<typename STR, typename... ARGS> 173 void PIXSetMarker(UINT64 color, STR formatString, ARGS... args) 174 { 175 PIXEventsThreadInfo* threadInfo = PIXGetThreadInfo(); 176 UINT64* limit = threadInfo->biasedLimit; 177 if (limit != nullptr) 178 { 179 UINT64* destination = threadInfo->destination; 180 if (destination < limit) 181 { 182 limit += PIXEventsSafeFastCopySpaceQwords; 183 UINT64 time = PIXGetTimestampCounter(); 184 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::SetMarker()); 185 *destination++ = color; 186 187 PIXCopyEventArguments(destination, limit, formatString, args...); 188 189 *destination = PIXEventsBlockEndMarker; 190 threadInfo->destination = destination; 191 } 192 else 193 { 194 PIXSetMarkerAllocate(threadInfo, color, formatString, args...); 195 } 196 } 197 } 198 199 template<typename STR, typename... ARGS> 200 __declspec(noinline) void PIXBeginEventOnContextCpuAllocate(PIXEventsThreadInfo* threadInfo, void* context, UINT64 color, STR formatString, ARGS... args) 201 { 202 #ifdef PIX_XBOX 203 UINT64 time = PIXEventsReplaceBlock(false); 204 #else 205 UINT64 time = PIXEventsReplaceBlock(threadInfo, false); 206 #endif 207 if (!time) 208 return; 209 210 UINT64* destination = threadInfo->destination; 211 UINT64* limit = threadInfo->biasedLimit; 212 213 if (destination >= limit) 214 return; 215 216 limit += PIXEventsSafeFastCopySpaceQwords; 217 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::BeginOnContext()); 218 *destination++ = color; 219 220 #ifdef PIX_XBOX 221 UNREFERENCED_PARAMETER(context); 222 PIXCopyEventArguments(destination, limit, formatString, args...); 223 #else 224 PIXCopyEventArguments(destination, limit, context, formatString, args...); 225 #endif 226 227 *destination = PIXEventsBlockEndMarker; 228 threadInfo->destination = destination; 229 } 230 231 template<typename STR, typename... ARGS> 232 void PIXBeginEventOnContextCpu(void* context, UINT64 color, STR formatString, ARGS... args) 233 { 234 PIXEventsThreadInfo* threadInfo = PIXGetThreadInfo(); 235 UINT64* limit = threadInfo->biasedLimit; 236 if (limit != nullptr) 237 { 238 UINT64* destination = threadInfo->destination; 239 if (destination < limit) 240 { 241 limit += PIXEventsSafeFastCopySpaceQwords; 242 UINT64 time = PIXGetTimestampCounter(); 243 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::BeginOnContext()); 244 *destination++ = color; 245 246 #ifdef PIX_XBOX 247 PIXCopyEventArguments(destination, limit, formatString, args...); 248 #else 249 PIXCopyEventArguments(destination, limit, context, formatString, args...); 250 #endif 251 252 *destination = PIXEventsBlockEndMarker; 253 threadInfo->destination = destination; 254 } 255 else 256 { 257 PIXBeginEventOnContextCpuAllocate(threadInfo, context, color, formatString, args...); 258 } 259 } 260 } 261 262 template<typename CONTEXT, typename STR, typename... ARGS> 263 void PIXBeginEvent(CONTEXT* context, UINT64 color, STR formatString, ARGS... args) 264 { 265 #ifdef PIX_CONTEXT_EMIT_CPU_EVENTS 266 PIXBeginEventOnContextCpu(context, color, formatString, args...); 267 #endif 268 269 // TODO: we've already encoded this once for the CPU event - figure out way to avoid doing it again 270 UINT64 buffer[PIXEventsGraphicsRecordSpaceQwords]; 271 UINT64* destination = buffer; 272 UINT64* limit = buffer + PIXEventsGraphicsRecordSpaceQwords - PIXEventsReservedTailSpaceQwords; 273 274 *destination++ = PIXEncodeEventInfo(0, PIXEventTypeInferer<ARGS...>::GpuBeginOnContext()); 275 *destination++ = color; 276 277 PIXCopyEventArguments(destination, limit, formatString, args...); 278 *destination = 0ull; 279 280 PIXBeginGPUEventOnContext(context, static_cast<void*>(buffer), static_cast<UINT>(reinterpret_cast<BYTE*>(destination) - reinterpret_cast<BYTE*>(buffer))); 281 } 282 283 template<typename STR, typename... ARGS> 284 __declspec(noinline) void PIXSetMarkerOnContextCpuAllocate(PIXEventsThreadInfo* threadInfo, void* context, UINT64 color, STR formatString, ARGS... args) 285 { 286 #ifdef PIX_XBOX 287 UINT64 time = PIXEventsReplaceBlock(false); 288 #else 289 UINT64 time = PIXEventsReplaceBlock(threadInfo, false); 290 #endif 291 if (!time) 292 return; 293 294 UINT64* destination = threadInfo->destination; 295 UINT64* limit = threadInfo->biasedLimit; 296 297 if (destination >= limit) 298 return; 299 300 limit += PIXEventsSafeFastCopySpaceQwords; 301 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::SetMarkerOnContext()); 302 *destination++ = color; 303 304 #ifdef PIX_XBOX 305 UNREFERENCED_PARAMETER(context); 306 PIXCopyEventArguments(destination, limit, formatString, args...); 307 #else 308 PIXCopyEventArguments(destination, limit, context, formatString, args...); 309 #endif 310 311 *destination = PIXEventsBlockEndMarker; 312 threadInfo->destination = destination; 313 } 314 315 template<typename STR, typename... ARGS> 316 void PIXSetMarkerOnContextCpu(void* context, UINT64 color, STR formatString, ARGS... args) 317 { 318 PIXEventsThreadInfo* threadInfo = PIXGetThreadInfo(); 319 UINT64* limit = threadInfo->biasedLimit; 320 if (limit != nullptr) 321 { 322 UINT64* destination = threadInfo->destination; 323 if (destination < limit) 324 { 325 limit += PIXEventsSafeFastCopySpaceQwords; 326 UINT64 time = PIXGetTimestampCounter(); 327 *destination++ = PIXEncodeEventInfo(time, PIXEventTypeInferer<ARGS...>::SetMarkerOnContext()); 328 *destination++ = color; 329 330 #ifdef PIX_XBOX 331 PIXCopyEventArguments(destination, limit, formatString, args...); 332 #else 333 PIXCopyEventArguments(destination, limit, context, formatString, args...); 334 #endif 335 336 *destination = PIXEventsBlockEndMarker; 337 threadInfo->destination = destination; 338 } 339 else 340 { 341 PIXSetMarkerOnContextCpuAllocate(threadInfo, context, color, formatString, args...); 342 } 343 } 344 } 345 346 template<typename CONTEXT, typename STR, typename... ARGS> 347 void PIXSetMarker(CONTEXT* context, UINT64 color, STR formatString, ARGS... args) 348 { 349 #ifdef PIX_CONTEXT_EMIT_CPU_EVENTS 350 PIXSetMarkerOnContextCpu(context, color, formatString, args...); 351 #endif 352 353 UINT64 buffer[PIXEventsGraphicsRecordSpaceQwords]; 354 UINT64* destination = buffer; 355 UINT64* limit = buffer + PIXEventsGraphicsRecordSpaceQwords - PIXEventsReservedTailSpaceQwords; 356 357 *destination++ = PIXEncodeEventInfo(0, PIXEventTypeInferer<ARGS...>::GpuSetMarkerOnContext()); 358 *destination++ = color; 359 360 PIXCopyEventArguments(destination, limit, formatString, args...); 361 *destination = 0ull; 362 363 PIXSetGPUMarkerOnContext(context, static_cast<void*>(buffer), static_cast<UINT>(reinterpret_cast<BYTE*>(destination) - reinterpret_cast<BYTE*>(buffer))); 364 } 365 366 __declspec(noinline) inline void PIXEndEventAllocate(PIXEventsThreadInfo* threadInfo) 367 { 368 #ifdef PIX_XBOX 369 UINT64 time = PIXEventsReplaceBlock(true); 370 #else 371 UINT64 time = PIXEventsReplaceBlock(threadInfo, true); 372 #endif 373 if (!time) 374 return; 375 376 UINT64* destination = threadInfo->destination; 377 UINT64* limit = threadInfo->biasedLimit; 378 379 if (destination >= limit) 380 return; 381 382 limit += PIXEventsSafeFastCopySpaceQwords; 383 *destination++ = PIXEncodeEventInfo(time, PIXEvent_EndEvent); 384 *destination = PIXEventsBlockEndMarker; 385 threadInfo->destination = destination; 386 } 387 388 inline void PIXEndEvent() 389 { 390 PIXEventsThreadInfo* threadInfo = PIXGetThreadInfo(); 391 UINT64* limit = threadInfo->biasedLimit; 392 if (limit != nullptr) 393 { 394 UINT64* destination = threadInfo->destination; 395 if (destination < limit) 396 { 397 limit += PIXEventsSafeFastCopySpaceQwords; 398 UINT64 time = PIXGetTimestampCounter(); 399 *destination++ = PIXEncodeEventInfo(time, PIXEvent_EndEvent); 400 *destination = PIXEventsBlockEndMarker; 401 threadInfo->destination = destination; 402 } 403 else 404 { 405 PIXEndEventAllocate(threadInfo); 406 } 407 } 408 } 409 410 __declspec(noinline) inline void PIXEndEventOnContextCpuAllocate(PIXEventsThreadInfo* threadInfo, void* context) 411 { 412 #ifdef PIX_XBOX 413 UINT64 time = PIXEventsReplaceBlock(true); 414 #else 415 UINT64 time = PIXEventsReplaceBlock(threadInfo, true); 416 #endif 417 if (!time) 418 return; 419 420 UINT64* destination = threadInfo->destination; 421 UINT64* limit = threadInfo->biasedLimit; 422 423 if (destination >= limit) 424 return; 425 426 limit += PIXEventsSafeFastCopySpaceQwords; 427 *destination++ = PIXEncodeEventInfo(time, PIXEvent_EndEvent_OnContext); 428 #ifdef PIX_XBOX 429 UNREFERENCED_PARAMETER(context); 430 #else 431 PIXCopyEventArgument(destination, limit, context); 432 #endif 433 *destination = PIXEventsBlockEndMarker; 434 threadInfo->destination = destination; 435 } 436 437 inline void PIXEndEventOnContextCpu(void* context) 438 { 439 PIXEventsThreadInfo* threadInfo = PIXGetThreadInfo(); 440 UINT64* limit = threadInfo->biasedLimit; 441 if (limit != nullptr) 442 { 443 UINT64* destination = threadInfo->destination; 444 if (destination < limit) 445 { 446 limit += PIXEventsSafeFastCopySpaceQwords; 447 UINT64 time = PIXGetTimestampCounter(); 448 *destination++ = PIXEncodeEventInfo(time, PIXEvent_EndEvent_OnContext); 449 #ifndef PIX_XBOX 450 PIXCopyEventArgument(destination, limit, context); 451 #endif 452 *destination = PIXEventsBlockEndMarker; 453 threadInfo->destination = destination; 454 } 455 else 456 { 457 PIXEndEventOnContextCpuAllocate(threadInfo, context); 458 } 459 } 460 } 461 462 template<typename CONTEXT> 463 void PIXEndEvent(CONTEXT* context) 464 { 465 #ifdef PIX_CONTEXT_EMIT_CPU_EVENTS 466 PIXEndEventOnContextCpu(context); 467 #endif 468 PIXEndGPUEventOnContext(context); 469 } 470 } 471 472 #if defined(USE_PIX) 473 474 template<typename... ARGS> 475 void PIXBeginEvent(UINT64 color, PCWSTR formatString, ARGS... args) 476 { 477 PIXEventsDetail::PIXBeginEvent(color, formatString, args...); 478 } 479 480 template<typename... ARGS> 481 void PIXBeginEvent(UINT64 color, PCSTR formatString, ARGS... args) 482 { 483 PIXEventsDetail::PIXBeginEvent(color, formatString, args...); 484 } 485 486 template<typename... ARGS> 487 void PIXSetMarker(UINT64 color, PCWSTR formatString, ARGS... args) 488 { 489 PIXEventsDetail::PIXSetMarker(color, formatString, args...); 490 } 491 492 template<typename... ARGS> 493 void PIXSetMarker(UINT64 color, PCSTR formatString, ARGS... args) 494 { 495 PIXEventsDetail::PIXSetMarker(color, formatString, args...); 496 } 497 498 template<typename CONTEXT, typename... ARGS> 499 void PIXBeginEvent(CONTEXT* context, UINT64 color, PCWSTR formatString, ARGS... args) 500 { 501 PIXEventsDetail::PIXBeginEvent(context, color, formatString, args...); 502 } 503 504 template<typename CONTEXT, typename... ARGS> 505 void PIXBeginEvent(CONTEXT* context, UINT64 color, PCSTR formatString, ARGS... args) 506 { 507 PIXEventsDetail::PIXBeginEvent(context, color, formatString, args...); 508 } 509 510 template<typename CONTEXT, typename... ARGS> 511 void PIXSetMarker(CONTEXT* context, UINT64 color, PCWSTR formatString, ARGS... args) 512 { 513 PIXEventsDetail::PIXSetMarker(context, color, formatString, args...); 514 } 515 516 template<typename CONTEXT, typename... ARGS> 517 void PIXSetMarker(CONTEXT* context, UINT64 color, PCSTR formatString, ARGS... args) 518 { 519 PIXEventsDetail::PIXSetMarker(context, color, formatString, args...); 520 } 521 522 inline void PIXEndEvent() 523 { 524 PIXEventsDetail::PIXEndEvent(); 525 } 526 527 template<typename CONTEXT> 528 void PIXEndEvent(CONTEXT* context) 529 { 530 PIXEventsDetail::PIXEndEvent(context); 531 } 532 533 #else // USE_PIX_RETAIL 534 535 inline void PIXBeginEvent(UINT64, _In_ PCSTR, ...) {} 536 inline void PIXBeginEvent(UINT64, _In_ PCWSTR, ...) {} 537 inline void PIXBeginEvent(void*, UINT64, _In_ PCSTR, ...) {} 538 inline void PIXBeginEvent(void*, UINT64, _In_ PCWSTR, ...) {} 539 inline void PIXEndEvent() {} 540 inline void PIXEndEvent(void*) {} 541 inline void PIXSetMarker(UINT64, _In_ PCSTR, ...) {} 542 inline void PIXSetMarker(UINT64, _In_ PCWSTR, ...) {} 543 inline void PIXSetMarker(void*, UINT64, _In_ PCSTR, ...) {} 544 inline void PIXSetMarker(void*, UINT64, _In_ PCWSTR, ...) {} 545 546 #endif // USE_PIX 547 548 template<typename CONTEXT, typename... ARGS> 549 void PIXBeginRetailEvent(CONTEXT* context, UINT64 color, PCWSTR formatString, ARGS... args) 550 { 551 PIXEventsDetail::PIXBeginEvent(context, color, formatString, args...); 552 } 553 554 template<typename CONTEXT, typename... ARGS> 555 void PIXBeginRetailEvent(CONTEXT* context, UINT64 color, PCSTR formatString, ARGS... args) 556 { 557 PIXEventsDetail::PIXBeginEvent(context, color, formatString, args...); 558 } 559 560 template<typename CONTEXT, typename... ARGS> 561 void PIXSetRetailMarker(CONTEXT* context, UINT64 color, PCWSTR formatString, ARGS... args) 562 { 563 PIXEventsDetail::PIXSetMarker(context, color, formatString, args...); 564 } 565 566 template<typename CONTEXT, typename... ARGS> 567 void PIXSetRetailMarker(CONTEXT* context, UINT64 color, PCSTR formatString, ARGS... args) 568 { 569 PIXEventsDetail::PIXSetMarker(context, color, formatString, args...); 570 } 571 572 template<typename CONTEXT> 573 void PIXEndRetailEvent(CONTEXT* context) 574 { 575 PIXEventsDetail::PIXEndEvent(context); 576 } 577 578 template<typename CONTEXT> 579 class PIXScopedEventObject 580 { 581 CONTEXT* m_context; 582 583 public: 584 template<typename... ARGS> 585 PIXScopedEventObject(CONTEXT* context, UINT64 color, PCWSTR formatString, ARGS... args) 586 : m_context(context) 587 { 588 PIXBeginEvent(m_context, color, formatString, args...); 589 } 590 591 template<typename... ARGS> 592 PIXScopedEventObject(CONTEXT* context, UINT64 color, PCSTR formatString, ARGS... args) 593 : m_context(context) 594 { 595 PIXBeginEvent(m_context, color, formatString, args...); 596 } 597 598 ~PIXScopedEventObject() 599 { 600 PIXEndEvent(m_context); 601 } 602 }; 603 604 template<typename CONTEXT> 605 class PIXScopedRetailEventObject 606 { 607 CONTEXT* m_context; 608 609 public: 610 template<typename... ARGS> 611 PIXScopedRetailEventObject(CONTEXT* context, UINT64 color, PCWSTR formatString, ARGS... args) 612 : m_context(context) 613 { 614 PIXBeginRetailEvent(m_context, color, formatString, args...); 615 } 616 617 template<typename... ARGS> 618 PIXScopedRetailEventObject(CONTEXT* context, UINT64 color, PCSTR formatString, ARGS... args) 619 : m_context(context) 620 { 621 PIXBeginRetailEvent(m_context, color, formatString, args...); 622 } 623 624 ~PIXScopedRetailEventObject() 625 { 626 PIXEndRetailEvent(m_context); 627 } 628 }; 629 630 template<> 631 class PIXScopedEventObject<void> 632 { 633 public: 634 template<typename... ARGS> 635 PIXScopedEventObject(UINT64 color, PCWSTR formatString, ARGS... args) 636 { 637 PIXBeginEvent(color, formatString, args...); 638 } 639 640 template<typename... ARGS> 641 PIXScopedEventObject(UINT64 color, PCSTR formatString, ARGS... args) 642 { 643 PIXBeginEvent(color, formatString, args...); 644 } 645 646 ~PIXScopedEventObject() 647 { 648 PIXEndEvent(); 649 } 650 }; 651 652 #define PIXConcatenate(a, b) a ## b 653 #define PIXGetScopedEventVariableName(a, b) PIXConcatenate(a, b) 654 #define PIXScopedEvent(context, ...) PIXScopedEventObject<PIXInferScopedEventType<decltype(context)>::Type> PIXGetScopedEventVariableName(pixEvent, __LINE__)(context, __VA_ARGS__) 655 656 #ifdef PIX3__DEFINED_CONSTEXPR 657 #undef constexpr 658 #undef PIX3__DEFINED_CONSTEXPR 659 #endif 660 661 #endif // _PIXEvents_H__