blob: 27c60eb28ca8259809cf3943fab7d1b34e55fe8e [file] [log] [blame]
// This file is ***GENERATED***. Do Not Edit.
// See layer_chassis_generator.py for modifications.
/* Copyright (c) 2015-2019 The Khronos Group Inc.
* Copyright (c) 2015-2019 Valve Corporation
* Copyright (c) 2015-2019 LunarG, Inc.
* Copyright (c) 2015-2019 Google Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* Author: Mark Lobodzinski <mark@lunarg.com>
*/
#include <string.h>
#include <mutex>
#define VALIDATION_ERROR_MAP_IMPL
#include "chassis.h"
#include "layer_chassis_dispatch.h"
small_unordered_map<void*, ValidationObject*, 2> layer_data_map;
// Global unique object identifier.
std::atomic<uint64_t> global_unique_id(1ULL);
// Map uniqueID to actual object handle. Accesses to the map itself are
// internally synchronized.
vl_concurrent_unordered_map<uint64_t, uint64_t, 4, HashedUint64> unique_id_mapping;
bool wrap_handles = true;
#define OBJECT_LAYER_NAME "VK_LAYER_KHRONOS_validation"
#define OBJECT_LAYER_DESCRIPTION "khronos_validation"
// Include layer validation object definitions
#include "best_practices.h"
#include "core_validation.h"
#include "gpu_validation.h"
#include "object_lifetime_validation.h"
#include "stateless_validation.h"
#include "thread_safety.h"
namespace vulkan_layer_chassis {
using std::unordered_map;
static const VkLayerProperties global_layer = {
OBJECT_LAYER_NAME, VK_LAYER_API_VERSION, 1, "LunarG validation Layer",
};
static const VkExtensionProperties instance_extensions[] = {{VK_EXT_DEBUG_REPORT_EXTENSION_NAME, VK_EXT_DEBUG_REPORT_SPEC_VERSION},
{VK_EXT_DEBUG_UTILS_EXTENSION_NAME, VK_EXT_DEBUG_UTILS_SPEC_VERSION}};
static const VkExtensionProperties device_extensions[] = {
{VK_EXT_VALIDATION_CACHE_EXTENSION_NAME, VK_EXT_VALIDATION_CACHE_SPEC_VERSION},
{VK_EXT_DEBUG_MARKER_EXTENSION_NAME, VK_EXT_DEBUG_MARKER_SPEC_VERSION},
};
typedef struct {
bool is_instance_api;
void* funcptr;
} function_data;
extern const std::unordered_map<std::string, function_data> name_to_funcptr_map;
// Manually written functions
// Check enabled instance extensions against supported instance extension whitelist
static void InstanceExtensionWhitelist(ValidationObject *layer_data, const VkInstanceCreateInfo *pCreateInfo, VkInstance instance) {
for (uint32_t i = 0; i < pCreateInfo->enabledExtensionCount; i++) {
// Check for recognized instance extensions
if (!white_list(pCreateInfo->ppEnabledExtensionNames[i], kInstanceExtensionNames)) {
log_msg(layer_data->report_data, VK_DEBUG_REPORT_WARNING_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0,
kVUIDUndefined,
"Instance Extension %s is not supported by this layer. Using this extension may adversely affect validation "
"results and/or produce undefined behavior.",
pCreateInfo->ppEnabledExtensionNames[i]);
}
}
}
// Check enabled device extensions against supported device extension whitelist
static void DeviceExtensionWhitelist(ValidationObject *layer_data, const VkDeviceCreateInfo *pCreateInfo, VkDevice device) {
for (uint32_t i = 0; i < pCreateInfo->enabledExtensionCount; i++) {
// Check for recognized device extensions
if (!white_list(pCreateInfo->ppEnabledExtensionNames[i], kDeviceExtensionNames)) {
log_msg(layer_data->report_data, VK_DEBUG_REPORT_WARNING_BIT_EXT, VK_DEBUG_REPORT_OBJECT_TYPE_UNKNOWN_EXT, 0,
kVUIDUndefined,
"Device Extension %s is not supported by this layer. Using this extension may adversely affect validation "
"results and/or produce undefined behavior.",
pCreateInfo->ppEnabledExtensionNames[i]);
}
}
}
// Process validation features, flags and settings specified through extensions, a layer settings file, or environment variables
static const std::unordered_map<std::string, VkValidationFeatureDisableEXT> VkValFeatureDisableLookup = {
{"VK_VALIDATION_FEATURE_DISABLE_SHADERS_EXT", VK_VALIDATION_FEATURE_DISABLE_SHADERS_EXT},
{"VK_VALIDATION_FEATURE_DISABLE_THREAD_SAFETY_EXT", VK_VALIDATION_FEATURE_DISABLE_THREAD_SAFETY_EXT},
{"VK_VALIDATION_FEATURE_DISABLE_API_PARAMETERS_EXT", VK_VALIDATION_FEATURE_DISABLE_API_PARAMETERS_EXT},
{"VK_VALIDATION_FEATURE_DISABLE_OBJECT_LIFETIMES_EXT", VK_VALIDATION_FEATURE_DISABLE_OBJECT_LIFETIMES_EXT},
{"VK_VALIDATION_FEATURE_DISABLE_CORE_CHECKS_EXT", VK_VALIDATION_FEATURE_DISABLE_CORE_CHECKS_EXT},
{"VK_VALIDATION_FEATURE_DISABLE_UNIQUE_HANDLES_EXT", VK_VALIDATION_FEATURE_DISABLE_UNIQUE_HANDLES_EXT},
{"VK_VALIDATION_FEATURE_DISABLE_ALL_EXT", VK_VALIDATION_FEATURE_DISABLE_ALL_EXT},
};
static const std::unordered_map<std::string, VkValidationFeatureEnableEXT> VkValFeatureEnableLookup = {
{"VK_VALIDATION_FEATURE_ENABLE_GPU_ASSISTED_EXT", VK_VALIDATION_FEATURE_ENABLE_GPU_ASSISTED_EXT},
{"VK_VALIDATION_FEATURE_ENABLE_GPU_ASSISTED_RESERVE_BINDING_SLOT_EXT", VK_VALIDATION_FEATURE_ENABLE_GPU_ASSISTED_RESERVE_BINDING_SLOT_EXT},
{"VK_VALIDATION_FEATURE_ENABLE_BEST_PRACTICES_EXT", VK_VALIDATION_FEATURE_ENABLE_BEST_PRACTICES_EXT},
};
static const std::unordered_map<std::string, ValidationCheckDisables> ValidationDisableLookup = {
{"VALIDATION_CHECK_DISABLE_COMMAND_BUFFER_STATE", VALIDATION_CHECK_DISABLE_COMMAND_BUFFER_STATE},
{"VALIDATION_CHECK_DISABLE_OBJECT_IN_USE", VALIDATION_CHECK_DISABLE_OBJECT_IN_USE},
{"VALIDATION_CHECK_DISABLE_IDLE_DESCRIPTOR_SET", VALIDATION_CHECK_DISABLE_IDLE_DESCRIPTOR_SET},
{"VALIDATION_CHECK_DISABLE_PUSH_CONSTANT_RANGE", VALIDATION_CHECK_DISABLE_PUSH_CONSTANT_RANGE},
{"VALIDATION_CHECK_DISABLE_QUERY_VALIDATION", VALIDATION_CHECK_DISABLE_QUERY_VALIDATION},
{"VALIDATION_CHECK_DISABLE_IMAGE_LAYOUT_VALIDATION", VALIDATION_CHECK_DISABLE_IMAGE_LAYOUT_VALIDATION},
};
// Set the local disable flag for the appropriate VALIDATION_CHECK_DISABLE enum
void SetValidationDisable(CHECK_DISABLED* disable_data, const ValidationCheckDisables disable_id) {
switch (disable_id) {
case VALIDATION_CHECK_DISABLE_COMMAND_BUFFER_STATE:
disable_data->command_buffer_state = true;
break;
case VALIDATION_CHECK_DISABLE_OBJECT_IN_USE:
disable_data->object_in_use = true;
break;
case VALIDATION_CHECK_DISABLE_IDLE_DESCRIPTOR_SET:
disable_data->idle_descriptor_set = true;
break;
case VALIDATION_CHECK_DISABLE_PUSH_CONSTANT_RANGE:
disable_data->push_constant_range = true;
break;
case VALIDATION_CHECK_DISABLE_QUERY_VALIDATION:
disable_data->query_validation = true;
break;
case VALIDATION_CHECK_DISABLE_IMAGE_LAYOUT_VALIDATION:
disable_data->image_layout_validation = true;
break;
default:
assert(true);
}
}
// Set the local disable flag for a single VK_VALIDATION_FEATURE_DISABLE_* flag
void SetValidationFeatureDisable(CHECK_DISABLED* disable_data, const VkValidationFeatureDisableEXT feature_disable) {
switch (feature_disable) {
case VK_VALIDATION_FEATURE_DISABLE_SHADERS_EXT:
disable_data->shader_validation = true;
break;
case VK_VALIDATION_FEATURE_DISABLE_THREAD_SAFETY_EXT:
disable_data->thread_safety = true;
break;
case VK_VALIDATION_FEATURE_DISABLE_API_PARAMETERS_EXT:
disable_data->stateless_checks = true;
break;
case VK_VALIDATION_FEATURE_DISABLE_OBJECT_LIFETIMES_EXT:
disable_data->object_tracking = true;
break;
case VK_VALIDATION_FEATURE_DISABLE_CORE_CHECKS_EXT:
disable_data->core_checks = true;
break;
case VK_VALIDATION_FEATURE_DISABLE_UNIQUE_HANDLES_EXT:
disable_data->handle_wrapping = true;
break;
case VK_VALIDATION_FEATURE_DISABLE_ALL_EXT:
// Set all disabled flags to true
disable_data->SetAll(true);
break;
default:
break;
}
}
// Set the local enable flag for a single VK_VALIDATION_FEATURE_ENABLE_* flag
void SetValidationFeatureEnable(CHECK_ENABLED *enable_data, const VkValidationFeatureEnableEXT feature_enable) {
switch (feature_enable) {
case VK_VALIDATION_FEATURE_ENABLE_GPU_ASSISTED_EXT:
enable_data->gpu_validation = true;
break;
case VK_VALIDATION_FEATURE_ENABLE_GPU_ASSISTED_RESERVE_BINDING_SLOT_EXT:
enable_data->gpu_validation_reserve_binding_slot = true;
break;
case VK_VALIDATION_FEATURE_ENABLE_BEST_PRACTICES_EXT:
enable_data->best_practices = true;
break;
default:
break;
}
}
// Set the local disable flag for settings specified through the VK_EXT_validation_flags extension
void SetValidationFlags(CHECK_DISABLED* disables, const VkValidationFlagsEXT* val_flags_struct) {
for (uint32_t i = 0; i < val_flags_struct->disabledValidationCheckCount; ++i) {
switch (val_flags_struct->pDisabledValidationChecks[i]) {
case VK_VALIDATION_CHECK_SHADERS_EXT:
disables->shader_validation = true;
break;
case VK_VALIDATION_CHECK_ALL_EXT:
// Set all disabled flags to true
disables->SetAll(true);
break;
default:
break;
}
}
}
// Process Validation Features flags specified through the ValidationFeature extension
void SetValidationFeatures(CHECK_DISABLED *disable_data, CHECK_ENABLED *enable_data,
const VkValidationFeaturesEXT *val_features_struct) {
for (uint32_t i = 0; i < val_features_struct->disabledValidationFeatureCount; ++i) {
SetValidationFeatureDisable(disable_data, val_features_struct->pDisabledValidationFeatures[i]);
}
for (uint32_t i = 0; i < val_features_struct->enabledValidationFeatureCount; ++i) {
SetValidationFeatureEnable(enable_data, val_features_struct->pEnabledValidationFeatures[i]);
}
}
// Given a string representation of a list of enable enum values, call the appropriate setter function
void SetLocalEnableSetting(std::string list_of_enables, std::string delimiter, CHECK_ENABLED* enables) {
size_t pos = 0;
std::string token;
while (list_of_enables.length() != 0) {
pos = list_of_enables.find(delimiter);
if (pos != std::string::npos) {
token = list_of_enables.substr(0, pos);
} else {
pos = list_of_enables.length() - delimiter.length();
token = list_of_enables;
}
if (token.find("VK_VALIDATION_FEATURE_ENABLE_") != std::string::npos) {
auto result = VkValFeatureEnableLookup.find(token);
if (result != VkValFeatureEnableLookup.end()) {
SetValidationFeatureEnable(enables, result->second);
}
}
list_of_enables.erase(0, pos + delimiter.length());
}
}
// Given a string representation of a list of disable enum values, call the appropriate setter function
void SetLocalDisableSetting(std::string list_of_disables, std::string delimiter, CHECK_DISABLED* disables) {
size_t pos = 0;
std::string token;
while (list_of_disables.length() != 0) {
pos = list_of_disables.find(delimiter);
if (pos != std::string::npos) {
token = list_of_disables.substr(0, pos);
} else {
pos = list_of_disables.length() - delimiter.length();
token = list_of_disables;
}
if (token.find("VK_VALIDATION_FEATURE_DISABLE_") != std::string::npos) {
auto result = VkValFeatureDisableLookup.find(token);
if (result != VkValFeatureDisableLookup.end()) {
SetValidationFeatureDisable(disables, result->second);
}
}
if (token.find("VALIDATION_CHECK_DISABLE_") != std::string::npos) {
auto result = ValidationDisableLookup.find(token);
if (result != ValidationDisableLookup.end()) {
SetValidationDisable(disables, result->second);
}
}
list_of_disables.erase(0, pos + delimiter.length());
}
}
// Process enables and disables set though the vk_layer_settings.txt config file or through an environment variable
void ProcessConfigAndEnvSettings(const char* layer_description, CHECK_ENABLED* enables, CHECK_DISABLED* disables) {
std::string enable_key = layer_description;
std::string disable_key = layer_description;
enable_key.append(".enables");
disable_key.append(".disables");
std::string list_of_config_enables = getLayerOption(enable_key.c_str());
std::string list_of_env_enables = GetLayerEnvVar("VK_LAYER_ENABLES");
std::string list_of_config_disables = getLayerOption(disable_key.c_str());
std::string list_of_env_disables = GetLayerEnvVar("VK_LAYER_DISABLES");
#if defined(_WIN32)
std::string env_delimiter = ";";
#else
std::string env_delimiter = ":";
#endif
SetLocalEnableSetting(list_of_config_enables, ",", enables);
SetLocalEnableSetting(list_of_env_enables, env_delimiter, enables);
SetLocalDisableSetting(list_of_config_disables, ",", disables);
SetLocalDisableSetting(list_of_env_disables, env_delimiter, disables);
}
// Non-code-generated chassis API functions
VKAPI_ATTR PFN_vkVoidFunction VKAPI_CALL GetDeviceProcAddr(VkDevice device, const char *funcName) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
if (!ApiParentExtensionEnabled(funcName, &layer_data->device_extensions)) {
return nullptr;
}
const auto &item = name_to_funcptr_map.find(funcName);
if (item != name_to_funcptr_map.end()) {
if (item->second.is_instance_api) {
return nullptr;
} else {
return reinterpret_cast<PFN_vkVoidFunction>(item->second.funcptr);
}
}
auto &table = layer_data->device_dispatch_table;
if (!table.GetDeviceProcAddr) return nullptr;
return table.GetDeviceProcAddr(device, funcName);
}
VKAPI_ATTR PFN_vkVoidFunction VKAPI_CALL GetInstanceProcAddr(VkInstance instance, const char *funcName) {
const auto &item = name_to_funcptr_map.find(funcName);
if (item != name_to_funcptr_map.end()) {
return reinterpret_cast<PFN_vkVoidFunction>(item->second.funcptr);
}
auto layer_data = GetLayerDataPtr(get_dispatch_key(instance), layer_data_map);
auto &table = layer_data->instance_dispatch_table;
if (!table.GetInstanceProcAddr) return nullptr;
return table.GetInstanceProcAddr(instance, funcName);
}
VKAPI_ATTR VkResult VKAPI_CALL EnumerateInstanceLayerProperties(uint32_t *pCount, VkLayerProperties *pProperties) {
return util_GetLayerProperties(1, &global_layer, pCount, pProperties);
}
VKAPI_ATTR VkResult VKAPI_CALL EnumerateDeviceLayerProperties(VkPhysicalDevice physicalDevice, uint32_t *pCount,
VkLayerProperties *pProperties) {
return util_GetLayerProperties(1, &global_layer, pCount, pProperties);
}
VKAPI_ATTR VkResult VKAPI_CALL EnumerateInstanceExtensionProperties(const char *pLayerName, uint32_t *pCount,
VkExtensionProperties *pProperties) {
if (pLayerName && !strcmp(pLayerName, global_layer.layerName))
return util_GetExtensionProperties(ARRAY_SIZE(instance_extensions), instance_extensions, pCount, pProperties);
return VK_ERROR_LAYER_NOT_PRESENT;
}
VKAPI_ATTR VkResult VKAPI_CALL EnumerateDeviceExtensionProperties(VkPhysicalDevice physicalDevice, const char *pLayerName,
uint32_t *pCount, VkExtensionProperties *pProperties) {
if (pLayerName && !strcmp(pLayerName, global_layer.layerName)) return util_GetExtensionProperties(ARRAY_SIZE(device_extensions), device_extensions, pCount, pProperties);
assert(physicalDevice);
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
return layer_data->instance_dispatch_table.EnumerateDeviceExtensionProperties(physicalDevice, pLayerName, pCount, pProperties);
}
VKAPI_ATTR VkResult VKAPI_CALL CreateInstance(const VkInstanceCreateInfo *pCreateInfo, const VkAllocationCallbacks *pAllocator,
VkInstance *pInstance) {
VkLayerInstanceCreateInfo* chain_info = get_chain_info(pCreateInfo, VK_LAYER_LINK_INFO);
assert(chain_info->u.pLayerInfo);
PFN_vkGetInstanceProcAddr fpGetInstanceProcAddr = chain_info->u.pLayerInfo->pfnNextGetInstanceProcAddr;
PFN_vkCreateInstance fpCreateInstance = (PFN_vkCreateInstance)fpGetInstanceProcAddr(NULL, "vkCreateInstance");
if (fpCreateInstance == NULL) return VK_ERROR_INITIALIZATION_FAILED;
chain_info->u.pLayerInfo = chain_info->u.pLayerInfo->pNext;
uint32_t specified_version = (pCreateInfo->pApplicationInfo ? pCreateInfo->pApplicationInfo->apiVersion : VK_API_VERSION_1_0);
uint32_t api_version = (specified_version < VK_API_VERSION_1_1) ? VK_API_VERSION_1_0 : VK_API_VERSION_1_1;
auto report_data = new debug_report_data{};
report_data->instance_pnext_chain = SafePnextCopy(pCreateInfo->pNext);
ActivateInstanceDebugCallbacks(report_data);
CHECK_ENABLED local_enables {};
CHECK_DISABLED local_disables {};
const auto *validation_features_ext = lvl_find_in_chain<VkValidationFeaturesEXT>(pCreateInfo->pNext);
if (validation_features_ext) {
SetValidationFeatures(&local_disables, &local_enables, validation_features_ext);
}
const auto *validation_flags_ext = lvl_find_in_chain<VkValidationFlagsEXT>(pCreateInfo->pNext);
if (validation_flags_ext) {
SetValidationFlags(&local_disables, validation_flags_ext);
}
ProcessConfigAndEnvSettings(OBJECT_LAYER_DESCRIPTION, &local_enables, &local_disables);
// Create temporary dispatch vector for pre-calls until instance is created
std::vector<ValidationObject*> local_object_dispatch;
// Add VOs to dispatch vector. Order here will be the validation dispatch order!
auto thread_checker = new ThreadSafety(nullptr);
if (!local_disables.thread_safety) {
local_object_dispatch.emplace_back(thread_checker);
}
thread_checker->container_type = LayerObjectTypeThreading;
thread_checker->api_version = api_version;
thread_checker->report_data = report_data;
auto parameter_validation = new StatelessValidation;
if (!local_disables.stateless_checks) {
local_object_dispatch.emplace_back(parameter_validation);
}
parameter_validation->container_type = LayerObjectTypeParameterValidation;
parameter_validation->api_version = api_version;
parameter_validation->report_data = report_data;
auto object_tracker = new ObjectLifetimes;
if (!local_disables.object_tracking) {
local_object_dispatch.emplace_back(object_tracker);
}
object_tracker->container_type = LayerObjectTypeObjectTracker;
object_tracker->api_version = api_version;
object_tracker->report_data = report_data;
auto core_checks = new CoreChecks;
if (!local_disables.core_checks) {
local_object_dispatch.emplace_back(core_checks);
}
core_checks->container_type = LayerObjectTypeCoreValidation;
core_checks->api_version = api_version;
core_checks->report_data = report_data;
auto best_practices = new BestPractices;
if (local_enables.best_practices) {
local_object_dispatch.emplace_back(best_practices);
}
best_practices->container_type = LayerObjectTypeBestPractices;
best_practices->api_version = api_version;
best_practices->report_data = report_data;
auto gpu_assisted = new GpuAssisted;
if (local_enables.gpu_validation) {
local_object_dispatch.emplace_back(gpu_assisted);
}
gpu_assisted->container_type = LayerObjectTypeGpuAssisted;
// If handle wrapping is disabled via the ValidationFeatures extension, override build flag
if (local_disables.handle_wrapping) {
wrap_handles = false;
}
// Init dispatch array and call registration functions
for (auto intercept : local_object_dispatch) {
(const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateInstance(pCreateInfo, pAllocator, pInstance);
}
for (auto intercept : local_object_dispatch) {
intercept->PreCallRecordCreateInstance(pCreateInfo, pAllocator, pInstance);
}
VkResult result = fpCreateInstance(pCreateInfo, pAllocator, pInstance);
if (result != VK_SUCCESS) return result;
auto framework = GetLayerDataPtr(get_dispatch_key(*pInstance), layer_data_map);
framework->object_dispatch = local_object_dispatch;
framework->container_type = LayerObjectTypeInstance;
framework->disabled = local_disables;
framework->enabled = local_enables;
framework->instance = *pInstance;
layer_init_instance_dispatch_table(*pInstance, &framework->instance_dispatch_table, fpGetInstanceProcAddr);
framework->report_data = report_data;
framework->api_version = api_version;
framework->instance_extensions.InitFromInstanceCreateInfo(specified_version, pCreateInfo);
layer_debug_messenger_actions(framework->report_data, pAllocator, OBJECT_LAYER_DESCRIPTION);
object_tracker->instance_dispatch_table = framework->instance_dispatch_table;
object_tracker->enabled = framework->enabled;
object_tracker->disabled = framework->disabled;
thread_checker->instance_dispatch_table = framework->instance_dispatch_table;
thread_checker->enabled = framework->enabled;
thread_checker->disabled = framework->disabled;
parameter_validation->instance_dispatch_table = framework->instance_dispatch_table;
parameter_validation->enabled = framework->enabled;
parameter_validation->disabled = framework->disabled;
core_checks->instance_dispatch_table = framework->instance_dispatch_table;
core_checks->instance = *pInstance;
core_checks->enabled = framework->enabled;
core_checks->disabled = framework->disabled;
core_checks->instance_state = core_checks;
best_practices->instance_dispatch_table = framework->instance_dispatch_table;
best_practices->enabled = framework->enabled;
best_practices->disabled = framework->disabled;
gpu_assisted->instance_dispatch_table = framework->instance_dispatch_table;
gpu_assisted->enabled = framework->enabled;
gpu_assisted->disabled = framework->disabled;
for (auto intercept : framework->object_dispatch) {
intercept->PostCallRecordCreateInstance(pCreateInfo, pAllocator, pInstance, result);
}
InstanceExtensionWhitelist(framework, pCreateInfo, *pInstance);
DeactivateInstanceDebugCallbacks(report_data);
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyInstance(VkInstance instance, const VkAllocationCallbacks *pAllocator) {
dispatch_key key = get_dispatch_key(instance);
auto layer_data = GetLayerDataPtr(key, layer_data_map);
ActivateInstanceDebugCallbacks(layer_data->report_data);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
(const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyInstance(instance, pAllocator);
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyInstance(instance, pAllocator);
}
layer_data->instance_dispatch_table.DestroyInstance(instance, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyInstance(instance, pAllocator);
}
DeactivateInstanceDebugCallbacks(layer_data->report_data);
FreePnextChain(layer_data->report_data->instance_pnext_chain);
layer_debug_utils_destroy_instance(layer_data->report_data);
for (auto item = layer_data->object_dispatch.begin(); item != layer_data->object_dispatch.end(); item++) {
delete *item;
}
FreeLayerDataPtr(key, layer_data_map);
}
VKAPI_ATTR VkResult VKAPI_CALL CreateDevice(VkPhysicalDevice gpu, const VkDeviceCreateInfo *pCreateInfo,
const VkAllocationCallbacks *pAllocator, VkDevice *pDevice) {
VkLayerDeviceCreateInfo *chain_info = get_chain_info(pCreateInfo, VK_LAYER_LINK_INFO);
auto instance_interceptor = GetLayerDataPtr(get_dispatch_key(gpu), layer_data_map);
PFN_vkGetInstanceProcAddr fpGetInstanceProcAddr = chain_info->u.pLayerInfo->pfnNextGetInstanceProcAddr;
PFN_vkGetDeviceProcAddr fpGetDeviceProcAddr = chain_info->u.pLayerInfo->pfnNextGetDeviceProcAddr;
PFN_vkCreateDevice fpCreateDevice = (PFN_vkCreateDevice)fpGetInstanceProcAddr(instance_interceptor->instance, "vkCreateDevice");
if (fpCreateDevice == NULL) {
return VK_ERROR_INITIALIZATION_FAILED;
}
chain_info->u.pLayerInfo = chain_info->u.pLayerInfo->pNext;
// Get physical device limits for device
VkPhysicalDeviceProperties device_properties = {};
instance_interceptor->instance_dispatch_table.GetPhysicalDeviceProperties(gpu, &device_properties);
// Setup the validation tables based on the application API version from the instance and the capabilities of the device driver
uint32_t effective_api_version = std::min(device_properties.apiVersion, instance_interceptor->api_version);
DeviceExtensions device_extensions = {};
device_extensions.InitFromDeviceCreateInfo(&instance_interceptor->instance_extensions, effective_api_version, pCreateInfo);
for (auto item : instance_interceptor->object_dispatch) {
item->device_extensions = device_extensions;
}
safe_VkDeviceCreateInfo modified_create_info(pCreateInfo);
bool skip = false;
for (auto intercept : instance_interceptor->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateDevice(gpu, pCreateInfo, pAllocator, pDevice);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : instance_interceptor->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateDevice(gpu, pCreateInfo, pAllocator, pDevice, &modified_create_info);
}
VkResult result = fpCreateDevice(gpu, reinterpret_cast<VkDeviceCreateInfo *>(&modified_create_info), pAllocator, pDevice);
if (result != VK_SUCCESS) {
return result;
}
auto device_interceptor = GetLayerDataPtr(get_dispatch_key(*pDevice), layer_data_map);
device_interceptor->container_type = LayerObjectTypeDevice;
// Save local info in device object
device_interceptor->phys_dev_properties.properties = device_properties;
device_interceptor->api_version = device_interceptor->device_extensions.InitFromDeviceCreateInfo(
&instance_interceptor->instance_extensions, effective_api_version, pCreateInfo);
device_interceptor->device_extensions = device_extensions;
layer_init_device_dispatch_table(*pDevice, &device_interceptor->device_dispatch_table, fpGetDeviceProcAddr);
device_interceptor->device = *pDevice;
device_interceptor->physical_device = gpu;
device_interceptor->instance = instance_interceptor->instance;
device_interceptor->report_data = instance_interceptor->report_data;
// Note that this defines the order in which the layer validation objects are called
auto thread_safety = new ThreadSafety(reinterpret_cast<ThreadSafety *>(instance_interceptor->GetValidationObject(instance_interceptor->object_dispatch, LayerObjectTypeThreading)));
thread_safety->container_type = LayerObjectTypeThreading;
if (!instance_interceptor->disabled.thread_safety) {
device_interceptor->object_dispatch.emplace_back(thread_safety);
}
auto stateless_validation = new StatelessValidation;
stateless_validation->container_type = LayerObjectTypeParameterValidation;
if (!instance_interceptor->disabled.stateless_checks) {
device_interceptor->object_dispatch.emplace_back(stateless_validation);
}
auto object_tracker = new ObjectLifetimes;
object_tracker->container_type = LayerObjectTypeObjectTracker;
if (!instance_interceptor->disabled.object_tracking) {
device_interceptor->object_dispatch.emplace_back(object_tracker);
}
auto core_checks = new CoreChecks;
core_checks->container_type = LayerObjectTypeCoreValidation;
core_checks->instance_state = reinterpret_cast<CoreChecks *>(
core_checks->GetValidationObject(instance_interceptor->object_dispatch, LayerObjectTypeCoreValidation));
if (!instance_interceptor->disabled.core_checks) {
device_interceptor->object_dispatch.emplace_back(core_checks);
}
auto best_practices = new BestPractices;
best_practices->container_type = LayerObjectTypeBestPractices;
best_practices->instance_state = reinterpret_cast<BestPractices *>(
best_practices->GetValidationObject(instance_interceptor->object_dispatch, LayerObjectTypeBestPractices));
if (instance_interceptor->enabled.best_practices) {
device_interceptor->object_dispatch.emplace_back(best_practices);
}
auto gpu_assisted = new GpuAssisted;
gpu_assisted->container_type = LayerObjectTypeGpuAssisted;
gpu_assisted->instance_state = reinterpret_cast<GpuAssisted *>(
gpu_assisted->GetValidationObject(instance_interceptor->object_dispatch, LayerObjectTypeGpuAssisted));
if (instance_interceptor->enabled.gpu_validation) {
device_interceptor->object_dispatch.emplace_back(gpu_assisted);
}
// Set per-intercept common data items
for (auto dev_intercept : device_interceptor->object_dispatch) {
dev_intercept->device = *pDevice;
dev_intercept->physical_device = gpu;
dev_intercept->instance = instance_interceptor->instance;
dev_intercept->report_data = device_interceptor->report_data;
dev_intercept->device_dispatch_table = device_interceptor->device_dispatch_table;
dev_intercept->api_version = device_interceptor->api_version;
dev_intercept->disabled = instance_interceptor->disabled;
dev_intercept->enabled = instance_interceptor->enabled;
dev_intercept->instance_dispatch_table = instance_interceptor->instance_dispatch_table;
dev_intercept->instance_extensions = instance_interceptor->instance_extensions;
dev_intercept->device_extensions = device_interceptor->device_extensions;
}
for (auto intercept : instance_interceptor->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateDevice(gpu, pCreateInfo, pAllocator, pDevice, result);
}
DeviceExtensionWhitelist(device_interceptor, pCreateInfo, *pDevice);
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyDevice(VkDevice device, const VkAllocationCallbacks *pAllocator) {
dispatch_key key = get_dispatch_key(device);
auto layer_data = GetLayerDataPtr(key, layer_data_map);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
(const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyDevice(device, pAllocator);
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyDevice(device, pAllocator);
}
layer_data->device_dispatch_table.DestroyDevice(device, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyDevice(device, pAllocator);
}
for (auto item = layer_data->object_dispatch.begin(); item != layer_data->object_dispatch.end(); item++) {
delete *item;
}
FreeLayerDataPtr(key, layer_data_map);
}
// Special-case APIs for which core_validation needs custom parameter lists and/or modifies parameters
VKAPI_ATTR VkResult VKAPI_CALL CreateGraphicsPipelines(
VkDevice device,
VkPipelineCache pipelineCache,
uint32_t createInfoCount,
const VkGraphicsPipelineCreateInfo* pCreateInfos,
const VkAllocationCallbacks* pAllocator,
VkPipeline* pPipelines) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
create_graphics_pipeline_api_state cgpl_state[LayerObjectTypeMaxEnum]{};
for (auto intercept : layer_data->object_dispatch) {
cgpl_state[intercept->container_type].pCreateInfos = pCreateInfos;
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateGraphicsPipelines(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines, &(cgpl_state[intercept->container_type]));
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateGraphicsPipelines(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines, &(cgpl_state[intercept->container_type]));
}
auto usepCreateInfos = (!cgpl_state[LayerObjectTypeGpuAssisted].pCreateInfos) ? pCreateInfos : cgpl_state[LayerObjectTypeGpuAssisted].pCreateInfos;
VkResult result = DispatchCreateGraphicsPipelines(device, pipelineCache, createInfoCount, usepCreateInfos, pAllocator, pPipelines);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateGraphicsPipelines(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines, result, &(cgpl_state[intercept->container_type]));
}
return result;
}
// This API saves some core_validation pipeline state state on the stack for performance purposes
VKAPI_ATTR VkResult VKAPI_CALL CreateComputePipelines(
VkDevice device,
VkPipelineCache pipelineCache,
uint32_t createInfoCount,
const VkComputePipelineCreateInfo* pCreateInfos,
const VkAllocationCallbacks* pAllocator,
VkPipeline* pPipelines) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
create_compute_pipeline_api_state ccpl_state[LayerObjectTypeMaxEnum]{};
for (auto intercept : layer_data->object_dispatch) {
ccpl_state[intercept->container_type].pCreateInfos = pCreateInfos;
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateComputePipelines(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines, &(ccpl_state[intercept->container_type]));
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateComputePipelines(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines, &(ccpl_state[intercept->container_type]));
}
auto usepCreateInfos = (!ccpl_state[LayerObjectTypeGpuAssisted].pCreateInfos) ? pCreateInfos : ccpl_state[LayerObjectTypeGpuAssisted].pCreateInfos;
VkResult result = DispatchCreateComputePipelines(device, pipelineCache, createInfoCount, usepCreateInfos, pAllocator, pPipelines);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateComputePipelines(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines, result, &(ccpl_state[intercept->container_type]));
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL CreateRayTracingPipelinesNV(
VkDevice device,
VkPipelineCache pipelineCache,
uint32_t createInfoCount,
const VkRayTracingPipelineCreateInfoNV* pCreateInfos,
const VkAllocationCallbacks* pAllocator,
VkPipeline* pPipelines) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
create_ray_tracing_pipeline_api_state crtpl_state[LayerObjectTypeMaxEnum]{};
for (auto intercept : layer_data->object_dispatch) {
crtpl_state[intercept->container_type].pCreateInfos = pCreateInfos;
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateRayTracingPipelinesNV(device, pipelineCache, createInfoCount, pCreateInfos,
pAllocator, pPipelines, &(crtpl_state[intercept->container_type]));
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateRayTracingPipelinesNV(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator,
pPipelines, &(crtpl_state[intercept->container_type]));
}
VkResult result = DispatchCreateRayTracingPipelinesNV(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator, pPipelines);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateRayTracingPipelinesNV(device, pipelineCache, createInfoCount, pCreateInfos, pAllocator,
pPipelines, result, &(crtpl_state[intercept->container_type]));
}
return result;
}
// This API needs the ability to modify a down-chain parameter
VKAPI_ATTR VkResult VKAPI_CALL CreatePipelineLayout(
VkDevice device,
const VkPipelineLayoutCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkPipelineLayout* pPipelineLayout) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
create_pipeline_layout_api_state cpl_state{};
cpl_state.modified_create_info = *pCreateInfo;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreatePipelineLayout(device, pCreateInfo, pAllocator, pPipelineLayout);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreatePipelineLayout(device, pCreateInfo, pAllocator, pPipelineLayout, &cpl_state);
}
VkResult result = DispatchCreatePipelineLayout(device, &cpl_state.modified_create_info, pAllocator, pPipelineLayout);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreatePipelineLayout(device, pCreateInfo, pAllocator, pPipelineLayout, result);
}
return result;
}
// This API needs some local stack data for performance reasons and also may modify a parameter
VKAPI_ATTR VkResult VKAPI_CALL CreateShaderModule(
VkDevice device,
const VkShaderModuleCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkShaderModule* pShaderModule) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
create_shader_module_api_state csm_state{};
csm_state.instrumented_create_info = *pCreateInfo;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateShaderModule(device, pCreateInfo, pAllocator, pShaderModule, &csm_state);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateShaderModule(device, pCreateInfo, pAllocator, pShaderModule, &csm_state);
}
VkResult result = DispatchCreateShaderModule(device, &csm_state.instrumented_create_info, pAllocator, pShaderModule);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateShaderModule(device, pCreateInfo, pAllocator, pShaderModule, result, &csm_state);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL AllocateDescriptorSets(
VkDevice device,
const VkDescriptorSetAllocateInfo* pAllocateInfo,
VkDescriptorSet* pDescriptorSets) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
cvdescriptorset::AllocateDescriptorSetsData ads_state(pAllocateInfo->descriptorSetCount);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateAllocateDescriptorSets(device, pAllocateInfo, pDescriptorSets, &ads_state);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordAllocateDescriptorSets(device, pAllocateInfo, pDescriptorSets);
}
VkResult result = DispatchAllocateDescriptorSets(device, pAllocateInfo, pDescriptorSets);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordAllocateDescriptorSets(device, pAllocateInfo, pDescriptorSets, result, &ads_state);
}
return result;
}
// This API needs the ability to modify a down-chain parameter
VKAPI_ATTR VkResult VKAPI_CALL CreateBuffer(
VkDevice device,
const VkBufferCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkBuffer* pBuffer) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
create_buffer_api_state cb_state{};
cb_state.modified_create_info = *pCreateInfo;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateBuffer(device, pCreateInfo, pAllocator, pBuffer);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateBuffer(device, pCreateInfo, pAllocator, pBuffer, &cb_state);
}
VkResult result = DispatchCreateBuffer(device, &cb_state.modified_create_info, pAllocator, pBuffer);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateBuffer(device, pCreateInfo, pAllocator, pBuffer, result);
}
return result;
}
// ValidationCache APIs do not dispatch
VKAPI_ATTR VkResult VKAPI_CALL CreateValidationCacheEXT(
VkDevice device,
const VkValidationCacheCreateInfoEXT* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkValidationCacheEXT* pValidationCache) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
VkResult result = VK_SUCCESS;
ValidationObject *validation_data = layer_data->GetValidationObject(layer_data->object_dispatch, LayerObjectTypeCoreValidation);
if (validation_data) {
auto lock = validation_data->write_lock();
result = validation_data->CoreLayerCreateValidationCacheEXT(device, pCreateInfo, pAllocator, pValidationCache);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyValidationCacheEXT(
VkDevice device,
VkValidationCacheEXT validationCache,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
ValidationObject *validation_data = layer_data->GetValidationObject(layer_data->object_dispatch, LayerObjectTypeCoreValidation);
if (validation_data) {
auto lock = validation_data->write_lock();
validation_data->CoreLayerDestroyValidationCacheEXT(device, validationCache, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL MergeValidationCachesEXT(
VkDevice device,
VkValidationCacheEXT dstCache,
uint32_t srcCacheCount,
const VkValidationCacheEXT* pSrcCaches) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
VkResult result = VK_SUCCESS;
ValidationObject *validation_data = layer_data->GetValidationObject(layer_data->object_dispatch, LayerObjectTypeCoreValidation);
if (validation_data) {
auto lock = validation_data->write_lock();
result = validation_data->CoreLayerMergeValidationCachesEXT(device, dstCache, srcCacheCount, pSrcCaches);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL GetValidationCacheDataEXT(
VkDevice device,
VkValidationCacheEXT validationCache,
size_t* pDataSize,
void* pData) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
VkResult result = VK_SUCCESS;
ValidationObject *validation_data = layer_data->GetValidationObject(layer_data->object_dispatch, LayerObjectTypeCoreValidation);
if (validation_data) {
auto lock = validation_data->write_lock();
result = validation_data->CoreLayerGetValidationCacheDataEXT(device, validationCache, pDataSize, pData);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL EnumeratePhysicalDevices(
VkInstance instance,
uint32_t* pPhysicalDeviceCount,
VkPhysicalDevice* pPhysicalDevices) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(instance), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateEnumeratePhysicalDevices(instance, pPhysicalDeviceCount, pPhysicalDevices);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordEnumeratePhysicalDevices(instance, pPhysicalDeviceCount, pPhysicalDevices);
}
VkResult result = DispatchEnumeratePhysicalDevices(instance, pPhysicalDeviceCount, pPhysicalDevices);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordEnumeratePhysicalDevices(instance, pPhysicalDeviceCount, pPhysicalDevices, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL GetPhysicalDeviceFeatures(
VkPhysicalDevice physicalDevice,
VkPhysicalDeviceFeatures* pFeatures) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPhysicalDeviceFeatures(physicalDevice, pFeatures);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPhysicalDeviceFeatures(physicalDevice, pFeatures);
}
DispatchGetPhysicalDeviceFeatures(physicalDevice, pFeatures);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPhysicalDeviceFeatures(physicalDevice, pFeatures);
}
}
VKAPI_ATTR void VKAPI_CALL GetPhysicalDeviceFormatProperties(
VkPhysicalDevice physicalDevice,
VkFormat format,
VkFormatProperties* pFormatProperties) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPhysicalDeviceFormatProperties(physicalDevice, format, pFormatProperties);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPhysicalDeviceFormatProperties(physicalDevice, format, pFormatProperties);
}
DispatchGetPhysicalDeviceFormatProperties(physicalDevice, format, pFormatProperties);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPhysicalDeviceFormatProperties(physicalDevice, format, pFormatProperties);
}
}
VKAPI_ATTR VkResult VKAPI_CALL GetPhysicalDeviceImageFormatProperties(
VkPhysicalDevice physicalDevice,
VkFormat format,
VkImageType type,
VkImageTiling tiling,
VkImageUsageFlags usage,
VkImageCreateFlags flags,
VkImageFormatProperties* pImageFormatProperties) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPhysicalDeviceImageFormatProperties(physicalDevice, format, type, tiling, usage, flags, pImageFormatProperties);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPhysicalDeviceImageFormatProperties(physicalDevice, format, type, tiling, usage, flags, pImageFormatProperties);
}
VkResult result = DispatchGetPhysicalDeviceImageFormatProperties(physicalDevice, format, type, tiling, usage, flags, pImageFormatProperties);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPhysicalDeviceImageFormatProperties(physicalDevice, format, type, tiling, usage, flags, pImageFormatProperties, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL GetPhysicalDeviceProperties(
VkPhysicalDevice physicalDevice,
VkPhysicalDeviceProperties* pProperties) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPhysicalDeviceProperties(physicalDevice, pProperties);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPhysicalDeviceProperties(physicalDevice, pProperties);
}
DispatchGetPhysicalDeviceProperties(physicalDevice, pProperties);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPhysicalDeviceProperties(physicalDevice, pProperties);
}
}
VKAPI_ATTR void VKAPI_CALL GetPhysicalDeviceQueueFamilyProperties(
VkPhysicalDevice physicalDevice,
uint32_t* pQueueFamilyPropertyCount,
VkQueueFamilyProperties* pQueueFamilyProperties) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPhysicalDeviceQueueFamilyProperties(physicalDevice, pQueueFamilyPropertyCount, pQueueFamilyProperties);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPhysicalDeviceQueueFamilyProperties(physicalDevice, pQueueFamilyPropertyCount, pQueueFamilyProperties);
}
DispatchGetPhysicalDeviceQueueFamilyProperties(physicalDevice, pQueueFamilyPropertyCount, pQueueFamilyProperties);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPhysicalDeviceQueueFamilyProperties(physicalDevice, pQueueFamilyPropertyCount, pQueueFamilyProperties);
}
}
VKAPI_ATTR void VKAPI_CALL GetPhysicalDeviceMemoryProperties(
VkPhysicalDevice physicalDevice,
VkPhysicalDeviceMemoryProperties* pMemoryProperties) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPhysicalDeviceMemoryProperties(physicalDevice, pMemoryProperties);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPhysicalDeviceMemoryProperties(physicalDevice, pMemoryProperties);
}
DispatchGetPhysicalDeviceMemoryProperties(physicalDevice, pMemoryProperties);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPhysicalDeviceMemoryProperties(physicalDevice, pMemoryProperties);
}
}
VKAPI_ATTR void VKAPI_CALL GetDeviceQueue(
VkDevice device,
uint32_t queueFamilyIndex,
uint32_t queueIndex,
VkQueue* pQueue) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetDeviceQueue(device, queueFamilyIndex, queueIndex, pQueue);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetDeviceQueue(device, queueFamilyIndex, queueIndex, pQueue);
}
DispatchGetDeviceQueue(device, queueFamilyIndex, queueIndex, pQueue);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetDeviceQueue(device, queueFamilyIndex, queueIndex, pQueue);
}
}
VKAPI_ATTR VkResult VKAPI_CALL QueueSubmit(
VkQueue queue,
uint32_t submitCount,
const VkSubmitInfo* pSubmits,
VkFence fence) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(queue), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateQueueSubmit(queue, submitCount, pSubmits, fence);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordQueueSubmit(queue, submitCount, pSubmits, fence);
}
VkResult result = DispatchQueueSubmit(queue, submitCount, pSubmits, fence);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordQueueSubmit(queue, submitCount, pSubmits, fence, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL QueueWaitIdle(
VkQueue queue) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(queue), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateQueueWaitIdle(queue);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordQueueWaitIdle(queue);
}
VkResult result = DispatchQueueWaitIdle(queue);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordQueueWaitIdle(queue, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL DeviceWaitIdle(
VkDevice device) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDeviceWaitIdle(device);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDeviceWaitIdle(device);
}
VkResult result = DispatchDeviceWaitIdle(device);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDeviceWaitIdle(device, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL AllocateMemory(
VkDevice device,
const VkMemoryAllocateInfo* pAllocateInfo,
const VkAllocationCallbacks* pAllocator,
VkDeviceMemory* pMemory) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateAllocateMemory(device, pAllocateInfo, pAllocator, pMemory);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordAllocateMemory(device, pAllocateInfo, pAllocator, pMemory);
}
VkResult result = DispatchAllocateMemory(device, pAllocateInfo, pAllocator, pMemory);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordAllocateMemory(device, pAllocateInfo, pAllocator, pMemory, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL FreeMemory(
VkDevice device,
VkDeviceMemory memory,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateFreeMemory(device, memory, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordFreeMemory(device, memory, pAllocator);
}
DispatchFreeMemory(device, memory, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordFreeMemory(device, memory, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL MapMemory(
VkDevice device,
VkDeviceMemory memory,
VkDeviceSize offset,
VkDeviceSize size,
VkMemoryMapFlags flags,
void** ppData) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateMapMemory(device, memory, offset, size, flags, ppData);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordMapMemory(device, memory, offset, size, flags, ppData);
}
VkResult result = DispatchMapMemory(device, memory, offset, size, flags, ppData);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordMapMemory(device, memory, offset, size, flags, ppData, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL UnmapMemory(
VkDevice device,
VkDeviceMemory memory) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateUnmapMemory(device, memory);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordUnmapMemory(device, memory);
}
DispatchUnmapMemory(device, memory);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordUnmapMemory(device, memory);
}
}
VKAPI_ATTR VkResult VKAPI_CALL FlushMappedMemoryRanges(
VkDevice device,
uint32_t memoryRangeCount,
const VkMappedMemoryRange* pMemoryRanges) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateFlushMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordFlushMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges);
}
VkResult result = DispatchFlushMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordFlushMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL InvalidateMappedMemoryRanges(
VkDevice device,
uint32_t memoryRangeCount,
const VkMappedMemoryRange* pMemoryRanges) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateInvalidateMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordInvalidateMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges);
}
VkResult result = DispatchInvalidateMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordInvalidateMappedMemoryRanges(device, memoryRangeCount, pMemoryRanges, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL GetDeviceMemoryCommitment(
VkDevice device,
VkDeviceMemory memory,
VkDeviceSize* pCommittedMemoryInBytes) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetDeviceMemoryCommitment(device, memory, pCommittedMemoryInBytes);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetDeviceMemoryCommitment(device, memory, pCommittedMemoryInBytes);
}
DispatchGetDeviceMemoryCommitment(device, memory, pCommittedMemoryInBytes);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetDeviceMemoryCommitment(device, memory, pCommittedMemoryInBytes);
}
}
VKAPI_ATTR VkResult VKAPI_CALL BindBufferMemory(
VkDevice device,
VkBuffer buffer,
VkDeviceMemory memory,
VkDeviceSize memoryOffset) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateBindBufferMemory(device, buffer, memory, memoryOffset);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordBindBufferMemory(device, buffer, memory, memoryOffset);
}
VkResult result = DispatchBindBufferMemory(device, buffer, memory, memoryOffset);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordBindBufferMemory(device, buffer, memory, memoryOffset, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL BindImageMemory(
VkDevice device,
VkImage image,
VkDeviceMemory memory,
VkDeviceSize memoryOffset) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateBindImageMemory(device, image, memory, memoryOffset);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordBindImageMemory(device, image, memory, memoryOffset);
}
VkResult result = DispatchBindImageMemory(device, image, memory, memoryOffset);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordBindImageMemory(device, image, memory, memoryOffset, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL GetBufferMemoryRequirements(
VkDevice device,
VkBuffer buffer,
VkMemoryRequirements* pMemoryRequirements) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetBufferMemoryRequirements(device, buffer, pMemoryRequirements);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetBufferMemoryRequirements(device, buffer, pMemoryRequirements);
}
DispatchGetBufferMemoryRequirements(device, buffer, pMemoryRequirements);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetBufferMemoryRequirements(device, buffer, pMemoryRequirements);
}
}
VKAPI_ATTR void VKAPI_CALL GetImageMemoryRequirements(
VkDevice device,
VkImage image,
VkMemoryRequirements* pMemoryRequirements) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetImageMemoryRequirements(device, image, pMemoryRequirements);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetImageMemoryRequirements(device, image, pMemoryRequirements);
}
DispatchGetImageMemoryRequirements(device, image, pMemoryRequirements);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetImageMemoryRequirements(device, image, pMemoryRequirements);
}
}
VKAPI_ATTR void VKAPI_CALL GetImageSparseMemoryRequirements(
VkDevice device,
VkImage image,
uint32_t* pSparseMemoryRequirementCount,
VkSparseImageMemoryRequirements* pSparseMemoryRequirements) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetImageSparseMemoryRequirements(device, image, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetImageSparseMemoryRequirements(device, image, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
}
DispatchGetImageSparseMemoryRequirements(device, image, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetImageSparseMemoryRequirements(device, image, pSparseMemoryRequirementCount, pSparseMemoryRequirements);
}
}
VKAPI_ATTR void VKAPI_CALL GetPhysicalDeviceSparseImageFormatProperties(
VkPhysicalDevice physicalDevice,
VkFormat format,
VkImageType type,
VkSampleCountFlagBits samples,
VkImageUsageFlags usage,
VkImageTiling tiling,
uint32_t* pPropertyCount,
VkSparseImageFormatProperties* pProperties) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(physicalDevice), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPhysicalDeviceSparseImageFormatProperties(physicalDevice, format, type, samples, usage, tiling, pPropertyCount, pProperties);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPhysicalDeviceSparseImageFormatProperties(physicalDevice, format, type, samples, usage, tiling, pPropertyCount, pProperties);
}
DispatchGetPhysicalDeviceSparseImageFormatProperties(physicalDevice, format, type, samples, usage, tiling, pPropertyCount, pProperties);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPhysicalDeviceSparseImageFormatProperties(physicalDevice, format, type, samples, usage, tiling, pPropertyCount, pProperties);
}
}
VKAPI_ATTR VkResult VKAPI_CALL QueueBindSparse(
VkQueue queue,
uint32_t bindInfoCount,
const VkBindSparseInfo* pBindInfo,
VkFence fence) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(queue), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateQueueBindSparse(queue, bindInfoCount, pBindInfo, fence);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordQueueBindSparse(queue, bindInfoCount, pBindInfo, fence);
}
VkResult result = DispatchQueueBindSparse(queue, bindInfoCount, pBindInfo, fence);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordQueueBindSparse(queue, bindInfoCount, pBindInfo, fence, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL CreateFence(
VkDevice device,
const VkFenceCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkFence* pFence) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateFence(device, pCreateInfo, pAllocator, pFence);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateFence(device, pCreateInfo, pAllocator, pFence);
}
VkResult result = DispatchCreateFence(device, pCreateInfo, pAllocator, pFence);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateFence(device, pCreateInfo, pAllocator, pFence, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyFence(
VkDevice device,
VkFence fence,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyFence(device, fence, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyFence(device, fence, pAllocator);
}
DispatchDestroyFence(device, fence, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyFence(device, fence, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL ResetFences(
VkDevice device,
uint32_t fenceCount,
const VkFence* pFences) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateResetFences(device, fenceCount, pFences);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordResetFences(device, fenceCount, pFences);
}
VkResult result = DispatchResetFences(device, fenceCount, pFences);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordResetFences(device, fenceCount, pFences, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL GetFenceStatus(
VkDevice device,
VkFence fence) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetFenceStatus(device, fence);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetFenceStatus(device, fence);
}
VkResult result = DispatchGetFenceStatus(device, fence);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetFenceStatus(device, fence, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL WaitForFences(
VkDevice device,
uint32_t fenceCount,
const VkFence* pFences,
VkBool32 waitAll,
uint64_t timeout) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateWaitForFences(device, fenceCount, pFences, waitAll, timeout);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordWaitForFences(device, fenceCount, pFences, waitAll, timeout);
}
VkResult result = DispatchWaitForFences(device, fenceCount, pFences, waitAll, timeout);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordWaitForFences(device, fenceCount, pFences, waitAll, timeout, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL CreateSemaphore(
VkDevice device,
const VkSemaphoreCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkSemaphore* pSemaphore) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateSemaphore(device, pCreateInfo, pAllocator, pSemaphore);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateSemaphore(device, pCreateInfo, pAllocator, pSemaphore);
}
VkResult result = DispatchCreateSemaphore(device, pCreateInfo, pAllocator, pSemaphore);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateSemaphore(device, pCreateInfo, pAllocator, pSemaphore, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroySemaphore(
VkDevice device,
VkSemaphore semaphore,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroySemaphore(device, semaphore, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroySemaphore(device, semaphore, pAllocator);
}
DispatchDestroySemaphore(device, semaphore, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroySemaphore(device, semaphore, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL CreateEvent(
VkDevice device,
const VkEventCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkEvent* pEvent) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateEvent(device, pCreateInfo, pAllocator, pEvent);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateEvent(device, pCreateInfo, pAllocator, pEvent);
}
VkResult result = DispatchCreateEvent(device, pCreateInfo, pAllocator, pEvent);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateEvent(device, pCreateInfo, pAllocator, pEvent, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyEvent(
VkDevice device,
VkEvent event,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyEvent(device, event, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyEvent(device, event, pAllocator);
}
DispatchDestroyEvent(device, event, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyEvent(device, event, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL GetEventStatus(
VkDevice device,
VkEvent event) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetEventStatus(device, event);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetEventStatus(device, event);
}
VkResult result = DispatchGetEventStatus(device, event);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetEventStatus(device, event, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL SetEvent(
VkDevice device,
VkEvent event) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateSetEvent(device, event);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordSetEvent(device, event);
}
VkResult result = DispatchSetEvent(device, event);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordSetEvent(device, event, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL ResetEvent(
VkDevice device,
VkEvent event) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateResetEvent(device, event);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordResetEvent(device, event);
}
VkResult result = DispatchResetEvent(device, event);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordResetEvent(device, event, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL CreateQueryPool(
VkDevice device,
const VkQueryPoolCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkQueryPool* pQueryPool) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateQueryPool(device, pCreateInfo, pAllocator, pQueryPool);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateQueryPool(device, pCreateInfo, pAllocator, pQueryPool);
}
VkResult result = DispatchCreateQueryPool(device, pCreateInfo, pAllocator, pQueryPool);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateQueryPool(device, pCreateInfo, pAllocator, pQueryPool, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyQueryPool(
VkDevice device,
VkQueryPool queryPool,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyQueryPool(device, queryPool, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyQueryPool(device, queryPool, pAllocator);
}
DispatchDestroyQueryPool(device, queryPool, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyQueryPool(device, queryPool, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL GetQueryPoolResults(
VkDevice device,
VkQueryPool queryPool,
uint32_t firstQuery,
uint32_t queryCount,
size_t dataSize,
void* pData,
VkDeviceSize stride,
VkQueryResultFlags flags) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetQueryPoolResults(device, queryPool, firstQuery, queryCount, dataSize, pData, stride, flags);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetQueryPoolResults(device, queryPool, firstQuery, queryCount, dataSize, pData, stride, flags);
}
VkResult result = DispatchGetQueryPoolResults(device, queryPool, firstQuery, queryCount, dataSize, pData, stride, flags);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetQueryPoolResults(device, queryPool, firstQuery, queryCount, dataSize, pData, stride, flags, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyBuffer(
VkDevice device,
VkBuffer buffer,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyBuffer(device, buffer, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyBuffer(device, buffer, pAllocator);
}
DispatchDestroyBuffer(device, buffer, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyBuffer(device, buffer, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL CreateBufferView(
VkDevice device,
const VkBufferViewCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkBufferView* pView) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateBufferView(device, pCreateInfo, pAllocator, pView);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateBufferView(device, pCreateInfo, pAllocator, pView);
}
VkResult result = DispatchCreateBufferView(device, pCreateInfo, pAllocator, pView);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateBufferView(device, pCreateInfo, pAllocator, pView, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyBufferView(
VkDevice device,
VkBufferView bufferView,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyBufferView(device, bufferView, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyBufferView(device, bufferView, pAllocator);
}
DispatchDestroyBufferView(device, bufferView, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyBufferView(device, bufferView, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL CreateImage(
VkDevice device,
const VkImageCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkImage* pImage) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateImage(device, pCreateInfo, pAllocator, pImage);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateImage(device, pCreateInfo, pAllocator, pImage);
}
VkResult result = DispatchCreateImage(device, pCreateInfo, pAllocator, pImage);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateImage(device, pCreateInfo, pAllocator, pImage, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyImage(
VkDevice device,
VkImage image,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyImage(device, image, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyImage(device, image, pAllocator);
}
DispatchDestroyImage(device, image, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyImage(device, image, pAllocator);
}
}
VKAPI_ATTR void VKAPI_CALL GetImageSubresourceLayout(
VkDevice device,
VkImage image,
const VkImageSubresource* pSubresource,
VkSubresourceLayout* pLayout) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetImageSubresourceLayout(device, image, pSubresource, pLayout);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetImageSubresourceLayout(device, image, pSubresource, pLayout);
}
DispatchGetImageSubresourceLayout(device, image, pSubresource, pLayout);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetImageSubresourceLayout(device, image, pSubresource, pLayout);
}
}
VKAPI_ATTR VkResult VKAPI_CALL CreateImageView(
VkDevice device,
const VkImageViewCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkImageView* pView) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateImageView(device, pCreateInfo, pAllocator, pView);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateImageView(device, pCreateInfo, pAllocator, pView);
}
VkResult result = DispatchCreateImageView(device, pCreateInfo, pAllocator, pView);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateImageView(device, pCreateInfo, pAllocator, pView, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyImageView(
VkDevice device,
VkImageView imageView,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyImageView(device, imageView, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyImageView(device, imageView, pAllocator);
}
DispatchDestroyImageView(device, imageView, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyImageView(device, imageView, pAllocator);
}
}
VKAPI_ATTR void VKAPI_CALL DestroyShaderModule(
VkDevice device,
VkShaderModule shaderModule,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyShaderModule(device, shaderModule, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyShaderModule(device, shaderModule, pAllocator);
}
DispatchDestroyShaderModule(device, shaderModule, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyShaderModule(device, shaderModule, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL CreatePipelineCache(
VkDevice device,
const VkPipelineCacheCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkPipelineCache* pPipelineCache) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreatePipelineCache(device, pCreateInfo, pAllocator, pPipelineCache);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreatePipelineCache(device, pCreateInfo, pAllocator, pPipelineCache);
}
VkResult result = DispatchCreatePipelineCache(device, pCreateInfo, pAllocator, pPipelineCache);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreatePipelineCache(device, pCreateInfo, pAllocator, pPipelineCache, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyPipelineCache(
VkDevice device,
VkPipelineCache pipelineCache,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyPipelineCache(device, pipelineCache, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyPipelineCache(device, pipelineCache, pAllocator);
}
DispatchDestroyPipelineCache(device, pipelineCache, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyPipelineCache(device, pipelineCache, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL GetPipelineCacheData(
VkDevice device,
VkPipelineCache pipelineCache,
size_t* pDataSize,
void* pData) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateGetPipelineCacheData(device, pipelineCache, pDataSize, pData);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordGetPipelineCacheData(device, pipelineCache, pDataSize, pData);
}
VkResult result = DispatchGetPipelineCacheData(device, pipelineCache, pDataSize, pData);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordGetPipelineCacheData(device, pipelineCache, pDataSize, pData, result);
}
return result;
}
VKAPI_ATTR VkResult VKAPI_CALL MergePipelineCaches(
VkDevice device,
VkPipelineCache dstCache,
uint32_t srcCacheCount,
const VkPipelineCache* pSrcCaches) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateMergePipelineCaches(device, dstCache, srcCacheCount, pSrcCaches);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordMergePipelineCaches(device, dstCache, srcCacheCount, pSrcCaches);
}
VkResult result = DispatchMergePipelineCaches(device, dstCache, srcCacheCount, pSrcCaches);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordMergePipelineCaches(device, dstCache, srcCacheCount, pSrcCaches, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroyPipeline(
VkDevice device,
VkPipeline pipeline,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyPipeline(device, pipeline, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyPipeline(device, pipeline, pAllocator);
}
DispatchDestroyPipeline(device, pipeline, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyPipeline(device, pipeline, pAllocator);
}
}
VKAPI_ATTR void VKAPI_CALL DestroyPipelineLayout(
VkDevice device,
VkPipelineLayout pipelineLayout,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroyPipelineLayout(device, pipelineLayout, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroyPipelineLayout(device, pipelineLayout, pAllocator);
}
DispatchDestroyPipelineLayout(device, pipelineLayout, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroyPipelineLayout(device, pipelineLayout, pAllocator);
}
}
VKAPI_ATTR VkResult VKAPI_CALL CreateSampler(
VkDevice device,
const VkSamplerCreateInfo* pCreateInfo,
const VkAllocationCallbacks* pAllocator,
VkSampler* pSampler) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateCreateSampler(device, pCreateInfo, pAllocator, pSampler);
if (skip) return VK_ERROR_VALIDATION_FAILED_EXT;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordCreateSampler(device, pCreateInfo, pAllocator, pSampler);
}
VkResult result = DispatchCreateSampler(device, pCreateInfo, pAllocator, pSampler);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordCreateSampler(device, pCreateInfo, pAllocator, pSampler, result);
}
return result;
}
VKAPI_ATTR void VKAPI_CALL DestroySampler(
VkDevice device,
VkSampler sampler,
const VkAllocationCallbacks* pAllocator) {
auto layer_data = GetLayerDataPtr(get_dispatch_key(device), layer_data_map);
bool skip = false;
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->read_lock();
skip |= (const_cast<const ValidationObject*>(intercept))->PreCallValidateDestroySampler(device, sampler, pAllocator);
if (skip) return;
}
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PreCallRecordDestroySampler(device, sampler, pAllocator);
}
DispatchDestroySampler(device, sampler, pAllocator);
for (auto intercept : layer_data->object_dispatch) {
auto lock = intercept->write_lock();
intercept->PostCallRecordDestroySampler(device, sampler, pAllocator);