/*
 * Copyright (c) 2015-2026 The Khronos Group Inc.
 * Copyright (c) 2015-2026 Valve Corporation
 * Copyright (c) 2015-2026 LunarG, Inc.
 * Copyright (c) 2015-2026 Google, Inc.
 * Modifications Copyright (C) 2020-2022 Advanced Micro Devices, Inc. All rights reserved.
 * Modifications Copyright (C) 2021 ARM, Inc. All rights reserved.
 *
 * 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
 */

#include <vulkan/vulkan_core.h>
#include <cstdint>
#include "utils/cast_utils.h"
#include "../framework/layer_validation_tests.h"
#include "../framework/pipeline_helper.h"
#include "../framework/ray_tracing_objects.h"

class NegativeDescriptorBuffer : public DescriptorBufferTest {};

TEST_F(NegativeDescriptorBuffer, SetLayout) {
    TEST_DESCRIPTION("Descriptor buffer set layout tests.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());

    {
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC, 1, VK_SHADER_STAGE_FRAGMENT_BIT,
                                                   nullptr};
        const VkDescriptorSetLayoutCreateFlags flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
        const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
        VkDescriptorSetLayout dsl;
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutCreateInfo-flags-08000");
        vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
        m_errorMonitor->VerifyFound();
    }
    {
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC, 1, VK_SHADER_STAGE_FRAGMENT_BIT,
                                                   nullptr};
        const VkDescriptorSetLayoutCreateFlags flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
        const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
        VkDescriptorSetLayout dsl;
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutCreateInfo-flags-08000");
        vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
        m_errorMonitor->VerifyFound();
    }
    {
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 1, VK_SHADER_STAGE_FRAGMENT_BIT, nullptr};
        const VkDescriptorSetLayoutCreateFlags flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT;
        const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
        VkDescriptorSetLayout dsl;
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutCreateInfo-flags-08001");
        vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
        m_errorMonitor->VerifyFound();
    }
    {
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 1, VK_SHADER_STAGE_FRAGMENT_BIT, nullptr};
        const VkDescriptorSetLayoutCreateFlags flags =
            VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT | VK_DESCRIPTOR_SET_LAYOUT_CREATE_UPDATE_AFTER_BIND_POOL_BIT;
        const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
        VkDescriptorSetLayout dsl;
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutCreateInfo-flags-08002");
        vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
        m_errorMonitor->VerifyFound();
    }
    {
        VkSampler samplers[2] = {sampler, sampler};
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 1, VK_SHADER_STAGE_FRAGMENT_BIT, samplers};
        const VkDescriptorSetLayoutCreateFlags flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                                       VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT;
        const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
        VkDescriptorSetLayout dsl;
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutBinding-flags-08005");
        vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
        m_errorMonitor->VerifyFound();
    }
    {
        VkSampler samplers[2] = {sampler, sampler};
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLER, 2, VK_SHADER_STAGE_FRAGMENT_BIT, samplers};
        const VkDescriptorSetLayoutCreateFlags flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                                       VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT;
        const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
        VkDescriptorSetLayout dsl;
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutBinding-flags-08006");
        vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
        m_errorMonitor->VerifyFound();
    }
    {
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, nullptr};
        const VkDescriptorSetLayoutCreateFlags flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                                       VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT;
        const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
        VkDescriptorSetLayout dsl;
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutBinding-flags-08007");
        vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
        m_errorMonitor->VerifyFound();
    }

    {
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, nullptr};
        vkt::DescriptorSetLayout dsl1(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
        vkt::DescriptorSetLayout dsl2(*m_device, binding, 0);

        VkPipelineLayout pipeline_layout;
        const std::array<VkDescriptorSetLayout, 2> set_layouts{dsl1, dsl2};
        VkPipelineLayoutCreateInfo plci = vku::InitStructHelper();
        plci.setLayoutCount = size32(set_layouts);
        plci.pSetLayouts = set_layouts.data();

        m_errorMonitor->SetDesiredError("VUID-VkPipelineLayoutCreateInfo-pSetLayouts-08008");
        vk::CreatePipelineLayout(device(), &plci, NULL, &pipeline_layout);
        m_errorMonitor->VerifyFound();
    }

    {
        const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, nullptr};
        vkt::DescriptorSetLayout dsl1(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);

        VkDescriptorPoolSize pool_size = {binding.descriptorType, binding.descriptorCount};
        const auto dspci =
            vku::InitStruct<VkDescriptorPoolCreateInfo>(nullptr, static_cast<VkDescriptorPoolCreateFlags>(0), 1U, 1U, &pool_size);
        vkt::DescriptorPool pool(*m_device, dspci);

        VkDescriptorSet ds = VK_NULL_HANDLE;
        const auto alloc_info = vku::InitStruct<VkDescriptorSetAllocateInfo>(nullptr, pool.handle(), 1U, &dsl1.handle());

        m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetAllocateInfo-pSetLayouts-08009");
        vk::AllocateDescriptorSets(device(), &alloc_info, &ds);
        m_errorMonitor->VerifyFound();
    }
}

TEST_F(NegativeDescriptorBuffer, GetSupportSetLayout) {
    TEST_DESCRIPTION("call vkGetDescriptorSetLayoutSupport on Descriptor buffer set layout tests.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());
    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC, 1, VK_SHADER_STAGE_FRAGMENT_BIT,
                                               nullptr};
    const VkDescriptorSetLayoutCreateFlags flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
    VkDescriptorSetLayoutSupport support = vku::InitStructHelper();
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutCreateInfo-flags-08000");
    vk::GetDescriptorSetLayoutSupport(device(), &dslci, &support);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, SetLayoutInlineUniformBlockEXT) {
    TEST_DESCRIPTION("Descriptor buffer set layout tests.");
    AddRequiredExtensions(VK_EXT_INLINE_UNIFORM_BLOCK_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::inlineUniformBlock);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());

    VkPhysicalDeviceInlineUniformBlockPropertiesEXT inlineUniformProps = vku::InitStructHelper();
    GetPhysicalDeviceProperties2(inlineUniformProps);

    const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_INLINE_UNIFORM_BLOCK,
                                               inlineUniformProps.maxInlineUniformBlockSize + 4, VK_SHADER_STAGE_FRAGMENT_BIT,
                                               nullptr};
    const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, 0U, 1U, &binding);
    VkDescriptorSetLayout dsl;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutBinding-descriptorType-08004");
    vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, SetLayoutMutableDescriptorEXT) {
    TEST_DESCRIPTION("Descriptor buffer set layout tests.");
    AddRequiredExtensions(VK_EXT_MUTABLE_DESCRIPTOR_TYPE_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::mutableDescriptorType);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());

    const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 1, VK_SHADER_STAGE_FRAGMENT_BIT, nullptr};
    const VkDescriptorSetLayoutCreateFlags flags =
        VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT | VK_DESCRIPTOR_SET_LAYOUT_CREATE_HOST_ONLY_POOL_BIT_EXT;
    const auto dslci = vku::InitStruct<VkDescriptorSetLayoutCreateInfo>(nullptr, flags, 1U, &binding);
    VkDescriptorSetLayout dsl;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorSetLayoutCreateInfo-flags-08003");
    vk::CreateDescriptorSetLayout(device(), &dslci, nullptr, &dsl);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, NotEnabled) {
    TEST_DESCRIPTION("Tests for when descriptor buffer is not enabled");
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);

    RETURN_IF_SKIP(Init());
    GetPhysicalDeviceProperties2(descriptor_buffer_properties);

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());

    const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler.handle()};
    vkt::DescriptorSetLayout dsl(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    {
        VkDeviceSize size;

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutSizeEXT-None-08011");
        vk::GetDescriptorSetLayoutSizeEXT(device(), dsl, &size);
        m_errorMonitor->VerifyFound();
    }

    {
        VkDeviceSize offset;

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutBindingOffsetEXT-None-08013");
        vk::GetDescriptorSetLayoutBindingOffsetEXT(device(), dsl, 0, &offset);
        m_errorMonitor->VerifyFound();
    }

    {
        uint8_t buffer[128];
        VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
        dgi.type = VK_DESCRIPTOR_TYPE_SAMPLER;
        dgi.data.pSampler = &sampler.handle();

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorEXT-None-08015");
        vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.samplerDescriptorSize, &buffer);
        m_errorMonitor->VerifyFound();
    }

    {
        vkt::DescriptorSetLayout embedded_dsl(*m_device, binding,
                                              VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                                  VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT);

        vkt::PipelineLayout pipeline_layout(*m_device, {&embedded_dsl});

        m_command_buffer.Begin();
        m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBufferEmbeddedSamplersEXT-None-08068");
        vk::CmdBindDescriptorBufferEmbeddedSamplersEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0);
        m_errorMonitor->VerifyFound();

        m_command_buffer.End();
    }
}

TEST_F(NegativeDescriptorBuffer, NotEnabledBufferDeviceAddress) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);
    AddRequiredExtensions(VK_KHR_BUFFER_DEVICE_ADDRESS_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::bufferDeviceAddress);

    RETURN_IF_SKIP(Init());

    vkt::Buffer d_buffer(*m_device, 4096,
                         VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT,
                         vkt::device_address);

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = d_buffer.Address();
    dbbi.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;

    d_buffer.Memory().Destroy();

    m_command_buffer.Begin();
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-None-08047");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();

    m_command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, NotEnabledGetBufferOpaqueCaptureDescriptorDataEXT) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);

    RETURN_IF_SKIP(Init());

    uint8_t data[256];
    vkt::Buffer temp_buffer(*m_device, 4096, VK_BUFFER_USAGE_TRANSFER_SRC_BIT, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT);

    VkBufferCaptureDescriptorDataInfoEXT bcddi = vku::InitStructHelper();
    bcddi.buffer = temp_buffer;

    m_errorMonitor->SetDesiredError("VUID-vkGetBufferOpaqueCaptureDescriptorDataEXT-None-08072");
    m_errorMonitor->SetDesiredError("VUID-VkBufferCaptureDescriptorDataInfoEXT-buffer-08075");
    vk::GetBufferOpaqueCaptureDescriptorDataEXT(device(), &bcddi, &data);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, NotEnabledGetImageOpaqueCaptureDescriptorDataEXT) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);

    RETURN_IF_SKIP(Init());

    uint8_t data[256];

    VkImageCreateInfo image_create_info = vku::InitStructHelper();
    image_create_info.imageType = VK_IMAGE_TYPE_2D;
    image_create_info.extent = {128, 128, 1};
    image_create_info.mipLevels = 1;
    image_create_info.arrayLayers = 1;
    image_create_info.samples = VK_SAMPLE_COUNT_1_BIT;
    image_create_info.tiling = VK_IMAGE_TILING_OPTIMAL;
    image_create_info.format = VK_FORMAT_D32_SFLOAT;
    image_create_info.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
    vkt::Image image(*m_device, image_create_info, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT);

    VkImageCaptureDescriptorDataInfoEXT icddi = vku::InitStructHelper();
    icddi.image = image;

    m_errorMonitor->SetDesiredError("VUID-vkGetImageOpaqueCaptureDescriptorDataEXT-None-08076");
    m_errorMonitor->SetDesiredError("VUID-VkImageCaptureDescriptorDataInfoEXT-image-08079");
    vk::GetImageOpaqueCaptureDescriptorDataEXT(device(), &icddi, &data);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, NotEnabledGetImageViewOpaqueCaptureDescriptorDataEXT) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);

    RETURN_IF_SKIP(Init());
    uint8_t data[256];

    VkImageCreateInfo image_create_info = vku::InitStructHelper();
    image_create_info.imageType = VK_IMAGE_TYPE_2D;
    image_create_info.extent = {128, 128, 1};
    image_create_info.mipLevels = 1;
    image_create_info.arrayLayers = 1;
    image_create_info.samples = VK_SAMPLE_COUNT_1_BIT;
    image_create_info.tiling = VK_IMAGE_TILING_OPTIMAL;
    image_create_info.format = VK_FORMAT_D32_SFLOAT;
    image_create_info.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
    vkt::Image image(*m_device, image_create_info, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT);

    // missing VK_IMAGE_VIEW_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
    vkt::ImageView dsv = image.CreateView(VK_IMAGE_ASPECT_DEPTH_BIT);

    VkImageViewCaptureDescriptorDataInfoEXT icddi = vku::InitStructHelper();
    icddi.imageView = dsv;

    m_errorMonitor->SetDesiredError("VUID-vkGetImageViewOpaqueCaptureDescriptorDataEXT-None-08080");
    m_errorMonitor->SetDesiredError("VUID-VkImageViewCaptureDescriptorDataInfoEXT-imageView-08083");
    vk::GetImageViewOpaqueCaptureDescriptorDataEXT(device(), &icddi, &data);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, NotEnabledGetSamplerOpaqueCaptureDescriptorDataEXT) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);

    RETURN_IF_SKIP(Init());

    uint8_t data[256];

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    VkSamplerCaptureDescriptorDataInfoEXT scddi = vku::InitStructHelper();
    scddi.sampler = sampler;

    m_errorMonitor->SetDesiredError("VUID-vkGetSamplerOpaqueCaptureDescriptorDataEXT-None-08084");
    m_errorMonitor->SetDesiredError("VUID-VkSamplerCaptureDescriptorDataInfoEXT-sampler-08087");
    vk::GetSamplerOpaqueCaptureDescriptorDataEXT(device(), &scddi, &data);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, NotEnabledGetAccelerationStructureOpaqueCaptureDescriptorDataEXT) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);
    AddRequiredExtensions(VK_KHR_BUFFER_DEVICE_ADDRESS_EXTENSION_NAME);
    AddRequiredExtensions(VK_KHR_ACCELERATION_STRUCTURE_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::bufferDeviceAddress);
    AddRequiredFeature(vkt::Feature::accelerationStructure);

    RETURN_IF_SKIP(Init());

    auto blas = vkt::as::blueprint::AccelStructSimpleOnDeviceBottomLevel(*m_device, 4096);
    blas->Create();

    uint8_t data[256];

    VkAccelerationStructureCaptureDescriptorDataInfoEXT ascddi = vku::InitStructHelper();
    ascddi.accelerationStructure = blas->handle();

    m_errorMonitor->SetDesiredError("VUID-vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT-None-08088");
    m_errorMonitor->SetDesiredError("VUID-VkAccelerationStructureCaptureDescriptorDataInfoEXT-accelerationStructure-08091");
    vk::GetAccelerationStructureOpaqueCaptureDescriptorDataEXT(device(), &ascddi, &data);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, NotEnabledDescriptorBufferCaptureReplay) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);
    AddRequiredExtensions(VK_KHR_BUFFER_DEVICE_ADDRESS_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::bufferDeviceAddress);

    RETURN_IF_SKIP(Init());
    GetPhysicalDeviceProperties2(descriptor_buffer_properties);

    uint32_t data[128];
    const auto ocddci = vku::InitStruct<VkOpaqueCaptureDescriptorDataCreateInfoEXT>(nullptr, &data);

    {
        VkBufferCreateInfo buffer_ci = vku::InitStructHelper();
        buffer_ci.size = 4096;
        buffer_ci.flags = VK_BUFFER_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        buffer_ci.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;

        buffer_ci.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
        CreateBufferTest(buffer_ci, "VUID-VkBufferCreateInfo-flags-08099");

        buffer_ci.flags = 0;

        if (descriptor_buffer_properties.bufferlessPushDescriptors) {
            m_errorMonitor->SetDesiredError("VUID-VkBufferCreateInfo-usage-08102");
        }
        buffer_ci.usage =
            VK_BUFFER_USAGE_PUSH_DESCRIPTORS_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
        CreateBufferTest(buffer_ci, "VUID-VkBufferCreateInfo-usage-08101");

        buffer_ci.pNext = &ocddci;
        buffer_ci.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
        CreateBufferTest(buffer_ci, "VUID-VkBufferCreateInfo-pNext-08100");
    }

    {
        VkImageCreateInfo image_create_info = vku::InitStructHelper();
        image_create_info.flags |= VK_IMAGE_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        image_create_info.imageType = VK_IMAGE_TYPE_2D;
        image_create_info.extent = {128, 128, 1};
        image_create_info.mipLevels = 1;
        image_create_info.arrayLayers = 1;
        image_create_info.samples = VK_SAMPLE_COUNT_1_BIT;
        image_create_info.tiling = VK_IMAGE_TILING_OPTIMAL;
        image_create_info.format = VK_FORMAT_D32_SFLOAT;
        image_create_info.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
        image_create_info.pNext = &ocddci;
        CreateImageTest(image_create_info, "VUID-VkImageCreateInfo-flags-08104");

        image_create_info.pNext = &ocddci;
        image_create_info.flags &= ~VK_IMAGE_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        CreateImageTest(image_create_info, "VUID-VkImageCreateInfo-pNext-08105");
    }

    {
        vkt::Image temp_image(*m_device, 64, 64, VK_FORMAT_D32_SFLOAT, VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT);

        VkImageViewCreateInfo dsvci = vku::InitStructHelper();
        dsvci.flags |= VK_IMAGE_VIEW_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        dsvci.image = temp_image;
        dsvci.viewType = VK_IMAGE_VIEW_TYPE_2D;
        dsvci.format = VK_FORMAT_D32_SFLOAT;
        dsvci.subresourceRange = {VK_IMAGE_ASPECT_DEPTH_BIT, 0, 1, 0, 1};
        CreateImageViewTest(dsvci, "VUID-VkImageViewCreateInfo-flags-08106");

        dsvci.pNext = &ocddci;
        dsvci.flags &= ~VK_IMAGE_VIEW_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        CreateImageViewTest(dsvci, "VUID-VkImageViewCreateInfo-pNext-08107");
    }

    {
        auto sampler_ci = SafeSaneSamplerCreateInfo();
        sampler_ci.flags |= VK_SAMPLER_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;

        CreateSamplerTest(sampler_ci, "VUID-VkSamplerCreateInfo-flags-08110");

        sampler_ci.pNext = &ocddci;
        sampler_ci.flags &= ~VK_SAMPLER_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        CreateSamplerTest(sampler_ci, "VUID-VkSamplerCreateInfo-pNext-08111");
    }
}

TEST_F(NegativeDescriptorBuffer, NotEnabledDescriptorBufferCaptureReplayAS) {
    SetTargetApiVersion(VK_API_VERSION_1_2);
    AddRequiredExtensions(VK_EXT_DESCRIPTOR_BUFFER_EXTENSION_NAME);
    AddRequiredExtensions(VK_KHR_BUFFER_DEVICE_ADDRESS_EXTENSION_NAME);
    AddRequiredExtensions(VK_KHR_ACCELERATION_STRUCTURE_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::bufferDeviceAddress);
    AddRequiredFeature(vkt::Feature::accelerationStructure);

    RETURN_IF_SKIP(Init());

    uint32_t data[128];
    const auto ocddci = vku::InitStruct<VkOpaqueCaptureDescriptorDataCreateInfoEXT>(nullptr, &data);

    vkt::Buffer as_buffer(*m_device, 4096, VK_BUFFER_USAGE_ACCELERATION_STRUCTURE_STORAGE_BIT_KHR, vkt::device_address);

    VkAccelerationStructureKHR as;
    VkAccelerationStructureCreateInfoKHR asci = vku::InitStructHelper();
    asci.createFlags = VK_ACCELERATION_STRUCTURE_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
    asci.buffer = as_buffer;

    m_errorMonitor->SetDesiredError("VUID-VkAccelerationStructureCreateInfoKHR-createFlags-08108");
    vk::CreateAccelerationStructureKHR(device(), &asci, NULL, &as);
    m_errorMonitor->VerifyFound();

    asci.pNext = &ocddci;
    asci.createFlags = 0;
    m_errorMonitor->SetDesiredError("VUID-VkAccelerationStructureCreateInfoKHR-pNext-08109");
    vk::CreateAccelerationStructureKHR(device(), &asci, NULL, &as);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BindWithNoValidUsageFlags) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());
    m_command_buffer.Begin();

    vkt::Buffer d_buffer(*m_device, 4096, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);

    VkDescriptorBufferBindingInfoEXT binding_info = vku::InitStructHelper();
    binding_info.address = d_buffer.Address();
    binding_info.usage = VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-usage-10998");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-pBindingInfos-08055");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &binding_info);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BufferlessPushDescriptorsOff) {
    TEST_DESCRIPTION("When bufferlessPushDescriptors is not supported.");
    AddRequiredFeature(vkt::Feature::descriptorBufferPushDescriptors);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer(&kDisableMessageLimit));

    if (descriptor_buffer_properties.bufferlessPushDescriptors) {
        GTEST_SKIP() << "bufferlessPushDescriptors is supported";
    }

    m_command_buffer.Begin();

    vkt::Buffer d_buffer(*m_device, 4096,
                         VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT |
                             VK_BUFFER_USAGE_PUSH_DESCRIPTORS_DESCRIPTOR_BUFFER_BIT_EXT,
                         vkt::device_address);

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = d_buffer.Address();
    dbbi.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT |
                 VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT | VK_BUFFER_USAGE_PUSH_DESCRIPTORS_DESCRIPTOR_BUFFER_BIT_EXT;

    std::vector<VkDescriptorBufferBindingInfoEXT> binding_infos;
    for (uint32_t i = 0; i < descriptor_buffer_properties.maxDescriptorBufferBindings + 1; i++) {
        binding_infos.push_back(dbbi);
    }

    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-maxSamplerDescriptorBufferBindings-08048");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-maxResourceDescriptorBufferBindings-08049");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-None-08050");
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-bufferlessPushDescriptors-08056",
                                    descriptor_buffer_properties.maxDescriptorBufferBindings + 1);
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-bufferCount-08051");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, binding_infos.size(), binding_infos.data());
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BufferlessPushDescriptors) {
    AddRequiredFeature(vkt::Feature::descriptorBufferPushDescriptors);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer(&kDisableMessageLimit));
    if (!descriptor_buffer_properties.bufferlessPushDescriptors) {
        GTEST_SKIP() << "bufferlessPushDescriptors is not supported";
    }

    m_command_buffer.Begin();

    vkt::Buffer d_buffer(*m_device, 4096,
                         VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT,
                         vkt::device_address);

    VkDescriptorBufferBindingPushDescriptorBufferHandleEXT dbbpdbh = vku::InitStructHelper();
    dbbpdbh.buffer = d_buffer;

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper(&dbbpdbh);
    dbbi.address = d_buffer.Address();
    dbbi.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT |
                 VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT;

    std::vector<VkDescriptorBufferBindingInfoEXT> binding_infos;
    for (uint32_t i = 0; i < descriptor_buffer_properties.maxDescriptorBufferBindings + 1; i++) {
        binding_infos.push_back(dbbi);
    }

    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-maxSamplerDescriptorBufferBindings-08048");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-maxResourceDescriptorBufferBindings-08049");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-bufferCount-08051");
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingPushDescriptorBufferHandleEXT-bufferlessPushDescriptors-08059",
                                    descriptor_buffer_properties.maxDescriptorBufferBindings + 1);
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, binding_infos.size(), binding_infos.data());
    m_errorMonitor->VerifyFound();

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingPushDescriptorBufferHandleEXT-bufferlessPushDescriptors-08059");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, DescriptorBufferOffsetAlignment) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    if (descriptor_buffer_properties.descriptorBufferOffsetAlignment == 1) {
        GTEST_SKIP() << "descriptorBufferOffsetAlignment is 1";
    }

    m_command_buffer.Begin();

    vkt::Buffer d_buffer(*m_device, 4096,
                         VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT,
                         vkt::device_address);

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = d_buffer.Address() + 1;  // make alignment bad
    dbbi.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT |
                 VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-address-08057");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BindingInfoUsage) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    m_command_buffer.Begin();

    vkt::Buffer buffer(*m_device, 4096, 0, vkt::device_address);

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = buffer.Address();
    dbbi.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-usage-08122");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-pBindingInfos-08055");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();

    dbbi.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-usage-08123");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-pBindingInfos-08055");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();

    dbbi.usage = VK_BUFFER_USAGE_PUSH_DESCRIPTORS_DESCRIPTOR_BUFFER_BIT_EXT;
    if (descriptor_buffer_properties.bufferlessPushDescriptors == VK_FALSE) {
        m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-bufferlessPushDescriptors-08056");
    }
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-usage-08124");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-pBindingInfos-08055");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, MultipleDeviceAddressBuffers) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());
    if (descriptor_buffer_properties.maxSamplerDescriptorBufferBindings < 3) {
        GTEST_SKIP() << "maxSamplerDescriptorBufferBindings is too low";
    }
    m_command_buffer.Begin();

    VkBufferCreateInfo buffer_ci = vku::InitStructHelper();
    buffer_ci.usage = VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT;
    buffer_ci.size = 4096;
    vkt::Buffer buffer_1(*m_device, buffer_ci, vkt::no_mem);
    vkt::Buffer buffer_2(*m_device, buffer_ci, vkt::no_mem);
    vkt::Buffer buffer_3(*m_device, buffer_ci, vkt::no_mem);

    VkMemoryRequirements mem_reqs;
    vk::GetBufferMemoryRequirements(device(), buffer_1, &mem_reqs);

    VkMemoryAllocateFlagsInfo alloc_flags = vku::InitStructHelper();
    alloc_flags.flags = VK_MEMORY_ALLOCATE_DEVICE_ADDRESS_BIT;
    VkMemoryAllocateInfo alloc_info = vku::InitStructHelper(&alloc_flags);
    alloc_info.allocationSize = 4096;
    vkt::DeviceMemory mem(*m_device, alloc_info);
    vk::BindBufferMemory(device(), buffer_1, mem, 0);
    vk::BindBufferMemory(device(), buffer_2, mem, 0);
    vk::BindBufferMemory(device(), buffer_3, mem, 0);
    if (buffer_1.Address() != buffer_2.Address() || buffer_1.Address() != buffer_3.Address()) {
        GTEST_SKIP() << "Did not get the same address for each buffer";
    }

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = buffer_1.Address();
    dbbi.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-usage-08122");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-pBindingInfos-08055");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BindingInfoUsage2) {
    TEST_DESCRIPTION("https://github.com/KhronosGroup/Vulkan-ValidationLayers/issues/9228");
    AddRequiredExtensions(VK_KHR_MAINTENANCE_5_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::maintenance5);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    m_command_buffer.Begin();

    vkt::Buffer buffer(*m_device, 4096, 0, vkt::device_address);

    VkBufferUsageFlags2CreateInfo buffer_usage_flags = vku::InitStructHelper();
    buffer_usage_flags.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper(&buffer_usage_flags);
    dbbi.address = buffer.Address();

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-usage-08122");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-pBindingInfos-08055");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BindingInfoUsageMultiBuffers) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    m_command_buffer.Begin();

    vkt::Buffer buffer_good1(*m_device, 4096, VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);
    vkt::Buffer buffer_good2(*m_device, 4096, VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);
    vkt::Buffer buffer_bad(*m_device, 4096, 0, vkt::device_address);

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = buffer_bad.Address();
    dbbi.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-usage-08122");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-pBindingInfos-08055");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, CmdBindDescriptorBufferEmbeddedSamplers) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    m_command_buffer.Begin();

    VkDescriptorSetLayoutBinding binding1 = {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_VERTEX_BIT, nullptr};
    vkt::DescriptorSetLayout dsl1(*m_device, binding1, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    VkDescriptorSetLayoutBinding binding2 = {0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler.handle()};
    vkt::DescriptorSetLayout dsl2(*m_device, binding2,
                                  VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                      VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&dsl1, &dsl2});

    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBufferEmbeddedSamplersEXT-set-08070");
    vk::CmdBindDescriptorBufferEmbeddedSamplersEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0);
    m_errorMonitor->VerifyFound();
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBufferEmbeddedSamplersEXT-set-08071");
    vk::CmdBindDescriptorBufferEmbeddedSamplersEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 2);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, CmdSetDescriptorBufferOffsets) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    m_command_buffer.Begin();

    VkDescriptorSetLayoutBinding binding1 = {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_VERTEX_BIT, nullptr};
    vkt::DescriptorSetLayout dsl1(*m_device, binding1, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    VkDescriptorSetLayoutBinding binding2 = {0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler.handle()};
    vkt::DescriptorSetLayout dsl2(*m_device, binding2,
                                  VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                      VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&dsl1, &dsl2});

    vkt::Buffer buffer(*m_device, 4096, VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = buffer.Address();
    dbbi.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);

    uint32_t index = 0;
    VkDeviceSize offset = 0;

    if (descriptor_buffer_properties.descriptorBufferOffsetAlignment != 1) {
        index = 0;
        offset = 1;
        m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pOffsets-08061");
        vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index,
                                             &offset);
        m_errorMonitor->VerifyFound();
    }

    index = descriptor_buffer_properties.maxDescriptorBufferBindings;
    offset = 0;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pBufferIndices-08064");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index, &offset);
    m_errorMonitor->VerifyFound();

    uint32_t indices[3] = {0};
    VkDeviceSize offsets[3] = {0};

    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-firstSet-08066");
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-firstSet-11804");
    m_errorMonitor->SetUnexpectedError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pOffsets-08063");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 3, indices,
                                         offsets);
    m_errorMonitor->VerifyFound();

    const std::optional<uint32_t> compute_qfi = m_device->ComputeOnlyQueueFamily();
    if (compute_qfi) {
        vkt::CommandPool command_pool(*m_device, compute_qfi.value());
        ASSERT_TRUE(command_pool.initialized());
        vkt::CommandBuffer command_buffer(*m_device, command_pool);
        index = 0;
        offset = 0;

        command_buffer.Begin();
        vk::CmdBindDescriptorBuffersEXT(command_buffer, 1, &dbbi);

        m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pipelineBindPoint-08067");
        vk::CmdSetDescriptorBufferOffsetsEXT(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index,
                                             &offset);
        m_errorMonitor->VerifyFound();
        command_buffer.End();
    }

    {
        const VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_VERTEX_BIT, nullptr};
        const vkt::DescriptorSetLayout set_layout_no_flag(*m_device, {binding});
        const vkt::PipelineLayout pipeline_layout_2(*m_device, {&set_layout_no_flag, &set_layout_no_flag});

        const uint32_t indices_2[2] = {0, 0};
        const VkDeviceSize offsets_2[2] = {0, 0};
        vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);
        // complain about set layout for set 0
        m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-firstSet-09006");
        // complain about set layout for set 1
        m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-firstSet-09006");
        vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout_2, 0, 2, indices_2,
                                             offsets_2);
        m_errorMonitor->VerifyFound();
    }
}

TEST_F(NegativeDescriptorBuffer, BindingAndOffsets) {
    TEST_DESCRIPTION("Test mapping from address to buffers when validating buffer offsets");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());
    if (descriptor_buffer_properties.maxSamplerDescriptorBufferBindings < 2) {
        GTEST_SKIP() << "maxSamplerDescriptorBufferBindings is too low";
    }
    m_command_buffer.Begin();

    VkDescriptorSetLayoutBinding binding1 = {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_VERTEX_BIT, nullptr};
    vkt::DescriptorSetLayout dsl1(*m_device, binding1, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    VkDescriptorSetLayoutBinding binding2 = {0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler.handle()};
    vkt::DescriptorSetLayout dsl2(*m_device, binding2,
                                  VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                      VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&dsl1, &dsl2});

    const VkDeviceSize large_buffer_size =
        std::max<VkDeviceSize>(256 * descriptor_buffer_properties.descriptorBufferOffsetAlignment, 8192);
    const VkDeviceSize small_buffer_size =
        std::max<VkDeviceSize>(4 * descriptor_buffer_properties.descriptorBufferOffsetAlignment, 4096);

    // Create a large and a small buffer
    VkBufferCreateInfo buffer_ci = vku::InitStructHelper();
    buffer_ci.size = large_buffer_size;
    buffer_ci.usage = VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;
    vkt::Buffer large_buffer(*m_device, buffer_ci, vkt::no_mem);

    buffer_ci.size = small_buffer_size;
    vkt::Buffer small_buffer(*m_device, buffer_ci, vkt::no_mem);

    VkMemoryRequirements buffer_mem_reqs = {};
    vk::GetBufferMemoryRequirements(device(), large_buffer, &buffer_mem_reqs);

    // Allocate common buffer memory
    VkMemoryAllocateFlagsInfo alloc_flags = vku::InitStructHelper();
    alloc_flags.flags = VK_MEMORY_ALLOCATE_DEVICE_ADDRESS_BIT;
    VkMemoryAllocateInfo alloc_info = vku::InitStructHelper(&alloc_flags);
    alloc_info.allocationSize = buffer_mem_reqs.size;
    m_device->Physical().SetMemoryType(buffer_mem_reqs.memoryTypeBits, &alloc_info, 0);
    vkt::DeviceMemory buffer_memory(*m_device, alloc_info);

    // Bind those buffers to the same buffer memory
    vk::BindBufferMemory(device(), large_buffer, buffer_memory, 0);
    vk::BindBufferMemory(device(), small_buffer, buffer_memory, 0);

    // Check that internal mapping from address to buffers is correctly updated
    if (large_buffer.Address() != small_buffer.Address()) {
        GTEST_SKIP() << "Buffers address don't match";
    }
    // calling large_buffer->Address() twice should not result in this buffer being mapped twice.
    // If it is mapped twice, the error below will not be thrown.
    const VkDeviceAddress common_address = large_buffer.Address();

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = common_address;
    dbbi.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;

    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);

    constexpr uint32_t index = 0;

    // First call should succeed because offset is small enough to fit in large_buffer
    const VkDeviceSize offset = small_buffer_size;
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index, &offset);

    large_buffer.Destroy();
    // Large buffer has been deleted, its entry in the address to buffers map must have been as well.
    // Since offset is too large to fit in small buffer, vkCmdSetDescriptorBufferOffsetsEXT should fail
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pOffsets-08063");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index, &offset);
    m_errorMonitor->VerifyFound();

    m_command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, BufferIndices) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr};
    vkt::DescriptorSetLayout ds_layout(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&ds_layout});

    VkDeviceSize ds_layout_size = ds_layout.GetDescriptorBufferSize();
    vkt::Buffer descriptor_buffer(*m_device, ds_layout_size, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT,
                                  vkt::device_address);

    m_command_buffer.Begin();

    VkDescriptorBufferBindingInfoEXT descriptor_buffer_binding_info = vku::InitStructHelper();
    descriptor_buffer_binding_info.address = descriptor_buffer.Address();
    descriptor_buffer_binding_info.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &descriptor_buffer_binding_info);

    uint32_t buffer_index = 2;
    VkDeviceSize buffer_offset = 0;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pBufferIndices-08065");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                         &buffer_offset);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BindingOffsetFirst) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr};
    vkt::DescriptorSetLayout ds_layout(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&ds_layout});

    m_command_buffer.Begin();

    uint32_t buffer_index = 0;
    VkDeviceSize buffer_offset = 0;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pBufferIndices-08065");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                         &buffer_offset);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, MaxDescriptorBufferRange) {
    AddRequiredExtensions(VK_KHR_MAINTENANCE_5_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::maintenance5);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());
    if (!IsPlatformMockICD()) {
        GTEST_SKIP() << "Hard to write a test that will reasonably work everywhere";
    }

    std::vector<VkDescriptorSetLayoutBinding> bindings = {{0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr},
                                                          {1, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_ALL, nullptr}};
    vkt::DescriptorSetLayout dsl(*m_device, bindings, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&dsl});

    vkt::Buffer buffer_s(*m_device, descriptor_buffer_properties.maxSamplerDescriptorBufferRange + 512,
                         VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);
    vkt::Buffer buffer_r(*m_device, descriptor_buffer_properties.maxResourceDescriptorBufferRange + 512,
                         VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);

    VkBufferUsageFlags2CreateInfo buffer_usage_flags = vku::InitStructHelper();
    buffer_usage_flags.usage = VK_BUFFER_USAGE_2_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;

    VkDescriptorBufferBindingInfoEXT buffer_bindings[2];
    buffer_bindings[0] = vku::InitStructHelper();
    buffer_bindings[0].address = buffer_s.Address();
    buffer_bindings[0].usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;
    buffer_bindings[1] = vku::InitStructHelper(&buffer_usage_flags);
    buffer_bindings[1].address = buffer_r.Address();

    m_command_buffer.Begin();
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 2, buffer_bindings);

    uint32_t index = 0;
    VkDeviceSize offset = descriptor_buffer_properties.maxSamplerDescriptorBufferRange + 256;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pOffsets-08126");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index, &offset);
    m_errorMonitor->VerifyFound();

    index = 1;
    offset = descriptor_buffer_properties.maxResourceDescriptorBufferRange + 256;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pOffsets-08127");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index, &offset);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, DescriptorBufferAddress) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr};
    vkt::DescriptorSetLayout ds_layout(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&ds_layout});

    VkDeviceSize ds_layout_size = ds_layout.GetDescriptorBufferSize();
    vkt::Buffer descriptor_buffer(*m_device, ds_layout_size, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT,
                                  vkt::device_address);

    m_command_buffer.Begin();

    VkDescriptorBufferBindingInfoEXT descriptor_buffer_binding_info = vku::InitStructHelper();
    descriptor_buffer_binding_info.address = descriptor_buffer.Address();
    descriptor_buffer_binding_info.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &descriptor_buffer_binding_info);

    descriptor_buffer.Destroy();

    uint32_t buffer_index = 0;
    VkDeviceSize buffer_offset = 0;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pBufferIndices-08065");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                         &buffer_offset);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, LegacyDescriptorInvalidate) {
    TEST_DESCRIPTION("Case 5 and 6 in https://gitlab.khronos.org/vulkan/vulkan/-/merge_requests/7504#note_549388");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Buffer legacy_buffer(*m_device, 16, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT);
    VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr};
    OneOffDescriptorSet legacy_ds(m_device, {binding});
    vkt::PipelineLayout legacy_pipeline_layout(*m_device, {&legacy_ds.layout_});
    legacy_ds.WriteDescriptorBufferInfo(0, legacy_buffer, 0, VK_WHOLE_SIZE, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER);
    legacy_ds.UpdateDescriptorSets();

    vkt::Buffer buffer_data(*m_device, 16, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, vkt::device_address);
    vkt::DescriptorSetLayout ds_layout(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&ds_layout});

    VkDeviceSize ds_layout_size = ds_layout.GetDescriptorBufferSize();
    vkt::Buffer descriptor_buffer(*m_device, ds_layout_size, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT,
                                  vkt::device_address);

    vkt::DescriptorGetInfo get_info(VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, buffer_data, 16);

    void* mapped_descriptor_data = descriptor_buffer.Memory().Map();
    vk::GetDescriptorEXT(device(), get_info, descriptor_buffer_properties.storageBufferDescriptorSize, mapped_descriptor_data);

    const char* cs_source = R"glsl(
        #version 450
        layout (set = 0, binding = 0) buffer SSBO_0 { uint x; };
        void main() {
            x = 0;
        }
    )glsl";

    CreateComputePipelineHelper pipe(*this);
    pipe.cs_ = VkShaderObj(*m_device, cs_source, VK_SHADER_STAGE_COMPUTE_BIT, SPV_ENV_VULKAN_1_2);
    pipe.cp_ci_.flags |= VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    pipe.cp_ci_.layout = pipeline_layout;
    pipe.CreateComputePipeline();

    VkDescriptorBufferBindingInfoEXT descriptor_buffer_binding_info = vku::InitStructHelper();
    descriptor_buffer_binding_info.address = descriptor_buffer.Address();
    descriptor_buffer_binding_info.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    uint32_t buffer_index = 0;
    VkDeviceSize buffer_offset = 0;

    {
        m_command_buffer.Begin();
        vk::CmdBindPipeline(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipe);

        vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &descriptor_buffer_binding_info);

        // invalidates
        vk::CmdBindDescriptorSets(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, legacy_pipeline_layout, 0, 1, &legacy_ds.set_,
                                  0, nullptr);

        m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pBufferIndices-08065");
        vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                             &buffer_offset);
        m_errorMonitor->VerifyFound();
        m_command_buffer.End();
    }
    {
        m_command_buffer.Begin();
        vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &descriptor_buffer_binding_info);
        vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                             &buffer_offset);

        // invalidates
        vk::CmdBindDescriptorSets(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, legacy_pipeline_layout, 0, 1, &legacy_ds.set_,
                                  0, nullptr);

        m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pBufferIndices-08065");
        vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                             &buffer_offset);
        m_errorMonitor->VerifyFound();
        m_command_buffer.End();
    }
}

TEST_F(NegativeDescriptorBuffer, InconsistentBuffer) {
    TEST_DESCRIPTION("Dispatch pipeline with descriptor set bound while descriptor buffer expected");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_COMPUTE_BIT, nullptr};

    VkDescriptorSetLayoutCreateInfo dslci = vku::InitStructHelper();
    dslci.flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    dslci.bindingCount = 1;
    dslci.pBindings = &binding;

    vkt::DescriptorSetLayout dsl(*m_device, dslci);
    vkt::PipelineLayout pipeline_layout(*m_device, {&dsl});
    ASSERT_TRUE(pipeline_layout.initialized());

    vkt::Buffer buffer(*m_device, 4096, VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);

    VkDescriptorBufferBindingInfoEXT dbbi = vku::InitStructHelper();
    dbbi.address = buffer.Address();
    dbbi.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;

    const char* shader_source = R"glsl(
        #version 450
        layout(set = 0, binding = 0) uniform ufoo { uint index; };
        void main() {
            uint x = index; // static usage
        }
    )glsl";

    CreateComputePipelineHelper pipe(*this);
    pipe.cs_ = VkShaderObj(*m_device, shader_source, VK_SHADER_STAGE_COMPUTE_BIT);
    pipe.CreateComputePipeline();

    m_command_buffer.Begin();
    vk::CmdBindPipeline(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipe);

    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &dbbi);

    uint32_t index = 0;
    VkDeviceSize offset = 0;
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &index, &offset);

    m_errorMonitor->SetDesiredError("VUID-vkCmdDispatch-None-08117");
    m_errorMonitor->SetDesiredError("VUID-vkCmdDispatch-None-08600");
    vk::CmdDispatch(m_command_buffer, 1, 1, 1);
    m_errorMonitor->VerifyFound();

    m_command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, InconsistentSet) {
    TEST_DESCRIPTION("Dispatch pipeline with descriptor buffer bound while of descriptor set expected");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    OneOffDescriptorSet descriptor_set(m_device,
                                       {
                                           {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_COMPUTE_BIT, nullptr},
                                       });
    vkt::PipelineLayout pipeline_layout(*m_device, {&descriptor_set.layout_});

    const char* shader_source = R"glsl(
        #version 450
        layout(set = 0, binding = 0) uniform ufoo { uint index; };
        void main() {
            uint x = index; // static usage
        }
    )glsl";

    CreateComputePipelineHelper pipe(*this);
    pipe.cp_ci_.flags |= VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    pipe.cs_ = VkShaderObj(*m_device, shader_source, VK_SHADER_STAGE_COMPUTE_BIT);
    pipe.CreateComputePipeline();

    m_command_buffer.Begin();
    vk::CmdBindPipeline(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipe);

    vk::CmdBindDescriptorSets(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &descriptor_set.set_, 0,
                              nullptr);

    m_errorMonitor->SetDesiredError("VUID-vkCmdDispatch-None-08115");
    vk::CmdDispatch(m_command_buffer, 1, 1, 1);
    m_errorMonitor->VerifyFound();

    m_command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, BindPoint) {
    TEST_DESCRIPTION("Descriptor buffer invalid bind point.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    VkDescriptorSetLayoutBinding binding1 = {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_VERTEX_BIT, nullptr};
    vkt::DescriptorSetLayout dsl1(*m_device, binding1, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    VkDescriptorSetLayoutBinding binding2 = {0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler.handle()};
    vkt::DescriptorSetLayout dsl2(*m_device, binding2,
                                  VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                      VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&dsl1, &dsl2});

    const std::optional<uint32_t> compute_qfi = m_device->ComputeOnlyQueueFamily();
    if (!compute_qfi) {
        GTEST_SKIP() << "No compute-only queue family, skipping bindpoint and queue tests.";
        return;
    }

    vkt::CommandPool command_pool(*m_device, compute_qfi.value());
    ASSERT_TRUE(command_pool.initialized());
    vkt::CommandBuffer command_buffer(*m_device, command_pool);

    command_buffer.Begin();
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBufferEmbeddedSamplersEXT-pipelineBindPoint-08069");
    vk::CmdBindDescriptorBufferEmbeddedSamplersEXT(command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 1);
    m_errorMonitor->VerifyFound();
    command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, DescriptorGetInfoBasic) {
    TEST_DESCRIPTION("Descriptor buffer vkDescriptorGetInfo().");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    uint8_t buffer[128];

    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08018");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08018");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, DescriptorGetInfoValidPointer) {
    TEST_DESCRIPTION("If type is used, need valid pointer to corresponding data.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    uint8_t buffer[16];
    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();

    dgi.type = VK_DESCRIPTOR_TYPE_SAMPLER;
    dgi.data.pSampler = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-pSampler-parameter");
    vk::GetDescriptorEXT(device(), &dgi, 4, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    dgi.data.pCombinedImageSampler = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-pCombinedImageSampler-parameter");
    vk::GetDescriptorEXT(device(), &dgi, 4, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT;
    dgi.data.pInputAttachmentImage = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-pInputAttachmentImage-parameter");
    vk::GetDescriptorEXT(device(), &dgi, 4, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    auto bad_struct = vku::InitStruct<VkBufferCopy2>();
    dgi.data.pUniformTexelBuffer = (VkDescriptorAddressInfoEXT*)&bad_struct;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-sType-sType");
    vk::GetDescriptorEXT(device(), &dgi, 4, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, DescriptorAddressInfoImplicit) {
    TEST_DESCRIPTION("Make sure VkDescriptorAddressInfoEXT are validated");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    auto bad_struct = vku::InitStruct<VkBufferCopy2>();
    VkDescriptorAddressInfoEXT dai = vku::InitStructHelper(&bad_struct);
    dai.address = 0;
    dai.range = 4;
    dai.format = VK_FORMAT_R8_UINT;

    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    dgi.data.pUniformTexelBuffer = &dai;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-pNext-pNext");
    uint8_t buffer[16];
    vk::GetDescriptorEXT(device(), &dgi, 4, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, DescriptorGetInfoSampler) {
    TEST_DESCRIPTION("Descriptor buffer vkDescriptorGetInfo() with a sampler backed VkDescriptorImageInfo.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    uint8_t buffer[128];

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    const VkDescriptorImageInfo dii = {sampler, VK_NULL_HANDLE, VK_IMAGE_LAYOUT_GENERAL};
    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();

    dgi.type = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    dgi.data.pCombinedImageSampler = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08034");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.combinedImageSamplerDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
    dgi.data.pSampledImage = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08035");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.sampledImageDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.data.pSampledImage = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08035");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.sampledImageDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE;
    dgi.data.pStorageImage = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08036");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageImageDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.data.pStorageImage = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08036");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageImageDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    dgi.data.pUniformTexelBuffer = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08037");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER;
    dgi.data.pStorageTexelBuffer = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08038");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageTexelBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    dgi.data.pUniformBuffer = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08039");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
    dgi.data.pStorageBuffer = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08040");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, DescriptorGetInfoAS) {
    TEST_DESCRIPTION("Descriptor buffer vkDescriptorGetInfo() for Acceleration Structure.");
    AddRequiredExtensions(VK_KHR_ACCELERATION_STRUCTURE_EXTENSION_NAME);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    uint8_t buffer[128];
    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR;
    dgi.data.accelerationStructure = 0;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorDataEXT-type-08041");
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08028");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.accelerationStructureDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, DescriptorGetInfoAddressRange) {
    TEST_DESCRIPTION("Descriptor buffer vkDescriptorGetInfo() with VkDescriptorAddressInfoEXT.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    uint8_t buffer[128];

    VkBufferCreateInfo buffer_ci = vku::InitStructHelper();
    buffer_ci.size = 4096;
    buffer_ci.usage = VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT | VK_BUFFER_USAGE_STORAGE_BUFFER_BIT |
                      VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT | VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT |
                      VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT;
    vkt::Buffer d_buffer(*m_device, buffer_ci, vkt::no_mem);

    VkDescriptorAddressInfoEXT dai = vku::InitStructHelper();
    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    dgi.data.pUniformBuffer = &dai;

    dai.address = 0;
    dai.range = 4;
    dai.format = VK_FORMAT_R8_UINT;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-address-08043");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    VkMemoryRequirements mem_reqs;
    vk::GetBufferMemoryRequirements(device(), d_buffer, &mem_reqs);

    VkMemoryAllocateFlagsInfo memflagsinfo = vku::InitStructHelper();
    memflagsinfo.flags = VK_MEMORY_ALLOCATE_DEVICE_ADDRESS_BIT;
    auto mem_alloc_info = vkt::DeviceMemory::GetResourceAllocInfo(*m_device, mem_reqs, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT);
    mem_alloc_info.pNext = &memflagsinfo;

    vkt::DeviceMemory mem(*m_device, mem_alloc_info);

    d_buffer.BindMemory(mem, 0);

    dai.address = d_buffer.Address();
    dai.range = 4096 * buffer_ci.size;
    dai.format = VK_FORMAT_R8_UINT;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-range-08045");
    // Might go over UBO range limit
    m_errorMonitor->SetAllowedFailureMsg("UNASSIGNED-VkDescriptorAddressInfoEXT-range-UBO");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dai.range = 0;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-range-08940");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dai.range = VK_WHOLE_SIZE;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-range-08045");
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-nullDescriptor-08939");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    {
        dai.range = 4;
        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorEXT-dataSize-08125");
        vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize - 1, &buffer);
        m_errorMonitor->VerifyFound();
    }

    mem.Destroy();

    dai.range = 4;

    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    dgi.data.pUniformBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-None-10894");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
    dgi.data.pStorageBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-None-10894");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    dgi.data.pUniformTexelBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-None-10894");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER;
    dgi.data.pStorageTexelBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-None-10894");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageTexelBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, LayoutFlags) {
    AddRequiredExtensions(VK_KHR_PUSH_DESCRIPTOR_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::descriptorBufferPushDescriptors);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    VkDeviceSize size;
    VkDeviceSize offset;
    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    const VkDescriptorSetLayoutBinding binding{0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_FRAGMENT_BIT, &sampler.handle()};

    {
        vkt::DescriptorSetLayout dsl(*m_device, binding);

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutSizeEXT-layout-08012");
        vk::GetDescriptorSetLayoutSizeEXT(device(), dsl, &size);
        m_errorMonitor->VerifyFound();

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutBindingOffsetEXT-layout-08014");
        vk::GetDescriptorSetLayoutBindingOffsetEXT(device(), dsl, 0, &offset);
        m_errorMonitor->VerifyFound();
    }
    {
        vkt::DescriptorSetLayout dsl(
            *m_device, binding,
            VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT | VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR);

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutSizeEXT-layout-11811");
        vk::GetDescriptorSetLayoutSizeEXT(device(), dsl, &size);
        m_errorMonitor->VerifyFound();

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutBindingOffsetEXT-layout-11813");
        vk::GetDescriptorSetLayoutBindingOffsetEXT(device(), dsl, 0, &offset);
        m_errorMonitor->VerifyFound();
    }
    {
        vkt::DescriptorSetLayout dsl(*m_device, binding,
                                     VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                         VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT);

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutSizeEXT-layout-11812");
        vk::GetDescriptorSetLayoutSizeEXT(device(), dsl, &size);
        m_errorMonitor->VerifyFound();

        m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorSetLayoutBindingOffsetEXT-layout-11814");
        vk::GetDescriptorSetLayoutBindingOffsetEXT(device(), dsl, 0, &offset);
        m_errorMonitor->VerifyFound();
    }
}

TEST_F(NegativeDescriptorBuffer, DescriptorBufferCaptureReplay) {
    AddRequiredFeature(vkt::Feature::descriptorBufferCaptureReplay);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    {
        VkBufferCreateInfo buffer_ci = vku::InitStructHelper();
        buffer_ci.flags = VK_BUFFER_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        buffer_ci.size = 4096;
        buffer_ci.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT;

        vkt::Buffer d_buffer(*m_device, buffer_ci, vkt::no_mem);

        VkMemoryRequirements mem_reqs;
        vk::GetBufferMemoryRequirements(device(), d_buffer, &mem_reqs);

        auto mem_alloc_info = vkt::DeviceMemory::GetResourceAllocInfo(*m_device, mem_reqs, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT);
        // no alloc flags
        vkt::DeviceMemory mem(*m_device, mem_alloc_info);

        m_errorMonitor->SetDesiredError("VUID-vkBindBufferMemory-descriptorBufferCaptureReplay-08112");
        m_errorMonitor->SetDesiredError("VUID-vkBindBufferMemory-bufferDeviceAddressCaptureReplay-09200");
        m_errorMonitor->SetDesiredError("VUID-vkBindBufferMemory-buffer-09201");
        m_errorMonitor->SetDesiredError("VUID-vkBindBufferMemory-bufferDeviceAddress-03339");
        vk::BindBufferMemory(device(), d_buffer, mem, 0);
        m_errorMonitor->VerifyFound();
    }

    {
        VkImageCreateInfo image_create_info = vku::InitStructHelper();
        image_create_info.flags = VK_IMAGE_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT;
        image_create_info.imageType = VK_IMAGE_TYPE_2D;
        image_create_info.extent = {128, 128, 1};
        image_create_info.mipLevels = 1;
        image_create_info.arrayLayers = 1;
        image_create_info.samples = VK_SAMPLE_COUNT_1_BIT;
        image_create_info.tiling = VK_IMAGE_TILING_OPTIMAL;
        image_create_info.format = VK_FORMAT_D32_SFLOAT;
        image_create_info.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
        vkt::Image temp_image(*m_device, image_create_info, vkt::no_mem);

        VkMemoryRequirements mem_reqs;
        vk::GetImageMemoryRequirements(device(), temp_image, &mem_reqs);

        auto mem_alloc_info = vkt::DeviceMemory::GetResourceAllocInfo(*m_device, mem_reqs, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT);
        // no allocate flags
        vkt::DeviceMemory mem(*m_device, mem_alloc_info);

        m_errorMonitor->SetDesiredError("VUID-vkBindImageMemory-image-08113");
        m_errorMonitor->SetDesiredError("VUID-vkBindImageMemory-image-09202");
        vk::BindImageMemory(device(), temp_image, mem, 0);
        m_errorMonitor->VerifyFound();
    }
}

TEST_F(NegativeDescriptorBuffer, DescriptorGetInfo) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());

    VkSampler invalid_sampler = CastToHandle<VkSampler, uintptr_t>(0xbad00000);
    VkImageView invalid_imageview = CastToHandle<VkImageView, uintptr_t>(0xbad00000);
    VkDeviceAddress invalid_buffer = CastToHandle<VkDeviceAddress, uintptr_t>(0xbad00000);

    uint8_t buffer[128];
    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();

    const VkDescriptorImageInfo dii = {invalid_sampler, invalid_imageview, VK_IMAGE_LAYOUT_GENERAL};

    dgi.type = VK_DESCRIPTOR_TYPE_SAMPLER;
    dgi.data.pSampler = &invalid_sampler;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-pSampler-parameter");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.samplerDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    dgi.data.pCombinedImageSampler = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08019");
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08020");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.combinedImageSamplerDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT;
    dgi.data.pInputAttachmentImage = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08021");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.inputAttachmentDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE;
    dgi.data.pSampledImage = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08022");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.sampledImageDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_IMAGE;
    dgi.data.pStorageImage = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08023");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageImageDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    VkDescriptorAddressInfoEXT dai = vku::InitStructHelper();
    dai.address = invalid_buffer;
    dai.range = 64;
    dai.format = VK_FORMAT_R8_UINT;

    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    dgi.data.pUniformTexelBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-size-11364");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER;
    dgi.data.pStorageTexelBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-size-11364");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageTexelBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER;
    dgi.data.pUniformTexelBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-size-11364");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();

    dgi.type = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
    dgi.data.pStorageTexelBuffer = &dai;
    m_errorMonitor->SetDesiredError("VUID-VkDeviceAddress-size-11364");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.storageBufferDescriptorSize, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, GetDescriptorImageUsage) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Image image(*m_device, 32, 32, VK_FORMAT_R8G8B8A8_UNORM, VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT);
    vkt::ImageView image_view = image.CreateView();
    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());

    vkt::Buffer descriptor_buffer(
        *m_device, 4096, VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT,
        vkt::device_address);
    uint8_t* data = (uint8_t*)descriptor_buffer.Memory().Map();

    vkt::DescriptorGetInfo get_info_combined(VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, sampler, image_view,
                                             VK_IMAGE_LAYOUT_GENERAL);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12216");
    vk::GetDescriptorEXT(device(), get_info_combined, descriptor_buffer_properties.combinedImageSamplerDescriptorSize, data);
    m_errorMonitor->VerifyFound();

    vkt::DescriptorGetInfo get_info_sampled(VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, VK_NULL_HANDLE, image_view, VK_IMAGE_LAYOUT_GENERAL);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12217");
    vk::GetDescriptorEXT(device(), get_info_sampled, descriptor_buffer_properties.sampledImageDescriptorSize, data);
    m_errorMonitor->VerifyFound();

    vkt::DescriptorGetInfo get_info_storage(VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, VK_NULL_HANDLE, image_view, VK_IMAGE_LAYOUT_GENERAL);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12218");
    vk::GetDescriptorEXT(device(), get_info_storage, descriptor_buffer_properties.storageImageDescriptorSize, data);
    m_errorMonitor->VerifyFound();

    vkt::DescriptorGetInfo get_info_input(VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT, VK_NULL_HANDLE, image_view, VK_IMAGE_LAYOUT_GENERAL);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12219");
    vk::GetDescriptorEXT(device(), get_info_input, descriptor_buffer_properties.inputAttachmentDescriptorSize, data);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, GetDescriptorBufferUsage) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Buffer buffer_data(*m_device, 16, 0, vkt::device_address);

    vkt::Buffer storage_buffer(*m_device, 32, VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT, vkt::device_address);
    vkt::BufferView storage_buffer_view(*m_device, storage_buffer, VK_FORMAT_R32_UINT);
    vkt::Buffer uniform_buffer(*m_device, 32, VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT, vkt::device_address);
    vkt::BufferView uniform_buffer_view(*m_device, uniform_buffer, VK_FORMAT_R32_UINT);

    vkt::Buffer descriptor_buffer(*m_device, 4096, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);
    uint8_t* data = (uint8_t*)descriptor_buffer.Memory().Map();

    vkt::DescriptorGetInfo get_info_uniform(VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, buffer_data, 16);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12220");
    vk::GetDescriptorEXT(device(), get_info_uniform, descriptor_buffer_properties.uniformBufferDescriptorSize, data);
    m_errorMonitor->VerifyFound();

    vkt::DescriptorGetInfo get_info_storage(VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, buffer_data, 16);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12221");
    vk::GetDescriptorEXT(device(), get_info_storage, descriptor_buffer_properties.storageBufferDescriptorSize, data);
    m_errorMonitor->VerifyFound();

    vkt::DescriptorGetInfo get_info_tex_uniform(VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, buffer_data, 16, VK_FORMAT_R32_UINT);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12222");
    vk::GetDescriptorEXT(device(), get_info_tex_uniform, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, data);
    m_errorMonitor->VerifyFound();

    vkt::DescriptorGetInfo get_info_tex_storage(VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, buffer_data, 16, VK_FORMAT_R32_UINT);
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12223");
    vk::GetDescriptorEXT(device(), get_info_tex_storage, descriptor_buffer_properties.storageTexelBufferDescriptorSize, data);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, SetBufferAddressSpaceLimits) {
    TEST_DESCRIPTION("Create VkBuffer with extension.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    // After a few GB, can have memory issues running these tests
    // descriptorBufferAddressSpaceSize is always the largest of the 3 buffer address size limits
    constexpr VkDeviceSize max_limit = static_cast<VkDeviceSize>(1) << 31;
    if (descriptor_buffer_properties.descriptorBufferAddressSpaceSize > max_limit) {
        GTEST_SKIP() << "descriptorBufferAddressSpaceSize are too large";
    }

    VkBufferCreateInfo buffer_ci = vku::InitStructHelper();
    buffer_ci.size = descriptor_buffer_properties.descriptorBufferAddressSpaceSize + 1;

    buffer_ci.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;
    CreateBufferTest(buffer_ci, "VUID-VkBufferCreateInfo-usage-08097");

    buffer_ci.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    CreateBufferTest(buffer_ci, "VUID-VkBufferCreateInfo-usage-08098");

    m_errorMonitor->SetDesiredError("VUID-VkBufferCreateInfo-usage-08097");
    buffer_ci.usage = VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT | VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT |
                      VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;
    CreateBufferTest(buffer_ci, "VUID-VkBufferCreateInfo-usage-08098");
}

// https://github.com/KhronosGroup/Vulkan-ValidationLayers/issues/5826
TEST_F(NegativeDescriptorBuffer, NullHandle) {
    TEST_DESCRIPTION("Descriptor buffer various tests.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    const auto invalid_sampler = CastToHandle<VkSampler, uintptr_t>(0x0);
    const auto invalid_imageview = CastToHandle<VkImageView, uintptr_t>(0x0);

    std::array<std::byte, 128> buffer = {};
    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();

    const VkDescriptorImageInfo dii = {invalid_sampler, invalid_imageview, VK_IMAGE_LAYOUT_GENERAL};

    dgi.type = VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT;
    dgi.data.pInputAttachmentImage = &dii;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-08021");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.inputAttachmentDescriptorSize, buffer.data());
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, NullCombinedImageSampler) {
    AddRequiredExtensions(VK_EXT_ROBUSTNESS_2_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::nullDescriptor);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    uint8_t out;
    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
    dgi.data.pCombinedImageSampler = nullptr;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-pCombinedImageSampler-parameter");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.combinedImageSamplerDescriptorSize / 2, &out);
    m_errorMonitor->VerifyFound();

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());
    const VkDescriptorImageInfo dii = {sampler, VK_NULL_HANDLE, VK_IMAGE_LAYOUT_GENERAL};
    dgi.data.pCombinedImageSampler = &dii;
    m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorEXT-pDescriptorInfo-09507");
    m_errorMonitor->SetDesiredError("VUID-vkGetDescriptorEXT-dataSize-08125");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.combinedImageSamplerDescriptorSize / 2, &out);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, BufferUsage) {
    TEST_DESCRIPTION("Wrong Usage for buffer createion.");
    AddRequiredFeature(vkt::Feature::descriptorBufferPushDescriptors);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    if (descriptor_buffer_properties.bufferlessPushDescriptors) {
        GTEST_SKIP() << "bufferlessPushDescriptors is supported";
    }

    VkBufferCreateInfo buffer_create_info = vku::InitStructHelper();
    buffer_create_info.size = 64;
    buffer_create_info.usage = VK_BUFFER_USAGE_PUSH_DESCRIPTORS_DESCRIPTOR_BUFFER_BIT_EXT;

    VkBuffer buffer;
    m_errorMonitor->SetDesiredError("VUID-VkBufferCreateInfo-usage-08103");
    vk::CreateBuffer(device(), &buffer_create_info, nullptr, &buffer);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, Binding) {
    AddRequiredExtensions(VK_KHR_MAINTENANCE_6_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::maintenance6);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    // TODO - try to get 08010 removed from spec as no possible way to create descriptor with the invalid flag
    m_errorMonitor->SetAllowedFailureMsg("VUID-VkDescriptorSetAllocateInfo-pSetLayouts-08009");
    OneOffDescriptorSet descriptor_set(m_device,
                                       {
                                           {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr},
                                       },
                                       VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    const vkt::PipelineLayout pipeline_layout(*m_device, {&descriptor_set.layout_});

    m_command_buffer.Begin();

    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorSets-pDescriptorSets-08010");
    vk::CmdBindDescriptorSets(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &descriptor_set.set_, 0,
                              nullptr);
    m_errorMonitor->VerifyFound();

    VkBindDescriptorSetsInfo bind_ds_info = vku::InitStructHelper();
    bind_ds_info.stageFlags = VK_SHADER_STAGE_FRAGMENT_BIT;
    bind_ds_info.layout = pipeline_layout;
    bind_ds_info.firstSet = 0;
    bind_ds_info.descriptorSetCount = 1;
    bind_ds_info.pDescriptorSets = &descriptor_set.set_;
    bind_ds_info.dynamicOffsetCount = 0;
    bind_ds_info.pDynamicOffsets = nullptr;

    m_errorMonitor->SetDesiredError("VUID-VkBindDescriptorSetsInfo-pDescriptorSets-08010");
    vk::CmdBindDescriptorSets2KHR(m_command_buffer, &bind_ds_info);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, InvalidDescriptorBufferUsage) {
    TEST_DESCRIPTION("Test vkCmdBindDescriptorBuffersEXT with invalid usage");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    VkBufferCreateInfo buffer_ci = vku::InitStructHelper();
    buffer_ci.size = 4096;
    buffer_ci.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT |
                      VK_BUFFER_USAGE_SHADER_DEVICE_ADDRESS_BIT;

    VkMemoryAllocateFlagsInfo allocate_flag_info = vku::InitStructHelper();
    allocate_flag_info.flags = VK_MEMORY_ALLOCATE_DEVICE_ADDRESS_BIT;
    vkt::Buffer d_buffer(*m_device, buffer_ci, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT, &allocate_flag_info);

    VkDescriptorBufferBindingInfoEXT binding_info = vku::InitStructHelper();
    binding_info.address = d_buffer.Address();
    binding_info.usage = buffer_ci.usage | 0x80000000;

    m_command_buffer.Begin();
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-None-09499");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1u, &binding_info);
    m_errorMonitor->VerifyFound();

    binding_info.usage = 0u;

    m_errorMonitor->SetDesiredError("VUID-VkDescriptorBufferBindingInfoEXT-None-09500");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1u, &binding_info);
    m_errorMonitor->VerifyFound();
    m_command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, MaxTexelBufferElements) {
    TEST_DESCRIPTION("texel buffers must be less than maxTexelBufferElements.");
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    if (!BufferFormatAndFeaturesSupported(Gpu(), VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT)) {
        GTEST_SKIP() << "Test requires support for VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT";
    }
    VkDeviceSize format_size = static_cast<VkDeviceSize>(vkuFormatTexelBlockSize(VK_FORMAT_R8G8B8A8_UNORM));

    VkDescriptorAddressInfoEXT dai = vku::InitStructHelper();
    dai.address = 0;
    dai.range = 2 * format_size * static_cast<VkDeviceSize>(m_device->Physical().limits_.maxTexelBufferElements);
    dai.format = VK_FORMAT_R8G8B8A8_UNORM;

    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    dgi.data.pUniformTexelBuffer = &dai;

    uint8_t out;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-address-08043");  // null address
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-09427");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, &out);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, TexelBufferFormat) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Buffer buffer(*m_device, 4096,
                       VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT,
                       vkt::device_address);

    VkDescriptorAddressInfoEXT dai = vku::InitStructHelper();
    dai.address = buffer.Address();
    dai.range = 4;
    dai.format = VK_FORMAT_UNDEFINED;

    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    dgi.data.pUniformTexelBuffer = &dai;

    uint8_t out;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-None-09508");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, &out);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, TexelBufferFormat2) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Buffer buffer(*m_device, 4096,
                       VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT,
                       vkt::device_address);

    VkDescriptorAddressInfoEXT dai = vku::InitStructHelper();
    dai.address = buffer.Address();
    dai.range = 4;
    dai.format = VK_FORMAT_G16_B16R16_2PLANE_444_UNORM;

    VkDescriptorGetInfoEXT dgi = vku::InitStructHelper();
    dgi.type = VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER;
    dgi.data.pUniformTexelBuffer = &dai;

    uint8_t out;
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-format-parameter");
    m_errorMonitor->SetDesiredError("VUID-VkDescriptorAddressInfoEXT-None-12271");
    vk::GetDescriptorEXT(device(), &dgi, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, &out);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, MaxResourceDescriptorBufferBindings) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    if (descriptor_buffer_properties.maxResourceDescriptorBufferBindings != 1) {
        GTEST_SKIP() << "maxResourceDescriptorBufferBindings  is not 1";
    }

    VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr};
    vkt::DescriptorSetLayout ds_layout(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);

    VkDeviceSize ds_layout_size = ds_layout.GetDescriptorBufferSize();
    vkt::Buffer descriptor_buffer(*m_device, ds_layout_size, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT,
                                  vkt::device_address);

    vkt::Buffer buffer_data(*m_device, 32, 0, vkt::device_address);
    VkDescriptorAddressInfoEXT addr_info = vku::InitStructHelper();
    addr_info.address = buffer_data.Address();
    addr_info.range = 32;
    addr_info.format = VK_FORMAT_UNDEFINED;

    VkDescriptorGetInfoEXT buffer_descriptor_info = vku::InitStructHelper();
    buffer_descriptor_info.type = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
    buffer_descriptor_info.data.pStorageBuffer = &addr_info;

    void* mapped_descriptor_data = descriptor_buffer.Memory().Map();
    vk::GetDescriptorEXT(device(), &buffer_descriptor_info, descriptor_buffer_properties.storageBufferDescriptorSize,
                         mapped_descriptor_data);

    m_command_buffer.Begin();

    VkDescriptorBufferBindingInfoEXT descriptor_buffer_binding_infos[2];
    descriptor_buffer_binding_infos[0] = vku::InitStructHelper();
    descriptor_buffer_binding_infos[0].address = descriptor_buffer.Address();
    descriptor_buffer_binding_infos[0].usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    descriptor_buffer_binding_infos[1] = vku::InitStructHelper();
    descriptor_buffer_binding_infos[1].address = descriptor_buffer.Address();
    descriptor_buffer_binding_infos[1].usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;

    // VUID-vkCmdBindDescriptorBuffersEXT-maxResourceDescriptorBufferBindings-08049
    m_errorMonitor->SetDesiredError(
        "Addresses pointing to the same VkBuffer still count as multiple 'descriptor buffer bindings' towards the limits");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 2, descriptor_buffer_binding_infos);
    m_errorMonitor->VerifyFound();

    m_command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, CommandBufferRecording) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());
    InitRenderTarget();

    vkt::Buffer buffer(*m_device, 4096, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT, vkt::device_address);

    VkDescriptorBufferBindingInfoEXT buffer_binding_info = vku::InitStructHelper();
    buffer_binding_info.address = buffer.Address();
    buffer_binding_info.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;

    const VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1, VK_SHADER_STAGE_VERTEX_BIT, nullptr};
    const vkt::DescriptorSetLayout set_layout(*m_device, {binding}, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    const vkt::PipelineLayout pipeline_layout(*m_device, {&set_layout});

    CreatePipelineHelper pipe(*this);
    pipe.gp_ci_.flags |= VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    pipe.gp_ci_.layout = pipeline_layout;
    pipe.CreateGraphicsPipeline();

    const uint32_t index = 0;
    const VkDeviceSize offset = 0;

    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBuffersEXT-commandBuffer-recording");
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &buffer_binding_info);
    m_errorMonitor->VerifyFound();
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBufferEmbeddedSamplersEXT-commandBuffer-recording");
    m_errorMonitor->SetDesiredError("VUID-vkCmdBindDescriptorBufferEmbeddedSamplersEXT-set-08070");
    vk::CmdBindDescriptorBufferEmbeddedSamplersEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0);
    m_errorMonitor->VerifyFound();
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-commandBuffer-recording");
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-pBufferIndices-08065");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &index, &offset);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, PushDescriptor) {
    AddRequiredExtensions(VK_KHR_PUSH_DESCRIPTOR_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::descriptorBufferPushDescriptors);
    AddRequiredFeature(vkt::Feature::pushDescriptor);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    OneOffDescriptorSet descriptor_set(
        m_device,
        {
            {0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr},
        },
        VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT | VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR);
    vkt::PipelineLayout pipeline_layout(*m_device, {&descriptor_set.layout_});

    VkBufferUsageFlags descriptor_buffer_usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    if (!descriptor_buffer_properties.bufferlessPushDescriptors) {
        descriptor_buffer_usage |= VK_BUFFER_USAGE_PUSH_DESCRIPTORS_DESCRIPTOR_BUFFER_BIT_EXT;
    }
    vkt::Buffer descriptor_buffer(*m_device, 4096, descriptor_buffer_usage, vkt::device_address);

    CreateComputePipelineHelper pipe(*this);
    pipe.cp_ci_.flags |= VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    pipe.cp_ci_.layout = pipeline_layout;
    pipe.CreateComputePipeline();

    m_command_buffer.Begin();
    vk::CmdBindPipeline(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipe);

    VkDescriptorBufferBindingPushDescriptorBufferHandleEXT descriptor_buffer_push_descriptor_buffer_handle =
        vku::InitStructHelper();
    descriptor_buffer_push_descriptor_buffer_handle.buffer = descriptor_buffer;

    VkDescriptorBufferBindingInfoEXT descriptor_buffer_binding_info = vku::InitStructHelper();
    descriptor_buffer_binding_info.address = descriptor_buffer.Address();
    descriptor_buffer_binding_info.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    if (!descriptor_buffer_properties.bufferlessPushDescriptors) {
        descriptor_buffer_binding_info.pNext = &descriptor_buffer_push_descriptor_buffer_handle;
        descriptor_buffer_binding_info.usage |= VK_BUFFER_USAGE_PUSH_DESCRIPTORS_DESCRIPTOR_BUFFER_BIT_EXT;
    }
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &descriptor_buffer_binding_info);

    uint32_t buffer_index = 0;
    VkDeviceSize buffer_offset = 0;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-firstSet-11803");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                         &buffer_offset);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, AddressOutOfBounds) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    const uint32_t alignment = static_cast<uint32_t>(m_device->Physical().limits_.minStorageBufferOffsetAlignment);
    vkt::Buffer buffer_data(*m_device, 16, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, vkt::device_address);
    VkDeviceAddress start_address = buffer_data.Address();

    vkt::DescriptorGetInfo get_info(VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, buffer_data, 4);
    uint8_t host_descriptor[1024];

    // VUID-VkDeviceAddress-size-11364
    m_errorMonitor->SetDesiredError("Below at range");
    get_info.address_info.address = start_address + (alignment * 50);  // OOB
    vk::GetDescriptorEXT(device(), get_info, descriptor_buffer_properties.storageBufferDescriptorSize, host_descriptor);
    m_errorMonitor->VerifyFound();

    // VUID-VkDeviceAddress-size-11364
    m_errorMonitor->SetDesiredError("Above at range");
    get_info.address_info.address = start_address - (alignment * 50);  // OOB
    vk::GetDescriptorEXT(device(), get_info, descriptor_buffer_properties.storageBufferDescriptorSize, host_descriptor);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, EmbeddedSamplers) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    vkt::Sampler sampler(*m_device, SafeSaneSamplerCreateInfo());

    const VkDescriptorSetLayoutBinding sampler_binding = {0, VK_DESCRIPTOR_TYPE_SAMPLER, 1, VK_SHADER_STAGE_ALL, &sampler.handle()};
    VkDescriptorSetLayoutCreateInfo sampler_ds_layout_ci = vku::InitStructHelper();
    sampler_ds_layout_ci.flags = VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT |
                                 VK_DESCRIPTOR_SET_LAYOUT_CREATE_EMBEDDED_IMMUTABLE_SAMPLERS_BIT_EXT;
    sampler_ds_layout_ci.bindingCount = 1u;
    sampler_ds_layout_ci.pBindings = &sampler_binding;
    vkt::DescriptorSetLayout sampler_ds_layout(*m_device, sampler_ds_layout_ci);
    vkt::PipelineLayout pipeline_layout(*m_device, {&sampler_ds_layout});

    VkBufferUsageFlags descriptor_buffer_usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;
    vkt::Buffer descriptor_buffer(*m_device, 4096, descriptor_buffer_usage, vkt::device_address);

    CreateComputePipelineHelper pipe(*this);
    pipe.cp_ci_.flags |= VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    pipe.cp_ci_.layout = pipeline_layout;
    pipe.CreateComputePipeline();

    m_command_buffer.Begin();
    vk::CmdBindPipeline(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipe);

    VkDescriptorBufferBindingInfoEXT descriptor_buffer_binding_info = vku::InitStructHelper();
    descriptor_buffer_binding_info.address = descriptor_buffer.Address();
    descriptor_buffer_binding_info.usage = VK_BUFFER_USAGE_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT;
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &descriptor_buffer_binding_info);

    uint32_t buffer_index = 0;
    VkDeviceSize buffer_offset = 0;
    m_errorMonitor->SetDesiredError("VUID-vkCmdSetDescriptorBufferOffsetsEXT-firstSet-11804");
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipeline_layout, 0, 1, &buffer_index,
                                         &buffer_offset);
    m_errorMonitor->VerifyFound();
}

TEST_F(NegativeDescriptorBuffer, GetDescriptorAlignment) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    uint8_t host_descriptor[1024];

    if (m_device->Physical().limits_.minStorageBufferOffsetAlignment != 1) {
        vkt::Buffer buffer_data(*m_device, 64, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, vkt::device_address);
        vkt::DescriptorGetInfo get_info(VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, buffer_data, 4);
        get_info.address_info.address += 1;

        m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12266");
        vk::GetDescriptorEXT(device(), get_info, descriptor_buffer_properties.storageBufferDescriptorSize, host_descriptor);
        m_errorMonitor->VerifyFound();
    }

    if (m_device->Physical().limits_.minUniformBufferOffsetAlignment != 1) {
        vkt::Buffer buffer_data(*m_device, 64, VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT, vkt::device_address);
        vkt::DescriptorGetInfo get_info(VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, buffer_data, 4);
        get_info.address_info.address += 1;

        m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12265");
        vk::GetDescriptorEXT(device(), get_info, descriptor_buffer_properties.uniformBufferDescriptorSize, host_descriptor);
        m_errorMonitor->VerifyFound();
    }

    if (m_device->Physical().limits_.minTexelBufferOffsetAlignment != 1) {
        vkt::Buffer u_buffer(*m_device, 32, VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT, vkt::device_address);
        vkt::DescriptorGetInfo get_info_u(VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, u_buffer, 4, VK_FORMAT_R32_UINT);
        get_info_u.address_info.address += 1;

        m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12269");
        vk::GetDescriptorEXT(device(), get_info_u, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, host_descriptor);
        m_errorMonitor->VerifyFound();

        vkt::Buffer s_buffer(*m_device, 32, VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT, vkt::device_address);
        vkt::DescriptorGetInfo get_info_s(VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, s_buffer, 4, VK_FORMAT_R32_UINT);
        get_info_s.address_info.address += 1;

        m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12270");
        vk::GetDescriptorEXT(device(), get_info_s, descriptor_buffer_properties.storageTexelBufferDescriptorSize, host_descriptor);
        m_errorMonitor->VerifyFound();
    }
}

TEST_F(NegativeDescriptorBuffer, GetDescriptorAlignment2) {
    AddRequiredExtensions(VK_EXT_TEXEL_BUFFER_ALIGNMENT_EXTENSION_NAME);
    AddRequiredFeature(vkt::Feature::texelBufferAlignment);
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());
    VkPhysicalDeviceTexelBufferAlignmentPropertiesEXT align_props = vku::InitStructHelper();
    GetPhysicalDeviceProperties2(align_props);

    uint8_t host_descriptor[1024];

    if (align_props.uniformTexelBufferOffsetAlignmentBytes != 1) {
        vkt::Buffer u_buffer(*m_device, 32, VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT, vkt::device_address);
        vkt::DescriptorGetInfo get_info_u(VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, u_buffer, 4, VK_FORMAT_R32_UINT);
        get_info_u.address_info.address += 1;

        m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12269");
        vk::GetDescriptorEXT(device(), get_info_u, descriptor_buffer_properties.uniformTexelBufferDescriptorSize, host_descriptor);
        m_errorMonitor->VerifyFound();
    }

    if (align_props.storageTexelBufferOffsetAlignmentBytes != 1) {
        vkt::Buffer s_buffer(*m_device, 32, VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT, vkt::device_address);
        vkt::DescriptorGetInfo get_info_s(VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, s_buffer, 4, VK_FORMAT_R32_UINT);
        get_info_s.address_info.address += 1;

        m_errorMonitor->SetDesiredError("VUID-VkDescriptorGetInfoEXT-type-12270");
        vk::GetDescriptorEXT(device(), get_info_s, descriptor_buffer_properties.storageTexelBufferDescriptorSize, host_descriptor);
        m_errorMonitor->VerifyFound();
    }
}

TEST_F(NegativeDescriptorBuffer, NoCmdSetDescriptorBufferOffsets) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    VkDescriptorSetLayoutBinding binding = {0, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1, VK_SHADER_STAGE_ALL, nullptr};
    vkt::DescriptorSetLayout ds_layout(*m_device, binding, VK_DESCRIPTOR_SET_LAYOUT_CREATE_DESCRIPTOR_BUFFER_BIT_EXT);
    vkt::PipelineLayout pipeline_layout(*m_device, {&ds_layout});

    VkDeviceSize ds_layout_size = ds_layout.GetDescriptorBufferSize();
    vkt::Buffer descriptor_buffer(*m_device, ds_layout_size, VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT,
                                  vkt::device_address);

    const char* cs_source = R"glsl(
        #version 450
        layout (set = 0, binding = 0) buffer SSBO_0 {
            uint a;
        };

        void main() {
            a = 0;
        }
    )glsl";

    CreateComputePipelineHelper pipe(*this);
    pipe.cs_ = VkShaderObj(*m_device, cs_source, VK_SHADER_STAGE_COMPUTE_BIT, SPV_ENV_VULKAN_1_2);
    pipe.cp_ci_.flags |= VK_PIPELINE_CREATE_DESCRIPTOR_BUFFER_BIT_EXT;
    pipe.cp_ci_.layout = pipeline_layout;
    pipe.CreateComputePipeline();

    m_command_buffer.Begin();
    vk::CmdBindPipeline(m_command_buffer, VK_PIPELINE_BIND_POINT_COMPUTE, pipe);

    VkDescriptorBufferBindingInfoEXT descriptor_buffer_binding_info = vku::InitStructHelper();
    descriptor_buffer_binding_info.address = descriptor_buffer.Address();
    descriptor_buffer_binding_info.usage = VK_BUFFER_USAGE_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT;
    vk::CmdBindDescriptorBuffersEXT(m_command_buffer, 1, &descriptor_buffer_binding_info);

    uint32_t buffer_index = 0;
    VkDeviceSize buffer_offset = 0;
    vk::CmdSetDescriptorBufferOffsetsEXT(m_command_buffer, VK_PIPELINE_BIND_POINT_GRAPHICS, pipeline_layout, 0, 1, &buffer_index,
                                         &buffer_offset);
    m_errorMonitor->SetDesiredWarning("WARNING-Missing-vkCmdSetDescriptorBufferOffsets");
    vk::CmdDispatch(m_command_buffer, 1, 1, 1);
    m_errorMonitor->VerifyFound();
    m_command_buffer.End();
}

TEST_F(NegativeDescriptorBuffer, MaxBufferRange) {
    RETURN_IF_SKIP(InitBasicDescriptorBuffer());

    if (!IsPlatformMockICD()) {
        GTEST_SKIP() << "Easier to control limit test on MockICD.";
    }

    const uint32_t max_ubo_range = m_device->Physical().limits_.maxUniformBufferRange;
    const uint32_t max_ssbo_range = m_device->Physical().limits_.maxStorageBufferRange;

    vkt::Buffer buffer_ubo(*m_device, max_ubo_range + 64, VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT, vkt::device_address);
    vkt::Buffer buffer_ssbo(*m_device, max_ssbo_range + 64, VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, vkt::device_address);

    uint8_t host_data[256];

    vkt::DescriptorGetInfo get_info_u(VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, buffer_ubo, buffer_ubo.CreateInfo().size);
    m_errorMonitor->SetDesiredError("UNASSIGNED-VkDescriptorAddressInfoEXT-range-UBO");
    vk::GetDescriptorEXT(device(), get_info_u, descriptor_buffer_properties.uniformBufferDescriptorSize, host_data);
    m_errorMonitor->VerifyFound();

    vkt::DescriptorGetInfo get_info_s(VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, buffer_ssbo, buffer_ssbo.CreateInfo().size);
    m_errorMonitor->SetDesiredError("UNASSIGNED-VkDescriptorAddressInfoEXT-range-SSBO");
    vk::GetDescriptorEXT(device(), get_info_s, descriptor_buffer_properties.storageBufferDescriptorSize, host_data);
    m_errorMonitor->VerifyFound();
}