// Copyright (C) 2018 The Android Open Source Project
// Copyright (C) 2018 Google Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

// Autogenerated module VkEncoder
//
// (impl) generated by codegen/vulkan/vulkan-docs-next/scripts/genvk.py -registry
// codegen/vulkan/vulkan-docs-next/xml/vk.xml -registryGfxstream
// codegen/vulkan/vulkan-docs-next/xml/vk_gfxstream.xml cereal -o host/vulkan/cereal
//
// Please do not modify directly;
// re-run gfxstream-protocols/scripts/generate-vulkan-sources.sh,
// or directly from Python by defining:
// VULKAN_REGISTRY_XML_DIR : Directory containing vk.xml
// VULKAN_REGISTRY_SCRIPTS_DIR : Directory containing genvk.py
// CEREAL_OUTPUT_DIR: Where to put the generated sources.
//
// python3 $VULKAN_REGISTRY_SCRIPTS_DIR/genvk.py -registry $VULKAN_REGISTRY_XML_DIR/vk.xml cereal -o
// $CEREAL_OUTPUT_DIR
//

#include "VkEncoder.h"

#include <cutils/properties.h>

#include <memory>
#include <optional>
#include <string>
#include <unordered_map>
#include <vector>

#include "EncoderDebug.h"
#include "ResourceTracker.h"
#include "Resources.h"
#include "Validation.h"
#include "VulkanStreamGuest.h"
#include "aemu/base/AlignedBuf.h"
#include "aemu/base/BumpPool.h"
#include "aemu/base/synchronization/AndroidLock.h"
#include "gfxstream/guest/IOStream.h"
#include "goldfish_vk_counting_guest.h"
#include "goldfish_vk_deepcopy_guest.h"
#include "goldfish_vk_marshaling_guest.h"
#include "goldfish_vk_private_defs.h"
#include "goldfish_vk_reserved_marshaling_guest.h"
#include "goldfish_vk_transform_guest.h"

namespace gfxstream {
namespace vk {

using namespace gfxstream::vk;

using gfxstream::guest::AutoLock;
using gfxstream::guest::BumpPool;
using gfxstream::guest::Lock;

#include "VkEncoder.cpp.inl"

#define VALIDATE_RET(retType, success, validate)   \
    retType goldfish_vk_validateResult = validate; \
    if (goldfish_vk_validateResult != success) return goldfish_vk_validateResult;

#define VALIDATE_VOID(validate)                     \
    VkResult goldfish_vk_validateResult = validate; \
    if (goldfish_vk_validateResult != VK_SUCCESS) return;

#ifdef VK_VERSION_1_0
VkResult VkEncoder::vkCreateInstance(const VkInstanceCreateInfo* pCreateInfo,
                                     const VkAllocationCallbacks* pAllocator, VkInstance* pInstance,
                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateInstance in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateInstance(pCreateInfo:%p, pAllocator:%p, pInstance:%p)", pCreateInfo,
                      pAllocator, pInstance);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkInstanceCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkInstanceCreateInfo*)pool->alloc(sizeof(const VkInstanceCreateInfo));
        deepcopy_VkInstanceCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                      (VkInstanceCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkInstanceCreateInfo(sResourceTracker,
                                              (VkInstanceCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        count_VkInstanceCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkInstanceCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_0;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateInstance = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateInstance);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateInstance);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateInstance = OP_vkCreateInstance;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateInstance, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateInstance, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    reservedmarshal_VkInstanceCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkInstanceCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_0 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_0, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_1;
    *&cgen_var_1 = (uint64_t)((*pInstance));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateInstance), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_2;
    stream->read((uint64_t*)&cgen_var_2, 8);
    stream->handleMapping()->mapHandles_u64_VkInstance(&cgen_var_2, (VkInstance*)pInstance, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateInstance_VkResult_return = (VkResult)0;
    stream->read(&vkCreateInstance_VkResult_return, sizeof(VkResult));
    sResourceTracker->on_vkCreateInstance(this, vkCreateInstance_VkResult_return, pCreateInfo,
                                          pAllocator, pInstance);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateInstance_VkResult_return;
}

void VkEncoder::vkDestroyInstance(VkInstance instance, const VkAllocationCallbacks* pAllocator,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyInstance in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyInstance(instance:%p, pAllocator:%p)", instance, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkInstance local_instance;
    VkAllocationCallbacks* local_pAllocator;
    local_instance = instance;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyInstance =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyInstance);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyInstance);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyInstance = OP_vkDestroyInstance;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyInstance, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyInstance, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkInstance((*&local_instance));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyInstance), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkInstance((VkInstance*)&instance);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkEnumeratePhysicalDevices(VkInstance instance, uint32_t* pPhysicalDeviceCount,
                                               VkPhysicalDevice* pPhysicalDevices,
                                               uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEnumeratePhysicalDevices in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkEnumeratePhysicalDevices(instance:%p, pPhysicalDeviceCount:%p, pPhysicalDevices:%p)",
        instance, pPhysicalDeviceCount, pPhysicalDevices);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkInstance local_instance;
    local_instance = instance;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPhysicalDeviceCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPhysicalDevices) {
            if ((*(pPhysicalDeviceCount))) {
                *countPtr += (*(pPhysicalDeviceCount)) * 8;
            }
        }
    }
    uint32_t packetSize_vkEnumeratePhysicalDevices =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkEnumeratePhysicalDevices);
    uint8_t* streamPtr = stream->reserve(packetSize_vkEnumeratePhysicalDevices);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEnumeratePhysicalDevices = OP_vkEnumeratePhysicalDevices;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkEnumeratePhysicalDevices, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEnumeratePhysicalDevices, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkInstance((*&local_instance));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pPhysicalDeviceCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPhysicalDeviceCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPhysicalDeviceCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    /* is handle, possibly out */;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pPhysicalDevices;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPhysicalDevices) {
        if ((*(pPhysicalDeviceCount))) {
            uint8_t* cgen_var_2_0_ptr = (uint8_t*)(*streamPtrPtr);
            if (pPhysicalDeviceCount) {
                for (uint32_t k = 0; k < (*(pPhysicalDeviceCount)); ++k) {
                    uint64_t tmpval = (uint64_t)(pPhysicalDevices[k]);
                    memcpy(cgen_var_2_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
                }
            }
            *streamPtrPtr += 8 * (*(pPhysicalDeviceCount));
        }
    }
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkEnumeratePhysicalDevices), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPhysicalDeviceCount;
    check_pPhysicalDeviceCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPhysicalDeviceCount) {
        if (!(check_pPhysicalDeviceCount)) {
            fprintf(stderr, "fatal: pPhysicalDeviceCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPhysicalDeviceCount, sizeof(uint32_t));
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    // WARNING PTR CHECK
    VkPhysicalDevice* check_pPhysicalDevices;
    check_pPhysicalDevices = (VkPhysicalDevice*)(uintptr_t)stream->getBe64();
    if (pPhysicalDevices) {
        if (!(check_pPhysicalDevices)) {
            fprintf(stderr, "fatal: pPhysicalDevices inconsistent between guest and host\n");
        }
        if ((*(pPhysicalDeviceCount))) {
            uint64_t* cgen_var_4_0;
            stream->alloc((void**)&cgen_var_4_0, (*(pPhysicalDeviceCount)) * 8);
            stream->read((uint64_t*)cgen_var_4_0, (*(pPhysicalDeviceCount)) * 8);
            stream->handleMapping()->mapHandles_u64_VkPhysicalDevice(
                cgen_var_4_0, (VkPhysicalDevice*)pPhysicalDevices, (*(pPhysicalDeviceCount)));
        }
    }
    stream->unsetHandleMapping();
    VkResult vkEnumeratePhysicalDevices_VkResult_return = (VkResult)0;
    stream->read(&vkEnumeratePhysicalDevices_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEnumeratePhysicalDevices_VkResult_return;
}

void VkEncoder::vkGetPhysicalDeviceFeatures(VkPhysicalDevice physicalDevice,
                                            VkPhysicalDeviceFeatures* pFeatures, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceFeatures in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPhysicalDeviceFeatures(physicalDevice:%p, pFeatures:%p)",
                      physicalDevice, pFeatures);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceFeatures(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkPhysicalDeviceFeatures*)(pFeatures), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceFeatures =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetPhysicalDeviceFeatures);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceFeatures);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceFeatures = OP_vkGetPhysicalDeviceFeatures;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceFeatures, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceFeatures, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceFeatures(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkPhysicalDeviceFeatures*)(pFeatures), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceFeatures), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceFeatures(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkPhysicalDeviceFeatures*)(pFeatures));
    if (pFeatures) {
        transform_fromhost_VkPhysicalDeviceFeatures(sResourceTracker,
                                                    (VkPhysicalDeviceFeatures*)(pFeatures));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceFormatProperties(VkPhysicalDevice physicalDevice,
                                                    VkFormat format,
                                                    VkFormatProperties* pFormatProperties,
                                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceFormatProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceFormatProperties(physicalDevice:%p, format:%d, pFormatProperties:%p)",
        physicalDevice, format, pFormatProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkFormat local_format;
    local_physicalDevice = physicalDevice;
    local_format = format;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        count_VkFormatProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkFormatProperties*)(pFormatProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceFormatProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceFormatProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceFormatProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceFormatProperties = OP_vkGetPhysicalDeviceFormatProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceFormatProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceFormatProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    reservedmarshal_VkFormatProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkFormatProperties*)(pFormatProperties), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPhysicalDeviceFormatProperties),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkFormatProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkFormatProperties*)(pFormatProperties));
    if (pFormatProperties) {
        transform_fromhost_VkFormatProperties(sResourceTracker,
                                              (VkFormatProperties*)(pFormatProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetPhysicalDeviceImageFormatProperties(
    VkPhysicalDevice physicalDevice, VkFormat format, VkImageType type, VkImageTiling tiling,
    VkImageUsageFlags usage, VkImageCreateFlags flags,
    VkImageFormatProperties* pImageFormatProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceImageFormatProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceImageFormatProperties(physicalDevice:%p, format:%d, usage:%d, "
        "flags:%d, pImageFormatProperties:%p)",
        physicalDevice, format, usage, flags, pImageFormatProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkFormat local_format;
    VkImageType local_type;
    VkImageTiling local_tiling;
    VkImageUsageFlags local_usage;
    VkImageCreateFlags local_flags;
    local_physicalDevice = physicalDevice;
    local_format = format;
    local_type = type;
    local_tiling = tiling;
    local_usage = usage;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        *countPtr += sizeof(VkImageType);
        *countPtr += sizeof(VkImageTiling);
        *countPtr += sizeof(VkImageUsageFlags);
        *countPtr += sizeof(VkImageCreateFlags);
        count_VkImageFormatProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkImageFormatProperties*)(pImageFormatProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceImageFormatProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceImageFormatProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceImageFormatProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceImageFormatProperties =
        OP_vkGetPhysicalDeviceImageFormatProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceImageFormatProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceImageFormatProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    memcpy(*streamPtrPtr, (VkImageType*)&local_type, sizeof(VkImageType));
    *streamPtrPtr += sizeof(VkImageType);
    memcpy(*streamPtrPtr, (VkImageTiling*)&local_tiling, sizeof(VkImageTiling));
    *streamPtrPtr += sizeof(VkImageTiling);
    memcpy(*streamPtrPtr, (VkImageUsageFlags*)&local_usage, sizeof(VkImageUsageFlags));
    *streamPtrPtr += sizeof(VkImageUsageFlags);
    memcpy(*streamPtrPtr, (VkImageCreateFlags*)&local_flags, sizeof(VkImageCreateFlags));
    *streamPtrPtr += sizeof(VkImageCreateFlags);
    reservedmarshal_VkImageFormatProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkImageFormatProperties*)(pImageFormatProperties),
                                            streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceImageFormatProperties),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkImageFormatProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkImageFormatProperties*)(pImageFormatProperties));
    if (pImageFormatProperties) {
        transform_fromhost_VkImageFormatProperties(
            sResourceTracker, (VkImageFormatProperties*)(pImageFormatProperties));
    }
    VkResult vkGetPhysicalDeviceImageFormatProperties_VkResult_return = (VkResult)0;
    stream->read(&vkGetPhysicalDeviceImageFormatProperties_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPhysicalDeviceImageFormatProperties_VkResult_return;
}

void VkEncoder::vkGetPhysicalDeviceProperties(VkPhysicalDevice physicalDevice,
                                              VkPhysicalDeviceProperties* pProperties,
                                              uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPhysicalDeviceProperties(physicalDevice:%p, pProperties:%p)",
                      physicalDevice, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkPhysicalDeviceProperties*)(pProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceProperties = OP_vkGetPhysicalDeviceProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                               (VkPhysicalDeviceProperties*)(pProperties),
                                               streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceProperties), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkPhysicalDeviceProperties*)(pProperties));
    if (pProperties) {
        transform_fromhost_VkPhysicalDeviceProperties(sResourceTracker,
                                                      (VkPhysicalDeviceProperties*)(pProperties));
    }
    sResourceTracker->on_vkGetPhysicalDeviceProperties(this, physicalDevice, pProperties);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceQueueFamilyProperties(
    VkPhysicalDevice physicalDevice, uint32_t* pQueueFamilyPropertyCount,
    VkQueueFamilyProperties* pQueueFamilyProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceQueueFamilyProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceQueueFamilyProperties(physicalDevice:%p, pQueueFamilyPropertyCount:%p, "
        "pQueueFamilyProperties:%p)",
        physicalDevice, pQueueFamilyPropertyCount, pQueueFamilyProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pQueueFamilyPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pQueueFamilyProperties) {
            if (pQueueFamilyPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                    count_VkQueueFamilyProperties(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkQueueFamilyProperties*)(pQueueFamilyProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceQueueFamilyProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceQueueFamilyProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceQueueFamilyProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceQueueFamilyProperties =
        OP_vkGetPhysicalDeviceQueueFamilyProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceQueueFamilyProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceQueueFamilyProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pQueueFamilyPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pQueueFamilyPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pQueueFamilyPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pQueueFamilyProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pQueueFamilyProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
            reservedmarshal_VkQueueFamilyProperties(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkQueueFamilyProperties*)(pQueueFamilyProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceQueueFamilyProperties),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pQueueFamilyPropertyCount;
    check_pQueueFamilyPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pQueueFamilyPropertyCount) {
        if (!(check_pQueueFamilyPropertyCount)) {
            fprintf(stderr,
                    "fatal: pQueueFamilyPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pQueueFamilyPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkQueueFamilyProperties* check_pQueueFamilyProperties;
    check_pQueueFamilyProperties = (VkQueueFamilyProperties*)(uintptr_t)stream->getBe64();
    if (pQueueFamilyProperties) {
        if (!(check_pQueueFamilyProperties)) {
            fprintf(stderr, "fatal: pQueueFamilyProperties inconsistent between guest and host\n");
        }
        if (pQueueFamilyPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                unmarshal_VkQueueFamilyProperties(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkQueueFamilyProperties*)(pQueueFamilyProperties + i));
            }
        }
    }
    if (pQueueFamilyPropertyCount) {
        if (pQueueFamilyProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                transform_fromhost_VkQueueFamilyProperties(
                    sResourceTracker, (VkQueueFamilyProperties*)(pQueueFamilyProperties + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceMemoryProperties(
    VkPhysicalDevice physicalDevice, VkPhysicalDeviceMemoryProperties* pMemoryProperties,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceMemoryProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceMemoryProperties(physicalDevice:%p, pMemoryProperties:%p)",
        physicalDevice, pMemoryProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceMemoryProperties(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceMemoryProperties*)(pMemoryProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceMemoryProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceMemoryProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceMemoryProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceMemoryProperties = OP_vkGetPhysicalDeviceMemoryProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceMemoryProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceMemoryProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceMemoryProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPhysicalDeviceMemoryProperties*)(pMemoryProperties),
        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPhysicalDeviceMemoryProperties),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceMemoryProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPhysicalDeviceMemoryProperties*)(pMemoryProperties));
    if (pMemoryProperties) {
        transform_fromhost_VkPhysicalDeviceMemoryProperties(
            sResourceTracker, (VkPhysicalDeviceMemoryProperties*)(pMemoryProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

PFN_vkVoidFunction VkEncoder::vkGetInstanceProcAddr(VkInstance instance, const char* pName,
                                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetInstanceProcAddr in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetInstanceProcAddr(instance:%p, pName:%p)", instance, pName);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkInstance local_instance;
    char* local_pName;
    local_instance = instance;
    // Avoiding deepcopy for pName
    local_pName = (char*)pName;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t) + (local_pName ? strlen(local_pName) : 0);
    }
    uint32_t packetSize_vkGetInstanceProcAddr =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetInstanceProcAddr);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetInstanceProcAddr);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetInstanceProcAddr = OP_vkGetInstanceProcAddr;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetInstanceProcAddr, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetInstanceProcAddr, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkInstance((*&local_instance));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    {
        uint32_t l = local_pName ? strlen(local_pName) : 0;
        memcpy(*streamPtrPtr, (uint32_t*)&l, sizeof(uint32_t));
        gfxstream::guest::Stream::toBe32((uint8_t*)*streamPtrPtr);
        *streamPtrPtr += sizeof(uint32_t);
        memcpy(*streamPtrPtr, (char*)local_pName, l);
        *streamPtrPtr += l;
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetInstanceProcAddr), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    PFN_vkVoidFunction vkGetInstanceProcAddr_PFN_vkVoidFunction_return = (PFN_vkVoidFunction)0;
    stream->read(&vkGetInstanceProcAddr_PFN_vkVoidFunction_return, sizeof(PFN_vkVoidFunction));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetInstanceProcAddr_PFN_vkVoidFunction_return;
}

PFN_vkVoidFunction VkEncoder::vkGetDeviceProcAddr(VkDevice device, const char* pName,
                                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceProcAddr in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDeviceProcAddr(device:%p, pName:%p)", device, pName);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    char* local_pName;
    local_device = device;
    // Avoiding deepcopy for pName
    local_pName = (char*)pName;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t) + (local_pName ? strlen(local_pName) : 0);
    }
    uint32_t packetSize_vkGetDeviceProcAddr =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetDeviceProcAddr);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceProcAddr);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceProcAddr = OP_vkGetDeviceProcAddr;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceProcAddr, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceProcAddr, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    {
        uint32_t l = local_pName ? strlen(local_pName) : 0;
        memcpy(*streamPtrPtr, (uint32_t*)&l, sizeof(uint32_t));
        gfxstream::guest::Stream::toBe32((uint8_t*)*streamPtrPtr);
        *streamPtrPtr += sizeof(uint32_t);
        memcpy(*streamPtrPtr, (char*)local_pName, l);
        *streamPtrPtr += l;
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDeviceProcAddr), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    PFN_vkVoidFunction vkGetDeviceProcAddr_PFN_vkVoidFunction_return = (PFN_vkVoidFunction)0;
    stream->read(&vkGetDeviceProcAddr_PFN_vkVoidFunction_return, sizeof(PFN_vkVoidFunction));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetDeviceProcAddr_PFN_vkVoidFunction_return;
}

VkResult VkEncoder::vkCreateDevice(VkPhysicalDevice physicalDevice,
                                   const VkDeviceCreateInfo* pCreateInfo,
                                   const VkAllocationCallbacks* pAllocator, VkDevice* pDevice,
                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateDevice in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateDevice(physicalDevice:%p, pCreateInfo:%p, pAllocator:%p, pDevice:%p)",
        physicalDevice, pCreateInfo, pAllocator, pDevice);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkDeviceCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_physicalDevice = physicalDevice;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkDeviceCreateInfo*)pool->alloc(sizeof(const VkDeviceCreateInfo));
        deepcopy_VkDeviceCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                    (VkDeviceCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkDeviceCreateInfo(sResourceTracker,
                                            (VkDeviceCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkDeviceCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateDevice = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateDevice);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateDevice);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateDevice = OP_vkCreateDevice;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateDevice, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateDevice, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkDeviceCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateDevice), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkDevice(&cgen_var_3, (VkDevice*)pDevice, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateDevice_VkResult_return = (VkResult)0;
    stream->read(&vkCreateDevice_VkResult_return, sizeof(VkResult));
    sResourceTracker->on_vkCreateDevice(this, vkCreateDevice_VkResult_return, physicalDevice,
                                        pCreateInfo, pAllocator, pDevice);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateDevice_VkResult_return;
}

void VkEncoder::vkDestroyDevice(VkDevice device, const VkAllocationCallbacks* pAllocator,
                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyDevice in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyDevice(device:%p, pAllocator:%p)", device, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    sResourceTracker->on_vkDestroyDevice_pre(this, device, pAllocator);
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyDevice = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyDevice);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyDevice);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyDevice = OP_vkDestroyDevice;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyDevice, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyDevice, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyDevice), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkDevice((VkDevice*)&device);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkEnumerateInstanceExtensionProperties(const char* pLayerName,
                                                           uint32_t* pPropertyCount,
                                                           VkExtensionProperties* pProperties,
                                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEnumerateInstanceExtensionProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkEnumerateInstanceExtensionProperties(pLayerName:%p, pPropertyCount:%p, pProperties:%p)",
        pLayerName, pPropertyCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    char* local_pLayerName;
    // Avoiding deepcopy for pLayerName
    local_pLayerName = (char*)pLayerName;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        if (sFeatureBits & VULKAN_STREAM_FEATURE_NULL_OPTIONAL_STRINGS_BIT) {
            // WARNING PTR CHECK
            *countPtr += 8;
            if (local_pLayerName) {
                *countPtr += sizeof(uint32_t) + (local_pLayerName ? strlen(local_pLayerName) : 0);
            }
        } else {
            *countPtr += sizeof(uint32_t) + (local_pLayerName ? strlen(local_pLayerName) : 0);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                    count_VkExtensionProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkExtensionProperties*)(pProperties + i),
                                                countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkEnumerateInstanceExtensionProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkEnumerateInstanceExtensionProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkEnumerateInstanceExtensionProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEnumerateInstanceExtensionProperties =
        OP_vkEnumerateInstanceExtensionProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkEnumerateInstanceExtensionProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEnumerateInstanceExtensionProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    if (stream->getFeatureBits() & VULKAN_STREAM_FEATURE_NULL_OPTIONAL_STRINGS_BIT) {
        // WARNING PTR CHECK
        uint64_t cgen_var_0 = (uint64_t)(uintptr_t)local_pLayerName;
        memcpy((*streamPtrPtr), &cgen_var_0, 8);
        gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
        *streamPtrPtr += 8;
        if (local_pLayerName) {
            {
                uint32_t l = local_pLayerName ? strlen(local_pLayerName) : 0;
                memcpy(*streamPtrPtr, (uint32_t*)&l, sizeof(uint32_t));
                gfxstream::guest::Stream::toBe32((uint8_t*)*streamPtrPtr);
                *streamPtrPtr += sizeof(uint32_t);
                memcpy(*streamPtrPtr, (char*)local_pLayerName, l);
                *streamPtrPtr += l;
            }
        }
    } else {
        {
            uint32_t l = local_pLayerName ? strlen(local_pLayerName) : 0;
            memcpy(*streamPtrPtr, (uint32_t*)&l, sizeof(uint32_t));
            gfxstream::guest::Stream::toBe32((uint8_t*)*streamPtrPtr);
            *streamPtrPtr += sizeof(uint32_t);
            memcpy(*streamPtrPtr, (char*)local_pLayerName, l);
            *streamPtrPtr += l;
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_0 = (uint64_t)(uintptr_t)pPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_0, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
            reservedmarshal_VkExtensionProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                  (VkExtensionProperties*)(pProperties + i),
                                                  streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkEnumerateInstanceExtensionProperties),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPropertyCount;
    check_pPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPropertyCount) {
        if (!(check_pPropertyCount)) {
            fprintf(stderr, "fatal: pPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkExtensionProperties* check_pProperties;
    check_pProperties = (VkExtensionProperties*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                unmarshal_VkExtensionProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkExtensionProperties*)(pProperties + i));
            }
        }
    }
    if (pPropertyCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                transform_fromhost_VkExtensionProperties(sResourceTracker,
                                                         (VkExtensionProperties*)(pProperties + i));
            }
        }
    }
    VkResult vkEnumerateInstanceExtensionProperties_VkResult_return = (VkResult)0;
    stream->read(&vkEnumerateInstanceExtensionProperties_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEnumerateInstanceExtensionProperties_VkResult_return;
}

VkResult VkEncoder::vkEnumerateDeviceExtensionProperties(VkPhysicalDevice physicalDevice,
                                                         const char* pLayerName,
                                                         uint32_t* pPropertyCount,
                                                         VkExtensionProperties* pProperties,
                                                         uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEnumerateDeviceExtensionProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkEnumerateDeviceExtensionProperties(physicalDevice:%p, pLayerName:%p, pPropertyCount:%p, "
        "pProperties:%p)",
        physicalDevice, pLayerName, pPropertyCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    char* local_pLayerName;
    local_physicalDevice = physicalDevice;
    // Avoiding deepcopy for pLayerName
    local_pLayerName = (char*)pLayerName;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        if (sFeatureBits & VULKAN_STREAM_FEATURE_NULL_OPTIONAL_STRINGS_BIT) {
            // WARNING PTR CHECK
            *countPtr += 8;
            if (local_pLayerName) {
                *countPtr += sizeof(uint32_t) + (local_pLayerName ? strlen(local_pLayerName) : 0);
            }
        } else {
            *countPtr += sizeof(uint32_t) + (local_pLayerName ? strlen(local_pLayerName) : 0);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                    count_VkExtensionProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkExtensionProperties*)(pProperties + i),
                                                countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkEnumerateDeviceExtensionProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkEnumerateDeviceExtensionProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkEnumerateDeviceExtensionProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEnumerateDeviceExtensionProperties = OP_vkEnumerateDeviceExtensionProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkEnumerateDeviceExtensionProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEnumerateDeviceExtensionProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (stream->getFeatureBits() & VULKAN_STREAM_FEATURE_NULL_OPTIONAL_STRINGS_BIT) {
        // WARNING PTR CHECK
        uint64_t cgen_var_0_0 = (uint64_t)(uintptr_t)local_pLayerName;
        memcpy((*streamPtrPtr), &cgen_var_0_0, 8);
        gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
        *streamPtrPtr += 8;
        if (local_pLayerName) {
            {
                uint32_t l = local_pLayerName ? strlen(local_pLayerName) : 0;
                memcpy(*streamPtrPtr, (uint32_t*)&l, sizeof(uint32_t));
                gfxstream::guest::Stream::toBe32((uint8_t*)*streamPtrPtr);
                *streamPtrPtr += sizeof(uint32_t);
                memcpy(*streamPtrPtr, (char*)local_pLayerName, l);
                *streamPtrPtr += l;
            }
        }
    } else {
        {
            uint32_t l = local_pLayerName ? strlen(local_pLayerName) : 0;
            memcpy(*streamPtrPtr, (uint32_t*)&l, sizeof(uint32_t));
            gfxstream::guest::Stream::toBe32((uint8_t*)*streamPtrPtr);
            *streamPtrPtr += sizeof(uint32_t);
            memcpy(*streamPtrPtr, (char*)local_pLayerName, l);
            *streamPtrPtr += l;
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
            reservedmarshal_VkExtensionProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                  (VkExtensionProperties*)(pProperties + i),
                                                  streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkEnumerateDeviceExtensionProperties),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPropertyCount;
    check_pPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPropertyCount) {
        if (!(check_pPropertyCount)) {
            fprintf(stderr, "fatal: pPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkExtensionProperties* check_pProperties;
    check_pProperties = (VkExtensionProperties*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                unmarshal_VkExtensionProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkExtensionProperties*)(pProperties + i));
            }
        }
    }
    if (pPropertyCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                transform_fromhost_VkExtensionProperties(sResourceTracker,
                                                         (VkExtensionProperties*)(pProperties + i));
            }
        }
    }
    VkResult vkEnumerateDeviceExtensionProperties_VkResult_return = (VkResult)0;
    stream->read(&vkEnumerateDeviceExtensionProperties_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEnumerateDeviceExtensionProperties_VkResult_return;
}

VkResult VkEncoder::vkEnumerateInstanceLayerProperties(uint32_t* pPropertyCount,
                                                       VkLayerProperties* pProperties,
                                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEnumerateInstanceLayerProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkEnumerateInstanceLayerProperties(pPropertyCount:%p, pProperties:%p)",
                      pPropertyCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    size_t count = 0;
    size_t* countPtr = &count;
    {
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                    count_VkLayerProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkLayerProperties*)(pProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkEnumerateInstanceLayerProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkEnumerateInstanceLayerProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkEnumerateInstanceLayerProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEnumerateInstanceLayerProperties = OP_vkEnumerateInstanceLayerProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkEnumerateInstanceLayerProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEnumerateInstanceLayerProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_0 = (uint64_t)(uintptr_t)pPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_0, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
            reservedmarshal_VkLayerProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkLayerProperties*)(pProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkEnumerateInstanceLayerProperties), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPropertyCount;
    check_pPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPropertyCount) {
        if (!(check_pPropertyCount)) {
            fprintf(stderr, "fatal: pPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkLayerProperties* check_pProperties;
    check_pProperties = (VkLayerProperties*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                unmarshal_VkLayerProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkLayerProperties*)(pProperties + i));
            }
        }
    }
    if (pPropertyCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                transform_fromhost_VkLayerProperties(sResourceTracker,
                                                     (VkLayerProperties*)(pProperties + i));
            }
        }
    }
    VkResult vkEnumerateInstanceLayerProperties_VkResult_return = (VkResult)0;
    stream->read(&vkEnumerateInstanceLayerProperties_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEnumerateInstanceLayerProperties_VkResult_return;
}

VkResult VkEncoder::vkEnumerateDeviceLayerProperties(VkPhysicalDevice physicalDevice,
                                                     uint32_t* pPropertyCount,
                                                     VkLayerProperties* pProperties,
                                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEnumerateDeviceLayerProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkEnumerateDeviceLayerProperties(physicalDevice:%p, pPropertyCount:%p, pProperties:%p)",
        physicalDevice, pPropertyCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                    count_VkLayerProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkLayerProperties*)(pProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkEnumerateDeviceLayerProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkEnumerateDeviceLayerProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkEnumerateDeviceLayerProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEnumerateDeviceLayerProperties = OP_vkEnumerateDeviceLayerProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkEnumerateDeviceLayerProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEnumerateDeviceLayerProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
            reservedmarshal_VkLayerProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkLayerProperties*)(pProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkEnumerateDeviceLayerProperties), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPropertyCount;
    check_pPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPropertyCount) {
        if (!(check_pPropertyCount)) {
            fprintf(stderr, "fatal: pPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkLayerProperties* check_pProperties;
    check_pProperties = (VkLayerProperties*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                unmarshal_VkLayerProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkLayerProperties*)(pProperties + i));
            }
        }
    }
    if (pPropertyCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                transform_fromhost_VkLayerProperties(sResourceTracker,
                                                     (VkLayerProperties*)(pProperties + i));
            }
        }
    }
    VkResult vkEnumerateDeviceLayerProperties_VkResult_return = (VkResult)0;
    stream->read(&vkEnumerateDeviceLayerProperties_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEnumerateDeviceLayerProperties_VkResult_return;
}

void VkEncoder::vkGetDeviceQueue(VkDevice device, uint32_t queueFamilyIndex, uint32_t queueIndex,
                                 VkQueue* pQueue, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceQueue in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDeviceQueue(device:%p, queueFamilyIndex:%d, queueIndex:%d, pQueue:%p)",
                      device, queueFamilyIndex, queueIndex, pQueue);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_queueFamilyIndex;
    uint32_t local_queueIndex;
    local_device = device;
    local_queueFamilyIndex = queueFamilyIndex;
    local_queueIndex = queueIndex;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkGetDeviceQueue = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetDeviceQueue);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceQueue);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceQueue = OP_vkGetDeviceQueue;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceQueue, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceQueue, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_queueFamilyIndex, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_queueIndex, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    /* is handle, possibly out */;
    uint64_t cgen_var_1;
    *&cgen_var_1 = (uint64_t)((*pQueue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetDeviceQueue), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_2;
    stream->read((uint64_t*)&cgen_var_2, 8);
    stream->handleMapping()->mapHandles_u64_VkQueue(&cgen_var_2, (VkQueue*)pQueue, 1);
    stream->unsetHandleMapping();
    sResourceTracker->on_vkGetDeviceQueue(this, device, queueFamilyIndex, queueIndex, pQueue);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkQueueSubmit(VkQueue queue, uint32_t submitCount, const VkSubmitInfo* pSubmits,
                                  VkFence fence, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueSubmit in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueSubmit(queue:%p, submitCount:%d, pSubmits:%p, fence:%p)", queue,
                      submitCount, pSubmits, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_submitCount;
    VkSubmitInfo* local_pSubmits;
    VkFence local_fence;
    local_queue = queue;
    local_submitCount = submitCount;
    local_pSubmits = nullptr;
    if (pSubmits) {
        local_pSubmits = (VkSubmitInfo*)pool->alloc(((submitCount)) * sizeof(const VkSubmitInfo));
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            deepcopy_VkSubmitInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubmits + i,
                                  (VkSubmitInfo*)(local_pSubmits + i));
        }
    }
    local_fence = fence;
    if (local_pSubmits) {
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            transform_tohost_VkSubmitInfo(sResourceTracker, (VkSubmitInfo*)(local_pSubmits + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            count_VkSubmitInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkSubmitInfo*)(local_pSubmits + i), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueSubmit = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueSubmit);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueSubmit);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueSubmit = OP_vkQueueSubmit;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueSubmit, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueSubmit, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_submitCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
        reservedmarshal_VkSubmitInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkSubmitInfo*)(local_pSubmits + i), streamPtrPtr);
    }
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkQueueSubmit), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkQueueSubmit_VkResult_return = (VkResult)0;
    stream->read(&vkQueueSubmit_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkQueueSubmit_VkResult_return;
}

VkResult VkEncoder::vkQueueWaitIdle(VkQueue queue, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueWaitIdle in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueWaitIdle(queue:%p)", queue);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    local_queue = queue;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueWaitIdle = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueWaitIdle);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueWaitIdle);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueWaitIdle = OP_vkQueueWaitIdle;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueWaitIdle, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueWaitIdle, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkQueueWaitIdle), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkQueueWaitIdle_VkResult_return = (VkResult)0;
    stream->read(&vkQueueWaitIdle_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkQueueWaitIdle_VkResult_return;
}

VkResult VkEncoder::vkDeviceWaitIdle(VkDevice device, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDeviceWaitIdle in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDeviceWaitIdle(device:%p)", device);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    local_device = device;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkDeviceWaitIdle = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDeviceWaitIdle);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDeviceWaitIdle);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDeviceWaitIdle = OP_vkDeviceWaitIdle;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDeviceWaitIdle, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDeviceWaitIdle, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDeviceWaitIdle), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkDeviceWaitIdle_VkResult_return = (VkResult)0;
    stream->read(&vkDeviceWaitIdle_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkDeviceWaitIdle_VkResult_return;
}

VkResult VkEncoder::vkAllocateMemory(VkDevice device, const VkMemoryAllocateInfo* pAllocateInfo,
                                     const VkAllocationCallbacks* pAllocator,
                                     VkDeviceMemory* pMemory, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkAllocateMemory in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkAllocateMemory(device:%p, pAllocateInfo:%p, pAllocator:%p, pMemory:%p)",
                      device, pAllocateInfo, pAllocator, pMemory);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkMemoryAllocateInfo* local_pAllocateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pAllocateInfo = nullptr;
    if (pAllocateInfo) {
        local_pAllocateInfo =
            (VkMemoryAllocateInfo*)pool->alloc(sizeof(const VkMemoryAllocateInfo));
        deepcopy_VkMemoryAllocateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocateInfo,
                                      (VkMemoryAllocateInfo*)(local_pAllocateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocateInfo) {
        transform_tohost_VkMemoryAllocateInfo(sResourceTracker,
                                              (VkMemoryAllocateInfo*)(local_pAllocateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkMemoryAllocateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryAllocateInfo*)(local_pAllocateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkAllocateMemory = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkAllocateMemory);
    uint8_t* streamPtr = stream->reserve(packetSize_vkAllocateMemory);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkAllocateMemory = OP_vkAllocateMemory;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkAllocateMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkAllocateMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkMemoryAllocateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkMemoryAllocateInfo*)(local_pAllocateInfo),
                                         streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pMemory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkAllocateMemory), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkDeviceMemory(&cgen_var_3, (VkDeviceMemory*)pMemory,
                                                           1);
    stream->unsetHandleMapping();
    VkResult vkAllocateMemory_VkResult_return = (VkResult)0;
    stream->read(&vkAllocateMemory_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkAllocateMemory_VkResult_return;
}

void VkEncoder::vkFreeMemory(VkDevice device, VkDeviceMemory memory,
                             const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkFreeMemory in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkFreeMemory(device:%p, memory:%p, pAllocator:%p)", device, memory,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemory local_memory;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_memory = memory;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)nullptr, 0, (VkDeviceSize*)nullptr, 0,
        (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkFreeMemory = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkFreeMemory);
    uint8_t* streamPtr = stream->reserve(packetSize_vkFreeMemory);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkFreeMemory = OP_vkFreeMemory;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkFreeMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkFreeMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkFreeMemory), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkDeviceMemory((VkDeviceMemory*)&memory);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkMapMemory(VkDevice device, VkDeviceMemory memory, VkDeviceSize offset,
                                VkDeviceSize size, VkMemoryMapFlags flags, void** ppData,
                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkMapMemory in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    VkResult vkMapMemory_VkResult_return = (VkResult)0;
    vkMapMemory_VkResult_return = sResourceTracker->on_vkMapMemory(this, VK_SUCCESS, device, memory,
                                                                   offset, size, flags, ppData);
    return vkMapMemory_VkResult_return;
}

void VkEncoder::vkUnmapMemory(VkDevice device, VkDeviceMemory memory, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkUnmapMemory in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    sResourceTracker->on_vkUnmapMemory(this, device, memory);
}

VkResult VkEncoder::vkFlushMappedMemoryRanges(VkDevice device, uint32_t memoryRangeCount,
                                              const VkMappedMemoryRange* pMemoryRanges,
                                              uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkFlushMappedMemoryRanges in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    VALIDATE_RET(VkResult, VK_SUCCESS,
                 mImpl->validation()->on_vkFlushMappedMemoryRanges(
                     this, VK_SUCCESS, device, memoryRangeCount, pMemoryRanges));
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_memoryRangeCount;
    VkMappedMemoryRange* local_pMemoryRanges;
    local_device = device;
    local_memoryRangeCount = memoryRangeCount;
    local_pMemoryRanges = nullptr;
    if (pMemoryRanges) {
        local_pMemoryRanges = (VkMappedMemoryRange*)pool->alloc(((memoryRangeCount)) *
                                                                sizeof(const VkMappedMemoryRange));
        for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
            deepcopy_VkMappedMemoryRange(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pMemoryRanges + i,
                                         (VkMappedMemoryRange*)(local_pMemoryRanges + i));
        }
    }
    if (local_pMemoryRanges) {
        for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
            transform_tohost_VkMappedMemoryRange(sResourceTracker,
                                                 (VkMappedMemoryRange*)(local_pMemoryRanges + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
            count_VkMappedMemoryRange(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkMappedMemoryRange*)(local_pMemoryRanges + i), countPtr);
        }
    }
    uint32_t packetSize_vkFlushMappedMemoryRanges =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkFlushMappedMemoryRanges);
    uint8_t* streamPtr = stream->reserve(packetSize_vkFlushMappedMemoryRanges);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkFlushMappedMemoryRanges = OP_vkFlushMappedMemoryRanges;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkFlushMappedMemoryRanges, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkFlushMappedMemoryRanges, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_memoryRangeCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
        reservedmarshal_VkMappedMemoryRange(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkMappedMemoryRange*)(local_pMemoryRanges + i),
                                            streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkFlushMappedMemoryRanges), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    if (!sResourceTracker->usingDirectMapping()) {
        for (uint32_t i = 0; i < memoryRangeCount; ++i) {
            auto range = pMemoryRanges[i];
            auto memory = pMemoryRanges[i].memory;
            auto size = pMemoryRanges[i].size;
            auto offset = pMemoryRanges[i].offset;
            uint64_t streamSize = 0;
            if (!memory) {
                stream->write(&streamSize, sizeof(uint64_t));
                continue;
            };
            auto hostPtr = sResourceTracker->getMappedPointer(memory);
            auto actualSize =
                size == VK_WHOLE_SIZE ? sResourceTracker->getMappedSize(memory) : size;
            if (!hostPtr) {
                stream->write(&streamSize, sizeof(uint64_t));
                continue;
            };
            streamSize = actualSize;
            stream->write(&streamSize, sizeof(uint64_t));
            uint8_t* targetRange = hostPtr + offset;
            stream->write(targetRange, actualSize);
        }
    }
    VkResult vkFlushMappedMemoryRanges_VkResult_return = (VkResult)0;
    stream->read(&vkFlushMappedMemoryRanges_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkFlushMappedMemoryRanges_VkResult_return;
}

VkResult VkEncoder::vkInvalidateMappedMemoryRanges(VkDevice device, uint32_t memoryRangeCount,
                                                   const VkMappedMemoryRange* pMemoryRanges,
                                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkInvalidateMappedMemoryRanges in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    VALIDATE_RET(VkResult, VK_SUCCESS,
                 mImpl->validation()->on_vkInvalidateMappedMemoryRanges(
                     this, VK_SUCCESS, device, memoryRangeCount, pMemoryRanges));
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_memoryRangeCount;
    VkMappedMemoryRange* local_pMemoryRanges;
    local_device = device;
    local_memoryRangeCount = memoryRangeCount;
    local_pMemoryRanges = nullptr;
    if (pMemoryRanges) {
        local_pMemoryRanges = (VkMappedMemoryRange*)pool->alloc(((memoryRangeCount)) *
                                                                sizeof(const VkMappedMemoryRange));
        for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
            deepcopy_VkMappedMemoryRange(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pMemoryRanges + i,
                                         (VkMappedMemoryRange*)(local_pMemoryRanges + i));
        }
    }
    if (local_pMemoryRanges) {
        for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
            transform_tohost_VkMappedMemoryRange(sResourceTracker,
                                                 (VkMappedMemoryRange*)(local_pMemoryRanges + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
            count_VkMappedMemoryRange(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkMappedMemoryRange*)(local_pMemoryRanges + i), countPtr);
        }
    }
    uint32_t packetSize_vkInvalidateMappedMemoryRanges =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkInvalidateMappedMemoryRanges);
    uint8_t* streamPtr = stream->reserve(packetSize_vkInvalidateMappedMemoryRanges);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkInvalidateMappedMemoryRanges = OP_vkInvalidateMappedMemoryRanges;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkInvalidateMappedMemoryRanges, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkInvalidateMappedMemoryRanges, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_memoryRangeCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((memoryRangeCount)); ++i) {
        reservedmarshal_VkMappedMemoryRange(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkMappedMemoryRange*)(local_pMemoryRanges + i),
                                            streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkInvalidateMappedMemoryRanges), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkInvalidateMappedMemoryRanges_VkResult_return = (VkResult)0;
    stream->read(&vkInvalidateMappedMemoryRanges_VkResult_return, sizeof(VkResult));
    if (!sResourceTracker->usingDirectMapping()) {
        for (uint32_t i = 0; i < memoryRangeCount; ++i) {
            auto range = pMemoryRanges[i];
            auto memory = pMemoryRanges[i].memory;
            auto size = pMemoryRanges[i].size;
            auto offset = pMemoryRanges[i].offset;
            uint64_t streamSize = 0;
            if (!memory) {
                stream->read(&streamSize, sizeof(uint64_t));
                continue;
            };
            auto hostPtr = sResourceTracker->getMappedPointer(memory);
            auto actualSize =
                size == VK_WHOLE_SIZE ? sResourceTracker->getMappedSize(memory) : size;
            if (!hostPtr) {
                stream->read(&streamSize, sizeof(uint64_t));
                continue;
            };
            streamSize = actualSize;
            stream->read(&streamSize, sizeof(uint64_t));
            uint8_t* targetRange = hostPtr + offset;
            stream->read(targetRange, actualSize);
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkInvalidateMappedMemoryRanges_VkResult_return;
}

void VkEncoder::vkGetDeviceMemoryCommitment(VkDevice device, VkDeviceMemory memory,
                                            VkDeviceSize* pCommittedMemoryInBytes,
                                            uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceMemoryCommitment in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceMemoryCommitment(device:%p, memory:%p, pCommittedMemoryInBytes:%p)", device,
        memory, pCommittedMemoryInBytes);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemory local_memory;
    local_device = device;
    local_memory = memory;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)nullptr, 0, (VkDeviceSize*)nullptr, 0,
        (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkGetDeviceMemoryCommitment =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetDeviceMemoryCommitment);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceMemoryCommitment);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceMemoryCommitment = OP_vkGetDeviceMemoryCommitment;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceMemoryCommitment, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceMemoryCommitment, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)pCommittedMemoryInBytes, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDeviceMemoryCommitment), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((VkDeviceSize*)pCommittedMemoryInBytes, sizeof(VkDeviceSize));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkBindBufferMemory(VkDevice device, VkBuffer buffer, VkDeviceMemory memory,
                                       VkDeviceSize memoryOffset, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBindBufferMemory in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkBindBufferMemory(device:%p, buffer:%p, memory:%p, memoryOffset:%ld)",
                      device, buffer, memory, memoryOffset);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBuffer local_buffer;
    VkDeviceMemory local_memory;
    VkDeviceSize local_memoryOffset;
    local_device = device;
    local_buffer = buffer;
    local_memory = memory;
    local_memoryOffset = memoryOffset;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)&local_memoryOffset, 1,
        (VkDeviceSize*)nullptr, 0, (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkBindBufferMemory =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkBindBufferMemory);
    uint8_t* streamPtr = stream->reserve(packetSize_vkBindBufferMemory);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBindBufferMemory = OP_vkBindBufferMemory;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkBindBufferMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBindBufferMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_memoryOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkBindBufferMemory), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkBindBufferMemory_VkResult_return = (VkResult)0;
    stream->read(&vkBindBufferMemory_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkBindBufferMemory_VkResult_return;
}

VkResult VkEncoder::vkBindImageMemory(VkDevice device, VkImage image, VkDeviceMemory memory,
                                      VkDeviceSize memoryOffset, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBindImageMemory in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkBindImageMemory(device:%p, image:%p, memory:%p, memoryOffset:%ld)", device,
                      image, memory, memoryOffset);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    VkDeviceMemory local_memory;
    VkDeviceSize local_memoryOffset;
    local_device = device;
    local_image = image;
    local_memory = memory;
    local_memoryOffset = memoryOffset;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)&local_memoryOffset, 1,
        (VkDeviceSize*)nullptr, 0, (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkBindImageMemory =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkBindImageMemory);
    uint8_t* streamPtr = stream->reserve(packetSize_vkBindImageMemory);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBindImageMemory = OP_vkBindImageMemory;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkBindImageMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBindImageMemory, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_memoryOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkBindImageMemory), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkBindImageMemory_VkResult_return = (VkResult)0;
    stream->read(&vkBindImageMemory_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkBindImageMemory_VkResult_return;
}

void VkEncoder::vkGetBufferMemoryRequirements(VkDevice device, VkBuffer buffer,
                                              VkMemoryRequirements* pMemoryRequirements,
                                              uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBufferMemoryRequirements in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetBufferMemoryRequirements(device:%p, buffer:%p, pMemoryRequirements:%p)",
                      device, buffer, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBuffer local_buffer;
    local_device = device;
    local_buffer = buffer;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetBufferMemoryRequirements =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetBufferMemoryRequirements);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBufferMemoryRequirements);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBufferMemoryRequirements = OP_vkGetBufferMemoryRequirements;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBufferMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBufferMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkMemoryRequirements*)(pMemoryRequirements),
                                         streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetBufferMemoryRequirements), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements(sResourceTracker,
                                                (VkMemoryRequirements*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetImageMemoryRequirements(VkDevice device, VkImage image,
                                             VkMemoryRequirements* pMemoryRequirements,
                                             uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageMemoryRequirements in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetImageMemoryRequirements(device:%p, image:%p, pMemoryRequirements:%p)",
                      device, image, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    local_device = device;
    local_image = image;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetImageMemoryRequirements =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageMemoryRequirements);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageMemoryRequirements);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageMemoryRequirements = OP_vkGetImageMemoryRequirements;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkMemoryRequirements*)(pMemoryRequirements),
                                         streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetImageMemoryRequirements), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements(sResourceTracker,
                                                (VkMemoryRequirements*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetImageSparseMemoryRequirements(
    VkDevice device, VkImage image, uint32_t* pSparseMemoryRequirementCount,
    VkSparseImageMemoryRequirements* pSparseMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageSparseMemoryRequirements in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetImageSparseMemoryRequirements(device:%p, image:%p, pSparseMemoryRequirementCount:%p, "
        "pSparseMemoryRequirements:%p)",
        device, image, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    local_device = device;
    local_image = image;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirementCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirements) {
            if (pSparseMemoryRequirementCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                    count_VkSparseImageMemoryRequirements(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageMemoryRequirements*)(pSparseMemoryRequirements + i),
                        countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetImageSparseMemoryRequirements =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageSparseMemoryRequirements);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageSparseMemoryRequirements);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageSparseMemoryRequirements = OP_vkGetImageSparseMemoryRequirements;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageSparseMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageSparseMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pSparseMemoryRequirementCount;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirementCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_3 = (uint64_t)(uintptr_t)pSparseMemoryRequirements;
    memcpy((*streamPtrPtr), &cgen_var_3, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirements) {
        for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
            reservedmarshal_VkSparseImageMemoryRequirements(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageMemoryRequirements*)(pSparseMemoryRequirements + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetImageSparseMemoryRequirements), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pSparseMemoryRequirementCount;
    check_pSparseMemoryRequirementCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirementCount) {
        if (!(check_pSparseMemoryRequirementCount)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirementCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageMemoryRequirements* check_pSparseMemoryRequirements;
    check_pSparseMemoryRequirements =
        (VkSparseImageMemoryRequirements*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirements) {
        if (!(check_pSparseMemoryRequirements)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirements inconsistent between guest and host\n");
        }
        if (pSparseMemoryRequirementCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                unmarshal_VkSparseImageMemoryRequirements(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageMemoryRequirements*)(pSparseMemoryRequirements + i));
            }
        }
    }
    if (pSparseMemoryRequirementCount) {
        if (pSparseMemoryRequirements) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                transform_fromhost_VkSparseImageMemoryRequirements(
                    sResourceTracker,
                    (VkSparseImageMemoryRequirements*)(pSparseMemoryRequirements + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceSparseImageFormatProperties(
    VkPhysicalDevice physicalDevice, VkFormat format, VkImageType type,
    VkSampleCountFlagBits samples, VkImageUsageFlags usage, VkImageTiling tiling,
    uint32_t* pPropertyCount, VkSparseImageFormatProperties* pProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceSparseImageFormatProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceSparseImageFormatProperties(physicalDevice:%p, format:%d, usage:%d, "
        "pPropertyCount:%p, pProperties:%p)",
        physicalDevice, format, usage, pPropertyCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkFormat local_format;
    VkImageType local_type;
    VkSampleCountFlagBits local_samples;
    VkImageUsageFlags local_usage;
    VkImageTiling local_tiling;
    local_physicalDevice = physicalDevice;
    local_format = format;
    local_type = type;
    local_samples = samples;
    local_usage = usage;
    local_tiling = tiling;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        *countPtr += sizeof(VkImageType);
        *countPtr += sizeof(VkSampleCountFlagBits);
        *countPtr += sizeof(VkImageUsageFlags);
        *countPtr += sizeof(VkImageTiling);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                    count_VkSparseImageFormatProperties(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageFormatProperties*)(pProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceSparseImageFormatProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceSparseImageFormatProperties =
        OP_vkGetPhysicalDeviceSparseImageFormatProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceSparseImageFormatProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceSparseImageFormatProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    memcpy(*streamPtrPtr, (VkImageType*)&local_type, sizeof(VkImageType));
    *streamPtrPtr += sizeof(VkImageType);
    memcpy(*streamPtrPtr, (VkSampleCountFlagBits*)&local_samples, sizeof(VkSampleCountFlagBits));
    *streamPtrPtr += sizeof(VkSampleCountFlagBits);
    memcpy(*streamPtrPtr, (VkImageUsageFlags*)&local_usage, sizeof(VkImageUsageFlags));
    *streamPtrPtr += sizeof(VkImageUsageFlags);
    memcpy(*streamPtrPtr, (VkImageTiling*)&local_tiling, sizeof(VkImageTiling));
    *streamPtrPtr += sizeof(VkImageTiling);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
            reservedmarshal_VkSparseImageFormatProperties(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageFormatProperties*)(pProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPropertyCount;
    check_pPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPropertyCount) {
        if (!(check_pPropertyCount)) {
            fprintf(stderr, "fatal: pPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageFormatProperties* check_pProperties;
    check_pProperties = (VkSparseImageFormatProperties*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                unmarshal_VkSparseImageFormatProperties(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageFormatProperties*)(pProperties + i));
            }
        }
    }
    if (pPropertyCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                transform_fromhost_VkSparseImageFormatProperties(
                    sResourceTracker, (VkSparseImageFormatProperties*)(pProperties + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkQueueBindSparse(VkQueue queue, uint32_t bindInfoCount,
                                      const VkBindSparseInfo* pBindInfo, VkFence fence,
                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueBindSparse in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueBindSparse(queue:%p, bindInfoCount:%d, pBindInfo:%p, fence:%p)",
                      queue, bindInfoCount, pBindInfo, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_bindInfoCount;
    VkBindSparseInfo* local_pBindInfo;
    VkFence local_fence;
    local_queue = queue;
    local_bindInfoCount = bindInfoCount;
    local_pBindInfo = nullptr;
    if (pBindInfo) {
        local_pBindInfo =
            (VkBindSparseInfo*)pool->alloc(((bindInfoCount)) * sizeof(const VkBindSparseInfo));
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            deepcopy_VkBindSparseInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBindInfo + i,
                                      (VkBindSparseInfo*)(local_pBindInfo + i));
        }
    }
    local_fence = fence;
    if (local_pBindInfo) {
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            transform_tohost_VkBindSparseInfo(sResourceTracker,
                                              (VkBindSparseInfo*)(local_pBindInfo + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            count_VkBindSparseInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkBindSparseInfo*)(local_pBindInfo + i), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueBindSparse =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueBindSparse);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueBindSparse);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueBindSparse = OP_vkQueueBindSparse;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueBindSparse, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueBindSparse, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
        reservedmarshal_VkBindSparseInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkBindSparseInfo*)(local_pBindInfo + i), streamPtrPtr);
    }
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkQueueBindSparse), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkQueueBindSparse_VkResult_return = (VkResult)0;
    stream->read(&vkQueueBindSparse_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkQueueBindSparse_VkResult_return;
}

VkResult VkEncoder::vkCreateFence(VkDevice device, const VkFenceCreateInfo* pCreateInfo,
                                  const VkAllocationCallbacks* pAllocator, VkFence* pFence,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateFence in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateFence(device:%p, pCreateInfo:%p, pAllocator:%p, pFence:%p)", device,
                      pCreateInfo, pAllocator, pFence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFenceCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkFenceCreateInfo*)pool->alloc(sizeof(const VkFenceCreateInfo));
        deepcopy_VkFenceCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                   (VkFenceCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkFenceCreateInfo(sResourceTracker,
                                           (VkFenceCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkFenceCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkFenceCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateFence = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateFence);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateFence);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateFence = OP_vkCreateFence;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateFence, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateFence, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkFenceCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkFenceCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pFence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateFence), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkFence(&cgen_var_3, (VkFence*)pFence, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateFence_VkResult_return = (VkResult)0;
    stream->read(&vkCreateFence_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateFence_VkResult_return;
}

void VkEncoder::vkDestroyFence(VkDevice device, VkFence fence,
                               const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyFence in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyFence(device:%p, fence:%p, pAllocator:%p)", device, fence,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFence local_fence;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_fence = fence;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyFence = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyFence);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyFence);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyFence = OP_vkDestroyFence;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyFence, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyFence, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyFence), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkFence((VkFence*)&fence);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkResetFences(VkDevice device, uint32_t fenceCount, const VkFence* pFences,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkResetFences in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkResetFences(device:%p, fenceCount:%d, pFences:%p)", device, fenceCount,
                      pFences);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_fenceCount;
    VkFence* local_pFences;
    local_device = device;
    local_fenceCount = fenceCount;
    // Avoiding deepcopy for pFences
    local_pFences = (VkFence*)pFences;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((fenceCount))) {
            *countPtr += ((fenceCount)) * 8;
        }
    }
    uint32_t packetSize_vkResetFences = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkResetFences);
    uint8_t* streamPtr = stream->reserve(packetSize_vkResetFences);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkResetFences = OP_vkResetFences;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkResetFences, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkResetFences, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_fenceCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((fenceCount))) {
        uint8_t* cgen_var_1_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((fenceCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkFence(local_pFences[k]);
            memcpy(cgen_var_1_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((fenceCount));
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkResetFences), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkResetFences_VkResult_return = (VkResult)0;
    stream->read(&vkResetFences_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkResetFences_VkResult_return;
}

VkResult VkEncoder::vkGetFenceStatus(VkDevice device, VkFence fence, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetFenceStatus in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetFenceStatus(device:%p, fence:%p)", device, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFence local_fence;
    local_device = device;
    local_fence = fence;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkGetFenceStatus = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetFenceStatus);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetFenceStatus);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetFenceStatus = OP_vkGetFenceStatus;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetFenceStatus, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetFenceStatus, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetFenceStatus), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkGetFenceStatus_VkResult_return = (VkResult)0;
    stream->read(&vkGetFenceStatus_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetFenceStatus_VkResult_return;
}

VkResult VkEncoder::vkWaitForFences(VkDevice device, uint32_t fenceCount, const VkFence* pFences,
                                    VkBool32 waitAll, uint64_t timeout, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkWaitForFences in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkWaitForFences(device:%p, fenceCount:%d, pFences:%p, waitAll:%d, timeout:%ld)", device,
        fenceCount, pFences, waitAll, timeout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_fenceCount;
    VkFence* local_pFences;
    VkBool32 local_waitAll;
    uint64_t local_timeout;
    local_device = device;
    local_fenceCount = fenceCount;
    // Avoiding deepcopy for pFences
    local_pFences = (VkFence*)pFences;
    local_waitAll = waitAll;
    local_timeout = timeout;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((fenceCount))) {
            *countPtr += ((fenceCount)) * 8;
        }
        *countPtr += sizeof(VkBool32);
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkWaitForFences = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkWaitForFences);
    uint8_t* streamPtr = stream->reserve(packetSize_vkWaitForFences);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkWaitForFences = OP_vkWaitForFences;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkWaitForFences, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkWaitForFences, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_fenceCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((fenceCount))) {
        uint8_t* cgen_var_1_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((fenceCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkFence(local_pFences[k]);
            memcpy(cgen_var_1_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((fenceCount));
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_waitAll, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    memcpy(*streamPtrPtr, (uint64_t*)&local_timeout, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkWaitForFences), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkWaitForFences_VkResult_return = (VkResult)0;
    stream->read(&vkWaitForFences_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkWaitForFences_VkResult_return;
}

VkResult VkEncoder::vkCreateSemaphore(VkDevice device, const VkSemaphoreCreateInfo* pCreateInfo,
                                      const VkAllocationCallbacks* pAllocator,
                                      VkSemaphore* pSemaphore, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateSemaphore in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateSemaphore(device:%p, pCreateInfo:%p, pAllocator:%p, pSemaphore:%p)",
                      device, pCreateInfo, pAllocator, pSemaphore);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSemaphoreCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkSemaphoreCreateInfo*)pool->alloc(sizeof(const VkSemaphoreCreateInfo));
        deepcopy_VkSemaphoreCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                       (VkSemaphoreCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkSemaphoreCreateInfo(sResourceTracker,
                                               (VkSemaphoreCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSemaphoreCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkSemaphoreCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateSemaphore =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateSemaphore);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateSemaphore);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateSemaphore = OP_vkCreateSemaphore;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateSemaphore, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateSemaphore, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkSemaphoreCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkSemaphoreCreateInfo*)(local_pCreateInfo),
                                          streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pSemaphore));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateSemaphore), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkSemaphore(&cgen_var_3, (VkSemaphore*)pSemaphore, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateSemaphore_VkResult_return = (VkResult)0;
    stream->read(&vkCreateSemaphore_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateSemaphore_VkResult_return;
}

void VkEncoder::vkDestroySemaphore(VkDevice device, VkSemaphore semaphore,
                                   const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroySemaphore in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroySemaphore(device:%p, semaphore:%p, pAllocator:%p)", device,
                      semaphore, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSemaphore local_semaphore;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_semaphore = semaphore;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroySemaphore =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroySemaphore);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroySemaphore);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroySemaphore = OP_vkDestroySemaphore;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroySemaphore, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroySemaphore, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkSemaphore((*&local_semaphore));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroySemaphore), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkSemaphore((VkSemaphore*)&semaphore);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateEvent(VkDevice device, const VkEventCreateInfo* pCreateInfo,
                                  const VkAllocationCallbacks* pAllocator, VkEvent* pEvent,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateEvent in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateEvent(device:%p, pCreateInfo:%p, pAllocator:%p, pEvent:%p)", device,
                      pCreateInfo, pAllocator, pEvent);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkEventCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkEventCreateInfo*)pool->alloc(sizeof(const VkEventCreateInfo));
        deepcopy_VkEventCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                   (VkEventCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkEventCreateInfo(sResourceTracker,
                                           (VkEventCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkEventCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkEventCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateEvent = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateEvent);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateEvent);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateEvent = OP_vkCreateEvent;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkEventCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkEventCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pEvent));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateEvent), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkEvent(&cgen_var_3, (VkEvent*)pEvent, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateEvent_VkResult_return = (VkResult)0;
    stream->read(&vkCreateEvent_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateEvent_VkResult_return;
}

void VkEncoder::vkDestroyEvent(VkDevice device, VkEvent event,
                               const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyEvent in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyEvent(device:%p, event:%p, pAllocator:%p)", device, event,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkEvent local_event;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_event = event;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyEvent = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyEvent);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyEvent);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyEvent = OP_vkDestroyEvent;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyEvent), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkEvent((VkEvent*)&event);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetEventStatus(VkDevice device, VkEvent event, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetEventStatus in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetEventStatus(device:%p, event:%p)", device, event);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkEvent local_event;
    local_device = device;
    local_event = event;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkGetEventStatus = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetEventStatus);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetEventStatus);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetEventStatus = OP_vkGetEventStatus;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetEventStatus, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetEventStatus, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetEventStatus), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkGetEventStatus_VkResult_return = (VkResult)0;
    stream->read(&vkGetEventStatus_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetEventStatus_VkResult_return;
}

VkResult VkEncoder::vkSetEvent(VkDevice device, VkEvent event, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkSetEvent in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkSetEvent(device:%p, event:%p)", device, event);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkEvent local_event;
    local_device = device;
    local_event = event;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkSetEvent = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkSetEvent);
    uint8_t* streamPtr = stream->reserve(packetSize_vkSetEvent);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkSetEvent = OP_vkSetEvent;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkSetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkSetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkSetEvent), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkSetEvent_VkResult_return = (VkResult)0;
    stream->read(&vkSetEvent_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkSetEvent_VkResult_return;
}

VkResult VkEncoder::vkResetEvent(VkDevice device, VkEvent event, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkResetEvent in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkResetEvent(device:%p, event:%p)", device, event);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkEvent local_event;
    local_device = device;
    local_event = event;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkResetEvent = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkResetEvent);
    uint8_t* streamPtr = stream->reserve(packetSize_vkResetEvent);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkResetEvent = OP_vkResetEvent;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkResetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkResetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkResetEvent), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkResetEvent_VkResult_return = (VkResult)0;
    stream->read(&vkResetEvent_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkResetEvent_VkResult_return;
}

VkResult VkEncoder::vkCreateQueryPool(VkDevice device, const VkQueryPoolCreateInfo* pCreateInfo,
                                      const VkAllocationCallbacks* pAllocator,
                                      VkQueryPool* pQueryPool, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateQueryPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateQueryPool(device:%p, pCreateInfo:%p, pAllocator:%p, pQueryPool:%p)",
                      device, pCreateInfo, pAllocator, pQueryPool);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkQueryPoolCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkQueryPoolCreateInfo*)pool->alloc(sizeof(const VkQueryPoolCreateInfo));
        deepcopy_VkQueryPoolCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                       (VkQueryPoolCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkQueryPoolCreateInfo(sResourceTracker,
                                               (VkQueryPoolCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkQueryPoolCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkQueryPoolCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateQueryPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateQueryPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateQueryPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateQueryPool = OP_vkCreateQueryPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkQueryPoolCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkQueryPoolCreateInfo*)(local_pCreateInfo),
                                          streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pQueryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateQueryPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkQueryPool(&cgen_var_3, (VkQueryPool*)pQueryPool, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateQueryPool_VkResult_return = (VkResult)0;
    stream->read(&vkCreateQueryPool_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateQueryPool_VkResult_return;
}

void VkEncoder::vkDestroyQueryPool(VkDevice device, VkQueryPool queryPool,
                                   const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyQueryPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyQueryPool(device:%p, queryPool:%p, pAllocator:%p)", device,
                      queryPool, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkQueryPool local_queryPool;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_queryPool = queryPool;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyQueryPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyQueryPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyQueryPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyQueryPool = OP_vkDestroyQueryPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyQueryPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkQueryPool((VkQueryPool*)&queryPool);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetQueryPoolResults(VkDevice device, VkQueryPool queryPool,
                                          uint32_t firstQuery, uint32_t queryCount, size_t dataSize,
                                          void* pData, VkDeviceSize stride,
                                          VkQueryResultFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetQueryPoolResults in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetQueryPoolResults(device:%p, queryPool:%p, firstQuery:%d, queryCount:%d, "
        "dataSize:%ld, pData:%p, stride:%ld, flags:%d)",
        device, queryPool, firstQuery, queryCount, dataSize, pData, stride, flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkQueryPool local_queryPool;
    uint32_t local_firstQuery;
    uint32_t local_queryCount;
    size_t local_dataSize;
    VkDeviceSize local_stride;
    VkQueryResultFlags local_flags;
    local_device = device;
    local_queryPool = queryPool;
    local_firstQuery = firstQuery;
    local_queryCount = queryCount;
    local_dataSize = dataSize;
    local_stride = stride;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += 8;
        *countPtr += ((dataSize)) * sizeof(uint8_t);
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkQueryResultFlags);
    }
    uint32_t packetSize_vkGetQueryPoolResults =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetQueryPoolResults);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetQueryPoolResults);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetQueryPoolResults = OP_vkGetQueryPoolResults;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetQueryPoolResults, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetQueryPoolResults, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstQuery, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_queryCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    uint64_t cgen_var_2 = (uint64_t)local_dataSize;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    memcpy(*streamPtrPtr, (void*)pData, ((dataSize)) * sizeof(uint8_t));
    *streamPtrPtr += ((dataSize)) * sizeof(uint8_t);
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_stride, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkQueryResultFlags*)&local_flags, sizeof(VkQueryResultFlags));
    *streamPtrPtr += sizeof(VkQueryResultFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetQueryPoolResults), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((void*)pData, ((dataSize)) * sizeof(uint8_t));
    VkResult vkGetQueryPoolResults_VkResult_return = (VkResult)0;
    stream->read(&vkGetQueryPoolResults_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetQueryPoolResults_VkResult_return;
}

VkResult VkEncoder::vkCreateBuffer(VkDevice device, const VkBufferCreateInfo* pCreateInfo,
                                   const VkAllocationCallbacks* pAllocator, VkBuffer* pBuffer,
                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateBuffer(device:%p, pCreateInfo:%p, pAllocator:%p, pBuffer:%p)",
                      device, pCreateInfo, pAllocator, pBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkBufferCreateInfo*)pool->alloc(sizeof(const VkBufferCreateInfo));
        deepcopy_VkBufferCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                    (VkBufferCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkBufferCreateInfo(sResourceTracker,
                                            (VkBufferCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkBufferCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateBuffer = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateBuffer);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateBuffer = OP_vkCreateBuffer;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkBufferCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkBuffer(&cgen_var_3, (VkBuffer*)pBuffer, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateBuffer_VkResult_return = (VkResult)0;
    stream->read(&vkCreateBuffer_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateBuffer_VkResult_return;
}

void VkEncoder::vkDestroyBuffer(VkDevice device, VkBuffer buffer,
                                const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyBuffer(device:%p, buffer:%p, pAllocator:%p)", device, buffer,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBuffer local_buffer;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_buffer = buffer;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyBuffer = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyBuffer);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyBuffer = OP_vkDestroyBuffer;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkBuffer((VkBuffer*)&buffer);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateBufferView(VkDevice device, const VkBufferViewCreateInfo* pCreateInfo,
                                       const VkAllocationCallbacks* pAllocator, VkBufferView* pView,
                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateBufferView in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateBufferView(device:%p, pCreateInfo:%p, pAllocator:%p, pView:%p)",
                      device, pCreateInfo, pAllocator, pView);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferViewCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkBufferViewCreateInfo*)pool->alloc(sizeof(const VkBufferViewCreateInfo));
        deepcopy_VkBufferViewCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                        (VkBufferViewCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkBufferViewCreateInfo(sResourceTracker,
                                                (VkBufferViewCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferViewCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkBufferViewCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateBufferView =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateBufferView);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateBufferView);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateBufferView = OP_vkCreateBufferView;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateBufferView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateBufferView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferViewCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkBufferViewCreateInfo*)(local_pCreateInfo),
                                           streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pView));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateBufferView), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkBufferView(&cgen_var_3, (VkBufferView*)pView, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateBufferView_VkResult_return = (VkResult)0;
    stream->read(&vkCreateBufferView_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateBufferView_VkResult_return;
}

void VkEncoder::vkDestroyBufferView(VkDevice device, VkBufferView bufferView,
                                    const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyBufferView in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyBufferView(device:%p, bufferView:%p, pAllocator:%p)", device,
                      bufferView, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferView local_bufferView;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_bufferView = bufferView;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyBufferView =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyBufferView);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyBufferView);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyBufferView = OP_vkDestroyBufferView;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyBufferView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyBufferView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBufferView((*&local_bufferView));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyBufferView), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkBufferView((VkBufferView*)&bufferView);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateImage(VkDevice device, const VkImageCreateInfo* pCreateInfo,
                                  const VkAllocationCallbacks* pAllocator, VkImage* pImage,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkImageCreateInfo*)pool->alloc(sizeof(const VkImageCreateInfo));
        deepcopy_VkImageCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                   (VkImageCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    sResourceTracker->unwrap_vkCreateImage_pCreateInfo(pCreateInfo, local_pCreateInfo);
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        sResourceTracker->transformImpl_VkImageCreateInfo_tohost(local_pCreateInfo, 1);
        transform_tohost_VkImageCreateInfo(sResourceTracker,
                                           (VkImageCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkImageCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateImage = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateImage);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateImage = OP_vkCreateImage;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkImageCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkImage(&cgen_var_3, (VkImage*)pImage, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateImage_VkResult_return = (VkResult)0;
    stream->read(&vkCreateImage_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateImage_VkResult_return;
}

void VkEncoder::vkDestroyImage(VkDevice device, VkImage image,
                               const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyImage(device:%p, image:%p, pAllocator:%p)", device, image,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_image = image;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyImage = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyImage);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyImage = OP_vkDestroyImage;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkImage((VkImage*)&image);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetImageSubresourceLayout(VkDevice device, VkImage image,
                                            const VkImageSubresource* pSubresource,
                                            VkSubresourceLayout* pLayout, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageSubresourceLayout in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetImageSubresourceLayout(device:%p, image:%p, pSubresource:%p, pLayout:%p)", device,
        image, pSubresource, pLayout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    VkImageSubresource* local_pSubresource;
    local_device = device;
    local_image = image;
    local_pSubresource = nullptr;
    if (pSubresource) {
        local_pSubresource = (VkImageSubresource*)pool->alloc(sizeof(const VkImageSubresource));
        deepcopy_VkImageSubresource(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubresource,
                                    (VkImageSubresource*)(local_pSubresource));
    }
    if (local_pSubresource) {
        transform_tohost_VkImageSubresource(sResourceTracker,
                                            (VkImageSubresource*)(local_pSubresource));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkImageSubresource(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkImageSubresource*)(local_pSubresource), countPtr);
        count_VkSubresourceLayout(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkSubresourceLayout*)(pLayout), countPtr);
    }
    uint32_t packetSize_vkGetImageSubresourceLayout =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetImageSubresourceLayout);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageSubresourceLayout);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageSubresourceLayout = OP_vkGetImageSubresourceLayout;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageSubresourceLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageSubresourceLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageSubresource(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageSubresource*)(local_pSubresource), streamPtrPtr);
    reservedmarshal_VkSubresourceLayout(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkSubresourceLayout*)(pLayout), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetImageSubresourceLayout), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkSubresourceLayout(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkSubresourceLayout*)(pLayout));
    if (pLayout) {
        transform_fromhost_VkSubresourceLayout(sResourceTracker, (VkSubresourceLayout*)(pLayout));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateImageView(VkDevice device, const VkImageViewCreateInfo* pCreateInfo,
                                      const VkAllocationCallbacks* pAllocator, VkImageView* pView,
                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateImageView in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateImageView(device:%p, pCreateInfo:%p, pAllocator:%p, pView:%p)",
                      device, pCreateInfo, pAllocator, pView);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageViewCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkImageViewCreateInfo*)pool->alloc(sizeof(const VkImageViewCreateInfo));
        deepcopy_VkImageViewCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                       (VkImageViewCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkImageViewCreateInfo(sResourceTracker,
                                               (VkImageViewCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageViewCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkImageViewCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateImageView =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateImageView);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateImageView);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateImageView = OP_vkCreateImageView;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateImageView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateImageView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageViewCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkImageViewCreateInfo*)(local_pCreateInfo),
                                          streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pView));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateImageView), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkImageView(&cgen_var_3, (VkImageView*)pView, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateImageView_VkResult_return = (VkResult)0;
    stream->read(&vkCreateImageView_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateImageView_VkResult_return;
}

void VkEncoder::vkDestroyImageView(VkDevice device, VkImageView imageView,
                                   const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyImageView in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyImageView(device:%p, imageView:%p, pAllocator:%p)", device,
                      imageView, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageView local_imageView;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_imageView = imageView;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyImageView =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyImageView);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyImageView);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyImageView = OP_vkDestroyImageView;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyImageView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyImageView, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImageView((*&local_imageView));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyImageView), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkImageView((VkImageView*)&imageView);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateShaderModule(VkDevice device,
                                         const VkShaderModuleCreateInfo* pCreateInfo,
                                         const VkAllocationCallbacks* pAllocator,
                                         VkShaderModule* pShaderModule, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateShaderModule in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateShaderModule(device:%p, pCreateInfo:%p, pAllocator:%p, pShaderModule:%p)", device,
        pCreateInfo, pAllocator, pShaderModule);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkShaderModuleCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkShaderModuleCreateInfo*)pool->alloc(sizeof(const VkShaderModuleCreateInfo));
        deepcopy_VkShaderModuleCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                          (VkShaderModuleCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkShaderModuleCreateInfo(sResourceTracker,
                                                  (VkShaderModuleCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkShaderModuleCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkShaderModuleCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateShaderModule =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateShaderModule);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateShaderModule);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateShaderModule = OP_vkCreateShaderModule;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateShaderModule, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateShaderModule, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkShaderModuleCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkShaderModuleCreateInfo*)(local_pCreateInfo),
                                             streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pShaderModule));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateShaderModule), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkShaderModule(&cgen_var_3,
                                                           (VkShaderModule*)pShaderModule, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateShaderModule_VkResult_return = (VkResult)0;
    stream->read(&vkCreateShaderModule_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateShaderModule_VkResult_return;
}

void VkEncoder::vkDestroyShaderModule(VkDevice device, VkShaderModule shaderModule,
                                      const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyShaderModule in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyShaderModule(device:%p, shaderModule:%p, pAllocator:%p)", device,
                      shaderModule, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkShaderModule local_shaderModule;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_shaderModule = shaderModule;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyShaderModule =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyShaderModule);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyShaderModule);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyShaderModule = OP_vkDestroyShaderModule;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyShaderModule, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyShaderModule, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkShaderModule((*&local_shaderModule));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyShaderModule), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkShaderModule((VkShaderModule*)&shaderModule);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreatePipelineCache(VkDevice device,
                                          const VkPipelineCacheCreateInfo* pCreateInfo,
                                          const VkAllocationCallbacks* pAllocator,
                                          VkPipelineCache* pPipelineCache, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreatePipelineCache in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreatePipelineCache(device:%p, pCreateInfo:%p, pAllocator:%p, pPipelineCache:%p)",
        device, pCreateInfo, pAllocator, pPipelineCache);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineCacheCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkPipelineCacheCreateInfo*)pool->alloc(sizeof(const VkPipelineCacheCreateInfo));
        deepcopy_VkPipelineCacheCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                           (VkPipelineCacheCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkPipelineCacheCreateInfo(sResourceTracker,
                                                   (VkPipelineCacheCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPipelineCacheCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkPipelineCacheCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreatePipelineCache =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreatePipelineCache);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreatePipelineCache);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreatePipelineCache = OP_vkCreatePipelineCache;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreatePipelineCache, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreatePipelineCache, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPipelineCacheCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkPipelineCacheCreateInfo*)(local_pCreateInfo),
                                              streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pPipelineCache));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreatePipelineCache), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkPipelineCache(&cgen_var_3,
                                                            (VkPipelineCache*)pPipelineCache, 1);
    stream->unsetHandleMapping();
    VkResult vkCreatePipelineCache_VkResult_return = (VkResult)0;
    stream->read(&vkCreatePipelineCache_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreatePipelineCache_VkResult_return;
}

void VkEncoder::vkDestroyPipelineCache(VkDevice device, VkPipelineCache pipelineCache,
                                       const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyPipelineCache in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyPipelineCache(device:%p, pipelineCache:%p, pAllocator:%p)", device,
                      pipelineCache, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineCache local_pipelineCache;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pipelineCache = pipelineCache;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyPipelineCache =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyPipelineCache);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyPipelineCache);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyPipelineCache = OP_vkDestroyPipelineCache;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyPipelineCache, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyPipelineCache, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkPipelineCache((*&local_pipelineCache));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyPipelineCache), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkPipelineCache(
        (VkPipelineCache*)&pipelineCache);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetPipelineCacheData(VkDevice device, VkPipelineCache pipelineCache,
                                           size_t* pDataSize, void* pData, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPipelineCacheData in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPipelineCacheData(device:%p, pipelineCache:%p, pDataSize:%p, pData:%p)",
                      device, pipelineCache, pDataSize, pData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineCache local_pipelineCache;
    local_device = device;
    local_pipelineCache = pipelineCache;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pDataSize) {
            *countPtr += 8;
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pData) {
            if (pDataSize) {
                *countPtr += (*(pDataSize)) * sizeof(uint8_t);
            }
        }
    }
    uint32_t packetSize_vkGetPipelineCacheData =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetPipelineCacheData);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPipelineCacheData);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPipelineCacheData = OP_vkGetPipelineCacheData;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPipelineCacheData, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPipelineCacheData, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkPipelineCache((*&local_pipelineCache));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pDataSize;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pDataSize) {
        uint64_t cgen_var_2_0 = (uint64_t)(*pDataSize);
        memcpy((*streamPtrPtr), &cgen_var_2_0, 8);
        gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
        *streamPtrPtr += 8;
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_3 = (uint64_t)(uintptr_t)pData;
    memcpy((*streamPtrPtr), &cgen_var_3, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pData) {
        memcpy(*streamPtrPtr, (void*)pData, (*(pDataSize)) * sizeof(uint8_t));
        *streamPtrPtr += (*(pDataSize)) * sizeof(uint8_t);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPipelineCacheData), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    size_t* check_pDataSize;
    check_pDataSize = (size_t*)(uintptr_t)stream->getBe64();
    if (pDataSize) {
        if (!(check_pDataSize)) {
            fprintf(stderr, "fatal: pDataSize inconsistent between guest and host\n");
        }
        (*pDataSize) = (size_t)stream->getBe64();
    }
    // WARNING PTR CHECK
    void* check_pData;
    check_pData = (void*)(uintptr_t)stream->getBe64();
    if (pData) {
        if (!(check_pData)) {
            fprintf(stderr, "fatal: pData inconsistent between guest and host\n");
        }
        stream->read((void*)pData, (*(pDataSize)) * sizeof(uint8_t));
    }
    VkResult vkGetPipelineCacheData_VkResult_return = (VkResult)0;
    stream->read(&vkGetPipelineCacheData_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPipelineCacheData_VkResult_return;
}

VkResult VkEncoder::vkMergePipelineCaches(VkDevice device, VkPipelineCache dstCache,
                                          uint32_t srcCacheCount, const VkPipelineCache* pSrcCaches,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkMergePipelineCaches in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkMergePipelineCaches(device:%p, dstCache:%p, srcCacheCount:%d, pSrcCaches:%p)", device,
        dstCache, srcCacheCount, pSrcCaches);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineCache local_dstCache;
    uint32_t local_srcCacheCount;
    VkPipelineCache* local_pSrcCaches;
    local_device = device;
    local_dstCache = dstCache;
    local_srcCacheCount = srcCacheCount;
    // Avoiding deepcopy for pSrcCaches
    local_pSrcCaches = (VkPipelineCache*)pSrcCaches;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((srcCacheCount))) {
            *countPtr += ((srcCacheCount)) * 8;
        }
    }
    uint32_t packetSize_vkMergePipelineCaches =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkMergePipelineCaches);
    uint8_t* streamPtr = stream->reserve(packetSize_vkMergePipelineCaches);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkMergePipelineCaches = OP_vkMergePipelineCaches;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkMergePipelineCaches, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkMergePipelineCaches, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkPipelineCache((*&local_dstCache));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_srcCacheCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((srcCacheCount))) {
        uint8_t* cgen_var_2_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((srcCacheCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkPipelineCache(local_pSrcCaches[k]);
            memcpy(cgen_var_2_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((srcCacheCount));
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkMergePipelineCaches), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkMergePipelineCaches_VkResult_return = (VkResult)0;
    stream->read(&vkMergePipelineCaches_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkMergePipelineCaches_VkResult_return;
}

VkResult VkEncoder::vkCreateGraphicsPipelines(VkDevice device, VkPipelineCache pipelineCache,
                                              uint32_t createInfoCount,
                                              const VkGraphicsPipelineCreateInfo* pCreateInfos,
                                              const VkAllocationCallbacks* pAllocator,
                                              VkPipeline* pPipelines, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateGraphicsPipelines in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateGraphicsPipelines(device:%p, pipelineCache:%p, createInfoCount:%d, "
        "pCreateInfos:%p, pAllocator:%p, pPipelines:%p)",
        device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineCache local_pipelineCache;
    uint32_t local_createInfoCount;
    VkGraphicsPipelineCreateInfo* local_pCreateInfos;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pipelineCache = pipelineCache;
    local_createInfoCount = createInfoCount;
    local_pCreateInfos = nullptr;
    if (pCreateInfos) {
        local_pCreateInfos = (VkGraphicsPipelineCreateInfo*)pool->alloc(
            ((createInfoCount)) * sizeof(const VkGraphicsPipelineCreateInfo));
        for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
            deepcopy_VkGraphicsPipelineCreateInfo(
                pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfos + i,
                (VkGraphicsPipelineCreateInfo*)(local_pCreateInfos + i));
        }
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfos) {
        for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
            transform_tohost_VkGraphicsPipelineCreateInfo(
                sResourceTracker, (VkGraphicsPipelineCreateInfo*)(local_pCreateInfos + i));
        }
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
            count_VkGraphicsPipelineCreateInfo(
                sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkGraphicsPipelineCreateInfo*)(local_pCreateInfos + i), countPtr);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        if (((createInfoCount))) {
            *countPtr += ((createInfoCount)) * 8;
        }
    }
    uint32_t packetSize_vkCreateGraphicsPipelines =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateGraphicsPipelines);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateGraphicsPipelines);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateGraphicsPipelines = OP_vkCreateGraphicsPipelines;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateGraphicsPipelines, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateGraphicsPipelines, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkPipelineCache((*&local_pipelineCache));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_createInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
        reservedmarshal_VkGraphicsPipelineCreateInfo(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkGraphicsPipelineCreateInfo*)(local_pCreateInfos + i), streamPtrPtr);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    if (((createInfoCount))) {
        uint8_t* cgen_var_3_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((createInfoCount)); ++k) {
            uint64_t tmpval = (uint64_t)(pPipelines[k]);
            memcpy(cgen_var_3_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((createInfoCount));
    }
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateGraphicsPipelines), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    if (((createInfoCount))) {
        uint64_t* cgen_var_4;
        stream->alloc((void**)&cgen_var_4, ((createInfoCount)) * 8);
        stream->read((uint64_t*)cgen_var_4, ((createInfoCount)) * 8);
        stream->handleMapping()->mapHandles_u64_VkPipeline(cgen_var_4, (VkPipeline*)pPipelines,
                                                           ((createInfoCount)));
    }
    stream->unsetHandleMapping();
    VkResult vkCreateGraphicsPipelines_VkResult_return = (VkResult)0;
    stream->read(&vkCreateGraphicsPipelines_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateGraphicsPipelines_VkResult_return;
}

VkResult VkEncoder::vkCreateComputePipelines(VkDevice device, VkPipelineCache pipelineCache,
                                             uint32_t createInfoCount,
                                             const VkComputePipelineCreateInfo* pCreateInfos,
                                             const VkAllocationCallbacks* pAllocator,
                                             VkPipeline* pPipelines, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateComputePipelines in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateComputePipelines(device:%p, pipelineCache:%p, createInfoCount:%d, "
        "pCreateInfos:%p, pAllocator:%p, pPipelines:%p)",
        device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineCache local_pipelineCache;
    uint32_t local_createInfoCount;
    VkComputePipelineCreateInfo* local_pCreateInfos;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pipelineCache = pipelineCache;
    local_createInfoCount = createInfoCount;
    local_pCreateInfos = nullptr;
    if (pCreateInfos) {
        local_pCreateInfos = (VkComputePipelineCreateInfo*)pool->alloc(
            ((createInfoCount)) * sizeof(const VkComputePipelineCreateInfo));
        for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
            deepcopy_VkComputePipelineCreateInfo(
                pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfos + i,
                (VkComputePipelineCreateInfo*)(local_pCreateInfos + i));
        }
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfos) {
        for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
            transform_tohost_VkComputePipelineCreateInfo(
                sResourceTracker, (VkComputePipelineCreateInfo*)(local_pCreateInfos + i));
        }
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
            count_VkComputePipelineCreateInfo(
                sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkComputePipelineCreateInfo*)(local_pCreateInfos + i), countPtr);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        if (((createInfoCount))) {
            *countPtr += ((createInfoCount)) * 8;
        }
    }
    uint32_t packetSize_vkCreateComputePipelines =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateComputePipelines);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateComputePipelines);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateComputePipelines = OP_vkCreateComputePipelines;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateComputePipelines, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateComputePipelines, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkPipelineCache((*&local_pipelineCache));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_createInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((createInfoCount)); ++i) {
        reservedmarshal_VkComputePipelineCreateInfo(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkComputePipelineCreateInfo*)(local_pCreateInfos + i), streamPtrPtr);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    if (((createInfoCount))) {
        uint8_t* cgen_var_3_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((createInfoCount)); ++k) {
            uint64_t tmpval = (uint64_t)(pPipelines[k]);
            memcpy(cgen_var_3_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((createInfoCount));
    }
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateComputePipelines), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    if (((createInfoCount))) {
        uint64_t* cgen_var_4;
        stream->alloc((void**)&cgen_var_4, ((createInfoCount)) * 8);
        stream->read((uint64_t*)cgen_var_4, ((createInfoCount)) * 8);
        stream->handleMapping()->mapHandles_u64_VkPipeline(cgen_var_4, (VkPipeline*)pPipelines,
                                                           ((createInfoCount)));
    }
    stream->unsetHandleMapping();
    VkResult vkCreateComputePipelines_VkResult_return = (VkResult)0;
    stream->read(&vkCreateComputePipelines_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateComputePipelines_VkResult_return;
}

void VkEncoder::vkDestroyPipeline(VkDevice device, VkPipeline pipeline,
                                  const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyPipeline in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyPipeline(device:%p, pipeline:%p, pAllocator:%p)", device, pipeline,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipeline local_pipeline;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pipeline = pipeline;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyPipeline =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyPipeline);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyPipeline);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyPipeline = OP_vkDestroyPipeline;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyPipeline, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyPipeline, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkPipeline((*&local_pipeline));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyPipeline), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkPipeline((VkPipeline*)&pipeline);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreatePipelineLayout(VkDevice device,
                                           const VkPipelineLayoutCreateInfo* pCreateInfo,
                                           const VkAllocationCallbacks* pAllocator,
                                           VkPipelineLayout* pPipelineLayout, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreatePipelineLayout in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreatePipelineLayout(device:%p, pCreateInfo:%p, pAllocator:%p, pPipelineLayout:%p)",
        device, pCreateInfo, pAllocator, pPipelineLayout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineLayoutCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkPipelineLayoutCreateInfo*)pool->alloc(sizeof(const VkPipelineLayoutCreateInfo));
        deepcopy_VkPipelineLayoutCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                            (VkPipelineLayoutCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkPipelineLayoutCreateInfo(
            sResourceTracker, (VkPipelineLayoutCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPipelineLayoutCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkPipelineLayoutCreateInfo*)(local_pCreateInfo),
                                         countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreatePipelineLayout =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreatePipelineLayout);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreatePipelineLayout);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreatePipelineLayout = OP_vkCreatePipelineLayout;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreatePipelineLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreatePipelineLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPipelineLayoutCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                               (VkPipelineLayoutCreateInfo*)(local_pCreateInfo),
                                               streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pPipelineLayout));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreatePipelineLayout), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkPipelineLayout(&cgen_var_3,
                                                             (VkPipelineLayout*)pPipelineLayout, 1);
    stream->unsetHandleMapping();
    VkResult vkCreatePipelineLayout_VkResult_return = (VkResult)0;
    stream->read(&vkCreatePipelineLayout_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreatePipelineLayout_VkResult_return;
}

void VkEncoder::vkDestroyPipelineLayout(VkDevice device, VkPipelineLayout pipelineLayout,
                                        const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyPipelineLayout in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyPipelineLayout(device:%p, pipelineLayout:%p, pAllocator:%p)",
                      device, pipelineLayout, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineLayout local_pipelineLayout;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pipelineLayout = pipelineLayout;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyPipelineLayout =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyPipelineLayout);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyPipelineLayout);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyPipelineLayout = OP_vkDestroyPipelineLayout;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyPipelineLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyPipelineLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkPipelineLayout((*&local_pipelineLayout));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyPipelineLayout), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkPipelineLayout(
        (VkPipelineLayout*)&pipelineLayout);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateSampler(VkDevice device, const VkSamplerCreateInfo* pCreateInfo,
                                    const VkAllocationCallbacks* pAllocator, VkSampler* pSampler,
                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateSampler in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCreateSampler(device:%p, pCreateInfo:%p, pAllocator:%p, pSampler:%p)",
                      device, pCreateInfo, pAllocator, pSampler);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSamplerCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkSamplerCreateInfo*)pool->alloc(sizeof(const VkSamplerCreateInfo));
        deepcopy_VkSamplerCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                     (VkSamplerCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkSamplerCreateInfo(sResourceTracker,
                                             (VkSamplerCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSamplerCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkSamplerCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateSampler = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateSampler);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateSampler);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateSampler = OP_vkCreateSampler;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateSampler, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateSampler, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkSamplerCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkSamplerCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pSampler));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateSampler), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkSampler(&cgen_var_3, (VkSampler*)pSampler, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateSampler_VkResult_return = (VkResult)0;
    stream->read(&vkCreateSampler_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateSampler_VkResult_return;
}

void VkEncoder::vkDestroySampler(VkDevice device, VkSampler sampler,
                                 const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroySampler in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroySampler(device:%p, sampler:%p, pAllocator:%p)", device, sampler,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSampler local_sampler;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_sampler = sampler;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroySampler = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroySampler);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroySampler);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroySampler = OP_vkDestroySampler;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroySampler, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroySampler, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkSampler((*&local_sampler));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroySampler), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkSampler((VkSampler*)&sampler);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateDescriptorSetLayout(VkDevice device,
                                                const VkDescriptorSetLayoutCreateInfo* pCreateInfo,
                                                const VkAllocationCallbacks* pAllocator,
                                                VkDescriptorSetLayout* pSetLayout,
                                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateDescriptorSetLayout in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateDescriptorSetLayout(device:%p, pCreateInfo:%p, pAllocator:%p, pSetLayout:%p)",
        device, pCreateInfo, pAllocator, pSetLayout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSetLayoutCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkDescriptorSetLayoutCreateInfo*)pool->alloc(
            sizeof(const VkDescriptorSetLayoutCreateInfo));
        deepcopy_VkDescriptorSetLayoutCreateInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
            (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkDescriptorSetLayoutCreateInfo(
            sResourceTracker, (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDescriptorSetLayoutCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo),
                                              countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateDescriptorSetLayout =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateDescriptorSetLayout);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateDescriptorSetLayout);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateDescriptorSetLayout = OP_vkCreateDescriptorSetLayout;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateDescriptorSetLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateDescriptorSetLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDescriptorSetLayoutCreateInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo),
        streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pSetLayout));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateDescriptorSetLayout), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkDescriptorSetLayout(
        &cgen_var_3, (VkDescriptorSetLayout*)pSetLayout, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateDescriptorSetLayout_VkResult_return = (VkResult)0;
    stream->read(&vkCreateDescriptorSetLayout_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateDescriptorSetLayout_VkResult_return;
}

void VkEncoder::vkDestroyDescriptorSetLayout(VkDevice device,
                                             VkDescriptorSetLayout descriptorSetLayout,
                                             const VkAllocationCallbacks* pAllocator,
                                             uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyDescriptorSetLayout in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkDestroyDescriptorSetLayout(device:%p, descriptorSetLayout:%p, pAllocator:%p)", device,
        descriptorSetLayout, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSetLayout local_descriptorSetLayout;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_descriptorSetLayout = descriptorSetLayout;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyDescriptorSetLayout =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkDestroyDescriptorSetLayout);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyDescriptorSetLayout);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyDescriptorSetLayout = OP_vkDestroyDescriptorSetLayout;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyDescriptorSetLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyDescriptorSetLayout, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorSetLayout((*&local_descriptorSetLayout));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyDescriptorSetLayout), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkDescriptorSetLayout(
        (VkDescriptorSetLayout*)&descriptorSetLayout);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateDescriptorPool(VkDevice device,
                                           const VkDescriptorPoolCreateInfo* pCreateInfo,
                                           const VkAllocationCallbacks* pAllocator,
                                           VkDescriptorPool* pDescriptorPool, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateDescriptorPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateDescriptorPool(device:%p, pCreateInfo:%p, pAllocator:%p, pDescriptorPool:%p)",
        device, pCreateInfo, pAllocator, pDescriptorPool);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorPoolCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkDescriptorPoolCreateInfo*)pool->alloc(sizeof(const VkDescriptorPoolCreateInfo));
        deepcopy_VkDescriptorPoolCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                            (VkDescriptorPoolCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkDescriptorPoolCreateInfo(
            sResourceTracker, (VkDescriptorPoolCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDescriptorPoolCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkDescriptorPoolCreateInfo*)(local_pCreateInfo),
                                         countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateDescriptorPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateDescriptorPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateDescriptorPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateDescriptorPool = OP_vkCreateDescriptorPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateDescriptorPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateDescriptorPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDescriptorPoolCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                               (VkDescriptorPoolCreateInfo*)(local_pCreateInfo),
                                               streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pDescriptorPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateDescriptorPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkDescriptorPool(&cgen_var_3,
                                                             (VkDescriptorPool*)pDescriptorPool, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateDescriptorPool_VkResult_return = (VkResult)0;
    stream->read(&vkCreateDescriptorPool_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateDescriptorPool_VkResult_return;
}

void VkEncoder::vkDestroyDescriptorPool(VkDevice device, VkDescriptorPool descriptorPool,
                                        const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyDescriptorPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyDescriptorPool(device:%p, descriptorPool:%p, pAllocator:%p)",
                      device, descriptorPool, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorPool local_descriptorPool;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_descriptorPool = descriptorPool;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyDescriptorPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyDescriptorPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyDescriptorPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyDescriptorPool = OP_vkDestroyDescriptorPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyDescriptorPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyDescriptorPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorPool((*&local_descriptorPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyDescriptorPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkDescriptorPool(
        (VkDescriptorPool*)&descriptorPool);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkResetDescriptorPool(VkDevice device, VkDescriptorPool descriptorPool,
                                          VkDescriptorPoolResetFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkResetDescriptorPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkResetDescriptorPool(device:%p, descriptorPool:%p, flags:%d)", device,
                      descriptorPool, flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorPool local_descriptorPool;
    VkDescriptorPoolResetFlags local_flags;
    local_device = device;
    local_descriptorPool = descriptorPool;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDescriptorPoolResetFlags);
    }
    uint32_t packetSize_vkResetDescriptorPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkResetDescriptorPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkResetDescriptorPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkResetDescriptorPool = OP_vkResetDescriptorPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkResetDescriptorPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkResetDescriptorPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorPool((*&local_descriptorPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDescriptorPoolResetFlags*)&local_flags,
           sizeof(VkDescriptorPoolResetFlags));
    *streamPtrPtr += sizeof(VkDescriptorPoolResetFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkResetDescriptorPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkResetDescriptorPool_VkResult_return = (VkResult)0;
    stream->read(&vkResetDescriptorPool_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkResetDescriptorPool_VkResult_return;
}

VkResult VkEncoder::vkAllocateDescriptorSets(VkDevice device,
                                             const VkDescriptorSetAllocateInfo* pAllocateInfo,
                                             VkDescriptorSet* pDescriptorSets, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkAllocateDescriptorSets in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkAllocateDescriptorSets(device:%p, pAllocateInfo:%p, pDescriptorSets:%p)",
                      device, pAllocateInfo, pDescriptorSets);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSetAllocateInfo* local_pAllocateInfo;
    local_device = device;
    local_pAllocateInfo = nullptr;
    if (pAllocateInfo) {
        local_pAllocateInfo =
            (VkDescriptorSetAllocateInfo*)pool->alloc(sizeof(const VkDescriptorSetAllocateInfo));
        deepcopy_VkDescriptorSetAllocateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocateInfo,
                                             (VkDescriptorSetAllocateInfo*)(local_pAllocateInfo));
    }
    if (local_pAllocateInfo) {
        transform_tohost_VkDescriptorSetAllocateInfo(
            sResourceTracker, (VkDescriptorSetAllocateInfo*)(local_pAllocateInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDescriptorSetAllocateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkDescriptorSetAllocateInfo*)(local_pAllocateInfo),
                                          countPtr);
        if (pAllocateInfo->descriptorSetCount) {
            *countPtr += pAllocateInfo->descriptorSetCount * 8;
        }
    }
    uint32_t packetSize_vkAllocateDescriptorSets =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkAllocateDescriptorSets);
    uint8_t* streamPtr = stream->reserve(packetSize_vkAllocateDescriptorSets);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkAllocateDescriptorSets = OP_vkAllocateDescriptorSets;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkAllocateDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkAllocateDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDescriptorSetAllocateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkDescriptorSetAllocateInfo*)(local_pAllocateInfo),
                                                streamPtrPtr);
    /* is handle, possibly out */;
    if (pAllocateInfo->descriptorSetCount) {
        uint8_t* cgen_var_1_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < pAllocateInfo->descriptorSetCount; ++k) {
            uint64_t tmpval = (uint64_t)(pDescriptorSets[k]);
            memcpy(cgen_var_1_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * pAllocateInfo->descriptorSetCount;
    }
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkAllocateDescriptorSets), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    if (pAllocateInfo->descriptorSetCount) {
        uint64_t* cgen_var_2;
        stream->alloc((void**)&cgen_var_2, pAllocateInfo->descriptorSetCount * 8);
        stream->read((uint64_t*)cgen_var_2, pAllocateInfo->descriptorSetCount * 8);
        stream->handleMapping()->mapHandles_u64_VkDescriptorSet(
            cgen_var_2, (VkDescriptorSet*)pDescriptorSets, pAllocateInfo->descriptorSetCount);
    }
    stream->unsetHandleMapping();
    VkResult vkAllocateDescriptorSets_VkResult_return = (VkResult)0;
    stream->read(&vkAllocateDescriptorSets_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkAllocateDescriptorSets_VkResult_return;
}

VkResult VkEncoder::vkFreeDescriptorSets(VkDevice device, VkDescriptorPool descriptorPool,
                                         uint32_t descriptorSetCount,
                                         const VkDescriptorSet* pDescriptorSets, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkFreeDescriptorSets in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkFreeDescriptorSets(device:%p, descriptorPool:%p, descriptorSetCount:%d, "
        "pDescriptorSets:%p)",
        device, descriptorPool, descriptorSetCount, pDescriptorSets);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorPool local_descriptorPool;
    uint32_t local_descriptorSetCount;
    VkDescriptorSet* local_pDescriptorSets;
    local_device = device;
    local_descriptorPool = descriptorPool;
    local_descriptorSetCount = descriptorSetCount;
    // Avoiding deepcopy for pDescriptorSets
    local_pDescriptorSets = (VkDescriptorSet*)pDescriptorSets;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pDescriptorSets) {
            if (((descriptorSetCount))) {
                *countPtr += ((descriptorSetCount)) * 8;
            }
        }
    }
    uint32_t packetSize_vkFreeDescriptorSets =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkFreeDescriptorSets);
    uint8_t* streamPtr = stream->reserve(packetSize_vkFreeDescriptorSets);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkFreeDescriptorSets = OP_vkFreeDescriptorSets;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkFreeDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkFreeDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorPool((*&local_descriptorPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_descriptorSetCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pDescriptorSets;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pDescriptorSets) {
        if (((descriptorSetCount))) {
            uint8_t* cgen_var_2_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((descriptorSetCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkDescriptorSet(local_pDescriptorSets[k]);
                memcpy(cgen_var_2_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((descriptorSetCount));
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkFreeDescriptorSets), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkFreeDescriptorSets_VkResult_return = (VkResult)0;
    stream->read(&vkFreeDescriptorSets_VkResult_return, sizeof(VkResult));
    if (pDescriptorSets) {
        sResourceTracker->destroyMapping()->mapHandles_VkDescriptorSet(
            (VkDescriptorSet*)pDescriptorSets, ((descriptorSetCount)));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkFreeDescriptorSets_VkResult_return;
}

void VkEncoder::vkUpdateDescriptorSets(VkDevice device, uint32_t descriptorWriteCount,
                                       const VkWriteDescriptorSet* pDescriptorWrites,
                                       uint32_t descriptorCopyCount,
                                       const VkCopyDescriptorSet* pDescriptorCopies,
                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkUpdateDescriptorSets in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkUpdateDescriptorSets(device:%p, descriptorWriteCount:%d, pDescriptorWrites:%p, "
        "descriptorCopyCount:%d, pDescriptorCopies:%p)",
        device, descriptorWriteCount, pDescriptorWrites, descriptorCopyCount, pDescriptorCopies);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_descriptorWriteCount;
    VkWriteDescriptorSet* local_pDescriptorWrites;
    uint32_t local_descriptorCopyCount;
    VkCopyDescriptorSet* local_pDescriptorCopies;
    local_device = device;
    local_descriptorWriteCount = descriptorWriteCount;
    local_pDescriptorWrites = nullptr;
    if (pDescriptorWrites) {
        local_pDescriptorWrites = (VkWriteDescriptorSet*)pool->alloc(
            ((descriptorWriteCount)) * sizeof(const VkWriteDescriptorSet));
        for (uint32_t i = 0; i < (uint32_t)((descriptorWriteCount)); ++i) {
            deepcopy_VkWriteDescriptorSet(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDescriptorWrites + i,
                                          (VkWriteDescriptorSet*)(local_pDescriptorWrites + i));
        }
    }
    local_descriptorCopyCount = descriptorCopyCount;
    local_pDescriptorCopies = nullptr;
    if (pDescriptorCopies) {
        local_pDescriptorCopies = (VkCopyDescriptorSet*)pool->alloc(
            ((descriptorCopyCount)) * sizeof(const VkCopyDescriptorSet));
        for (uint32_t i = 0; i < (uint32_t)((descriptorCopyCount)); ++i) {
            deepcopy_VkCopyDescriptorSet(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDescriptorCopies + i,
                                         (VkCopyDescriptorSet*)(local_pDescriptorCopies + i));
        }
    }
    if (local_pDescriptorWrites) {
        for (uint32_t i = 0; i < (uint32_t)((descriptorWriteCount)); ++i) {
            transform_tohost_VkWriteDescriptorSet(
                sResourceTracker, (VkWriteDescriptorSet*)(local_pDescriptorWrites + i));
        }
    }
    if (local_pDescriptorCopies) {
        for (uint32_t i = 0; i < (uint32_t)((descriptorCopyCount)); ++i) {
            transform_tohost_VkCopyDescriptorSet(
                sResourceTracker, (VkCopyDescriptorSet*)(local_pDescriptorCopies + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((descriptorWriteCount)); ++i) {
            count_VkWriteDescriptorSet(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkWriteDescriptorSet*)(local_pDescriptorWrites + i),
                                       countPtr);
        }
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((descriptorCopyCount)); ++i) {
            count_VkCopyDescriptorSet(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkCopyDescriptorSet*)(local_pDescriptorCopies + i),
                                      countPtr);
        }
    }
    uint32_t packetSize_vkUpdateDescriptorSets =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkUpdateDescriptorSets);
    uint8_t* streamPtr = stream->reserve(packetSize_vkUpdateDescriptorSets);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkUpdateDescriptorSets = OP_vkUpdateDescriptorSets;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkUpdateDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkUpdateDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_descriptorWriteCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((descriptorWriteCount)); ++i) {
        reservedmarshal_VkWriteDescriptorSet(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkWriteDescriptorSet*)(local_pDescriptorWrites + i),
                                             streamPtrPtr);
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_descriptorCopyCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((descriptorCopyCount)); ++i) {
        reservedmarshal_VkCopyDescriptorSet(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkCopyDescriptorSet*)(local_pDescriptorCopies + i),
                                            streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkUpdateDescriptorSets), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateFramebuffer(VkDevice device, const VkFramebufferCreateInfo* pCreateInfo,
                                        const VkAllocationCallbacks* pAllocator,
                                        VkFramebuffer* pFramebuffer, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateFramebuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateFramebuffer(device:%p, pCreateInfo:%p, pAllocator:%p, pFramebuffer:%p)", device,
        pCreateInfo, pAllocator, pFramebuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFramebufferCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkFramebufferCreateInfo*)pool->alloc(sizeof(const VkFramebufferCreateInfo));
        deepcopy_VkFramebufferCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                         (VkFramebufferCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkFramebufferCreateInfo(sResourceTracker,
                                                 (VkFramebufferCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkFramebufferCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkFramebufferCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateFramebuffer =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateFramebuffer);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateFramebuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateFramebuffer = OP_vkCreateFramebuffer;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateFramebuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateFramebuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkFramebufferCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkFramebufferCreateInfo*)(local_pCreateInfo),
                                            streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pFramebuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateFramebuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkFramebuffer(&cgen_var_3, (VkFramebuffer*)pFramebuffer,
                                                          1);
    stream->unsetHandleMapping();
    VkResult vkCreateFramebuffer_VkResult_return = (VkResult)0;
    stream->read(&vkCreateFramebuffer_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateFramebuffer_VkResult_return;
}

void VkEncoder::vkDestroyFramebuffer(VkDevice device, VkFramebuffer framebuffer,
                                     const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyFramebuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyFramebuffer(device:%p, framebuffer:%p, pAllocator:%p)", device,
                      framebuffer, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFramebuffer local_framebuffer;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_framebuffer = framebuffer;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyFramebuffer =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyFramebuffer);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyFramebuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyFramebuffer = OP_vkDestroyFramebuffer;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyFramebuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyFramebuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFramebuffer((*&local_framebuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyFramebuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkFramebuffer((VkFramebuffer*)&framebuffer);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateRenderPass(VkDevice device, const VkRenderPassCreateInfo* pCreateInfo,
                                       const VkAllocationCallbacks* pAllocator,
                                       VkRenderPass* pRenderPass, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateRenderPass in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateRenderPass(device:%p, pCreateInfo:%p, pAllocator:%p, pRenderPass:%p)", device,
        pCreateInfo, pAllocator, pRenderPass);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkRenderPassCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkRenderPassCreateInfo*)pool->alloc(sizeof(const VkRenderPassCreateInfo));
        deepcopy_VkRenderPassCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                        (VkRenderPassCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkRenderPassCreateInfo(sResourceTracker,
                                                (VkRenderPassCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderPassCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkRenderPassCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateRenderPass =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateRenderPass);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateRenderPass);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateRenderPass = OP_vkCreateRenderPass;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkRenderPassCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkRenderPassCreateInfo*)(local_pCreateInfo),
                                           streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pRenderPass));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateRenderPass), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkRenderPass(&cgen_var_3, (VkRenderPass*)pRenderPass,
                                                         1);
    stream->unsetHandleMapping();
    VkResult vkCreateRenderPass_VkResult_return = (VkResult)0;
    stream->read(&vkCreateRenderPass_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateRenderPass_VkResult_return;
}

void VkEncoder::vkDestroyRenderPass(VkDevice device, VkRenderPass renderPass,
                                    const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyRenderPass in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyRenderPass(device:%p, renderPass:%p, pAllocator:%p)", device,
                      renderPass, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkRenderPass local_renderPass;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_renderPass = renderPass;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyRenderPass =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyRenderPass);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyRenderPass);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyRenderPass = OP_vkDestroyRenderPass;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkRenderPass((*&local_renderPass));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyRenderPass), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkRenderPass((VkRenderPass*)&renderPass);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetRenderAreaGranularity(VkDevice device, VkRenderPass renderPass,
                                           VkExtent2D* pGranularity, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetRenderAreaGranularity in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetRenderAreaGranularity(device:%p, renderPass:%p, pGranularity:%p)",
                      device, renderPass, pGranularity);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkRenderPass local_renderPass;
    local_device = device;
    local_renderPass = renderPass;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkExtent2D(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExtent2D*)(pGranularity),
                         countPtr);
    }
    uint32_t packetSize_vkGetRenderAreaGranularity =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetRenderAreaGranularity);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetRenderAreaGranularity);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetRenderAreaGranularity = OP_vkGetRenderAreaGranularity;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetRenderAreaGranularity, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetRenderAreaGranularity, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkRenderPass((*&local_renderPass));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkExtent2D(stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExtent2D*)(pGranularity),
                               streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetRenderAreaGranularity), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExtent2D(stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExtent2D*)(pGranularity));
    if (pGranularity) {
        transform_fromhost_VkExtent2D(sResourceTracker, (VkExtent2D*)(pGranularity));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateCommandPool(VkDevice device, const VkCommandPoolCreateInfo* pCreateInfo,
                                        const VkAllocationCallbacks* pAllocator,
                                        VkCommandPool* pCommandPool, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateCommandPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateCommandPool(device:%p, pCreateInfo:%p, pAllocator:%p, pCommandPool:%p)", device,
        pCreateInfo, pAllocator, pCommandPool);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCommandPoolCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkCommandPoolCreateInfo*)pool->alloc(sizeof(const VkCommandPoolCreateInfo));
        deepcopy_VkCommandPoolCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                         (VkCommandPoolCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkCommandPoolCreateInfo(sResourceTracker,
                                                 (VkCommandPoolCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCommandPoolCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkCommandPoolCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateCommandPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateCommandPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateCommandPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateCommandPool = OP_vkCreateCommandPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkCommandPoolCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkCommandPoolCreateInfo*)(local_pCreateInfo),
                                            streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pCommandPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateCommandPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkCommandPool(&cgen_var_3, (VkCommandPool*)pCommandPool,
                                                          1);
    stream->unsetHandleMapping();
    VkResult vkCreateCommandPool_VkResult_return = (VkResult)0;
    stream->read(&vkCreateCommandPool_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateCommandPool_VkResult_return;
}

void VkEncoder::vkDestroyCommandPool(VkDevice device, VkCommandPool commandPool,
                                     const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyCommandPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyCommandPool(device:%p, commandPool:%p, pAllocator:%p)", device,
                      commandPool, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCommandPool local_commandPool;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_commandPool = commandPool;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyCommandPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyCommandPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyCommandPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyCommandPool = OP_vkDestroyCommandPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkCommandPool((*&local_commandPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyCommandPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkCommandPool((VkCommandPool*)&commandPool);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkResetCommandPool(VkDevice device, VkCommandPool commandPool,
                                       VkCommandPoolResetFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkResetCommandPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkResetCommandPool(device:%p, commandPool:%p, flags:%d)", device,
                      commandPool, flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCommandPool local_commandPool;
    VkCommandPoolResetFlags local_flags;
    local_device = device;
    local_commandPool = commandPool;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCommandPoolResetFlags);
    }
    uint32_t packetSize_vkResetCommandPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkResetCommandPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkResetCommandPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkResetCommandPool = OP_vkResetCommandPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkResetCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkResetCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkCommandPool((*&local_commandPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkCommandPoolResetFlags*)&local_flags, sizeof(VkCommandPoolResetFlags));
    *streamPtrPtr += sizeof(VkCommandPoolResetFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkResetCommandPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkResetCommandPool_VkResult_return = (VkResult)0;
    stream->read(&vkResetCommandPool_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkResetCommandPool_VkResult_return;
}

VkResult VkEncoder::vkAllocateCommandBuffers(VkDevice device,
                                             const VkCommandBufferAllocateInfo* pAllocateInfo,
                                             VkCommandBuffer* pCommandBuffers, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkAllocateCommandBuffers in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkAllocateCommandBuffers(device:%p, pAllocateInfo:%p, pCommandBuffers:%p)",
                      device, pAllocateInfo, pCommandBuffers);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCommandBufferAllocateInfo* local_pAllocateInfo;
    local_device = device;
    local_pAllocateInfo = nullptr;
    if (pAllocateInfo) {
        local_pAllocateInfo =
            (VkCommandBufferAllocateInfo*)pool->alloc(sizeof(const VkCommandBufferAllocateInfo));
        deepcopy_VkCommandBufferAllocateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocateInfo,
                                             (VkCommandBufferAllocateInfo*)(local_pAllocateInfo));
    }
    if (local_pAllocateInfo) {
        transform_tohost_VkCommandBufferAllocateInfo(
            sResourceTracker, (VkCommandBufferAllocateInfo*)(local_pAllocateInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCommandBufferAllocateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkCommandBufferAllocateInfo*)(local_pAllocateInfo),
                                          countPtr);
        if (pAllocateInfo->commandBufferCount) {
            *countPtr += pAllocateInfo->commandBufferCount * 8;
        }
    }
    uint32_t packetSize_vkAllocateCommandBuffers =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkAllocateCommandBuffers);
    uint8_t* streamPtr = stream->reserve(packetSize_vkAllocateCommandBuffers);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkAllocateCommandBuffers = OP_vkAllocateCommandBuffers;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkAllocateCommandBuffers, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkAllocateCommandBuffers, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkCommandBufferAllocateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkCommandBufferAllocateInfo*)(local_pAllocateInfo),
                                                streamPtrPtr);
    /* is handle, possibly out */;
    if (pAllocateInfo->commandBufferCount) {
        uint8_t* cgen_var_1_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < pAllocateInfo->commandBufferCount; ++k) {
            uint64_t tmpval = (uint64_t)(pCommandBuffers[k]);
            memcpy(cgen_var_1_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * pAllocateInfo->commandBufferCount;
    }
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkAllocateCommandBuffers), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    if (pAllocateInfo->commandBufferCount) {
        uint64_t* cgen_var_2;
        stream->alloc((void**)&cgen_var_2, pAllocateInfo->commandBufferCount * 8);
        stream->read((uint64_t*)cgen_var_2, pAllocateInfo->commandBufferCount * 8);
        stream->handleMapping()->mapHandles_u64_VkCommandBuffer(
            cgen_var_2, (VkCommandBuffer*)pCommandBuffers, pAllocateInfo->commandBufferCount);
    }
    stream->unsetHandleMapping();
    VkResult vkAllocateCommandBuffers_VkResult_return = (VkResult)0;
    stream->read(&vkAllocateCommandBuffers_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkAllocateCommandBuffers_VkResult_return;
}

void VkEncoder::vkFreeCommandBuffers(VkDevice device, VkCommandPool commandPool,
                                     uint32_t commandBufferCount,
                                     const VkCommandBuffer* pCommandBuffers, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkFreeCommandBuffers in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkFreeCommandBuffers(device:%p, commandPool:%p, commandBufferCount:%d, "
        "pCommandBuffers:%p)",
        device, commandPool, commandBufferCount, pCommandBuffers);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCommandPool local_commandPool;
    uint32_t local_commandBufferCount;
    VkCommandBuffer* local_pCommandBuffers;
    local_device = device;
    local_commandPool = commandPool;
    local_commandBufferCount = commandBufferCount;
    // Avoiding deepcopy for pCommandBuffers
    local_pCommandBuffers = (VkCommandBuffer*)pCommandBuffers;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pCommandBuffers) {
            if (((commandBufferCount))) {
                *countPtr += ((commandBufferCount)) * 8;
            }
        }
    }
    uint32_t packetSize_vkFreeCommandBuffers =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkFreeCommandBuffers);
    uint8_t* streamPtr = stream->reserve(packetSize_vkFreeCommandBuffers);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkFreeCommandBuffers = OP_vkFreeCommandBuffers;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkFreeCommandBuffers, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkFreeCommandBuffers, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkCommandPool((*&local_commandPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_commandBufferCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pCommandBuffers;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pCommandBuffers) {
        if (((commandBufferCount))) {
            uint8_t* cgen_var_2_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((commandBufferCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkCommandBuffer(local_pCommandBuffers[k]);
                memcpy(cgen_var_2_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((commandBufferCount));
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkFreeCommandBuffers), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    if (pCommandBuffers) {
        sResourceTracker->destroyMapping()->mapHandles_VkCommandBuffer(
            (VkCommandBuffer*)pCommandBuffers, ((commandBufferCount)));
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkBeginCommandBuffer(VkCommandBuffer commandBuffer,
                                         const VkCommandBufferBeginInfo* pBeginInfo,
                                         uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBeginCommandBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkBeginCommandBuffer(commandBuffer:%p, pBeginInfo:%p)", commandBuffer,
                      pBeginInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCommandBufferBeginInfo* local_pBeginInfo;
    local_commandBuffer = commandBuffer;
    local_pBeginInfo = nullptr;
    if (pBeginInfo) {
        local_pBeginInfo =
            (VkCommandBufferBeginInfo*)pool->alloc(sizeof(const VkCommandBufferBeginInfo));
        deepcopy_VkCommandBufferBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBeginInfo,
                                          (VkCommandBufferBeginInfo*)(local_pBeginInfo));
    }
    if (local_pBeginInfo) {
        transform_tohost_VkCommandBufferBeginInfo(sResourceTracker,
                                                  (VkCommandBufferBeginInfo*)(local_pBeginInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCommandBufferBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkCommandBufferBeginInfo*)(local_pBeginInfo), countPtr);
    }
    uint32_t packetSize_vkBeginCommandBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkBeginCommandBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkBeginCommandBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkBeginCommandBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBeginCommandBuffer = OP_vkBeginCommandBuffer;
    memcpy(streamPtr, &opcode_vkBeginCommandBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBeginCommandBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCommandBufferBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkCommandBufferBeginInfo*)(local_pBeginInfo),
                                             streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkBeginCommandBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkBeginCommandBuffer_VkResult_return = (VkResult)0;
    stream->read(&vkBeginCommandBuffer_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkBeginCommandBuffer_VkResult_return;
}

VkResult VkEncoder::vkEndCommandBuffer(VkCommandBuffer commandBuffer, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEndCommandBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkEndCommandBuffer(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    local_commandBuffer = commandBuffer;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkEndCommandBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkEndCommandBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkEndCommandBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkEndCommandBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEndCommandBuffer = OP_vkEndCommandBuffer;
    memcpy(streamPtr, &opcode_vkEndCommandBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEndCommandBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkEndCommandBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkEndCommandBuffer_VkResult_return = (VkResult)0;
    stream->read(&vkEndCommandBuffer_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEndCommandBuffer_VkResult_return;
}

VkResult VkEncoder::vkResetCommandBuffer(VkCommandBuffer commandBuffer,
                                         VkCommandBufferResetFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkResetCommandBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkResetCommandBuffer(commandBuffer:%p, flags:%d)", commandBuffer, flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCommandBufferResetFlags local_flags;
    local_commandBuffer = commandBuffer;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCommandBufferResetFlags);
    }
    uint32_t packetSize_vkResetCommandBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkResetCommandBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkResetCommandBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkResetCommandBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkResetCommandBuffer = OP_vkResetCommandBuffer;
    memcpy(streamPtr, &opcode_vkResetCommandBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkResetCommandBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkCommandBufferResetFlags*)&local_flags,
           sizeof(VkCommandBufferResetFlags));
    *streamPtrPtr += sizeof(VkCommandBufferResetFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkResetCommandBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkResetCommandBuffer_VkResult_return = (VkResult)0;
    stream->read(&vkResetCommandBuffer_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkResetCommandBuffer_VkResult_return;
}

void VkEncoder::vkCmdBindPipeline(VkCommandBuffer commandBuffer,
                                  VkPipelineBindPoint pipelineBindPoint, VkPipeline pipeline,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindPipeline in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBindPipeline(commandBuffer:%p, pipeline:%p)", commandBuffer, pipeline);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineBindPoint local_pipelineBindPoint;
    VkPipeline local_pipeline;
    local_commandBuffer = commandBuffer;
    local_pipelineBindPoint = pipelineBindPoint;
    local_pipeline = pipeline;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineBindPoint);
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkCmdBindPipeline = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBindPipeline);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindPipeline -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindPipeline);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindPipeline = OP_vkCmdBindPipeline;
    memcpy(streamPtr, &opcode_vkCmdBindPipeline, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindPipeline, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPipelineBindPoint*)&local_pipelineBindPoint,
           sizeof(VkPipelineBindPoint));
    *streamPtrPtr += sizeof(VkPipelineBindPoint);
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPipeline((*&local_pipeline));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdBindPipeline), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetViewport(VkCommandBuffer commandBuffer, uint32_t firstViewport,
                                 uint32_t viewportCount, const VkViewport* pViewports,
                                 uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetViewport in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetViewport(commandBuffer:%p, firstViewport:%d, viewportCount:%d, pViewports:%p)",
        commandBuffer, firstViewport, viewportCount, pViewports);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstViewport;
    uint32_t local_viewportCount;
    VkViewport* local_pViewports;
    local_commandBuffer = commandBuffer;
    local_firstViewport = firstViewport;
    local_viewportCount = viewportCount;
    local_pViewports = nullptr;
    if (pViewports) {
        local_pViewports = (VkViewport*)pool->alloc(((viewportCount)) * sizeof(const VkViewport));
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            deepcopy_VkViewport(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pViewports + i,
                                (VkViewport*)(local_pViewports + i));
        }
    }
    if (local_pViewports) {
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            transform_tohost_VkViewport(sResourceTracker, (VkViewport*)(local_pViewports + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            count_VkViewport(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                             (VkViewport*)(local_pViewports + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdSetViewport = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetViewport);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetViewport -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetViewport);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetViewport = OP_vkCmdSetViewport;
    memcpy(streamPtr, &opcode_vkCmdSetViewport, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetViewport, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstViewport, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_viewportCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
        reservedmarshal_VkViewport(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkViewport*)(local_pViewports + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetViewport), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetScissor(VkCommandBuffer commandBuffer, uint32_t firstScissor,
                                uint32_t scissorCount, const VkRect2D* pScissors, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetScissor in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetScissor(commandBuffer:%p, firstScissor:%d, scissorCount:%d, pScissors:%p)",
        commandBuffer, firstScissor, scissorCount, pScissors);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstScissor;
    uint32_t local_scissorCount;
    VkRect2D* local_pScissors;
    local_commandBuffer = commandBuffer;
    local_firstScissor = firstScissor;
    local_scissorCount = scissorCount;
    local_pScissors = nullptr;
    if (pScissors) {
        local_pScissors = (VkRect2D*)pool->alloc(((scissorCount)) * sizeof(const VkRect2D));
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            deepcopy_VkRect2D(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pScissors + i,
                              (VkRect2D*)(local_pScissors + i));
        }
    }
    if (local_pScissors) {
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            transform_tohost_VkRect2D(sResourceTracker, (VkRect2D*)(local_pScissors + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            count_VkRect2D(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                           (VkRect2D*)(local_pScissors + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdSetScissor = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetScissor);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetScissor -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetScissor);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetScissor = OP_vkCmdSetScissor;
    memcpy(streamPtr, &opcode_vkCmdSetScissor, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetScissor, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstScissor, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_scissorCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
        reservedmarshal_VkRect2D(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkRect2D*)(local_pScissors + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetScissor), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetLineWidth(VkCommandBuffer commandBuffer, float lineWidth, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetLineWidth in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetLineWidth(commandBuffer:%p, lineWidth:%f)", commandBuffer,
                      lineWidth);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    float local_lineWidth;
    local_commandBuffer = commandBuffer;
    local_lineWidth = lineWidth;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(float);
    }
    uint32_t packetSize_vkCmdSetLineWidth = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetLineWidth);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetLineWidth -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetLineWidth);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetLineWidth = OP_vkCmdSetLineWidth;
    memcpy(streamPtr, &opcode_vkCmdSetLineWidth, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetLineWidth, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (float*)&local_lineWidth, sizeof(float));
    *streamPtrPtr += sizeof(float);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetLineWidth), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthBias(VkCommandBuffer commandBuffer, float depthBiasConstantFactor,
                                  float depthBiasClamp, float depthBiasSlopeFactor,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthBias in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetDepthBias(commandBuffer:%p, depthBiasConstantFactor:%f, depthBiasClamp:%f, "
        "depthBiasSlopeFactor:%f)",
        commandBuffer, depthBiasConstantFactor, depthBiasClamp, depthBiasSlopeFactor);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    float local_depthBiasConstantFactor;
    float local_depthBiasClamp;
    float local_depthBiasSlopeFactor;
    local_commandBuffer = commandBuffer;
    local_depthBiasConstantFactor = depthBiasConstantFactor;
    local_depthBiasClamp = depthBiasClamp;
    local_depthBiasSlopeFactor = depthBiasSlopeFactor;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(float);
        *countPtr += sizeof(float);
        *countPtr += sizeof(float);
    }
    uint32_t packetSize_vkCmdSetDepthBias = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthBias);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthBias -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthBias);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthBias = OP_vkCmdSetDepthBias;
    memcpy(streamPtr, &opcode_vkCmdSetDepthBias, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthBias, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (float*)&local_depthBiasConstantFactor, sizeof(float));
    *streamPtrPtr += sizeof(float);
    memcpy(*streamPtrPtr, (float*)&local_depthBiasClamp, sizeof(float));
    *streamPtrPtr += sizeof(float);
    memcpy(*streamPtrPtr, (float*)&local_depthBiasSlopeFactor, sizeof(float));
    *streamPtrPtr += sizeof(float);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetDepthBias), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetBlendConstants(VkCommandBuffer commandBuffer, const float blendConstants[4],
                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetBlendConstants in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetBlendConstants(commandBuffer:%p, blendConstants:%f)", commandBuffer,
                      blendConstants);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    float local_blendConstants[4];
    local_commandBuffer = commandBuffer;
    memcpy(local_blendConstants, blendConstants, 4 * sizeof(const float));
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += 4 * sizeof(float);
    }
    uint32_t packetSize_vkCmdSetBlendConstants = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetBlendConstants);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetBlendConstants -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetBlendConstants);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetBlendConstants = OP_vkCmdSetBlendConstants;
    memcpy(streamPtr, &opcode_vkCmdSetBlendConstants, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetBlendConstants, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (float*)local_blendConstants, 4 * sizeof(float));
    *streamPtrPtr += 4 * sizeof(float);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetBlendConstants), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthBounds(VkCommandBuffer commandBuffer, float minDepthBounds,
                                    float maxDepthBounds, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthBounds in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthBounds(commandBuffer:%p, minDepthBounds:%f, maxDepthBounds:%f)",
                      commandBuffer, minDepthBounds, maxDepthBounds);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    float local_minDepthBounds;
    float local_maxDepthBounds;
    local_commandBuffer = commandBuffer;
    local_minDepthBounds = minDepthBounds;
    local_maxDepthBounds = maxDepthBounds;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(float);
        *countPtr += sizeof(float);
    }
    uint32_t packetSize_vkCmdSetDepthBounds = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthBounds);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthBounds -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthBounds);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthBounds = OP_vkCmdSetDepthBounds;
    memcpy(streamPtr, &opcode_vkCmdSetDepthBounds, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthBounds, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (float*)&local_minDepthBounds, sizeof(float));
    *streamPtrPtr += sizeof(float);
    memcpy(*streamPtrPtr, (float*)&local_maxDepthBounds, sizeof(float));
    *streamPtrPtr += sizeof(float);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthBounds), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetStencilCompareMask(VkCommandBuffer commandBuffer,
                                           VkStencilFaceFlags faceMask, uint32_t compareMask,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetStencilCompareMask in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetStencilCompareMask(commandBuffer:%p, faceMask:%d, compareMask:%d)",
                      commandBuffer, faceMask, compareMask);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkStencilFaceFlags local_faceMask;
    uint32_t local_compareMask;
    local_commandBuffer = commandBuffer;
    local_faceMask = faceMask;
    local_compareMask = compareMask;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkStencilFaceFlags);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdSetStencilCompareMask = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetStencilCompareMask);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetStencilCompareMask -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetStencilCompareMask);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetStencilCompareMask = OP_vkCmdSetStencilCompareMask;
    memcpy(streamPtr, &opcode_vkCmdSetStencilCompareMask, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetStencilCompareMask, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkStencilFaceFlags*)&local_faceMask, sizeof(VkStencilFaceFlags));
    *streamPtrPtr += sizeof(VkStencilFaceFlags);
    memcpy(*streamPtrPtr, (uint32_t*)&local_compareMask, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetStencilCompareMask), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetStencilWriteMask(VkCommandBuffer commandBuffer, VkStencilFaceFlags faceMask,
                                         uint32_t writeMask, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetStencilWriteMask in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetStencilWriteMask(commandBuffer:%p, faceMask:%d, writeMask:%d)",
                      commandBuffer, faceMask, writeMask);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkStencilFaceFlags local_faceMask;
    uint32_t local_writeMask;
    local_commandBuffer = commandBuffer;
    local_faceMask = faceMask;
    local_writeMask = writeMask;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkStencilFaceFlags);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdSetStencilWriteMask = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetStencilWriteMask);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetStencilWriteMask -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetStencilWriteMask);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetStencilWriteMask = OP_vkCmdSetStencilWriteMask;
    memcpy(streamPtr, &opcode_vkCmdSetStencilWriteMask, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetStencilWriteMask, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkStencilFaceFlags*)&local_faceMask, sizeof(VkStencilFaceFlags));
    *streamPtrPtr += sizeof(VkStencilFaceFlags);
    memcpy(*streamPtrPtr, (uint32_t*)&local_writeMask, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetStencilWriteMask), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetStencilReference(VkCommandBuffer commandBuffer, VkStencilFaceFlags faceMask,
                                         uint32_t reference, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetStencilReference in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetStencilReference(commandBuffer:%p, faceMask:%d, reference:%d)",
                      commandBuffer, faceMask, reference);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkStencilFaceFlags local_faceMask;
    uint32_t local_reference;
    local_commandBuffer = commandBuffer;
    local_faceMask = faceMask;
    local_reference = reference;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkStencilFaceFlags);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdSetStencilReference = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetStencilReference);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetStencilReference -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetStencilReference);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetStencilReference = OP_vkCmdSetStencilReference;
    memcpy(streamPtr, &opcode_vkCmdSetStencilReference, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetStencilReference, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkStencilFaceFlags*)&local_faceMask, sizeof(VkStencilFaceFlags));
    *streamPtrPtr += sizeof(VkStencilFaceFlags);
    memcpy(*streamPtrPtr, (uint32_t*)&local_reference, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetStencilReference), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBindDescriptorSets(
    VkCommandBuffer commandBuffer, VkPipelineBindPoint pipelineBindPoint, VkPipelineLayout layout,
    uint32_t firstSet, uint32_t descriptorSetCount, const VkDescriptorSet* pDescriptorSets,
    uint32_t dynamicOffsetCount, const uint32_t* pDynamicOffsets, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindDescriptorSets in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBindDescriptorSets(commandBuffer:%p, layout:%p, firstSet:%d, descriptorSetCount:%d, "
        "pDescriptorSets:%p, dynamicOffsetCount:%d, pDynamicOffsets:%p)",
        commandBuffer, layout, firstSet, descriptorSetCount, pDescriptorSets, dynamicOffsetCount,
        pDynamicOffsets);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineBindPoint local_pipelineBindPoint;
    VkPipelineLayout local_layout;
    uint32_t local_firstSet;
    uint32_t local_descriptorSetCount;
    VkDescriptorSet* local_pDescriptorSets;
    uint32_t local_dynamicOffsetCount;
    uint32_t* local_pDynamicOffsets;
    local_commandBuffer = commandBuffer;
    local_pipelineBindPoint = pipelineBindPoint;
    local_layout = layout;
    local_firstSet = firstSet;
    local_descriptorSetCount = descriptorSetCount;
    // Avoiding deepcopy for pDescriptorSets
    local_pDescriptorSets = (VkDescriptorSet*)pDescriptorSets;
    local_dynamicOffsetCount = dynamicOffsetCount;
    // Avoiding deepcopy for pDynamicOffsets
    local_pDynamicOffsets = (uint32_t*)pDynamicOffsets;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineBindPoint);
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        if (((descriptorSetCount))) {
            *countPtr += ((descriptorSetCount)) * 8;
        }
        *countPtr += sizeof(uint32_t);
        *countPtr += ((dynamicOffsetCount)) * sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdBindDescriptorSets = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBindDescriptorSets);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindDescriptorSets -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindDescriptorSets);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindDescriptorSets = OP_vkCmdBindDescriptorSets;
    memcpy(streamPtr, &opcode_vkCmdBindDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindDescriptorSets, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPipelineBindPoint*)&local_pipelineBindPoint,
           sizeof(VkPipelineBindPoint));
    *streamPtrPtr += sizeof(VkPipelineBindPoint);
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPipelineLayout((*&local_layout));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstSet, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_descriptorSetCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((descriptorSetCount))) {
        uint8_t* cgen_var_1_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((descriptorSetCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkDescriptorSet(local_pDescriptorSets[k]);
            memcpy(cgen_var_1_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((descriptorSetCount));
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_dynamicOffsetCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)local_pDynamicOffsets,
           ((dynamicOffsetCount)) * sizeof(uint32_t));
    *streamPtrPtr += ((dynamicOffsetCount)) * sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBindDescriptorSets), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBindIndexBuffer(VkCommandBuffer commandBuffer, VkBuffer buffer,
                                     VkDeviceSize offset, VkIndexType indexType, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindIndexBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBindIndexBuffer(commandBuffer:%p, buffer:%p, offset:%ld)",
                      commandBuffer, buffer, offset);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_buffer;
    VkDeviceSize local_offset;
    VkIndexType local_indexType;
    local_commandBuffer = commandBuffer;
    local_buffer = buffer;
    local_offset = offset;
    local_indexType = indexType;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkIndexType);
    }
    uint32_t packetSize_vkCmdBindIndexBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBindIndexBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindIndexBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindIndexBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindIndexBuffer = OP_vkCmdBindIndexBuffer;
    memcpy(streamPtr, &opcode_vkCmdBindIndexBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindIndexBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_offset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkIndexType*)&local_indexType, sizeof(VkIndexType));
    *streamPtrPtr += sizeof(VkIndexType);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBindIndexBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBindVertexBuffers(VkCommandBuffer commandBuffer, uint32_t firstBinding,
                                       uint32_t bindingCount, const VkBuffer* pBuffers,
                                       const VkDeviceSize* pOffsets, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindVertexBuffers in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBindVertexBuffers(commandBuffer:%p, firstBinding:%d, bindingCount:%d, pBuffers:%p, "
        "pOffsets:%p)",
        commandBuffer, firstBinding, bindingCount, pBuffers, pOffsets);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstBinding;
    uint32_t local_bindingCount;
    VkBuffer* local_pBuffers;
    VkDeviceSize* local_pOffsets;
    local_commandBuffer = commandBuffer;
    local_firstBinding = firstBinding;
    local_bindingCount = bindingCount;
    // Avoiding deepcopy for pBuffers
    local_pBuffers = (VkBuffer*)pBuffers;
    // Avoiding deepcopy for pOffsets
    local_pOffsets = (VkDeviceSize*)pOffsets;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        if (((bindingCount))) {
            *countPtr += ((bindingCount)) * 8;
        }
        *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkCmdBindVertexBuffers = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBindVertexBuffers);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindVertexBuffers -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindVertexBuffers);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindVertexBuffers = OP_vkCmdBindVertexBuffers;
    memcpy(streamPtr, &opcode_vkCmdBindVertexBuffers, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindVertexBuffers, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstBinding, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindingCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((bindingCount))) {
        uint8_t* cgen_var_0_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((bindingCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkBuffer(local_pBuffers[k]);
            memcpy(cgen_var_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((bindingCount));
    }
    memcpy(*streamPtrPtr, (VkDeviceSize*)local_pOffsets, ((bindingCount)) * sizeof(VkDeviceSize));
    *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBindVertexBuffers), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDraw(VkCommandBuffer commandBuffer, uint32_t vertexCount,
                          uint32_t instanceCount, uint32_t firstVertex, uint32_t firstInstance,
                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDraw in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDraw(commandBuffer:%p, vertexCount:%d, instanceCount:%d, firstVertex:%d, "
        "firstInstance:%d)",
        commandBuffer, vertexCount, instanceCount, firstVertex, firstInstance);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_vertexCount;
    uint32_t local_instanceCount;
    uint32_t local_firstVertex;
    uint32_t local_firstInstance;
    local_commandBuffer = commandBuffer;
    local_vertexCount = vertexCount;
    local_instanceCount = instanceCount;
    local_firstVertex = firstVertex;
    local_firstInstance = firstInstance;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDraw = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDraw);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDraw -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDraw);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDraw = OP_vkCmdDraw;
    memcpy(streamPtr, &opcode_vkCmdDraw, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDraw, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_vertexCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_instanceCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstVertex, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstInstance, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdDraw), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDrawIndexed(VkCommandBuffer commandBuffer, uint32_t indexCount,
                                 uint32_t instanceCount, uint32_t firstIndex, int32_t vertexOffset,
                                 uint32_t firstInstance, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDrawIndexed in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDrawIndexed(commandBuffer:%p, indexCount:%d, instanceCount:%d, firstIndex:%d, "
        "vertexOffset:%d, firstInstance:%d)",
        commandBuffer, indexCount, instanceCount, firstIndex, vertexOffset, firstInstance);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_indexCount;
    uint32_t local_instanceCount;
    uint32_t local_firstIndex;
    int32_t local_vertexOffset;
    uint32_t local_firstInstance;
    local_commandBuffer = commandBuffer;
    local_indexCount = indexCount;
    local_instanceCount = instanceCount;
    local_firstIndex = firstIndex;
    local_vertexOffset = vertexOffset;
    local_firstInstance = firstInstance;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(int32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDrawIndexed = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDrawIndexed);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDrawIndexed -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDrawIndexed);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDrawIndexed = OP_vkCmdDrawIndexed;
    memcpy(streamPtr, &opcode_vkCmdDrawIndexed, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDrawIndexed, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_indexCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_instanceCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstIndex, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (int32_t*)&local_vertexOffset, sizeof(int32_t));
    *streamPtrPtr += sizeof(int32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstInstance, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdDrawIndexed), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDrawIndirect(VkCommandBuffer commandBuffer, VkBuffer buffer,
                                  VkDeviceSize offset, uint32_t drawCount, uint32_t stride,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDrawIndirect in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDrawIndirect(commandBuffer:%p, buffer:%p, offset:%ld, drawCount:%d, stride:%d)",
        commandBuffer, buffer, offset, drawCount, stride);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_buffer;
    VkDeviceSize local_offset;
    uint32_t local_drawCount;
    uint32_t local_stride;
    local_commandBuffer = commandBuffer;
    local_buffer = buffer;
    local_offset = offset;
    local_drawCount = drawCount;
    local_stride = stride;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDrawIndirect = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDrawIndirect);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDrawIndirect -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDrawIndirect);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDrawIndirect = OP_vkCmdDrawIndirect;
    memcpy(streamPtr, &opcode_vkCmdDrawIndirect, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDrawIndirect, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_offset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (uint32_t*)&local_drawCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_stride, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdDrawIndirect), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDrawIndexedIndirect(VkCommandBuffer commandBuffer, VkBuffer buffer,
                                         VkDeviceSize offset, uint32_t drawCount, uint32_t stride,
                                         uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDrawIndexedIndirect in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDrawIndexedIndirect(commandBuffer:%p, buffer:%p, offset:%ld, drawCount:%d, "
        "stride:%d)",
        commandBuffer, buffer, offset, drawCount, stride);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_buffer;
    VkDeviceSize local_offset;
    uint32_t local_drawCount;
    uint32_t local_stride;
    local_commandBuffer = commandBuffer;
    local_buffer = buffer;
    local_offset = offset;
    local_drawCount = drawCount;
    local_stride = stride;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDrawIndexedIndirect = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDrawIndexedIndirect);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDrawIndexedIndirect -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDrawIndexedIndirect);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDrawIndexedIndirect = OP_vkCmdDrawIndexedIndirect;
    memcpy(streamPtr, &opcode_vkCmdDrawIndexedIndirect, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDrawIndexedIndirect, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_offset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (uint32_t*)&local_drawCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_stride, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdDrawIndexedIndirect), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDispatch(VkCommandBuffer commandBuffer, uint32_t groupCountX,
                              uint32_t groupCountY, uint32_t groupCountZ, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDispatch in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDispatch(commandBuffer:%p, groupCountX:%d, groupCountY:%d, groupCountZ:%d)",
        commandBuffer, groupCountX, groupCountY, groupCountZ);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_groupCountX;
    uint32_t local_groupCountY;
    uint32_t local_groupCountZ;
    local_commandBuffer = commandBuffer;
    local_groupCountX = groupCountX;
    local_groupCountY = groupCountY;
    local_groupCountZ = groupCountZ;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDispatch = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDispatch);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDispatch -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDispatch);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDispatch = OP_vkCmdDispatch;
    memcpy(streamPtr, &opcode_vkCmdDispatch, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDispatch, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_groupCountX, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_groupCountY, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_groupCountZ, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdDispatch), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDispatchIndirect(VkCommandBuffer commandBuffer, VkBuffer buffer,
                                      VkDeviceSize offset, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDispatchIndirect in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdDispatchIndirect(commandBuffer:%p, buffer:%p, offset:%ld)",
                      commandBuffer, buffer, offset);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_buffer;
    VkDeviceSize local_offset;
    local_commandBuffer = commandBuffer;
    local_buffer = buffer;
    local_offset = offset;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkCmdDispatchIndirect = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDispatchIndirect);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDispatchIndirect -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDispatchIndirect);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDispatchIndirect = OP_vkCmdDispatchIndirect;
    memcpy(streamPtr, &opcode_vkCmdDispatchIndirect, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDispatchIndirect, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_offset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdDispatchIndirect), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyBuffer(VkCommandBuffer commandBuffer, VkBuffer srcBuffer,
                                VkBuffer dstBuffer, uint32_t regionCount,
                                const VkBufferCopy* pRegions, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdCopyBuffer(commandBuffer:%p, srcBuffer:%p, dstBuffer:%p, regionCount:%d, "
        "pRegions:%p)",
        commandBuffer, srcBuffer, dstBuffer, regionCount, pRegions);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_srcBuffer;
    VkBuffer local_dstBuffer;
    uint32_t local_regionCount;
    VkBufferCopy* local_pRegions;
    local_commandBuffer = commandBuffer;
    local_srcBuffer = srcBuffer;
    local_dstBuffer = dstBuffer;
    local_regionCount = regionCount;
    local_pRegions = nullptr;
    if (pRegions) {
        local_pRegions = (VkBufferCopy*)pool->alloc(((regionCount)) * sizeof(const VkBufferCopy));
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            deepcopy_VkBufferCopy(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRegions + i,
                                  (VkBufferCopy*)(local_pRegions + i));
        }
    }
    if (local_pRegions) {
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            transform_tohost_VkBufferCopy(sResourceTracker, (VkBufferCopy*)(local_pRegions + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            count_VkBufferCopy(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkBufferCopy*)(local_pRegions + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdCopyBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyBuffer = OP_vkCmdCopyBuffer;
    memcpy(streamPtr, &opcode_vkCmdCopyBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_srcBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_dstBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_regionCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
        reservedmarshal_VkBufferCopy(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkBufferCopy*)(local_pRegions + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdCopyBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyImage(VkCommandBuffer commandBuffer, VkImage srcImage,
                               VkImageLayout srcImageLayout, VkImage dstImage,
                               VkImageLayout dstImageLayout, uint32_t regionCount,
                               const VkImageCopy* pRegions, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdCopyImage(commandBuffer:%p, srcImage:%p, srcImageLayout:%d, dstImage:%p, "
        "dstImageLayout:%d, regionCount:%d, pRegions:%p)",
        commandBuffer, srcImage, srcImageLayout, dstImage, dstImageLayout, regionCount, pRegions);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkImage local_srcImage;
    VkImageLayout local_srcImageLayout;
    VkImage local_dstImage;
    VkImageLayout local_dstImageLayout;
    uint32_t local_regionCount;
    VkImageCopy* local_pRegions;
    local_commandBuffer = commandBuffer;
    local_srcImage = srcImage;
    local_srcImageLayout = srcImageLayout;
    local_dstImage = dstImage;
    local_dstImageLayout = dstImageLayout;
    local_regionCount = regionCount;
    local_pRegions = nullptr;
    if (pRegions) {
        local_pRegions = (VkImageCopy*)pool->alloc(((regionCount)) * sizeof(const VkImageCopy));
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            deepcopy_VkImageCopy(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRegions + i,
                                 (VkImageCopy*)(local_pRegions + i));
        }
    }
    if (local_pRegions) {
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            transform_tohost_VkImageCopy(sResourceTracker, (VkImageCopy*)(local_pRegions + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            count_VkImageCopy(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                              (VkImageCopy*)(local_pRegions + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdCopyImage = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyImage);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyImage -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyImage = OP_vkCmdCopyImage;
    memcpy(streamPtr, &opcode_vkCmdCopyImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkImage((*&local_srcImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_srcImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_dstImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_dstImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    memcpy(*streamPtrPtr, (uint32_t*)&local_regionCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
        reservedmarshal_VkImageCopy(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkImageCopy*)(local_pRegions + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdCopyImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBlitImage(VkCommandBuffer commandBuffer, VkImage srcImage,
                               VkImageLayout srcImageLayout, VkImage dstImage,
                               VkImageLayout dstImageLayout, uint32_t regionCount,
                               const VkImageBlit* pRegions, VkFilter filter, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBlitImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBlitImage(commandBuffer:%p, srcImage:%p, srcImageLayout:%d, dstImage:%p, "
        "dstImageLayout:%d, regionCount:%d, pRegions:%p)",
        commandBuffer, srcImage, srcImageLayout, dstImage, dstImageLayout, regionCount, pRegions);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkImage local_srcImage;
    VkImageLayout local_srcImageLayout;
    VkImage local_dstImage;
    VkImageLayout local_dstImageLayout;
    uint32_t local_regionCount;
    VkImageBlit* local_pRegions;
    VkFilter local_filter;
    local_commandBuffer = commandBuffer;
    local_srcImage = srcImage;
    local_srcImageLayout = srcImageLayout;
    local_dstImage = dstImage;
    local_dstImageLayout = dstImageLayout;
    local_regionCount = regionCount;
    local_pRegions = nullptr;
    if (pRegions) {
        local_pRegions = (VkImageBlit*)pool->alloc(((regionCount)) * sizeof(const VkImageBlit));
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            deepcopy_VkImageBlit(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRegions + i,
                                 (VkImageBlit*)(local_pRegions + i));
        }
    }
    local_filter = filter;
    if (local_pRegions) {
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            transform_tohost_VkImageBlit(sResourceTracker, (VkImageBlit*)(local_pRegions + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            count_VkImageBlit(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                              (VkImageBlit*)(local_pRegions + i), countPtr);
        }
        *countPtr += sizeof(VkFilter);
    }
    uint32_t packetSize_vkCmdBlitImage = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBlitImage);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBlitImage -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBlitImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBlitImage = OP_vkCmdBlitImage;
    memcpy(streamPtr, &opcode_vkCmdBlitImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBlitImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkImage((*&local_srcImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_srcImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_dstImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_dstImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    memcpy(*streamPtrPtr, (uint32_t*)&local_regionCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
        reservedmarshal_VkImageBlit(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkImageBlit*)(local_pRegions + i), streamPtrPtr);
    }
    memcpy(*streamPtrPtr, (VkFilter*)&local_filter, sizeof(VkFilter));
    *streamPtrPtr += sizeof(VkFilter);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdBlitImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyBufferToImage(VkCommandBuffer commandBuffer, VkBuffer srcBuffer,
                                       VkImage dstImage, VkImageLayout dstImageLayout,
                                       uint32_t regionCount, const VkBufferImageCopy* pRegions,
                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyBufferToImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdCopyBufferToImage(commandBuffer:%p, srcBuffer:%p, dstImage:%p, dstImageLayout:%d, "
        "regionCount:%d, pRegions:%p)",
        commandBuffer, srcBuffer, dstImage, dstImageLayout, regionCount, pRegions);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_srcBuffer;
    VkImage local_dstImage;
    VkImageLayout local_dstImageLayout;
    uint32_t local_regionCount;
    VkBufferImageCopy* local_pRegions;
    local_commandBuffer = commandBuffer;
    local_srcBuffer = srcBuffer;
    local_dstImage = dstImage;
    local_dstImageLayout = dstImageLayout;
    local_regionCount = regionCount;
    local_pRegions = nullptr;
    if (pRegions) {
        local_pRegions =
            (VkBufferImageCopy*)pool->alloc(((regionCount)) * sizeof(const VkBufferImageCopy));
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            deepcopy_VkBufferImageCopy(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRegions + i,
                                       (VkBufferImageCopy*)(local_pRegions + i));
        }
    }
    if (local_pRegions) {
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            transform_tohost_VkBufferImageCopy(sResourceTracker,
                                               (VkBufferImageCopy*)(local_pRegions + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            count_VkBufferImageCopy(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkBufferImageCopy*)(local_pRegions + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdCopyBufferToImage = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyBufferToImage);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyBufferToImage -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyBufferToImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyBufferToImage = OP_vkCmdCopyBufferToImage;
    memcpy(streamPtr, &opcode_vkCmdCopyBufferToImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyBufferToImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_srcBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_dstImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_dstImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    memcpy(*streamPtrPtr, (uint32_t*)&local_regionCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
        reservedmarshal_VkBufferImageCopy(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkBufferImageCopy*)(local_pRegions + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyBufferToImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyImageToBuffer(VkCommandBuffer commandBuffer, VkImage srcImage,
                                       VkImageLayout srcImageLayout, VkBuffer dstBuffer,
                                       uint32_t regionCount, const VkBufferImageCopy* pRegions,
                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyImageToBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdCopyImageToBuffer(commandBuffer:%p, srcImage:%p, srcImageLayout:%d, dstBuffer:%p, "
        "regionCount:%d, pRegions:%p)",
        commandBuffer, srcImage, srcImageLayout, dstBuffer, regionCount, pRegions);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkImage local_srcImage;
    VkImageLayout local_srcImageLayout;
    VkBuffer local_dstBuffer;
    uint32_t local_regionCount;
    VkBufferImageCopy* local_pRegions;
    local_commandBuffer = commandBuffer;
    local_srcImage = srcImage;
    local_srcImageLayout = srcImageLayout;
    local_dstBuffer = dstBuffer;
    local_regionCount = regionCount;
    local_pRegions = nullptr;
    if (pRegions) {
        local_pRegions =
            (VkBufferImageCopy*)pool->alloc(((regionCount)) * sizeof(const VkBufferImageCopy));
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            deepcopy_VkBufferImageCopy(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRegions + i,
                                       (VkBufferImageCopy*)(local_pRegions + i));
        }
    }
    if (local_pRegions) {
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            transform_tohost_VkBufferImageCopy(sResourceTracker,
                                               (VkBufferImageCopy*)(local_pRegions + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            count_VkBufferImageCopy(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkBufferImageCopy*)(local_pRegions + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdCopyImageToBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyImageToBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyImageToBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyImageToBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyImageToBuffer = OP_vkCmdCopyImageToBuffer;
    memcpy(streamPtr, &opcode_vkCmdCopyImageToBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyImageToBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkImage((*&local_srcImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_srcImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_dstBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_regionCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
        reservedmarshal_VkBufferImageCopy(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkBufferImageCopy*)(local_pRegions + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyImageToBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdUpdateBuffer(VkCommandBuffer commandBuffer, VkBuffer dstBuffer,
                                  VkDeviceSize dstOffset, VkDeviceSize dataSize, const void* pData,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdUpdateBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdUpdateBuffer(commandBuffer:%p, dstBuffer:%p, dstOffset:%ld, dataSize:%ld, pData:%p)",
        commandBuffer, dstBuffer, dstOffset, dataSize, pData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_dstBuffer;
    VkDeviceSize local_dstOffset;
    VkDeviceSize local_dataSize;
    void* local_pData;
    local_commandBuffer = commandBuffer;
    local_dstBuffer = dstBuffer;
    local_dstOffset = dstOffset;
    local_dataSize = dataSize;
    // Avoiding deepcopy for pData
    local_pData = (void*)pData;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += ((dataSize)) * sizeof(uint8_t);
    }
    uint32_t packetSize_vkCmdUpdateBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdUpdateBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdUpdateBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdUpdateBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdUpdateBuffer = OP_vkCmdUpdateBuffer;
    memcpy(streamPtr, &opcode_vkCmdUpdateBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdUpdateBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_dstBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_dstOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_dataSize, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (void*)local_pData, ((dataSize)) * sizeof(uint8_t));
    *streamPtrPtr += ((dataSize)) * sizeof(uint8_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdUpdateBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdFillBuffer(VkCommandBuffer commandBuffer, VkBuffer dstBuffer,
                                VkDeviceSize dstOffset, VkDeviceSize size, uint32_t data,
                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdFillBuffer in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdFillBuffer(commandBuffer:%p, dstBuffer:%p, dstOffset:%ld, size:%ld, data:%d)",
        commandBuffer, dstBuffer, dstOffset, size, data);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_dstBuffer;
    VkDeviceSize local_dstOffset;
    VkDeviceSize local_size;
    uint32_t local_data;
    local_commandBuffer = commandBuffer;
    local_dstBuffer = dstBuffer;
    local_dstOffset = dstOffset;
    local_size = size;
    local_data = data;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdFillBuffer = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdFillBuffer);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdFillBuffer -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdFillBuffer);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdFillBuffer = OP_vkCmdFillBuffer;
    memcpy(streamPtr, &opcode_vkCmdFillBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdFillBuffer, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_dstBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_dstOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_size, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (uint32_t*)&local_data, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdFillBuffer), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdClearColorImage(VkCommandBuffer commandBuffer, VkImage image,
                                     VkImageLayout imageLayout, const VkClearColorValue* pColor,
                                     uint32_t rangeCount, const VkImageSubresourceRange* pRanges,
                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdClearColorImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdClearColorImage(commandBuffer:%p, image:%p, imageLayout:%d, pColor:%p, "
        "rangeCount:%d, pRanges:%p)",
        commandBuffer, image, imageLayout, pColor, rangeCount, pRanges);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkImage local_image;
    VkImageLayout local_imageLayout;
    VkClearColorValue* local_pColor;
    uint32_t local_rangeCount;
    VkImageSubresourceRange* local_pRanges;
    local_commandBuffer = commandBuffer;
    local_image = image;
    local_imageLayout = imageLayout;
    local_pColor = nullptr;
    if (pColor) {
        local_pColor = (VkClearColorValue*)pool->alloc(sizeof(const VkClearColorValue));
        deepcopy_VkClearColorValue(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pColor,
                                   (VkClearColorValue*)(local_pColor));
    }
    local_rangeCount = rangeCount;
    local_pRanges = nullptr;
    if (pRanges) {
        local_pRanges = (VkImageSubresourceRange*)pool->alloc(
            ((rangeCount)) * sizeof(const VkImageSubresourceRange));
        for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
            deepcopy_VkImageSubresourceRange(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRanges + i,
                                             (VkImageSubresourceRange*)(local_pRanges + i));
        }
    }
    if (local_pColor) {
        transform_tohost_VkClearColorValue(sResourceTracker, (VkClearColorValue*)(local_pColor));
    }
    if (local_pRanges) {
        for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
            transform_tohost_VkImageSubresourceRange(sResourceTracker,
                                                     (VkImageSubresourceRange*)(local_pRanges + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        count_VkClearColorValue(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkClearColorValue*)(local_pColor), countPtr);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
            count_VkImageSubresourceRange(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkImageSubresourceRange*)(local_pRanges + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdClearColorImage = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdClearColorImage);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdClearColorImage -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdClearColorImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdClearColorImage = OP_vkCmdClearColorImage;
    memcpy(streamPtr, &opcode_vkCmdClearColorImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdClearColorImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_imageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    reservedmarshal_VkClearColorValue(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkClearColorValue*)(local_pColor), streamPtrPtr);
    memcpy(*streamPtrPtr, (uint32_t*)&local_rangeCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
        reservedmarshal_VkImageSubresourceRange(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkImageSubresourceRange*)(local_pRanges + i),
                                                streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdClearColorImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdClearDepthStencilImage(VkCommandBuffer commandBuffer, VkImage image,
                                            VkImageLayout imageLayout,
                                            const VkClearDepthStencilValue* pDepthStencil,
                                            uint32_t rangeCount,
                                            const VkImageSubresourceRange* pRanges,
                                            uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdClearDepthStencilImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdClearDepthStencilImage(commandBuffer:%p, image:%p, imageLayout:%d, pDepthStencil:%p, "
        "rangeCount:%d, pRanges:%p)",
        commandBuffer, image, imageLayout, pDepthStencil, rangeCount, pRanges);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkImage local_image;
    VkImageLayout local_imageLayout;
    VkClearDepthStencilValue* local_pDepthStencil;
    uint32_t local_rangeCount;
    VkImageSubresourceRange* local_pRanges;
    local_commandBuffer = commandBuffer;
    local_image = image;
    local_imageLayout = imageLayout;
    local_pDepthStencil = nullptr;
    if (pDepthStencil) {
        local_pDepthStencil =
            (VkClearDepthStencilValue*)pool->alloc(sizeof(const VkClearDepthStencilValue));
        deepcopy_VkClearDepthStencilValue(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDepthStencil,
                                          (VkClearDepthStencilValue*)(local_pDepthStencil));
    }
    local_rangeCount = rangeCount;
    local_pRanges = nullptr;
    if (pRanges) {
        local_pRanges = (VkImageSubresourceRange*)pool->alloc(
            ((rangeCount)) * sizeof(const VkImageSubresourceRange));
        for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
            deepcopy_VkImageSubresourceRange(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRanges + i,
                                             (VkImageSubresourceRange*)(local_pRanges + i));
        }
    }
    if (local_pDepthStencil) {
        transform_tohost_VkClearDepthStencilValue(sResourceTracker,
                                                  (VkClearDepthStencilValue*)(local_pDepthStencil));
    }
    if (local_pRanges) {
        for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
            transform_tohost_VkImageSubresourceRange(sResourceTracker,
                                                     (VkImageSubresourceRange*)(local_pRanges + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        count_VkClearDepthStencilValue(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkClearDepthStencilValue*)(local_pDepthStencil), countPtr);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
            count_VkImageSubresourceRange(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkImageSubresourceRange*)(local_pRanges + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdClearDepthStencilImage = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdClearDepthStencilImage);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdClearDepthStencilImage -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdClearDepthStencilImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdClearDepthStencilImage = OP_vkCmdClearDepthStencilImage;
    memcpy(streamPtr, &opcode_vkCmdClearDepthStencilImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdClearDepthStencilImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_imageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    reservedmarshal_VkClearDepthStencilValue(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkClearDepthStencilValue*)(local_pDepthStencil),
                                             streamPtrPtr);
    memcpy(*streamPtrPtr, (uint32_t*)&local_rangeCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((rangeCount)); ++i) {
        reservedmarshal_VkImageSubresourceRange(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkImageSubresourceRange*)(local_pRanges + i),
                                                streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdClearDepthStencilImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdClearAttachments(VkCommandBuffer commandBuffer, uint32_t attachmentCount,
                                      const VkClearAttachment* pAttachments, uint32_t rectCount,
                                      const VkClearRect* pRects, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdClearAttachments in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdClearAttachments(commandBuffer:%p, attachmentCount:%d, pAttachments:%p, "
        "rectCount:%d, pRects:%p)",
        commandBuffer, attachmentCount, pAttachments, rectCount, pRects);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_attachmentCount;
    VkClearAttachment* local_pAttachments;
    uint32_t local_rectCount;
    VkClearRect* local_pRects;
    local_commandBuffer = commandBuffer;
    local_attachmentCount = attachmentCount;
    local_pAttachments = nullptr;
    if (pAttachments) {
        local_pAttachments =
            (VkClearAttachment*)pool->alloc(((attachmentCount)) * sizeof(const VkClearAttachment));
        for (uint32_t i = 0; i < (uint32_t)((attachmentCount)); ++i) {
            deepcopy_VkClearAttachment(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAttachments + i,
                                       (VkClearAttachment*)(local_pAttachments + i));
        }
    }
    local_rectCount = rectCount;
    local_pRects = nullptr;
    if (pRects) {
        local_pRects = (VkClearRect*)pool->alloc(((rectCount)) * sizeof(const VkClearRect));
        for (uint32_t i = 0; i < (uint32_t)((rectCount)); ++i) {
            deepcopy_VkClearRect(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRects + i,
                                 (VkClearRect*)(local_pRects + i));
        }
    }
    if (local_pAttachments) {
        for (uint32_t i = 0; i < (uint32_t)((attachmentCount)); ++i) {
            transform_tohost_VkClearAttachment(sResourceTracker,
                                               (VkClearAttachment*)(local_pAttachments + i));
        }
    }
    if (local_pRects) {
        for (uint32_t i = 0; i < (uint32_t)((rectCount)); ++i) {
            transform_tohost_VkClearRect(sResourceTracker, (VkClearRect*)(local_pRects + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((attachmentCount)); ++i) {
            count_VkClearAttachment(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkClearAttachment*)(local_pAttachments + i), countPtr);
        }
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((rectCount)); ++i) {
            count_VkClearRect(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                              (VkClearRect*)(local_pRects + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdClearAttachments = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdClearAttachments);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdClearAttachments -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdClearAttachments);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdClearAttachments = OP_vkCmdClearAttachments;
    memcpy(streamPtr, &opcode_vkCmdClearAttachments, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdClearAttachments, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_attachmentCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((attachmentCount)); ++i) {
        reservedmarshal_VkClearAttachment(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkClearAttachment*)(local_pAttachments + i),
                                          streamPtrPtr);
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_rectCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((rectCount)); ++i) {
        reservedmarshal_VkClearRect(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkClearRect*)(local_pRects + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdClearAttachments), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdResolveImage(VkCommandBuffer commandBuffer, VkImage srcImage,
                                  VkImageLayout srcImageLayout, VkImage dstImage,
                                  VkImageLayout dstImageLayout, uint32_t regionCount,
                                  const VkImageResolve* pRegions, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdResolveImage in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdResolveImage(commandBuffer:%p, srcImage:%p, srcImageLayout:%d, dstImage:%p, "
        "dstImageLayout:%d, regionCount:%d, pRegions:%p)",
        commandBuffer, srcImage, srcImageLayout, dstImage, dstImageLayout, regionCount, pRegions);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkImage local_srcImage;
    VkImageLayout local_srcImageLayout;
    VkImage local_dstImage;
    VkImageLayout local_dstImageLayout;
    uint32_t local_regionCount;
    VkImageResolve* local_pRegions;
    local_commandBuffer = commandBuffer;
    local_srcImage = srcImage;
    local_srcImageLayout = srcImageLayout;
    local_dstImage = dstImage;
    local_dstImageLayout = dstImageLayout;
    local_regionCount = regionCount;
    local_pRegions = nullptr;
    if (pRegions) {
        local_pRegions =
            (VkImageResolve*)pool->alloc(((regionCount)) * sizeof(const VkImageResolve));
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            deepcopy_VkImageResolve(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRegions + i,
                                    (VkImageResolve*)(local_pRegions + i));
        }
    }
    if (local_pRegions) {
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            transform_tohost_VkImageResolve(sResourceTracker,
                                            (VkImageResolve*)(local_pRegions + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkImageLayout);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
            count_VkImageResolve(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkImageResolve*)(local_pRegions + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdResolveImage = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdResolveImage);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdResolveImage -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdResolveImage);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdResolveImage = OP_vkCmdResolveImage;
    memcpy(streamPtr, &opcode_vkCmdResolveImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdResolveImage, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkImage((*&local_srcImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_srcImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_dstImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkImageLayout*)&local_dstImageLayout, sizeof(VkImageLayout));
    *streamPtrPtr += sizeof(VkImageLayout);
    memcpy(*streamPtrPtr, (uint32_t*)&local_regionCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((regionCount)); ++i) {
        reservedmarshal_VkImageResolve(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageResolve*)(local_pRegions + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdResolveImage), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetEvent(VkCommandBuffer commandBuffer, VkEvent event,
                              VkPipelineStageFlags stageMask, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetEvent in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetEvent(commandBuffer:%p, event:%p, stageMask:%d)", commandBuffer,
                      event, stageMask);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkEvent local_event;
    VkPipelineStageFlags local_stageMask;
    local_commandBuffer = commandBuffer;
    local_event = event;
    local_stageMask = stageMask;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags);
    }
    uint32_t packetSize_vkCmdSetEvent = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetEvent);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetEvent -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetEvent);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetEvent = OP_vkCmdSetEvent;
    memcpy(streamPtr, &opcode_vkCmdSetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkPipelineStageFlags*)&local_stageMask, sizeof(VkPipelineStageFlags));
    *streamPtrPtr += sizeof(VkPipelineStageFlags);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetEvent), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdResetEvent(VkCommandBuffer commandBuffer, VkEvent event,
                                VkPipelineStageFlags stageMask, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdResetEvent in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdResetEvent(commandBuffer:%p, event:%p, stageMask:%d)", commandBuffer,
                      event, stageMask);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkEvent local_event;
    VkPipelineStageFlags local_stageMask;
    local_commandBuffer = commandBuffer;
    local_event = event;
    local_stageMask = stageMask;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags);
    }
    uint32_t packetSize_vkCmdResetEvent = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdResetEvent);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdResetEvent -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdResetEvent);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdResetEvent = OP_vkCmdResetEvent;
    memcpy(streamPtr, &opcode_vkCmdResetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdResetEvent, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkPipelineStageFlags*)&local_stageMask, sizeof(VkPipelineStageFlags));
    *streamPtrPtr += sizeof(VkPipelineStageFlags);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdResetEvent), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdWaitEvents(VkCommandBuffer commandBuffer, uint32_t eventCount,
                                const VkEvent* pEvents, VkPipelineStageFlags srcStageMask,
                                VkPipelineStageFlags dstStageMask, uint32_t memoryBarrierCount,
                                const VkMemoryBarrier* pMemoryBarriers,
                                uint32_t bufferMemoryBarrierCount,
                                const VkBufferMemoryBarrier* pBufferMemoryBarriers,
                                uint32_t imageMemoryBarrierCount,
                                const VkImageMemoryBarrier* pImageMemoryBarriers, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdWaitEvents in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdWaitEvents(commandBuffer:%p, eventCount:%d, pEvents:%p, srcStageMask:%d, "
        "dstStageMask:%d, memoryBarrierCount:%d, pMemoryBarriers:%p, bufferMemoryBarrierCount:%d, "
        "pBufferMemoryBarriers:%p, imageMemoryBarrierCount:%d, pImageMemoryBarriers:%p)",
        commandBuffer, eventCount, pEvents, srcStageMask, dstStageMask, memoryBarrierCount,
        pMemoryBarriers, bufferMemoryBarrierCount, pBufferMemoryBarriers, imageMemoryBarrierCount,
        pImageMemoryBarriers);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_eventCount;
    VkEvent* local_pEvents;
    VkPipelineStageFlags local_srcStageMask;
    VkPipelineStageFlags local_dstStageMask;
    uint32_t local_memoryBarrierCount;
    VkMemoryBarrier* local_pMemoryBarriers;
    uint32_t local_bufferMemoryBarrierCount;
    VkBufferMemoryBarrier* local_pBufferMemoryBarriers;
    uint32_t local_imageMemoryBarrierCount;
    VkImageMemoryBarrier* local_pImageMemoryBarriers;
    local_commandBuffer = commandBuffer;
    local_eventCount = eventCount;
    // Avoiding deepcopy for pEvents
    local_pEvents = (VkEvent*)pEvents;
    local_srcStageMask = srcStageMask;
    local_dstStageMask = dstStageMask;
    local_memoryBarrierCount = memoryBarrierCount;
    local_pMemoryBarriers = nullptr;
    if (pMemoryBarriers) {
        local_pMemoryBarriers =
            (VkMemoryBarrier*)pool->alloc(((memoryBarrierCount)) * sizeof(const VkMemoryBarrier));
        for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
            deepcopy_VkMemoryBarrier(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pMemoryBarriers + i,
                                     (VkMemoryBarrier*)(local_pMemoryBarriers + i));
        }
    }
    local_bufferMemoryBarrierCount = bufferMemoryBarrierCount;
    local_pBufferMemoryBarriers = nullptr;
    if (pBufferMemoryBarriers) {
        local_pBufferMemoryBarriers = (VkBufferMemoryBarrier*)pool->alloc(
            ((bufferMemoryBarrierCount)) * sizeof(const VkBufferMemoryBarrier));
        for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
            deepcopy_VkBufferMemoryBarrier(
                pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBufferMemoryBarriers + i,
                (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i));
        }
    }
    local_imageMemoryBarrierCount = imageMemoryBarrierCount;
    local_pImageMemoryBarriers = nullptr;
    if (pImageMemoryBarriers) {
        local_pImageMemoryBarriers = (VkImageMemoryBarrier*)pool->alloc(
            ((imageMemoryBarrierCount)) * sizeof(const VkImageMemoryBarrier));
        for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
            deepcopy_VkImageMemoryBarrier(pool, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          pImageMemoryBarriers + i,
                                          (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i));
        }
    }
    if (local_pMemoryBarriers) {
        for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
            transform_tohost_VkMemoryBarrier(sResourceTracker,
                                             (VkMemoryBarrier*)(local_pMemoryBarriers + i));
        }
    }
    if (local_pBufferMemoryBarriers) {
        for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
            transform_tohost_VkBufferMemoryBarrier(
                sResourceTracker, (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i));
        }
    }
    if (local_pImageMemoryBarriers) {
        for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
            transform_tohost_VkImageMemoryBarrier(
                sResourceTracker, (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((eventCount))) {
            *countPtr += ((eventCount)) * 8;
        }
        *countPtr += sizeof(VkPipelineStageFlags);
        *countPtr += sizeof(VkPipelineStageFlags);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
            count_VkMemoryBarrier(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkMemoryBarrier*)(local_pMemoryBarriers + i), countPtr);
        }
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
            count_VkBufferMemoryBarrier(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i),
                                        countPtr);
        }
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
            count_VkImageMemoryBarrier(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i),
                                       countPtr);
        }
    }
    uint32_t packetSize_vkCmdWaitEvents = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdWaitEvents);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdWaitEvents -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdWaitEvents);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdWaitEvents = OP_vkCmdWaitEvents;
    memcpy(streamPtr, &opcode_vkCmdWaitEvents, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdWaitEvents, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_eventCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((eventCount))) {
        uint8_t* cgen_var_0_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((eventCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkEvent(local_pEvents[k]);
            memcpy(cgen_var_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((eventCount));
    }
    memcpy(*streamPtrPtr, (VkPipelineStageFlags*)&local_srcStageMask, sizeof(VkPipelineStageFlags));
    *streamPtrPtr += sizeof(VkPipelineStageFlags);
    memcpy(*streamPtrPtr, (VkPipelineStageFlags*)&local_dstStageMask, sizeof(VkPipelineStageFlags));
    *streamPtrPtr += sizeof(VkPipelineStageFlags);
    memcpy(*streamPtrPtr, (uint32_t*)&local_memoryBarrierCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
        reservedmarshal_VkMemoryBarrier(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkMemoryBarrier*)(local_pMemoryBarriers + i),
                                        streamPtrPtr);
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_bufferMemoryBarrierCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
        reservedmarshal_VkBufferMemoryBarrier(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i), streamPtrPtr);
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_imageMemoryBarrierCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
        reservedmarshal_VkImageMemoryBarrier(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdWaitEvents), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdPipelineBarrier(
    VkCommandBuffer commandBuffer, VkPipelineStageFlags srcStageMask,
    VkPipelineStageFlags dstStageMask, VkDependencyFlags dependencyFlags,
    uint32_t memoryBarrierCount, const VkMemoryBarrier* pMemoryBarriers,
    uint32_t bufferMemoryBarrierCount, const VkBufferMemoryBarrier* pBufferMemoryBarriers,
    uint32_t imageMemoryBarrierCount, const VkImageMemoryBarrier* pImageMemoryBarriers,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdPipelineBarrier in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdPipelineBarrier(commandBuffer:%p, srcStageMask:%d, dstStageMask:%d, "
        "dependencyFlags:%d, memoryBarrierCount:%d, pMemoryBarriers:%p, "
        "bufferMemoryBarrierCount:%d, pBufferMemoryBarriers:%p, imageMemoryBarrierCount:%d, "
        "pImageMemoryBarriers:%p)",
        commandBuffer, srcStageMask, dstStageMask, dependencyFlags, memoryBarrierCount,
        pMemoryBarriers, bufferMemoryBarrierCount, pBufferMemoryBarriers, imageMemoryBarrierCount,
        pImageMemoryBarriers);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineStageFlags local_srcStageMask;
    VkPipelineStageFlags local_dstStageMask;
    VkDependencyFlags local_dependencyFlags;
    uint32_t local_memoryBarrierCount;
    VkMemoryBarrier* local_pMemoryBarriers;
    uint32_t local_bufferMemoryBarrierCount;
    VkBufferMemoryBarrier* local_pBufferMemoryBarriers;
    uint32_t local_imageMemoryBarrierCount;
    VkImageMemoryBarrier* local_pImageMemoryBarriers;
    local_commandBuffer = commandBuffer;
    local_srcStageMask = srcStageMask;
    local_dstStageMask = dstStageMask;
    local_dependencyFlags = dependencyFlags;
    local_memoryBarrierCount = memoryBarrierCount;
    local_pMemoryBarriers = nullptr;
    if (pMemoryBarriers) {
        local_pMemoryBarriers =
            (VkMemoryBarrier*)pool->alloc(((memoryBarrierCount)) * sizeof(const VkMemoryBarrier));
        for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
            deepcopy_VkMemoryBarrier(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pMemoryBarriers + i,
                                     (VkMemoryBarrier*)(local_pMemoryBarriers + i));
        }
    }
    local_bufferMemoryBarrierCount = bufferMemoryBarrierCount;
    local_pBufferMemoryBarriers = nullptr;
    if (pBufferMemoryBarriers) {
        local_pBufferMemoryBarriers = (VkBufferMemoryBarrier*)pool->alloc(
            ((bufferMemoryBarrierCount)) * sizeof(const VkBufferMemoryBarrier));
        for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
            deepcopy_VkBufferMemoryBarrier(
                pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBufferMemoryBarriers + i,
                (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i));
        }
    }
    local_imageMemoryBarrierCount = imageMemoryBarrierCount;
    local_pImageMemoryBarriers = nullptr;
    if (pImageMemoryBarriers) {
        local_pImageMemoryBarriers = (VkImageMemoryBarrier*)pool->alloc(
            ((imageMemoryBarrierCount)) * sizeof(const VkImageMemoryBarrier));
        for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
            deepcopy_VkImageMemoryBarrier(pool, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          pImageMemoryBarriers + i,
                                          (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i));
        }
    }
    if (local_pMemoryBarriers) {
        for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
            transform_tohost_VkMemoryBarrier(sResourceTracker,
                                             (VkMemoryBarrier*)(local_pMemoryBarriers + i));
        }
    }
    if (local_pBufferMemoryBarriers) {
        for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
            transform_tohost_VkBufferMemoryBarrier(
                sResourceTracker, (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i));
        }
    }
    if (local_pImageMemoryBarriers) {
        for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
            transform_tohost_VkImageMemoryBarrier(
                sResourceTracker, (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags);
        *countPtr += sizeof(VkPipelineStageFlags);
        *countPtr += sizeof(VkDependencyFlags);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
            count_VkMemoryBarrier(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkMemoryBarrier*)(local_pMemoryBarriers + i), countPtr);
        }
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
            count_VkBufferMemoryBarrier(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i),
                                        countPtr);
        }
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
            count_VkImageMemoryBarrier(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i),
                                       countPtr);
        }
    }
    uint32_t packetSize_vkCmdPipelineBarrier = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdPipelineBarrier);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdPipelineBarrier -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdPipelineBarrier);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdPipelineBarrier = OP_vkCmdPipelineBarrier;
    memcpy(streamPtr, &opcode_vkCmdPipelineBarrier, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdPipelineBarrier, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPipelineStageFlags*)&local_srcStageMask, sizeof(VkPipelineStageFlags));
    *streamPtrPtr += sizeof(VkPipelineStageFlags);
    memcpy(*streamPtrPtr, (VkPipelineStageFlags*)&local_dstStageMask, sizeof(VkPipelineStageFlags));
    *streamPtrPtr += sizeof(VkPipelineStageFlags);
    memcpy(*streamPtrPtr, (VkDependencyFlags*)&local_dependencyFlags, sizeof(VkDependencyFlags));
    *streamPtrPtr += sizeof(VkDependencyFlags);
    memcpy(*streamPtrPtr, (uint32_t*)&local_memoryBarrierCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((memoryBarrierCount)); ++i) {
        reservedmarshal_VkMemoryBarrier(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkMemoryBarrier*)(local_pMemoryBarriers + i),
                                        streamPtrPtr);
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_bufferMemoryBarrierCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bufferMemoryBarrierCount)); ++i) {
        reservedmarshal_VkBufferMemoryBarrier(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkBufferMemoryBarrier*)(local_pBufferMemoryBarriers + i), streamPtrPtr);
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_imageMemoryBarrierCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((imageMemoryBarrierCount)); ++i) {
        reservedmarshal_VkImageMemoryBarrier(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkImageMemoryBarrier*)(local_pImageMemoryBarriers + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdPipelineBarrier), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBeginQuery(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
                                uint32_t query, VkQueryControlFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginQuery in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBeginQuery(commandBuffer:%p, queryPool:%p, query:%d, flags:%d)",
                      commandBuffer, queryPool, query, flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkQueryPool local_queryPool;
    uint32_t local_query;
    VkQueryControlFlags local_flags;
    local_commandBuffer = commandBuffer;
    local_queryPool = queryPool;
    local_query = query;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(VkQueryControlFlags);
    }
    uint32_t packetSize_vkCmdBeginQuery = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBeginQuery);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginQuery -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginQuery);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginQuery = OP_vkCmdBeginQuery;
    memcpy(streamPtr, &opcode_vkCmdBeginQuery, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginQuery, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_query, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (VkQueryControlFlags*)&local_flags, sizeof(VkQueryControlFlags));
    *streamPtrPtr += sizeof(VkQueryControlFlags);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdBeginQuery), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndQuery(VkCommandBuffer commandBuffer, VkQueryPool queryPool, uint32_t query,
                              uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndQuery in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdEndQuery(commandBuffer:%p, queryPool:%p, query:%d)", commandBuffer,
                      queryPool, query);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkQueryPool local_queryPool;
    uint32_t local_query;
    local_commandBuffer = commandBuffer;
    local_queryPool = queryPool;
    local_query = query;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdEndQuery = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdEndQuery);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndQuery -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndQuery);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndQuery = OP_vkCmdEndQuery;
    memcpy(streamPtr, &opcode_vkCmdEndQuery, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndQuery, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_query, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdEndQuery), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdResetQueryPool(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
                                    uint32_t firstQuery, uint32_t queryCount, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdResetQueryPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdResetQueryPool(commandBuffer:%p, queryPool:%p, firstQuery:%d, queryCount:%d)",
        commandBuffer, queryPool, firstQuery, queryCount);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkQueryPool local_queryPool;
    uint32_t local_firstQuery;
    uint32_t local_queryCount;
    local_commandBuffer = commandBuffer;
    local_queryPool = queryPool;
    local_firstQuery = firstQuery;
    local_queryCount = queryCount;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdResetQueryPool = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdResetQueryPool);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdResetQueryPool -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdResetQueryPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdResetQueryPool = OP_vkCmdResetQueryPool;
    memcpy(streamPtr, &opcode_vkCmdResetQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdResetQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstQuery, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_queryCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdResetQueryPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdWriteTimestamp(VkCommandBuffer commandBuffer,
                                    VkPipelineStageFlagBits pipelineStage, VkQueryPool queryPool,
                                    uint32_t query, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdWriteTimestamp in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdWriteTimestamp(commandBuffer:%p, queryPool:%p, query:%d)",
                      commandBuffer, queryPool, query);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineStageFlagBits local_pipelineStage;
    VkQueryPool local_queryPool;
    uint32_t local_query;
    local_commandBuffer = commandBuffer;
    local_pipelineStage = pipelineStage;
    local_queryPool = queryPool;
    local_query = query;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlagBits);
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdWriteTimestamp = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdWriteTimestamp);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdWriteTimestamp -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdWriteTimestamp);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdWriteTimestamp = OP_vkCmdWriteTimestamp;
    memcpy(streamPtr, &opcode_vkCmdWriteTimestamp, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdWriteTimestamp, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPipelineStageFlagBits*)&local_pipelineStage,
           sizeof(VkPipelineStageFlagBits));
    *streamPtrPtr += sizeof(VkPipelineStageFlagBits);
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_query, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdWriteTimestamp), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyQueryPoolResults(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
                                          uint32_t firstQuery, uint32_t queryCount,
                                          VkBuffer dstBuffer, VkDeviceSize dstOffset,
                                          VkDeviceSize stride, VkQueryResultFlags flags,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyQueryPoolResults in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdCopyQueryPoolResults(commandBuffer:%p, queryPool:%p, firstQuery:%d, queryCount:%d, "
        "dstBuffer:%p, dstOffset:%ld, stride:%ld, flags:%d)",
        commandBuffer, queryPool, firstQuery, queryCount, dstBuffer, dstOffset, stride, flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkQueryPool local_queryPool;
    uint32_t local_firstQuery;
    uint32_t local_queryCount;
    VkBuffer local_dstBuffer;
    VkDeviceSize local_dstOffset;
    VkDeviceSize local_stride;
    VkQueryResultFlags local_flags;
    local_commandBuffer = commandBuffer;
    local_queryPool = queryPool;
    local_firstQuery = firstQuery;
    local_queryCount = queryCount;
    local_dstBuffer = dstBuffer;
    local_dstOffset = dstOffset;
    local_stride = stride;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkQueryResultFlags);
    }
    uint32_t packetSize_vkCmdCopyQueryPoolResults = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyQueryPoolResults);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyQueryPoolResults -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyQueryPoolResults);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyQueryPoolResults = OP_vkCmdCopyQueryPoolResults;
    memcpy(streamPtr, &opcode_vkCmdCopyQueryPoolResults, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyQueryPoolResults, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstQuery, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_queryCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_dstBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_dstOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_stride, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkQueryResultFlags*)&local_flags, sizeof(VkQueryResultFlags));
    *streamPtrPtr += sizeof(VkQueryResultFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyQueryPoolResults), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdPushConstants(VkCommandBuffer commandBuffer, VkPipelineLayout layout,
                                   VkShaderStageFlags stageFlags, uint32_t offset, uint32_t size,
                                   const void* pValues, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdPushConstants in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdPushConstants(commandBuffer:%p, layout:%p, stageFlags:%d, offset:%d, size:%d, "
        "pValues:%p)",
        commandBuffer, layout, stageFlags, offset, size, pValues);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineLayout local_layout;
    VkShaderStageFlags local_stageFlags;
    uint32_t local_offset;
    uint32_t local_size;
    void* local_pValues;
    local_commandBuffer = commandBuffer;
    local_layout = layout;
    local_stageFlags = stageFlags;
    local_offset = offset;
    local_size = size;
    // Avoiding deepcopy for pValues
    local_pValues = (void*)pValues;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkShaderStageFlags);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += ((size)) * sizeof(uint8_t);
    }
    uint32_t packetSize_vkCmdPushConstants = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdPushConstants);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdPushConstants -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdPushConstants);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdPushConstants = OP_vkCmdPushConstants;
    memcpy(streamPtr, &opcode_vkCmdPushConstants, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdPushConstants, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPipelineLayout((*&local_layout));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkShaderStageFlags*)&local_stageFlags, sizeof(VkShaderStageFlags));
    *streamPtrPtr += sizeof(VkShaderStageFlags);
    memcpy(*streamPtrPtr, (uint32_t*)&local_offset, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_size, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (void*)local_pValues, ((size)) * sizeof(uint8_t));
    *streamPtrPtr += ((size)) * sizeof(uint8_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdPushConstants), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBeginRenderPass(VkCommandBuffer commandBuffer,
                                     const VkRenderPassBeginInfo* pRenderPassBegin,
                                     VkSubpassContents contents, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginRenderPass in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBeginRenderPass(commandBuffer:%p, pRenderPassBegin:%p)", commandBuffer,
                      pRenderPassBegin);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkRenderPassBeginInfo* local_pRenderPassBegin;
    VkSubpassContents local_contents;
    local_commandBuffer = commandBuffer;
    local_pRenderPassBegin = nullptr;
    if (pRenderPassBegin) {
        local_pRenderPassBegin =
            (VkRenderPassBeginInfo*)pool->alloc(sizeof(const VkRenderPassBeginInfo));
        deepcopy_VkRenderPassBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRenderPassBegin,
                                       (VkRenderPassBeginInfo*)(local_pRenderPassBegin));
    }
    local_contents = contents;
    if (local_pRenderPassBegin) {
        transform_tohost_VkRenderPassBeginInfo(sResourceTracker,
                                               (VkRenderPassBeginInfo*)(local_pRenderPassBegin));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderPassBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkRenderPassBeginInfo*)(local_pRenderPassBegin), countPtr);
        *countPtr += sizeof(VkSubpassContents);
    }
    uint32_t packetSize_vkCmdBeginRenderPass = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBeginRenderPass);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginRenderPass -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginRenderPass);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginRenderPass = OP_vkCmdBeginRenderPass;
    memcpy(streamPtr, &opcode_vkCmdBeginRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkRenderPassBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkRenderPassBeginInfo*)(local_pRenderPassBegin),
                                          streamPtrPtr);
    memcpy(*streamPtrPtr, (VkSubpassContents*)&local_contents, sizeof(VkSubpassContents));
    *streamPtrPtr += sizeof(VkSubpassContents);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBeginRenderPass), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdNextSubpass(VkCommandBuffer commandBuffer, VkSubpassContents contents,
                                 uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdNextSubpass in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdNextSubpass(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkSubpassContents local_contents;
    local_commandBuffer = commandBuffer;
    local_contents = contents;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkSubpassContents);
    }
    uint32_t packetSize_vkCmdNextSubpass = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdNextSubpass);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdNextSubpass -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdNextSubpass);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdNextSubpass = OP_vkCmdNextSubpass;
    memcpy(streamPtr, &opcode_vkCmdNextSubpass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdNextSubpass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkSubpassContents*)&local_contents, sizeof(VkSubpassContents));
    *streamPtrPtr += sizeof(VkSubpassContents);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdNextSubpass), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndRenderPass(VkCommandBuffer commandBuffer, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndRenderPass in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdEndRenderPass(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    local_commandBuffer = commandBuffer;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkCmdEndRenderPass = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdEndRenderPass);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndRenderPass -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndRenderPass);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndRenderPass = OP_vkCmdEndRenderPass;
    memcpy(streamPtr, &opcode_vkCmdEndRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndRenderPass, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdEndRenderPass), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdExecuteCommands(VkCommandBuffer commandBuffer, uint32_t commandBufferCount,
                                     const VkCommandBuffer* pCommandBuffers, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdExecuteCommands in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdExecuteCommands(commandBuffer:%p, commandBufferCount:%d, pCommandBuffers:%p)",
        commandBuffer, commandBufferCount, pCommandBuffers);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_commandBufferCount;
    VkCommandBuffer* local_pCommandBuffers;
    local_commandBuffer = commandBuffer;
    local_commandBufferCount = commandBufferCount;
    // Avoiding deepcopy for pCommandBuffers
    local_pCommandBuffers = (VkCommandBuffer*)pCommandBuffers;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((commandBufferCount))) {
            *countPtr += ((commandBufferCount)) * 8;
        }
    }
    uint32_t packetSize_vkCmdExecuteCommands = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdExecuteCommands);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdExecuteCommands -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdExecuteCommands);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdExecuteCommands = OP_vkCmdExecuteCommands;
    memcpy(streamPtr, &opcode_vkCmdExecuteCommands, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdExecuteCommands, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_commandBufferCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((commandBufferCount))) {
        uint8_t* cgen_var_0_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((commandBufferCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkCommandBuffer(local_pCommandBuffers[k]);
            memcpy(cgen_var_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((commandBufferCount));
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdExecuteCommands), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_VERSION_1_1
VkResult VkEncoder::vkEnumerateInstanceVersion(uint32_t* pApiVersion, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEnumerateInstanceVersion in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkEnumerateInstanceVersion(pApiVersion:%p)", pApiVersion);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    size_t count = 0;
    size_t* countPtr = &count;
    { *countPtr += sizeof(uint32_t); }
    uint32_t packetSize_vkEnumerateInstanceVersion =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkEnumerateInstanceVersion);
    uint8_t* streamPtr = stream->reserve(packetSize_vkEnumerateInstanceVersion);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEnumerateInstanceVersion = OP_vkEnumerateInstanceVersion;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkEnumerateInstanceVersion, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEnumerateInstanceVersion, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    memcpy(*streamPtrPtr, (uint32_t*)pApiVersion, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkEnumerateInstanceVersion), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((uint32_t*)pApiVersion, sizeof(uint32_t));
    VkResult vkEnumerateInstanceVersion_VkResult_return = (VkResult)0;
    stream->read(&vkEnumerateInstanceVersion_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEnumerateInstanceVersion_VkResult_return;
}

VkResult VkEncoder::vkBindBufferMemory2(VkDevice device, uint32_t bindInfoCount,
                                        const VkBindBufferMemoryInfo* pBindInfos, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBindBufferMemory2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkBindBufferMemory2(device:%p, bindInfoCount:%d, pBindInfos:%p)", device,
                      bindInfoCount, pBindInfos);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_bindInfoCount;
    VkBindBufferMemoryInfo* local_pBindInfos;
    local_device = device;
    local_bindInfoCount = bindInfoCount;
    local_pBindInfos = nullptr;
    if (pBindInfos) {
        local_pBindInfos = (VkBindBufferMemoryInfo*)pool->alloc(
            ((bindInfoCount)) * sizeof(const VkBindBufferMemoryInfo));
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            deepcopy_VkBindBufferMemoryInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBindInfos + i,
                                            (VkBindBufferMemoryInfo*)(local_pBindInfos + i));
        }
    }
    if (local_pBindInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            transform_tohost_VkBindBufferMemoryInfo(
                sResourceTracker, (VkBindBufferMemoryInfo*)(local_pBindInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            count_VkBindBufferMemoryInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkBindBufferMemoryInfo*)(local_pBindInfos + i), countPtr);
        }
    }
    uint32_t packetSize_vkBindBufferMemory2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkBindBufferMemory2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkBindBufferMemory2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBindBufferMemory2 = OP_vkBindBufferMemory2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkBindBufferMemory2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBindBufferMemory2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
        reservedmarshal_VkBindBufferMemoryInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                               (VkBindBufferMemoryInfo*)(local_pBindInfos + i),
                                               streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkBindBufferMemory2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkBindBufferMemory2_VkResult_return = (VkResult)0;
    stream->read(&vkBindBufferMemory2_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkBindBufferMemory2_VkResult_return;
}

VkResult VkEncoder::vkBindImageMemory2(VkDevice device, uint32_t bindInfoCount,
                                       const VkBindImageMemoryInfo* pBindInfos, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBindImageMemory2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_bindInfoCount;
    VkBindImageMemoryInfo* local_pBindInfos;
    local_device = device;
    local_bindInfoCount = bindInfoCount;
    local_pBindInfos = nullptr;
    if (pBindInfos) {
        local_pBindInfos = (VkBindImageMemoryInfo*)pool->alloc(((bindInfoCount)) *
                                                               sizeof(const VkBindImageMemoryInfo));
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            deepcopy_VkBindImageMemoryInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBindInfos + i,
                                           (VkBindImageMemoryInfo*)(local_pBindInfos + i));
        }
    }
    sResourceTracker->unwrap_VkBindImageMemory2_pBindInfos(bindInfoCount, pBindInfos,
                                                           local_pBindInfos);
    if (local_pBindInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            transform_tohost_VkBindImageMemoryInfo(sResourceTracker,
                                                   (VkBindImageMemoryInfo*)(local_pBindInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            count_VkBindImageMemoryInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBindImageMemoryInfo*)(local_pBindInfos + i), countPtr);
        }
    }
    uint32_t packetSize_vkBindImageMemory2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkBindImageMemory2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkBindImageMemory2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBindImageMemory2 = OP_vkBindImageMemory2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkBindImageMemory2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBindImageMemory2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
        reservedmarshal_VkBindImageMemoryInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBindImageMemoryInfo*)(local_pBindInfos + i),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkBindImageMemory2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkBindImageMemory2_VkResult_return = (VkResult)0;
    stream->read(&vkBindImageMemory2_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkBindImageMemory2_VkResult_return;
}

void VkEncoder::vkGetDeviceGroupPeerMemoryFeatures(VkDevice device, uint32_t heapIndex,
                                                   uint32_t localDeviceIndex,
                                                   uint32_t remoteDeviceIndex,
                                                   VkPeerMemoryFeatureFlags* pPeerMemoryFeatures,
                                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceGroupPeerMemoryFeatures in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceGroupPeerMemoryFeatures(device:%p, heapIndex:%d, localDeviceIndex:%d, "
        "remoteDeviceIndex:%d, pPeerMemoryFeatures:%p)",
        device, heapIndex, localDeviceIndex, remoteDeviceIndex, pPeerMemoryFeatures);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_heapIndex;
    uint32_t local_localDeviceIndex;
    uint32_t local_remoteDeviceIndex;
    local_device = device;
    local_heapIndex = heapIndex;
    local_localDeviceIndex = localDeviceIndex;
    local_remoteDeviceIndex = remoteDeviceIndex;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(VkPeerMemoryFeatureFlags);
    }
    uint32_t packetSize_vkGetDeviceGroupPeerMemoryFeatures =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceGroupPeerMemoryFeatures);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceGroupPeerMemoryFeatures);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceGroupPeerMemoryFeatures = OP_vkGetDeviceGroupPeerMemoryFeatures;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceGroupPeerMemoryFeatures, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceGroupPeerMemoryFeatures, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_heapIndex, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_localDeviceIndex, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_remoteDeviceIndex, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (VkPeerMemoryFeatureFlags*)pPeerMemoryFeatures,
           sizeof(VkPeerMemoryFeatureFlags));
    *streamPtrPtr += sizeof(VkPeerMemoryFeatureFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDeviceGroupPeerMemoryFeatures), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((VkPeerMemoryFeatureFlags*)pPeerMemoryFeatures, sizeof(VkPeerMemoryFeatureFlags));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDeviceMask(VkCommandBuffer commandBuffer, uint32_t deviceMask,
                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDeviceMask in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDeviceMask(commandBuffer:%p, deviceMask:%d)", commandBuffer,
                      deviceMask);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_deviceMask;
    local_commandBuffer = commandBuffer;
    local_deviceMask = deviceMask;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdSetDeviceMask = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDeviceMask);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDeviceMask -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDeviceMask);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDeviceMask = OP_vkCmdSetDeviceMask;
    memcpy(streamPtr, &opcode_vkCmdSetDeviceMask, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDeviceMask, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_deviceMask, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDeviceMask), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDispatchBase(VkCommandBuffer commandBuffer, uint32_t baseGroupX,
                                  uint32_t baseGroupY, uint32_t baseGroupZ, uint32_t groupCountX,
                                  uint32_t groupCountY, uint32_t groupCountZ, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDispatchBase in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDispatchBase(commandBuffer:%p, baseGroupX:%d, baseGroupY:%d, baseGroupZ:%d, "
        "groupCountX:%d, groupCountY:%d, groupCountZ:%d)",
        commandBuffer, baseGroupX, baseGroupY, baseGroupZ, groupCountX, groupCountY, groupCountZ);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_baseGroupX;
    uint32_t local_baseGroupY;
    uint32_t local_baseGroupZ;
    uint32_t local_groupCountX;
    uint32_t local_groupCountY;
    uint32_t local_groupCountZ;
    local_commandBuffer = commandBuffer;
    local_baseGroupX = baseGroupX;
    local_baseGroupY = baseGroupY;
    local_baseGroupZ = baseGroupZ;
    local_groupCountX = groupCountX;
    local_groupCountY = groupCountY;
    local_groupCountZ = groupCountZ;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDispatchBase = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDispatchBase);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDispatchBase -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDispatchBase);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDispatchBase = OP_vkCmdDispatchBase;
    memcpy(streamPtr, &opcode_vkCmdDispatchBase, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDispatchBase, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_baseGroupX, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_baseGroupY, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_baseGroupZ, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_groupCountX, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_groupCountY, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_groupCountZ, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdDispatchBase), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkEnumeratePhysicalDeviceGroups(
    VkInstance instance, uint32_t* pPhysicalDeviceGroupCount,
    VkPhysicalDeviceGroupProperties* pPhysicalDeviceGroupProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEnumeratePhysicalDeviceGroups in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkEnumeratePhysicalDeviceGroups(instance:%p, pPhysicalDeviceGroupCount:%p, "
        "pPhysicalDeviceGroupProperties:%p)",
        instance, pPhysicalDeviceGroupCount, pPhysicalDeviceGroupProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkInstance local_instance;
    local_instance = instance;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPhysicalDeviceGroupCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPhysicalDeviceGroupProperties) {
            if (pPhysicalDeviceGroupCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPhysicalDeviceGroupCount)); ++i) {
                    count_VkPhysicalDeviceGroupProperties(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkPhysicalDeviceGroupProperties*)(pPhysicalDeviceGroupProperties + i),
                        countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkEnumeratePhysicalDeviceGroups =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkEnumeratePhysicalDeviceGroups);
    uint8_t* streamPtr = stream->reserve(packetSize_vkEnumeratePhysicalDeviceGroups);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEnumeratePhysicalDeviceGroups = OP_vkEnumeratePhysicalDeviceGroups;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkEnumeratePhysicalDeviceGroups, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEnumeratePhysicalDeviceGroups, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkInstance((*&local_instance));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pPhysicalDeviceGroupCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPhysicalDeviceGroupCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPhysicalDeviceGroupCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pPhysicalDeviceGroupProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPhysicalDeviceGroupProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPhysicalDeviceGroupCount)); ++i) {
            reservedmarshal_VkPhysicalDeviceGroupProperties(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkPhysicalDeviceGroupProperties*)(pPhysicalDeviceGroupProperties + i),
                streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkEnumeratePhysicalDeviceGroups), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPhysicalDeviceGroupCount;
    check_pPhysicalDeviceGroupCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPhysicalDeviceGroupCount) {
        if (!(check_pPhysicalDeviceGroupCount)) {
            fprintf(stderr,
                    "fatal: pPhysicalDeviceGroupCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPhysicalDeviceGroupCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkPhysicalDeviceGroupProperties* check_pPhysicalDeviceGroupProperties;
    check_pPhysicalDeviceGroupProperties =
        (VkPhysicalDeviceGroupProperties*)(uintptr_t)stream->getBe64();
    if (pPhysicalDeviceGroupProperties) {
        if (!(check_pPhysicalDeviceGroupProperties)) {
            fprintf(stderr,
                    "fatal: pPhysicalDeviceGroupProperties inconsistent between guest and host\n");
        }
        if (pPhysicalDeviceGroupCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPhysicalDeviceGroupCount)); ++i) {
                unmarshal_VkPhysicalDeviceGroupProperties(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkPhysicalDeviceGroupProperties*)(pPhysicalDeviceGroupProperties + i));
            }
        }
    }
    if (pPhysicalDeviceGroupCount) {
        if (pPhysicalDeviceGroupProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPhysicalDeviceGroupCount)); ++i) {
                transform_fromhost_VkPhysicalDeviceGroupProperties(
                    sResourceTracker,
                    (VkPhysicalDeviceGroupProperties*)(pPhysicalDeviceGroupProperties + i));
            }
        }
    }
    VkResult vkEnumeratePhysicalDeviceGroups_VkResult_return = (VkResult)0;
    stream->read(&vkEnumeratePhysicalDeviceGroups_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkEnumeratePhysicalDeviceGroups_VkResult_return;
}

void VkEncoder::vkGetImageMemoryRequirements2(VkDevice device,
                                              const VkImageMemoryRequirementsInfo2* pInfo,
                                              VkMemoryRequirements2* pMemoryRequirements,
                                              uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageMemoryRequirements2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetImageMemoryRequirements2(device:%p, pInfo:%p, pMemoryRequirements:%p)",
                      device, pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageMemoryRequirementsInfo2* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkImageMemoryRequirementsInfo2*)pool->alloc(
            sizeof(const VkImageMemoryRequirementsInfo2));
        deepcopy_VkImageMemoryRequirementsInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                (VkImageMemoryRequirementsInfo2*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkImageMemoryRequirementsInfo2(
            sResourceTracker, (VkImageMemoryRequirementsInfo2*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageMemoryRequirementsInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkImageMemoryRequirementsInfo2*)(local_pInfo),
                                             countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetImageMemoryRequirements2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageMemoryRequirements2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageMemoryRequirements2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageMemoryRequirements2 = OP_vkGetImageMemoryRequirements2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageMemoryRequirements2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageMemoryRequirements2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageMemoryRequirementsInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                   (VkImageMemoryRequirementsInfo2*)(local_pInfo),
                                                   streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetImageMemoryRequirements2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetBufferMemoryRequirements2(VkDevice device,
                                               const VkBufferMemoryRequirementsInfo2* pInfo,
                                               VkMemoryRequirements2* pMemoryRequirements,
                                               uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBufferMemoryRequirements2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetBufferMemoryRequirements2(device:%p, pInfo:%p, pMemoryRequirements:%p)",
                      device, pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferMemoryRequirementsInfo2* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkBufferMemoryRequirementsInfo2*)pool->alloc(
            sizeof(const VkBufferMemoryRequirementsInfo2));
        deepcopy_VkBufferMemoryRequirementsInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                 (VkBufferMemoryRequirementsInfo2*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkBufferMemoryRequirementsInfo2(
            sResourceTracker, (VkBufferMemoryRequirementsInfo2*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferMemoryRequirementsInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBufferMemoryRequirementsInfo2*)(local_pInfo),
                                              countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetBufferMemoryRequirements2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetBufferMemoryRequirements2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBufferMemoryRequirements2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBufferMemoryRequirements2 = OP_vkGetBufferMemoryRequirements2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBufferMemoryRequirements2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBufferMemoryRequirements2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferMemoryRequirementsInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                    (VkBufferMemoryRequirementsInfo2*)(local_pInfo),
                                                    streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetBufferMemoryRequirements2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetImageSparseMemoryRequirements2(
    VkDevice device, const VkImageSparseMemoryRequirementsInfo2* pInfo,
    uint32_t* pSparseMemoryRequirementCount,
    VkSparseImageMemoryRequirements2* pSparseMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageSparseMemoryRequirements2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetImageSparseMemoryRequirements2(device:%p, pInfo:%p, "
        "pSparseMemoryRequirementCount:%p, pSparseMemoryRequirements:%p)",
        device, pInfo, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageSparseMemoryRequirementsInfo2* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkImageSparseMemoryRequirementsInfo2*)pool->alloc(
            sizeof(const VkImageSparseMemoryRequirementsInfo2));
        deepcopy_VkImageSparseMemoryRequirementsInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
            (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkImageSparseMemoryRequirementsInfo2(
            sResourceTracker, (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageSparseMemoryRequirementsInfo2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirementCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirements) {
            if (pSparseMemoryRequirementCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                    count_VkSparseImageMemoryRequirements2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i),
                        countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetImageSparseMemoryRequirements2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageSparseMemoryRequirements2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageSparseMemoryRequirements2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageSparseMemoryRequirements2 = OP_vkGetImageSparseMemoryRequirements2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageSparseMemoryRequirements2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageSparseMemoryRequirements2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageSparseMemoryRequirementsInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo),
        streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pSparseMemoryRequirementCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirementCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pSparseMemoryRequirements;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirements) {
        for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
            reservedmarshal_VkSparseImageMemoryRequirements2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetImageSparseMemoryRequirements2),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pSparseMemoryRequirementCount;
    check_pSparseMemoryRequirementCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirementCount) {
        if (!(check_pSparseMemoryRequirementCount)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirementCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageMemoryRequirements2* check_pSparseMemoryRequirements;
    check_pSparseMemoryRequirements =
        (VkSparseImageMemoryRequirements2*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirements) {
        if (!(check_pSparseMemoryRequirements)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirements inconsistent between guest and host\n");
        }
        if (pSparseMemoryRequirementCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                unmarshal_VkSparseImageMemoryRequirements2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    if (pSparseMemoryRequirementCount) {
        if (pSparseMemoryRequirements) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                transform_fromhost_VkSparseImageMemoryRequirements2(
                    sResourceTracker,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceFeatures2(VkPhysicalDevice physicalDevice,
                                             VkPhysicalDeviceFeatures2* pFeatures,
                                             uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceFeatures2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPhysicalDeviceFeatures2(physicalDevice:%p, pFeatures:%p)",
                      physicalDevice, pFeatures);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceFeatures2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkPhysicalDeviceFeatures2*)(pFeatures), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceFeatures2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceFeatures2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceFeatures2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceFeatures2 = OP_vkGetPhysicalDeviceFeatures2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceFeatures2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceFeatures2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceFeatures2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPhysicalDeviceFeatures2*)(pFeatures), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceFeatures2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceFeatures2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkPhysicalDeviceFeatures2*)(pFeatures));
    if (pFeatures) {
        transform_fromhost_VkPhysicalDeviceFeatures2(sResourceTracker,
                                                     (VkPhysicalDeviceFeatures2*)(pFeatures));
    }
    sResourceTracker->on_vkGetPhysicalDeviceFeatures2(this, physicalDevice, pFeatures);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceProperties2(VkPhysicalDevice physicalDevice,
                                               VkPhysicalDeviceProperties2* pProperties,
                                               uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceProperties2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPhysicalDeviceProperties2(physicalDevice:%p, pProperties:%p)",
                      physicalDevice, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceProperties2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPhysicalDeviceProperties2*)(pProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceProperties2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceProperties2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceProperties2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceProperties2 = OP_vkGetPhysicalDeviceProperties2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkPhysicalDeviceProperties2*)(pProperties),
                                                streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceProperties2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPhysicalDeviceProperties2*)(pProperties));
    if (pProperties) {
        transform_fromhost_VkPhysicalDeviceProperties2(sResourceTracker,
                                                       (VkPhysicalDeviceProperties2*)(pProperties));
    }
    sResourceTracker->on_vkGetPhysicalDeviceProperties2(this, physicalDevice, pProperties);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceFormatProperties2(VkPhysicalDevice physicalDevice,
                                                     VkFormat format,
                                                     VkFormatProperties2* pFormatProperties,
                                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceFormatProperties2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceFormatProperties2(physicalDevice:%p, format:%d, pFormatProperties:%p)",
        physicalDevice, format, pFormatProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkFormat local_format;
    local_physicalDevice = physicalDevice;
    local_format = format;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        count_VkFormatProperties2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkFormatProperties2*)(pFormatProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceFormatProperties2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceFormatProperties2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceFormatProperties2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceFormatProperties2 = OP_vkGetPhysicalDeviceFormatProperties2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceFormatProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceFormatProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    reservedmarshal_VkFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkFormatProperties2*)(pFormatProperties), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPhysicalDeviceFormatProperties2),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkFormatProperties2*)(pFormatProperties));
    if (pFormatProperties) {
        transform_fromhost_VkFormatProperties2(sResourceTracker,
                                               (VkFormatProperties2*)(pFormatProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetPhysicalDeviceImageFormatProperties2(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceImageFormatInfo2* pImageFormatInfo,
    VkImageFormatProperties2* pImageFormatProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceImageFormatProperties2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceImageFormatProperties2(physicalDevice:%p, pImageFormatInfo:%p, "
        "pImageFormatProperties:%p)",
        physicalDevice, pImageFormatInfo, pImageFormatProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceImageFormatInfo2* local_pImageFormatInfo;
    local_physicalDevice = physicalDevice;
    local_pImageFormatInfo = nullptr;
    if (pImageFormatInfo) {
        local_pImageFormatInfo = (VkPhysicalDeviceImageFormatInfo2*)pool->alloc(
            sizeof(const VkPhysicalDeviceImageFormatInfo2));
        deepcopy_VkPhysicalDeviceImageFormatInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pImageFormatInfo,
            (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo));
    }
    if (local_pImageFormatInfo) {
        transform_tohost_VkPhysicalDeviceImageFormatInfo2(
            sResourceTracker, (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceImageFormatInfo2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo), countPtr);
        count_VkImageFormatProperties2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageFormatProperties2*)(pImageFormatProperties),
                                       countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceImageFormatProperties2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceImageFormatProperties2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceImageFormatProperties2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceImageFormatProperties2 =
        OP_vkGetPhysicalDeviceImageFormatProperties2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceImageFormatProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceImageFormatProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceImageFormatInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo), streamPtrPtr);
    reservedmarshal_VkImageFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkImageFormatProperties2*)(pImageFormatProperties),
                                             streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceImageFormatProperties2),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkImageFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageFormatProperties2*)(pImageFormatProperties));
    if (pImageFormatProperties) {
        transform_fromhost_VkImageFormatProperties2(
            sResourceTracker, (VkImageFormatProperties2*)(pImageFormatProperties));
    }
    VkResult vkGetPhysicalDeviceImageFormatProperties2_VkResult_return = (VkResult)0;
    stream->read(&vkGetPhysicalDeviceImageFormatProperties2_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPhysicalDeviceImageFormatProperties2_VkResult_return;
}

void VkEncoder::vkGetPhysicalDeviceQueueFamilyProperties2(
    VkPhysicalDevice physicalDevice, uint32_t* pQueueFamilyPropertyCount,
    VkQueueFamilyProperties2* pQueueFamilyProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceQueueFamilyProperties2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceQueueFamilyProperties2(physicalDevice:%p, "
        "pQueueFamilyPropertyCount:%p, pQueueFamilyProperties:%p)",
        physicalDevice, pQueueFamilyPropertyCount, pQueueFamilyProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pQueueFamilyPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pQueueFamilyProperties) {
            if (pQueueFamilyPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                    count_VkQueueFamilyProperties2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceQueueFamilyProperties2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceQueueFamilyProperties2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceQueueFamilyProperties2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceQueueFamilyProperties2 =
        OP_vkGetPhysicalDeviceQueueFamilyProperties2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceQueueFamilyProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceQueueFamilyProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pQueueFamilyPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pQueueFamilyPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pQueueFamilyPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pQueueFamilyProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pQueueFamilyProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
            reservedmarshal_VkQueueFamilyProperties2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceQueueFamilyProperties2),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pQueueFamilyPropertyCount;
    check_pQueueFamilyPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pQueueFamilyPropertyCount) {
        if (!(check_pQueueFamilyPropertyCount)) {
            fprintf(stderr,
                    "fatal: pQueueFamilyPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pQueueFamilyPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkQueueFamilyProperties2* check_pQueueFamilyProperties;
    check_pQueueFamilyProperties = (VkQueueFamilyProperties2*)(uintptr_t)stream->getBe64();
    if (pQueueFamilyProperties) {
        if (!(check_pQueueFamilyProperties)) {
            fprintf(stderr, "fatal: pQueueFamilyProperties inconsistent between guest and host\n");
        }
        if (pQueueFamilyPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                unmarshal_VkQueueFamilyProperties2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i));
            }
        }
    }
    if (pQueueFamilyPropertyCount) {
        if (pQueueFamilyProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                transform_fromhost_VkQueueFamilyProperties2(
                    sResourceTracker, (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceMemoryProperties2(
    VkPhysicalDevice physicalDevice, VkPhysicalDeviceMemoryProperties2* pMemoryProperties,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceMemoryProperties2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceMemoryProperties2(physicalDevice:%p, pMemoryProperties:%p)",
        physicalDevice, pMemoryProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceMemoryProperties2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceMemoryProperties2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceMemoryProperties2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceMemoryProperties2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceMemoryProperties2 = OP_vkGetPhysicalDeviceMemoryProperties2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceMemoryProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceMemoryProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceMemoryProperties2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties),
        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPhysicalDeviceMemoryProperties2),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceMemoryProperties2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties));
    if (pMemoryProperties) {
        transform_fromhost_VkPhysicalDeviceMemoryProperties2(
            sResourceTracker, (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceSparseImageFormatProperties2(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceSparseImageFormatInfo2* pFormatInfo,
    uint32_t* pPropertyCount, VkSparseImageFormatProperties2* pProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceSparseImageFormatProperties2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceSparseImageFormatProperties2(physicalDevice:%p, pFormatInfo:%p, "
        "pPropertyCount:%p, pProperties:%p)",
        physicalDevice, pFormatInfo, pPropertyCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceSparseImageFormatInfo2* local_pFormatInfo;
    local_physicalDevice = physicalDevice;
    local_pFormatInfo = nullptr;
    if (pFormatInfo) {
        local_pFormatInfo = (VkPhysicalDeviceSparseImageFormatInfo2*)pool->alloc(
            sizeof(const VkPhysicalDeviceSparseImageFormatInfo2));
        deepcopy_VkPhysicalDeviceSparseImageFormatInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pFormatInfo,
            (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo));
    }
    if (local_pFormatInfo) {
        transform_tohost_VkPhysicalDeviceSparseImageFormatInfo2(
            sResourceTracker, (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceSparseImageFormatInfo2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                    count_VkSparseImageFormatProperties2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageFormatProperties2*)(pProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2);
    uint8_t* streamPtr =
        stream->reserve(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceSparseImageFormatProperties2 =
        OP_vkGetPhysicalDeviceSparseImageFormatProperties2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceSparseImageFormatProperties2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2,
           sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceSparseImageFormatInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
            reservedmarshal_VkSparseImageFormatProperties2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageFormatProperties2*)(pProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPropertyCount;
    check_pPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPropertyCount) {
        if (!(check_pPropertyCount)) {
            fprintf(stderr, "fatal: pPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageFormatProperties2* check_pProperties;
    check_pProperties = (VkSparseImageFormatProperties2*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                unmarshal_VkSparseImageFormatProperties2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageFormatProperties2*)(pProperties + i));
            }
        }
    }
    if (pPropertyCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                transform_fromhost_VkSparseImageFormatProperties2(
                    sResourceTracker, (VkSparseImageFormatProperties2*)(pProperties + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkTrimCommandPool(VkDevice device, VkCommandPool commandPool,
                                  VkCommandPoolTrimFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkTrimCommandPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkTrimCommandPool(device:%p, commandPool:%p, flags:%d)", device, commandPool,
                      flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCommandPool local_commandPool;
    VkCommandPoolTrimFlags local_flags;
    local_device = device;
    local_commandPool = commandPool;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCommandPoolTrimFlags);
    }
    uint32_t packetSize_vkTrimCommandPool =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkTrimCommandPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkTrimCommandPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkTrimCommandPool = OP_vkTrimCommandPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkTrimCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkTrimCommandPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkCommandPool((*&local_commandPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkCommandPoolTrimFlags*)&local_flags, sizeof(VkCommandPoolTrimFlags));
    *streamPtrPtr += sizeof(VkCommandPoolTrimFlags);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkTrimCommandPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDeviceQueue2(VkDevice device, const VkDeviceQueueInfo2* pQueueInfo,
                                  VkQueue* pQueue, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceQueue2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDeviceQueue2(device:%p, pQueueInfo:%p, pQueue:%p)", device, pQueueInfo,
                      pQueue);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceQueueInfo2* local_pQueueInfo;
    local_device = device;
    local_pQueueInfo = nullptr;
    if (pQueueInfo) {
        local_pQueueInfo = (VkDeviceQueueInfo2*)pool->alloc(sizeof(const VkDeviceQueueInfo2));
        deepcopy_VkDeviceQueueInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pQueueInfo,
                                    (VkDeviceQueueInfo2*)(local_pQueueInfo));
    }
    if (local_pQueueInfo) {
        transform_tohost_VkDeviceQueueInfo2(sResourceTracker,
                                            (VkDeviceQueueInfo2*)(local_pQueueInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceQueueInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkDeviceQueueInfo2*)(local_pQueueInfo), countPtr);
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkGetDeviceQueue2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetDeviceQueue2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceQueue2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceQueue2 = OP_vkGetDeviceQueue2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceQueue2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceQueue2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceQueueInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkDeviceQueueInfo2*)(local_pQueueInfo), streamPtrPtr);
    /* is handle, possibly out */;
    uint64_t cgen_var_1;
    *&cgen_var_1 = (uint64_t)((*pQueue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetDeviceQueue2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_2;
    stream->read((uint64_t*)&cgen_var_2, 8);
    stream->handleMapping()->mapHandles_u64_VkQueue(&cgen_var_2, (VkQueue*)pQueue, 1);
    stream->unsetHandleMapping();
    sResourceTracker->on_vkGetDeviceQueue2(this, device, pQueueInfo, pQueue);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateSamplerYcbcrConversion(
    VkDevice device, const VkSamplerYcbcrConversionCreateInfo* pCreateInfo,
    const VkAllocationCallbacks* pAllocator, VkSamplerYcbcrConversion* pYcbcrConversion,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateSamplerYcbcrConversion in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateSamplerYcbcrConversion(device:%p, pCreateInfo:%p, pAllocator:%p, "
        "pYcbcrConversion:%p)",
        device, pCreateInfo, pAllocator, pYcbcrConversion);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSamplerYcbcrConversionCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkSamplerYcbcrConversionCreateInfo*)pool->alloc(
            sizeof(const VkSamplerYcbcrConversionCreateInfo));
        deepcopy_VkSamplerYcbcrConversionCreateInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
            (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkSamplerYcbcrConversionCreateInfo(
            sResourceTracker, (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSamplerYcbcrConversionCreateInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateSamplerYcbcrConversion =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCreateSamplerYcbcrConversion);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateSamplerYcbcrConversion);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateSamplerYcbcrConversion = OP_vkCreateSamplerYcbcrConversion;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateSamplerYcbcrConversion, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateSamplerYcbcrConversion, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkSamplerYcbcrConversionCreateInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pYcbcrConversion));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateSamplerYcbcrConversion), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkSamplerYcbcrConversion(
        &cgen_var_3, (VkSamplerYcbcrConversion*)pYcbcrConversion, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateSamplerYcbcrConversion_VkResult_return = (VkResult)0;
    stream->read(&vkCreateSamplerYcbcrConversion_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateSamplerYcbcrConversion_VkResult_return;
}

void VkEncoder::vkDestroySamplerYcbcrConversion(VkDevice device,
                                                VkSamplerYcbcrConversion ycbcrConversion,
                                                const VkAllocationCallbacks* pAllocator,
                                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroySamplerYcbcrConversion in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkDestroySamplerYcbcrConversion(device:%p, ycbcrConversion:%p, pAllocator:%p)", device,
        ycbcrConversion, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSamplerYcbcrConversion local_ycbcrConversion;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_ycbcrConversion = ycbcrConversion;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroySamplerYcbcrConversion =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkDestroySamplerYcbcrConversion);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroySamplerYcbcrConversion);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroySamplerYcbcrConversion = OP_vkDestroySamplerYcbcrConversion;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroySamplerYcbcrConversion, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroySamplerYcbcrConversion, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkSamplerYcbcrConversion((*&local_ycbcrConversion));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroySamplerYcbcrConversion), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkSamplerYcbcrConversion(
        (VkSamplerYcbcrConversion*)&ycbcrConversion);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateDescriptorUpdateTemplate(
    VkDevice device, const VkDescriptorUpdateTemplateCreateInfo* pCreateInfo,
    const VkAllocationCallbacks* pAllocator, VkDescriptorUpdateTemplate* pDescriptorUpdateTemplate,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateDescriptorUpdateTemplate in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateDescriptorUpdateTemplate(device:%p, pCreateInfo:%p, pAllocator:%p, "
        "pDescriptorUpdateTemplate:%p)",
        device, pCreateInfo, pAllocator, pDescriptorUpdateTemplate);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorUpdateTemplateCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkDescriptorUpdateTemplateCreateInfo*)pool->alloc(
            sizeof(const VkDescriptorUpdateTemplateCreateInfo));
        deepcopy_VkDescriptorUpdateTemplateCreateInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
            (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkDescriptorUpdateTemplateCreateInfo(
            sResourceTracker, (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDescriptorUpdateTemplateCreateInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateDescriptorUpdateTemplate =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCreateDescriptorUpdateTemplate);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateDescriptorUpdateTemplate);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateDescriptorUpdateTemplate = OP_vkCreateDescriptorUpdateTemplate;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateDescriptorUpdateTemplate, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateDescriptorUpdateTemplate, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDescriptorUpdateTemplateCreateInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pDescriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateDescriptorUpdateTemplate), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkDescriptorUpdateTemplate(
        &cgen_var_3, (VkDescriptorUpdateTemplate*)pDescriptorUpdateTemplate, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateDescriptorUpdateTemplate_VkResult_return = (VkResult)0;
    stream->read(&vkCreateDescriptorUpdateTemplate_VkResult_return, sizeof(VkResult));
    sResourceTracker->on_vkCreateDescriptorUpdateTemplate(
        this, vkCreateDescriptorUpdateTemplate_VkResult_return, device, pCreateInfo, pAllocator,
        pDescriptorUpdateTemplate);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateDescriptorUpdateTemplate_VkResult_return;
}

void VkEncoder::vkDestroyDescriptorUpdateTemplate(
    VkDevice device, VkDescriptorUpdateTemplate descriptorUpdateTemplate,
    const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyDescriptorUpdateTemplate in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkDestroyDescriptorUpdateTemplate(device:%p, descriptorUpdateTemplate:%p, pAllocator:%p)",
        device, descriptorUpdateTemplate, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorUpdateTemplate local_descriptorUpdateTemplate;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_descriptorUpdateTemplate = descriptorUpdateTemplate;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyDescriptorUpdateTemplate =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkDestroyDescriptorUpdateTemplate);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyDescriptorUpdateTemplate);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyDescriptorUpdateTemplate = OP_vkDestroyDescriptorUpdateTemplate;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyDescriptorUpdateTemplate, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyDescriptorUpdateTemplate, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorUpdateTemplate((*&local_descriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyDescriptorUpdateTemplate), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkDescriptorUpdateTemplate(
        (VkDescriptorUpdateTemplate*)&descriptorUpdateTemplate);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkUpdateDescriptorSetWithTemplate(
    VkDevice device, VkDescriptorSet descriptorSet,
    VkDescriptorUpdateTemplate descriptorUpdateTemplate, const void* pData, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkUpdateDescriptorSetWithTemplate in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkUpdateDescriptorSetWithTemplate(device:%p, descriptorSet:%p, "
        "descriptorUpdateTemplate:%p, pData:%p)",
        device, descriptorSet, descriptorUpdateTemplate, pData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSet local_descriptorSet;
    VkDescriptorUpdateTemplate local_descriptorUpdateTemplate;
    void* local_pData;
    local_device = device;
    local_descriptorSet = descriptorSet;
    local_descriptorUpdateTemplate = descriptorUpdateTemplate;
    // Avoiding deepcopy for pData
    local_pData = (void*)pData;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pData) {
            *countPtr += sizeof(uint8_t);
        }
    }
    uint32_t packetSize_vkUpdateDescriptorSetWithTemplate =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkUpdateDescriptorSetWithTemplate);
    uint8_t* streamPtr = stream->reserve(packetSize_vkUpdateDescriptorSetWithTemplate);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkUpdateDescriptorSetWithTemplate = OP_vkUpdateDescriptorSetWithTemplate;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkUpdateDescriptorSetWithTemplate, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkUpdateDescriptorSetWithTemplate, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorSet((*&local_descriptorSet));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkDescriptorUpdateTemplate((*&local_descriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_3 = (uint64_t)(uintptr_t)local_pData;
    memcpy((*streamPtrPtr), &cgen_var_3, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pData) {
        memcpy(*streamPtrPtr, (void*)local_pData, sizeof(uint8_t));
        *streamPtrPtr += sizeof(uint8_t);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkUpdateDescriptorSetWithTemplate), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceExternalBufferProperties(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceExternalBufferInfo* pExternalBufferInfo,
    VkExternalBufferProperties* pExternalBufferProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceExternalBufferProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceExternalBufferProperties(physicalDevice:%p, pExternalBufferInfo:%p, "
        "pExternalBufferProperties:%p)",
        physicalDevice, pExternalBufferInfo, pExternalBufferProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceExternalBufferInfo* local_pExternalBufferInfo;
    local_physicalDevice = physicalDevice;
    local_pExternalBufferInfo = nullptr;
    if (pExternalBufferInfo) {
        local_pExternalBufferInfo = (VkPhysicalDeviceExternalBufferInfo*)pool->alloc(
            sizeof(const VkPhysicalDeviceExternalBufferInfo));
        deepcopy_VkPhysicalDeviceExternalBufferInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExternalBufferInfo,
            (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo));
    }
    if (local_pExternalBufferInfo) {
        sResourceTracker->transformImpl_VkPhysicalDeviceExternalBufferInfo_tohost(
            local_pExternalBufferInfo, 1);
        transform_tohost_VkPhysicalDeviceExternalBufferInfo(
            sResourceTracker, (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceExternalBufferInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo), countPtr);
        count_VkExternalBufferProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkExternalBufferProperties*)(pExternalBufferProperties),
                                         countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceExternalBufferProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceExternalBufferProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceExternalBufferProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceExternalBufferProperties =
        OP_vkGetPhysicalDeviceExternalBufferProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceExternalBufferProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceExternalBufferProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceExternalBufferInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo), streamPtrPtr);
    reservedmarshal_VkExternalBufferProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkExternalBufferProperties*)(pExternalBufferProperties), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceExternalBufferProperties),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExternalBufferProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkExternalBufferProperties*)(pExternalBufferProperties));
    if (pExternalBufferProperties) {
        sResourceTracker->transformImpl_VkExternalBufferProperties_fromhost(
            pExternalBufferProperties, 1);
        transform_fromhost_VkExternalBufferProperties(
            sResourceTracker, (VkExternalBufferProperties*)(pExternalBufferProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceExternalFenceProperties(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceExternalFenceInfo* pExternalFenceInfo,
    VkExternalFenceProperties* pExternalFenceProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceExternalFenceProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceExternalFenceProperties(physicalDevice:%p, pExternalFenceInfo:%p, "
        "pExternalFenceProperties:%p)",
        physicalDevice, pExternalFenceInfo, pExternalFenceProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceExternalFenceInfo* local_pExternalFenceInfo;
    local_physicalDevice = physicalDevice;
    local_pExternalFenceInfo = nullptr;
    if (pExternalFenceInfo) {
        local_pExternalFenceInfo = (VkPhysicalDeviceExternalFenceInfo*)pool->alloc(
            sizeof(const VkPhysicalDeviceExternalFenceInfo));
        deepcopy_VkPhysicalDeviceExternalFenceInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExternalFenceInfo,
            (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo));
    }
    if (local_pExternalFenceInfo) {
        transform_tohost_VkPhysicalDeviceExternalFenceInfo(
            sResourceTracker, (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceExternalFenceInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo), countPtr);
        count_VkExternalFenceProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkExternalFenceProperties*)(pExternalFenceProperties),
                                        countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceExternalFenceProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceExternalFenceProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceExternalFenceProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceExternalFenceProperties =
        OP_vkGetPhysicalDeviceExternalFenceProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceExternalFenceProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceExternalFenceProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceExternalFenceInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo), streamPtrPtr);
    reservedmarshal_VkExternalFenceProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExternalFenceProperties*)(pExternalFenceProperties),
        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceExternalFenceProperties),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExternalFenceProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkExternalFenceProperties*)(pExternalFenceProperties));
    if (pExternalFenceProperties) {
        transform_fromhost_VkExternalFenceProperties(
            sResourceTracker, (VkExternalFenceProperties*)(pExternalFenceProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceExternalSemaphoreProperties(
    VkPhysicalDevice physicalDevice,
    const VkPhysicalDeviceExternalSemaphoreInfo* pExternalSemaphoreInfo,
    VkExternalSemaphoreProperties* pExternalSemaphoreProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceExternalSemaphoreProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceExternalSemaphoreProperties(physicalDevice:%p, "
        "pExternalSemaphoreInfo:%p, pExternalSemaphoreProperties:%p)",
        physicalDevice, pExternalSemaphoreInfo, pExternalSemaphoreProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceExternalSemaphoreInfo* local_pExternalSemaphoreInfo;
    local_physicalDevice = physicalDevice;
    local_pExternalSemaphoreInfo = nullptr;
    if (pExternalSemaphoreInfo) {
        local_pExternalSemaphoreInfo = (VkPhysicalDeviceExternalSemaphoreInfo*)pool->alloc(
            sizeof(const VkPhysicalDeviceExternalSemaphoreInfo));
        deepcopy_VkPhysicalDeviceExternalSemaphoreInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExternalSemaphoreInfo,
            (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo));
    }
    if (local_pExternalSemaphoreInfo) {
        transform_tohost_VkPhysicalDeviceExternalSemaphoreInfo(
            sResourceTracker,
            (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceExternalSemaphoreInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo), countPtr);
        count_VkExternalSemaphoreProperties(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceExternalSemaphoreProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceExternalSemaphoreProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceExternalSemaphoreProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceExternalSemaphoreProperties =
        OP_vkGetPhysicalDeviceExternalSemaphoreProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceExternalSemaphoreProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceExternalSemaphoreProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceExternalSemaphoreInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo), streamPtrPtr);
    reservedmarshal_VkExternalSemaphoreProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceExternalSemaphoreProperties),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExternalSemaphoreProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties));
    if (pExternalSemaphoreProperties) {
        transform_fromhost_VkExternalSemaphoreProperties(
            sResourceTracker, (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties));
    }
    sResourceTracker->on_vkGetPhysicalDeviceExternalSemaphoreProperties(
        this, physicalDevice, pExternalSemaphoreInfo, pExternalSemaphoreProperties);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDescriptorSetLayoutSupport(VkDevice device,
                                                const VkDescriptorSetLayoutCreateInfo* pCreateInfo,
                                                VkDescriptorSetLayoutSupport* pSupport,
                                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDescriptorSetLayoutSupport in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDescriptorSetLayoutSupport(device:%p, pCreateInfo:%p, pSupport:%p)",
                      device, pCreateInfo, pSupport);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSetLayoutCreateInfo* local_pCreateInfo;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkDescriptorSetLayoutCreateInfo*)pool->alloc(
            sizeof(const VkDescriptorSetLayoutCreateInfo));
        deepcopy_VkDescriptorSetLayoutCreateInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
            (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo));
    }
    if (local_pCreateInfo) {
        transform_tohost_VkDescriptorSetLayoutCreateInfo(
            sResourceTracker, (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDescriptorSetLayoutCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo),
                                              countPtr);
        count_VkDescriptorSetLayoutSupport(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkDescriptorSetLayoutSupport*)(pSupport), countPtr);
    }
    uint32_t packetSize_vkGetDescriptorSetLayoutSupport =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDescriptorSetLayoutSupport);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDescriptorSetLayoutSupport);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDescriptorSetLayoutSupport = OP_vkGetDescriptorSetLayoutSupport;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDescriptorSetLayoutSupport, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDescriptorSetLayoutSupport, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDescriptorSetLayoutCreateInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo),
        streamPtrPtr);
    reservedmarshal_VkDescriptorSetLayoutSupport(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                 (VkDescriptorSetLayoutSupport*)(pSupport),
                                                 streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDescriptorSetLayoutSupport), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkDescriptorSetLayoutSupport(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkDescriptorSetLayoutSupport*)(pSupport));
    if (pSupport) {
        transform_fromhost_VkDescriptorSetLayoutSupport(sResourceTracker,
                                                        (VkDescriptorSetLayoutSupport*)(pSupport));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_VERSION_1_2
void VkEncoder::vkCmdDrawIndirectCount(VkCommandBuffer commandBuffer, VkBuffer buffer,
                                       VkDeviceSize offset, VkBuffer countBuffer,
                                       VkDeviceSize countBufferOffset, uint32_t maxDrawCount,
                                       uint32_t stride, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDrawIndirectCount in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDrawIndirectCount(commandBuffer:%p, buffer:%p, offset:%ld, countBuffer:%p, "
        "countBufferOffset:%ld, maxDrawCount:%d, stride:%d)",
        commandBuffer, buffer, offset, countBuffer, countBufferOffset, maxDrawCount, stride);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_buffer;
    VkDeviceSize local_offset;
    VkBuffer local_countBuffer;
    VkDeviceSize local_countBufferOffset;
    uint32_t local_maxDrawCount;
    uint32_t local_stride;
    local_commandBuffer = commandBuffer;
    local_buffer = buffer;
    local_offset = offset;
    local_countBuffer = countBuffer;
    local_countBufferOffset = countBufferOffset;
    local_maxDrawCount = maxDrawCount;
    local_stride = stride;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDrawIndirectCount = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdDrawIndirectCount);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDrawIndirectCount -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDrawIndirectCount);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDrawIndirectCount = OP_vkCmdDrawIndirectCount;
    memcpy(streamPtr, &opcode_vkCmdDrawIndirectCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDrawIndirectCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_offset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_countBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_countBufferOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (uint32_t*)&local_maxDrawCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_stride, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdDrawIndirectCount), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDrawIndexedIndirectCount(VkCommandBuffer commandBuffer, VkBuffer buffer,
                                              VkDeviceSize offset, VkBuffer countBuffer,
                                              VkDeviceSize countBufferOffset, uint32_t maxDrawCount,
                                              uint32_t stride, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDrawIndexedIndirectCount in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDrawIndexedIndirectCount(commandBuffer:%p, buffer:%p, offset:%ld, countBuffer:%p, "
        "countBufferOffset:%ld, maxDrawCount:%d, stride:%d)",
        commandBuffer, buffer, offset, countBuffer, countBufferOffset, maxDrawCount, stride);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_buffer;
    VkDeviceSize local_offset;
    VkBuffer local_countBuffer;
    VkDeviceSize local_countBufferOffset;
    uint32_t local_maxDrawCount;
    uint32_t local_stride;
    local_commandBuffer = commandBuffer;
    local_buffer = buffer;
    local_offset = offset;
    local_countBuffer = countBuffer;
    local_countBufferOffset = countBufferOffset;
    local_maxDrawCount = maxDrawCount;
    local_stride = stride;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDrawIndexedIndirectCount = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdDrawIndexedIndirectCount);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDrawIndexedIndirectCount -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDrawIndexedIndirectCount);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDrawIndexedIndirectCount = OP_vkCmdDrawIndexedIndirectCount;
    memcpy(streamPtr, &opcode_vkCmdDrawIndexedIndirectCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDrawIndexedIndirectCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_offset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkBuffer((*&local_countBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_countBufferOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (uint32_t*)&local_maxDrawCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_stride, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdDrawIndexedIndirectCount), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateRenderPass2(VkDevice device, const VkRenderPassCreateInfo2* pCreateInfo,
                                        const VkAllocationCallbacks* pAllocator,
                                        VkRenderPass* pRenderPass, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateRenderPass2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateRenderPass2(device:%p, pCreateInfo:%p, pAllocator:%p, pRenderPass:%p)", device,
        pCreateInfo, pAllocator, pRenderPass);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkRenderPassCreateInfo2* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkRenderPassCreateInfo2*)pool->alloc(sizeof(const VkRenderPassCreateInfo2));
        deepcopy_VkRenderPassCreateInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                         (VkRenderPassCreateInfo2*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkRenderPassCreateInfo2(sResourceTracker,
                                                 (VkRenderPassCreateInfo2*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderPassCreateInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkRenderPassCreateInfo2*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateRenderPass2 =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateRenderPass2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateRenderPass2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateRenderPass2 = OP_vkCreateRenderPass2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateRenderPass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateRenderPass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkRenderPassCreateInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkRenderPassCreateInfo2*)(local_pCreateInfo),
                                            streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pRenderPass));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateRenderPass2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkRenderPass(&cgen_var_3, (VkRenderPass*)pRenderPass,
                                                         1);
    stream->unsetHandleMapping();
    VkResult vkCreateRenderPass2_VkResult_return = (VkResult)0;
    stream->read(&vkCreateRenderPass2_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateRenderPass2_VkResult_return;
}

void VkEncoder::vkCmdBeginRenderPass2(VkCommandBuffer commandBuffer,
                                      const VkRenderPassBeginInfo* pRenderPassBegin,
                                      const VkSubpassBeginInfo* pSubpassBeginInfo,
                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginRenderPass2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBeginRenderPass2(commandBuffer:%p, pRenderPassBegin:%p, pSubpassBeginInfo:%p)",
        commandBuffer, pRenderPassBegin, pSubpassBeginInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkRenderPassBeginInfo* local_pRenderPassBegin;
    VkSubpassBeginInfo* local_pSubpassBeginInfo;
    local_commandBuffer = commandBuffer;
    local_pRenderPassBegin = nullptr;
    if (pRenderPassBegin) {
        local_pRenderPassBegin =
            (VkRenderPassBeginInfo*)pool->alloc(sizeof(const VkRenderPassBeginInfo));
        deepcopy_VkRenderPassBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRenderPassBegin,
                                       (VkRenderPassBeginInfo*)(local_pRenderPassBegin));
    }
    local_pSubpassBeginInfo = nullptr;
    if (pSubpassBeginInfo) {
        local_pSubpassBeginInfo =
            (VkSubpassBeginInfo*)pool->alloc(sizeof(const VkSubpassBeginInfo));
        deepcopy_VkSubpassBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassBeginInfo,
                                    (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    if (local_pRenderPassBegin) {
        transform_tohost_VkRenderPassBeginInfo(sResourceTracker,
                                               (VkRenderPassBeginInfo*)(local_pRenderPassBegin));
    }
    if (local_pSubpassBeginInfo) {
        transform_tohost_VkSubpassBeginInfo(sResourceTracker,
                                            (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderPassBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkRenderPassBeginInfo*)(local_pRenderPassBegin), countPtr);
        count_VkSubpassBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkSubpassBeginInfo*)(local_pSubpassBeginInfo), countPtr);
    }
    uint32_t packetSize_vkCmdBeginRenderPass2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBeginRenderPass2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginRenderPass2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginRenderPass2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginRenderPass2 = OP_vkCmdBeginRenderPass2;
    memcpy(streamPtr, &opcode_vkCmdBeginRenderPass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginRenderPass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkRenderPassBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkRenderPassBeginInfo*)(local_pRenderPassBegin),
                                          streamPtrPtr);
    reservedmarshal_VkSubpassBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkSubpassBeginInfo*)(local_pSubpassBeginInfo),
                                       streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBeginRenderPass2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdNextSubpass2(VkCommandBuffer commandBuffer,
                                  const VkSubpassBeginInfo* pSubpassBeginInfo,
                                  const VkSubpassEndInfo* pSubpassEndInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdNextSubpass2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdNextSubpass2(commandBuffer:%p, pSubpassBeginInfo:%p, pSubpassEndInfo:%p)",
        commandBuffer, pSubpassBeginInfo, pSubpassEndInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkSubpassBeginInfo* local_pSubpassBeginInfo;
    VkSubpassEndInfo* local_pSubpassEndInfo;
    local_commandBuffer = commandBuffer;
    local_pSubpassBeginInfo = nullptr;
    if (pSubpassBeginInfo) {
        local_pSubpassBeginInfo =
            (VkSubpassBeginInfo*)pool->alloc(sizeof(const VkSubpassBeginInfo));
        deepcopy_VkSubpassBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassBeginInfo,
                                    (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    local_pSubpassEndInfo = nullptr;
    if (pSubpassEndInfo) {
        local_pSubpassEndInfo = (VkSubpassEndInfo*)pool->alloc(sizeof(const VkSubpassEndInfo));
        deepcopy_VkSubpassEndInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassEndInfo,
                                  (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    if (local_pSubpassBeginInfo) {
        transform_tohost_VkSubpassBeginInfo(sResourceTracker,
                                            (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    if (local_pSubpassEndInfo) {
        transform_tohost_VkSubpassEndInfo(sResourceTracker,
                                          (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSubpassBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkSubpassBeginInfo*)(local_pSubpassBeginInfo), countPtr);
        count_VkSubpassEndInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkSubpassEndInfo*)(local_pSubpassEndInfo), countPtr);
    }
    uint32_t packetSize_vkCmdNextSubpass2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdNextSubpass2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdNextSubpass2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdNextSubpass2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdNextSubpass2 = OP_vkCmdNextSubpass2;
    memcpy(streamPtr, &opcode_vkCmdNextSubpass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdNextSubpass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkSubpassBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkSubpassBeginInfo*)(local_pSubpassBeginInfo),
                                       streamPtrPtr);
    reservedmarshal_VkSubpassEndInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkSubpassEndInfo*)(local_pSubpassEndInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdNextSubpass2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndRenderPass2(VkCommandBuffer commandBuffer,
                                    const VkSubpassEndInfo* pSubpassEndInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndRenderPass2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdEndRenderPass2(commandBuffer:%p, pSubpassEndInfo:%p)", commandBuffer,
                      pSubpassEndInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkSubpassEndInfo* local_pSubpassEndInfo;
    local_commandBuffer = commandBuffer;
    local_pSubpassEndInfo = nullptr;
    if (pSubpassEndInfo) {
        local_pSubpassEndInfo = (VkSubpassEndInfo*)pool->alloc(sizeof(const VkSubpassEndInfo));
        deepcopy_VkSubpassEndInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassEndInfo,
                                  (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    if (local_pSubpassEndInfo) {
        transform_tohost_VkSubpassEndInfo(sResourceTracker,
                                          (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSubpassEndInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkSubpassEndInfo*)(local_pSubpassEndInfo), countPtr);
    }
    uint32_t packetSize_vkCmdEndRenderPass2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdEndRenderPass2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndRenderPass2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndRenderPass2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndRenderPass2 = OP_vkCmdEndRenderPass2;
    memcpy(streamPtr, &opcode_vkCmdEndRenderPass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndRenderPass2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkSubpassEndInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkSubpassEndInfo*)(local_pSubpassEndInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdEndRenderPass2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkResetQueryPool(VkDevice device, VkQueryPool queryPool, uint32_t firstQuery,
                                 uint32_t queryCount, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkResetQueryPool in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkResetQueryPool(device:%p, queryPool:%p, firstQuery:%d, queryCount:%d)",
                      device, queryPool, firstQuery, queryCount);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkQueryPool local_queryPool;
    uint32_t local_firstQuery;
    uint32_t local_queryCount;
    local_device = device;
    local_queryPool = queryPool;
    local_firstQuery = firstQuery;
    local_queryCount = queryCount;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkResetQueryPool = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkResetQueryPool);
    uint8_t* streamPtr = stream->reserve(packetSize_vkResetQueryPool);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkResetQueryPool = OP_vkResetQueryPool;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkResetQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkResetQueryPool, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstQuery, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_queryCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkResetQueryPool), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetSemaphoreCounterValue(VkDevice device, VkSemaphore semaphore,
                                               uint64_t* pValue, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetSemaphoreCounterValue in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetSemaphoreCounterValue(device:%p, semaphore:%p, pValue:%p)", device,
                      semaphore, pValue);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSemaphore local_semaphore;
    local_device = device;
    local_semaphore = semaphore;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkGetSemaphoreCounterValue =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetSemaphoreCounterValue);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetSemaphoreCounterValue);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetSemaphoreCounterValue = OP_vkGetSemaphoreCounterValue;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetSemaphoreCounterValue, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetSemaphoreCounterValue, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkSemaphore((*&local_semaphore));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint64_t*)pValue, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetSemaphoreCounterValue), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((uint64_t*)pValue, sizeof(uint64_t));
    VkResult vkGetSemaphoreCounterValue_VkResult_return = (VkResult)0;
    stream->read(&vkGetSemaphoreCounterValue_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetSemaphoreCounterValue_VkResult_return;
}

VkResult VkEncoder::vkWaitSemaphores(VkDevice device, const VkSemaphoreWaitInfo* pWaitInfo,
                                     uint64_t timeout, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkWaitSemaphores in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkWaitSemaphores(device:%p, pWaitInfo:%p, timeout:%ld)", device, pWaitInfo,
                      timeout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSemaphoreWaitInfo* local_pWaitInfo;
    uint64_t local_timeout;
    local_device = device;
    local_pWaitInfo = nullptr;
    if (pWaitInfo) {
        local_pWaitInfo = (VkSemaphoreWaitInfo*)pool->alloc(sizeof(const VkSemaphoreWaitInfo));
        deepcopy_VkSemaphoreWaitInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pWaitInfo,
                                     (VkSemaphoreWaitInfo*)(local_pWaitInfo));
    }
    local_timeout = timeout;
    if (local_pWaitInfo) {
        transform_tohost_VkSemaphoreWaitInfo(sResourceTracker,
                                             (VkSemaphoreWaitInfo*)(local_pWaitInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSemaphoreWaitInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkSemaphoreWaitInfo*)(local_pWaitInfo), countPtr);
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkWaitSemaphores = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkWaitSemaphores);
    uint8_t* streamPtr = stream->reserve(packetSize_vkWaitSemaphores);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkWaitSemaphores = OP_vkWaitSemaphores;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkWaitSemaphores, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkWaitSemaphores, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkSemaphoreWaitInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkSemaphoreWaitInfo*)(local_pWaitInfo), streamPtrPtr);
    memcpy(*streamPtrPtr, (uint64_t*)&local_timeout, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkWaitSemaphores), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkWaitSemaphores_VkResult_return = (VkResult)0;
    stream->read(&vkWaitSemaphores_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkWaitSemaphores_VkResult_return;
}

VkResult VkEncoder::vkSignalSemaphore(VkDevice device, const VkSemaphoreSignalInfo* pSignalInfo,
                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkSignalSemaphore in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkSignalSemaphore(device:%p, pSignalInfo:%p)", device, pSignalInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSemaphoreSignalInfo* local_pSignalInfo;
    local_device = device;
    local_pSignalInfo = nullptr;
    if (pSignalInfo) {
        local_pSignalInfo =
            (VkSemaphoreSignalInfo*)pool->alloc(sizeof(const VkSemaphoreSignalInfo));
        deepcopy_VkSemaphoreSignalInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSignalInfo,
                                       (VkSemaphoreSignalInfo*)(local_pSignalInfo));
    }
    if (local_pSignalInfo) {
        transform_tohost_VkSemaphoreSignalInfo(sResourceTracker,
                                               (VkSemaphoreSignalInfo*)(local_pSignalInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSemaphoreSignalInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkSemaphoreSignalInfo*)(local_pSignalInfo), countPtr);
    }
    uint32_t packetSize_vkSignalSemaphore =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkSignalSemaphore);
    uint8_t* streamPtr = stream->reserve(packetSize_vkSignalSemaphore);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkSignalSemaphore = OP_vkSignalSemaphore;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkSignalSemaphore, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkSignalSemaphore, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkSemaphoreSignalInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkSemaphoreSignalInfo*)(local_pSignalInfo),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkSignalSemaphore), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkSignalSemaphore_VkResult_return = (VkResult)0;
    stream->read(&vkSignalSemaphore_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkSignalSemaphore_VkResult_return;
}

VkDeviceAddress VkEncoder::vkGetBufferDeviceAddress(VkDevice device,
                                                    const VkBufferDeviceAddressInfo* pInfo,
                                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBufferDeviceAddress in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetBufferDeviceAddress(device:%p, pInfo:%p)", device, pInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferDeviceAddressInfo* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo =
            (VkBufferDeviceAddressInfo*)pool->alloc(sizeof(const VkBufferDeviceAddressInfo));
        deepcopy_VkBufferDeviceAddressInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                           (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkBufferDeviceAddressInfo(sResourceTracker,
                                                   (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferDeviceAddressInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBufferDeviceAddressInfo*)(local_pInfo), countPtr);
    }
    uint32_t packetSize_vkGetBufferDeviceAddress =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetBufferDeviceAddress);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBufferDeviceAddress);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBufferDeviceAddress = OP_vkGetBufferDeviceAddress;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBufferDeviceAddress, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBufferDeviceAddress, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferDeviceAddressInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBufferDeviceAddressInfo*)(local_pInfo),
                                              streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetBufferDeviceAddress), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkDeviceAddress vkGetBufferDeviceAddress_VkDeviceAddress_return = (VkDeviceAddress)0;
    stream->read(&vkGetBufferDeviceAddress_VkDeviceAddress_return, sizeof(VkDeviceAddress));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetBufferDeviceAddress_VkDeviceAddress_return;
}

uint64_t VkEncoder::vkGetBufferOpaqueCaptureAddress(VkDevice device,
                                                    const VkBufferDeviceAddressInfo* pInfo,
                                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBufferOpaqueCaptureAddress in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetBufferOpaqueCaptureAddress(device:%p, pInfo:%p)", device, pInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferDeviceAddressInfo* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo =
            (VkBufferDeviceAddressInfo*)pool->alloc(sizeof(const VkBufferDeviceAddressInfo));
        deepcopy_VkBufferDeviceAddressInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                           (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkBufferDeviceAddressInfo(sResourceTracker,
                                                   (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferDeviceAddressInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBufferDeviceAddressInfo*)(local_pInfo), countPtr);
    }
    uint32_t packetSize_vkGetBufferOpaqueCaptureAddress =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetBufferOpaqueCaptureAddress);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBufferOpaqueCaptureAddress);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBufferOpaqueCaptureAddress = OP_vkGetBufferOpaqueCaptureAddress;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBufferOpaqueCaptureAddress, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBufferOpaqueCaptureAddress, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferDeviceAddressInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBufferDeviceAddressInfo*)(local_pInfo),
                                              streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetBufferOpaqueCaptureAddress), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    uint64_t vkGetBufferOpaqueCaptureAddress_uint64_t_return = (uint64_t)0;
    stream->read(&vkGetBufferOpaqueCaptureAddress_uint64_t_return, sizeof(uint64_t));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetBufferOpaqueCaptureAddress_uint64_t_return;
}

uint64_t VkEncoder::vkGetDeviceMemoryOpaqueCaptureAddress(
    VkDevice device, const VkDeviceMemoryOpaqueCaptureAddressInfo* pInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceMemoryOpaqueCaptureAddress in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDeviceMemoryOpaqueCaptureAddress(device:%p, pInfo:%p)", device, pInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemoryOpaqueCaptureAddressInfo* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceMemoryOpaqueCaptureAddressInfo*)pool->alloc(
            sizeof(const VkDeviceMemoryOpaqueCaptureAddressInfo));
        deepcopy_VkDeviceMemoryOpaqueCaptureAddressInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
            (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceMemoryOpaqueCaptureAddressInfo(
            sResourceTracker, (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceMemoryOpaqueCaptureAddressInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo), countPtr);
    }
    uint32_t packetSize_vkGetDeviceMemoryOpaqueCaptureAddress =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceMemoryOpaqueCaptureAddress);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceMemoryOpaqueCaptureAddress);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceMemoryOpaqueCaptureAddress =
        OP_vkGetDeviceMemoryOpaqueCaptureAddress;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceMemoryOpaqueCaptureAddress, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceMemoryOpaqueCaptureAddress, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceMemoryOpaqueCaptureAddressInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo),
        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetDeviceMemoryOpaqueCaptureAddress),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    uint64_t vkGetDeviceMemoryOpaqueCaptureAddress_uint64_t_return = (uint64_t)0;
    stream->read(&vkGetDeviceMemoryOpaqueCaptureAddress_uint64_t_return, sizeof(uint64_t));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetDeviceMemoryOpaqueCaptureAddress_uint64_t_return;
}

#endif
#ifdef VK_VERSION_1_3
VkResult VkEncoder::vkGetPhysicalDeviceToolProperties(
    VkPhysicalDevice physicalDevice, uint32_t* pToolCount,
    VkPhysicalDeviceToolProperties* pToolProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceToolProperties in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceToolProperties(physicalDevice:%p, pToolCount:%p, pToolProperties:%p)",
        physicalDevice, pToolCount, pToolProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pToolCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pToolProperties) {
            if (pToolCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
                    count_VkPhysicalDeviceToolProperties(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkPhysicalDeviceToolProperties*)(pToolProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceToolProperties =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceToolProperties);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceToolProperties);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceToolProperties = OP_vkGetPhysicalDeviceToolProperties;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceToolProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceToolProperties, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pToolCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pToolCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pToolCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pToolProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pToolProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
            reservedmarshal_VkPhysicalDeviceToolProperties(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkPhysicalDeviceToolProperties*)(pToolProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceToolProperties), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pToolCount;
    check_pToolCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pToolCount) {
        if (!(check_pToolCount)) {
            fprintf(stderr, "fatal: pToolCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pToolCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkPhysicalDeviceToolProperties* check_pToolProperties;
    check_pToolProperties = (VkPhysicalDeviceToolProperties*)(uintptr_t)stream->getBe64();
    if (pToolProperties) {
        if (!(check_pToolProperties)) {
            fprintf(stderr, "fatal: pToolProperties inconsistent between guest and host\n");
        }
        if (pToolCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
                unmarshal_VkPhysicalDeviceToolProperties(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkPhysicalDeviceToolProperties*)(pToolProperties + i));
            }
        }
    }
    if (pToolCount) {
        if (pToolProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
                transform_fromhost_VkPhysicalDeviceToolProperties(
                    sResourceTracker, (VkPhysicalDeviceToolProperties*)(pToolProperties + i));
            }
        }
    }
    VkResult vkGetPhysicalDeviceToolProperties_VkResult_return = (VkResult)0;
    stream->read(&vkGetPhysicalDeviceToolProperties_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPhysicalDeviceToolProperties_VkResult_return;
}

VkResult VkEncoder::vkCreatePrivateDataSlot(VkDevice device,
                                            const VkPrivateDataSlotCreateInfo* pCreateInfo,
                                            const VkAllocationCallbacks* pAllocator,
                                            VkPrivateDataSlot* pPrivateDataSlot, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreatePrivateDataSlot in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreatePrivateDataSlot(device:%p, pCreateInfo:%p, pAllocator:%p, pPrivateDataSlot:%p)",
        device, pCreateInfo, pAllocator, pPrivateDataSlot);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPrivateDataSlotCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkPrivateDataSlotCreateInfo*)pool->alloc(sizeof(const VkPrivateDataSlotCreateInfo));
        deepcopy_VkPrivateDataSlotCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                             (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkPrivateDataSlotCreateInfo(
            sResourceTracker, (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPrivateDataSlotCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo),
                                          countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreatePrivateDataSlot =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreatePrivateDataSlot);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreatePrivateDataSlot);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreatePrivateDataSlot = OP_vkCreatePrivateDataSlot;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreatePrivateDataSlot, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreatePrivateDataSlot, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPrivateDataSlotCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo),
                                                streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    uint64_t cgen_var_2 = (uint64_t)(*pPrivateDataSlot);
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreatePrivateDataSlot), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    (*pPrivateDataSlot) = (VkPrivateDataSlot)stream->getBe64();
    VkResult vkCreatePrivateDataSlot_VkResult_return = (VkResult)0;
    stream->read(&vkCreatePrivateDataSlot_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreatePrivateDataSlot_VkResult_return;
}

void VkEncoder::vkDestroyPrivateDataSlot(VkDevice device, VkPrivateDataSlot privateDataSlot,
                                         const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyPrivateDataSlot in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyPrivateDataSlot(device:%p, pAllocator:%p)", device, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPrivateDataSlot local_privateDataSlot;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_privateDataSlot = privateDataSlot;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyPrivateDataSlot =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyPrivateDataSlot);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyPrivateDataSlot);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyPrivateDataSlot = OP_vkDestroyPrivateDataSlot;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyPrivateDataSlot, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyPrivateDataSlot, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1 = (uint64_t)local_privateDataSlot;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyPrivateDataSlot), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkSetPrivateData(VkDevice device, VkObjectType objectType,
                                     uint64_t objectHandle, VkPrivateDataSlot privateDataSlot,
                                     uint64_t data, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkSetPrivateData in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkSetPrivateData(device:%p, objectHandle:%ld, data:%ld)", device,
                      objectHandle, data);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkObjectType local_objectType;
    uint64_t local_objectHandle;
    VkPrivateDataSlot local_privateDataSlot;
    uint64_t local_data;
    local_device = device;
    local_objectType = objectType;
    local_objectHandle = objectHandle;
    local_privateDataSlot = privateDataSlot;
    local_data = data;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkObjectType);
        *countPtr += sizeof(uint64_t);
        *countPtr += 8;
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkSetPrivateData = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkSetPrivateData);
    uint8_t* streamPtr = stream->reserve(packetSize_vkSetPrivateData);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkSetPrivateData = OP_vkSetPrivateData;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkSetPrivateData, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkSetPrivateData, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkObjectType*)&local_objectType, sizeof(VkObjectType));
    *streamPtrPtr += sizeof(VkObjectType);
    memcpy(*streamPtrPtr, (uint64_t*)&local_objectHandle, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    uint64_t cgen_var_1 = (uint64_t)local_privateDataSlot;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    memcpy(*streamPtrPtr, (uint64_t*)&local_data, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkSetPrivateData), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkSetPrivateData_VkResult_return = (VkResult)0;
    stream->read(&vkSetPrivateData_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkSetPrivateData_VkResult_return;
}

void VkEncoder::vkGetPrivateData(VkDevice device, VkObjectType objectType, uint64_t objectHandle,
                                 VkPrivateDataSlot privateDataSlot, uint64_t* pData,
                                 uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPrivateData in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPrivateData(device:%p, objectHandle:%ld, pData:%p)", device,
                      objectHandle, pData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkObjectType local_objectType;
    uint64_t local_objectHandle;
    VkPrivateDataSlot local_privateDataSlot;
    local_device = device;
    local_objectType = objectType;
    local_objectHandle = objectHandle;
    local_privateDataSlot = privateDataSlot;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkObjectType);
        *countPtr += sizeof(uint64_t);
        *countPtr += 8;
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkGetPrivateData = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetPrivateData);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPrivateData);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPrivateData = OP_vkGetPrivateData;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPrivateData, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPrivateData, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkObjectType*)&local_objectType, sizeof(VkObjectType));
    *streamPtrPtr += sizeof(VkObjectType);
    memcpy(*streamPtrPtr, (uint64_t*)&local_objectHandle, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    uint64_t cgen_var_1 = (uint64_t)local_privateDataSlot;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    memcpy(*streamPtrPtr, (uint64_t*)pData, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPrivateData), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((uint64_t*)pData, sizeof(uint64_t));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetEvent2(VkCommandBuffer commandBuffer, VkEvent event,
                               const VkDependencyInfo* pDependencyInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetEvent2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetEvent2(commandBuffer:%p, event:%p, pDependencyInfo:%p)",
                      commandBuffer, event, pDependencyInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkEvent local_event;
    VkDependencyInfo* local_pDependencyInfo;
    local_commandBuffer = commandBuffer;
    local_event = event;
    local_pDependencyInfo = nullptr;
    if (pDependencyInfo) {
        local_pDependencyInfo = (VkDependencyInfo*)pool->alloc(sizeof(const VkDependencyInfo));
        deepcopy_VkDependencyInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDependencyInfo,
                                  (VkDependencyInfo*)(local_pDependencyInfo));
    }
    if (local_pDependencyInfo) {
        transform_tohost_VkDependencyInfo(sResourceTracker,
                                          (VkDependencyInfo*)(local_pDependencyInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkDependencyInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkDependencyInfo*)(local_pDependencyInfo), countPtr);
    }
    uint32_t packetSize_vkCmdSetEvent2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetEvent2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetEvent2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetEvent2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetEvent2 = OP_vkCmdSetEvent2;
    memcpy(streamPtr, &opcode_vkCmdSetEvent2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetEvent2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDependencyInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkDependencyInfo*)(local_pDependencyInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetEvent2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdResetEvent2(VkCommandBuffer commandBuffer, VkEvent event,
                                 VkPipelineStageFlags2 stageMask, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdResetEvent2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdResetEvent2(commandBuffer:%p, event:%p)", commandBuffer, event);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkEvent local_event;
    VkPipelineStageFlags2 local_stageMask;
    local_commandBuffer = commandBuffer;
    local_event = event;
    local_stageMask = stageMask;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags2);
    }
    uint32_t packetSize_vkCmdResetEvent2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdResetEvent2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdResetEvent2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdResetEvent2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdResetEvent2 = OP_vkCmdResetEvent2;
    memcpy(streamPtr, &opcode_vkCmdResetEvent2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdResetEvent2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkPipelineStageFlags2*)&local_stageMask, sizeof(VkPipelineStageFlags2));
    *streamPtrPtr += sizeof(VkPipelineStageFlags2);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdResetEvent2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdWaitEvents2(VkCommandBuffer commandBuffer, uint32_t eventCount,
                                 const VkEvent* pEvents, const VkDependencyInfo* pDependencyInfos,
                                 uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdWaitEvents2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdWaitEvents2(commandBuffer:%p, eventCount:%d, pEvents:%p, pDependencyInfos:%p)",
        commandBuffer, eventCount, pEvents, pDependencyInfos);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_eventCount;
    VkEvent* local_pEvents;
    VkDependencyInfo* local_pDependencyInfos;
    local_commandBuffer = commandBuffer;
    local_eventCount = eventCount;
    // Avoiding deepcopy for pEvents
    local_pEvents = (VkEvent*)pEvents;
    local_pDependencyInfos = nullptr;
    if (pDependencyInfos) {
        local_pDependencyInfos =
            (VkDependencyInfo*)pool->alloc(((eventCount)) * sizeof(const VkDependencyInfo));
        for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
            deepcopy_VkDependencyInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDependencyInfos + i,
                                      (VkDependencyInfo*)(local_pDependencyInfos + i));
        }
    }
    if (local_pDependencyInfos) {
        for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
            transform_tohost_VkDependencyInfo(sResourceTracker,
                                              (VkDependencyInfo*)(local_pDependencyInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((eventCount))) {
            *countPtr += ((eventCount)) * 8;
        }
        for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
            count_VkDependencyInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkDependencyInfo*)(local_pDependencyInfos + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdWaitEvents2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdWaitEvents2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdWaitEvents2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdWaitEvents2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdWaitEvents2 = OP_vkCmdWaitEvents2;
    memcpy(streamPtr, &opcode_vkCmdWaitEvents2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdWaitEvents2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_eventCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((eventCount))) {
        uint8_t* cgen_var_0_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((eventCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkEvent(local_pEvents[k]);
            memcpy(cgen_var_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((eventCount));
    }
    for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
        reservedmarshal_VkDependencyInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkDependencyInfo*)(local_pDependencyInfos + i),
                                         streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdWaitEvents2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdPipelineBarrier2(VkCommandBuffer commandBuffer,
                                      const VkDependencyInfo* pDependencyInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdPipelineBarrier2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdPipelineBarrier2(commandBuffer:%p, pDependencyInfo:%p)", commandBuffer,
                      pDependencyInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkDependencyInfo* local_pDependencyInfo;
    local_commandBuffer = commandBuffer;
    local_pDependencyInfo = nullptr;
    if (pDependencyInfo) {
        local_pDependencyInfo = (VkDependencyInfo*)pool->alloc(sizeof(const VkDependencyInfo));
        deepcopy_VkDependencyInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDependencyInfo,
                                  (VkDependencyInfo*)(local_pDependencyInfo));
    }
    if (local_pDependencyInfo) {
        transform_tohost_VkDependencyInfo(sResourceTracker,
                                          (VkDependencyInfo*)(local_pDependencyInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDependencyInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkDependencyInfo*)(local_pDependencyInfo), countPtr);
    }
    uint32_t packetSize_vkCmdPipelineBarrier2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdPipelineBarrier2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdPipelineBarrier2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdPipelineBarrier2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdPipelineBarrier2 = OP_vkCmdPipelineBarrier2;
    memcpy(streamPtr, &opcode_vkCmdPipelineBarrier2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdPipelineBarrier2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkDependencyInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkDependencyInfo*)(local_pDependencyInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdPipelineBarrier2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdWriteTimestamp2(VkCommandBuffer commandBuffer, VkPipelineStageFlags2 stage,
                                     VkQueryPool queryPool, uint32_t query, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdWriteTimestamp2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdWriteTimestamp2(commandBuffer:%p, queryPool:%p, query:%d)",
                      commandBuffer, queryPool, query);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineStageFlags2 local_stage;
    VkQueryPool local_queryPool;
    uint32_t local_query;
    local_commandBuffer = commandBuffer;
    local_stage = stage;
    local_queryPool = queryPool;
    local_query = query;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags2);
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdWriteTimestamp2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdWriteTimestamp2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdWriteTimestamp2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdWriteTimestamp2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdWriteTimestamp2 = OP_vkCmdWriteTimestamp2;
    memcpy(streamPtr, &opcode_vkCmdWriteTimestamp2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdWriteTimestamp2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPipelineStageFlags2*)&local_stage, sizeof(VkPipelineStageFlags2));
    *streamPtrPtr += sizeof(VkPipelineStageFlags2);
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_query, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdWriteTimestamp2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkQueueSubmit2(VkQueue queue, uint32_t submitCount,
                                   const VkSubmitInfo2* pSubmits, VkFence fence, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueSubmit2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueSubmit2(queue:%p, submitCount:%d, pSubmits:%p, fence:%p)", queue,
                      submitCount, pSubmits, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_submitCount;
    VkSubmitInfo2* local_pSubmits;
    VkFence local_fence;
    local_queue = queue;
    local_submitCount = submitCount;
    local_pSubmits = nullptr;
    if (pSubmits) {
        local_pSubmits = (VkSubmitInfo2*)pool->alloc(((submitCount)) * sizeof(const VkSubmitInfo2));
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            deepcopy_VkSubmitInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubmits + i,
                                   (VkSubmitInfo2*)(local_pSubmits + i));
        }
    }
    local_fence = fence;
    if (local_pSubmits) {
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            transform_tohost_VkSubmitInfo2(sResourceTracker, (VkSubmitInfo2*)(local_pSubmits + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            count_VkSubmitInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkSubmitInfo2*)(local_pSubmits + i), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueSubmit2 = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueSubmit2);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueSubmit2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueSubmit2 = OP_vkQueueSubmit2;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueSubmit2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueSubmit2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_submitCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
        reservedmarshal_VkSubmitInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubmitInfo2*)(local_pSubmits + i), streamPtrPtr);
    }
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkQueueSubmit2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkQueueSubmit2_VkResult_return = (VkResult)0;
    stream->read(&vkQueueSubmit2_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkQueueSubmit2_VkResult_return;
}

void VkEncoder::vkCmdCopyBuffer2(VkCommandBuffer commandBuffer,
                                 const VkCopyBufferInfo2* pCopyBufferInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyBuffer2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyBuffer2(commandBuffer:%p, pCopyBufferInfo:%p)", commandBuffer,
                      pCopyBufferInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyBufferInfo2* local_pCopyBufferInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyBufferInfo = nullptr;
    if (pCopyBufferInfo) {
        local_pCopyBufferInfo = (VkCopyBufferInfo2*)pool->alloc(sizeof(const VkCopyBufferInfo2));
        deepcopy_VkCopyBufferInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyBufferInfo,
                                   (VkCopyBufferInfo2*)(local_pCopyBufferInfo));
    }
    if (local_pCopyBufferInfo) {
        transform_tohost_VkCopyBufferInfo2(sResourceTracker,
                                           (VkCopyBufferInfo2*)(local_pCopyBufferInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyBufferInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkCopyBufferInfo2*)(local_pCopyBufferInfo), countPtr);
    }
    uint32_t packetSize_vkCmdCopyBuffer2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyBuffer2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyBuffer2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyBuffer2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyBuffer2 = OP_vkCmdCopyBuffer2;
    memcpy(streamPtr, &opcode_vkCmdCopyBuffer2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyBuffer2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyBufferInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkCopyBufferInfo2*)(local_pCopyBufferInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdCopyBuffer2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyImage2(VkCommandBuffer commandBuffer,
                                const VkCopyImageInfo2* pCopyImageInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyImage2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyImage2(commandBuffer:%p, pCopyImageInfo:%p)", commandBuffer,
                      pCopyImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyImageInfo2* local_pCopyImageInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyImageInfo = nullptr;
    if (pCopyImageInfo) {
        local_pCopyImageInfo = (VkCopyImageInfo2*)pool->alloc(sizeof(const VkCopyImageInfo2));
        deepcopy_VkCopyImageInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyImageInfo,
                                  (VkCopyImageInfo2*)(local_pCopyImageInfo));
    }
    if (local_pCopyImageInfo) {
        transform_tohost_VkCopyImageInfo2(sResourceTracker,
                                          (VkCopyImageInfo2*)(local_pCopyImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkCopyImageInfo2*)(local_pCopyImageInfo), countPtr);
    }
    uint32_t packetSize_vkCmdCopyImage2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyImage2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyImage2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyImage2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyImage2 = OP_vkCmdCopyImage2;
    memcpy(streamPtr, &opcode_vkCmdCopyImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyImageInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkCopyImageInfo2*)(local_pCopyImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdCopyImage2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyBufferToImage2(VkCommandBuffer commandBuffer,
                                        const VkCopyBufferToImageInfo2* pCopyBufferToImageInfo,
                                        uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyBufferToImage2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyBufferToImage2(commandBuffer:%p, pCopyBufferToImageInfo:%p)",
                      commandBuffer, pCopyBufferToImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyBufferToImageInfo2* local_pCopyBufferToImageInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyBufferToImageInfo = nullptr;
    if (pCopyBufferToImageInfo) {
        local_pCopyBufferToImageInfo =
            (VkCopyBufferToImageInfo2*)pool->alloc(sizeof(const VkCopyBufferToImageInfo2));
        deepcopy_VkCopyBufferToImageInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyBufferToImageInfo,
            (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo));
    }
    if (local_pCopyBufferToImageInfo) {
        transform_tohost_VkCopyBufferToImageInfo2(
            sResourceTracker, (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyBufferToImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo),
                                       countPtr);
    }
    uint32_t packetSize_vkCmdCopyBufferToImage2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyBufferToImage2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyBufferToImage2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyBufferToImage2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyBufferToImage2 = OP_vkCmdCopyBufferToImage2;
    memcpy(streamPtr, &opcode_vkCmdCopyBufferToImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyBufferToImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyBufferToImageInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyBufferToImage2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyImageToBuffer2(VkCommandBuffer commandBuffer,
                                        const VkCopyImageToBufferInfo2* pCopyImageToBufferInfo,
                                        uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyImageToBuffer2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyImageToBuffer2(commandBuffer:%p, pCopyImageToBufferInfo:%p)",
                      commandBuffer, pCopyImageToBufferInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyImageToBufferInfo2* local_pCopyImageToBufferInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyImageToBufferInfo = nullptr;
    if (pCopyImageToBufferInfo) {
        local_pCopyImageToBufferInfo =
            (VkCopyImageToBufferInfo2*)pool->alloc(sizeof(const VkCopyImageToBufferInfo2));
        deepcopy_VkCopyImageToBufferInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyImageToBufferInfo,
            (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo));
    }
    if (local_pCopyImageToBufferInfo) {
        transform_tohost_VkCopyImageToBufferInfo2(
            sResourceTracker, (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyImageToBufferInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo),
                                       countPtr);
    }
    uint32_t packetSize_vkCmdCopyImageToBuffer2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyImageToBuffer2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyImageToBuffer2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyImageToBuffer2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyImageToBuffer2 = OP_vkCmdCopyImageToBuffer2;
    memcpy(streamPtr, &opcode_vkCmdCopyImageToBuffer2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyImageToBuffer2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyImageToBufferInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyImageToBuffer2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBlitImage2(VkCommandBuffer commandBuffer,
                                const VkBlitImageInfo2* pBlitImageInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBlitImage2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBlitImage2(commandBuffer:%p, pBlitImageInfo:%p)", commandBuffer,
                      pBlitImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBlitImageInfo2* local_pBlitImageInfo;
    local_commandBuffer = commandBuffer;
    local_pBlitImageInfo = nullptr;
    if (pBlitImageInfo) {
        local_pBlitImageInfo = (VkBlitImageInfo2*)pool->alloc(sizeof(const VkBlitImageInfo2));
        deepcopy_VkBlitImageInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBlitImageInfo,
                                  (VkBlitImageInfo2*)(local_pBlitImageInfo));
    }
    if (local_pBlitImageInfo) {
        transform_tohost_VkBlitImageInfo2(sResourceTracker,
                                          (VkBlitImageInfo2*)(local_pBlitImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBlitImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkBlitImageInfo2*)(local_pBlitImageInfo), countPtr);
    }
    uint32_t packetSize_vkCmdBlitImage2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBlitImage2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBlitImage2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBlitImage2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBlitImage2 = OP_vkCmdBlitImage2;
    memcpy(streamPtr, &opcode_vkCmdBlitImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBlitImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkBlitImageInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkBlitImageInfo2*)(local_pBlitImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdBlitImage2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdResolveImage2(VkCommandBuffer commandBuffer,
                                   const VkResolveImageInfo2* pResolveImageInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdResolveImage2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdResolveImage2(commandBuffer:%p, pResolveImageInfo:%p)", commandBuffer,
                      pResolveImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkResolveImageInfo2* local_pResolveImageInfo;
    local_commandBuffer = commandBuffer;
    local_pResolveImageInfo = nullptr;
    if (pResolveImageInfo) {
        local_pResolveImageInfo =
            (VkResolveImageInfo2*)pool->alloc(sizeof(const VkResolveImageInfo2));
        deepcopy_VkResolveImageInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pResolveImageInfo,
                                     (VkResolveImageInfo2*)(local_pResolveImageInfo));
    }
    if (local_pResolveImageInfo) {
        transform_tohost_VkResolveImageInfo2(sResourceTracker,
                                             (VkResolveImageInfo2*)(local_pResolveImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkResolveImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkResolveImageInfo2*)(local_pResolveImageInfo), countPtr);
    }
    uint32_t packetSize_vkCmdResolveImage2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdResolveImage2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdResolveImage2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdResolveImage2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdResolveImage2 = OP_vkCmdResolveImage2;
    memcpy(streamPtr, &opcode_vkCmdResolveImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdResolveImage2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkResolveImageInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkResolveImageInfo2*)(local_pResolveImageInfo),
                                        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdResolveImage2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBeginRendering(VkCommandBuffer commandBuffer,
                                    const VkRenderingInfo* pRenderingInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginRendering in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBeginRendering(commandBuffer:%p, pRenderingInfo:%p)", commandBuffer,
                      pRenderingInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkRenderingInfo* local_pRenderingInfo;
    local_commandBuffer = commandBuffer;
    local_pRenderingInfo = nullptr;
    if (pRenderingInfo) {
        local_pRenderingInfo = (VkRenderingInfo*)pool->alloc(sizeof(const VkRenderingInfo));
        deepcopy_VkRenderingInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRenderingInfo,
                                 (VkRenderingInfo*)(local_pRenderingInfo));
    }
    if (local_pRenderingInfo) {
        transform_tohost_VkRenderingInfo(sResourceTracker,
                                         (VkRenderingInfo*)(local_pRenderingInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderingInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                              (VkRenderingInfo*)(local_pRenderingInfo), countPtr);
    }
    uint32_t packetSize_vkCmdBeginRendering = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBeginRendering);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginRendering -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginRendering);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginRendering = OP_vkCmdBeginRendering;
    memcpy(streamPtr, &opcode_vkCmdBeginRendering, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginRendering, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkRenderingInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkRenderingInfo*)(local_pRenderingInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBeginRendering), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndRendering(VkCommandBuffer commandBuffer, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndRendering in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdEndRendering(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    local_commandBuffer = commandBuffer;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkCmdEndRendering = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdEndRendering);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndRendering -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndRendering);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndRendering = OP_vkCmdEndRendering;
    memcpy(streamPtr, &opcode_vkCmdEndRendering, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndRendering, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdEndRendering), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetCullMode(VkCommandBuffer commandBuffer, VkCullModeFlags cullMode,
                                 uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetCullMode in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetCullMode(commandBuffer:%p, cullMode:%d)", commandBuffer, cullMode);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCullModeFlags local_cullMode;
    local_commandBuffer = commandBuffer;
    local_cullMode = cullMode;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCullModeFlags);
    }
    uint32_t packetSize_vkCmdSetCullMode = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetCullMode);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetCullMode -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetCullMode);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetCullMode = OP_vkCmdSetCullMode;
    memcpy(streamPtr, &opcode_vkCmdSetCullMode, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetCullMode, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkCullModeFlags*)&local_cullMode, sizeof(VkCullModeFlags));
    *streamPtrPtr += sizeof(VkCullModeFlags);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetCullMode), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetFrontFace(VkCommandBuffer commandBuffer, VkFrontFace frontFace,
                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetFrontFace in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetFrontFace(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkFrontFace local_frontFace;
    local_commandBuffer = commandBuffer;
    local_frontFace = frontFace;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFrontFace);
    }
    uint32_t packetSize_vkCmdSetFrontFace = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetFrontFace);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetFrontFace -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetFrontFace);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetFrontFace = OP_vkCmdSetFrontFace;
    memcpy(streamPtr, &opcode_vkCmdSetFrontFace, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetFrontFace, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkFrontFace*)&local_frontFace, sizeof(VkFrontFace));
    *streamPtrPtr += sizeof(VkFrontFace);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetFrontFace), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetPrimitiveTopology(VkCommandBuffer commandBuffer,
                                          VkPrimitiveTopology primitiveTopology, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetPrimitiveTopology in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetPrimitiveTopology(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPrimitiveTopology local_primitiveTopology;
    local_commandBuffer = commandBuffer;
    local_primitiveTopology = primitiveTopology;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPrimitiveTopology);
    }
    uint32_t packetSize_vkCmdSetPrimitiveTopology = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetPrimitiveTopology);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetPrimitiveTopology -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetPrimitiveTopology);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetPrimitiveTopology = OP_vkCmdSetPrimitiveTopology;
    memcpy(streamPtr, &opcode_vkCmdSetPrimitiveTopology, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetPrimitiveTopology, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPrimitiveTopology*)&local_primitiveTopology,
           sizeof(VkPrimitiveTopology));
    *streamPtrPtr += sizeof(VkPrimitiveTopology);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetPrimitiveTopology), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetViewportWithCount(VkCommandBuffer commandBuffer, uint32_t viewportCount,
                                          const VkViewport* pViewports, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetViewportWithCount in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetViewportWithCount(commandBuffer:%p, viewportCount:%d, pViewports:%p)",
        commandBuffer, viewportCount, pViewports);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_viewportCount;
    VkViewport* local_pViewports;
    local_commandBuffer = commandBuffer;
    local_viewportCount = viewportCount;
    local_pViewports = nullptr;
    if (pViewports) {
        local_pViewports = (VkViewport*)pool->alloc(((viewportCount)) * sizeof(const VkViewport));
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            deepcopy_VkViewport(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pViewports + i,
                                (VkViewport*)(local_pViewports + i));
        }
    }
    if (local_pViewports) {
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            transform_tohost_VkViewport(sResourceTracker, (VkViewport*)(local_pViewports + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            count_VkViewport(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                             (VkViewport*)(local_pViewports + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdSetViewportWithCount = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetViewportWithCount);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetViewportWithCount -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetViewportWithCount);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetViewportWithCount = OP_vkCmdSetViewportWithCount;
    memcpy(streamPtr, &opcode_vkCmdSetViewportWithCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetViewportWithCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_viewportCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
        reservedmarshal_VkViewport(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkViewport*)(local_pViewports + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetViewportWithCount), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetScissorWithCount(VkCommandBuffer commandBuffer, uint32_t scissorCount,
                                         const VkRect2D* pScissors, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetScissorWithCount in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetScissorWithCount(commandBuffer:%p, scissorCount:%d, pScissors:%p)",
                      commandBuffer, scissorCount, pScissors);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_scissorCount;
    VkRect2D* local_pScissors;
    local_commandBuffer = commandBuffer;
    local_scissorCount = scissorCount;
    local_pScissors = nullptr;
    if (pScissors) {
        local_pScissors = (VkRect2D*)pool->alloc(((scissorCount)) * sizeof(const VkRect2D));
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            deepcopy_VkRect2D(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pScissors + i,
                              (VkRect2D*)(local_pScissors + i));
        }
    }
    if (local_pScissors) {
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            transform_tohost_VkRect2D(sResourceTracker, (VkRect2D*)(local_pScissors + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            count_VkRect2D(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                           (VkRect2D*)(local_pScissors + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdSetScissorWithCount = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetScissorWithCount);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetScissorWithCount -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetScissorWithCount);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetScissorWithCount = OP_vkCmdSetScissorWithCount;
    memcpy(streamPtr, &opcode_vkCmdSetScissorWithCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetScissorWithCount, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_scissorCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
        reservedmarshal_VkRect2D(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkRect2D*)(local_pScissors + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetScissorWithCount), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBindVertexBuffers2(VkCommandBuffer commandBuffer, uint32_t firstBinding,
                                        uint32_t bindingCount, const VkBuffer* pBuffers,
                                        const VkDeviceSize* pOffsets, const VkDeviceSize* pSizes,
                                        const VkDeviceSize* pStrides, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindVertexBuffers2 in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBindVertexBuffers2(commandBuffer:%p, firstBinding:%d, bindingCount:%d, pBuffers:%p, "
        "pOffsets:%p, pSizes:%p, pStrides:%p)",
        commandBuffer, firstBinding, bindingCount, pBuffers, pOffsets, pSizes, pStrides);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstBinding;
    uint32_t local_bindingCount;
    VkBuffer* local_pBuffers;
    VkDeviceSize* local_pOffsets;
    VkDeviceSize* local_pSizes;
    VkDeviceSize* local_pStrides;
    local_commandBuffer = commandBuffer;
    local_firstBinding = firstBinding;
    local_bindingCount = bindingCount;
    // Avoiding deepcopy for pBuffers
    local_pBuffers = (VkBuffer*)pBuffers;
    // Avoiding deepcopy for pOffsets
    local_pOffsets = (VkDeviceSize*)pOffsets;
    // Avoiding deepcopy for pSizes
    local_pSizes = (VkDeviceSize*)pSizes;
    // Avoiding deepcopy for pStrides
    local_pStrides = (VkDeviceSize*)pStrides;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBuffers) {
            if (((bindingCount))) {
                *countPtr += ((bindingCount)) * 8;
            }
        }
        *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pSizes) {
            *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pStrides) {
            *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        }
    }
    uint32_t packetSize_vkCmdBindVertexBuffers2 = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBindVertexBuffers2);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindVertexBuffers2 -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindVertexBuffers2);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindVertexBuffers2 = OP_vkCmdBindVertexBuffers2;
    memcpy(streamPtr, &opcode_vkCmdBindVertexBuffers2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindVertexBuffers2, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstBinding, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindingCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_0 = (uint64_t)(uintptr_t)local_pBuffers;
    memcpy((*streamPtrPtr), &cgen_var_0, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBuffers) {
        if (((bindingCount))) {
            uint8_t* cgen_var_0_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((bindingCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkBuffer(local_pBuffers[k]);
                memcpy(cgen_var_0_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((bindingCount));
        }
    }
    memcpy(*streamPtrPtr, (VkDeviceSize*)local_pOffsets, ((bindingCount)) * sizeof(VkDeviceSize));
    *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pSizes;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pSizes) {
        memcpy(*streamPtrPtr, (VkDeviceSize*)local_pSizes, ((bindingCount)) * sizeof(VkDeviceSize));
        *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pStrides;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pStrides) {
        memcpy(*streamPtrPtr, (VkDeviceSize*)local_pStrides,
               ((bindingCount)) * sizeof(VkDeviceSize));
        *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBindVertexBuffers2), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthTestEnable(VkCommandBuffer commandBuffer, VkBool32 depthTestEnable,
                                        uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthTestEnable in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthTestEnable(commandBuffer:%p, depthTestEnable:%d)",
                      commandBuffer, depthTestEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthTestEnable;
    local_commandBuffer = commandBuffer;
    local_depthTestEnable = depthTestEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthTestEnable = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthTestEnable);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthTestEnable -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthTestEnable);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthTestEnable = OP_vkCmdSetDepthTestEnable;
    memcpy(streamPtr, &opcode_vkCmdSetDepthTestEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthTestEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthTestEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthTestEnable), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthWriteEnable(VkCommandBuffer commandBuffer, VkBool32 depthWriteEnable,
                                         uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthWriteEnable in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthWriteEnable(commandBuffer:%p, depthWriteEnable:%d)",
                      commandBuffer, depthWriteEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthWriteEnable;
    local_commandBuffer = commandBuffer;
    local_depthWriteEnable = depthWriteEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthWriteEnable = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthWriteEnable);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthWriteEnable -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthWriteEnable);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthWriteEnable = OP_vkCmdSetDepthWriteEnable;
    memcpy(streamPtr, &opcode_vkCmdSetDepthWriteEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthWriteEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthWriteEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthWriteEnable), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthCompareOp(VkCommandBuffer commandBuffer, VkCompareOp depthCompareOp,
                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthCompareOp in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthCompareOp(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCompareOp local_depthCompareOp;
    local_commandBuffer = commandBuffer;
    local_depthCompareOp = depthCompareOp;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCompareOp);
    }
    uint32_t packetSize_vkCmdSetDepthCompareOp = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthCompareOp);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthCompareOp -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthCompareOp);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthCompareOp = OP_vkCmdSetDepthCompareOp;
    memcpy(streamPtr, &opcode_vkCmdSetDepthCompareOp, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthCompareOp, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkCompareOp*)&local_depthCompareOp, sizeof(VkCompareOp));
    *streamPtrPtr += sizeof(VkCompareOp);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthCompareOp), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthBoundsTestEnable(VkCommandBuffer commandBuffer,
                                              VkBool32 depthBoundsTestEnable, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthBoundsTestEnable in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthBoundsTestEnable(commandBuffer:%p, depthBoundsTestEnable:%d)",
                      commandBuffer, depthBoundsTestEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthBoundsTestEnable;
    local_commandBuffer = commandBuffer;
    local_depthBoundsTestEnable = depthBoundsTestEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthBoundsTestEnable = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetDepthBoundsTestEnable);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthBoundsTestEnable -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthBoundsTestEnable);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthBoundsTestEnable = OP_vkCmdSetDepthBoundsTestEnable;
    memcpy(streamPtr, &opcode_vkCmdSetDepthBoundsTestEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthBoundsTestEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthBoundsTestEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthBoundsTestEnable), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetStencilTestEnable(VkCommandBuffer commandBuffer, VkBool32 stencilTestEnable,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetStencilTestEnable in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetStencilTestEnable(commandBuffer:%p, stencilTestEnable:%d)",
                      commandBuffer, stencilTestEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_stencilTestEnable;
    local_commandBuffer = commandBuffer;
    local_stencilTestEnable = stencilTestEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetStencilTestEnable = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetStencilTestEnable);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetStencilTestEnable -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetStencilTestEnable);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetStencilTestEnable = OP_vkCmdSetStencilTestEnable;
    memcpy(streamPtr, &opcode_vkCmdSetStencilTestEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetStencilTestEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_stencilTestEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetStencilTestEnable), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetStencilOp(VkCommandBuffer commandBuffer, VkStencilFaceFlags faceMask,
                                  VkStencilOp failOp, VkStencilOp passOp, VkStencilOp depthFailOp,
                                  VkCompareOp compareOp, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetStencilOp in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetStencilOp(commandBuffer:%p, faceMask:%d)", commandBuffer, faceMask);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkStencilFaceFlags local_faceMask;
    VkStencilOp local_failOp;
    VkStencilOp local_passOp;
    VkStencilOp local_depthFailOp;
    VkCompareOp local_compareOp;
    local_commandBuffer = commandBuffer;
    local_faceMask = faceMask;
    local_failOp = failOp;
    local_passOp = passOp;
    local_depthFailOp = depthFailOp;
    local_compareOp = compareOp;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkStencilFaceFlags);
        *countPtr += sizeof(VkStencilOp);
        *countPtr += sizeof(VkStencilOp);
        *countPtr += sizeof(VkStencilOp);
        *countPtr += sizeof(VkCompareOp);
    }
    uint32_t packetSize_vkCmdSetStencilOp = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetStencilOp);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetStencilOp -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetStencilOp);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetStencilOp = OP_vkCmdSetStencilOp;
    memcpy(streamPtr, &opcode_vkCmdSetStencilOp, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetStencilOp, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkStencilFaceFlags*)&local_faceMask, sizeof(VkStencilFaceFlags));
    *streamPtrPtr += sizeof(VkStencilFaceFlags);
    memcpy(*streamPtrPtr, (VkStencilOp*)&local_failOp, sizeof(VkStencilOp));
    *streamPtrPtr += sizeof(VkStencilOp);
    memcpy(*streamPtrPtr, (VkStencilOp*)&local_passOp, sizeof(VkStencilOp));
    *streamPtrPtr += sizeof(VkStencilOp);
    memcpy(*streamPtrPtr, (VkStencilOp*)&local_depthFailOp, sizeof(VkStencilOp));
    *streamPtrPtr += sizeof(VkStencilOp);
    memcpy(*streamPtrPtr, (VkCompareOp*)&local_compareOp, sizeof(VkCompareOp));
    *streamPtrPtr += sizeof(VkCompareOp);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetStencilOp), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetRasterizerDiscardEnable(VkCommandBuffer commandBuffer,
                                                VkBool32 rasterizerDiscardEnable, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetRasterizerDiscardEnable in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetRasterizerDiscardEnable(commandBuffer:%p, rasterizerDiscardEnable:%d)",
        commandBuffer, rasterizerDiscardEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_rasterizerDiscardEnable;
    local_commandBuffer = commandBuffer;
    local_rasterizerDiscardEnable = rasterizerDiscardEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetRasterizerDiscardEnable = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetRasterizerDiscardEnable);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetRasterizerDiscardEnable -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetRasterizerDiscardEnable);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetRasterizerDiscardEnable = OP_vkCmdSetRasterizerDiscardEnable;
    memcpy(streamPtr, &opcode_vkCmdSetRasterizerDiscardEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetRasterizerDiscardEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_rasterizerDiscardEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetRasterizerDiscardEnable), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthBiasEnable(VkCommandBuffer commandBuffer, VkBool32 depthBiasEnable,
                                        uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthBiasEnable in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthBiasEnable(commandBuffer:%p, depthBiasEnable:%d)",
                      commandBuffer, depthBiasEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthBiasEnable;
    local_commandBuffer = commandBuffer;
    local_depthBiasEnable = depthBiasEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthBiasEnable = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthBiasEnable);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthBiasEnable -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthBiasEnable);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthBiasEnable = OP_vkCmdSetDepthBiasEnable;
    memcpy(streamPtr, &opcode_vkCmdSetDepthBiasEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthBiasEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthBiasEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthBiasEnable), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetPrimitiveRestartEnable(VkCommandBuffer commandBuffer,
                                               VkBool32 primitiveRestartEnable, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetPrimitiveRestartEnable in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetPrimitiveRestartEnable(commandBuffer:%p, primitiveRestartEnable:%d)",
                      commandBuffer, primitiveRestartEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_primitiveRestartEnable;
    local_commandBuffer = commandBuffer;
    local_primitiveRestartEnable = primitiveRestartEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetPrimitiveRestartEnable = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetPrimitiveRestartEnable);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetPrimitiveRestartEnable -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetPrimitiveRestartEnable);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetPrimitiveRestartEnable = OP_vkCmdSetPrimitiveRestartEnable;
    memcpy(streamPtr, &opcode_vkCmdSetPrimitiveRestartEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetPrimitiveRestartEnable, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_primitiveRestartEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetPrimitiveRestartEnable), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDeviceBufferMemoryRequirements(VkDevice device,
                                                    const VkDeviceBufferMemoryRequirements* pInfo,
                                                    VkMemoryRequirements2* pMemoryRequirements,
                                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceBufferMemoryRequirements in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceBufferMemoryRequirements(device:%p, pInfo:%p, pMemoryRequirements:%p)", device,
        pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceBufferMemoryRequirements* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceBufferMemoryRequirements*)pool->alloc(
            sizeof(const VkDeviceBufferMemoryRequirements));
        deepcopy_VkDeviceBufferMemoryRequirements(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                  (VkDeviceBufferMemoryRequirements*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceBufferMemoryRequirements(
            sResourceTracker, (VkDeviceBufferMemoryRequirements*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceBufferMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                               (VkDeviceBufferMemoryRequirements*)(local_pInfo),
                                               countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetDeviceBufferMemoryRequirements =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceBufferMemoryRequirements);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceBufferMemoryRequirements);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceBufferMemoryRequirements = OP_vkGetDeviceBufferMemoryRequirements;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceBufferMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceBufferMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceBufferMemoryRequirements(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkDeviceBufferMemoryRequirements*)(local_pInfo),
        streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetDeviceBufferMemoryRequirements),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDeviceImageMemoryRequirements(VkDevice device,
                                                   const VkDeviceImageMemoryRequirements* pInfo,
                                                   VkMemoryRequirements2* pMemoryRequirements,
                                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceImageMemoryRequirements in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceImageMemoryRequirements(device:%p, pInfo:%p, pMemoryRequirements:%p)", device,
        pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceImageMemoryRequirements* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceImageMemoryRequirements*)pool->alloc(
            sizeof(const VkDeviceImageMemoryRequirements));
        deepcopy_VkDeviceImageMemoryRequirements(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                 (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceImageMemoryRequirements(
            sResourceTracker, (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceImageMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                              countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetDeviceImageMemoryRequirements =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceImageMemoryRequirements);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceImageMemoryRequirements);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceImageMemoryRequirements = OP_vkGetDeviceImageMemoryRequirements;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceImageMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceImageMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceImageMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                    (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                                    streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDeviceImageMemoryRequirements), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDeviceImageSparseMemoryRequirements(
    VkDevice device, const VkDeviceImageMemoryRequirements* pInfo,
    uint32_t* pSparseMemoryRequirementCount,
    VkSparseImageMemoryRequirements2* pSparseMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceImageSparseMemoryRequirements in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceImageSparseMemoryRequirements(device:%p, pInfo:%p, "
        "pSparseMemoryRequirementCount:%p, pSparseMemoryRequirements:%p)",
        device, pInfo, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceImageMemoryRequirements* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceImageMemoryRequirements*)pool->alloc(
            sizeof(const VkDeviceImageMemoryRequirements));
        deepcopy_VkDeviceImageMemoryRequirements(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                 (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceImageMemoryRequirements(
            sResourceTracker, (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceImageMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                              countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirementCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirements) {
            if (pSparseMemoryRequirementCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                    count_VkSparseImageMemoryRequirements2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i),
                        countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetDeviceImageSparseMemoryRequirements =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceImageSparseMemoryRequirements);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceImageSparseMemoryRequirements);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceImageSparseMemoryRequirements =
        OP_vkGetDeviceImageSparseMemoryRequirements;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceImageSparseMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceImageSparseMemoryRequirements, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceImageMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                    (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                                    streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pSparseMemoryRequirementCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirementCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pSparseMemoryRequirements;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirements) {
        for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
            reservedmarshal_VkSparseImageMemoryRequirements2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDeviceImageSparseMemoryRequirements),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pSparseMemoryRequirementCount;
    check_pSparseMemoryRequirementCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirementCount) {
        if (!(check_pSparseMemoryRequirementCount)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirementCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageMemoryRequirements2* check_pSparseMemoryRequirements;
    check_pSparseMemoryRequirements =
        (VkSparseImageMemoryRequirements2*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirements) {
        if (!(check_pSparseMemoryRequirements)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirements inconsistent between guest and host\n");
        }
        if (pSparseMemoryRequirementCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                unmarshal_VkSparseImageMemoryRequirements2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    if (pSparseMemoryRequirementCount) {
        if (pSparseMemoryRequirements) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                transform_fromhost_VkSparseImageMemoryRequirements2(
                    sResourceTracker,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_dynamic_rendering
void VkEncoder::vkCmdBeginRenderingKHR(VkCommandBuffer commandBuffer,
                                       const VkRenderingInfo* pRenderingInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginRenderingKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBeginRenderingKHR(commandBuffer:%p, pRenderingInfo:%p)", commandBuffer,
                      pRenderingInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkRenderingInfo* local_pRenderingInfo;
    local_commandBuffer = commandBuffer;
    local_pRenderingInfo = nullptr;
    if (pRenderingInfo) {
        local_pRenderingInfo = (VkRenderingInfo*)pool->alloc(sizeof(const VkRenderingInfo));
        deepcopy_VkRenderingInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRenderingInfo,
                                 (VkRenderingInfo*)(local_pRenderingInfo));
    }
    if (local_pRenderingInfo) {
        transform_tohost_VkRenderingInfo(sResourceTracker,
                                         (VkRenderingInfo*)(local_pRenderingInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderingInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                              (VkRenderingInfo*)(local_pRenderingInfo), countPtr);
    }
    uint32_t packetSize_vkCmdBeginRenderingKHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBeginRenderingKHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginRenderingKHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginRenderingKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginRenderingKHR = OP_vkCmdBeginRenderingKHR;
    memcpy(streamPtr, &opcode_vkCmdBeginRenderingKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginRenderingKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkRenderingInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkRenderingInfo*)(local_pRenderingInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBeginRenderingKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndRenderingKHR(VkCommandBuffer commandBuffer, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndRenderingKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdEndRenderingKHR(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    local_commandBuffer = commandBuffer;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkCmdEndRenderingKHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdEndRenderingKHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndRenderingKHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndRenderingKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndRenderingKHR = OP_vkCmdEndRenderingKHR;
    memcpy(streamPtr, &opcode_vkCmdEndRenderingKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndRenderingKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdEndRenderingKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_get_physical_device_properties2
void VkEncoder::vkGetPhysicalDeviceFeatures2KHR(VkPhysicalDevice physicalDevice,
                                                VkPhysicalDeviceFeatures2* pFeatures,
                                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceFeatures2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPhysicalDeviceFeatures2KHR(physicalDevice:%p, pFeatures:%p)",
                      physicalDevice, pFeatures);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceFeatures2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkPhysicalDeviceFeatures2*)(pFeatures), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceFeatures2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceFeatures2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceFeatures2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceFeatures2KHR = OP_vkGetPhysicalDeviceFeatures2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceFeatures2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceFeatures2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceFeatures2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPhysicalDeviceFeatures2*)(pFeatures), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceFeatures2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceFeatures2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkPhysicalDeviceFeatures2*)(pFeatures));
    if (pFeatures) {
        transform_fromhost_VkPhysicalDeviceFeatures2(sResourceTracker,
                                                     (VkPhysicalDeviceFeatures2*)(pFeatures));
    }
    sResourceTracker->on_vkGetPhysicalDeviceFeatures2KHR(this, physicalDevice, pFeatures);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceProperties2KHR(VkPhysicalDevice physicalDevice,
                                                  VkPhysicalDeviceProperties2* pProperties,
                                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceProperties2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPhysicalDeviceProperties2KHR(physicalDevice:%p, pProperties:%p)",
                      physicalDevice, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceProperties2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPhysicalDeviceProperties2*)(pProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceProperties2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceProperties2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceProperties2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceProperties2KHR = OP_vkGetPhysicalDeviceProperties2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkPhysicalDeviceProperties2*)(pProperties),
                                                streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceProperties2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPhysicalDeviceProperties2*)(pProperties));
    if (pProperties) {
        transform_fromhost_VkPhysicalDeviceProperties2(sResourceTracker,
                                                       (VkPhysicalDeviceProperties2*)(pProperties));
    }
    sResourceTracker->on_vkGetPhysicalDeviceProperties2KHR(this, physicalDevice, pProperties);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceFormatProperties2KHR(VkPhysicalDevice physicalDevice,
                                                        VkFormat format,
                                                        VkFormatProperties2* pFormatProperties,
                                                        uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceFormatProperties2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceFormatProperties2KHR(physicalDevice:%p, format:%d, "
        "pFormatProperties:%p)",
        physicalDevice, format, pFormatProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkFormat local_format;
    local_physicalDevice = physicalDevice;
    local_format = format;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        count_VkFormatProperties2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkFormatProperties2*)(pFormatProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceFormatProperties2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceFormatProperties2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceFormatProperties2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceFormatProperties2KHR =
        OP_vkGetPhysicalDeviceFormatProperties2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceFormatProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceFormatProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    reservedmarshal_VkFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkFormatProperties2*)(pFormatProperties), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceFormatProperties2KHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkFormatProperties2*)(pFormatProperties));
    if (pFormatProperties) {
        transform_fromhost_VkFormatProperties2(sResourceTracker,
                                               (VkFormatProperties2*)(pFormatProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetPhysicalDeviceImageFormatProperties2KHR(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceImageFormatInfo2* pImageFormatInfo,
    VkImageFormatProperties2* pImageFormatProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceImageFormatProperties2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceImageFormatProperties2KHR(physicalDevice:%p, pImageFormatInfo:%p, "
        "pImageFormatProperties:%p)",
        physicalDevice, pImageFormatInfo, pImageFormatProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceImageFormatInfo2* local_pImageFormatInfo;
    local_physicalDevice = physicalDevice;
    local_pImageFormatInfo = nullptr;
    if (pImageFormatInfo) {
        local_pImageFormatInfo = (VkPhysicalDeviceImageFormatInfo2*)pool->alloc(
            sizeof(const VkPhysicalDeviceImageFormatInfo2));
        deepcopy_VkPhysicalDeviceImageFormatInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pImageFormatInfo,
            (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo));
    }
    if (local_pImageFormatInfo) {
        transform_tohost_VkPhysicalDeviceImageFormatInfo2(
            sResourceTracker, (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceImageFormatInfo2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo), countPtr);
        count_VkImageFormatProperties2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageFormatProperties2*)(pImageFormatProperties),
                                       countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceImageFormatProperties2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceImageFormatProperties2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceImageFormatProperties2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceImageFormatProperties2KHR =
        OP_vkGetPhysicalDeviceImageFormatProperties2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceImageFormatProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceImageFormatProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceImageFormatInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceImageFormatInfo2*)(local_pImageFormatInfo), streamPtrPtr);
    reservedmarshal_VkImageFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkImageFormatProperties2*)(pImageFormatProperties),
                                             streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceImageFormatProperties2KHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkImageFormatProperties2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkImageFormatProperties2*)(pImageFormatProperties));
    if (pImageFormatProperties) {
        transform_fromhost_VkImageFormatProperties2(
            sResourceTracker, (VkImageFormatProperties2*)(pImageFormatProperties));
    }
    VkResult vkGetPhysicalDeviceImageFormatProperties2KHR_VkResult_return = (VkResult)0;
    stream->read(&vkGetPhysicalDeviceImageFormatProperties2KHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPhysicalDeviceImageFormatProperties2KHR_VkResult_return;
}

void VkEncoder::vkGetPhysicalDeviceQueueFamilyProperties2KHR(
    VkPhysicalDevice physicalDevice, uint32_t* pQueueFamilyPropertyCount,
    VkQueueFamilyProperties2* pQueueFamilyProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceQueueFamilyProperties2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceQueueFamilyProperties2KHR(physicalDevice:%p, "
        "pQueueFamilyPropertyCount:%p, pQueueFamilyProperties:%p)",
        physicalDevice, pQueueFamilyPropertyCount, pQueueFamilyProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pQueueFamilyPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pQueueFamilyProperties) {
            if (pQueueFamilyPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                    count_VkQueueFamilyProperties2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceQueueFamilyProperties2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceQueueFamilyProperties2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceQueueFamilyProperties2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceQueueFamilyProperties2KHR =
        OP_vkGetPhysicalDeviceQueueFamilyProperties2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceQueueFamilyProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceQueueFamilyProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pQueueFamilyPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pQueueFamilyPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pQueueFamilyPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pQueueFamilyProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pQueueFamilyProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
            reservedmarshal_VkQueueFamilyProperties2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceQueueFamilyProperties2KHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pQueueFamilyPropertyCount;
    check_pQueueFamilyPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pQueueFamilyPropertyCount) {
        if (!(check_pQueueFamilyPropertyCount)) {
            fprintf(stderr,
                    "fatal: pQueueFamilyPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pQueueFamilyPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkQueueFamilyProperties2* check_pQueueFamilyProperties;
    check_pQueueFamilyProperties = (VkQueueFamilyProperties2*)(uintptr_t)stream->getBe64();
    if (pQueueFamilyProperties) {
        if (!(check_pQueueFamilyProperties)) {
            fprintf(stderr, "fatal: pQueueFamilyProperties inconsistent between guest and host\n");
        }
        if (pQueueFamilyPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                unmarshal_VkQueueFamilyProperties2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i));
            }
        }
    }
    if (pQueueFamilyPropertyCount) {
        if (pQueueFamilyProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pQueueFamilyPropertyCount)); ++i) {
                transform_fromhost_VkQueueFamilyProperties2(
                    sResourceTracker, (VkQueueFamilyProperties2*)(pQueueFamilyProperties + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceMemoryProperties2KHR(
    VkPhysicalDevice physicalDevice, VkPhysicalDeviceMemoryProperties2* pMemoryProperties,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceMemoryProperties2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceMemoryProperties2KHR(physicalDevice:%p, pMemoryProperties:%p)",
        physicalDevice, pMemoryProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceMemoryProperties2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceMemoryProperties2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceMemoryProperties2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceMemoryProperties2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceMemoryProperties2KHR =
        OP_vkGetPhysicalDeviceMemoryProperties2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceMemoryProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceMemoryProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceMemoryProperties2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties),
        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceMemoryProperties2KHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkPhysicalDeviceMemoryProperties2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties));
    if (pMemoryProperties) {
        transform_fromhost_VkPhysicalDeviceMemoryProperties2(
            sResourceTracker, (VkPhysicalDeviceMemoryProperties2*)(pMemoryProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetPhysicalDeviceSparseImageFormatProperties2KHR(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceSparseImageFormatInfo2* pFormatInfo,
    uint32_t* pPropertyCount, VkSparseImageFormatProperties2* pProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceSparseImageFormatProperties2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceSparseImageFormatProperties2KHR(physicalDevice:%p, pFormatInfo:%p, "
        "pPropertyCount:%p, pProperties:%p)",
        physicalDevice, pFormatInfo, pPropertyCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceSparseImageFormatInfo2* local_pFormatInfo;
    local_physicalDevice = physicalDevice;
    local_pFormatInfo = nullptr;
    if (pFormatInfo) {
        local_pFormatInfo = (VkPhysicalDeviceSparseImageFormatInfo2*)pool->alloc(
            sizeof(const VkPhysicalDeviceSparseImageFormatInfo2));
        deepcopy_VkPhysicalDeviceSparseImageFormatInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pFormatInfo,
            (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo));
    }
    if (local_pFormatInfo) {
        transform_tohost_VkPhysicalDeviceSparseImageFormatInfo2(
            sResourceTracker, (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceSparseImageFormatInfo2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPropertyCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pPropertyCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                    count_VkSparseImageFormatProperties2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageFormatProperties2*)(pProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2KHR);
    uint8_t* streamPtr =
        stream->reserve(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceSparseImageFormatProperties2KHR =
        OP_vkGetPhysicalDeviceSparseImageFormatProperties2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceSparseImageFormatProperties2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2KHR,
           sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceSparseImageFormatInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceSparseImageFormatInfo2*)(local_pFormatInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pPropertyCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPropertyCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pPropertyCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
            reservedmarshal_VkSparseImageFormatProperties2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageFormatProperties2*)(pProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceSparseImageFormatProperties2KHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pPropertyCount;
    check_pPropertyCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pPropertyCount) {
        if (!(check_pPropertyCount)) {
            fprintf(stderr, "fatal: pPropertyCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pPropertyCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageFormatProperties2* check_pProperties;
    check_pProperties = (VkSparseImageFormatProperties2*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pPropertyCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                unmarshal_VkSparseImageFormatProperties2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageFormatProperties2*)(pProperties + i));
            }
        }
    }
    if (pPropertyCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pPropertyCount)); ++i) {
                transform_fromhost_VkSparseImageFormatProperties2(
                    sResourceTracker, (VkSparseImageFormatProperties2*)(pProperties + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_maintenance1
void VkEncoder::vkTrimCommandPoolKHR(VkDevice device, VkCommandPool commandPool,
                                     VkCommandPoolTrimFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkTrimCommandPoolKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkTrimCommandPoolKHR(device:%p, commandPool:%p, flags:%d)", device,
                      commandPool, flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCommandPool local_commandPool;
    VkCommandPoolTrimFlags local_flags;
    local_device = device;
    local_commandPool = commandPool;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCommandPoolTrimFlags);
    }
    uint32_t packetSize_vkTrimCommandPoolKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkTrimCommandPoolKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkTrimCommandPoolKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkTrimCommandPoolKHR = OP_vkTrimCommandPoolKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkTrimCommandPoolKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkTrimCommandPoolKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkCommandPool((*&local_commandPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkCommandPoolTrimFlags*)&local_flags, sizeof(VkCommandPoolTrimFlags));
    *streamPtrPtr += sizeof(VkCommandPoolTrimFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkTrimCommandPoolKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_external_memory_capabilities
void VkEncoder::vkGetPhysicalDeviceExternalBufferPropertiesKHR(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceExternalBufferInfo* pExternalBufferInfo,
    VkExternalBufferProperties* pExternalBufferProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceExternalBufferPropertiesKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceExternalBufferPropertiesKHR(physicalDevice:%p, pExternalBufferInfo:%p, "
        "pExternalBufferProperties:%p)",
        physicalDevice, pExternalBufferInfo, pExternalBufferProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceExternalBufferInfo* local_pExternalBufferInfo;
    local_physicalDevice = physicalDevice;
    local_pExternalBufferInfo = nullptr;
    if (pExternalBufferInfo) {
        local_pExternalBufferInfo = (VkPhysicalDeviceExternalBufferInfo*)pool->alloc(
            sizeof(const VkPhysicalDeviceExternalBufferInfo));
        deepcopy_VkPhysicalDeviceExternalBufferInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExternalBufferInfo,
            (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo));
    }
    if (local_pExternalBufferInfo) {
        sResourceTracker->transformImpl_VkPhysicalDeviceExternalBufferInfo_tohost(
            local_pExternalBufferInfo, 1);
        transform_tohost_VkPhysicalDeviceExternalBufferInfo(
            sResourceTracker, (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceExternalBufferInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo), countPtr);
        count_VkExternalBufferProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkExternalBufferProperties*)(pExternalBufferProperties),
                                         countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceExternalBufferPropertiesKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceExternalBufferPropertiesKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceExternalBufferPropertiesKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceExternalBufferPropertiesKHR =
        OP_vkGetPhysicalDeviceExternalBufferPropertiesKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceExternalBufferPropertiesKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceExternalBufferPropertiesKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceExternalBufferInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceExternalBufferInfo*)(local_pExternalBufferInfo), streamPtrPtr);
    reservedmarshal_VkExternalBufferProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkExternalBufferProperties*)(pExternalBufferProperties), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceExternalBufferPropertiesKHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExternalBufferProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkExternalBufferProperties*)(pExternalBufferProperties));
    if (pExternalBufferProperties) {
        sResourceTracker->transformImpl_VkExternalBufferProperties_fromhost(
            pExternalBufferProperties, 1);
        transform_fromhost_VkExternalBufferProperties(
            sResourceTracker, (VkExternalBufferProperties*)(pExternalBufferProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_external_semaphore_capabilities
void VkEncoder::vkGetPhysicalDeviceExternalSemaphorePropertiesKHR(
    VkPhysicalDevice physicalDevice,
    const VkPhysicalDeviceExternalSemaphoreInfo* pExternalSemaphoreInfo,
    VkExternalSemaphoreProperties* pExternalSemaphoreProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceExternalSemaphorePropertiesKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceExternalSemaphorePropertiesKHR(physicalDevice:%p, "
        "pExternalSemaphoreInfo:%p, pExternalSemaphoreProperties:%p)",
        physicalDevice, pExternalSemaphoreInfo, pExternalSemaphoreProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceExternalSemaphoreInfo* local_pExternalSemaphoreInfo;
    local_physicalDevice = physicalDevice;
    local_pExternalSemaphoreInfo = nullptr;
    if (pExternalSemaphoreInfo) {
        local_pExternalSemaphoreInfo = (VkPhysicalDeviceExternalSemaphoreInfo*)pool->alloc(
            sizeof(const VkPhysicalDeviceExternalSemaphoreInfo));
        deepcopy_VkPhysicalDeviceExternalSemaphoreInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExternalSemaphoreInfo,
            (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo));
    }
    if (local_pExternalSemaphoreInfo) {
        transform_tohost_VkPhysicalDeviceExternalSemaphoreInfo(
            sResourceTracker,
            (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceExternalSemaphoreInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo), countPtr);
        count_VkExternalSemaphoreProperties(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties), countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR);
    uint8_t* streamPtr =
        stream->reserve(packetSize_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR =
        OP_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR,
           sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceExternalSemaphoreInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceExternalSemaphoreInfo*)(local_pExternalSemaphoreInfo), streamPtrPtr);
    reservedmarshal_VkExternalSemaphoreProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExternalSemaphoreProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties));
    if (pExternalSemaphoreProperties) {
        transform_fromhost_VkExternalSemaphoreProperties(
            sResourceTracker, (VkExternalSemaphoreProperties*)(pExternalSemaphoreProperties));
    }
    sResourceTracker->on_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR(
        this, physicalDevice, pExternalSemaphoreInfo, pExternalSemaphoreProperties);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_external_semaphore_fd
VkResult VkEncoder::vkImportSemaphoreFdKHR(VkDevice device,
                                           const VkImportSemaphoreFdInfoKHR* pImportSemaphoreFdInfo,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkImportSemaphoreFdKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkImportSemaphoreFdKHR(device:%p, pImportSemaphoreFdInfo:%p)", device,
                      pImportSemaphoreFdInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImportSemaphoreFdInfoKHR* local_pImportSemaphoreFdInfo;
    local_device = device;
    local_pImportSemaphoreFdInfo = nullptr;
    if (pImportSemaphoreFdInfo) {
        local_pImportSemaphoreFdInfo =
            (VkImportSemaphoreFdInfoKHR*)pool->alloc(sizeof(const VkImportSemaphoreFdInfoKHR));
        deepcopy_VkImportSemaphoreFdInfoKHR(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pImportSemaphoreFdInfo,
            (VkImportSemaphoreFdInfoKHR*)(local_pImportSemaphoreFdInfo));
    }
    if (local_pImportSemaphoreFdInfo) {
        transform_tohost_VkImportSemaphoreFdInfoKHR(
            sResourceTracker, (VkImportSemaphoreFdInfoKHR*)(local_pImportSemaphoreFdInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImportSemaphoreFdInfoKHR(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkImportSemaphoreFdInfoKHR*)(local_pImportSemaphoreFdInfo), countPtr);
    }
    uint32_t packetSize_vkImportSemaphoreFdKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkImportSemaphoreFdKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkImportSemaphoreFdKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkImportSemaphoreFdKHR = OP_vkImportSemaphoreFdKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkImportSemaphoreFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkImportSemaphoreFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImportSemaphoreFdInfoKHR(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkImportSemaphoreFdInfoKHR*)(local_pImportSemaphoreFdInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkImportSemaphoreFdKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkImportSemaphoreFdKHR_VkResult_return = (VkResult)0;
    stream->read(&vkImportSemaphoreFdKHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkImportSemaphoreFdKHR_VkResult_return;
}

VkResult VkEncoder::vkGetSemaphoreFdKHR(VkDevice device, const VkSemaphoreGetFdInfoKHR* pGetFdInfo,
                                        int* pFd, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetSemaphoreFdKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetSemaphoreFdKHR(device:%p, pGetFdInfo:%p, pFd:%p)", device, pGetFdInfo,
                      pFd);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSemaphoreGetFdInfoKHR* local_pGetFdInfo;
    local_device = device;
    local_pGetFdInfo = nullptr;
    if (pGetFdInfo) {
        local_pGetFdInfo =
            (VkSemaphoreGetFdInfoKHR*)pool->alloc(sizeof(const VkSemaphoreGetFdInfoKHR));
        deepcopy_VkSemaphoreGetFdInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pGetFdInfo,
                                         (VkSemaphoreGetFdInfoKHR*)(local_pGetFdInfo));
    }
    if (local_pGetFdInfo) {
        transform_tohost_VkSemaphoreGetFdInfoKHR(sResourceTracker,
                                                 (VkSemaphoreGetFdInfoKHR*)(local_pGetFdInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSemaphoreGetFdInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSemaphoreGetFdInfoKHR*)(local_pGetFdInfo), countPtr);
        *countPtr += sizeof(int);
    }
    uint32_t packetSize_vkGetSemaphoreFdKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetSemaphoreFdKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetSemaphoreFdKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetSemaphoreFdKHR = OP_vkGetSemaphoreFdKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetSemaphoreFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetSemaphoreFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkSemaphoreGetFdInfoKHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkSemaphoreGetFdInfoKHR*)(local_pGetFdInfo),
                                            streamPtrPtr);
    memcpy(*streamPtrPtr, (int*)pFd, sizeof(int));
    *streamPtrPtr += sizeof(int);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetSemaphoreFdKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((int*)pFd, sizeof(int));
    VkResult vkGetSemaphoreFdKHR_VkResult_return = (VkResult)0;
    stream->read(&vkGetSemaphoreFdKHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetSemaphoreFdKHR_VkResult_return;
}

#endif
#ifdef VK_KHR_descriptor_update_template
VkResult VkEncoder::vkCreateDescriptorUpdateTemplateKHR(
    VkDevice device, const VkDescriptorUpdateTemplateCreateInfo* pCreateInfo,
    const VkAllocationCallbacks* pAllocator, VkDescriptorUpdateTemplate* pDescriptorUpdateTemplate,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateDescriptorUpdateTemplateKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateDescriptorUpdateTemplateKHR(device:%p, pCreateInfo:%p, pAllocator:%p, "
        "pDescriptorUpdateTemplate:%p)",
        device, pCreateInfo, pAllocator, pDescriptorUpdateTemplate);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorUpdateTemplateCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkDescriptorUpdateTemplateCreateInfo*)pool->alloc(
            sizeof(const VkDescriptorUpdateTemplateCreateInfo));
        deepcopy_VkDescriptorUpdateTemplateCreateInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
            (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkDescriptorUpdateTemplateCreateInfo(
            sResourceTracker, (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDescriptorUpdateTemplateCreateInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateDescriptorUpdateTemplateKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCreateDescriptorUpdateTemplateKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateDescriptorUpdateTemplateKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateDescriptorUpdateTemplateKHR = OP_vkCreateDescriptorUpdateTemplateKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateDescriptorUpdateTemplateKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateDescriptorUpdateTemplateKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDescriptorUpdateTemplateCreateInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkDescriptorUpdateTemplateCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pDescriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateDescriptorUpdateTemplateKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkDescriptorUpdateTemplate(
        &cgen_var_3, (VkDescriptorUpdateTemplate*)pDescriptorUpdateTemplate, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateDescriptorUpdateTemplateKHR_VkResult_return = (VkResult)0;
    stream->read(&vkCreateDescriptorUpdateTemplateKHR_VkResult_return, sizeof(VkResult));
    sResourceTracker->on_vkCreateDescriptorUpdateTemplateKHR(
        this, vkCreateDescriptorUpdateTemplateKHR_VkResult_return, device, pCreateInfo, pAllocator,
        pDescriptorUpdateTemplate);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateDescriptorUpdateTemplateKHR_VkResult_return;
}

void VkEncoder::vkDestroyDescriptorUpdateTemplateKHR(
    VkDevice device, VkDescriptorUpdateTemplate descriptorUpdateTemplate,
    const VkAllocationCallbacks* pAllocator, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyDescriptorUpdateTemplateKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkDestroyDescriptorUpdateTemplateKHR(device:%p, descriptorUpdateTemplate:%p, "
        "pAllocator:%p)",
        device, descriptorUpdateTemplate, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorUpdateTemplate local_descriptorUpdateTemplate;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_descriptorUpdateTemplate = descriptorUpdateTemplate;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyDescriptorUpdateTemplateKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkDestroyDescriptorUpdateTemplateKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyDescriptorUpdateTemplateKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyDescriptorUpdateTemplateKHR = OP_vkDestroyDescriptorUpdateTemplateKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyDescriptorUpdateTemplateKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyDescriptorUpdateTemplateKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorUpdateTemplate((*&local_descriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkDestroyDescriptorUpdateTemplateKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkDescriptorUpdateTemplate(
        (VkDescriptorUpdateTemplate*)&descriptorUpdateTemplate);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkUpdateDescriptorSetWithTemplateKHR(
    VkDevice device, VkDescriptorSet descriptorSet,
    VkDescriptorUpdateTemplate descriptorUpdateTemplate, const void* pData, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkUpdateDescriptorSetWithTemplateKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkUpdateDescriptorSetWithTemplateKHR(device:%p, descriptorSet:%p, "
        "descriptorUpdateTemplate:%p, pData:%p)",
        device, descriptorSet, descriptorUpdateTemplate, pData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSet local_descriptorSet;
    VkDescriptorUpdateTemplate local_descriptorUpdateTemplate;
    void* local_pData;
    local_device = device;
    local_descriptorSet = descriptorSet;
    local_descriptorUpdateTemplate = descriptorUpdateTemplate;
    // Avoiding deepcopy for pData
    local_pData = (void*)pData;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pData) {
            *countPtr += sizeof(uint8_t);
        }
    }
    uint32_t packetSize_vkUpdateDescriptorSetWithTemplateKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkUpdateDescriptorSetWithTemplateKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkUpdateDescriptorSetWithTemplateKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkUpdateDescriptorSetWithTemplateKHR = OP_vkUpdateDescriptorSetWithTemplateKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkUpdateDescriptorSetWithTemplateKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkUpdateDescriptorSetWithTemplateKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorSet((*&local_descriptorSet));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkDescriptorUpdateTemplate((*&local_descriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_3 = (uint64_t)(uintptr_t)local_pData;
    memcpy((*streamPtrPtr), &cgen_var_3, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pData) {
        memcpy(*streamPtrPtr, (void*)local_pData, sizeof(uint8_t));
        *streamPtrPtr += sizeof(uint8_t);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkUpdateDescriptorSetWithTemplateKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_create_renderpass2
VkResult VkEncoder::vkCreateRenderPass2KHR(VkDevice device,
                                           const VkRenderPassCreateInfo2* pCreateInfo,
                                           const VkAllocationCallbacks* pAllocator,
                                           VkRenderPass* pRenderPass, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateRenderPass2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateRenderPass2KHR(device:%p, pCreateInfo:%p, pAllocator:%p, pRenderPass:%p)", device,
        pCreateInfo, pAllocator, pRenderPass);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkRenderPassCreateInfo2* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkRenderPassCreateInfo2*)pool->alloc(sizeof(const VkRenderPassCreateInfo2));
        deepcopy_VkRenderPassCreateInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                         (VkRenderPassCreateInfo2*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkRenderPassCreateInfo2(sResourceTracker,
                                                 (VkRenderPassCreateInfo2*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderPassCreateInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkRenderPassCreateInfo2*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateRenderPass2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreateRenderPass2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateRenderPass2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateRenderPass2KHR = OP_vkCreateRenderPass2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateRenderPass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateRenderPass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkRenderPassCreateInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkRenderPassCreateInfo2*)(local_pCreateInfo),
                                            streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pRenderPass));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateRenderPass2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkRenderPass(&cgen_var_3, (VkRenderPass*)pRenderPass,
                                                         1);
    stream->unsetHandleMapping();
    VkResult vkCreateRenderPass2KHR_VkResult_return = (VkResult)0;
    stream->read(&vkCreateRenderPass2KHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateRenderPass2KHR_VkResult_return;
}

void VkEncoder::vkCmdBeginRenderPass2KHR(VkCommandBuffer commandBuffer,
                                         const VkRenderPassBeginInfo* pRenderPassBegin,
                                         const VkSubpassBeginInfo* pSubpassBeginInfo,
                                         uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginRenderPass2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBeginRenderPass2KHR(commandBuffer:%p, pRenderPassBegin:%p, pSubpassBeginInfo:%p)",
        commandBuffer, pRenderPassBegin, pSubpassBeginInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkRenderPassBeginInfo* local_pRenderPassBegin;
    VkSubpassBeginInfo* local_pSubpassBeginInfo;
    local_commandBuffer = commandBuffer;
    local_pRenderPassBegin = nullptr;
    if (pRenderPassBegin) {
        local_pRenderPassBegin =
            (VkRenderPassBeginInfo*)pool->alloc(sizeof(const VkRenderPassBeginInfo));
        deepcopy_VkRenderPassBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRenderPassBegin,
                                       (VkRenderPassBeginInfo*)(local_pRenderPassBegin));
    }
    local_pSubpassBeginInfo = nullptr;
    if (pSubpassBeginInfo) {
        local_pSubpassBeginInfo =
            (VkSubpassBeginInfo*)pool->alloc(sizeof(const VkSubpassBeginInfo));
        deepcopy_VkSubpassBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassBeginInfo,
                                    (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    if (local_pRenderPassBegin) {
        transform_tohost_VkRenderPassBeginInfo(sResourceTracker,
                                               (VkRenderPassBeginInfo*)(local_pRenderPassBegin));
    }
    if (local_pSubpassBeginInfo) {
        transform_tohost_VkSubpassBeginInfo(sResourceTracker,
                                            (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderPassBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkRenderPassBeginInfo*)(local_pRenderPassBegin), countPtr);
        count_VkSubpassBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkSubpassBeginInfo*)(local_pSubpassBeginInfo), countPtr);
    }
    uint32_t packetSize_vkCmdBeginRenderPass2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBeginRenderPass2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginRenderPass2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginRenderPass2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginRenderPass2KHR = OP_vkCmdBeginRenderPass2KHR;
    memcpy(streamPtr, &opcode_vkCmdBeginRenderPass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginRenderPass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkRenderPassBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkRenderPassBeginInfo*)(local_pRenderPassBegin),
                                          streamPtrPtr);
    reservedmarshal_VkSubpassBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkSubpassBeginInfo*)(local_pSubpassBeginInfo),
                                       streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBeginRenderPass2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdNextSubpass2KHR(VkCommandBuffer commandBuffer,
                                     const VkSubpassBeginInfo* pSubpassBeginInfo,
                                     const VkSubpassEndInfo* pSubpassEndInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdNextSubpass2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdNextSubpass2KHR(commandBuffer:%p, pSubpassBeginInfo:%p, pSubpassEndInfo:%p)",
        commandBuffer, pSubpassBeginInfo, pSubpassEndInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkSubpassBeginInfo* local_pSubpassBeginInfo;
    VkSubpassEndInfo* local_pSubpassEndInfo;
    local_commandBuffer = commandBuffer;
    local_pSubpassBeginInfo = nullptr;
    if (pSubpassBeginInfo) {
        local_pSubpassBeginInfo =
            (VkSubpassBeginInfo*)pool->alloc(sizeof(const VkSubpassBeginInfo));
        deepcopy_VkSubpassBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassBeginInfo,
                                    (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    local_pSubpassEndInfo = nullptr;
    if (pSubpassEndInfo) {
        local_pSubpassEndInfo = (VkSubpassEndInfo*)pool->alloc(sizeof(const VkSubpassEndInfo));
        deepcopy_VkSubpassEndInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassEndInfo,
                                  (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    if (local_pSubpassBeginInfo) {
        transform_tohost_VkSubpassBeginInfo(sResourceTracker,
                                            (VkSubpassBeginInfo*)(local_pSubpassBeginInfo));
    }
    if (local_pSubpassEndInfo) {
        transform_tohost_VkSubpassEndInfo(sResourceTracker,
                                          (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSubpassBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkSubpassBeginInfo*)(local_pSubpassBeginInfo), countPtr);
        count_VkSubpassEndInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkSubpassEndInfo*)(local_pSubpassEndInfo), countPtr);
    }
    uint32_t packetSize_vkCmdNextSubpass2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdNextSubpass2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdNextSubpass2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdNextSubpass2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdNextSubpass2KHR = OP_vkCmdNextSubpass2KHR;
    memcpy(streamPtr, &opcode_vkCmdNextSubpass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdNextSubpass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkSubpassBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkSubpassBeginInfo*)(local_pSubpassBeginInfo),
                                       streamPtrPtr);
    reservedmarshal_VkSubpassEndInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkSubpassEndInfo*)(local_pSubpassEndInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdNextSubpass2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndRenderPass2KHR(VkCommandBuffer commandBuffer,
                                       const VkSubpassEndInfo* pSubpassEndInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndRenderPass2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdEndRenderPass2KHR(commandBuffer:%p, pSubpassEndInfo:%p)", commandBuffer,
                      pSubpassEndInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkSubpassEndInfo* local_pSubpassEndInfo;
    local_commandBuffer = commandBuffer;
    local_pSubpassEndInfo = nullptr;
    if (pSubpassEndInfo) {
        local_pSubpassEndInfo = (VkSubpassEndInfo*)pool->alloc(sizeof(const VkSubpassEndInfo));
        deepcopy_VkSubpassEndInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubpassEndInfo,
                                  (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    if (local_pSubpassEndInfo) {
        transform_tohost_VkSubpassEndInfo(sResourceTracker,
                                          (VkSubpassEndInfo*)(local_pSubpassEndInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSubpassEndInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkSubpassEndInfo*)(local_pSubpassEndInfo), countPtr);
    }
    uint32_t packetSize_vkCmdEndRenderPass2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdEndRenderPass2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndRenderPass2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndRenderPass2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndRenderPass2KHR = OP_vkCmdEndRenderPass2KHR;
    memcpy(streamPtr, &opcode_vkCmdEndRenderPass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndRenderPass2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkSubpassEndInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkSubpassEndInfo*)(local_pSubpassEndInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdEndRenderPass2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_external_fence_capabilities
void VkEncoder::vkGetPhysicalDeviceExternalFencePropertiesKHR(
    VkPhysicalDevice physicalDevice, const VkPhysicalDeviceExternalFenceInfo* pExternalFenceInfo,
    VkExternalFenceProperties* pExternalFenceProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPhysicalDeviceExternalFencePropertiesKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceExternalFencePropertiesKHR(physicalDevice:%p, pExternalFenceInfo:%p, "
        "pExternalFenceProperties:%p)",
        physicalDevice, pExternalFenceInfo, pExternalFenceProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    VkPhysicalDeviceExternalFenceInfo* local_pExternalFenceInfo;
    local_physicalDevice = physicalDevice;
    local_pExternalFenceInfo = nullptr;
    if (pExternalFenceInfo) {
        local_pExternalFenceInfo = (VkPhysicalDeviceExternalFenceInfo*)pool->alloc(
            sizeof(const VkPhysicalDeviceExternalFenceInfo));
        deepcopy_VkPhysicalDeviceExternalFenceInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExternalFenceInfo,
            (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo));
    }
    if (local_pExternalFenceInfo) {
        transform_tohost_VkPhysicalDeviceExternalFenceInfo(
            sResourceTracker, (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPhysicalDeviceExternalFenceInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo), countPtr);
        count_VkExternalFenceProperties(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkExternalFenceProperties*)(pExternalFenceProperties),
                                        countPtr);
    }
    uint32_t packetSize_vkGetPhysicalDeviceExternalFencePropertiesKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceExternalFencePropertiesKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceExternalFencePropertiesKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceExternalFencePropertiesKHR =
        OP_vkGetPhysicalDeviceExternalFencePropertiesKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceExternalFencePropertiesKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceExternalFencePropertiesKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPhysicalDeviceExternalFenceInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkPhysicalDeviceExternalFenceInfo*)(local_pExternalFenceInfo), streamPtrPtr);
    reservedmarshal_VkExternalFenceProperties(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExternalFenceProperties*)(pExternalFenceProperties),
        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPhysicalDeviceExternalFencePropertiesKHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExternalFenceProperties(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkExternalFenceProperties*)(pExternalFenceProperties));
    if (pExternalFenceProperties) {
        transform_fromhost_VkExternalFenceProperties(
            sResourceTracker, (VkExternalFenceProperties*)(pExternalFenceProperties));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_external_fence_fd
VkResult VkEncoder::vkImportFenceFdKHR(VkDevice device,
                                       const VkImportFenceFdInfoKHR* pImportFenceFdInfo,
                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkImportFenceFdKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkImportFenceFdKHR(device:%p, pImportFenceFdInfo:%p)", device,
                      pImportFenceFdInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImportFenceFdInfoKHR* local_pImportFenceFdInfo;
    local_device = device;
    local_pImportFenceFdInfo = nullptr;
    if (pImportFenceFdInfo) {
        local_pImportFenceFdInfo =
            (VkImportFenceFdInfoKHR*)pool->alloc(sizeof(const VkImportFenceFdInfoKHR));
        deepcopy_VkImportFenceFdInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pImportFenceFdInfo,
                                        (VkImportFenceFdInfoKHR*)(local_pImportFenceFdInfo));
    }
    if (local_pImportFenceFdInfo) {
        transform_tohost_VkImportFenceFdInfoKHR(
            sResourceTracker, (VkImportFenceFdInfoKHR*)(local_pImportFenceFdInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImportFenceFdInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkImportFenceFdInfoKHR*)(local_pImportFenceFdInfo), countPtr);
    }
    uint32_t packetSize_vkImportFenceFdKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkImportFenceFdKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkImportFenceFdKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkImportFenceFdKHR = OP_vkImportFenceFdKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkImportFenceFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkImportFenceFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImportFenceFdInfoKHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkImportFenceFdInfoKHR*)(local_pImportFenceFdInfo),
                                           streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkImportFenceFdKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkImportFenceFdKHR_VkResult_return = (VkResult)0;
    stream->read(&vkImportFenceFdKHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkImportFenceFdKHR_VkResult_return;
}

VkResult VkEncoder::vkGetFenceFdKHR(VkDevice device, const VkFenceGetFdInfoKHR* pGetFdInfo,
                                    int* pFd, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetFenceFdKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetFenceFdKHR(device:%p, pGetFdInfo:%p, pFd:%p)", device, pGetFdInfo, pFd);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFenceGetFdInfoKHR* local_pGetFdInfo;
    local_device = device;
    local_pGetFdInfo = nullptr;
    if (pGetFdInfo) {
        local_pGetFdInfo = (VkFenceGetFdInfoKHR*)pool->alloc(sizeof(const VkFenceGetFdInfoKHR));
        deepcopy_VkFenceGetFdInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pGetFdInfo,
                                     (VkFenceGetFdInfoKHR*)(local_pGetFdInfo));
    }
    if (local_pGetFdInfo) {
        transform_tohost_VkFenceGetFdInfoKHR(sResourceTracker,
                                             (VkFenceGetFdInfoKHR*)(local_pGetFdInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkFenceGetFdInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkFenceGetFdInfoKHR*)(local_pGetFdInfo), countPtr);
        *countPtr += sizeof(int);
    }
    uint32_t packetSize_vkGetFenceFdKHR = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetFenceFdKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetFenceFdKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetFenceFdKHR = OP_vkGetFenceFdKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetFenceFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetFenceFdKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkFenceGetFdInfoKHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkFenceGetFdInfoKHR*)(local_pGetFdInfo), streamPtrPtr);
    memcpy(*streamPtrPtr, (int*)pFd, sizeof(int));
    *streamPtrPtr += sizeof(int);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetFenceFdKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((int*)pFd, sizeof(int));
    VkResult vkGetFenceFdKHR_VkResult_return = (VkResult)0;
    stream->read(&vkGetFenceFdKHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetFenceFdKHR_VkResult_return;
}

#endif
#ifdef VK_KHR_get_memory_requirements2
void VkEncoder::vkGetImageMemoryRequirements2KHR(VkDevice device,
                                                 const VkImageMemoryRequirementsInfo2* pInfo,
                                                 VkMemoryRequirements2* pMemoryRequirements,
                                                 uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageMemoryRequirements2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetImageMemoryRequirements2KHR(device:%p, pInfo:%p, pMemoryRequirements:%p)", device,
        pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageMemoryRequirementsInfo2* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkImageMemoryRequirementsInfo2*)pool->alloc(
            sizeof(const VkImageMemoryRequirementsInfo2));
        deepcopy_VkImageMemoryRequirementsInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                (VkImageMemoryRequirementsInfo2*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkImageMemoryRequirementsInfo2(
            sResourceTracker, (VkImageMemoryRequirementsInfo2*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageMemoryRequirementsInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkImageMemoryRequirementsInfo2*)(local_pInfo),
                                             countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetImageMemoryRequirements2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageMemoryRequirements2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageMemoryRequirements2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageMemoryRequirements2KHR = OP_vkGetImageMemoryRequirements2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageMemoryRequirements2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageMemoryRequirements2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageMemoryRequirementsInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                   (VkImageMemoryRequirementsInfo2*)(local_pInfo),
                                                   streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetImageMemoryRequirements2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetBufferMemoryRequirements2KHR(VkDevice device,
                                                  const VkBufferMemoryRequirementsInfo2* pInfo,
                                                  VkMemoryRequirements2* pMemoryRequirements,
                                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBufferMemoryRequirements2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetBufferMemoryRequirements2KHR(device:%p, pInfo:%p, pMemoryRequirements:%p)", device,
        pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferMemoryRequirementsInfo2* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkBufferMemoryRequirementsInfo2*)pool->alloc(
            sizeof(const VkBufferMemoryRequirementsInfo2));
        deepcopy_VkBufferMemoryRequirementsInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                 (VkBufferMemoryRequirementsInfo2*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkBufferMemoryRequirementsInfo2(
            sResourceTracker, (VkBufferMemoryRequirementsInfo2*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferMemoryRequirementsInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBufferMemoryRequirementsInfo2*)(local_pInfo),
                                              countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetBufferMemoryRequirements2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetBufferMemoryRequirements2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBufferMemoryRequirements2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBufferMemoryRequirements2KHR = OP_vkGetBufferMemoryRequirements2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBufferMemoryRequirements2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBufferMemoryRequirements2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferMemoryRequirementsInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                    (VkBufferMemoryRequirementsInfo2*)(local_pInfo),
                                                    streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetBufferMemoryRequirements2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetImageSparseMemoryRequirements2KHR(
    VkDevice device, const VkImageSparseMemoryRequirementsInfo2* pInfo,
    uint32_t* pSparseMemoryRequirementCount,
    VkSparseImageMemoryRequirements2* pSparseMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageSparseMemoryRequirements2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetImageSparseMemoryRequirements2KHR(device:%p, pInfo:%p, "
        "pSparseMemoryRequirementCount:%p, pSparseMemoryRequirements:%p)",
        device, pInfo, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageSparseMemoryRequirementsInfo2* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkImageSparseMemoryRequirementsInfo2*)pool->alloc(
            sizeof(const VkImageSparseMemoryRequirementsInfo2));
        deepcopy_VkImageSparseMemoryRequirementsInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
            (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkImageSparseMemoryRequirementsInfo2(
            sResourceTracker, (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageSparseMemoryRequirementsInfo2(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirementCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirements) {
            if (pSparseMemoryRequirementCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                    count_VkSparseImageMemoryRequirements2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i),
                        countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetImageSparseMemoryRequirements2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageSparseMemoryRequirements2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageSparseMemoryRequirements2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageSparseMemoryRequirements2KHR =
        OP_vkGetImageSparseMemoryRequirements2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageSparseMemoryRequirements2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageSparseMemoryRequirements2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageSparseMemoryRequirementsInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkImageSparseMemoryRequirementsInfo2*)(local_pInfo),
        streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pSparseMemoryRequirementCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirementCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pSparseMemoryRequirements;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirements) {
        for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
            reservedmarshal_VkSparseImageMemoryRequirements2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetImageSparseMemoryRequirements2KHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pSparseMemoryRequirementCount;
    check_pSparseMemoryRequirementCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirementCount) {
        if (!(check_pSparseMemoryRequirementCount)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirementCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageMemoryRequirements2* check_pSparseMemoryRequirements;
    check_pSparseMemoryRequirements =
        (VkSparseImageMemoryRequirements2*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirements) {
        if (!(check_pSparseMemoryRequirements)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirements inconsistent between guest and host\n");
        }
        if (pSparseMemoryRequirementCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                unmarshal_VkSparseImageMemoryRequirements2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    if (pSparseMemoryRequirementCount) {
        if (pSparseMemoryRequirements) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                transform_fromhost_VkSparseImageMemoryRequirements2(
                    sResourceTracker,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_sampler_ycbcr_conversion
VkResult VkEncoder::vkCreateSamplerYcbcrConversionKHR(
    VkDevice device, const VkSamplerYcbcrConversionCreateInfo* pCreateInfo,
    const VkAllocationCallbacks* pAllocator, VkSamplerYcbcrConversion* pYcbcrConversion,
    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateSamplerYcbcrConversionKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateSamplerYcbcrConversionKHR(device:%p, pCreateInfo:%p, pAllocator:%p, "
        "pYcbcrConversion:%p)",
        device, pCreateInfo, pAllocator, pYcbcrConversion);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSamplerYcbcrConversionCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkSamplerYcbcrConversionCreateInfo*)pool->alloc(
            sizeof(const VkSamplerYcbcrConversionCreateInfo));
        deepcopy_VkSamplerYcbcrConversionCreateInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
            (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkSamplerYcbcrConversionCreateInfo(
            sResourceTracker, (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkSamplerYcbcrConversionCreateInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreateSamplerYcbcrConversionKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCreateSamplerYcbcrConversionKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateSamplerYcbcrConversionKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateSamplerYcbcrConversionKHR = OP_vkCreateSamplerYcbcrConversionKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateSamplerYcbcrConversionKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateSamplerYcbcrConversionKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkSamplerYcbcrConversionCreateInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkSamplerYcbcrConversionCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pYcbcrConversion));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreateSamplerYcbcrConversionKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkSamplerYcbcrConversion(
        &cgen_var_3, (VkSamplerYcbcrConversion*)pYcbcrConversion, 1);
    stream->unsetHandleMapping();
    VkResult vkCreateSamplerYcbcrConversionKHR_VkResult_return = (VkResult)0;
    stream->read(&vkCreateSamplerYcbcrConversionKHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateSamplerYcbcrConversionKHR_VkResult_return;
}

void VkEncoder::vkDestroySamplerYcbcrConversionKHR(VkDevice device,
                                                   VkSamplerYcbcrConversion ycbcrConversion,
                                                   const VkAllocationCallbacks* pAllocator,
                                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroySamplerYcbcrConversionKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkDestroySamplerYcbcrConversionKHR(device:%p, ycbcrConversion:%p, pAllocator:%p)", device,
        ycbcrConversion, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSamplerYcbcrConversion local_ycbcrConversion;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_ycbcrConversion = ycbcrConversion;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroySamplerYcbcrConversionKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkDestroySamplerYcbcrConversionKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroySamplerYcbcrConversionKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroySamplerYcbcrConversionKHR = OP_vkDestroySamplerYcbcrConversionKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroySamplerYcbcrConversionKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroySamplerYcbcrConversionKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkSamplerYcbcrConversion((*&local_ycbcrConversion));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroySamplerYcbcrConversionKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    sResourceTracker->destroyMapping()->mapHandles_VkSamplerYcbcrConversion(
        (VkSamplerYcbcrConversion*)&ycbcrConversion);
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_bind_memory2
VkResult VkEncoder::vkBindBufferMemory2KHR(VkDevice device, uint32_t bindInfoCount,
                                           const VkBindBufferMemoryInfo* pBindInfos,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBindBufferMemory2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkBindBufferMemory2KHR(device:%p, bindInfoCount:%d, pBindInfos:%p)", device,
                      bindInfoCount, pBindInfos);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_bindInfoCount;
    VkBindBufferMemoryInfo* local_pBindInfos;
    local_device = device;
    local_bindInfoCount = bindInfoCount;
    local_pBindInfos = nullptr;
    if (pBindInfos) {
        local_pBindInfos = (VkBindBufferMemoryInfo*)pool->alloc(
            ((bindInfoCount)) * sizeof(const VkBindBufferMemoryInfo));
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            deepcopy_VkBindBufferMemoryInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBindInfos + i,
                                            (VkBindBufferMemoryInfo*)(local_pBindInfos + i));
        }
    }
    if (local_pBindInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            transform_tohost_VkBindBufferMemoryInfo(
                sResourceTracker, (VkBindBufferMemoryInfo*)(local_pBindInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            count_VkBindBufferMemoryInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkBindBufferMemoryInfo*)(local_pBindInfos + i), countPtr);
        }
    }
    uint32_t packetSize_vkBindBufferMemory2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkBindBufferMemory2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkBindBufferMemory2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBindBufferMemory2KHR = OP_vkBindBufferMemory2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkBindBufferMemory2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBindBufferMemory2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
        reservedmarshal_VkBindBufferMemoryInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                               (VkBindBufferMemoryInfo*)(local_pBindInfos + i),
                                               streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkBindBufferMemory2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkBindBufferMemory2KHR_VkResult_return = (VkResult)0;
    stream->read(&vkBindBufferMemory2KHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkBindBufferMemory2KHR_VkResult_return;
}

VkResult VkEncoder::vkBindImageMemory2KHR(VkDevice device, uint32_t bindInfoCount,
                                          const VkBindImageMemoryInfo* pBindInfos,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBindImageMemory2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkBindImageMemory2KHR(device:%p, bindInfoCount:%d, pBindInfos:%p)", device,
                      bindInfoCount, pBindInfos);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_bindInfoCount;
    VkBindImageMemoryInfo* local_pBindInfos;
    local_device = device;
    local_bindInfoCount = bindInfoCount;
    local_pBindInfos = nullptr;
    if (pBindInfos) {
        local_pBindInfos = (VkBindImageMemoryInfo*)pool->alloc(((bindInfoCount)) *
                                                               sizeof(const VkBindImageMemoryInfo));
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            deepcopy_VkBindImageMemoryInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBindInfos + i,
                                           (VkBindImageMemoryInfo*)(local_pBindInfos + i));
        }
    }
    if (local_pBindInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            transform_tohost_VkBindImageMemoryInfo(sResourceTracker,
                                                   (VkBindImageMemoryInfo*)(local_pBindInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            count_VkBindImageMemoryInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBindImageMemoryInfo*)(local_pBindInfos + i), countPtr);
        }
    }
    uint32_t packetSize_vkBindImageMemory2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkBindImageMemory2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkBindImageMemory2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBindImageMemory2KHR = OP_vkBindImageMemory2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkBindImageMemory2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBindImageMemory2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
        reservedmarshal_VkBindImageMemoryInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBindImageMemoryInfo*)(local_pBindInfos + i),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkBindImageMemory2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkBindImageMemory2KHR_VkResult_return = (VkResult)0;
    stream->read(&vkBindImageMemory2KHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkBindImageMemory2KHR_VkResult_return;
}

#endif
#ifdef VK_KHR_maintenance3
void VkEncoder::vkGetDescriptorSetLayoutSupportKHR(
    VkDevice device, const VkDescriptorSetLayoutCreateInfo* pCreateInfo,
    VkDescriptorSetLayoutSupport* pSupport, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDescriptorSetLayoutSupportKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDescriptorSetLayoutSupportKHR(device:%p, pCreateInfo:%p, pSupport:%p)",
                      device, pCreateInfo, pSupport);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSetLayoutCreateInfo* local_pCreateInfo;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkDescriptorSetLayoutCreateInfo*)pool->alloc(
            sizeof(const VkDescriptorSetLayoutCreateInfo));
        deepcopy_VkDescriptorSetLayoutCreateInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
            (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo));
    }
    if (local_pCreateInfo) {
        transform_tohost_VkDescriptorSetLayoutCreateInfo(
            sResourceTracker, (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDescriptorSetLayoutCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo),
                                              countPtr);
        count_VkDescriptorSetLayoutSupport(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkDescriptorSetLayoutSupport*)(pSupport), countPtr);
    }
    uint32_t packetSize_vkGetDescriptorSetLayoutSupportKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDescriptorSetLayoutSupportKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDescriptorSetLayoutSupportKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDescriptorSetLayoutSupportKHR = OP_vkGetDescriptorSetLayoutSupportKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDescriptorSetLayoutSupportKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDescriptorSetLayoutSupportKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDescriptorSetLayoutCreateInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkDescriptorSetLayoutCreateInfo*)(local_pCreateInfo),
        streamPtrPtr);
    reservedmarshal_VkDescriptorSetLayoutSupport(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                 (VkDescriptorSetLayoutSupport*)(pSupport),
                                                 streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDescriptorSetLayoutSupportKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkDescriptorSetLayoutSupport(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkDescriptorSetLayoutSupport*)(pSupport));
    if (pSupport) {
        transform_fromhost_VkDescriptorSetLayoutSupport(sResourceTracker,
                                                        (VkDescriptorSetLayoutSupport*)(pSupport));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_buffer_device_address
VkDeviceAddress VkEncoder::vkGetBufferDeviceAddressKHR(VkDevice device,
                                                       const VkBufferDeviceAddressInfo* pInfo,
                                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBufferDeviceAddressKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetBufferDeviceAddressKHR(device:%p, pInfo:%p)", device, pInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferDeviceAddressInfo* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo =
            (VkBufferDeviceAddressInfo*)pool->alloc(sizeof(const VkBufferDeviceAddressInfo));
        deepcopy_VkBufferDeviceAddressInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                           (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkBufferDeviceAddressInfo(sResourceTracker,
                                                   (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferDeviceAddressInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBufferDeviceAddressInfo*)(local_pInfo), countPtr);
    }
    uint32_t packetSize_vkGetBufferDeviceAddressKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetBufferDeviceAddressKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBufferDeviceAddressKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBufferDeviceAddressKHR = OP_vkGetBufferDeviceAddressKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBufferDeviceAddressKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBufferDeviceAddressKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferDeviceAddressInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBufferDeviceAddressInfo*)(local_pInfo),
                                              streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetBufferDeviceAddressKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkDeviceAddress vkGetBufferDeviceAddressKHR_VkDeviceAddress_return = (VkDeviceAddress)0;
    stream->read(&vkGetBufferDeviceAddressKHR_VkDeviceAddress_return, sizeof(VkDeviceAddress));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetBufferDeviceAddressKHR_VkDeviceAddress_return;
}

uint64_t VkEncoder::vkGetBufferOpaqueCaptureAddressKHR(VkDevice device,
                                                       const VkBufferDeviceAddressInfo* pInfo,
                                                       uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBufferOpaqueCaptureAddressKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetBufferOpaqueCaptureAddressKHR(device:%p, pInfo:%p)", device, pInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferDeviceAddressInfo* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo =
            (VkBufferDeviceAddressInfo*)pool->alloc(sizeof(const VkBufferDeviceAddressInfo));
        deepcopy_VkBufferDeviceAddressInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                           (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkBufferDeviceAddressInfo(sResourceTracker,
                                                   (VkBufferDeviceAddressInfo*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferDeviceAddressInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkBufferDeviceAddressInfo*)(local_pInfo), countPtr);
    }
    uint32_t packetSize_vkGetBufferOpaqueCaptureAddressKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetBufferOpaqueCaptureAddressKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBufferOpaqueCaptureAddressKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBufferOpaqueCaptureAddressKHR = OP_vkGetBufferOpaqueCaptureAddressKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBufferOpaqueCaptureAddressKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBufferOpaqueCaptureAddressKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferDeviceAddressInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkBufferDeviceAddressInfo*)(local_pInfo),
                                              streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetBufferOpaqueCaptureAddressKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    uint64_t vkGetBufferOpaqueCaptureAddressKHR_uint64_t_return = (uint64_t)0;
    stream->read(&vkGetBufferOpaqueCaptureAddressKHR_uint64_t_return, sizeof(uint64_t));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetBufferOpaqueCaptureAddressKHR_uint64_t_return;
}

uint64_t VkEncoder::vkGetDeviceMemoryOpaqueCaptureAddressKHR(
    VkDevice device, const VkDeviceMemoryOpaqueCaptureAddressInfo* pInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceMemoryOpaqueCaptureAddressKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDeviceMemoryOpaqueCaptureAddressKHR(device:%p, pInfo:%p)", device,
                      pInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemoryOpaqueCaptureAddressInfo* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceMemoryOpaqueCaptureAddressInfo*)pool->alloc(
            sizeof(const VkDeviceMemoryOpaqueCaptureAddressInfo));
        deepcopy_VkDeviceMemoryOpaqueCaptureAddressInfo(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
            (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceMemoryOpaqueCaptureAddressInfo(
            sResourceTracker, (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceMemoryOpaqueCaptureAddressInfo(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo), countPtr);
    }
    uint32_t packetSize_vkGetDeviceMemoryOpaqueCaptureAddressKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceMemoryOpaqueCaptureAddressKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceMemoryOpaqueCaptureAddressKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceMemoryOpaqueCaptureAddressKHR =
        OP_vkGetDeviceMemoryOpaqueCaptureAddressKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceMemoryOpaqueCaptureAddressKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceMemoryOpaqueCaptureAddressKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceMemoryOpaqueCaptureAddressInfo(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkDeviceMemoryOpaqueCaptureAddressInfo*)(local_pInfo),
        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDeviceMemoryOpaqueCaptureAddressKHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    uint64_t vkGetDeviceMemoryOpaqueCaptureAddressKHR_uint64_t_return = (uint64_t)0;
    stream->read(&vkGetDeviceMemoryOpaqueCaptureAddressKHR_uint64_t_return, sizeof(uint64_t));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetDeviceMemoryOpaqueCaptureAddressKHR_uint64_t_return;
}

#endif
#ifdef VK_KHR_pipeline_executable_properties
VkResult VkEncoder::vkGetPipelineExecutablePropertiesKHR(
    VkDevice device, const VkPipelineInfoKHR* pPipelineInfo, uint32_t* pExecutableCount,
    VkPipelineExecutablePropertiesKHR* pProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPipelineExecutablePropertiesKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPipelineExecutablePropertiesKHR(device:%p, pPipelineInfo:%p, pExecutableCount:%p, "
        "pProperties:%p)",
        device, pPipelineInfo, pExecutableCount, pProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineInfoKHR* local_pPipelineInfo;
    local_device = device;
    local_pPipelineInfo = nullptr;
    if (pPipelineInfo) {
        local_pPipelineInfo = (VkPipelineInfoKHR*)pool->alloc(sizeof(const VkPipelineInfoKHR));
        deepcopy_VkPipelineInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pPipelineInfo,
                                   (VkPipelineInfoKHR*)(local_pPipelineInfo));
    }
    if (local_pPipelineInfo) {
        transform_tohost_VkPipelineInfoKHR(sResourceTracker,
                                           (VkPipelineInfoKHR*)(local_pPipelineInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPipelineInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkPipelineInfoKHR*)(local_pPipelineInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pExecutableCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pProperties) {
            if (pExecutableCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pExecutableCount)); ++i) {
                    count_VkPipelineExecutablePropertiesKHR(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkPipelineExecutablePropertiesKHR*)(pProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPipelineExecutablePropertiesKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPipelineExecutablePropertiesKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPipelineExecutablePropertiesKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPipelineExecutablePropertiesKHR = OP_vkGetPipelineExecutablePropertiesKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPipelineExecutablePropertiesKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPipelineExecutablePropertiesKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPipelineInfoKHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkPipelineInfoKHR*)(local_pPipelineInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pExecutableCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pExecutableCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pExecutableCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pExecutableCount)); ++i) {
            reservedmarshal_VkPipelineExecutablePropertiesKHR(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkPipelineExecutablePropertiesKHR*)(pProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPipelineExecutablePropertiesKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pExecutableCount;
    check_pExecutableCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pExecutableCount) {
        if (!(check_pExecutableCount)) {
            fprintf(stderr, "fatal: pExecutableCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pExecutableCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkPipelineExecutablePropertiesKHR* check_pProperties;
    check_pProperties = (VkPipelineExecutablePropertiesKHR*)(uintptr_t)stream->getBe64();
    if (pProperties) {
        if (!(check_pProperties)) {
            fprintf(stderr, "fatal: pProperties inconsistent between guest and host\n");
        }
        if (pExecutableCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pExecutableCount)); ++i) {
                unmarshal_VkPipelineExecutablePropertiesKHR(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkPipelineExecutablePropertiesKHR*)(pProperties + i));
            }
        }
    }
    if (pExecutableCount) {
        if (pProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pExecutableCount)); ++i) {
                transform_fromhost_VkPipelineExecutablePropertiesKHR(
                    sResourceTracker, (VkPipelineExecutablePropertiesKHR*)(pProperties + i));
            }
        }
    }
    VkResult vkGetPipelineExecutablePropertiesKHR_VkResult_return = (VkResult)0;
    stream->read(&vkGetPipelineExecutablePropertiesKHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPipelineExecutablePropertiesKHR_VkResult_return;
}

VkResult VkEncoder::vkGetPipelineExecutableStatisticsKHR(
    VkDevice device, const VkPipelineExecutableInfoKHR* pExecutableInfo, uint32_t* pStatisticCount,
    VkPipelineExecutableStatisticKHR* pStatistics, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPipelineExecutableStatisticsKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPipelineExecutableStatisticsKHR(device:%p, pExecutableInfo:%p, pStatisticCount:%p, "
        "pStatistics:%p)",
        device, pExecutableInfo, pStatisticCount, pStatistics);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineExecutableInfoKHR* local_pExecutableInfo;
    local_device = device;
    local_pExecutableInfo = nullptr;
    if (pExecutableInfo) {
        local_pExecutableInfo =
            (VkPipelineExecutableInfoKHR*)pool->alloc(sizeof(const VkPipelineExecutableInfoKHR));
        deepcopy_VkPipelineExecutableInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExecutableInfo,
                                             (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo));
    }
    if (local_pExecutableInfo) {
        transform_tohost_VkPipelineExecutableInfoKHR(
            sResourceTracker, (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPipelineExecutableInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo),
                                          countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pStatisticCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pStatistics) {
            if (pStatisticCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pStatisticCount)); ++i) {
                    count_VkPipelineExecutableStatisticKHR(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkPipelineExecutableStatisticKHR*)(pStatistics + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPipelineExecutableStatisticsKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPipelineExecutableStatisticsKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPipelineExecutableStatisticsKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPipelineExecutableStatisticsKHR = OP_vkGetPipelineExecutableStatisticsKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPipelineExecutableStatisticsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPipelineExecutableStatisticsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPipelineExecutableInfoKHR(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo),
        streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pStatisticCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pStatisticCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pStatisticCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pStatistics;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pStatistics) {
        for (uint32_t i = 0; i < (uint32_t)(*(pStatisticCount)); ++i) {
            reservedmarshal_VkPipelineExecutableStatisticKHR(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkPipelineExecutableStatisticKHR*)(pStatistics + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPipelineExecutableStatisticsKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pStatisticCount;
    check_pStatisticCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pStatisticCount) {
        if (!(check_pStatisticCount)) {
            fprintf(stderr, "fatal: pStatisticCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pStatisticCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkPipelineExecutableStatisticKHR* check_pStatistics;
    check_pStatistics = (VkPipelineExecutableStatisticKHR*)(uintptr_t)stream->getBe64();
    if (pStatistics) {
        if (!(check_pStatistics)) {
            fprintf(stderr, "fatal: pStatistics inconsistent between guest and host\n");
        }
        if (pStatisticCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pStatisticCount)); ++i) {
                unmarshal_VkPipelineExecutableStatisticKHR(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkPipelineExecutableStatisticKHR*)(pStatistics + i));
            }
        }
    }
    if (pStatisticCount) {
        if (pStatistics) {
            for (uint32_t i = 0; i < (uint32_t)(*(pStatisticCount)); ++i) {
                transform_fromhost_VkPipelineExecutableStatisticKHR(
                    sResourceTracker, (VkPipelineExecutableStatisticKHR*)(pStatistics + i));
            }
        }
    }
    VkResult vkGetPipelineExecutableStatisticsKHR_VkResult_return = (VkResult)0;
    stream->read(&vkGetPipelineExecutableStatisticsKHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPipelineExecutableStatisticsKHR_VkResult_return;
}

VkResult VkEncoder::vkGetPipelineExecutableInternalRepresentationsKHR(
    VkDevice device, const VkPipelineExecutableInfoKHR* pExecutableInfo,
    uint32_t* pInternalRepresentationCount,
    VkPipelineExecutableInternalRepresentationKHR* pInternalRepresentations, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkGetPipelineExecutableInternalRepresentationsKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPipelineExecutableInternalRepresentationsKHR(device:%p, pExecutableInfo:%p, "
        "pInternalRepresentationCount:%p, pInternalRepresentations:%p)",
        device, pExecutableInfo, pInternalRepresentationCount, pInternalRepresentations);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPipelineExecutableInfoKHR* local_pExecutableInfo;
    local_device = device;
    local_pExecutableInfo = nullptr;
    if (pExecutableInfo) {
        local_pExecutableInfo =
            (VkPipelineExecutableInfoKHR*)pool->alloc(sizeof(const VkPipelineExecutableInfoKHR));
        deepcopy_VkPipelineExecutableInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pExecutableInfo,
                                             (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo));
    }
    if (local_pExecutableInfo) {
        transform_tohost_VkPipelineExecutableInfoKHR(
            sResourceTracker, (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPipelineExecutableInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo),
                                          countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pInternalRepresentationCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pInternalRepresentations) {
            if (pInternalRepresentationCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pInternalRepresentationCount)); ++i) {
                    count_VkPipelineExecutableInternalRepresentationKHR(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkPipelineExecutableInternalRepresentationKHR*)(pInternalRepresentations +
                                                                         i),
                        countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPipelineExecutableInternalRepresentationsKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPipelineExecutableInternalRepresentationsKHR);
    uint8_t* streamPtr =
        stream->reserve(packetSize_vkGetPipelineExecutableInternalRepresentationsKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPipelineExecutableInternalRepresentationsKHR =
        OP_vkGetPipelineExecutableInternalRepresentationsKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPipelineExecutableInternalRepresentationsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPipelineExecutableInternalRepresentationsKHR,
           sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPipelineExecutableInfoKHR(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkPipelineExecutableInfoKHR*)(local_pExecutableInfo),
        streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pInternalRepresentationCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pInternalRepresentationCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pInternalRepresentationCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pInternalRepresentations;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pInternalRepresentations) {
        for (uint32_t i = 0; i < (uint32_t)(*(pInternalRepresentationCount)); ++i) {
            reservedmarshal_VkPipelineExecutableInternalRepresentationKHR(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkPipelineExecutableInternalRepresentationKHR*)(pInternalRepresentations + i),
                streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPipelineExecutableInternalRepresentationsKHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pInternalRepresentationCount;
    check_pInternalRepresentationCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pInternalRepresentationCount) {
        if (!(check_pInternalRepresentationCount)) {
            fprintf(stderr,
                    "fatal: pInternalRepresentationCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pInternalRepresentationCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkPipelineExecutableInternalRepresentationKHR* check_pInternalRepresentations;
    check_pInternalRepresentations =
        (VkPipelineExecutableInternalRepresentationKHR*)(uintptr_t)stream->getBe64();
    if (pInternalRepresentations) {
        if (!(check_pInternalRepresentations)) {
            fprintf(stderr,
                    "fatal: pInternalRepresentations inconsistent between guest and host\n");
        }
        if (pInternalRepresentationCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pInternalRepresentationCount)); ++i) {
                unmarshal_VkPipelineExecutableInternalRepresentationKHR(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkPipelineExecutableInternalRepresentationKHR*)(pInternalRepresentations + i));
            }
        }
    }
    if (pInternalRepresentationCount) {
        if (pInternalRepresentations) {
            for (uint32_t i = 0; i < (uint32_t)(*(pInternalRepresentationCount)); ++i) {
                transform_fromhost_VkPipelineExecutableInternalRepresentationKHR(
                    sResourceTracker,
                    (VkPipelineExecutableInternalRepresentationKHR*)(pInternalRepresentations + i));
            }
        }
    }
    VkResult vkGetPipelineExecutableInternalRepresentationsKHR_VkResult_return = (VkResult)0;
    stream->read(&vkGetPipelineExecutableInternalRepresentationsKHR_VkResult_return,
                 sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPipelineExecutableInternalRepresentationsKHR_VkResult_return;
}

#endif
#ifdef VK_KHR_synchronization2
void VkEncoder::vkCmdSetEvent2KHR(VkCommandBuffer commandBuffer, VkEvent event,
                                  const VkDependencyInfo* pDependencyInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetEvent2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetEvent2KHR(commandBuffer:%p, event:%p, pDependencyInfo:%p)",
                      commandBuffer, event, pDependencyInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkEvent local_event;
    VkDependencyInfo* local_pDependencyInfo;
    local_commandBuffer = commandBuffer;
    local_event = event;
    local_pDependencyInfo = nullptr;
    if (pDependencyInfo) {
        local_pDependencyInfo = (VkDependencyInfo*)pool->alloc(sizeof(const VkDependencyInfo));
        deepcopy_VkDependencyInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDependencyInfo,
                                  (VkDependencyInfo*)(local_pDependencyInfo));
    }
    if (local_pDependencyInfo) {
        transform_tohost_VkDependencyInfo(sResourceTracker,
                                          (VkDependencyInfo*)(local_pDependencyInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkDependencyInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkDependencyInfo*)(local_pDependencyInfo), countPtr);
    }
    uint32_t packetSize_vkCmdSetEvent2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetEvent2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetEvent2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetEvent2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetEvent2KHR = OP_vkCmdSetEvent2KHR;
    memcpy(streamPtr, &opcode_vkCmdSetEvent2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetEvent2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDependencyInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkDependencyInfo*)(local_pDependencyInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdSetEvent2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdResetEvent2KHR(VkCommandBuffer commandBuffer, VkEvent event,
                                    VkPipelineStageFlags2 stageMask, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdResetEvent2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdResetEvent2KHR(commandBuffer:%p, event:%p)", commandBuffer, event);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkEvent local_event;
    VkPipelineStageFlags2 local_stageMask;
    local_commandBuffer = commandBuffer;
    local_event = event;
    local_stageMask = stageMask;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags2);
    }
    uint32_t packetSize_vkCmdResetEvent2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdResetEvent2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdResetEvent2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdResetEvent2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdResetEvent2KHR = OP_vkCmdResetEvent2KHR;
    memcpy(streamPtr, &opcode_vkCmdResetEvent2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdResetEvent2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkEvent((*&local_event));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkPipelineStageFlags2*)&local_stageMask, sizeof(VkPipelineStageFlags2));
    *streamPtrPtr += sizeof(VkPipelineStageFlags2);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdResetEvent2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdWaitEvents2KHR(VkCommandBuffer commandBuffer, uint32_t eventCount,
                                    const VkEvent* pEvents,
                                    const VkDependencyInfo* pDependencyInfos, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdWaitEvents2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdWaitEvents2KHR(commandBuffer:%p, eventCount:%d, pEvents:%p, pDependencyInfos:%p)",
        commandBuffer, eventCount, pEvents, pDependencyInfos);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_eventCount;
    VkEvent* local_pEvents;
    VkDependencyInfo* local_pDependencyInfos;
    local_commandBuffer = commandBuffer;
    local_eventCount = eventCount;
    // Avoiding deepcopy for pEvents
    local_pEvents = (VkEvent*)pEvents;
    local_pDependencyInfos = nullptr;
    if (pDependencyInfos) {
        local_pDependencyInfos =
            (VkDependencyInfo*)pool->alloc(((eventCount)) * sizeof(const VkDependencyInfo));
        for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
            deepcopy_VkDependencyInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDependencyInfos + i,
                                      (VkDependencyInfo*)(local_pDependencyInfos + i));
        }
    }
    if (local_pDependencyInfos) {
        for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
            transform_tohost_VkDependencyInfo(sResourceTracker,
                                              (VkDependencyInfo*)(local_pDependencyInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((eventCount))) {
            *countPtr += ((eventCount)) * 8;
        }
        for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
            count_VkDependencyInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkDependencyInfo*)(local_pDependencyInfos + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdWaitEvents2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdWaitEvents2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdWaitEvents2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdWaitEvents2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdWaitEvents2KHR = OP_vkCmdWaitEvents2KHR;
    memcpy(streamPtr, &opcode_vkCmdWaitEvents2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdWaitEvents2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_eventCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((eventCount))) {
        uint8_t* cgen_var_0_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((eventCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkEvent(local_pEvents[k]);
            memcpy(cgen_var_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((eventCount));
    }
    for (uint32_t i = 0; i < (uint32_t)((eventCount)); ++i) {
        reservedmarshal_VkDependencyInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkDependencyInfo*)(local_pDependencyInfos + i),
                                         streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdWaitEvents2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdPipelineBarrier2KHR(VkCommandBuffer commandBuffer,
                                         const VkDependencyInfo* pDependencyInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdPipelineBarrier2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdPipelineBarrier2KHR(commandBuffer:%p, pDependencyInfo:%p)",
                      commandBuffer, pDependencyInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkDependencyInfo* local_pDependencyInfo;
    local_commandBuffer = commandBuffer;
    local_pDependencyInfo = nullptr;
    if (pDependencyInfo) {
        local_pDependencyInfo = (VkDependencyInfo*)pool->alloc(sizeof(const VkDependencyInfo));
        deepcopy_VkDependencyInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pDependencyInfo,
                                  (VkDependencyInfo*)(local_pDependencyInfo));
    }
    if (local_pDependencyInfo) {
        transform_tohost_VkDependencyInfo(sResourceTracker,
                                          (VkDependencyInfo*)(local_pDependencyInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDependencyInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkDependencyInfo*)(local_pDependencyInfo), countPtr);
    }
    uint32_t packetSize_vkCmdPipelineBarrier2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdPipelineBarrier2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdPipelineBarrier2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdPipelineBarrier2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdPipelineBarrier2KHR = OP_vkCmdPipelineBarrier2KHR;
    memcpy(streamPtr, &opcode_vkCmdPipelineBarrier2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdPipelineBarrier2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkDependencyInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkDependencyInfo*)(local_pDependencyInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdPipelineBarrier2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdWriteTimestamp2KHR(VkCommandBuffer commandBuffer, VkPipelineStageFlags2 stage,
                                        VkQueryPool queryPool, uint32_t query, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdWriteTimestamp2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdWriteTimestamp2KHR(commandBuffer:%p, queryPool:%p, query:%d)",
                      commandBuffer, queryPool, query);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineStageFlags2 local_stage;
    VkQueryPool local_queryPool;
    uint32_t local_query;
    local_commandBuffer = commandBuffer;
    local_stage = stage;
    local_queryPool = queryPool;
    local_query = query;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags2);
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdWriteTimestamp2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdWriteTimestamp2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdWriteTimestamp2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdWriteTimestamp2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdWriteTimestamp2KHR = OP_vkCmdWriteTimestamp2KHR;
    memcpy(streamPtr, &opcode_vkCmdWriteTimestamp2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdWriteTimestamp2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPipelineStageFlags2*)&local_stage, sizeof(VkPipelineStageFlags2));
    *streamPtrPtr += sizeof(VkPipelineStageFlags2);
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_query, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdWriteTimestamp2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkQueueSubmit2KHR(VkQueue queue, uint32_t submitCount,
                                      const VkSubmitInfo2* pSubmits, VkFence fence,
                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueSubmit2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueSubmit2KHR(queue:%p, submitCount:%d, pSubmits:%p, fence:%p)", queue,
                      submitCount, pSubmits, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_submitCount;
    VkSubmitInfo2* local_pSubmits;
    VkFence local_fence;
    local_queue = queue;
    local_submitCount = submitCount;
    local_pSubmits = nullptr;
    if (pSubmits) {
        local_pSubmits = (VkSubmitInfo2*)pool->alloc(((submitCount)) * sizeof(const VkSubmitInfo2));
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            deepcopy_VkSubmitInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubmits + i,
                                   (VkSubmitInfo2*)(local_pSubmits + i));
        }
    }
    local_fence = fence;
    if (local_pSubmits) {
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            transform_tohost_VkSubmitInfo2(sResourceTracker, (VkSubmitInfo2*)(local_pSubmits + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            count_VkSubmitInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkSubmitInfo2*)(local_pSubmits + i), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueSubmit2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueSubmit2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueSubmit2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueSubmit2KHR = OP_vkQueueSubmit2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueSubmit2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueSubmit2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_submitCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
        reservedmarshal_VkSubmitInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubmitInfo2*)(local_pSubmits + i), streamPtrPtr);
    }
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkQueueSubmit2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkQueueSubmit2KHR_VkResult_return = (VkResult)0;
    stream->read(&vkQueueSubmit2KHR_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkQueueSubmit2KHR_VkResult_return;
}

void VkEncoder::vkCmdWriteBufferMarker2AMD(VkCommandBuffer commandBuffer,
                                           VkPipelineStageFlags2 stage, VkBuffer dstBuffer,
                                           VkDeviceSize dstOffset, uint32_t marker,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdWriteBufferMarker2AMD in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdWriteBufferMarker2AMD(commandBuffer:%p, dstBuffer:%p, dstOffset:%ld, marker:%d)",
        commandBuffer, dstBuffer, dstOffset, marker);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPipelineStageFlags2 local_stage;
    VkBuffer local_dstBuffer;
    VkDeviceSize local_dstOffset;
    uint32_t local_marker;
    local_commandBuffer = commandBuffer;
    local_stage = stage;
    local_dstBuffer = dstBuffer;
    local_dstOffset = dstOffset;
    local_marker = marker;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPipelineStageFlags2);
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdWriteBufferMarker2AMD = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdWriteBufferMarker2AMD);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdWriteBufferMarker2AMD -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdWriteBufferMarker2AMD);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdWriteBufferMarker2AMD = OP_vkCmdWriteBufferMarker2AMD;
    memcpy(streamPtr, &opcode_vkCmdWriteBufferMarker2AMD, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdWriteBufferMarker2AMD, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPipelineStageFlags2*)&local_stage, sizeof(VkPipelineStageFlags2));
    *streamPtrPtr += sizeof(VkPipelineStageFlags2);
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_dstBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_dstOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (uint32_t*)&local_marker, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdWriteBufferMarker2AMD), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetQueueCheckpointData2NV(VkQueue queue, uint32_t* pCheckpointDataCount,
                                            VkCheckpointData2NV* pCheckpointData, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetQueueCheckpointData2NV in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetQueueCheckpointData2NV(queue:%p, pCheckpointDataCount:%p, pCheckpointData:%p)", queue,
        pCheckpointDataCount, pCheckpointData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    local_queue = queue;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pCheckpointDataCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pCheckpointData) {
            if (pCheckpointDataCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pCheckpointDataCount)); ++i) {
                    count_VkCheckpointData2NV(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkCheckpointData2NV*)(pCheckpointData + i),
                                              countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetQueueCheckpointData2NV =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetQueueCheckpointData2NV);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetQueueCheckpointData2NV);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetQueueCheckpointData2NV = OP_vkGetQueueCheckpointData2NV;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetQueueCheckpointData2NV, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetQueueCheckpointData2NV, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pCheckpointDataCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pCheckpointDataCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pCheckpointDataCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pCheckpointData;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pCheckpointData) {
        for (uint32_t i = 0; i < (uint32_t)(*(pCheckpointDataCount)); ++i) {
            reservedmarshal_VkCheckpointData2NV(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkCheckpointData2NV*)(pCheckpointData + i),
                                                streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetQueueCheckpointData2NV), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pCheckpointDataCount;
    check_pCheckpointDataCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pCheckpointDataCount) {
        if (!(check_pCheckpointDataCount)) {
            fprintf(stderr, "fatal: pCheckpointDataCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pCheckpointDataCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkCheckpointData2NV* check_pCheckpointData;
    check_pCheckpointData = (VkCheckpointData2NV*)(uintptr_t)stream->getBe64();
    if (pCheckpointData) {
        if (!(check_pCheckpointData)) {
            fprintf(stderr, "fatal: pCheckpointData inconsistent between guest and host\n");
        }
        if (pCheckpointDataCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pCheckpointDataCount)); ++i) {
                unmarshal_VkCheckpointData2NV(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkCheckpointData2NV*)(pCheckpointData + i));
            }
        }
    }
    if (pCheckpointDataCount) {
        if (pCheckpointData) {
            for (uint32_t i = 0; i < (uint32_t)(*(pCheckpointDataCount)); ++i) {
                transform_fromhost_VkCheckpointData2NV(sResourceTracker,
                                                       (VkCheckpointData2NV*)(pCheckpointData + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_copy_commands2
void VkEncoder::vkCmdCopyBuffer2KHR(VkCommandBuffer commandBuffer,
                                    const VkCopyBufferInfo2* pCopyBufferInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyBuffer2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyBuffer2KHR(commandBuffer:%p, pCopyBufferInfo:%p)", commandBuffer,
                      pCopyBufferInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyBufferInfo2* local_pCopyBufferInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyBufferInfo = nullptr;
    if (pCopyBufferInfo) {
        local_pCopyBufferInfo = (VkCopyBufferInfo2*)pool->alloc(sizeof(const VkCopyBufferInfo2));
        deepcopy_VkCopyBufferInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyBufferInfo,
                                   (VkCopyBufferInfo2*)(local_pCopyBufferInfo));
    }
    if (local_pCopyBufferInfo) {
        transform_tohost_VkCopyBufferInfo2(sResourceTracker,
                                           (VkCopyBufferInfo2*)(local_pCopyBufferInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyBufferInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkCopyBufferInfo2*)(local_pCopyBufferInfo), countPtr);
    }
    uint32_t packetSize_vkCmdCopyBuffer2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyBuffer2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyBuffer2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyBuffer2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyBuffer2KHR = OP_vkCmdCopyBuffer2KHR;
    memcpy(streamPtr, &opcode_vkCmdCopyBuffer2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyBuffer2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyBufferInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkCopyBufferInfo2*)(local_pCopyBufferInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyBuffer2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyImage2KHR(VkCommandBuffer commandBuffer,
                                   const VkCopyImageInfo2* pCopyImageInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyImage2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyImage2KHR(commandBuffer:%p, pCopyImageInfo:%p)", commandBuffer,
                      pCopyImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyImageInfo2* local_pCopyImageInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyImageInfo = nullptr;
    if (pCopyImageInfo) {
        local_pCopyImageInfo = (VkCopyImageInfo2*)pool->alloc(sizeof(const VkCopyImageInfo2));
        deepcopy_VkCopyImageInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyImageInfo,
                                  (VkCopyImageInfo2*)(local_pCopyImageInfo));
    }
    if (local_pCopyImageInfo) {
        transform_tohost_VkCopyImageInfo2(sResourceTracker,
                                          (VkCopyImageInfo2*)(local_pCopyImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkCopyImageInfo2*)(local_pCopyImageInfo), countPtr);
    }
    uint32_t packetSize_vkCmdCopyImage2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyImage2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyImage2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyImage2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyImage2KHR = OP_vkCmdCopyImage2KHR;
    memcpy(streamPtr, &opcode_vkCmdCopyImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyImageInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkCopyImageInfo2*)(local_pCopyImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyImage2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyBufferToImage2KHR(VkCommandBuffer commandBuffer,
                                           const VkCopyBufferToImageInfo2* pCopyBufferToImageInfo,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyBufferToImage2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyBufferToImage2KHR(commandBuffer:%p, pCopyBufferToImageInfo:%p)",
                      commandBuffer, pCopyBufferToImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyBufferToImageInfo2* local_pCopyBufferToImageInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyBufferToImageInfo = nullptr;
    if (pCopyBufferToImageInfo) {
        local_pCopyBufferToImageInfo =
            (VkCopyBufferToImageInfo2*)pool->alloc(sizeof(const VkCopyBufferToImageInfo2));
        deepcopy_VkCopyBufferToImageInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyBufferToImageInfo,
            (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo));
    }
    if (local_pCopyBufferToImageInfo) {
        transform_tohost_VkCopyBufferToImageInfo2(
            sResourceTracker, (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyBufferToImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo),
                                       countPtr);
    }
    uint32_t packetSize_vkCmdCopyBufferToImage2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyBufferToImage2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyBufferToImage2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyBufferToImage2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyBufferToImage2KHR = OP_vkCmdCopyBufferToImage2KHR;
    memcpy(streamPtr, &opcode_vkCmdCopyBufferToImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyBufferToImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyBufferToImageInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkCopyBufferToImageInfo2*)(local_pCopyBufferToImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyBufferToImage2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdCopyImageToBuffer2KHR(VkCommandBuffer commandBuffer,
                                           const VkCopyImageToBufferInfo2* pCopyImageToBufferInfo,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdCopyImageToBuffer2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdCopyImageToBuffer2KHR(commandBuffer:%p, pCopyImageToBufferInfo:%p)",
                      commandBuffer, pCopyImageToBufferInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCopyImageToBufferInfo2* local_pCopyImageToBufferInfo;
    local_commandBuffer = commandBuffer;
    local_pCopyImageToBufferInfo = nullptr;
    if (pCopyImageToBufferInfo) {
        local_pCopyImageToBufferInfo =
            (VkCopyImageToBufferInfo2*)pool->alloc(sizeof(const VkCopyImageToBufferInfo2));
        deepcopy_VkCopyImageToBufferInfo2(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyImageToBufferInfo,
            (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo));
    }
    if (local_pCopyImageToBufferInfo) {
        transform_tohost_VkCopyImageToBufferInfo2(
            sResourceTracker, (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyImageToBufferInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo),
                                       countPtr);
    }
    uint32_t packetSize_vkCmdCopyImageToBuffer2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdCopyImageToBuffer2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdCopyImageToBuffer2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdCopyImageToBuffer2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdCopyImageToBuffer2KHR = OP_vkCmdCopyImageToBuffer2KHR;
    memcpy(streamPtr, &opcode_vkCmdCopyImageToBuffer2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdCopyImageToBuffer2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCopyImageToBufferInfo2(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkCopyImageToBufferInfo2*)(local_pCopyImageToBufferInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdCopyImageToBuffer2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBlitImage2KHR(VkCommandBuffer commandBuffer,
                                   const VkBlitImageInfo2* pBlitImageInfo, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBlitImage2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBlitImage2KHR(commandBuffer:%p, pBlitImageInfo:%p)", commandBuffer,
                      pBlitImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBlitImageInfo2* local_pBlitImageInfo;
    local_commandBuffer = commandBuffer;
    local_pBlitImageInfo = nullptr;
    if (pBlitImageInfo) {
        local_pBlitImageInfo = (VkBlitImageInfo2*)pool->alloc(sizeof(const VkBlitImageInfo2));
        deepcopy_VkBlitImageInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBlitImageInfo,
                                  (VkBlitImageInfo2*)(local_pBlitImageInfo));
    }
    if (local_pBlitImageInfo) {
        transform_tohost_VkBlitImageInfo2(sResourceTracker,
                                          (VkBlitImageInfo2*)(local_pBlitImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBlitImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkBlitImageInfo2*)(local_pBlitImageInfo), countPtr);
    }
    uint32_t packetSize_vkCmdBlitImage2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBlitImage2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBlitImage2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBlitImage2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBlitImage2KHR = OP_vkCmdBlitImage2KHR;
    memcpy(streamPtr, &opcode_vkCmdBlitImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBlitImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkBlitImageInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkBlitImageInfo2*)(local_pBlitImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBlitImage2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdResolveImage2KHR(VkCommandBuffer commandBuffer,
                                      const VkResolveImageInfo2* pResolveImageInfo,
                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdResolveImage2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdResolveImage2KHR(commandBuffer:%p, pResolveImageInfo:%p)",
                      commandBuffer, pResolveImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkResolveImageInfo2* local_pResolveImageInfo;
    local_commandBuffer = commandBuffer;
    local_pResolveImageInfo = nullptr;
    if (pResolveImageInfo) {
        local_pResolveImageInfo =
            (VkResolveImageInfo2*)pool->alloc(sizeof(const VkResolveImageInfo2));
        deepcopy_VkResolveImageInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pResolveImageInfo,
                                     (VkResolveImageInfo2*)(local_pResolveImageInfo));
    }
    if (local_pResolveImageInfo) {
        transform_tohost_VkResolveImageInfo2(sResourceTracker,
                                             (VkResolveImageInfo2*)(local_pResolveImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkResolveImageInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                  (VkResolveImageInfo2*)(local_pResolveImageInfo), countPtr);
    }
    uint32_t packetSize_vkCmdResolveImage2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdResolveImage2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdResolveImage2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdResolveImage2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdResolveImage2KHR = OP_vkCmdResolveImage2KHR;
    memcpy(streamPtr, &opcode_vkCmdResolveImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdResolveImage2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkResolveImageInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkResolveImageInfo2*)(local_pResolveImageInfo),
                                        streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdResolveImage2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_maintenance4
void VkEncoder::vkGetDeviceBufferMemoryRequirementsKHR(
    VkDevice device, const VkDeviceBufferMemoryRequirements* pInfo,
    VkMemoryRequirements2* pMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceBufferMemoryRequirementsKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceBufferMemoryRequirementsKHR(device:%p, pInfo:%p, pMemoryRequirements:%p)",
        device, pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceBufferMemoryRequirements* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceBufferMemoryRequirements*)pool->alloc(
            sizeof(const VkDeviceBufferMemoryRequirements));
        deepcopy_VkDeviceBufferMemoryRequirements(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                  (VkDeviceBufferMemoryRequirements*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceBufferMemoryRequirements(
            sResourceTracker, (VkDeviceBufferMemoryRequirements*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceBufferMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                               (VkDeviceBufferMemoryRequirements*)(local_pInfo),
                                               countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetDeviceBufferMemoryRequirementsKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceBufferMemoryRequirementsKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceBufferMemoryRequirementsKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceBufferMemoryRequirementsKHR =
        OP_vkGetDeviceBufferMemoryRequirementsKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceBufferMemoryRequirementsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceBufferMemoryRequirementsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceBufferMemoryRequirements(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkDeviceBufferMemoryRequirements*)(local_pInfo),
        streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetDeviceBufferMemoryRequirementsKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDeviceImageMemoryRequirementsKHR(VkDevice device,
                                                      const VkDeviceImageMemoryRequirements* pInfo,
                                                      VkMemoryRequirements2* pMemoryRequirements,
                                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceImageMemoryRequirementsKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceImageMemoryRequirementsKHR(device:%p, pInfo:%p, pMemoryRequirements:%p)",
        device, pInfo, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceImageMemoryRequirements* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceImageMemoryRequirements*)pool->alloc(
            sizeof(const VkDeviceImageMemoryRequirements));
        deepcopy_VkDeviceImageMemoryRequirements(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                 (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceImageMemoryRequirements(
            sResourceTracker, (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceImageMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                              countPtr);
        count_VkMemoryRequirements2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkGetDeviceImageMemoryRequirementsKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceImageMemoryRequirementsKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceImageMemoryRequirementsKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceImageMemoryRequirementsKHR =
        OP_vkGetDeviceImageMemoryRequirementsKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceImageMemoryRequirementsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceImageMemoryRequirementsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceImageMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                    (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                                    streamPtrPtr);
    reservedmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkMemoryRequirements2*)(pMemoryRequirements),
                                          streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetDeviceImageMemoryRequirementsKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkMemoryRequirements2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                    (VkMemoryRequirements2*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements2(sResourceTracker,
                                                 (VkMemoryRequirements2*)(pMemoryRequirements));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDeviceImageSparseMemoryRequirementsKHR(
    VkDevice device, const VkDeviceImageMemoryRequirements* pInfo,
    uint32_t* pSparseMemoryRequirementCount,
    VkSparseImageMemoryRequirements2* pSparseMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceImageSparseMemoryRequirementsKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetDeviceImageSparseMemoryRequirementsKHR(device:%p, pInfo:%p, "
        "pSparseMemoryRequirementCount:%p, pSparseMemoryRequirements:%p)",
        device, pInfo, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceImageMemoryRequirements* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceImageMemoryRequirements*)pool->alloc(
            sizeof(const VkDeviceImageMemoryRequirements));
        deepcopy_VkDeviceImageMemoryRequirements(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                 (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceImageMemoryRequirements(
            sResourceTracker, (VkDeviceImageMemoryRequirements*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceImageMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                              countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirementCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSparseMemoryRequirements) {
            if (pSparseMemoryRequirementCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                    count_VkSparseImageMemoryRequirements2(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i),
                        countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetDeviceImageSparseMemoryRequirementsKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceImageSparseMemoryRequirementsKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceImageSparseMemoryRequirementsKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceImageSparseMemoryRequirementsKHR =
        OP_vkGetDeviceImageSparseMemoryRequirementsKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceImageSparseMemoryRequirementsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceImageSparseMemoryRequirementsKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceImageMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                    (VkDeviceImageMemoryRequirements*)(local_pInfo),
                                                    streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pSparseMemoryRequirementCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirementCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pSparseMemoryRequirements;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSparseMemoryRequirements) {
        for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
            reservedmarshal_VkSparseImageMemoryRequirements2(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetDeviceImageSparseMemoryRequirementsKHR),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pSparseMemoryRequirementCount;
    check_pSparseMemoryRequirementCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirementCount) {
        if (!(check_pSparseMemoryRequirementCount)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirementCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pSparseMemoryRequirementCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkSparseImageMemoryRequirements2* check_pSparseMemoryRequirements;
    check_pSparseMemoryRequirements =
        (VkSparseImageMemoryRequirements2*)(uintptr_t)stream->getBe64();
    if (pSparseMemoryRequirements) {
        if (!(check_pSparseMemoryRequirements)) {
            fprintf(stderr,
                    "fatal: pSparseMemoryRequirements inconsistent between guest and host\n");
        }
        if (pSparseMemoryRequirementCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                unmarshal_VkSparseImageMemoryRequirements2(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    if (pSparseMemoryRequirementCount) {
        if (pSparseMemoryRequirements) {
            for (uint32_t i = 0; i < (uint32_t)(*(pSparseMemoryRequirementCount)); ++i) {
                transform_fromhost_VkSparseImageMemoryRequirements2(
                    sResourceTracker,
                    (VkSparseImageMemoryRequirements2*)(pSparseMemoryRequirements + i));
            }
        }
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_KHR_maintenance5
void VkEncoder::vkCmdBindIndexBuffer2KHR(VkCommandBuffer commandBuffer, VkBuffer buffer,
                                         VkDeviceSize offset, VkDeviceSize size,
                                         VkIndexType indexType, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindIndexBuffer2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdBindIndexBuffer2KHR(commandBuffer:%p, buffer:%p, offset:%ld, size:%ld)",
                      commandBuffer, buffer, offset, size);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBuffer local_buffer;
    VkDeviceSize local_offset;
    VkDeviceSize local_size;
    VkIndexType local_indexType;
    local_commandBuffer = commandBuffer;
    local_buffer = buffer;
    local_offset = offset;
    local_size = size;
    local_indexType = indexType;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkIndexType);
    }
    uint32_t packetSize_vkCmdBindIndexBuffer2KHR = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBindIndexBuffer2KHR);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindIndexBuffer2KHR -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindIndexBuffer2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindIndexBuffer2KHR = OP_vkCmdBindIndexBuffer2KHR;
    memcpy(streamPtr, &opcode_vkCmdBindIndexBuffer2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindIndexBuffer2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_buffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_offset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_size, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkIndexType*)&local_indexType, sizeof(VkIndexType));
    *streamPtrPtr += sizeof(VkIndexType);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBindIndexBuffer2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetRenderingAreaGranularityKHR(VkDevice device,
                                                 const VkRenderingAreaInfoKHR* pRenderingAreaInfo,
                                                 VkExtent2D* pGranularity, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetRenderingAreaGranularityKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetRenderingAreaGranularityKHR(device:%p, pRenderingAreaInfo:%p, pGranularity:%p)",
        device, pRenderingAreaInfo, pGranularity);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkRenderingAreaInfoKHR* local_pRenderingAreaInfo;
    local_device = device;
    local_pRenderingAreaInfo = nullptr;
    if (pRenderingAreaInfo) {
        local_pRenderingAreaInfo =
            (VkRenderingAreaInfoKHR*)pool->alloc(sizeof(const VkRenderingAreaInfoKHR));
        deepcopy_VkRenderingAreaInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pRenderingAreaInfo,
                                        (VkRenderingAreaInfoKHR*)(local_pRenderingAreaInfo));
    }
    if (local_pRenderingAreaInfo) {
        transform_tohost_VkRenderingAreaInfoKHR(
            sResourceTracker, (VkRenderingAreaInfoKHR*)(local_pRenderingAreaInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkRenderingAreaInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkRenderingAreaInfoKHR*)(local_pRenderingAreaInfo), countPtr);
        count_VkExtent2D(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExtent2D*)(pGranularity),
                         countPtr);
    }
    uint32_t packetSize_vkGetRenderingAreaGranularityKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetRenderingAreaGranularityKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetRenderingAreaGranularityKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetRenderingAreaGranularityKHR = OP_vkGetRenderingAreaGranularityKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetRenderingAreaGranularityKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetRenderingAreaGranularityKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkRenderingAreaInfoKHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkRenderingAreaInfoKHR*)(local_pRenderingAreaInfo),
                                           streamPtrPtr);
    reservedmarshal_VkExtent2D(stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExtent2D*)(pGranularity),
                               streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetRenderingAreaGranularityKHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkExtent2D(stream, VK_STRUCTURE_TYPE_MAX_ENUM, (VkExtent2D*)(pGranularity));
    if (pGranularity) {
        transform_fromhost_VkExtent2D(sResourceTracker, (VkExtent2D*)(pGranularity));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetDeviceImageSubresourceLayoutKHR(VkDevice device,
                                                     const VkDeviceImageSubresourceInfoKHR* pInfo,
                                                     VkSubresourceLayout2KHR* pLayout,
                                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetDeviceImageSubresourceLayoutKHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetDeviceImageSubresourceLayoutKHR(device:%p, pInfo:%p, pLayout:%p)",
                      device, pInfo, pLayout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceImageSubresourceInfoKHR* local_pInfo;
    local_device = device;
    local_pInfo = nullptr;
    if (pInfo) {
        local_pInfo = (VkDeviceImageSubresourceInfoKHR*)pool->alloc(
            sizeof(const VkDeviceImageSubresourceInfoKHR));
        deepcopy_VkDeviceImageSubresourceInfoKHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pInfo,
                                                 (VkDeviceImageSubresourceInfoKHR*)(local_pInfo));
    }
    if (local_pInfo) {
        transform_tohost_VkDeviceImageSubresourceInfoKHR(
            sResourceTracker, (VkDeviceImageSubresourceInfoKHR*)(local_pInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkDeviceImageSubresourceInfoKHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkDeviceImageSubresourceInfoKHR*)(local_pInfo),
                                              countPtr);
        count_VkSubresourceLayout2KHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubresourceLayout2KHR*)(pLayout), countPtr);
    }
    uint32_t packetSize_vkGetDeviceImageSubresourceLayoutKHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetDeviceImageSubresourceLayoutKHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetDeviceImageSubresourceLayoutKHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetDeviceImageSubresourceLayoutKHR = OP_vkGetDeviceImageSubresourceLayoutKHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetDeviceImageSubresourceLayoutKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetDeviceImageSubresourceLayoutKHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkDeviceImageSubresourceInfoKHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                    (VkDeviceImageSubresourceInfoKHR*)(local_pInfo),
                                                    streamPtrPtr);
    reservedmarshal_VkSubresourceLayout2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkSubresourceLayout2KHR*)(pLayout), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetDeviceImageSubresourceLayoutKHR),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkSubresourceLayout2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubresourceLayout2KHR*)(pLayout));
    if (pLayout) {
        transform_fromhost_VkSubresourceLayout2KHR(sResourceTracker,
                                                   (VkSubresourceLayout2KHR*)(pLayout));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetImageSubresourceLayout2KHR(VkDevice device, VkImage image,
                                                const VkImageSubresource2KHR* pSubresource,
                                                VkSubresourceLayout2KHR* pLayout, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageSubresourceLayout2KHR in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetImageSubresourceLayout2KHR(device:%p, image:%p, pSubresource:%p, pLayout:%p)", device,
        image, pSubresource, pLayout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    VkImageSubresource2KHR* local_pSubresource;
    local_device = device;
    local_image = image;
    local_pSubresource = nullptr;
    if (pSubresource) {
        local_pSubresource =
            (VkImageSubresource2KHR*)pool->alloc(sizeof(const VkImageSubresource2KHR));
        deepcopy_VkImageSubresource2KHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubresource,
                                        (VkImageSubresource2KHR*)(local_pSubresource));
    }
    if (local_pSubresource) {
        transform_tohost_VkImageSubresource2KHR(sResourceTracker,
                                                (VkImageSubresource2KHR*)(local_pSubresource));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkImageSubresource2KHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkImageSubresource2KHR*)(local_pSubresource), countPtr);
        count_VkSubresourceLayout2KHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubresourceLayout2KHR*)(pLayout), countPtr);
    }
    uint32_t packetSize_vkGetImageSubresourceLayout2KHR =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageSubresourceLayout2KHR);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageSubresourceLayout2KHR);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageSubresourceLayout2KHR = OP_vkGetImageSubresourceLayout2KHR;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageSubresourceLayout2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageSubresourceLayout2KHR, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageSubresource2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkImageSubresource2KHR*)(local_pSubresource),
                                           streamPtrPtr);
    reservedmarshal_VkSubresourceLayout2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkSubresourceLayout2KHR*)(pLayout), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetImageSubresourceLayout2KHR), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkSubresourceLayout2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubresourceLayout2KHR*)(pLayout));
    if (pLayout) {
        transform_fromhost_VkSubresourceLayout2KHR(sResourceTracker,
                                                   (VkSubresourceLayout2KHR*)(pLayout));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_ANDROID_native_buffer
VkResult VkEncoder::vkGetSwapchainGrallocUsageANDROID(VkDevice device, VkFormat format,
                                                      VkImageUsageFlags imageUsage,
                                                      int* grallocUsage, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetSwapchainGrallocUsageANDROID in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetSwapchainGrallocUsageANDROID(device:%p, format:%d, imageUsage:%d, grallocUsage:%p)",
        device, format, imageUsage, grallocUsage);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFormat local_format;
    VkImageUsageFlags local_imageUsage;
    local_device = device;
    local_format = format;
    local_imageUsage = imageUsage;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        *countPtr += sizeof(VkImageUsageFlags);
        *countPtr += sizeof(int);
    }
    uint32_t packetSize_vkGetSwapchainGrallocUsageANDROID =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetSwapchainGrallocUsageANDROID);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetSwapchainGrallocUsageANDROID);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetSwapchainGrallocUsageANDROID = OP_vkGetSwapchainGrallocUsageANDROID;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetSwapchainGrallocUsageANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetSwapchainGrallocUsageANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    memcpy(*streamPtrPtr, (VkImageUsageFlags*)&local_imageUsage, sizeof(VkImageUsageFlags));
    *streamPtrPtr += sizeof(VkImageUsageFlags);
    memcpy(*streamPtrPtr, (int*)grallocUsage, sizeof(int));
    *streamPtrPtr += sizeof(int);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetSwapchainGrallocUsageANDROID), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((int*)grallocUsage, sizeof(int));
    VkResult vkGetSwapchainGrallocUsageANDROID_VkResult_return = (VkResult)0;
    stream->read(&vkGetSwapchainGrallocUsageANDROID_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetSwapchainGrallocUsageANDROID_VkResult_return;
}

VkResult VkEncoder::vkAcquireImageANDROID(VkDevice device, VkImage image, int nativeFenceFd,
                                          VkSemaphore semaphore, VkFence fence, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkAcquireImageANDROID in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    int local_nativeFenceFd;
    VkSemaphore local_semaphore;
    VkFence local_fence;
    local_device = device;
    local_image = image;
    local_nativeFenceFd = nativeFenceFd;
    local_semaphore = semaphore;
    local_fence = fence;
    sResourceTracker->unwrap_vkAcquireImageANDROID_nativeFenceFd(nativeFenceFd,
                                                                 &local_nativeFenceFd);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(int);
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        uint64_t cgen_var_3;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkAcquireImageANDROID =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkAcquireImageANDROID);
    uint8_t* streamPtr = stream->reserve(packetSize_vkAcquireImageANDROID);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkAcquireImageANDROID = OP_vkAcquireImageANDROID;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkAcquireImageANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkAcquireImageANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (int*)&local_nativeFenceFd, sizeof(int));
    *streamPtrPtr += sizeof(int);
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkSemaphore((*&local_semaphore));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_3;
    *&cgen_var_3 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_3, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkAcquireImageANDROID), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkAcquireImageANDROID_VkResult_return = (VkResult)0;
    stream->read(&vkAcquireImageANDROID_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkAcquireImageANDROID_VkResult_return;
}

VkResult VkEncoder::vkQueueSignalReleaseImageANDROID(VkQueue queue, uint32_t waitSemaphoreCount,
                                                     const VkSemaphore* pWaitSemaphores,
                                                     VkImage image, int* pNativeFenceFd,
                                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueSignalReleaseImageANDROID in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkQueueSignalReleaseImageANDROID(queue:%p, waitSemaphoreCount:%d, pWaitSemaphores:%p, "
        "image:%p, pNativeFenceFd:%p)",
        queue, waitSemaphoreCount, pWaitSemaphores, image, pNativeFenceFd);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_waitSemaphoreCount;
    VkSemaphore* local_pWaitSemaphores;
    VkImage local_image;
    local_queue = queue;
    local_waitSemaphoreCount = waitSemaphoreCount;
    // Avoiding deepcopy for pWaitSemaphores
    local_pWaitSemaphores = (VkSemaphore*)pWaitSemaphores;
    local_image = image;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pWaitSemaphores) {
            if (((waitSemaphoreCount))) {
                *countPtr += ((waitSemaphoreCount)) * 8;
            }
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(int);
    }
    uint32_t packetSize_vkQueueSignalReleaseImageANDROID =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkQueueSignalReleaseImageANDROID);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueSignalReleaseImageANDROID);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueSignalReleaseImageANDROID = OP_vkQueueSignalReleaseImageANDROID;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueSignalReleaseImageANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueSignalReleaseImageANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_waitSemaphoreCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pWaitSemaphores;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pWaitSemaphores) {
        if (((waitSemaphoreCount))) {
            uint8_t* cgen_var_1_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((waitSemaphoreCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkSemaphore(local_pWaitSemaphores[k]);
                memcpy(cgen_var_1_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((waitSemaphoreCount));
        }
    }
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (int*)pNativeFenceFd, sizeof(int));
    *streamPtrPtr += sizeof(int);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueSignalReleaseImageANDROID), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((int*)pNativeFenceFd, sizeof(int));
    VkResult vkQueueSignalReleaseImageANDROID_VkResult_return = (VkResult)0;
    stream->read(&vkQueueSignalReleaseImageANDROID_VkResult_return, sizeof(VkResult));
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkQueueSignalReleaseImageANDROID_VkResult_return;
}

VkResult VkEncoder::vkGetSwapchainGrallocUsage2ANDROID(
    VkDevice device, VkFormat format, VkImageUsageFlags imageUsage,
    VkSwapchainImageUsageFlagsANDROID swapchainImageUsage, uint64_t* grallocConsumerUsage,
    uint64_t* grallocProducerUsage, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetSwapchainGrallocUsage2ANDROID in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetSwapchainGrallocUsage2ANDROID(device:%p, format:%d, imageUsage:%d, "
        "grallocConsumerUsage:%p, grallocProducerUsage:%p)",
        device, format, imageUsage, grallocConsumerUsage, grallocProducerUsage);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFormat local_format;
    VkImageUsageFlags local_imageUsage;
    VkSwapchainImageUsageFlagsANDROID local_swapchainImageUsage;
    local_device = device;
    local_format = format;
    local_imageUsage = imageUsage;
    local_swapchainImageUsage = swapchainImageUsage;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        *countPtr += sizeof(VkImageUsageFlags);
        *countPtr += sizeof(VkSwapchainImageUsageFlagsANDROID);
        *countPtr += sizeof(uint64_t);
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkGetSwapchainGrallocUsage2ANDROID =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetSwapchainGrallocUsage2ANDROID);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetSwapchainGrallocUsage2ANDROID);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetSwapchainGrallocUsage2ANDROID = OP_vkGetSwapchainGrallocUsage2ANDROID;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetSwapchainGrallocUsage2ANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetSwapchainGrallocUsage2ANDROID, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    memcpy(*streamPtrPtr, (VkImageUsageFlags*)&local_imageUsage, sizeof(VkImageUsageFlags));
    *streamPtrPtr += sizeof(VkImageUsageFlags);
    memcpy(*streamPtrPtr, (VkSwapchainImageUsageFlagsANDROID*)&local_swapchainImageUsage,
           sizeof(VkSwapchainImageUsageFlagsANDROID));
    *streamPtrPtr += sizeof(VkSwapchainImageUsageFlagsANDROID);
    memcpy(*streamPtrPtr, (uint64_t*)grallocConsumerUsage, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    memcpy(*streamPtrPtr, (uint64_t*)grallocProducerUsage, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetSwapchainGrallocUsage2ANDROID), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((uint64_t*)grallocConsumerUsage, sizeof(uint64_t));
    stream->read((uint64_t*)grallocProducerUsage, sizeof(uint64_t));
    VkResult vkGetSwapchainGrallocUsage2ANDROID_VkResult_return = (VkResult)0;
    stream->read(&vkGetSwapchainGrallocUsage2ANDROID_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetSwapchainGrallocUsage2ANDROID_VkResult_return;
}

#endif
#ifdef VK_EXT_transform_feedback
void VkEncoder::vkCmdBindTransformFeedbackBuffersEXT(VkCommandBuffer commandBuffer,
                                                     uint32_t firstBinding, uint32_t bindingCount,
                                                     const VkBuffer* pBuffers,
                                                     const VkDeviceSize* pOffsets,
                                                     const VkDeviceSize* pSizes, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindTransformFeedbackBuffersEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBindTransformFeedbackBuffersEXT(commandBuffer:%p, firstBinding:%d, bindingCount:%d, "
        "pBuffers:%p, pOffsets:%p, pSizes:%p)",
        commandBuffer, firstBinding, bindingCount, pBuffers, pOffsets, pSizes);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstBinding;
    uint32_t local_bindingCount;
    VkBuffer* local_pBuffers;
    VkDeviceSize* local_pOffsets;
    VkDeviceSize* local_pSizes;
    local_commandBuffer = commandBuffer;
    local_firstBinding = firstBinding;
    local_bindingCount = bindingCount;
    // Avoiding deepcopy for pBuffers
    local_pBuffers = (VkBuffer*)pBuffers;
    // Avoiding deepcopy for pOffsets
    local_pOffsets = (VkDeviceSize*)pOffsets;
    // Avoiding deepcopy for pSizes
    local_pSizes = (VkDeviceSize*)pSizes;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        if (((bindingCount))) {
            *countPtr += ((bindingCount)) * 8;
        }
        *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pSizes) {
            *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        }
    }
    uint32_t packetSize_vkCmdBindTransformFeedbackBuffersEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdBindTransformFeedbackBuffersEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindTransformFeedbackBuffersEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindTransformFeedbackBuffersEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindTransformFeedbackBuffersEXT = OP_vkCmdBindTransformFeedbackBuffersEXT;
    memcpy(streamPtr, &opcode_vkCmdBindTransformFeedbackBuffersEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindTransformFeedbackBuffersEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstBinding, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindingCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((bindingCount))) {
        uint8_t* cgen_var_0_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((bindingCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkBuffer(local_pBuffers[k]);
            memcpy(cgen_var_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((bindingCount));
    }
    memcpy(*streamPtrPtr, (VkDeviceSize*)local_pOffsets, ((bindingCount)) * sizeof(VkDeviceSize));
    *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pSizes;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pSizes) {
        memcpy(*streamPtrPtr, (VkDeviceSize*)local_pSizes, ((bindingCount)) * sizeof(VkDeviceSize));
        *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCmdBindTransformFeedbackBuffersEXT),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBeginTransformFeedbackEXT(
    VkCommandBuffer commandBuffer, uint32_t firstCounterBuffer, uint32_t counterBufferCount,
    const VkBuffer* pCounterBuffers, const VkDeviceSize* pCounterBufferOffsets, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginTransformFeedbackEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBeginTransformFeedbackEXT(commandBuffer:%p, firstCounterBuffer:%d, "
        "counterBufferCount:%d, pCounterBuffers:%p, pCounterBufferOffsets:%p)",
        commandBuffer, firstCounterBuffer, counterBufferCount, pCounterBuffers,
        pCounterBufferOffsets);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstCounterBuffer;
    uint32_t local_counterBufferCount;
    VkBuffer* local_pCounterBuffers;
    VkDeviceSize* local_pCounterBufferOffsets;
    local_commandBuffer = commandBuffer;
    local_firstCounterBuffer = firstCounterBuffer;
    local_counterBufferCount = counterBufferCount;
    // Avoiding deepcopy for pCounterBuffers
    local_pCounterBuffers = (VkBuffer*)pCounterBuffers;
    // Avoiding deepcopy for pCounterBufferOffsets
    local_pCounterBufferOffsets = (VkDeviceSize*)pCounterBufferOffsets;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pCounterBuffers) {
            if (((counterBufferCount))) {
                *countPtr += ((counterBufferCount)) * 8;
            }
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pCounterBufferOffsets) {
            *countPtr += ((counterBufferCount)) * sizeof(VkDeviceSize);
        }
    }
    uint32_t packetSize_vkCmdBeginTransformFeedbackEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdBeginTransformFeedbackEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginTransformFeedbackEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginTransformFeedbackEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginTransformFeedbackEXT = OP_vkCmdBeginTransformFeedbackEXT;
    memcpy(streamPtr, &opcode_vkCmdBeginTransformFeedbackEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginTransformFeedbackEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstCounterBuffer, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_counterBufferCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_0 = (uint64_t)(uintptr_t)local_pCounterBuffers;
    memcpy((*streamPtrPtr), &cgen_var_0, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pCounterBuffers) {
        if (((counterBufferCount))) {
            uint8_t* cgen_var_0_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((counterBufferCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkBuffer(local_pCounterBuffers[k]);
                memcpy(cgen_var_0_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((counterBufferCount));
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pCounterBufferOffsets;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pCounterBufferOffsets) {
        memcpy(*streamPtrPtr, (VkDeviceSize*)local_pCounterBufferOffsets,
               ((counterBufferCount)) * sizeof(VkDeviceSize));
        *streamPtrPtr += ((counterBufferCount)) * sizeof(VkDeviceSize);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBeginTransformFeedbackEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndTransformFeedbackEXT(
    VkCommandBuffer commandBuffer, uint32_t firstCounterBuffer, uint32_t counterBufferCount,
    const VkBuffer* pCounterBuffers, const VkDeviceSize* pCounterBufferOffsets, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndTransformFeedbackEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdEndTransformFeedbackEXT(commandBuffer:%p, firstCounterBuffer:%d, "
        "counterBufferCount:%d, pCounterBuffers:%p, pCounterBufferOffsets:%p)",
        commandBuffer, firstCounterBuffer, counterBufferCount, pCounterBuffers,
        pCounterBufferOffsets);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstCounterBuffer;
    uint32_t local_counterBufferCount;
    VkBuffer* local_pCounterBuffers;
    VkDeviceSize* local_pCounterBufferOffsets;
    local_commandBuffer = commandBuffer;
    local_firstCounterBuffer = firstCounterBuffer;
    local_counterBufferCount = counterBufferCount;
    // Avoiding deepcopy for pCounterBuffers
    local_pCounterBuffers = (VkBuffer*)pCounterBuffers;
    // Avoiding deepcopy for pCounterBufferOffsets
    local_pCounterBufferOffsets = (VkDeviceSize*)pCounterBufferOffsets;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pCounterBuffers) {
            if (((counterBufferCount))) {
                *countPtr += ((counterBufferCount)) * 8;
            }
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pCounterBufferOffsets) {
            *countPtr += ((counterBufferCount)) * sizeof(VkDeviceSize);
        }
    }
    uint32_t packetSize_vkCmdEndTransformFeedbackEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdEndTransformFeedbackEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndTransformFeedbackEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndTransformFeedbackEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndTransformFeedbackEXT = OP_vkCmdEndTransformFeedbackEXT;
    memcpy(streamPtr, &opcode_vkCmdEndTransformFeedbackEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndTransformFeedbackEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstCounterBuffer, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_counterBufferCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_0 = (uint64_t)(uintptr_t)local_pCounterBuffers;
    memcpy((*streamPtrPtr), &cgen_var_0, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pCounterBuffers) {
        if (((counterBufferCount))) {
            uint8_t* cgen_var_0_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((counterBufferCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkBuffer(local_pCounterBuffers[k]);
                memcpy(cgen_var_0_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((counterBufferCount));
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pCounterBufferOffsets;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pCounterBufferOffsets) {
        memcpy(*streamPtrPtr, (VkDeviceSize*)local_pCounterBufferOffsets,
               ((counterBufferCount)) * sizeof(VkDeviceSize));
        *streamPtrPtr += ((counterBufferCount)) * sizeof(VkDeviceSize);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdEndTransformFeedbackEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBeginQueryIndexedEXT(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
                                          uint32_t query, VkQueryControlFlags flags, uint32_t index,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBeginQueryIndexedEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBeginQueryIndexedEXT(commandBuffer:%p, queryPool:%p, query:%d, flags:%d, index:%d)",
        commandBuffer, queryPool, query, flags, index);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkQueryPool local_queryPool;
    uint32_t local_query;
    VkQueryControlFlags local_flags;
    uint32_t local_index;
    local_commandBuffer = commandBuffer;
    local_queryPool = queryPool;
    local_query = query;
    local_flags = flags;
    local_index = index;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(VkQueryControlFlags);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdBeginQueryIndexedEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBeginQueryIndexedEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBeginQueryIndexedEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBeginQueryIndexedEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBeginQueryIndexedEXT = OP_vkCmdBeginQueryIndexedEXT;
    memcpy(streamPtr, &opcode_vkCmdBeginQueryIndexedEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBeginQueryIndexedEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_query, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (VkQueryControlFlags*)&local_flags, sizeof(VkQueryControlFlags));
    *streamPtrPtr += sizeof(VkQueryControlFlags);
    memcpy(*streamPtrPtr, (uint32_t*)&local_index, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBeginQueryIndexedEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdEndQueryIndexedEXT(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
                                        uint32_t query, uint32_t index, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdEndQueryIndexedEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdEndQueryIndexedEXT(commandBuffer:%p, queryPool:%p, query:%d, index:%d)",
                      commandBuffer, queryPool, query, index);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkQueryPool local_queryPool;
    uint32_t local_query;
    uint32_t local_index;
    local_commandBuffer = commandBuffer;
    local_queryPool = queryPool;
    local_query = query;
    local_index = index;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdEndQueryIndexedEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdEndQueryIndexedEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdEndQueryIndexedEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdEndQueryIndexedEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdEndQueryIndexedEXT = OP_vkCmdEndQueryIndexedEXT;
    memcpy(streamPtr, &opcode_vkCmdEndQueryIndexedEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdEndQueryIndexedEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueryPool((*&local_queryPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_query, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_index, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdEndQueryIndexedEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdDrawIndirectByteCountEXT(VkCommandBuffer commandBuffer, uint32_t instanceCount,
                                              uint32_t firstInstance, VkBuffer counterBuffer,
                                              VkDeviceSize counterBufferOffset,
                                              uint32_t counterOffset, uint32_t vertexStride,
                                              uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdDrawIndirectByteCountEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdDrawIndirectByteCountEXT(commandBuffer:%p, instanceCount:%d, firstInstance:%d, "
        "counterBuffer:%p, counterBufferOffset:%ld, counterOffset:%d, vertexStride:%d)",
        commandBuffer, instanceCount, firstInstance, counterBuffer, counterBufferOffset,
        counterOffset, vertexStride);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_instanceCount;
    uint32_t local_firstInstance;
    VkBuffer local_counterBuffer;
    VkDeviceSize local_counterBufferOffset;
    uint32_t local_counterOffset;
    uint32_t local_vertexStride;
    local_commandBuffer = commandBuffer;
    local_instanceCount = instanceCount;
    local_firstInstance = firstInstance;
    local_counterBuffer = counterBuffer;
    local_counterBufferOffset = counterBufferOffset;
    local_counterOffset = counterOffset;
    local_vertexStride = vertexStride;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdDrawIndirectByteCountEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdDrawIndirectByteCountEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdDrawIndirectByteCountEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdDrawIndirectByteCountEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdDrawIndirectByteCountEXT = OP_vkCmdDrawIndirectByteCountEXT;
    memcpy(streamPtr, &opcode_vkCmdDrawIndirectByteCountEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdDrawIndirectByteCountEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_instanceCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstInstance, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkBuffer((*&local_counterBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_counterBufferOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (uint32_t*)&local_counterOffset, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_vertexStride, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdDrawIndirectByteCountEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_EXT_tooling_info
VkResult VkEncoder::vkGetPhysicalDeviceToolPropertiesEXT(
    VkPhysicalDevice physicalDevice, uint32_t* pToolCount,
    VkPhysicalDeviceToolProperties* pToolProperties, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPhysicalDeviceToolPropertiesEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetPhysicalDeviceToolPropertiesEXT(physicalDevice:%p, pToolCount:%p, "
        "pToolProperties:%p)",
        physicalDevice, pToolCount, pToolProperties);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkPhysicalDevice local_physicalDevice;
    local_physicalDevice = physicalDevice;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pToolCount) {
            *countPtr += sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pToolProperties) {
            if (pToolCount) {
                for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
                    count_VkPhysicalDeviceToolProperties(
                        sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                        (VkPhysicalDeviceToolProperties*)(pToolProperties + i), countPtr);
                }
            }
        }
    }
    uint32_t packetSize_vkGetPhysicalDeviceToolPropertiesEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetPhysicalDeviceToolPropertiesEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPhysicalDeviceToolPropertiesEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPhysicalDeviceToolPropertiesEXT = OP_vkGetPhysicalDeviceToolPropertiesEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPhysicalDeviceToolPropertiesEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPhysicalDeviceToolPropertiesEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkPhysicalDevice((*&local_physicalDevice));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)pToolCount;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pToolCount) {
        memcpy(*streamPtrPtr, (uint32_t*)pToolCount, sizeof(uint32_t));
        *streamPtrPtr += sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pToolProperties;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pToolProperties) {
        for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
            reservedmarshal_VkPhysicalDeviceToolProperties(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkPhysicalDeviceToolProperties*)(pToolProperties + i), streamPtrPtr);
        }
    }
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetPhysicalDeviceToolPropertiesEXT),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint32_t* check_pToolCount;
    check_pToolCount = (uint32_t*)(uintptr_t)stream->getBe64();
    if (pToolCount) {
        if (!(check_pToolCount)) {
            fprintf(stderr, "fatal: pToolCount inconsistent between guest and host\n");
        }
        stream->read((uint32_t*)pToolCount, sizeof(uint32_t));
    }
    // WARNING PTR CHECK
    VkPhysicalDeviceToolProperties* check_pToolProperties;
    check_pToolProperties = (VkPhysicalDeviceToolProperties*)(uintptr_t)stream->getBe64();
    if (pToolProperties) {
        if (!(check_pToolProperties)) {
            fprintf(stderr, "fatal: pToolProperties inconsistent between guest and host\n");
        }
        if (pToolCount) {
            for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
                unmarshal_VkPhysicalDeviceToolProperties(
                    stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                    (VkPhysicalDeviceToolProperties*)(pToolProperties + i));
            }
        }
    }
    if (pToolCount) {
        if (pToolProperties) {
            for (uint32_t i = 0; i < (uint32_t)(*(pToolCount)); ++i) {
                transform_fromhost_VkPhysicalDeviceToolProperties(
                    sResourceTracker, (VkPhysicalDeviceToolProperties*)(pToolProperties + i));
            }
        }
    }
    VkResult vkGetPhysicalDeviceToolPropertiesEXT_VkResult_return = (VkResult)0;
    stream->read(&vkGetPhysicalDeviceToolPropertiesEXT_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetPhysicalDeviceToolPropertiesEXT_VkResult_return;
}

#endif
#ifdef VK_EXT_line_rasterization
void VkEncoder::vkCmdSetLineStippleEXT(VkCommandBuffer commandBuffer, uint32_t lineStippleFactor,
                                       uint16_t lineStipplePattern, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetLineStippleEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetLineStippleEXT(commandBuffer:%p, lineStippleFactor:%d, lineStipplePattern:%d)",
        commandBuffer, lineStippleFactor, lineStipplePattern);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_lineStippleFactor;
    uint16_t local_lineStipplePattern;
    local_commandBuffer = commandBuffer;
    local_lineStippleFactor = lineStippleFactor;
    local_lineStipplePattern = lineStipplePattern;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint16_t);
    }
    uint32_t packetSize_vkCmdSetLineStippleEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetLineStippleEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetLineStippleEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetLineStippleEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetLineStippleEXT = OP_vkCmdSetLineStippleEXT;
    memcpy(streamPtr, &opcode_vkCmdSetLineStippleEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetLineStippleEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_lineStippleFactor, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint16_t*)&local_lineStipplePattern, sizeof(uint16_t));
    *streamPtrPtr += sizeof(uint16_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetLineStippleEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_EXT_extended_dynamic_state
void VkEncoder::vkCmdSetCullModeEXT(VkCommandBuffer commandBuffer, VkCullModeFlags cullMode,
                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetCullModeEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetCullModeEXT(commandBuffer:%p, cullMode:%d)", commandBuffer,
                      cullMode);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCullModeFlags local_cullMode;
    local_commandBuffer = commandBuffer;
    local_cullMode = cullMode;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCullModeFlags);
    }
    uint32_t packetSize_vkCmdSetCullModeEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetCullModeEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetCullModeEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetCullModeEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetCullModeEXT = OP_vkCmdSetCullModeEXT;
    memcpy(streamPtr, &opcode_vkCmdSetCullModeEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetCullModeEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkCullModeFlags*)&local_cullMode, sizeof(VkCullModeFlags));
    *streamPtrPtr += sizeof(VkCullModeFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetCullModeEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetFrontFaceEXT(VkCommandBuffer commandBuffer, VkFrontFace frontFace,
                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetFrontFaceEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetFrontFaceEXT(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkFrontFace local_frontFace;
    local_commandBuffer = commandBuffer;
    local_frontFace = frontFace;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFrontFace);
    }
    uint32_t packetSize_vkCmdSetFrontFaceEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetFrontFaceEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetFrontFaceEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetFrontFaceEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetFrontFaceEXT = OP_vkCmdSetFrontFaceEXT;
    memcpy(streamPtr, &opcode_vkCmdSetFrontFaceEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetFrontFaceEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkFrontFace*)&local_frontFace, sizeof(VkFrontFace));
    *streamPtrPtr += sizeof(VkFrontFace);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetFrontFaceEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetPrimitiveTopologyEXT(VkCommandBuffer commandBuffer,
                                             VkPrimitiveTopology primitiveTopology,
                                             uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetPrimitiveTopologyEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetPrimitiveTopologyEXT(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkPrimitiveTopology local_primitiveTopology;
    local_commandBuffer = commandBuffer;
    local_primitiveTopology = primitiveTopology;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkPrimitiveTopology);
    }
    uint32_t packetSize_vkCmdSetPrimitiveTopologyEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetPrimitiveTopologyEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetPrimitiveTopologyEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetPrimitiveTopologyEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetPrimitiveTopologyEXT = OP_vkCmdSetPrimitiveTopologyEXT;
    memcpy(streamPtr, &opcode_vkCmdSetPrimitiveTopologyEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetPrimitiveTopologyEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkPrimitiveTopology*)&local_primitiveTopology,
           sizeof(VkPrimitiveTopology));
    *streamPtrPtr += sizeof(VkPrimitiveTopology);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetPrimitiveTopologyEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetViewportWithCountEXT(VkCommandBuffer commandBuffer, uint32_t viewportCount,
                                             const VkViewport* pViewports, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetViewportWithCountEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetViewportWithCountEXT(commandBuffer:%p, viewportCount:%d, pViewports:%p)",
        commandBuffer, viewportCount, pViewports);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_viewportCount;
    VkViewport* local_pViewports;
    local_commandBuffer = commandBuffer;
    local_viewportCount = viewportCount;
    local_pViewports = nullptr;
    if (pViewports) {
        local_pViewports = (VkViewport*)pool->alloc(((viewportCount)) * sizeof(const VkViewport));
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            deepcopy_VkViewport(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pViewports + i,
                                (VkViewport*)(local_pViewports + i));
        }
    }
    if (local_pViewports) {
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            transform_tohost_VkViewport(sResourceTracker, (VkViewport*)(local_pViewports + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
            count_VkViewport(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                             (VkViewport*)(local_pViewports + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdSetViewportWithCountEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetViewportWithCountEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetViewportWithCountEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetViewportWithCountEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetViewportWithCountEXT = OP_vkCmdSetViewportWithCountEXT;
    memcpy(streamPtr, &opcode_vkCmdSetViewportWithCountEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetViewportWithCountEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_viewportCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((viewportCount)); ++i) {
        reservedmarshal_VkViewport(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkViewport*)(local_pViewports + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetViewportWithCountEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetScissorWithCountEXT(VkCommandBuffer commandBuffer, uint32_t scissorCount,
                                            const VkRect2D* pScissors, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetScissorWithCountEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetScissorWithCountEXT(commandBuffer:%p, scissorCount:%d, pScissors:%p)",
        commandBuffer, scissorCount, pScissors);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_scissorCount;
    VkRect2D* local_pScissors;
    local_commandBuffer = commandBuffer;
    local_scissorCount = scissorCount;
    local_pScissors = nullptr;
    if (pScissors) {
        local_pScissors = (VkRect2D*)pool->alloc(((scissorCount)) * sizeof(const VkRect2D));
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            deepcopy_VkRect2D(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pScissors + i,
                              (VkRect2D*)(local_pScissors + i));
        }
    }
    if (local_pScissors) {
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            transform_tohost_VkRect2D(sResourceTracker, (VkRect2D*)(local_pScissors + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
            count_VkRect2D(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                           (VkRect2D*)(local_pScissors + i), countPtr);
        }
    }
    uint32_t packetSize_vkCmdSetScissorWithCountEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetScissorWithCountEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetScissorWithCountEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetScissorWithCountEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetScissorWithCountEXT = OP_vkCmdSetScissorWithCountEXT;
    memcpy(streamPtr, &opcode_vkCmdSetScissorWithCountEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetScissorWithCountEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_scissorCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((scissorCount)); ++i) {
        reservedmarshal_VkRect2D(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkRect2D*)(local_pScissors + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetScissorWithCountEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdBindVertexBuffers2EXT(VkCommandBuffer commandBuffer, uint32_t firstBinding,
                                           uint32_t bindingCount, const VkBuffer* pBuffers,
                                           const VkDeviceSize* pOffsets, const VkDeviceSize* pSizes,
                                           const VkDeviceSize* pStrides, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdBindVertexBuffers2EXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdBindVertexBuffers2EXT(commandBuffer:%p, firstBinding:%d, bindingCount:%d, "
        "pBuffers:%p, pOffsets:%p, pSizes:%p, pStrides:%p)",
        commandBuffer, firstBinding, bindingCount, pBuffers, pOffsets, pSizes, pStrides);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_firstBinding;
    uint32_t local_bindingCount;
    VkBuffer* local_pBuffers;
    VkDeviceSize* local_pOffsets;
    VkDeviceSize* local_pSizes;
    VkDeviceSize* local_pStrides;
    local_commandBuffer = commandBuffer;
    local_firstBinding = firstBinding;
    local_bindingCount = bindingCount;
    // Avoiding deepcopy for pBuffers
    local_pBuffers = (VkBuffer*)pBuffers;
    // Avoiding deepcopy for pOffsets
    local_pOffsets = (VkDeviceSize*)pOffsets;
    // Avoiding deepcopy for pSizes
    local_pSizes = (VkDeviceSize*)pSizes;
    // Avoiding deepcopy for pStrides
    local_pStrides = (VkDeviceSize*)pStrides;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBuffers) {
            if (((bindingCount))) {
                *countPtr += ((bindingCount)) * 8;
            }
        }
        *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pSizes) {
            *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pStrides) {
            *countPtr += ((bindingCount)) * sizeof(VkDeviceSize);
        }
    }
    uint32_t packetSize_vkCmdBindVertexBuffers2EXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdBindVertexBuffers2EXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdBindVertexBuffers2EXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdBindVertexBuffers2EXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdBindVertexBuffers2EXT = OP_vkCmdBindVertexBuffers2EXT;
    memcpy(streamPtr, &opcode_vkCmdBindVertexBuffers2EXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdBindVertexBuffers2EXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_firstBinding, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindingCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_0 = (uint64_t)(uintptr_t)local_pBuffers;
    memcpy((*streamPtrPtr), &cgen_var_0, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBuffers) {
        if (((bindingCount))) {
            uint8_t* cgen_var_0_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((bindingCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkBuffer(local_pBuffers[k]);
                memcpy(cgen_var_0_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((bindingCount));
        }
    }
    memcpy(*streamPtrPtr, (VkDeviceSize*)local_pOffsets, ((bindingCount)) * sizeof(VkDeviceSize));
    *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pSizes;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pSizes) {
        memcpy(*streamPtrPtr, (VkDeviceSize*)local_pSizes, ((bindingCount)) * sizeof(VkDeviceSize));
        *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pStrides;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pStrides) {
        memcpy(*streamPtrPtr, (VkDeviceSize*)local_pStrides,
               ((bindingCount)) * sizeof(VkDeviceSize));
        *streamPtrPtr += ((bindingCount)) * sizeof(VkDeviceSize);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdBindVertexBuffers2EXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthTestEnableEXT(VkCommandBuffer commandBuffer, VkBool32 depthTestEnable,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthTestEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthTestEnableEXT(commandBuffer:%p, depthTestEnable:%d)",
                      commandBuffer, depthTestEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthTestEnable;
    local_commandBuffer = commandBuffer;
    local_depthTestEnable = depthTestEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthTestEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthTestEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthTestEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthTestEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthTestEnableEXT = OP_vkCmdSetDepthTestEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetDepthTestEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthTestEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthTestEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthTestEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthWriteEnableEXT(VkCommandBuffer commandBuffer,
                                            VkBool32 depthWriteEnable, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthWriteEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthWriteEnableEXT(commandBuffer:%p, depthWriteEnable:%d)",
                      commandBuffer, depthWriteEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthWriteEnable;
    local_commandBuffer = commandBuffer;
    local_depthWriteEnable = depthWriteEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthWriteEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthWriteEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthWriteEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthWriteEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthWriteEnableEXT = OP_vkCmdSetDepthWriteEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetDepthWriteEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthWriteEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthWriteEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthWriteEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthCompareOpEXT(VkCommandBuffer commandBuffer, VkCompareOp depthCompareOp,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthCompareOpEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthCompareOpEXT(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCompareOp local_depthCompareOp;
    local_commandBuffer = commandBuffer;
    local_depthCompareOp = depthCompareOp;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCompareOp);
    }
    uint32_t packetSize_vkCmdSetDepthCompareOpEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthCompareOpEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthCompareOpEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthCompareOpEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthCompareOpEXT = OP_vkCmdSetDepthCompareOpEXT;
    memcpy(streamPtr, &opcode_vkCmdSetDepthCompareOpEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthCompareOpEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkCompareOp*)&local_depthCompareOp, sizeof(VkCompareOp));
    *streamPtrPtr += sizeof(VkCompareOp);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthCompareOpEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthBoundsTestEnableEXT(VkCommandBuffer commandBuffer,
                                                 VkBool32 depthBoundsTestEnable, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthBoundsTestEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetDepthBoundsTestEnableEXT(commandBuffer:%p, depthBoundsTestEnable:%d)",
        commandBuffer, depthBoundsTestEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthBoundsTestEnable;
    local_commandBuffer = commandBuffer;
    local_depthBoundsTestEnable = depthBoundsTestEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthBoundsTestEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetDepthBoundsTestEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthBoundsTestEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthBoundsTestEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthBoundsTestEnableEXT = OP_vkCmdSetDepthBoundsTestEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetDepthBoundsTestEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthBoundsTestEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthBoundsTestEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthBoundsTestEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetStencilTestEnableEXT(VkCommandBuffer commandBuffer,
                                             VkBool32 stencilTestEnable, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetStencilTestEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetStencilTestEnableEXT(commandBuffer:%p, stencilTestEnable:%d)",
                      commandBuffer, stencilTestEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_stencilTestEnable;
    local_commandBuffer = commandBuffer;
    local_stencilTestEnable = stencilTestEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetStencilTestEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetStencilTestEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetStencilTestEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetStencilTestEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetStencilTestEnableEXT = OP_vkCmdSetStencilTestEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetStencilTestEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetStencilTestEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_stencilTestEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetStencilTestEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetStencilOpEXT(VkCommandBuffer commandBuffer, VkStencilFaceFlags faceMask,
                                     VkStencilOp failOp, VkStencilOp passOp,
                                     VkStencilOp depthFailOp, VkCompareOp compareOp,
                                     uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetStencilOpEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetStencilOpEXT(commandBuffer:%p, faceMask:%d)", commandBuffer,
                      faceMask);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkStencilFaceFlags local_faceMask;
    VkStencilOp local_failOp;
    VkStencilOp local_passOp;
    VkStencilOp local_depthFailOp;
    VkCompareOp local_compareOp;
    local_commandBuffer = commandBuffer;
    local_faceMask = faceMask;
    local_failOp = failOp;
    local_passOp = passOp;
    local_depthFailOp = depthFailOp;
    local_compareOp = compareOp;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkStencilFaceFlags);
        *countPtr += sizeof(VkStencilOp);
        *countPtr += sizeof(VkStencilOp);
        *countPtr += sizeof(VkStencilOp);
        *countPtr += sizeof(VkCompareOp);
    }
    uint32_t packetSize_vkCmdSetStencilOpEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetStencilOpEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetStencilOpEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetStencilOpEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetStencilOpEXT = OP_vkCmdSetStencilOpEXT;
    memcpy(streamPtr, &opcode_vkCmdSetStencilOpEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetStencilOpEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkStencilFaceFlags*)&local_faceMask, sizeof(VkStencilFaceFlags));
    *streamPtrPtr += sizeof(VkStencilFaceFlags);
    memcpy(*streamPtrPtr, (VkStencilOp*)&local_failOp, sizeof(VkStencilOp));
    *streamPtrPtr += sizeof(VkStencilOp);
    memcpy(*streamPtrPtr, (VkStencilOp*)&local_passOp, sizeof(VkStencilOp));
    *streamPtrPtr += sizeof(VkStencilOp);
    memcpy(*streamPtrPtr, (VkStencilOp*)&local_depthFailOp, sizeof(VkStencilOp));
    *streamPtrPtr += sizeof(VkStencilOp);
    memcpy(*streamPtrPtr, (VkCompareOp*)&local_compareOp, sizeof(VkCompareOp));
    *streamPtrPtr += sizeof(VkCompareOp);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetStencilOpEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_EXT_host_image_copy
VkResult VkEncoder::vkCopyMemoryToImageEXT(VkDevice device,
                                           const VkCopyMemoryToImageInfoEXT* pCopyMemoryToImageInfo,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCopyMemoryToImageEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCopyMemoryToImageEXT(device:%p, pCopyMemoryToImageInfo:%p)", device,
                      pCopyMemoryToImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCopyMemoryToImageInfoEXT* local_pCopyMemoryToImageInfo;
    local_device = device;
    local_pCopyMemoryToImageInfo = nullptr;
    if (pCopyMemoryToImageInfo) {
        local_pCopyMemoryToImageInfo =
            (VkCopyMemoryToImageInfoEXT*)pool->alloc(sizeof(const VkCopyMemoryToImageInfoEXT));
        deepcopy_VkCopyMemoryToImageInfoEXT(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyMemoryToImageInfo,
            (VkCopyMemoryToImageInfoEXT*)(local_pCopyMemoryToImageInfo));
    }
    if (local_pCopyMemoryToImageInfo) {
        transform_tohost_VkCopyMemoryToImageInfoEXT(
            sResourceTracker, (VkCopyMemoryToImageInfoEXT*)(local_pCopyMemoryToImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyMemoryToImageInfoEXT(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkCopyMemoryToImageInfoEXT*)(local_pCopyMemoryToImageInfo), countPtr);
    }
    uint32_t packetSize_vkCopyMemoryToImageEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCopyMemoryToImageEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCopyMemoryToImageEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCopyMemoryToImageEXT = OP_vkCopyMemoryToImageEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCopyMemoryToImageEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCopyMemoryToImageEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkCopyMemoryToImageInfoEXT(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkCopyMemoryToImageInfoEXT*)(local_pCopyMemoryToImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCopyMemoryToImageEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkCopyMemoryToImageEXT_VkResult_return = (VkResult)0;
    stream->read(&vkCopyMemoryToImageEXT_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCopyMemoryToImageEXT_VkResult_return;
}

VkResult VkEncoder::vkCopyImageToMemoryEXT(VkDevice device,
                                           const VkCopyImageToMemoryInfoEXT* pCopyImageToMemoryInfo,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCopyImageToMemoryEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCopyImageToMemoryEXT(device:%p, pCopyImageToMemoryInfo:%p)", device,
                      pCopyImageToMemoryInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCopyImageToMemoryInfoEXT* local_pCopyImageToMemoryInfo;
    local_device = device;
    local_pCopyImageToMemoryInfo = nullptr;
    if (pCopyImageToMemoryInfo) {
        local_pCopyImageToMemoryInfo =
            (VkCopyImageToMemoryInfoEXT*)pool->alloc(sizeof(const VkCopyImageToMemoryInfoEXT));
        deepcopy_VkCopyImageToMemoryInfoEXT(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyImageToMemoryInfo,
            (VkCopyImageToMemoryInfoEXT*)(local_pCopyImageToMemoryInfo));
    }
    if (local_pCopyImageToMemoryInfo) {
        transform_tohost_VkCopyImageToMemoryInfoEXT(
            sResourceTracker, (VkCopyImageToMemoryInfoEXT*)(local_pCopyImageToMemoryInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyImageToMemoryInfoEXT(
            sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkCopyImageToMemoryInfoEXT*)(local_pCopyImageToMemoryInfo), countPtr);
    }
    uint32_t packetSize_vkCopyImageToMemoryEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCopyImageToMemoryEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCopyImageToMemoryEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCopyImageToMemoryEXT = OP_vkCopyImageToMemoryEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCopyImageToMemoryEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCopyImageToMemoryEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkCopyImageToMemoryInfoEXT(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkCopyImageToMemoryInfoEXT*)(local_pCopyImageToMemoryInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCopyImageToMemoryEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkCopyImageToMemoryEXT_VkResult_return = (VkResult)0;
    stream->read(&vkCopyImageToMemoryEXT_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCopyImageToMemoryEXT_VkResult_return;
}

VkResult VkEncoder::vkCopyImageToImageEXT(VkDevice device,
                                          const VkCopyImageToImageInfoEXT* pCopyImageToImageInfo,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCopyImageToImageEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCopyImageToImageEXT(device:%p, pCopyImageToImageInfo:%p)", device,
                      pCopyImageToImageInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkCopyImageToImageInfoEXT* local_pCopyImageToImageInfo;
    local_device = device;
    local_pCopyImageToImageInfo = nullptr;
    if (pCopyImageToImageInfo) {
        local_pCopyImageToImageInfo =
            (VkCopyImageToImageInfoEXT*)pool->alloc(sizeof(const VkCopyImageToImageInfoEXT));
        deepcopy_VkCopyImageToImageInfoEXT(
            pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCopyImageToImageInfo,
            (VkCopyImageToImageInfoEXT*)(local_pCopyImageToImageInfo));
    }
    if (local_pCopyImageToImageInfo) {
        transform_tohost_VkCopyImageToImageInfoEXT(
            sResourceTracker, (VkCopyImageToImageInfoEXT*)(local_pCopyImageToImageInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCopyImageToImageInfoEXT(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkCopyImageToImageInfoEXT*)(local_pCopyImageToImageInfo),
                                        countPtr);
    }
    uint32_t packetSize_vkCopyImageToImageEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCopyImageToImageEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCopyImageToImageEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCopyImageToImageEXT = OP_vkCopyImageToImageEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCopyImageToImageEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCopyImageToImageEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkCopyImageToImageInfoEXT(
        stream, VK_STRUCTURE_TYPE_MAX_ENUM,
        (VkCopyImageToImageInfoEXT*)(local_pCopyImageToImageInfo), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCopyImageToImageEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkCopyImageToImageEXT_VkResult_return = (VkResult)0;
    stream->read(&vkCopyImageToImageEXT_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCopyImageToImageEXT_VkResult_return;
}

VkResult VkEncoder::vkTransitionImageLayoutEXT(
    VkDevice device, uint32_t transitionCount,
    const VkHostImageLayoutTransitionInfoEXT* pTransitions, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkTransitionImageLayoutEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkTransitionImageLayoutEXT(device:%p, transitionCount:%d, pTransitions:%p)",
                      device, transitionCount, pTransitions);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    uint32_t local_transitionCount;
    VkHostImageLayoutTransitionInfoEXT* local_pTransitions;
    local_device = device;
    local_transitionCount = transitionCount;
    local_pTransitions = nullptr;
    if (pTransitions) {
        local_pTransitions = (VkHostImageLayoutTransitionInfoEXT*)pool->alloc(
            ((transitionCount)) * sizeof(const VkHostImageLayoutTransitionInfoEXT));
        for (uint32_t i = 0; i < (uint32_t)((transitionCount)); ++i) {
            deepcopy_VkHostImageLayoutTransitionInfoEXT(
                pool, VK_STRUCTURE_TYPE_MAX_ENUM, pTransitions + i,
                (VkHostImageLayoutTransitionInfoEXT*)(local_pTransitions + i));
        }
    }
    if (local_pTransitions) {
        for (uint32_t i = 0; i < (uint32_t)((transitionCount)); ++i) {
            transform_tohost_VkHostImageLayoutTransitionInfoEXT(
                sResourceTracker, (VkHostImageLayoutTransitionInfoEXT*)(local_pTransitions + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((transitionCount)); ++i) {
            count_VkHostImageLayoutTransitionInfoEXT(
                sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkHostImageLayoutTransitionInfoEXT*)(local_pTransitions + i), countPtr);
        }
    }
    uint32_t packetSize_vkTransitionImageLayoutEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkTransitionImageLayoutEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkTransitionImageLayoutEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkTransitionImageLayoutEXT = OP_vkTransitionImageLayoutEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkTransitionImageLayoutEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkTransitionImageLayoutEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_transitionCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((transitionCount)); ++i) {
        reservedmarshal_VkHostImageLayoutTransitionInfoEXT(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkHostImageLayoutTransitionInfoEXT*)(local_pTransitions + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkTransitionImageLayoutEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkTransitionImageLayoutEXT_VkResult_return = (VkResult)0;
    stream->read(&vkTransitionImageLayoutEXT_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkTransitionImageLayoutEXT_VkResult_return;
}

void VkEncoder::vkGetImageSubresourceLayout2EXT(VkDevice device, VkImage image,
                                                const VkImageSubresource2KHR* pSubresource,
                                                VkSubresourceLayout2KHR* pLayout, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetImageSubresourceLayout2EXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetImageSubresourceLayout2EXT(device:%p, image:%p, pSubresource:%p, pLayout:%p)", device,
        image, pSubresource, pLayout);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImage local_image;
    VkImageSubresource2KHR* local_pSubresource;
    local_device = device;
    local_image = image;
    local_pSubresource = nullptr;
    if (pSubresource) {
        local_pSubresource =
            (VkImageSubresource2KHR*)pool->alloc(sizeof(const VkImageSubresource2KHR));
        deepcopy_VkImageSubresource2KHR(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubresource,
                                        (VkImageSubresource2KHR*)(local_pSubresource));
    }
    if (local_pSubresource) {
        transform_tohost_VkImageSubresource2KHR(sResourceTracker,
                                                (VkImageSubresource2KHR*)(local_pSubresource));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        count_VkImageSubresource2KHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkImageSubresource2KHR*)(local_pSubresource), countPtr);
        count_VkSubresourceLayout2KHR(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubresourceLayout2KHR*)(pLayout), countPtr);
    }
    uint32_t packetSize_vkGetImageSubresourceLayout2EXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetImageSubresourceLayout2EXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetImageSubresourceLayout2EXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetImageSubresourceLayout2EXT = OP_vkGetImageSubresourceLayout2EXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetImageSubresourceLayout2EXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetImageSubresourceLayout2EXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageSubresource2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                           (VkImageSubresource2KHR*)(local_pSubresource),
                                           streamPtrPtr);
    reservedmarshal_VkSubresourceLayout2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkSubresourceLayout2KHR*)(pLayout), streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetImageSubresourceLayout2EXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    unmarshal_VkSubresourceLayout2KHR(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubresourceLayout2KHR*)(pLayout));
    if (pLayout) {
        transform_fromhost_VkSubresourceLayout2KHR(sResourceTracker,
                                                   (VkSubresourceLayout2KHR*)(pLayout));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_EXT_private_data
VkResult VkEncoder::vkCreatePrivateDataSlotEXT(VkDevice device,
                                               const VkPrivateDataSlotCreateInfo* pCreateInfo,
                                               const VkAllocationCallbacks* pAllocator,
                                               VkPrivateDataSlot* pPrivateDataSlot,
                                               uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreatePrivateDataSlotEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreatePrivateDataSlotEXT(device:%p, pCreateInfo:%p, pAllocator:%p, pPrivateDataSlot:%p)",
        device, pCreateInfo, pAllocator, pPrivateDataSlot);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPrivateDataSlotCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo =
            (VkPrivateDataSlotCreateInfo*)pool->alloc(sizeof(const VkPrivateDataSlotCreateInfo));
        deepcopy_VkPrivateDataSlotCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                             (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkPrivateDataSlotCreateInfo(
            sResourceTracker, (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkPrivateDataSlotCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                          (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo),
                                          countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        *countPtr += 8;
    }
    uint32_t packetSize_vkCreatePrivateDataSlotEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCreatePrivateDataSlotEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreatePrivateDataSlotEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreatePrivateDataSlotEXT = OP_vkCreatePrivateDataSlotEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreatePrivateDataSlotEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreatePrivateDataSlotEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkPrivateDataSlotCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                (VkPrivateDataSlotCreateInfo*)(local_pCreateInfo),
                                                streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    uint64_t cgen_var_2 = (uint64_t)(*pPrivateDataSlot);
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCreatePrivateDataSlotEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    (*pPrivateDataSlot) = (VkPrivateDataSlot)stream->getBe64();
    VkResult vkCreatePrivateDataSlotEXT_VkResult_return = (VkResult)0;
    stream->read(&vkCreatePrivateDataSlotEXT_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreatePrivateDataSlotEXT_VkResult_return;
}

void VkEncoder::vkDestroyPrivateDataSlotEXT(VkDevice device, VkPrivateDataSlot privateDataSlot,
                                            const VkAllocationCallbacks* pAllocator,
                                            uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkDestroyPrivateDataSlotEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkDestroyPrivateDataSlotEXT(device:%p, pAllocator:%p)", device, pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkPrivateDataSlot local_privateDataSlot;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_privateDataSlot = privateDataSlot;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkDestroyPrivateDataSlotEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkDestroyPrivateDataSlotEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkDestroyPrivateDataSlotEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkDestroyPrivateDataSlotEXT = OP_vkDestroyPrivateDataSlotEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkDestroyPrivateDataSlotEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkDestroyPrivateDataSlotEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1 = (uint64_t)local_privateDataSlot;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkDestroyPrivateDataSlotEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkSetPrivateDataEXT(VkDevice device, VkObjectType objectType,
                                        uint64_t objectHandle, VkPrivateDataSlot privateDataSlot,
                                        uint64_t data, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkSetPrivateDataEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkSetPrivateDataEXT(device:%p, objectHandle:%ld, data:%ld)", device,
                      objectHandle, data);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkObjectType local_objectType;
    uint64_t local_objectHandle;
    VkPrivateDataSlot local_privateDataSlot;
    uint64_t local_data;
    local_device = device;
    local_objectType = objectType;
    local_objectHandle = objectHandle;
    local_privateDataSlot = privateDataSlot;
    local_data = data;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkObjectType);
        *countPtr += sizeof(uint64_t);
        *countPtr += 8;
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkSetPrivateDataEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkSetPrivateDataEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkSetPrivateDataEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkSetPrivateDataEXT = OP_vkSetPrivateDataEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkSetPrivateDataEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkSetPrivateDataEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkObjectType*)&local_objectType, sizeof(VkObjectType));
    *streamPtrPtr += sizeof(VkObjectType);
    memcpy(*streamPtrPtr, (uint64_t*)&local_objectHandle, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    uint64_t cgen_var_1 = (uint64_t)local_privateDataSlot;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    memcpy(*streamPtrPtr, (uint64_t*)&local_data, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkSetPrivateDataEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkSetPrivateDataEXT_VkResult_return = (VkResult)0;
    stream->read(&vkSetPrivateDataEXT_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkSetPrivateDataEXT_VkResult_return;
}

void VkEncoder::vkGetPrivateDataEXT(VkDevice device, VkObjectType objectType, uint64_t objectHandle,
                                    VkPrivateDataSlot privateDataSlot, uint64_t* pData,
                                    uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetPrivateDataEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetPrivateDataEXT(device:%p, objectHandle:%ld, pData:%p)", device,
                      objectHandle, pData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkObjectType local_objectType;
    uint64_t local_objectHandle;
    VkPrivateDataSlot local_privateDataSlot;
    local_device = device;
    local_objectType = objectType;
    local_objectHandle = objectHandle;
    local_privateDataSlot = privateDataSlot;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkObjectType);
        *countPtr += sizeof(uint64_t);
        *countPtr += 8;
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkGetPrivateDataEXT =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetPrivateDataEXT);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetPrivateDataEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetPrivateDataEXT = OP_vkGetPrivateDataEXT;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetPrivateDataEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetPrivateDataEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkObjectType*)&local_objectType, sizeof(VkObjectType));
    *streamPtrPtr += sizeof(VkObjectType);
    memcpy(*streamPtrPtr, (uint64_t*)&local_objectHandle, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    uint64_t cgen_var_1 = (uint64_t)local_privateDataSlot;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    memcpy(*streamPtrPtr, (uint64_t*)pData, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetPrivateDataEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((uint64_t*)pData, sizeof(uint64_t));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_EXT_extended_dynamic_state2
void VkEncoder::vkCmdSetPatchControlPointsEXT(VkCommandBuffer commandBuffer,
                                              uint32_t patchControlPoints, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetPatchControlPointsEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetPatchControlPointsEXT(commandBuffer:%p, patchControlPoints:%d)",
                      commandBuffer, patchControlPoints);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_patchControlPoints;
    local_commandBuffer = commandBuffer;
    local_patchControlPoints = patchControlPoints;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCmdSetPatchControlPointsEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetPatchControlPointsEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetPatchControlPointsEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetPatchControlPointsEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetPatchControlPointsEXT = OP_vkCmdSetPatchControlPointsEXT;
    memcpy(streamPtr, &opcode_vkCmdSetPatchControlPointsEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetPatchControlPointsEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_patchControlPoints, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetPatchControlPointsEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetRasterizerDiscardEnableEXT(VkCommandBuffer commandBuffer,
                                                   VkBool32 rasterizerDiscardEnable,
                                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetRasterizerDiscardEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetRasterizerDiscardEnableEXT(commandBuffer:%p, rasterizerDiscardEnable:%d)",
        commandBuffer, rasterizerDiscardEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_rasterizerDiscardEnable;
    local_commandBuffer = commandBuffer;
    local_rasterizerDiscardEnable = rasterizerDiscardEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetRasterizerDiscardEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetRasterizerDiscardEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetRasterizerDiscardEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetRasterizerDiscardEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetRasterizerDiscardEnableEXT = OP_vkCmdSetRasterizerDiscardEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetRasterizerDiscardEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetRasterizerDiscardEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_rasterizerDiscardEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetRasterizerDiscardEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetDepthBiasEnableEXT(VkCommandBuffer commandBuffer, VkBool32 depthBiasEnable,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetDepthBiasEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetDepthBiasEnableEXT(commandBuffer:%p, depthBiasEnable:%d)",
                      commandBuffer, depthBiasEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_depthBiasEnable;
    local_commandBuffer = commandBuffer;
    local_depthBiasEnable = depthBiasEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetDepthBiasEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetDepthBiasEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetDepthBiasEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetDepthBiasEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetDepthBiasEnableEXT = OP_vkCmdSetDepthBiasEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetDepthBiasEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetDepthBiasEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_depthBiasEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetDepthBiasEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetLogicOpEXT(VkCommandBuffer commandBuffer, VkLogicOp logicOp,
                                   uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetLogicOpEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkCmdSetLogicOpEXT(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkLogicOp local_logicOp;
    local_commandBuffer = commandBuffer;
    local_logicOp = logicOp;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkLogicOp);
    }
    uint32_t packetSize_vkCmdSetLogicOpEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetLogicOpEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetLogicOpEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetLogicOpEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetLogicOpEXT = OP_vkCmdSetLogicOpEXT;
    memcpy(streamPtr, &opcode_vkCmdSetLogicOpEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetLogicOpEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkLogicOp*)&local_logicOp, sizeof(VkLogicOp));
    *streamPtrPtr += sizeof(VkLogicOp);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetLogicOpEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCmdSetPrimitiveRestartEnableEXT(VkCommandBuffer commandBuffer,
                                                  VkBool32 primitiveRestartEnable,
                                                  uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetPrimitiveRestartEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetPrimitiveRestartEnableEXT(commandBuffer:%p, primitiveRestartEnable:%d)",
        commandBuffer, primitiveRestartEnable);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkBool32 local_primitiveRestartEnable;
    local_commandBuffer = commandBuffer;
    local_primitiveRestartEnable = primitiveRestartEnable;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetPrimitiveRestartEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCmdSetPrimitiveRestartEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetPrimitiveRestartEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetPrimitiveRestartEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetPrimitiveRestartEnableEXT = OP_vkCmdSetPrimitiveRestartEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetPrimitiveRestartEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetPrimitiveRestartEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkBool32*)&local_primitiveRestartEnable, sizeof(VkBool32));
    *streamPtrPtr += sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetPrimitiveRestartEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_EXT_color_write_enable
void VkEncoder::vkCmdSetColorWriteEnableEXT(VkCommandBuffer commandBuffer, uint32_t attachmentCount,
                                            const VkBool32* pColorWriteEnables, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCmdSetColorWriteEnableEXT in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCmdSetColorWriteEnableEXT(commandBuffer:%p, attachmentCount:%d, pColorWriteEnables:%p)",
        commandBuffer, attachmentCount, pColorWriteEnables);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_attachmentCount;
    VkBool32* local_pColorWriteEnables;
    local_commandBuffer = commandBuffer;
    local_attachmentCount = attachmentCount;
    // Avoiding deepcopy for pColorWriteEnables
    local_pColorWriteEnables = (VkBool32*)pColorWriteEnables;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += ((attachmentCount)) * sizeof(VkBool32);
    }
    uint32_t packetSize_vkCmdSetColorWriteEnableEXT = 4 + 4 + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkCmdSetColorWriteEnableEXT);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCmdSetColorWriteEnableEXT -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCmdSetColorWriteEnableEXT);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCmdSetColorWriteEnableEXT = OP_vkCmdSetColorWriteEnableEXT;
    memcpy(streamPtr, &opcode_vkCmdSetColorWriteEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCmdSetColorWriteEnableEXT, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_attachmentCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (VkBool32*)local_pColorWriteEnables,
           ((attachmentCount)) * sizeof(VkBool32));
    *streamPtrPtr += ((attachmentCount)) * sizeof(VkBool32);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCmdSetColorWriteEnableEXT), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

#endif
#ifdef VK_GOOGLE_gfxstream
VkResult VkEncoder::vkMapMemoryIntoAddressSpaceGOOGLE(VkDevice device, VkDeviceMemory memory,
                                                      uint64_t* pAddress, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkMapMemoryIntoAddressSpaceGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkMapMemoryIntoAddressSpaceGOOGLE(device:%p, memory:%p, pAddress:%p)",
                      device, memory, pAddress);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    sResourceTracker->on_vkMapMemoryIntoAddressSpaceGOOGLE_pre(this, VK_SUCCESS, device, memory,
                                                               pAddress);
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemory local_memory;
    local_device = device;
    local_memory = memory;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)nullptr, 0, (VkDeviceSize*)nullptr, 0,
        (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pAddress) {
            *countPtr += sizeof(uint64_t);
        }
    }
    uint32_t packetSize_vkMapMemoryIntoAddressSpaceGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkMapMemoryIntoAddressSpaceGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkMapMemoryIntoAddressSpaceGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkMapMemoryIntoAddressSpaceGOOGLE = OP_vkMapMemoryIntoAddressSpaceGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkMapMemoryIntoAddressSpaceGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkMapMemoryIntoAddressSpaceGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pAddress;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pAddress) {
        memcpy(*streamPtrPtr, (uint64_t*)pAddress, sizeof(uint64_t));
        *streamPtrPtr += sizeof(uint64_t);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkMapMemoryIntoAddressSpaceGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint64_t* check_pAddress;
    check_pAddress = (uint64_t*)(uintptr_t)stream->getBe64();
    if (pAddress) {
        if (!(check_pAddress)) {
            fprintf(stderr, "fatal: pAddress inconsistent between guest and host\n");
        }
        stream->read((uint64_t*)pAddress, sizeof(uint64_t));
    }
    VkResult vkMapMemoryIntoAddressSpaceGOOGLE_VkResult_return = (VkResult)0;
    stream->read(&vkMapMemoryIntoAddressSpaceGOOGLE_VkResult_return, sizeof(VkResult));
    sResourceTracker->on_vkMapMemoryIntoAddressSpaceGOOGLE(
        this, vkMapMemoryIntoAddressSpaceGOOGLE_VkResult_return, device, memory, pAddress);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkMapMemoryIntoAddressSpaceGOOGLE_VkResult_return;
}

void VkEncoder::vkUpdateDescriptorSetWithTemplateSizedGOOGLE(
    VkDevice device, VkDescriptorSet descriptorSet,
    VkDescriptorUpdateTemplate descriptorUpdateTemplate, uint32_t imageInfoCount,
    uint32_t bufferInfoCount, uint32_t bufferViewCount, const uint32_t* pImageInfoEntryIndices,
    const uint32_t* pBufferInfoEntryIndices, const uint32_t* pBufferViewEntryIndices,
    const VkDescriptorImageInfo* pImageInfos, const VkDescriptorBufferInfo* pBufferInfos,
    const VkBufferView* pBufferViews, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkUpdateDescriptorSetWithTemplateSizedGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkUpdateDescriptorSetWithTemplateSizedGOOGLE(device:%p, descriptorSet:%p, "
        "descriptorUpdateTemplate:%p, imageInfoCount:%d, bufferInfoCount:%d, bufferViewCount:%d, "
        "pImageInfoEntryIndices:%p, pBufferInfoEntryIndices:%p, pBufferViewEntryIndices:%p, "
        "pImageInfos:%p, pBufferInfos:%p, pBufferViews:%p)",
        device, descriptorSet, descriptorUpdateTemplate, imageInfoCount, bufferInfoCount,
        bufferViewCount, pImageInfoEntryIndices, pBufferInfoEntryIndices, pBufferViewEntryIndices,
        pImageInfos, pBufferInfos, pBufferViews);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSet local_descriptorSet;
    VkDescriptorUpdateTemplate local_descriptorUpdateTemplate;
    uint32_t local_imageInfoCount;
    uint32_t local_bufferInfoCount;
    uint32_t local_bufferViewCount;
    uint32_t* local_pImageInfoEntryIndices;
    uint32_t* local_pBufferInfoEntryIndices;
    uint32_t* local_pBufferViewEntryIndices;
    VkDescriptorImageInfo* local_pImageInfos;
    VkDescriptorBufferInfo* local_pBufferInfos;
    VkBufferView* local_pBufferViews;
    local_device = device;
    local_descriptorSet = descriptorSet;
    local_descriptorUpdateTemplate = descriptorUpdateTemplate;
    local_imageInfoCount = imageInfoCount;
    local_bufferInfoCount = bufferInfoCount;
    local_bufferViewCount = bufferViewCount;
    // Avoiding deepcopy for pImageInfoEntryIndices
    local_pImageInfoEntryIndices = (uint32_t*)pImageInfoEntryIndices;
    // Avoiding deepcopy for pBufferInfoEntryIndices
    local_pBufferInfoEntryIndices = (uint32_t*)pBufferInfoEntryIndices;
    // Avoiding deepcopy for pBufferViewEntryIndices
    local_pBufferViewEntryIndices = (uint32_t*)pBufferViewEntryIndices;
    local_pImageInfos = nullptr;
    if (pImageInfos) {
        local_pImageInfos = (VkDescriptorImageInfo*)pool->alloc(
            ((imageInfoCount)) * sizeof(const VkDescriptorImageInfo));
        for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
            deepcopy_VkDescriptorImageInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pImageInfos + i,
                                           (VkDescriptorImageInfo*)(local_pImageInfos + i));
        }
    }
    local_pBufferInfos = nullptr;
    if (pBufferInfos) {
        local_pBufferInfos = (VkDescriptorBufferInfo*)pool->alloc(
            ((bufferInfoCount)) * sizeof(const VkDescriptorBufferInfo));
        for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
            deepcopy_VkDescriptorBufferInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBufferInfos + i,
                                            (VkDescriptorBufferInfo*)(local_pBufferInfos + i));
        }
    }
    // Avoiding deepcopy for pBufferViews
    local_pBufferViews = (VkBufferView*)pBufferViews;
    if (local_pImageInfos) {
        for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
            transform_tohost_VkDescriptorImageInfo(sResourceTracker,
                                                   (VkDescriptorImageInfo*)(local_pImageInfos + i));
        }
    }
    if (local_pBufferInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
            transform_tohost_VkDescriptorBufferInfo(
                sResourceTracker, (VkDescriptorBufferInfo*)(local_pBufferInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pImageInfoEntryIndices) {
            *countPtr += ((imageInfoCount)) * sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferInfoEntryIndices) {
            *countPtr += ((bufferInfoCount)) * sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferViewEntryIndices) {
            *countPtr += ((bufferViewCount)) * sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pImageInfos) {
            for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
                count_VkDescriptorImageInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkDescriptorImageInfo*)(local_pImageInfos + i),
                                            countPtr);
            }
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferInfos) {
            for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
                count_VkDescriptorBufferInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkDescriptorBufferInfo*)(local_pBufferInfos + i),
                                             countPtr);
            }
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferViews) {
            if (((bufferViewCount))) {
                *countPtr += ((bufferViewCount)) * 8;
            }
        }
    }
    uint32_t packetSize_vkUpdateDescriptorSetWithTemplateSizedGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkUpdateDescriptorSetWithTemplateSizedGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkUpdateDescriptorSetWithTemplateSizedGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkUpdateDescriptorSetWithTemplateSizedGOOGLE =
        OP_vkUpdateDescriptorSetWithTemplateSizedGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkUpdateDescriptorSetWithTemplateSizedGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkUpdateDescriptorSetWithTemplateSizedGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorSet((*&local_descriptorSet));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkDescriptorUpdateTemplate((*&local_descriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_imageInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bufferInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bufferViewCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_3 = (uint64_t)(uintptr_t)local_pImageInfoEntryIndices;
    memcpy((*streamPtrPtr), &cgen_var_3, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pImageInfoEntryIndices) {
        memcpy(*streamPtrPtr, (uint32_t*)local_pImageInfoEntryIndices,
               ((imageInfoCount)) * sizeof(uint32_t));
        *streamPtrPtr += ((imageInfoCount)) * sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_4 = (uint64_t)(uintptr_t)local_pBufferInfoEntryIndices;
    memcpy((*streamPtrPtr), &cgen_var_4, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferInfoEntryIndices) {
        memcpy(*streamPtrPtr, (uint32_t*)local_pBufferInfoEntryIndices,
               ((bufferInfoCount)) * sizeof(uint32_t));
        *streamPtrPtr += ((bufferInfoCount)) * sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_5 = (uint64_t)(uintptr_t)local_pBufferViewEntryIndices;
    memcpy((*streamPtrPtr), &cgen_var_5, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferViewEntryIndices) {
        memcpy(*streamPtrPtr, (uint32_t*)local_pBufferViewEntryIndices,
               ((bufferViewCount)) * sizeof(uint32_t));
        *streamPtrPtr += ((bufferViewCount)) * sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_6 = (uint64_t)(uintptr_t)local_pImageInfos;
    memcpy((*streamPtrPtr), &cgen_var_6, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pImageInfos) {
        for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
            reservedmarshal_VkDescriptorImageInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                  (VkDescriptorImageInfo*)(local_pImageInfos + i),
                                                  streamPtrPtr);
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_7 = (uint64_t)(uintptr_t)local_pBufferInfos;
    memcpy((*streamPtrPtr), &cgen_var_7, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
            reservedmarshal_VkDescriptorBufferInfo(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkDescriptorBufferInfo*)(local_pBufferInfos + i), streamPtrPtr);
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_8 = (uint64_t)(uintptr_t)local_pBufferViews;
    memcpy((*streamPtrPtr), &cgen_var_8, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferViews) {
        if (((bufferViewCount))) {
            uint8_t* cgen_var_8_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((bufferViewCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkBufferView(local_pBufferViews[k]);
                memcpy(cgen_var_8_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((bufferViewCount));
        }
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkUpdateDescriptorSetWithTemplateSizedGOOGLE),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkBeginCommandBufferAsyncGOOGLE(VkCommandBuffer commandBuffer,
                                                const VkCommandBufferBeginInfo* pBeginInfo,
                                                uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkBeginCommandBufferAsyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkBeginCommandBufferAsyncGOOGLE(commandBuffer:%p, pBeginInfo:%p)",
                      commandBuffer, pBeginInfo);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCommandBufferBeginInfo* local_pBeginInfo;
    local_commandBuffer = commandBuffer;
    local_pBeginInfo = nullptr;
    if (pBeginInfo) {
        local_pBeginInfo =
            (VkCommandBufferBeginInfo*)pool->alloc(sizeof(const VkCommandBufferBeginInfo));
        deepcopy_VkCommandBufferBeginInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBeginInfo,
                                          (VkCommandBufferBeginInfo*)(local_pBeginInfo));
    }
    if (local_pBeginInfo) {
        transform_tohost_VkCommandBufferBeginInfo(sResourceTracker,
                                                  (VkCommandBufferBeginInfo*)(local_pBeginInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkCommandBufferBeginInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkCommandBufferBeginInfo*)(local_pBeginInfo), countPtr);
    }
    uint32_t packetSize_vkBeginCommandBufferAsyncGOOGLE = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkBeginCommandBufferAsyncGOOGLE);
    if (queueSubmitWithCommandsEnabled) packetSize_vkBeginCommandBufferAsyncGOOGLE -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkBeginCommandBufferAsyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkBeginCommandBufferAsyncGOOGLE = OP_vkBeginCommandBufferAsyncGOOGLE;
    memcpy(streamPtr, &opcode_vkBeginCommandBufferAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkBeginCommandBufferAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    reservedmarshal_VkCommandBufferBeginInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkCommandBufferBeginInfo*)(local_pBeginInfo),
                                             streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkBeginCommandBufferAsyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkEndCommandBufferAsyncGOOGLE(VkCommandBuffer commandBuffer, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkEndCommandBufferAsyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkEndCommandBufferAsyncGOOGLE(commandBuffer:%p)", commandBuffer);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    local_commandBuffer = commandBuffer;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkEndCommandBufferAsyncGOOGLE = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkEndCommandBufferAsyncGOOGLE);
    if (queueSubmitWithCommandsEnabled) packetSize_vkEndCommandBufferAsyncGOOGLE -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkEndCommandBufferAsyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkEndCommandBufferAsyncGOOGLE = OP_vkEndCommandBufferAsyncGOOGLE;
    memcpy(streamPtr, &opcode_vkEndCommandBufferAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkEndCommandBufferAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkEndCommandBufferAsyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkResetCommandBufferAsyncGOOGLE(VkCommandBuffer commandBuffer,
                                                VkCommandBufferResetFlags flags, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkResetCommandBufferAsyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkResetCommandBufferAsyncGOOGLE(commandBuffer:%p, flags:%d)", commandBuffer,
                      flags);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    VkCommandBufferResetFlags local_flags;
    local_commandBuffer = commandBuffer;
    local_flags = flags;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkCommandBufferResetFlags);
    }
    uint32_t packetSize_vkResetCommandBufferAsyncGOOGLE = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkResetCommandBufferAsyncGOOGLE);
    if (queueSubmitWithCommandsEnabled) packetSize_vkResetCommandBufferAsyncGOOGLE -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkResetCommandBufferAsyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkResetCommandBufferAsyncGOOGLE = OP_vkResetCommandBufferAsyncGOOGLE;
    memcpy(streamPtr, &opcode_vkResetCommandBufferAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkResetCommandBufferAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (VkCommandBufferResetFlags*)&local_flags,
           sizeof(VkCommandBufferResetFlags));
    *streamPtrPtr += sizeof(VkCommandBufferResetFlags);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkResetCommandBufferAsyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCommandBufferHostSyncGOOGLE(VkCommandBuffer commandBuffer, uint32_t needHostSync,
                                              uint32_t sequenceNumber, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCommandBufferHostSyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCommandBufferHostSyncGOOGLE(commandBuffer:%p, needHostSync:%d, sequenceNumber:%d)",
        commandBuffer, needHostSync, sequenceNumber);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkCommandBuffer local_commandBuffer;
    uint32_t local_needHostSync;
    uint32_t local_sequenceNumber;
    local_commandBuffer = commandBuffer;
    local_needHostSync = needHostSync;
    local_sequenceNumber = sequenceNumber;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkCommandBufferHostSyncGOOGLE = 4 + 4 + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCommandBufferHostSyncGOOGLE);
    if (queueSubmitWithCommandsEnabled) packetSize_vkCommandBufferHostSyncGOOGLE -= 8;
    uint8_t* streamPtr = stream->reserve(packetSize_vkCommandBufferHostSyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCommandBufferHostSyncGOOGLE = OP_vkCommandBufferHostSyncGOOGLE;
    memcpy(streamPtr, &opcode_vkCommandBufferHostSyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCommandBufferHostSyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (!queueSubmitWithCommandsEnabled) {
        uint64_t cgen_var_0;
        *&cgen_var_0 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
        memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
        *streamPtrPtr += 1 * 8;
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_needHostSync, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_sequenceNumber, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCommandBufferHostSyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkCreateImageWithRequirementsGOOGLE(
    VkDevice device, const VkImageCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator,
    VkImage* pImage, VkMemoryRequirements* pMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateImageWithRequirementsGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkImageCreateInfo*)pool->alloc(sizeof(const VkImageCreateInfo));
        deepcopy_VkImageCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                   (VkImageCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    sResourceTracker->unwrap_vkCreateImage_pCreateInfo(pCreateInfo, local_pCreateInfo);
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        sResourceTracker->transformImpl_VkImageCreateInfo_tohost(local_pCreateInfo, 1);
        transform_tohost_VkImageCreateInfo(sResourceTracker,
                                           (VkImageCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkImageCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
        count_VkMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkCreateImageWithRequirementsGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCreateImageWithRequirementsGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateImageWithRequirementsGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateImageWithRequirementsGOOGLE = OP_vkCreateImageWithRequirementsGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateImageWithRequirementsGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateImageWithRequirementsGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkImageCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pImage));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    reservedmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkMemoryRequirements*)(pMemoryRequirements),
                                         streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateImageWithRequirementsGOOGLE),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkImage(&cgen_var_3, (VkImage*)pImage, 1);
    stream->unsetHandleMapping();
    unmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements(sResourceTracker,
                                                (VkMemoryRequirements*)(pMemoryRequirements));
    }
    VkResult vkCreateImageWithRequirementsGOOGLE_VkResult_return = (VkResult)0;
    stream->read(&vkCreateImageWithRequirementsGOOGLE_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateImageWithRequirementsGOOGLE_VkResult_return;
}

VkResult VkEncoder::vkCreateBufferWithRequirementsGOOGLE(
    VkDevice device, const VkBufferCreateInfo* pCreateInfo, const VkAllocationCallbacks* pAllocator,
    VkBuffer* pBuffer, VkMemoryRequirements* pMemoryRequirements, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCreateBufferWithRequirementsGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCreateBufferWithRequirementsGOOGLE(device:%p, pCreateInfo:%p, pAllocator:%p, "
        "pBuffer:%p, pMemoryRequirements:%p)",
        device, pCreateInfo, pAllocator, pBuffer, pMemoryRequirements);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkBufferCreateInfo* local_pCreateInfo;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkBufferCreateInfo*)pool->alloc(sizeof(const VkBufferCreateInfo));
        deepcopy_VkBufferCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                    (VkBufferCreateInfo*)(local_pCreateInfo));
    }
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    if (local_pCreateInfo) {
        transform_tohost_VkBufferCreateInfo(sResourceTracker,
                                            (VkBufferCreateInfo*)(local_pCreateInfo));
    }
    if (local_pAllocator) {
        transform_tohost_VkAllocationCallbacks(sResourceTracker,
                                               (VkAllocationCallbacks*)(local_pAllocator));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkBufferCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                 (VkBufferCreateInfo*)(local_pCreateInfo), countPtr);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 8;
        count_VkMemoryRequirements(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements), countPtr);
    }
    uint32_t packetSize_vkCreateBufferWithRequirementsGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCreateBufferWithRequirementsGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCreateBufferWithRequirementsGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCreateBufferWithRequirementsGOOGLE = OP_vkCreateBufferWithRequirementsGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCreateBufferWithRequirementsGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCreateBufferWithRequirementsGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkBufferCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkBufferCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    /* is handle, possibly out */;
    uint64_t cgen_var_2;
    *&cgen_var_2 = (uint64_t)((*pBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 8);
    *streamPtrPtr += 8;
    /* is handle, possibly out */;
    reservedmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkMemoryRequirements*)(pMemoryRequirements),
                                         streamPtrPtr);
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkCreateBufferWithRequirementsGOOGLE),
                             kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->setHandleMapping(sResourceTracker->createMapping());
    uint64_t cgen_var_3;
    stream->read((uint64_t*)&cgen_var_3, 8);
    stream->handleMapping()->mapHandles_u64_VkBuffer(&cgen_var_3, (VkBuffer*)pBuffer, 1);
    stream->unsetHandleMapping();
    unmarshal_VkMemoryRequirements(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkMemoryRequirements*)(pMemoryRequirements));
    if (pMemoryRequirements) {
        transform_fromhost_VkMemoryRequirements(sResourceTracker,
                                                (VkMemoryRequirements*)(pMemoryRequirements));
    }
    VkResult vkCreateBufferWithRequirementsGOOGLE_VkResult_return = (VkResult)0;
    stream->read(&vkCreateBufferWithRequirementsGOOGLE_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkCreateBufferWithRequirementsGOOGLE_VkResult_return;
}

VkResult VkEncoder::vkGetMemoryHostAddressInfoGOOGLE(VkDevice device, VkDeviceMemory memory,
                                                     uint64_t* pAddress, uint64_t* pSize,
                                                     uint64_t* pHostmemId, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetMemoryHostAddressInfoGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetMemoryHostAddressInfoGOOGLE(device:%p, memory:%p, pAddress:%p, pSize:%p, "
        "pHostmemId:%p)",
        device, memory, pAddress, pSize, pHostmemId);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemory local_memory;
    local_device = device;
    local_memory = memory;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)nullptr, 0, (VkDeviceSize*)nullptr, 0,
        (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pAddress) {
            *countPtr += sizeof(uint64_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pSize) {
            *countPtr += sizeof(uint64_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pHostmemId) {
            *countPtr += sizeof(uint64_t);
        }
    }
    uint32_t packetSize_vkGetMemoryHostAddressInfoGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetMemoryHostAddressInfoGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetMemoryHostAddressInfoGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetMemoryHostAddressInfoGOOGLE = OP_vkGetMemoryHostAddressInfoGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetMemoryHostAddressInfoGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetMemoryHostAddressInfoGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pAddress;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pAddress) {
        memcpy(*streamPtrPtr, (uint64_t*)pAddress, sizeof(uint64_t));
        *streamPtrPtr += sizeof(uint64_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_3 = (uint64_t)(uintptr_t)pSize;
    memcpy((*streamPtrPtr), &cgen_var_3, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pSize) {
        memcpy(*streamPtrPtr, (uint64_t*)pSize, sizeof(uint64_t));
        *streamPtrPtr += sizeof(uint64_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_4 = (uint64_t)(uintptr_t)pHostmemId;
    memcpy((*streamPtrPtr), &cgen_var_4, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pHostmemId) {
        memcpy(*streamPtrPtr, (uint64_t*)pHostmemId, sizeof(uint64_t));
        *streamPtrPtr += sizeof(uint64_t);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetMemoryHostAddressInfoGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    // WARNING PTR CHECK
    uint64_t* check_pAddress;
    check_pAddress = (uint64_t*)(uintptr_t)stream->getBe64();
    if (pAddress) {
        if (!(check_pAddress)) {
            fprintf(stderr, "fatal: pAddress inconsistent between guest and host\n");
        }
        stream->read((uint64_t*)pAddress, sizeof(uint64_t));
    }
    // WARNING PTR CHECK
    uint64_t* check_pSize;
    check_pSize = (uint64_t*)(uintptr_t)stream->getBe64();
    if (pSize) {
        if (!(check_pSize)) {
            fprintf(stderr, "fatal: pSize inconsistent between guest and host\n");
        }
        stream->read((uint64_t*)pSize, sizeof(uint64_t));
    }
    // WARNING PTR CHECK
    uint64_t* check_pHostmemId;
    check_pHostmemId = (uint64_t*)(uintptr_t)stream->getBe64();
    if (pHostmemId) {
        if (!(check_pHostmemId)) {
            fprintf(stderr, "fatal: pHostmemId inconsistent between guest and host\n");
        }
        stream->read((uint64_t*)pHostmemId, sizeof(uint64_t));
    }
    VkResult vkGetMemoryHostAddressInfoGOOGLE_VkResult_return = (VkResult)0;
    stream->read(&vkGetMemoryHostAddressInfoGOOGLE_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetMemoryHostAddressInfoGOOGLE_VkResult_return;
}

VkResult VkEncoder::vkFreeMemorySyncGOOGLE(VkDevice device, VkDeviceMemory memory,
                                           const VkAllocationCallbacks* pAllocator,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkFreeMemorySyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkFreeMemorySyncGOOGLE(device:%p, memory:%p, pAllocator:%p)", device, memory,
                      pAllocator);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemory local_memory;
    VkAllocationCallbacks* local_pAllocator;
    local_device = device;
    local_memory = memory;
    local_pAllocator = nullptr;
    if (pAllocator) {
        local_pAllocator = (VkAllocationCallbacks*)pool->alloc(sizeof(const VkAllocationCallbacks));
        deepcopy_VkAllocationCallbacks(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pAllocator,
                                       (VkAllocationCallbacks*)(local_pAllocator));
    }
    local_pAllocator = nullptr;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)nullptr, 0, (VkDeviceSize*)nullptr, 0,
        (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pAllocator) {
            count_VkAllocationCallbacks(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                        (VkAllocationCallbacks*)(local_pAllocator), countPtr);
        }
    }
    uint32_t packetSize_vkFreeMemorySyncGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkFreeMemorySyncGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkFreeMemorySyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkFreeMemorySyncGOOGLE = OP_vkFreeMemorySyncGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkFreeMemorySyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkFreeMemorySyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)local_pAllocator;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pAllocator) {
        reservedmarshal_VkAllocationCallbacks(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                              (VkAllocationCallbacks*)(local_pAllocator),
                                              streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkFreeMemorySyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkFreeMemorySyncGOOGLE_VkResult_return = (VkResult)0;
    stream->read(&vkFreeMemorySyncGOOGLE_VkResult_return, sizeof(VkResult));
    sResourceTracker->destroyMapping()->mapHandles_VkDeviceMemory((VkDeviceMemory*)&memory);
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkFreeMemorySyncGOOGLE_VkResult_return;
}

void VkEncoder::vkQueueHostSyncGOOGLE(VkQueue queue, uint32_t needHostSync, uint32_t sequenceNumber,
                                      uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueHostSyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueHostSyncGOOGLE(queue:%p, needHostSync:%d, sequenceNumber:%d)", queue,
                      needHostSync, sequenceNumber);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_needHostSync;
    uint32_t local_sequenceNumber;
    local_queue = queue;
    local_needHostSync = needHostSync;
    local_sequenceNumber = sequenceNumber;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
    }
    uint32_t packetSize_vkQueueHostSyncGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueHostSyncGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueHostSyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueHostSyncGOOGLE = OP_vkQueueHostSyncGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueHostSyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueHostSyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_needHostSync, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_sequenceNumber, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueHostSyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkQueueSubmitAsyncGOOGLE(VkQueue queue, uint32_t submitCount,
                                         const VkSubmitInfo* pSubmits, VkFence fence,
                                         uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueSubmitAsyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueSubmitAsyncGOOGLE(queue:%p, submitCount:%d, pSubmits:%p, fence:%p)",
                      queue, submitCount, pSubmits, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_submitCount;
    VkSubmitInfo* local_pSubmits;
    VkFence local_fence;
    local_queue = queue;
    local_submitCount = submitCount;
    local_pSubmits = nullptr;
    if (pSubmits) {
        local_pSubmits = (VkSubmitInfo*)pool->alloc(((submitCount)) * sizeof(const VkSubmitInfo));
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            deepcopy_VkSubmitInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubmits + i,
                                  (VkSubmitInfo*)(local_pSubmits + i));
        }
    }
    local_fence = fence;
    if (local_pSubmits) {
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            transform_tohost_VkSubmitInfo(sResourceTracker, (VkSubmitInfo*)(local_pSubmits + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            count_VkSubmitInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                               (VkSubmitInfo*)(local_pSubmits + i), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueSubmitAsyncGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueSubmitAsyncGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueSubmitAsyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueSubmitAsyncGOOGLE = OP_vkQueueSubmitAsyncGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueSubmitAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueSubmitAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_submitCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
        reservedmarshal_VkSubmitInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                     (VkSubmitInfo*)(local_pSubmits + i), streamPtrPtr);
    }
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueSubmitAsyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkQueueWaitIdleAsyncGOOGLE(VkQueue queue, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueWaitIdleAsyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueWaitIdleAsyncGOOGLE(queue:%p)", queue);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    local_queue = queue;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueWaitIdleAsyncGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueWaitIdleAsyncGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueWaitIdleAsyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueWaitIdleAsyncGOOGLE = OP_vkQueueWaitIdleAsyncGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueWaitIdleAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueWaitIdleAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueWaitIdleAsyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkQueueBindSparseAsyncGOOGLE(VkQueue queue, uint32_t bindInfoCount,
                                             const VkBindSparseInfo* pBindInfo, VkFence fence,
                                             uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueBindSparseAsyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkQueueBindSparseAsyncGOOGLE(queue:%p, bindInfoCount:%d, pBindInfo:%p, fence:%p)", queue,
        bindInfoCount, pBindInfo, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_bindInfoCount;
    VkBindSparseInfo* local_pBindInfo;
    VkFence local_fence;
    local_queue = queue;
    local_bindInfoCount = bindInfoCount;
    local_pBindInfo = nullptr;
    if (pBindInfo) {
        local_pBindInfo =
            (VkBindSparseInfo*)pool->alloc(((bindInfoCount)) * sizeof(const VkBindSparseInfo));
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            deepcopy_VkBindSparseInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBindInfo + i,
                                      (VkBindSparseInfo*)(local_pBindInfo + i));
        }
    }
    local_fence = fence;
    if (local_pBindInfo) {
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            transform_tohost_VkBindSparseInfo(sResourceTracker,
                                              (VkBindSparseInfo*)(local_pBindInfo + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
            count_VkBindSparseInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                   (VkBindSparseInfo*)(local_pBindInfo + i), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueBindSparseAsyncGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkQueueBindSparseAsyncGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueBindSparseAsyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueBindSparseAsyncGOOGLE = OP_vkQueueBindSparseAsyncGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueBindSparseAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueBindSparseAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_bindInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((bindInfoCount)); ++i) {
        reservedmarshal_VkBindSparseInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                         (VkBindSparseInfo*)(local_pBindInfo + i), streamPtrPtr);
    }
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueBindSparseAsyncGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetLinearImageLayoutGOOGLE(VkDevice device, VkFormat format,
                                             VkDeviceSize* pOffset,
                                             VkDeviceSize* pRowPitchAlignment, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetLinearImageLayoutGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetLinearImageLayoutGOOGLE(device:%p, format:%d, pOffset:%p, pRowPitchAlignment:%p)",
        device, format, pOffset, pRowPitchAlignment);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkFormat local_format;
    local_device = device;
    local_format = format;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkFormat);
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkGetLinearImageLayoutGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetLinearImageLayoutGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetLinearImageLayoutGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetLinearImageLayoutGOOGLE = OP_vkGetLinearImageLayoutGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetLinearImageLayoutGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetLinearImageLayoutGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkFormat*)&local_format, sizeof(VkFormat));
    *streamPtrPtr += sizeof(VkFormat);
    memcpy(*streamPtrPtr, (VkDeviceSize*)pOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkDeviceSize*)pRowPitchAlignment, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetLinearImageLayoutGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((VkDeviceSize*)pOffset, sizeof(VkDeviceSize));
    stream->read((VkDeviceSize*)pRowPitchAlignment, sizeof(VkDeviceSize));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkGetLinearImageLayout2GOOGLE(VkDevice device, const VkImageCreateInfo* pCreateInfo,
                                              VkDeviceSize* pOffset,
                                              VkDeviceSize* pRowPitchAlignment, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetLinearImageLayout2GOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkGetLinearImageLayout2GOOGLE(device:%p, pCreateInfo:%p, pOffset:%p, "
        "pRowPitchAlignment:%p)",
        device, pCreateInfo, pOffset, pRowPitchAlignment);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkImageCreateInfo* local_pCreateInfo;
    local_device = device;
    local_pCreateInfo = nullptr;
    if (pCreateInfo) {
        local_pCreateInfo = (VkImageCreateInfo*)pool->alloc(sizeof(const VkImageCreateInfo));
        deepcopy_VkImageCreateInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pCreateInfo,
                                   (VkImageCreateInfo*)(local_pCreateInfo));
    }
    if (local_pCreateInfo) {
        sResourceTracker->transformImpl_VkImageCreateInfo_tohost(local_pCreateInfo, 1);
        transform_tohost_VkImageCreateInfo(sResourceTracker,
                                           (VkImageCreateInfo*)(local_pCreateInfo));
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        count_VkImageCreateInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkImageCreateInfo*)(local_pCreateInfo), countPtr);
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkGetLinearImageLayout2GOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkGetLinearImageLayout2GOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetLinearImageLayout2GOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetLinearImageLayout2GOOGLE = OP_vkGetLinearImageLayout2GOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetLinearImageLayout2GOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetLinearImageLayout2GOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    reservedmarshal_VkImageCreateInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkImageCreateInfo*)(local_pCreateInfo), streamPtrPtr);
    memcpy(*streamPtrPtr, (VkDeviceSize*)pOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkDeviceSize*)pRowPitchAlignment, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetLinearImageLayout2GOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((VkDeviceSize*)pOffset, sizeof(VkDeviceSize));
    stream->read((VkDeviceSize*)pRowPitchAlignment, sizeof(VkDeviceSize));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkQueueFlushCommandsGOOGLE(VkQueue queue, VkCommandBuffer commandBuffer,
                                           VkDeviceSize dataSize, const void* pData,
                                           uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueFlushCommandsGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

#include "vkQueueFlushCommandsGOOGLE_encode_impl.cpp.inl"
}

void VkEncoder::vkQueueCommitDescriptorSetUpdatesGOOGLE(
    VkQueue queue, uint32_t descriptorPoolCount, const VkDescriptorPool* pDescriptorPools,
    uint32_t descriptorSetCount, const VkDescriptorSetLayout* pSetLayouts,
    const uint64_t* pDescriptorSetPoolIds, const uint32_t* pDescriptorSetWhichPool,
    const uint32_t* pDescriptorSetPendingAllocation,
    const uint32_t* pDescriptorWriteStartingIndices, uint32_t pendingDescriptorWriteCount,
    const VkWriteDescriptorSet* pPendingDescriptorWrites, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueCommitDescriptorSetUpdatesGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkQueueCommitDescriptorSetUpdatesGOOGLE(queue:%p, descriptorPoolCount:%d, "
        "pDescriptorPools:%p, descriptorSetCount:%d, pSetLayouts:%p, pDescriptorSetPoolIds:%p, "
        "pDescriptorSetWhichPool:%p, pDescriptorSetPendingAllocation:%p, "
        "pDescriptorWriteStartingIndices:%p, pendingDescriptorWriteCount:%d, "
        "pPendingDescriptorWrites:%p)",
        queue, descriptorPoolCount, pDescriptorPools, descriptorSetCount, pSetLayouts,
        pDescriptorSetPoolIds, pDescriptorSetWhichPool, pDescriptorSetPendingAllocation,
        pDescriptorWriteStartingIndices, pendingDescriptorWriteCount, pPendingDescriptorWrites);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_descriptorPoolCount;
    VkDescriptorPool* local_pDescriptorPools;
    uint32_t local_descriptorSetCount;
    VkDescriptorSetLayout* local_pSetLayouts;
    uint64_t* local_pDescriptorSetPoolIds;
    uint32_t* local_pDescriptorSetWhichPool;
    uint32_t* local_pDescriptorSetPendingAllocation;
    uint32_t* local_pDescriptorWriteStartingIndices;
    uint32_t local_pendingDescriptorWriteCount;
    VkWriteDescriptorSet* local_pPendingDescriptorWrites;
    local_queue = queue;
    local_descriptorPoolCount = descriptorPoolCount;
    // Avoiding deepcopy for pDescriptorPools
    local_pDescriptorPools = (VkDescriptorPool*)pDescriptorPools;
    local_descriptorSetCount = descriptorSetCount;
    // Avoiding deepcopy for pSetLayouts
    local_pSetLayouts = (VkDescriptorSetLayout*)pSetLayouts;
    // Avoiding deepcopy for pDescriptorSetPoolIds
    local_pDescriptorSetPoolIds = (uint64_t*)pDescriptorSetPoolIds;
    // Avoiding deepcopy for pDescriptorSetWhichPool
    local_pDescriptorSetWhichPool = (uint32_t*)pDescriptorSetWhichPool;
    // Avoiding deepcopy for pDescriptorSetPendingAllocation
    local_pDescriptorSetPendingAllocation = (uint32_t*)pDescriptorSetPendingAllocation;
    // Avoiding deepcopy for pDescriptorWriteStartingIndices
    local_pDescriptorWriteStartingIndices = (uint32_t*)pDescriptorWriteStartingIndices;
    local_pendingDescriptorWriteCount = pendingDescriptorWriteCount;
    local_pPendingDescriptorWrites = nullptr;
    if (pPendingDescriptorWrites) {
        local_pPendingDescriptorWrites = (VkWriteDescriptorSet*)pool->alloc(
            ((pendingDescriptorWriteCount)) * sizeof(const VkWriteDescriptorSet));
        for (uint32_t i = 0; i < (uint32_t)((pendingDescriptorWriteCount)); ++i) {
            deepcopy_VkWriteDescriptorSet(
                pool, VK_STRUCTURE_TYPE_MAX_ENUM, pPendingDescriptorWrites + i,
                (VkWriteDescriptorSet*)(local_pPendingDescriptorWrites + i));
        }
    }
    if (local_pPendingDescriptorWrites) {
        for (uint32_t i = 0; i < (uint32_t)((pendingDescriptorWriteCount)); ++i) {
            transform_tohost_VkWriteDescriptorSet(
                sResourceTracker, (VkWriteDescriptorSet*)(local_pPendingDescriptorWrites + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        if (((descriptorPoolCount))) {
            *countPtr += ((descriptorPoolCount)) * 8;
        }
        *countPtr += sizeof(uint32_t);
        if (((descriptorSetCount))) {
            *countPtr += ((descriptorSetCount)) * 8;
        }
        *countPtr += ((descriptorSetCount)) * sizeof(uint64_t);
        *countPtr += ((descriptorSetCount)) * sizeof(uint32_t);
        *countPtr += ((descriptorSetCount)) * sizeof(uint32_t);
        *countPtr += ((descriptorSetCount)) * sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((pendingDescriptorWriteCount)); ++i) {
            count_VkWriteDescriptorSet(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                       (VkWriteDescriptorSet*)(local_pPendingDescriptorWrites + i),
                                       countPtr);
        }
    }
    uint32_t packetSize_vkQueueCommitDescriptorSetUpdatesGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkQueueCommitDescriptorSetUpdatesGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueCommitDescriptorSetUpdatesGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueCommitDescriptorSetUpdatesGOOGLE =
        OP_vkQueueCommitDescriptorSetUpdatesGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueCommitDescriptorSetUpdatesGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueCommitDescriptorSetUpdatesGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_descriptorPoolCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((descriptorPoolCount))) {
        uint8_t* cgen_var_1_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((descriptorPoolCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkDescriptorPool(local_pDescriptorPools[k]);
            memcpy(cgen_var_1_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((descriptorPoolCount));
    }
    memcpy(*streamPtrPtr, (uint32_t*)&local_descriptorSetCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    if (((descriptorSetCount))) {
        uint8_t* cgen_var_2_ptr = (uint8_t*)(*streamPtrPtr);
        for (uint32_t k = 0; k < ((descriptorSetCount)); ++k) {
            uint64_t tmpval = get_host_u64_VkDescriptorSetLayout(local_pSetLayouts[k]);
            memcpy(cgen_var_2_ptr + k * 8, &tmpval, sizeof(uint64_t));
        }
        *streamPtrPtr += 8 * ((descriptorSetCount));
    }
    memcpy(*streamPtrPtr, (uint64_t*)local_pDescriptorSetPoolIds,
           ((descriptorSetCount)) * sizeof(uint64_t));
    *streamPtrPtr += ((descriptorSetCount)) * sizeof(uint64_t);
    memcpy(*streamPtrPtr, (uint32_t*)local_pDescriptorSetWhichPool,
           ((descriptorSetCount)) * sizeof(uint32_t));
    *streamPtrPtr += ((descriptorSetCount)) * sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)local_pDescriptorSetPendingAllocation,
           ((descriptorSetCount)) * sizeof(uint32_t));
    *streamPtrPtr += ((descriptorSetCount)) * sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)local_pDescriptorWriteStartingIndices,
           ((descriptorSetCount)) * sizeof(uint32_t));
    *streamPtrPtr += ((descriptorSetCount)) * sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_pendingDescriptorWriteCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((pendingDescriptorWriteCount)); ++i) {
        reservedmarshal_VkWriteDescriptorSet(
            stream, VK_STRUCTURE_TYPE_MAX_ENUM,
            (VkWriteDescriptorSet*)(local_pPendingDescriptorWrites + i), streamPtrPtr);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueCommitDescriptorSetUpdatesGOOGLE),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkCollectDescriptorPoolIdsGOOGLE(VkDevice device, VkDescriptorPool descriptorPool,
                                                 uint32_t* pPoolIdCount, uint64_t* pPoolIds,
                                                 uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkCollectDescriptorPoolIdsGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkCollectDescriptorPoolIdsGOOGLE(device:%p, descriptorPool:%p, pPoolIdCount:%p, "
        "pPoolIds:%p)",
        device, descriptorPool, pPoolIdCount, pPoolIds);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorPool local_descriptorPool;
    local_device = device;
    local_descriptorPool = descriptorPool;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (pPoolIds) {
            if (pPoolIdCount) {
                *countPtr += (*(pPoolIdCount)) * sizeof(uint64_t);
            }
        }
    }
    uint32_t packetSize_vkCollectDescriptorPoolIdsGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkCollectDescriptorPoolIdsGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkCollectDescriptorPoolIdsGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkCollectDescriptorPoolIdsGOOGLE = OP_vkCollectDescriptorPoolIdsGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkCollectDescriptorPoolIdsGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkCollectDescriptorPoolIdsGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorPool((*&local_descriptorPool));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)pPoolIdCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_2 = (uint64_t)(uintptr_t)pPoolIds;
    memcpy((*streamPtrPtr), &cgen_var_2, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (pPoolIds) {
        memcpy(*streamPtrPtr, (uint64_t*)pPoolIds, (*(pPoolIdCount)) * sizeof(uint64_t));
        *streamPtrPtr += (*(pPoolIdCount)) * sizeof(uint64_t);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkCollectDescriptorPoolIdsGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->read((uint32_t*)pPoolIdCount, sizeof(uint32_t));
    // WARNING PTR CHECK
    uint64_t* check_pPoolIds;
    check_pPoolIds = (uint64_t*)(uintptr_t)stream->getBe64();
    if (pPoolIds) {
        if (!(check_pPoolIds)) {
            fprintf(stderr, "fatal: pPoolIds inconsistent between guest and host\n");
        }
        stream->read((uint64_t*)pPoolIds, (*(pPoolIdCount)) * sizeof(uint64_t));
    }
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkQueueSignalReleaseImageANDROIDAsyncGOOGLE(VkQueue queue,
                                                            uint32_t waitSemaphoreCount,
                                                            const VkSemaphore* pWaitSemaphores,
                                                            VkImage image, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueSignalReleaseImageANDROIDAsyncGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkQueueSignalReleaseImageANDROIDAsyncGOOGLE(queue:%p, waitSemaphoreCount:%d, "
        "pWaitSemaphores:%p, image:%p)",
        queue, waitSemaphoreCount, pWaitSemaphores, image);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_waitSemaphoreCount;
    VkSemaphore* local_pWaitSemaphores;
    VkImage local_image;
    local_queue = queue;
    local_waitSemaphoreCount = waitSemaphoreCount;
    // Avoiding deepcopy for pWaitSemaphores
    local_pWaitSemaphores = (VkSemaphore*)pWaitSemaphores;
    local_image = image;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pWaitSemaphores) {
            if (((waitSemaphoreCount))) {
                *countPtr += ((waitSemaphoreCount)) * 8;
            }
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE =
        OP_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_waitSemaphoreCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_1 = (uint64_t)(uintptr_t)local_pWaitSemaphores;
    memcpy((*streamPtrPtr), &cgen_var_1, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pWaitSemaphores) {
        if (((waitSemaphoreCount))) {
            uint8_t* cgen_var_1_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((waitSemaphoreCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkSemaphore(local_pWaitSemaphores[k]);
                memcpy(cgen_var_1_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((waitSemaphoreCount));
        }
    }
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkImage((*&local_image));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueSignalReleaseImageANDROIDAsyncGOOGLE),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkQueueFlushCommandsFromAuxMemoryGOOGLE(VkQueue queue,
                                                        VkCommandBuffer commandBuffer,
                                                        VkDeviceMemory deviceMemory,
                                                        VkDeviceSize dataOffset,
                                                        VkDeviceSize dataSize, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueFlushCommandsFromAuxMemoryGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkQueueFlushCommandsFromAuxMemoryGOOGLE(queue:%p, commandBuffer:%p, deviceMemory:%p, "
        "dataOffset:%ld, dataSize:%ld)",
        queue, commandBuffer, deviceMemory, dataOffset, dataSize);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    VkCommandBuffer local_commandBuffer;
    VkDeviceMemory local_deviceMemory;
    VkDeviceSize local_dataOffset;
    VkDeviceSize local_dataSize;
    local_queue = queue;
    local_commandBuffer = commandBuffer;
    local_deviceMemory = deviceMemory;
    local_dataOffset = dataOffset;
    local_dataSize = dataSize;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(VkDeviceSize);
        *countPtr += sizeof(VkDeviceSize);
    }
    uint32_t packetSize_vkQueueFlushCommandsFromAuxMemoryGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkQueueFlushCommandsFromAuxMemoryGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueFlushCommandsFromAuxMemoryGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueFlushCommandsFromAuxMemoryGOOGLE =
        OP_vkQueueFlushCommandsFromAuxMemoryGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueFlushCommandsFromAuxMemoryGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueFlushCommandsFromAuxMemoryGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkCommandBuffer((*&local_commandBuffer));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkDeviceMemory((*&local_deviceMemory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_dataOffset, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    memcpy(*streamPtrPtr, (VkDeviceSize*)&local_dataSize, sizeof(VkDeviceSize));
    *streamPtrPtr += sizeof(VkDeviceSize);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueFlushCommandsFromAuxMemoryGOOGLE),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetBlobGOOGLE(VkDevice device, VkDeviceMemory memory, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetBlobGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetBlobGOOGLE(device:%p, memory:%p)", device, memory);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDeviceMemory local_memory;
    local_device = device;
    local_memory = memory;
    sResourceTracker->deviceMemoryTransform_tohost(
        (VkDeviceMemory*)&local_memory, 1, (VkDeviceSize*)nullptr, 0, (VkDeviceSize*)nullptr, 0,
        (uint32_t*)nullptr, 0, (uint32_t*)nullptr, 0);
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkGetBlobGOOGLE = 4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetBlobGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetBlobGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetBlobGOOGLE = OP_vkGetBlobGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetBlobGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetBlobGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDeviceMemory((*&local_memory));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize =
            std::min<size_t>(static_cast<size_t>(packetSize_vkGetBlobGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkGetBlobGOOGLE_VkResult_return = (VkResult)0;
    stream->read(&vkGetBlobGOOGLE_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetBlobGOOGLE_VkResult_return;
}

void VkEncoder::vkUpdateDescriptorSetWithTemplateSized2GOOGLE(
    VkDevice device, VkDescriptorSet descriptorSet,
    VkDescriptorUpdateTemplate descriptorUpdateTemplate, uint32_t imageInfoCount,
    uint32_t bufferInfoCount, uint32_t bufferViewCount, uint32_t inlineUniformBlockCount,
    const uint32_t* pImageInfoEntryIndices, const uint32_t* pBufferInfoEntryIndices,
    const uint32_t* pBufferViewEntryIndices, const VkDescriptorImageInfo* pImageInfos,
    const VkDescriptorBufferInfo* pBufferInfos, const VkBufferView* pBufferViews,
    const uint8_t* pInlineUniformBlockData, uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor,
                         "vkUpdateDescriptorSetWithTemplateSized2GOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG(
        "vkUpdateDescriptorSetWithTemplateSized2GOOGLE(device:%p, descriptorSet:%p, "
        "descriptorUpdateTemplate:%p, imageInfoCount:%d, bufferInfoCount:%d, bufferViewCount:%d, "
        "inlineUniformBlockCount:%d, pImageInfoEntryIndices:%p, pBufferInfoEntryIndices:%p, "
        "pBufferViewEntryIndices:%p, pImageInfos:%p, pBufferInfos:%p, pBufferViews:%p, "
        "pInlineUniformBlockData:%p)",
        device, descriptorSet, descriptorUpdateTemplate, imageInfoCount, bufferInfoCount,
        bufferViewCount, inlineUniformBlockCount, pImageInfoEntryIndices, pBufferInfoEntryIndices,
        pBufferViewEntryIndices, pImageInfos, pBufferInfos, pBufferViews, pInlineUniformBlockData);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkDescriptorSet local_descriptorSet;
    VkDescriptorUpdateTemplate local_descriptorUpdateTemplate;
    uint32_t local_imageInfoCount;
    uint32_t local_bufferInfoCount;
    uint32_t local_bufferViewCount;
    uint32_t local_inlineUniformBlockCount;
    uint32_t* local_pImageInfoEntryIndices;
    uint32_t* local_pBufferInfoEntryIndices;
    uint32_t* local_pBufferViewEntryIndices;
    VkDescriptorImageInfo* local_pImageInfos;
    VkDescriptorBufferInfo* local_pBufferInfos;
    VkBufferView* local_pBufferViews;
    uint8_t* local_pInlineUniformBlockData;
    local_device = device;
    local_descriptorSet = descriptorSet;
    local_descriptorUpdateTemplate = descriptorUpdateTemplate;
    local_imageInfoCount = imageInfoCount;
    local_bufferInfoCount = bufferInfoCount;
    local_bufferViewCount = bufferViewCount;
    local_inlineUniformBlockCount = inlineUniformBlockCount;
    // Avoiding deepcopy for pImageInfoEntryIndices
    local_pImageInfoEntryIndices = (uint32_t*)pImageInfoEntryIndices;
    // Avoiding deepcopy for pBufferInfoEntryIndices
    local_pBufferInfoEntryIndices = (uint32_t*)pBufferInfoEntryIndices;
    // Avoiding deepcopy for pBufferViewEntryIndices
    local_pBufferViewEntryIndices = (uint32_t*)pBufferViewEntryIndices;
    local_pImageInfos = nullptr;
    if (pImageInfos) {
        local_pImageInfos = (VkDescriptorImageInfo*)pool->alloc(
            ((imageInfoCount)) * sizeof(const VkDescriptorImageInfo));
        for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
            deepcopy_VkDescriptorImageInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pImageInfos + i,
                                           (VkDescriptorImageInfo*)(local_pImageInfos + i));
        }
    }
    local_pBufferInfos = nullptr;
    if (pBufferInfos) {
        local_pBufferInfos = (VkDescriptorBufferInfo*)pool->alloc(
            ((bufferInfoCount)) * sizeof(const VkDescriptorBufferInfo));
        for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
            deepcopy_VkDescriptorBufferInfo(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pBufferInfos + i,
                                            (VkDescriptorBufferInfo*)(local_pBufferInfos + i));
        }
    }
    // Avoiding deepcopy for pBufferViews
    local_pBufferViews = (VkBufferView*)pBufferViews;
    // Avoiding deepcopy for pInlineUniformBlockData
    local_pInlineUniformBlockData = (uint8_t*)pInlineUniformBlockData;
    if (local_pImageInfos) {
        for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
            transform_tohost_VkDescriptorImageInfo(sResourceTracker,
                                                   (VkDescriptorImageInfo*)(local_pImageInfos + i));
        }
    }
    if (local_pBufferInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
            transform_tohost_VkDescriptorBufferInfo(
                sResourceTracker, (VkDescriptorBufferInfo*)(local_pBufferInfos + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        uint64_t cgen_var_2;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        *countPtr += sizeof(uint32_t);
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pImageInfoEntryIndices) {
            *countPtr += ((imageInfoCount)) * sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferInfoEntryIndices) {
            *countPtr += ((bufferInfoCount)) * sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferViewEntryIndices) {
            *countPtr += ((bufferViewCount)) * sizeof(uint32_t);
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pImageInfos) {
            for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
                count_VkDescriptorImageInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                            (VkDescriptorImageInfo*)(local_pImageInfos + i),
                                            countPtr);
            }
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferInfos) {
            for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
                count_VkDescriptorBufferInfo(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                             (VkDescriptorBufferInfo*)(local_pBufferInfos + i),
                                             countPtr);
            }
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pBufferViews) {
            if (((bufferViewCount))) {
                *countPtr += ((bufferViewCount)) * 8;
            }
        }
        // WARNING PTR CHECK
        *countPtr += 8;
        if (local_pInlineUniformBlockData) {
            *countPtr += ((inlineUniformBlockCount)) * sizeof(uint8_t);
        }
    }
    uint32_t packetSize_vkUpdateDescriptorSetWithTemplateSized2GOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize =
        std::make_optional(packetSize_vkUpdateDescriptorSetWithTemplateSized2GOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkUpdateDescriptorSetWithTemplateSized2GOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkUpdateDescriptorSetWithTemplateSized2GOOGLE =
        OP_vkUpdateDescriptorSetWithTemplateSized2GOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkUpdateDescriptorSetWithTemplateSized2GOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkUpdateDescriptorSetWithTemplateSized2GOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkDescriptorSet((*&local_descriptorSet));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_2;
    *&cgen_var_2 = get_host_u64_VkDescriptorUpdateTemplate((*&local_descriptorUpdateTemplate));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_2, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_imageInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bufferInfoCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_bufferViewCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    memcpy(*streamPtrPtr, (uint32_t*)&local_inlineUniformBlockCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    // WARNING PTR CHECK
    uint64_t cgen_var_3 = (uint64_t)(uintptr_t)local_pImageInfoEntryIndices;
    memcpy((*streamPtrPtr), &cgen_var_3, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pImageInfoEntryIndices) {
        memcpy(*streamPtrPtr, (uint32_t*)local_pImageInfoEntryIndices,
               ((imageInfoCount)) * sizeof(uint32_t));
        *streamPtrPtr += ((imageInfoCount)) * sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_4 = (uint64_t)(uintptr_t)local_pBufferInfoEntryIndices;
    memcpy((*streamPtrPtr), &cgen_var_4, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferInfoEntryIndices) {
        memcpy(*streamPtrPtr, (uint32_t*)local_pBufferInfoEntryIndices,
               ((bufferInfoCount)) * sizeof(uint32_t));
        *streamPtrPtr += ((bufferInfoCount)) * sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_5 = (uint64_t)(uintptr_t)local_pBufferViewEntryIndices;
    memcpy((*streamPtrPtr), &cgen_var_5, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferViewEntryIndices) {
        memcpy(*streamPtrPtr, (uint32_t*)local_pBufferViewEntryIndices,
               ((bufferViewCount)) * sizeof(uint32_t));
        *streamPtrPtr += ((bufferViewCount)) * sizeof(uint32_t);
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_6 = (uint64_t)(uintptr_t)local_pImageInfos;
    memcpy((*streamPtrPtr), &cgen_var_6, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pImageInfos) {
        for (uint32_t i = 0; i < (uint32_t)((imageInfoCount)); ++i) {
            reservedmarshal_VkDescriptorImageInfo(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                                  (VkDescriptorImageInfo*)(local_pImageInfos + i),
                                                  streamPtrPtr);
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_7 = (uint64_t)(uintptr_t)local_pBufferInfos;
    memcpy((*streamPtrPtr), &cgen_var_7, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferInfos) {
        for (uint32_t i = 0; i < (uint32_t)((bufferInfoCount)); ++i) {
            reservedmarshal_VkDescriptorBufferInfo(
                stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                (VkDescriptorBufferInfo*)(local_pBufferInfos + i), streamPtrPtr);
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_8 = (uint64_t)(uintptr_t)local_pBufferViews;
    memcpy((*streamPtrPtr), &cgen_var_8, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pBufferViews) {
        if (((bufferViewCount))) {
            uint8_t* cgen_var_8_0_ptr = (uint8_t*)(*streamPtrPtr);
            for (uint32_t k = 0; k < ((bufferViewCount)); ++k) {
                uint64_t tmpval = get_host_u64_VkBufferView(local_pBufferViews[k]);
                memcpy(cgen_var_8_0_ptr + k * 8, &tmpval, sizeof(uint64_t));
            }
            *streamPtrPtr += 8 * ((bufferViewCount));
        }
    }
    // WARNING PTR CHECK
    uint64_t cgen_var_9 = (uint64_t)(uintptr_t)local_pInlineUniformBlockData;
    memcpy((*streamPtrPtr), &cgen_var_9, 8);
    gfxstream::guest::Stream::toBe64((uint8_t*)(*streamPtrPtr));
    *streamPtrPtr += 8;
    if (local_pInlineUniformBlockData) {
        memcpy(*streamPtrPtr, (uint8_t*)local_pInlineUniformBlockData,
               ((inlineUniformBlockCount)) * sizeof(uint8_t));
        *streamPtrPtr += ((inlineUniformBlockCount)) * sizeof(uint8_t);
    }
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkUpdateDescriptorSetWithTemplateSized2GOOGLE),
            kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

void VkEncoder::vkQueueSubmitAsync2GOOGLE(VkQueue queue, uint32_t submitCount,
                                          const VkSubmitInfo2* pSubmits, VkFence fence,
                                          uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkQueueSubmitAsync2GOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkQueueSubmitAsync2GOOGLE(queue:%p, submitCount:%d, pSubmits:%p, fence:%p)",
                      queue, submitCount, pSubmits, fence);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkQueue local_queue;
    uint32_t local_submitCount;
    VkSubmitInfo2* local_pSubmits;
    VkFence local_fence;
    local_queue = queue;
    local_submitCount = submitCount;
    local_pSubmits = nullptr;
    if (pSubmits) {
        local_pSubmits = (VkSubmitInfo2*)pool->alloc(((submitCount)) * sizeof(const VkSubmitInfo2));
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            deepcopy_VkSubmitInfo2(pool, VK_STRUCTURE_TYPE_MAX_ENUM, pSubmits + i,
                                   (VkSubmitInfo2*)(local_pSubmits + i));
        }
    }
    local_fence = fence;
    if (local_pSubmits) {
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            transform_tohost_VkSubmitInfo2(sResourceTracker, (VkSubmitInfo2*)(local_pSubmits + i));
        }
    }
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint32_t);
        for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
            count_VkSubmitInfo2(sFeatureBits, VK_STRUCTURE_TYPE_MAX_ENUM,
                                (VkSubmitInfo2*)(local_pSubmits + i), countPtr);
        }
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
    }
    uint32_t packetSize_vkQueueSubmitAsync2GOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkQueueSubmitAsync2GOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkQueueSubmitAsync2GOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkQueueSubmitAsync2GOOGLE = OP_vkQueueSubmitAsync2GOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkQueueSubmitAsync2GOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkQueueSubmitAsync2GOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkQueue((*&local_queue));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint32_t*)&local_submitCount, sizeof(uint32_t));
    *streamPtrPtr += sizeof(uint32_t);
    for (uint32_t i = 0; i < (uint32_t)((submitCount)); ++i) {
        reservedmarshal_VkSubmitInfo2(stream, VK_STRUCTURE_TYPE_MAX_ENUM,
                                      (VkSubmitInfo2*)(local_pSubmits + i), streamPtrPtr);
    }
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkFence((*&local_fence));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkQueueSubmitAsync2GOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    stream->flush();
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
}

VkResult VkEncoder::vkGetSemaphoreGOOGLE(VkDevice device, VkSemaphore semaphore, uint64_t syncId,
                                         uint32_t doLock) {
    std::optional<uint32_t> healthMonitorAnnotation_seqno = std::nullopt;
    std::optional<uint32_t> healthMonitorAnnotation_packetSize = std::nullopt;
    std::vector<uint8_t> healthMonitorAnnotation_packetContents;

    auto watchdog =
        WATCHDOG_BUILDER(mHealthMonitor, "vkGetSemaphoreGOOGLE in VkEncoder")
            .setOnHangCallback([&]() {
                auto annotations = std::make_unique<EventHangMetadata::HangAnnotations>();
                if (healthMonitorAnnotation_seqno) {
                    annotations->insert(
                        {{"seqno", std::to_string(healthMonitorAnnotation_seqno.value())}});
                }
                if (healthMonitorAnnotation_packetSize) {
                    annotations->insert(
                        {{"packetSize",
                          std::to_string(healthMonitorAnnotation_packetSize.value())}});
                }
                if (!healthMonitorAnnotation_packetContents.empty()) {
                    annotations->insert(
                        {{"packetContents",
                          getPacketContents(&healthMonitorAnnotation_packetContents[0],
                                            healthMonitorAnnotation_packetContents.size())}});
                }
                return std::move(annotations);
            })
            .build();

    ENCODER_DEBUG_LOG("vkGetSemaphoreGOOGLE(device:%p, semaphore:%p, syncId:%ld)", device,
                      semaphore, syncId);
    (void)doLock;
    bool queueSubmitWithCommandsEnabled =
        sFeatureBits & VULKAN_STREAM_FEATURE_QUEUE_SUBMIT_WITH_COMMANDS_BIT;
    if (!queueSubmitWithCommandsEnabled && doLock) this->lock();
    auto stream = mImpl->stream();
    auto pool = mImpl->pool();
    VkDevice local_device;
    VkSemaphore local_semaphore;
    uint64_t local_syncId;
    local_device = device;
    local_semaphore = semaphore;
    local_syncId = syncId;
    size_t count = 0;
    size_t* countPtr = &count;
    {
        uint64_t cgen_var_0;
        *countPtr += 1 * 8;
        uint64_t cgen_var_1;
        *countPtr += 1 * 8;
        *countPtr += sizeof(uint64_t);
    }
    uint32_t packetSize_vkGetSemaphoreGOOGLE =
        4 + 4 + (queueSubmitWithCommandsEnabled ? 4 : 0) + count;
    healthMonitorAnnotation_packetSize = std::make_optional(packetSize_vkGetSemaphoreGOOGLE);
    uint8_t* streamPtr = stream->reserve(packetSize_vkGetSemaphoreGOOGLE);
    uint8_t* packetBeginPtr = streamPtr;
    uint8_t** streamPtrPtr = &streamPtr;
    uint32_t opcode_vkGetSemaphoreGOOGLE = OP_vkGetSemaphoreGOOGLE;
    uint32_t seqno;
    if (queueSubmitWithCommandsEnabled) seqno = ResourceTracker::nextSeqno();
    healthMonitorAnnotation_seqno = std::make_optional(seqno);
    memcpy(streamPtr, &opcode_vkGetSemaphoreGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    memcpy(streamPtr, &packetSize_vkGetSemaphoreGOOGLE, sizeof(uint32_t));
    streamPtr += sizeof(uint32_t);
    if (queueSubmitWithCommandsEnabled) {
        memcpy(streamPtr, &seqno, sizeof(uint32_t));
        streamPtr += sizeof(uint32_t);
    }
    uint64_t cgen_var_0;
    *&cgen_var_0 = get_host_u64_VkDevice((*&local_device));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_0, 1 * 8);
    *streamPtrPtr += 1 * 8;
    uint64_t cgen_var_1;
    *&cgen_var_1 = get_host_u64_VkSemaphore((*&local_semaphore));
    memcpy(*streamPtrPtr, (uint64_t*)&cgen_var_1, 1 * 8);
    *streamPtrPtr += 1 * 8;
    memcpy(*streamPtrPtr, (uint64_t*)&local_syncId, sizeof(uint64_t));
    *streamPtrPtr += sizeof(uint64_t);
    if (watchdog) {
        size_t watchdogBufSize = std::min<size_t>(
            static_cast<size_t>(packetSize_vkGetSemaphoreGOOGLE), kWatchdogBufferMax);
        healthMonitorAnnotation_packetContents.resize(watchdogBufSize);
        memcpy(&healthMonitorAnnotation_packetContents[0], packetBeginPtr, watchdogBufSize);
    }
    VkResult vkGetSemaphoreGOOGLE_VkResult_return = (VkResult)0;
    stream->read(&vkGetSemaphoreGOOGLE_VkResult_return, sizeof(VkResult));
    ++encodeCount;
    if (0 == encodeCount % POOL_CLEAR_INTERVAL) {
        pool->freeAll();
        stream->clearPool();
    }
    if (!queueSubmitWithCommandsEnabled && doLock) this->unlock();
    return vkGetSemaphoreGOOGLE_VkResult_return;
}

#endif
}  // namespace vk
}  // namespace gfxstream
