1 // 2 // Copyright 2022 The ANGLE Project Authors. All rights reserved. 3 // Use of this source code is governed by a BSD-style license that can be 4 // found in the LICENSE file. 5 // 6 // frame_capture_utils.h: 7 // ANGLE Frame capture common classes. 8 // 9 10 #ifndef COMMON_FRAME_CAPTURE_UTILS_H_ 11 #define COMMON_FRAME_CAPTURE_UTILS_H_ 12 13 #include "common/frame_capture_utils_autogen.h" 14 #include "common/gl_enum_utils_autogen.h" 15 16 namespace angle 17 { 18 namespace 19 { 20 template <typename ParamValueType> 21 struct ParamValueTrait 22 { 23 static_assert(sizeof(ParamValueType) == 0, "invalid ParamValueType"); 24 }; 25 26 template <> 27 struct ParamValueTrait<gl::FramebufferID> 28 { 29 static constexpr const char *name = "framebufferPacked"; 30 static const ParamType typeID = ParamType::TFramebufferID; 31 }; 32 33 template <> 34 struct ParamValueTrait<gl::BufferID> 35 { 36 static constexpr const char *name = "bufferPacked"; 37 static const ParamType typeID = ParamType::TBufferID; 38 }; 39 40 template <> 41 struct ParamValueTrait<gl::RenderbufferID> 42 { 43 static constexpr const char *name = "renderbufferPacked"; 44 static const ParamType typeID = ParamType::TRenderbufferID; 45 }; 46 47 template <> 48 struct ParamValueTrait<gl::TextureID> 49 { 50 static constexpr const char *name = "texturePacked"; 51 static const ParamType typeID = ParamType::TTextureID; 52 }; 53 54 template <> 55 struct ParamValueTrait<gl::ShaderProgramID> 56 { 57 static constexpr const char *name = "programPacked"; 58 static const ParamType typeID = ParamType::TShaderProgramID; 59 }; 60 } // namespace 61 62 using ParamData = std::vector<std::vector<uint8_t>>; 63 struct ParamCapture : angle::NonCopyable 64 { 65 ParamCapture(); 66 ParamCapture(const char *nameIn, ParamType typeIn); 67 ~ParamCapture(); 68 69 ParamCapture(ParamCapture &&other); 70 ParamCapture &operator=(ParamCapture &&other); 71 72 std::string name; 73 ParamType type; 74 ParamValue value; 75 gl::GLESEnum enumGroup; // only used for param type GLenum, GLboolean and GLbitfield 76 gl::BigGLEnum bigGLEnum; // only used for param type GLenum, GLboolean and GLbitfield 77 ParamData data; 78 int dataNElements = 0; 79 int arrayClientPointerIndex = -1; 80 size_t readBufferSizeBytes = 0; 81 uint32_t uniqueID = 0; 82 static uint32_t nextID; 83 }; 84 85 using Captures = std::vector<ParamCapture>; 86 87 class ParamBuffer final : angle::NonCopyable 88 { 89 public: 90 ParamBuffer(); 91 ~ParamBuffer(); 92 93 ParamBuffer(ParamBuffer &&other); 94 ParamBuffer &operator=(ParamBuffer &&other); 95 96 template <typename T> 97 void addValueParam(const char *paramName, ParamType paramType, T paramValue); 98 template <typename T> 99 void setValueParamAtIndex(const char *paramName, ParamType paramType, T paramValue, int index); 100 template <typename T> 101 void addEnumParam(const char *paramName, 102 gl::GLESEnum enumGroup, 103 ParamType paramType, 104 T paramValue); 105 template <typename T> 106 void addEnumParam(const char *paramName, 107 gl::BigGLEnum enumGroup, 108 ParamType paramType, 109 T paramValue); 110 111 template <typename T> 112 void addUnnamedParam(ParamType paramType, T paramValue); 113 114 ParamCapture &getParam(const char *paramName, ParamType paramType, int index); 115 const ParamCapture &getParam(const char *paramName, ParamType paramType, int index) const; 116 ParamCapture &getParamFlexName(const char *paramName1, 117 const char *paramName2, 118 ParamType paramType, 119 int index); 120 const ParamCapture &getParamFlexName(const char *paramName1, 121 const char *paramName2, 122 ParamType paramType, 123 int index) const; 124 const ParamCapture &getReturnValue() const { return mReturnValueCapture; } 125 126 void addParam(ParamCapture &¶m); 127 void addReturnValue(ParamCapture &&returnValue); 128 bool hasClientArrayData() const { return mClientArrayDataParam != -1; } 129 ParamCapture &getClientArrayPointerParameter(); 130 size_t getReadBufferSize() const { return mReadBufferSize; } 131 132 bool empty() const { return mParamCaptures.empty(); } 133 const std::vector<ParamCapture> &getParamCaptures() const { return mParamCaptures; } 134 135 const char *getNextParamName(); 136 137 private: 138 std::vector<ParamCapture> mParamCaptures; 139 ParamCapture mReturnValueCapture; 140 int mClientArrayDataParam = -1; 141 size_t mReadBufferSize = 0; 142 }; 143 144 struct CallCapture 145 { 146 CallCapture(EntryPoint entryPointIn, ParamBuffer &¶msIn); 147 CallCapture(const std::string &customFunctionNameIn, ParamBuffer &¶msIn); 148 ~CallCapture(); 149 150 CallCapture(CallCapture &&other); 151 CallCapture &operator=(CallCapture &&other); 152 153 const char *name() const; 154 155 EntryPoint entryPoint; 156 std::string customFunctionName; 157 ParamBuffer params; 158 bool isActive = true; 159 gl::ContextID contextID; 160 bool isSyncPoint = false; 161 }; 162 163 template <typename T> 164 void ParamBuffer::addValueParam(const char *paramName, ParamType paramType, T paramValue) 165 { 166 ParamCapture capture(paramName, paramType); 167 InitParamValue(paramType, paramValue, &capture.value); 168 mParamCaptures.emplace_back(std::move(capture)); 169 } 170 171 template <typename T> 172 void ParamBuffer::setValueParamAtIndex(const char *paramName, 173 ParamType paramType, 174 T paramValue, 175 int index) 176 { 177 ASSERT(mParamCaptures.size() > static_cast<size_t>(index)); 178 179 ParamCapture capture(paramName, paramType); 180 InitParamValue(paramType, paramValue, &capture.value); 181 mParamCaptures[index] = std::move(capture); 182 } 183 184 template <typename T> 185 void ParamBuffer::addEnumParam(const char *paramName, 186 gl::GLESEnum enumGroup, 187 ParamType paramType, 188 T paramValue) 189 { 190 ParamCapture capture(paramName, paramType); 191 InitParamValue(paramType, paramValue, &capture.value); 192 capture.enumGroup = enumGroup; 193 mParamCaptures.emplace_back(std::move(capture)); 194 } 195 196 template <typename T> 197 void ParamBuffer::addEnumParam(const char *paramName, 198 gl::BigGLEnum enumGroup, 199 ParamType paramType, 200 T paramValue) 201 { 202 ParamCapture capture(paramName, paramType); 203 InitParamValue(paramType, paramValue, &capture.value); 204 capture.bigGLEnum = enumGroup; 205 mParamCaptures.emplace_back(std::move(capture)); 206 } 207 208 template <typename T> 209 void ParamBuffer::addUnnamedParam(ParamType paramType, T paramValue) 210 { 211 addValueParam(getNextParamName(), paramType, paramValue); 212 } 213 214 template <ParamType ParamT, typename T> 215 void WriteParamValueReplay(std::ostream &os, const CallCapture &call, T value); 216 217 template <> 218 void WriteParamValueReplay<ParamType::TGLboolean>(std::ostream &os, 219 const CallCapture &call, 220 GLboolean value); 221 222 template <> 223 void WriteParamValueReplay<ParamType::TGLbooleanPointer>(std::ostream &os, 224 const CallCapture &call, 225 GLboolean *value); 226 227 template <> 228 void WriteParamValueReplay<ParamType::TvoidConstPointer>(std::ostream &os, 229 const CallCapture &call, 230 const void *value); 231 232 template <> 233 void WriteParamValueReplay<ParamType::TvoidPointer>(std::ostream &os, 234 const CallCapture &call, 235 void *value); 236 237 template <> 238 void WriteParamValueReplay<ParamType::TGLfloatConstPointer>(std::ostream &os, 239 const CallCapture &call, 240 const GLfloat *value); 241 242 template <> 243 void WriteParamValueReplay<ParamType::TGLintConstPointer>(std::ostream &os, 244 const CallCapture &call, 245 const GLint *value); 246 247 template <> 248 void WriteParamValueReplay<ParamType::TGLsizeiPointer>(std::ostream &os, 249 const CallCapture &call, 250 GLsizei *value); 251 template <> 252 void WriteParamValueReplay<ParamType::TGLuintPointer>(std::ostream &os, 253 const CallCapture &call, 254 GLuint *value); 255 template <> 256 void WriteParamValueReplay<ParamType::TGLuintConstPointer>(std::ostream &os, 257 const CallCapture &call, 258 const GLuint *value); 259 260 template <> 261 void WriteParamValueReplay<ParamType::TGLDEBUGPROCKHR>(std::ostream &os, 262 const CallCapture &call, 263 GLDEBUGPROCKHR value); 264 265 template <> 266 void WriteParamValueReplay<ParamType::TGLDEBUGPROC>(std::ostream &os, 267 const CallCapture &call, 268 GLDEBUGPROC value); 269 270 template <> 271 void WriteParamValueReplay<ParamType::TBufferID>(std::ostream &os, 272 const CallCapture &call, 273 gl::BufferID value); 274 275 template <> 276 void WriteParamValueReplay<ParamType::TFenceNVID>(std::ostream &os, 277 const CallCapture &call, 278 gl::FenceNVID value); 279 280 template <> 281 void WriteParamValueReplay<ParamType::TFramebufferID>(std::ostream &os, 282 const CallCapture &call, 283 gl::FramebufferID value); 284 285 template <> 286 void WriteParamValueReplay<ParamType::TMemoryObjectID>(std::ostream &os, 287 const CallCapture &call, 288 gl::MemoryObjectID value); 289 290 template <> 291 void WriteParamValueReplay<ParamType::TProgramPipelineID>(std::ostream &os, 292 const CallCapture &call, 293 gl::ProgramPipelineID value); 294 295 template <> 296 void WriteParamValueReplay<ParamType::TQueryID>(std::ostream &os, 297 const CallCapture &call, 298 gl::QueryID value); 299 300 template <> 301 void WriteParamValueReplay<ParamType::TRenderbufferID>(std::ostream &os, 302 const CallCapture &call, 303 gl::RenderbufferID value); 304 305 template <> 306 void WriteParamValueReplay<ParamType::TSamplerID>(std::ostream &os, 307 const CallCapture &call, 308 gl::SamplerID value); 309 310 template <> 311 void WriteParamValueReplay<ParamType::TSemaphoreID>(std::ostream &os, 312 const CallCapture &call, 313 gl::SemaphoreID value); 314 315 template <> 316 void WriteParamValueReplay<ParamType::TShaderProgramID>(std::ostream &os, 317 const CallCapture &call, 318 gl::ShaderProgramID value); 319 320 template <> 321 void WriteParamValueReplay<ParamType::TTextureID>(std::ostream &os, 322 const CallCapture &call, 323 gl::TextureID value); 324 325 template <> 326 void WriteParamValueReplay<ParamType::TTransformFeedbackID>(std::ostream &os, 327 const CallCapture &call, 328 gl::TransformFeedbackID value); 329 330 template <> 331 void WriteParamValueReplay<ParamType::TVertexArrayID>(std::ostream &os, 332 const CallCapture &call, 333 gl::VertexArrayID value); 334 335 template <> 336 void WriteParamValueReplay<ParamType::TUniformLocation>(std::ostream &os, 337 const CallCapture &call, 338 gl::UniformLocation value); 339 340 template <> 341 void WriteParamValueReplay<ParamType::TUniformBlockIndex>(std::ostream &os, 342 const CallCapture &call, 343 gl::UniformBlockIndex value); 344 345 template <> 346 void WriteParamValueReplay<ParamType::TSyncID>(std::ostream &os, 347 const CallCapture &call, 348 gl::SyncID value); 349 350 template <> 351 void WriteParamValueReplay<ParamType::TGLubyte>(std::ostream &os, 352 const CallCapture &call, 353 GLubyte value); 354 355 template <> 356 void WriteParamValueReplay<ParamType::TContextID>(std::ostream &os, 357 const CallCapture &call, 358 gl::ContextID value); 359 360 template <> 361 void WriteParamValueReplay<ParamType::Tegl_DisplayPointer>(std::ostream &os, 362 const CallCapture &call, 363 egl::Display *value); 364 365 template <> 366 void WriteParamValueReplay<ParamType::TImageID>(std::ostream &os, 367 const CallCapture &call, 368 egl::ImageID value); 369 370 template <> 371 void WriteParamValueReplay<ParamType::TSurfaceID>(std::ostream &os, 372 const CallCapture &call, 373 egl::SurfaceID value); 374 375 template <> 376 void WriteParamValueReplay<ParamType::TEGLDEBUGPROCKHR>(std::ostream &os, 377 const CallCapture &call, 378 EGLDEBUGPROCKHR value); 379 380 template <> 381 void WriteParamValueReplay<ParamType::TEGLGetBlobFuncANDROID>(std::ostream &os, 382 const CallCapture &call, 383 EGLGetBlobFuncANDROID value); 384 385 template <> 386 void WriteParamValueReplay<ParamType::TEGLSetBlobFuncANDROID>(std::ostream &os, 387 const CallCapture &call, 388 EGLSetBlobFuncANDROID value); 389 template <> 390 void WriteParamValueReplay<ParamType::TEGLClientBuffer>(std::ostream &os, 391 const CallCapture &call, 392 EGLClientBuffer value); 393 394 template <> 395 void WriteParamValueReplay<ParamType::TEGLAttribPointer>(std::ostream &os, 396 const CallCapture &call, 397 EGLAttrib *value); 398 399 template <> 400 void WriteParamValueReplay<ParamType::TEGLAttribConstPointer>(std::ostream &os, 401 const CallCapture &call, 402 const EGLAttrib *value); 403 404 template <> 405 void WriteParamValueReplay<ParamType::TEGLintPointer>(std::ostream &os, 406 const CallCapture &call, 407 EGLint *value); 408 409 template <> 410 void WriteParamValueReplay<ParamType::TEGLintConstPointer>(std::ostream &os, 411 const CallCapture &call, 412 const EGLint *value); 413 414 template <> 415 void WriteParamValueReplay<ParamType::Tegl_ConfigPointer>(std::ostream &os, 416 const CallCapture &call, 417 egl::Config *value); 418 419 template <> 420 void WriteParamValueReplay<ParamType::Tegl_SyncID>(std::ostream &os, 421 const CallCapture &call, 422 egl::SyncID value); 423 424 template <> 425 void WriteParamValueReplay<ParamType::TEGLTime>(std::ostream &os, 426 const CallCapture &call, 427 EGLTime value); 428 429 template <> 430 void WriteParamValueReplay<ParamType::TEGLTimeKHR>(std::ostream &os, 431 const CallCapture &call, 432 EGLTimeKHR value); 433 434 template <> 435 void WriteParamValueReplay<ParamType::TGLGETBLOBPROCANGLE>(std::ostream &os, 436 const CallCapture &call, 437 GLGETBLOBPROCANGLE value); 438 439 template <> 440 void WriteParamValueReplay<ParamType::TGLSETBLOBPROCANGLE>(std::ostream &os, 441 const CallCapture &call, 442 GLSETBLOBPROCANGLE value); 443 444 template <> 445 void WriteParamValueReplay<ParamType::TcharConstPointer>(std::ostream &os, 446 const CallCapture &call, 447 const char *value); 448 449 template <> 450 void WriteParamValueReplay<ParamType::Tsize_tPointer>(std::ostream &os, 451 const CallCapture &call, 452 size_t *value); 453 454 template <> 455 void WriteParamValueReplay<ParamType::Tsize_tConstPointer>(std::ostream &os, 456 const CallCapture &call, 457 size_t const *value); 458 459 template <> 460 void WriteParamValueReplay<ParamType::TcharConstPointerPointer>(std::ostream &os, 461 const CallCapture &call, 462 const char **value); 463 464 template <> 465 void WriteParamValueReplay<ParamType::TcharUnsignedConstPointerPointer>( 466 std::ostream &os, 467 const CallCapture &call, 468 const unsigned char **value); 469 470 #ifdef ANGLE_ENABLE_CL 471 472 template <> 473 void WriteParamValueReplay<ParamType::Tcl_platform_idPointer>(std::ostream &os, 474 const CallCapture &call, 475 cl_platform_id *value); 476 477 template <> 478 void WriteParamValueReplay<ParamType::Tcl_uintPointer>(std::ostream &os, 479 const CallCapture &call, 480 cl_uint *value); 481 482 template <> 483 void WriteParamValueReplay<ParamType::Tcl_device_idPointer>(std::ostream &os, 484 const CallCapture &call, 485 cl_device_id *value); 486 487 template <> 488 void WriteParamValueReplay<ParamType::Tcl_context_propertiesConstPointer>( 489 std::ostream &os, 490 const CallCapture &call, 491 cl_context_properties const *value); 492 493 template <> 494 void WriteParamValueReplay<ParamType::Tcl_eventPointer>(std::ostream &os, 495 const CallCapture &call, 496 cl_event *value); 497 498 template <> 499 void WriteParamValueReplay<ParamType::Tcl_eventConstPointer>(std::ostream &os, 500 const CallCapture &call, 501 cl_event const *value); 502 503 template <> 504 void WriteParamValueReplay<ParamType::Tcl_device_idConstPointer>(std::ostream &os, 505 const CallCapture &call, 506 cl_device_id const *value); 507 508 template <> 509 void WriteParamValueReplay<ParamType::Tcl_image_formatPointer>(std::ostream &os, 510 const CallCapture &call, 511 cl_image_format *value); 512 513 template <> 514 void WriteParamValueReplay<ParamType::Tcl_intPointer>(std::ostream &os, 515 const CallCapture &call, 516 cl_int *value); 517 518 template <> 519 void WriteParamValueReplay<ParamType::Tcl_queue_propertiesConstPointer>( 520 std::ostream &os, 521 const CallCapture &call, 522 const cl_queue_properties *value); 523 524 template <> 525 void WriteParamValueReplay<ParamType::Tcl_command_queue_propertiesPointer>( 526 std::ostream &os, 527 const CallCapture &call, 528 const cl_command_queue_properties *value); 529 530 template <> 531 void WriteParamValueReplay<ParamType::Tcl_device_partition_propertyConstPointer>( 532 std::ostream &os, 533 const CallCapture &call, 534 const cl_device_partition_property *value); 535 536 template <> 537 void WriteParamValueReplay<ParamType::Tcl_programConstPointer>(std::ostream &os, 538 const CallCapture &call, 539 const cl_program *value); 540 541 template <> 542 void WriteParamValueReplay<ParamType::Tcl_pipe_propertiesConstPointer>( 543 std::ostream &os, 544 const CallCapture &call, 545 const cl_pipe_properties *value); 546 547 template <> 548 void WriteParamValueReplay<ParamType::Tcl_ulongPointer>(std::ostream &os, 549 const CallCapture &call, 550 cl_ulong *value); 551 552 template <> 553 void WriteParamValueReplay<ParamType::Tcl_callback_func_type>(std::ostream &os, 554 const CallCapture &call, 555 cl_callback_func_type value); 556 557 template <> 558 void WriteParamValueReplay<ParamType::Tcl_context_destructor_func_type>( 559 std::ostream &os, 560 const CallCapture &call, 561 cl_context_destructor_func_type value); 562 563 template <> 564 void WriteParamValueReplay<ParamType::Tcl_context_func_type>(std::ostream &os, 565 const CallCapture &call, 566 cl_context_func_type value); 567 568 template <> 569 void WriteParamValueReplay<ParamType::Tcl_mem_destructor_func_type>( 570 std::ostream &os, 571 const CallCapture &call, 572 cl_mem_destructor_func_type value); 573 574 template <> 575 void WriteParamValueReplay<ParamType::Tcl_program_func_type>(std::ostream &os, 576 const CallCapture &call, 577 cl_program_func_type value); 578 579 template <> 580 void WriteParamValueReplay<ParamType::Tcl_svm_free_callback_func_type>( 581 std::ostream &os, 582 const CallCapture &call, 583 cl_svm_free_callback_func_type value); 584 585 template <> 586 void WriteParamValueReplay<ParamType::Tcl_void_func_type>(std::ostream &os, 587 const CallCapture &call, 588 cl_void_func_type value); 589 590 template <ParamType ParamT> 591 void WriteParamValueReplay(std::ostream &os, const CallCapture &call, cl::BitField value) 592 { 593 os << value.get(); 594 } 595 596 #endif 597 598 // General fallback for any unspecific type. 599 template <ParamType ParamT, typename T> 600 void WriteParamValueReplay(std::ostream &os, const CallCapture &call, T value) 601 { 602 os << value; 603 } 604 605 struct FmtPointerIndex 606 { 607 FmtPointerIndex(const void *ptrIn) : ptr(ptrIn) {} 608 const void *ptr; 609 }; 610 611 inline std::ostream &operator<<(std::ostream &os, const FmtPointerIndex &fmt) 612 { 613 os << reinterpret_cast<uintptr_t>(fmt.ptr) << "ul"; 614 return os; 615 } 616 617 template <typename ParamValueType> 618 bool FindResourceIDsInCall(const CallCapture &call, std::vector<ParamValueType> &idsOut); 619 } // namespace angle 620 621 #endif // COMMON_FRAME_CAPTURE_UTILS_H_ 622