trampoline.c revision 7cb441ad98af7d515d934db466d07e16ff624a31
15d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj/*
25d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *
35d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Copyright (c) 2015-2016 The Khronos Group Inc.
45d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Copyright (c) 2015-2016 Valve Corporation
55d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Copyright (c) 2015-2016 LunarG, Inc.
65d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Copyright (C) 2015 Google Inc.
75d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *
85d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Licensed under the Apache License, Version 2.0 (the "License");
95d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * you may not use this file except in compliance with the License.
105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * You may obtain a copy of the License at
115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *
125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *     http://www.apache.org/licenses/LICENSE-2.0
135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *
145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Unless required by applicable law or agreed to in writing, software
155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * distributed under the License is distributed on an "AS IS" BASIS,
165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * See the License for the specific language governing permissions and
185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * limitations under the License.
195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *
20ed39800a83baf5bffbe391f3974eb2af0f415f80Elliott Hughes * Author: Courtney Goeltzenleuchter <courtney@lunarg.com>
215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Author: Jon Ashburn <jon@lunarg.com>
225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Author: Tony Barbour <tony@LunarG.com>
235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Author: Chia-I Wu <olv@lunarg.com>
245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj */
255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#define _GNU_SOURCE
265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include <stdlib.h>
275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include <string.h>
285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include "vk_loader_platform.h"
305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include "loader.h"
315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include "debug_report.h"
325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include "wsi.h"
335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include "extensions.h"
345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include "gpa_helper.h"
355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#include "table_ops.h"
365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj/* Trampoline entrypoints are in this file for core Vulkan commands */
385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj/**
395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Get an instance level or global level entry point address.
405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * @param instance
415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * @param pName
425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * @return
435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *    If instance == NULL returns a global level functions only
445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *    If instance is valid returns a trampoline entry point for all dispatchable
455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Vulkan
465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *    functions both core and extensions.
475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj */
485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR PFN_vkVoidFunction VKAPI_CALL
495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetInstanceProcAddr(VkInstance instance, const char *pName) {
505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    void *addr;
525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    addr = globalGetProcAddr(pName);
545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (instance == VK_NULL_HANDLE) {
555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // get entrypoint addresses that are global (no dispatchable object)
565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return addr;
585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    } else {
595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // if a global entrypoint return NULL
605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (addr)
615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            return NULL;
625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_instance *ptr_instance = loader_get_instance(instance);
655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (ptr_instance == NULL)
665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return NULL;
675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // Return trampoline code for non-global entrypoints including any
685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // extensions.
695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // Device extensions are returned if a layer or ICD supports the extension.
705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // Instance extensions are returned if the extension is enabled and the
715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // loader
725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // or someone else supports the extension
735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return trampolineGetProcAddr(ptr_instance, pName);
745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj/**
775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * Get a device level or global level entry point address.
785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * @param device
795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * @param pName
805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj * @return
815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *    If device is valid, returns a device relative entry point for device level
825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *    entry points both core and extensions.
835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj *    Device relative means call down the device chain.
845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj */
855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR PFN_vkVoidFunction VKAPI_CALL
865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetDeviceProcAddr(VkDevice device, const char *pName) {
875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    void *addr;
885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* for entrypoints that loader must handle (ie non-dispatchable or create
905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj       object)
915d7fde14f7e0323477a6721da5b6e9f76a94401dsewardj       make sure the loader entrypoint is returned */
920dc35261140f7612f1e516a9fa2a977f4e30e04erhyskidd    addr = loader_non_passthrough_gdpa(pName);
938eb8bab992e3998c33770b0cdb16059a8b918a06sewardj    if (addr) {
940dc35261140f7612f1e516a9fa2a977f4e30e04erhyskidd        return addr;
955d7fde14f7e0323477a6721da5b6e9f76a94401dsewardj    }
965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* Although CreateDevice is on device chain it's dispatchable object isn't
985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     * a VkDevice or child of VkDevice so return NULL.
995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     */
1005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (!strcmp(pName, "CreateDevice"))
1015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return NULL;
1025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* return the dispatch table entrypoint for the fastest case */
1045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp_table = *(VkLayerDispatchTable **)device;
1055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (disp_table == NULL)
1065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return NULL;
1075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    addr = loader_lookup_device_dispatch_table(disp_table, pName);
1095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (addr)
1105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return addr;
1115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (disp_table->GetDeviceProcAddr == NULL)
1135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return NULL;
114044514a949280ebcda5b9f9f402ec84098229354florian    return disp_table->GetDeviceProcAddr(device, pName);
115044514a949280ebcda5b9f9f402ec84098229354florian}
116044514a949280ebcda5b9f9f402ec84098229354florian
117044514a949280ebcda5b9f9f402ec84098229354florianLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
118044514a949280ebcda5b9f9f402ec84098229354florianvkEnumerateInstanceExtensionProperties(const char *pLayerName,
119044514a949280ebcda5b9f9f402ec84098229354florian                                       uint32_t *pPropertyCount,
120044514a949280ebcda5b9f9f402ec84098229354florian                                       VkExtensionProperties *pProperties) {
1215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_extension_list *global_ext_list = NULL;
1225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_layer_list instance_layers;
1235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_extension_list local_ext_list;
1245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_icd_libs icd_libs;
1255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    uint32_t copy_size;
1265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkResult res = VK_SUCCESS;
1275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    tls_instance = NULL;
1295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memset(&local_ext_list, 0, sizeof(local_ext_list));
1305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memset(&instance_layers, 0, sizeof(instance_layers));
1315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_once(&once_init, loader_initialize);
1325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* get layer libraries if needed */
1345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pLayerName && strlen(pLayerName) != 0) {
1355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (vk_string_validate(MaxLoaderStringLength, pLayerName) !=
1365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            VK_STRING_ERROR_NONE) {
1375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            assert(VK_FALSE && "vkEnumerateInstanceExtensionProperties:  "
1385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                               "pLayerName is too long or is badly formed");
1395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            res = VK_ERROR_EXTENSION_NOT_PRESENT;
1405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            goto out;
1415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
1425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_layer_scan(NULL, &instance_layers);
1445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (strcmp(pLayerName, std_validation_str) == 0) {
1455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            struct loader_layer_list local_list;
1465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            memset(&local_list, 0, sizeof(local_list));
1475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            for (uint32_t i = 0; i < sizeof(std_validation_names) /
1485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                         sizeof(std_validation_names[0]);
1495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                 i++) {
1505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                loader_find_layer_name_add_list(NULL, std_validation_names[i],
1515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                VK_LAYER_TYPE_INSTANCE_EXPLICIT,
1525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                &instance_layers, &local_list);
1535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
1545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            for (uint32_t i = 0; i < local_list.count; i++) {
1555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                struct loader_extension_list *ext_list =
1565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    &local_list.list[i].instance_extension_list;
1575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                loader_add_to_ext_list(NULL, &local_ext_list, ext_list->count,
1585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                       ext_list->list);
1595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
160044514a949280ebcda5b9f9f402ec84098229354florian            loader_destroy_layer_list(NULL, NULL, &local_list);
161044514a949280ebcda5b9f9f402ec84098229354florian            global_ext_list = &local_ext_list;
162044514a949280ebcda5b9f9f402ec84098229354florian
163044514a949280ebcda5b9f9f402ec84098229354florian        } else {
164044514a949280ebcda5b9f9f402ec84098229354florian            for (uint32_t i = 0; i < instance_layers.count; i++) {
165044514a949280ebcda5b9f9f402ec84098229354florian                struct loader_layer_properties *props =
166044514a949280ebcda5b9f9f402ec84098229354florian                    &instance_layers.list[i];
167044514a949280ebcda5b9f9f402ec84098229354florian                if (strcmp(props->info.layerName, pLayerName) == 0) {
168044514a949280ebcda5b9f9f402ec84098229354florian                    global_ext_list = &props->instance_extension_list;
169044514a949280ebcda5b9f9f402ec84098229354florian                    break;
170044514a949280ebcda5b9f9f402ec84098229354florian                }
171044514a949280ebcda5b9f9f402ec84098229354florian            }
172044514a949280ebcda5b9f9f402ec84098229354florian        }
173044514a949280ebcda5b9f9f402ec84098229354florian    } else {
1745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        /* Scan/discover all ICD libraries */
1755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        memset(&icd_libs, 0, sizeof(struct loader_icd_libs));
1765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = loader_icd_scan(NULL, &icd_libs);
1775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (VK_SUCCESS != res) {
1785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            goto out;
1795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
1805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        /* get extensions from all ICD's, merge so no duplicates */
1815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = loader_get_icd_loader_instance_extensions(NULL, &icd_libs,
1825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                        &local_ext_list);
1835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (VK_SUCCESS != res) {
1845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            goto out;
1855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
1865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_scanned_icd_clear(NULL, &icd_libs);
1875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // Append implicit layers.
1895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_implicit_layer_scan(NULL, &instance_layers);
1905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        for (uint32_t i = 0; i < instance_layers.count; i++) {
1915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            struct loader_extension_list *ext_list =
1925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                &instance_layers.list[i].instance_extension_list;
1935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_add_to_ext_list(NULL, &local_ext_list, ext_list->count,
1945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                   ext_list->list);
1955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
1965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
197044514a949280ebcda5b9f9f402ec84098229354florian        global_ext_list = &local_ext_list;
1985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
1995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (global_ext_list == NULL) {
2015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = VK_ERROR_LAYER_NOT_PRESENT;
2025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
2035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pProperties == NULL) {
2065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        *pPropertyCount = global_ext_list->count;
2075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
2085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    copy_size = *pPropertyCount < global_ext_list->count
2115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    ? *pPropertyCount
2125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    : global_ext_list->count;
2135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    for (uint32_t i = 0; i < copy_size; i++) {
2145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        memcpy(&pProperties[i], &global_ext_list->list[i],
2155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj               sizeof(VkExtensionProperties));
2165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    *pPropertyCount = copy_size;
2185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (copy_size < global_ext_list->count) {
2205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = VK_INCOMPLETE;
2215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
2225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjout:
2255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_destroy_generic_list(NULL, (struct loader_generic_list *)&local_ext_list);
2265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_delete_layer_properties(NULL, &instance_layers);
2275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return res;
2285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
2295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
2315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkEnumerateInstanceLayerProperties(uint32_t *pPropertyCount,
2325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                   VkLayerProperties *pProperties) {
2335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_layer_list instance_layer_list;
2355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    tls_instance = NULL;
2365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_once(&once_init, loader_initialize);
2385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    uint32_t copy_size;
2405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* get layer libraries */
2425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memset(&instance_layer_list, 0, sizeof(instance_layer_list));
2435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_layer_scan(NULL, &instance_layer_list);
2445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pProperties == NULL) {
2465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        *pPropertyCount = instance_layer_list.count;
2475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_destroy_layer_list(NULL, NULL, &instance_layer_list);
2485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return VK_SUCCESS;
2495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    copy_size = (*pPropertyCount < instance_layer_list.count)
2525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    ? *pPropertyCount
2535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    : instance_layer_list.count;
2545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    for (uint32_t i = 0; i < copy_size; i++) {
2555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        memcpy(&pProperties[i], &instance_layer_list.list[i].info,
2565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj               sizeof(VkLayerProperties));
2575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    *pPropertyCount = copy_size;
2605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (copy_size < instance_layer_list.count) {
2625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_destroy_layer_list(NULL, NULL, &instance_layer_list);
2635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return VK_INCOMPLETE;
2645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_destroy_layer_list(NULL, NULL, &instance_layer_list);
2675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return VK_SUCCESS;
2695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
2705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL vkCreateInstance(
2725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkInstanceCreateInfo *pCreateInfo,
2735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkAllocationCallbacks *pAllocator, VkInstance *pInstance) {
2745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_instance *ptr_instance = NULL;
2755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkInstance created_instance = VK_NULL_HANDLE;
2765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    bool loaderLocked = false;
2775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkResult res = VK_ERROR_INITIALIZATION_FAILED;
2785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_once(&once_init, loader_initialize);
2805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#if (DEBUG_DISABLE_APP_ALLOCATORS == 1)
2825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    {
2835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#else
2845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pAllocator) {
2855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance = (struct loader_instance *)pAllocator->pfnAllocation(
2865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            pAllocator->pUserData, sizeof(struct loader_instance),
2875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            sizeof(int *), VK_SYSTEM_ALLOCATION_SCOPE_INSTANCE);
2885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    } else {
2895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj#endif
2905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance =
2915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            (struct loader_instance *)malloc(sizeof(struct loader_instance));
2925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
2935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkInstanceCreateInfo ici = *pCreateInfo;
2955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
2965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (ptr_instance == NULL) {
2975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = VK_ERROR_OUT_OF_HOST_MEMORY;
2985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
2995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    tls_instance = ptr_instance;
3025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_lock_mutex(&loader_lock);
3035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loaderLocked = true;
3045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memset(ptr_instance, 0, sizeof(struct loader_instance));
3055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pAllocator) {
3065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance->alloc_callbacks = *pAllocator;
3075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /*
3105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     * Look for one or more debug report create info structures
3115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     * and setup a callback(s) for each one found.
3125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     */
3135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    ptr_instance->num_tmp_callbacks = 0;
3145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    ptr_instance->tmp_dbg_create_infos = NULL;
3155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    ptr_instance->tmp_callbacks = NULL;
3165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (util_CopyDebugReportCreateInfos(pCreateInfo->pNext, pAllocator,
3175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                        &ptr_instance->num_tmp_callbacks,
3185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                        &ptr_instance->tmp_dbg_create_infos,
3195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                        &ptr_instance->tmp_callbacks)) {
3205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // One or more were found, but allocation failed.  Therefore, clean up
3215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // and fail this function:
3225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = VK_ERROR_OUT_OF_HOST_MEMORY;
3235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
3245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    } else if (ptr_instance->num_tmp_callbacks > 0) {
3255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // Setup the temporary callback(s) here to catch early issues:
3265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (util_CreateDebugReportCallbacks(ptr_instance, pAllocator,
3275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                            ptr_instance->num_tmp_callbacks,
3285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                            ptr_instance->tmp_dbg_create_infos,
3295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                            ptr_instance->tmp_callbacks)) {
3305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            // Failure of setting up one or more of the callback.  Therefore,
3315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            // clean up and fail this function:
3325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            res = VK_ERROR_OUT_OF_HOST_MEMORY;
3335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            goto out;
3345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
3355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* Due to implicit layers need to get layer list even if
3385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     * enabledLayerCount == 0 and VK_INSTANCE_LAYERS is unset. For now always
3395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     * get layer list via loader_layer_scan(). */
3405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memset(&ptr_instance->instance_layer_list, 0,
3415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj           sizeof(ptr_instance->instance_layer_list));
3425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_layer_scan(ptr_instance, &ptr_instance->instance_layer_list);
3435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* validate the app requested layers to be enabled */
3455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pCreateInfo->enabledLayerCount > 0) {
3465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res =
3475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_validate_layers(ptr_instance, pCreateInfo->enabledLayerCount,
3485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                   pCreateInfo->ppEnabledLayerNames,
3495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                   &ptr_instance->instance_layer_list);
3505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (res != VK_SUCCESS) {
3515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            goto out;
3525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
3535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* convert any meta layers to the actual layers makes a copy of layer name*/
3565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkResult layerErr = loader_expand_layer_names(
3575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance, std_validation_str,
3585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        sizeof(std_validation_names) / sizeof(std_validation_names[0]),
3595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        std_validation_names, &ici.enabledLayerCount, &ici.ppEnabledLayerNames);
3605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (VK_SUCCESS != layerErr) {
3615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = layerErr;
3625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
3635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* Scan/discover all ICD libraries */
3665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memset(&ptr_instance->icd_libs, 0, sizeof(ptr_instance->icd_libs));
3675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_icd_scan(ptr_instance, &ptr_instance->icd_libs);
3685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS) {
3695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
3705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* get extensions from all ICD's, merge so no duplicates, then validate */
3735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_get_icd_loader_instance_extensions(
3745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance, &ptr_instance->icd_libs, &ptr_instance->ext_list);
3755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS) {
3765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
3775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_validate_instance_extensions(
3795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance, &ptr_instance->ext_list,
3805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        &ptr_instance->instance_layer_list, &ici);
3815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS) {
3825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
3835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    ptr_instance->disp = loader_instance_heap_alloc(
3865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance, sizeof(VkLayerInstanceDispatchTable),
3875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        VK_SYSTEM_ALLOCATION_SCOPE_INSTANCE);
3885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (ptr_instance->disp == NULL) {
3895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = VK_ERROR_OUT_OF_HOST_MEMORY;
3905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
3915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
3925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memcpy(ptr_instance->disp, &instance_disp, sizeof(instance_disp));
3935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    ptr_instance->next = loader.instances;
3945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader.instances = ptr_instance;
3955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
3965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* activate any layers on instance chain */
3975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_enable_instance_layers(ptr_instance, &ici,
3985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                        &ptr_instance->instance_layer_list);
3995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS) {
4005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
4015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
4025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    created_instance = (VkInstance)ptr_instance;
4045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_create_instance_chain(&ici, pAllocator, ptr_instance,
4055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                       &created_instance);
4065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res == VK_SUCCESS) {
4085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        wsi_create_instance(ptr_instance, &ici);
4095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        debug_report_create_instance(ptr_instance, &ici);
4105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        extensions_create_instance(ptr_instance, &ici);
4115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        *pInstance = created_instance;
4135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        /*
4155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj         * Finally have the layers in place and everyone has seen
4165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj         * the CreateInstance command go by. This allows the layer's
4175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj         * GetInstanceProcAddr functions to return valid extension functions
4185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj         * if enabled.
4195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj         */
4205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_activate_instance_layer_extensions(ptr_instance, *pInstance);
4215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    } else {
4225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // TODO: cleanup here.
4235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
4245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjout:
4265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (NULL != ptr_instance) {
4285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (res != VK_SUCCESS) {
4295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            if (NULL != ptr_instance->next) {
4305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                loader.instances = ptr_instance->next;
4315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
4325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            if (NULL != ptr_instance->disp) {
4335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                loader_instance_heap_free(ptr_instance, ptr_instance->disp);
4345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
4355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            if (ptr_instance->num_tmp_callbacks > 0) {
4365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                util_DestroyDebugReportCallbacks(
4375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    ptr_instance, pAllocator, ptr_instance->num_tmp_callbacks,
4385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    ptr_instance->tmp_callbacks);
4395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                util_FreeDebugReportCreateInfos(
4405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    pAllocator, ptr_instance->tmp_dbg_create_infos,
4415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    ptr_instance->tmp_callbacks);
4425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
4435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_deactivate_layers(ptr_instance, NULL,
4455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                     &ptr_instance->activated_layer_list);
4465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_delete_shadow_inst_layer_names(ptr_instance, pCreateInfo,
4485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                  &ici);
4495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_delete_layer_properties(ptr_instance,
4505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                           &ptr_instance->instance_layer_list);
4515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_scanned_icd_clear(ptr_instance, &ptr_instance->icd_libs);
4525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_destroy_generic_list(
4535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                ptr_instance,
4545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                (struct loader_generic_list *)&ptr_instance->ext_list);
4555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_instance_heap_free(ptr_instance, ptr_instance);
4575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        } else {
4585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            /* Remove temporary debug_report callback */
4595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            util_DestroyDebugReportCallbacks(ptr_instance, pAllocator,
4605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                             ptr_instance->num_tmp_callbacks,
4615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                             ptr_instance->tmp_callbacks);
4625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_delete_shadow_inst_layer_names(ptr_instance, pCreateInfo,
4635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                  &ici);
4645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
4655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (loaderLocked) {
4675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_platform_thread_unlock_mutex(&loader_lock);
4685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
4695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
4705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return res;
4725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
4735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL vkDestroyInstance(
4755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkInstance instance, const VkAllocationCallbacks *pAllocator) {
4765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
4775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_instance *ptr_instance = NULL;
4785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    bool callback_setup = false;
4795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (instance == VK_NULL_HANDLE) {
4815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return;
4825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
4835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(instance);
4855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_lock_mutex(&loader_lock);
4875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    ptr_instance = loader_get_instance(instance);
4895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pAllocator) {
4915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        ptr_instance->alloc_callbacks = *pAllocator;
4925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
4935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
4945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (ptr_instance->num_tmp_callbacks > 0) {
4955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // Setup the temporary callback(s) here to catch cleanup issues:
4965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (!util_CreateDebugReportCallbacks(ptr_instance, pAllocator,
4975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                             ptr_instance->num_tmp_callbacks,
4985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                             ptr_instance->tmp_dbg_create_infos,
4995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                             ptr_instance->tmp_callbacks)) {
5005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            callback_setup = true;
5015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
5025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->DestroyInstance(instance, pAllocator);
5055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_deactivate_layers(ptr_instance, NULL,
5075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                             &ptr_instance->activated_layer_list);
5085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (ptr_instance->phys_devs) {
5095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_instance_heap_free(ptr_instance, ptr_instance->phys_devs);
5105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (callback_setup) {
5125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        util_DestroyDebugReportCallbacks(ptr_instance, pAllocator,
5135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                         ptr_instance->num_tmp_callbacks,
5145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                         ptr_instance->tmp_callbacks);
5155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        util_FreeDebugReportCreateInfos(pAllocator,
5165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                        ptr_instance->tmp_dbg_create_infos,
5175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                        ptr_instance->tmp_callbacks);
5185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_instance_heap_free(ptr_instance, ptr_instance->disp);
5205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_instance_heap_free(ptr_instance, ptr_instance);
5215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_unlock_mutex(&loader_lock);
5225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
5235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
5255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkEnumeratePhysicalDevices(VkInstance instance, uint32_t *pPhysicalDeviceCount,
5265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                           VkPhysicalDevice *pPhysicalDevices) {
5275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
5285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkResult res;
5295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    uint32_t count, i;
5305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_instance *inst;
5315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(instance);
5325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_lock_mutex(&loader_lock);
5345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = disp->EnumeratePhysicalDevices(instance, pPhysicalDeviceCount,
5355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                         pPhysicalDevices);
5365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS && res != VK_INCOMPLETE) {
5385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_platform_thread_unlock_mutex(&loader_lock);
5395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return res;
5405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (!pPhysicalDevices) {
5435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_platform_thread_unlock_mutex(&loader_lock);
5445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return res;
5455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // wrap the PhysDev object for loader usage, return wrapped objects
5485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    inst = loader_get_instance(instance);
5495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (!inst) {
5505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_platform_thread_unlock_mutex(&loader_lock);
5515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return VK_ERROR_INITIALIZATION_FAILED;
5525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    count = (inst->total_gpu_count < *pPhysicalDeviceCount)
5545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                ? inst->total_gpu_count
5555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                : *pPhysicalDeviceCount;
5565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    *pPhysicalDeviceCount = count;
5575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (!inst->phys_devs) {
5585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        inst->phys_devs =
5595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            (struct loader_physical_device_tramp *)loader_instance_heap_alloc(
5605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                inst, inst->total_gpu_count *
5615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                          sizeof(struct loader_physical_device_tramp),
5625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                VK_SYSTEM_ALLOCATION_SCOPE_INSTANCE);
5635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (!inst->phys_devs) {
5655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_platform_thread_unlock_mutex(&loader_lock);
5665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return VK_ERROR_OUT_OF_HOST_MEMORY;
5675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    for (i = 0; i < count; i++) {
5705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // initialize the loader's physicalDevice object
5725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_set_dispatch((void *)&inst->phys_devs[i], inst->disp);
5735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        inst->phys_devs[i].this_instance = inst;
5745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        inst->phys_devs[i].phys_dev = pPhysicalDevices[i];
5755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        // copy wrapped object into Application provided array
5775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        pPhysicalDevices[i] = (VkPhysicalDevice)&inst->phys_devs[i];
5785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
5795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_unlock_mutex(&loader_lock);
5805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return res;
5815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
5825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
5845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetPhysicalDeviceFeatures(VkPhysicalDevice physicalDevice,
5855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                            VkPhysicalDeviceFeatures *pFeatures) {
5865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
5875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice unwrapped_phys_dev =
5885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_unwrap_physical_device(physicalDevice);
5895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(physicalDevice);
5905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetPhysicalDeviceFeatures(unwrapped_phys_dev, pFeatures);
5915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
5925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
5935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
5945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetPhysicalDeviceFormatProperties(VkPhysicalDevice physicalDevice,
5955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                    VkFormat format,
5965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                    VkFormatProperties *pFormatInfo) {
5975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
5985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice unwrapped_pd =
5995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_unwrap_physical_device(physicalDevice);
6005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(physicalDevice);
6015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetPhysicalDeviceFormatProperties(unwrapped_pd, format, pFormatInfo);
6025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
6035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
6055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetPhysicalDeviceImageFormatProperties(
6065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice physicalDevice, VkFormat format, VkImageType type,
6075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkImageTiling tiling, VkImageUsageFlags usage, VkImageCreateFlags flags,
6085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkImageFormatProperties *pImageFormatProperties) {
6095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
6105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice unwrapped_phys_dev =
6115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_unwrap_physical_device(physicalDevice);
6125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(physicalDevice);
6135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->GetPhysicalDeviceImageFormatProperties(
6145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        unwrapped_phys_dev, format, type, tiling, usage, flags,
6155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        pImageFormatProperties);
6165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
6175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
6195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetPhysicalDeviceProperties(VkPhysicalDevice physicalDevice,
6205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                              VkPhysicalDeviceProperties *pProperties) {
6215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
6225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice unwrapped_phys_dev =
6235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_unwrap_physical_device(physicalDevice);
6245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(physicalDevice);
6255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetPhysicalDeviceProperties(unwrapped_phys_dev, pProperties);
6265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
6275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
6295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetPhysicalDeviceQueueFamilyProperties(
6305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice physicalDevice, uint32_t *pQueueFamilyPropertyCount,
6315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkQueueFamilyProperties *pQueueProperties) {
6325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
6335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice unwrapped_phys_dev =
6345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_unwrap_physical_device(physicalDevice);
6355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(physicalDevice);
6365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetPhysicalDeviceQueueFamilyProperties(
6375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        unwrapped_phys_dev, pQueueFamilyPropertyCount, pQueueProperties);
6385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
6395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL vkGetPhysicalDeviceMemoryProperties(
6415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice physicalDevice,
6425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDeviceMemoryProperties *pMemoryProperties) {
6435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
6445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice unwrapped_phys_dev =
6455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_unwrap_physical_device(physicalDevice);
6465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(physicalDevice);
6475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetPhysicalDeviceMemoryProperties(unwrapped_phys_dev,
6485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                            pMemoryProperties);
6495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
6505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL vkCreateDevice(
6525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice physicalDevice, const VkDeviceCreateInfo *pCreateInfo,
6535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkAllocationCallbacks *pAllocator, VkDevice *pDevice) {
6545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkResult res;
6555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_physical_device_tramp *phys_dev = NULL;
6565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_device *dev = NULL;
6575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_instance *inst = NULL;
6585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    assert(pCreateInfo->queueCreateInfoCount >= 1);
6605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_lock_mutex(&loader_lock);
6625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    phys_dev = (struct loader_physical_device_tramp *)physicalDevice;
6645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    inst = (struct loader_instance *)phys_dev->this_instance;
6655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* Get the physical device (ICD) extensions  */
6675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_extension_list icd_exts;
6685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    icd_exts.list = NULL;
6695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res =
6705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_init_generic_list(inst, (struct loader_generic_list *)&icd_exts,
6715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                 sizeof(VkExtensionProperties));
6725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (VK_SUCCESS != res) {
6735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
6745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
6755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_add_device_extensions(
6775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        inst, inst->disp->EnumerateDeviceExtensionProperties,
6785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        phys_dev->phys_dev, "Unknown", &icd_exts);
6795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS) {
6805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
6815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
6825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* make sure requested extensions to be enabled are supported */
6845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_validate_device_extensions(
6855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        phys_dev, &inst->activated_layer_list, &icd_exts, pCreateInfo);
6865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS) {
6875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
6885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
6895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    dev = loader_create_logical_device(inst, pAllocator);
6915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (dev == NULL) {
6925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = VK_ERROR_OUT_OF_HOST_MEMORY;
6935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
6945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
6955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
6965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* copy the instance layer list into the device */
6975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    dev->activated_layer_list.capacity = inst->activated_layer_list.capacity;
6985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    dev->activated_layer_list.count = inst->activated_layer_list.count;
6995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    dev->activated_layer_list.list =
7005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_device_heap_alloc(dev, inst->activated_layer_list.capacity,
7015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                 VK_SYSTEM_ALLOCATION_SCOPE_DEVICE);
7025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (dev->activated_layer_list.list == NULL) {
7035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = VK_ERROR_OUT_OF_HOST_MEMORY;
7045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
7055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
7065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memcpy(dev->activated_layer_list.list, inst->activated_layer_list.list,
7075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj           sizeof(*dev->activated_layer_list.list) *
7085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj               dev->activated_layer_list.count);
7095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    res = loader_create_device_chain(phys_dev, pCreateInfo, pAllocator, inst,
7115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                     dev);
7125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (res != VK_SUCCESS) {
7135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        goto out;
7145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
7155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    *pDevice = dev->device;
7175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* initialize any device extension dispatch entry's from the instance list*/
7195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_init_dispatch_dev_ext(inst, dev);
7205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* initialize WSI device extensions as part of core dispatch since loader
7225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     * has
7235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     * dedicated trampoline code for these*/
7245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_init_device_extension_dispatch_table(
7255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        &dev->loader_dispatch,
7265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        dev->loader_dispatch.core_dispatch.GetDeviceProcAddr, *pDevice);
7275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjout:
7295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // Failure cleanup
7315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (VK_SUCCESS != res) {
7325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (NULL != dev) {
7335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_destroy_logical_device(inst, dev, pAllocator);
7345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
7355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
7365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (NULL != icd_exts.list) {
7385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_destroy_generic_list(inst,
7395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                    (struct loader_generic_list *)&icd_exts);
7405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
7415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_unlock_mutex(&loader_lock);
7425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return res;
7435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
7445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
7465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkDestroyDevice(VkDevice device, const VkAllocationCallbacks *pAllocator) {
7475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
7485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_device *dev;
7495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (device == VK_NULL_HANDLE) {
7515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return;
7525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
7535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_lock_mutex(&loader_lock);
7555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_icd *icd = loader_get_icd_and_device(device, &dev);
7575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const struct loader_instance *inst = icd->this_instance;
7585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
7595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->DestroyDevice(device, pAllocator);
7615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    dev->device = NULL;
7625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_remove_logical_device(inst, icd, dev, pAllocator);
7635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_unlock_mutex(&loader_lock);
7655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
7665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
767518510be4037764bdf6313dd275cee9b34e75aaesewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
768518510be4037764bdf6313dd275cee9b34e75aaesewardjvkEnumerateDeviceExtensionProperties(VkPhysicalDevice physicalDevice,
7695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                     const char *pLayerName,
7705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                     uint32_t *pPropertyCount,
7715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                     VkExtensionProperties *pProperties) {
7725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkResult res = VK_SUCCESS;
7735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_physical_device_tramp *phys_dev;
7745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    phys_dev = (struct loader_physical_device_tramp *)physicalDevice;
7755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_lock_mutex(&loader_lock);
7775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* If pLayerName == NULL, then querying ICD extensions, pass this call
7795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj       down the instance chain which will terminate in the ICD. This allows
7805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj       layers to filter the extensions coming back up the chain.
7815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj       If pLayerName != NULL then get layer extensions from manifest file.  */
7825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pLayerName == NULL || strlen(pLayerName) == 0) {
7835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        const VkLayerInstanceDispatchTable *disp;
7845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        disp = loader_get_instance_dispatch(physicalDevice);
7865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        res = disp->EnumerateDeviceExtensionProperties(
7875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            phys_dev->phys_dev, NULL, pPropertyCount, pProperties);
7885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    } else {
7895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
7905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        uint32_t count;
7915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        uint32_t copy_size;
7925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        const struct loader_instance *inst = phys_dev->this_instance;
7935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        struct loader_device_extension_list *dev_ext_list = NULL;
7945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        struct loader_device_extension_list local_ext_list;
7955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        memset(&local_ext_list, 0, sizeof(local_ext_list));
7965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (vk_string_validate(MaxLoaderStringLength, pLayerName) ==
7975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            VK_STRING_ERROR_NONE) {
7985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            if (strcmp(pLayerName, std_validation_str) == 0) {
7995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                struct loader_layer_list local_list;
8005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                memset(&local_list, 0, sizeof(local_list));
8015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                for (uint32_t i = 0; i < sizeof(std_validation_names) /
8025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                             sizeof(std_validation_names[0]);
8035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                     i++) {
8045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    loader_find_layer_name_add_list(
8055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                        NULL, std_validation_names[i],
806bd7a24a33d1e67aeada94ce39e160c5da5712744sewardj                        VK_LAYER_TYPE_INSTANCE_EXPLICIT, &inst->instance_layer_list,
8075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                        &local_list);
8085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                }
8095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                for (uint32_t i = 0; i < local_list.count; i++) {
8105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    struct loader_device_extension_list *ext_list =
8115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                        &local_list.list[i].device_extension_list;
8125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    for (uint32_t j = 0; j < ext_list->count; j++) {
8135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                        loader_add_to_dev_ext_list(NULL, &local_ext_list,
8145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                   &ext_list->list[j].props, 0,
8155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                   NULL);
8165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    }
8175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                }
8185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                dev_ext_list = &local_ext_list;
8195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            } else {
8215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                for (uint32_t i = 0; i < inst->instance_layer_list.count; i++) {
8225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    struct loader_layer_properties *props =
8235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                        &inst->instance_layer_list.list[i];
8245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    if (strcmp(props->info.layerName, pLayerName) == 0) {
8255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                        dev_ext_list = &props->device_extension_list;
8265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    }
827044514a949280ebcda5b9f9f402ec84098229354florian                }
8285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
8295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            count = (dev_ext_list == NULL) ? 0 : dev_ext_list->count;
8315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            if (pProperties == NULL) {
8325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                *pPropertyCount = count;
8335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                loader_destroy_generic_list(
8342d3aed7fb6346af04d46cf2d7b658fd4ba2ebd54florian                    inst, (struct loader_generic_list *)&local_ext_list);
8355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                loader_platform_thread_unlock_mutex(&loader_lock);
8365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                return VK_SUCCESS;
8375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
8385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            copy_size = *pPropertyCount < count ? *pPropertyCount : count;
8405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            for (uint32_t i = 0; i < copy_size; i++) {
8415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                memcpy(&pProperties[i], &dev_ext_list->list[i].props,
8425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                       sizeof(VkExtensionProperties));
8435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
8445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            *pPropertyCount = copy_size;
8455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
846044514a949280ebcda5b9f9f402ec84098229354florian            loader_destroy_generic_list(
8472d3aed7fb6346af04d46cf2d7b658fd4ba2ebd54florian                inst, (struct loader_generic_list *)&local_ext_list);
8485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            if (copy_size < count) {
8492d3aed7fb6346af04d46cf2d7b658fd4ba2ebd54florian                loader_platform_thread_unlock_mutex(&loader_lock);
8505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                return VK_INCOMPLETE;
8515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
8525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        } else {
8535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_log(inst, VK_DEBUG_REPORT_ERROR_BIT_EXT, 0,
8545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                       "vkEnumerateDeviceExtensionProperties:  pLayerName "
8555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                       "is too long or is badly formed");
8565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            loader_platform_thread_unlock_mutex(&loader_lock);
8575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            return VK_ERROR_EXTENSION_NOT_PRESENT;
8585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
8595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
8605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_unlock_mutex(&loader_lock);
8625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return res;
8635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
8645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
8665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkEnumerateDeviceLayerProperties(VkPhysicalDevice physicalDevice,
8675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                 uint32_t *pPropertyCount,
8685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                 VkLayerProperties *pProperties) {
8695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    uint32_t copy_size;
8705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_physical_device_tramp *phys_dev;
8715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    struct loader_layer_list *enabled_layers, layers_list;
8725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    uint32_t std_val_count = sizeof(std_validation_names) /
8735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                sizeof(std_validation_names[0]);
8745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    memset(&layers_list, 0, sizeof(layers_list));
8755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_lock_mutex(&loader_lock);
8765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* Don't dispatch this call down the instance chain, want all device layers
8785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj       enumerated and instance chain may not contain all device layers */
8795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // TODO re-evaluate the above statement we maybe able to start calling
8805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    // down the chain
8815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    phys_dev = (struct loader_physical_device_tramp *)physicalDevice;
8835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const struct loader_instance *inst = phys_dev->this_instance;
8845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
8855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    uint32_t count = inst->activated_layer_list.count;
8865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (inst->activated_layers_are_std_val)
8875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        count = count - std_val_count + 1;
8885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (pProperties == NULL) {
8895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        *pPropertyCount = count;
8905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_platform_thread_unlock_mutex(&loader_lock);
8915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return VK_SUCCESS;
8925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
8935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    /* make sure to enumerate standard_validation if that is what was used
8945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj     at the instance layer enablement */
8955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (inst->activated_layers_are_std_val) {
8965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        enabled_layers = &layers_list;
8975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        enabled_layers->count = count;
8985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        enabled_layers->capacity = enabled_layers->count *
8995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                 sizeof(struct loader_layer_properties);
9005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        enabled_layers->list = loader_instance_heap_alloc(inst, enabled_layers->capacity,
9015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                VK_SYSTEM_ALLOCATION_SCOPE_INSTANCE);
9025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        if (!enabled_layers->list)
9035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            return VK_ERROR_OUT_OF_HOST_MEMORY;
9045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        uint32_t j = 0;
9065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        for (uint32_t i = 0; i < inst->activated_layer_list.count; j++) {
9075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
90897b89f7a284a15590beb9e8dfc932f5aeffd68d5florian            if (loader_find_layer_name_array(
90997b89f7a284a15590beb9e8dfc932f5aeffd68d5florian                    inst->activated_layer_list.list[i].info.layerName,
9105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    std_val_count, std_validation_names)) {
9115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                struct loader_layer_properties props;
9125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                loader_init_std_validation_props(&props);
9135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                VkResult err = loader_copy_layer_properties(inst,
9145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                            &enabled_layers->list[j],
9155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                            &props);
9165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                if (err != VK_SUCCESS) {
9175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    return err;
9185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                }
9195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                i += std_val_count;
9205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
9215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            else {
9225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                VkResult err = loader_copy_layer_properties(inst,
9235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                            &enabled_layers->list[j],
9245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                                            &inst->activated_layer_list.list[i++]);
9255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                if (err != VK_SUCCESS) {
9265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                    return err;
9275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                }
9285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            }
9295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        }
9305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
9315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    else {
9325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        enabled_layers = (struct loader_layer_list *) &inst->activated_layer_list;
9335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
9345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    copy_size = (*pPropertyCount < count) ? *pPropertyCount : count;
9375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    for (uint32_t i = 0; i < copy_size; i++) {
9385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        memcpy(&pProperties[i], &(enabled_layers->list[i].info),
9395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj               sizeof(VkLayerProperties));
9405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
9415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    *pPropertyCount = copy_size;
9425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (inst->activated_layers_are_std_val) {
9445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_delete_layer_properties(inst, enabled_layers);
9455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
9465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    if (copy_size < count) {
9475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_platform_thread_unlock_mutex(&loader_lock);
9485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        return VK_INCOMPLETE;
9495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    }
9505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_platform_thread_unlock_mutex(&loader_lock);
9525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return VK_SUCCESS;
9535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
9545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
9565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetDeviceQueue(VkDevice device, uint32_t queueNodeIndex, uint32_t queueIndex,
9575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                 VkQueue *pQueue) {
9585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
9595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
9615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetDeviceQueue(device, queueNodeIndex, queueIndex, pQueue);
9635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    loader_set_dispatch(*pQueue, disp);
9645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
9655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
9675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkQueueSubmit(VkQueue queue, uint32_t submitCount, const VkSubmitInfo *pSubmits,
9685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj              VkFence fence) {
9695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
9705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(queue);
9725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->QueueSubmit(queue, submitCount, pSubmits, fence);
9745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
9755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL vkQueueWaitIdle(VkQueue queue) {
9775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
9785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(queue);
9805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->QueueWaitIdle(queue);
9825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
9835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL vkDeviceWaitIdle(VkDevice device) {
9855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
9865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
9885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
989044514a949280ebcda5b9f9f402ec84098229354florian    return disp->DeviceWaitIdle(device);
990044514a949280ebcda5b9f9f402ec84098229354florian}
9915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
9935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkAllocateMemory(VkDevice device, const VkMemoryAllocateInfo *pAllocateInfo,
9945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                 const VkAllocationCallbacks *pAllocator,
9955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                 VkDeviceMemory *pMemory) {
9965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
9975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
9985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
9995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1000044514a949280ebcda5b9f9f402ec84098229354florian    return disp->AllocateMemory(device, pAllocateInfo, pAllocator, pMemory);
10015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
10025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1003044514a949280ebcda5b9f9f402ec84098229354florianLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1004044514a949280ebcda5b9f9f402ec84098229354florianvkFreeMemory(VkDevice device, VkDeviceMemory mem,
1005044514a949280ebcda5b9f9f402ec84098229354florian             const VkAllocationCallbacks *pAllocator) {
1006044514a949280ebcda5b9f9f402ec84098229354florian    const VkLayerDispatchTable *disp;
1007044514a949280ebcda5b9f9f402ec84098229354florian
1008044514a949280ebcda5b9f9f402ec84098229354florian    disp = loader_get_dispatch(device);
1009044514a949280ebcda5b9f9f402ec84098229354florian
1010044514a949280ebcda5b9f9f402ec84098229354florian    disp->FreeMemory(device, mem, pAllocator);
1011044514a949280ebcda5b9f9f402ec84098229354florian}
10125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
10145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkMapMemory(VkDevice device, VkDeviceMemory mem, VkDeviceSize offset,
10155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj            VkDeviceSize size, VkFlags flags, void **ppData) {
10165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->MapMemory(device, mem, offset, size, flags, ppData);
10215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
10225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
10245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkUnmapMemory(VkDevice device, VkDeviceMemory mem) {
10255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->UnmapMemory(device, mem);
1030044514a949280ebcda5b9f9f402ec84098229354florian}
1031044514a949280ebcda5b9f9f402ec84098229354florian
1032044514a949280ebcda5b9f9f402ec84098229354florianLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1033044514a949280ebcda5b9f9f402ec84098229354florianvkFlushMappedMemoryRanges(VkDevice device, uint32_t memoryRangeCount,
10345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                          const VkMappedMemoryRange *pMemoryRanges) {
10355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1039044514a949280ebcda5b9f9f402ec84098229354florian    return disp->FlushMappedMemoryRanges(device, memoryRangeCount,
10405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                         pMemoryRanges);
10415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
10425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
10445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkInvalidateMappedMemoryRanges(VkDevice device, uint32_t memoryRangeCount,
10455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                               const VkMappedMemoryRange *pMemoryRanges) {
10465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->InvalidateMappedMemoryRanges(device, memoryRangeCount,
10515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                              pMemoryRanges);
10525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
10535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
10555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetDeviceMemoryCommitment(VkDevice device, VkDeviceMemory memory,
10565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                            VkDeviceSize *pCommittedMemoryInBytes) {
10575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetDeviceMemoryCommitment(device, memory, pCommittedMemoryInBytes);
10625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
10635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
10655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkBindBufferMemory(VkDevice device, VkBuffer buffer, VkDeviceMemory mem,
10665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                   VkDeviceSize offset) {
10675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->BindBufferMemory(device, buffer, mem, offset);
10725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
10735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
10755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkBindImageMemory(VkDevice device, VkImage image, VkDeviceMemory mem,
10765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                  VkDeviceSize offset) {
10775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->BindImageMemory(device, image, mem, offset);
1082044514a949280ebcda5b9f9f402ec84098229354florian}
1083044514a949280ebcda5b9f9f402ec84098229354florian
1084044514a949280ebcda5b9f9f402ec84098229354florianLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1085044514a949280ebcda5b9f9f402ec84098229354florianvkGetBufferMemoryRequirements(VkDevice device, VkBuffer buffer,
1086044514a949280ebcda5b9f9f402ec84098229354florian                              VkMemoryRequirements *pMemoryRequirements) {
10875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
10885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
10905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetBufferMemoryRequirements(device, buffer, pMemoryRequirements);
10925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
10935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
10945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1095044514a949280ebcda5b9f9f402ec84098229354florianvkGetImageMemoryRequirements(VkDevice device, VkImage image,
1096044514a949280ebcda5b9f9f402ec84098229354florian                             VkMemoryRequirements *pMemoryRequirements) {
1097044514a949280ebcda5b9f9f402ec84098229354florian    const VkLayerDispatchTable *disp;
1098044514a949280ebcda5b9f9f402ec84098229354florian
1099044514a949280ebcda5b9f9f402ec84098229354florian    disp = loader_get_dispatch(device);
11005d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11015d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetImageMemoryRequirements(device, image, pMemoryRequirements);
11025d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11035d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1104044514a949280ebcda5b9f9f402ec84098229354florianLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL vkGetImageSparseMemoryRequirements(
11055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkDevice device, VkImage image, uint32_t *pSparseMemoryRequirementCount,
11065d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkSparseImageMemoryRequirements *pSparseMemoryRequirements) {
11075d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11085d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11095d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
11105d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetImageSparseMemoryRequirements(device, image,
11125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                           pSparseMemoryRequirementCount,
11135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                                           pSparseMemoryRequirements);
11145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
11175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetPhysicalDeviceSparseImageFormatProperties(
11185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice physicalDevice, VkFormat format, VkImageType type,
11195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkSampleCountFlagBits samples, VkImageUsageFlags usage,
11205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkImageTiling tiling, uint32_t *pPropertyCount,
11215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkSparseImageFormatProperties *pProperties) {
11225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerInstanceDispatchTable *disp;
11235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    VkPhysicalDevice unwrapped_phys_dev =
11245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        loader_unwrap_physical_device(physicalDevice);
11255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_instance_dispatch(physicalDevice);
11265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->GetPhysicalDeviceSparseImageFormatProperties(
11285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        unwrapped_phys_dev, format, type, samples, usage, tiling,
11295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj        pPropertyCount, pProperties);
11305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
11335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkQueueBindSparse(VkQueue queue, uint32_t bindInfoCount,
11345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                  const VkBindSparseInfo *pBindInfo, VkFence fence) {
11355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(queue);
11385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->QueueBindSparse(queue, bindInfoCount, pBindInfo, fence);
11405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
11435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkCreateFence(VkDevice device, const VkFenceCreateInfo *pCreateInfo,
11445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj              const VkAllocationCallbacks *pAllocator, VkFence *pFence) {
11455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
11485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->CreateFence(device, pCreateInfo, pAllocator, pFence);
11505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
11535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkDestroyFence(VkDevice device, VkFence fence,
11545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj               const VkAllocationCallbacks *pAllocator) {
11555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
11585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->DestroyFence(device, fence, pAllocator);
11605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
11635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkResetFences(VkDevice device, uint32_t fenceCount, const VkFence *pFences) {
11645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
11675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->ResetFences(device, fenceCount, pFences);
11695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
11725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetFenceStatus(VkDevice device, VkFence fence) {
11735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1175044514a949280ebcda5b9f9f402ec84098229354florian    disp = loader_get_dispatch(device);
1176044514a949280ebcda5b9f9f402ec84098229354florian
1177044514a949280ebcda5b9f9f402ec84098229354florian    return disp->GetFenceStatus(device, fence);
1178044514a949280ebcda5b9f9f402ec84098229354florian}
1179044514a949280ebcda5b9f9f402ec84098229354florian
11805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
11815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkWaitForFences(VkDevice device, uint32_t fenceCount, const VkFence *pFences,
11825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                VkBool32 waitAll, uint64_t timeout) {
11835d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11845d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11855d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
11865d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11875d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->WaitForFences(device, fenceCount, pFences, waitAll, timeout);
11885d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
11895d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11905d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
11915d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkCreateSemaphore(VkDevice device, const VkSemaphoreCreateInfo *pCreateInfo,
11925d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                  const VkAllocationCallbacks *pAllocator,
11935d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                  VkSemaphore *pSemaphore) {
11945d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
11955d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11965d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
11975d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
11985d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->CreateSemaphore(device, pCreateInfo, pAllocator, pSemaphore);
11995d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
1200044514a949280ebcda5b9f9f402ec84098229354florian
1201044514a949280ebcda5b9f9f402ec84098229354florianLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1202044514a949280ebcda5b9f9f402ec84098229354florianvkDestroySemaphore(VkDevice device, VkSemaphore semaphore,
1203044514a949280ebcda5b9f9f402ec84098229354florian                   const VkAllocationCallbacks *pAllocator) {
12045d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12055d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
1206044514a949280ebcda5b9f9f402ec84098229354florian    disp = loader_get_dispatch(device);
1207044514a949280ebcda5b9f9f402ec84098229354florian
1208044514a949280ebcda5b9f9f402ec84098229354florian    disp->DestroySemaphore(device, semaphore, pAllocator);
1209044514a949280ebcda5b9f9f402ec84098229354florian}
1210044514a949280ebcda5b9f9f402ec84098229354florian
12115d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
12125d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkCreateEvent(VkDevice device, const VkEventCreateInfo *pCreateInfo,
12135d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj              const VkAllocationCallbacks *pAllocator, VkEvent *pEvent) {
12145d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12155d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12165d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
12175d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12185d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->CreateEvent(device, pCreateInfo, pAllocator, pEvent);
12195d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
12205d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12215d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
12225d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkDestroyEvent(VkDevice device, VkEvent event,
12235d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj               const VkAllocationCallbacks *pAllocator) {
12245d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12255d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12265d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
12275d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12285d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->DestroyEvent(device, event, pAllocator);
12295d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
12305d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12315d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
12325d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetEventStatus(VkDevice device, VkEvent event) {
12335d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12345d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12355d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
12365d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12375d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->GetEventStatus(device, event);
12385d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
12395d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12405d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
12415d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkSetEvent(VkDevice device, VkEvent event) {
12425d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12435d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12445d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
12455d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12465d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->SetEvent(device, event);
12475d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
12485d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12495d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
12505d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkResetEvent(VkDevice device, VkEvent event) {
12515d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12525d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12535d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
12545d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12555d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->ResetEvent(device, event);
12565d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
12575d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12585d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
12595d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkCreateQueryPool(VkDevice device, const VkQueryPoolCreateInfo *pCreateInfo,
12605d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                  const VkAllocationCallbacks *pAllocator,
12615d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                  VkQueryPool *pQueryPool) {
12625d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12635d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12645d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
12655d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12665d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    return disp->CreateQueryPool(device, pCreateInfo, pAllocator, pQueryPool);
12675d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
12685d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12695d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
12705d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkDestroyQueryPool(VkDevice device, VkQueryPool queryPool,
12715d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                   const VkAllocationCallbacks *pAllocator) {
12725d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    const VkLayerDispatchTable *disp;
12735d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12745d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp = loader_get_dispatch(device);
12755d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12765d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj    disp->DestroyQueryPool(device, queryPool, pAllocator);
12775d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj}
12785d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj
12795d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjLOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
12805d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardjvkGetQueryPoolResults(VkDevice device, VkQueryPool queryPool,
12815d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                      uint32_t firstQuery, uint32_t queryCount, size_t dataSize,
12825d616dfbb8439dfd51a40ddf1dba970938baa1ebsewardj                      void *pData, VkDeviceSize stride,
1283                      VkQueryResultFlags flags) {
1284    const VkLayerDispatchTable *disp;
1285
1286    disp = loader_get_dispatch(device);
1287
1288    return disp->GetQueryPoolResults(device, queryPool, firstQuery, queryCount,
1289                                     dataSize, pData, stride, flags);
1290}
1291
1292LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1293vkCreateBuffer(VkDevice device, const VkBufferCreateInfo *pCreateInfo,
1294               const VkAllocationCallbacks *pAllocator, VkBuffer *pBuffer) {
1295    const VkLayerDispatchTable *disp;
1296
1297    disp = loader_get_dispatch(device);
1298
1299    return disp->CreateBuffer(device, pCreateInfo, pAllocator, pBuffer);
1300}
1301
1302LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1303vkDestroyBuffer(VkDevice device, VkBuffer buffer,
1304                const VkAllocationCallbacks *pAllocator) {
1305    const VkLayerDispatchTable *disp;
1306
1307    disp = loader_get_dispatch(device);
1308
1309    disp->DestroyBuffer(device, buffer, pAllocator);
1310}
1311
1312LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1313vkCreateBufferView(VkDevice device, const VkBufferViewCreateInfo *pCreateInfo,
1314                   const VkAllocationCallbacks *pAllocator,
1315                   VkBufferView *pView) {
1316    const VkLayerDispatchTable *disp;
1317
1318    disp = loader_get_dispatch(device);
1319
1320    return disp->CreateBufferView(device, pCreateInfo, pAllocator, pView);
1321}
1322
1323LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1324vkDestroyBufferView(VkDevice device, VkBufferView bufferView,
1325                    const VkAllocationCallbacks *pAllocator) {
1326    const VkLayerDispatchTable *disp;
1327
1328    disp = loader_get_dispatch(device);
1329
1330    disp->DestroyBufferView(device, bufferView, pAllocator);
1331}
1332
1333LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1334vkCreateImage(VkDevice device, const VkImageCreateInfo *pCreateInfo,
1335              const VkAllocationCallbacks *pAllocator, VkImage *pImage) {
1336    const VkLayerDispatchTable *disp;
1337
1338    disp = loader_get_dispatch(device);
1339
1340    return disp->CreateImage(device, pCreateInfo, pAllocator, pImage);
1341}
1342
1343LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1344vkDestroyImage(VkDevice device, VkImage image,
1345               const VkAllocationCallbacks *pAllocator) {
1346    const VkLayerDispatchTable *disp;
1347
1348    disp = loader_get_dispatch(device);
1349
1350    disp->DestroyImage(device, image, pAllocator);
1351}
1352
1353LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1354vkGetImageSubresourceLayout(VkDevice device, VkImage image,
1355                            const VkImageSubresource *pSubresource,
1356                            VkSubresourceLayout *pLayout) {
1357    const VkLayerDispatchTable *disp;
1358
1359    disp = loader_get_dispatch(device);
1360
1361    disp->GetImageSubresourceLayout(device, image, pSubresource, pLayout);
1362}
1363
1364LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1365vkCreateImageView(VkDevice device, const VkImageViewCreateInfo *pCreateInfo,
1366                  const VkAllocationCallbacks *pAllocator, VkImageView *pView) {
1367    const VkLayerDispatchTable *disp;
1368
1369    disp = loader_get_dispatch(device);
1370
1371    return disp->CreateImageView(device, pCreateInfo, pAllocator, pView);
1372}
1373
1374LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1375vkDestroyImageView(VkDevice device, VkImageView imageView,
1376                   const VkAllocationCallbacks *pAllocator) {
1377    const VkLayerDispatchTable *disp;
1378
1379    disp = loader_get_dispatch(device);
1380
1381    disp->DestroyImageView(device, imageView, pAllocator);
1382}
1383
1384LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1385vkCreateShaderModule(VkDevice device,
1386                     const VkShaderModuleCreateInfo *pCreateInfo,
1387                     const VkAllocationCallbacks *pAllocator,
1388                     VkShaderModule *pShader) {
1389    const VkLayerDispatchTable *disp;
1390
1391    disp = loader_get_dispatch(device);
1392
1393    return disp->CreateShaderModule(device, pCreateInfo, pAllocator, pShader);
1394}
1395
1396LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1397vkDestroyShaderModule(VkDevice device, VkShaderModule shaderModule,
1398                      const VkAllocationCallbacks *pAllocator) {
1399    const VkLayerDispatchTable *disp;
1400
1401    disp = loader_get_dispatch(device);
1402
1403    disp->DestroyShaderModule(device, shaderModule, pAllocator);
1404}
1405
1406LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1407vkCreatePipelineCache(VkDevice device,
1408                      const VkPipelineCacheCreateInfo *pCreateInfo,
1409                      const VkAllocationCallbacks *pAllocator,
1410                      VkPipelineCache *pPipelineCache) {
1411    const VkLayerDispatchTable *disp;
1412
1413    disp = loader_get_dispatch(device);
1414
1415    return disp->CreatePipelineCache(device, pCreateInfo, pAllocator,
1416                                     pPipelineCache);
1417}
1418
1419LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1420vkDestroyPipelineCache(VkDevice device, VkPipelineCache pipelineCache,
1421                       const VkAllocationCallbacks *pAllocator) {
1422    const VkLayerDispatchTable *disp;
1423
1424    disp = loader_get_dispatch(device);
1425
1426    disp->DestroyPipelineCache(device, pipelineCache, pAllocator);
1427}
1428
1429LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1430vkGetPipelineCacheData(VkDevice device, VkPipelineCache pipelineCache,
1431                       size_t *pDataSize, void *pData) {
1432    const VkLayerDispatchTable *disp;
1433
1434    disp = loader_get_dispatch(device);
1435
1436    return disp->GetPipelineCacheData(device, pipelineCache, pDataSize, pData);
1437}
1438
1439LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1440vkMergePipelineCaches(VkDevice device, VkPipelineCache dstCache,
1441                      uint32_t srcCacheCount,
1442                      const VkPipelineCache *pSrcCaches) {
1443    const VkLayerDispatchTable *disp;
1444
1445    disp = loader_get_dispatch(device);
1446
1447    return disp->MergePipelineCaches(device, dstCache, srcCacheCount,
1448                                     pSrcCaches);
1449}
1450
1451LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1452vkCreateGraphicsPipelines(VkDevice device, VkPipelineCache pipelineCache,
1453                          uint32_t createInfoCount,
1454                          const VkGraphicsPipelineCreateInfo *pCreateInfos,
1455                          const VkAllocationCallbacks *pAllocator,
1456                          VkPipeline *pPipelines) {
1457    const VkLayerDispatchTable *disp;
1458
1459    disp = loader_get_dispatch(device);
1460
1461    return disp->CreateGraphicsPipelines(device, pipelineCache, createInfoCount,
1462                                         pCreateInfos, pAllocator, pPipelines);
1463}
1464
1465LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1466vkCreateComputePipelines(VkDevice device, VkPipelineCache pipelineCache,
1467                         uint32_t createInfoCount,
1468                         const VkComputePipelineCreateInfo *pCreateInfos,
1469                         const VkAllocationCallbacks *pAllocator,
1470                         VkPipeline *pPipelines) {
1471    const VkLayerDispatchTable *disp;
1472
1473    disp = loader_get_dispatch(device);
1474
1475    return disp->CreateComputePipelines(device, pipelineCache, createInfoCount,
1476                                        pCreateInfos, pAllocator, pPipelines);
1477}
1478
1479LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1480vkDestroyPipeline(VkDevice device, VkPipeline pipeline,
1481                  const VkAllocationCallbacks *pAllocator) {
1482    const VkLayerDispatchTable *disp;
1483
1484    disp = loader_get_dispatch(device);
1485
1486    disp->DestroyPipeline(device, pipeline, pAllocator);
1487}
1488
1489LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1490vkCreatePipelineLayout(VkDevice device,
1491                       const VkPipelineLayoutCreateInfo *pCreateInfo,
1492                       const VkAllocationCallbacks *pAllocator,
1493                       VkPipelineLayout *pPipelineLayout) {
1494    const VkLayerDispatchTable *disp;
1495
1496    disp = loader_get_dispatch(device);
1497
1498    return disp->CreatePipelineLayout(device, pCreateInfo, pAllocator,
1499                                      pPipelineLayout);
1500}
1501
1502LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1503vkDestroyPipelineLayout(VkDevice device, VkPipelineLayout pipelineLayout,
1504                        const VkAllocationCallbacks *pAllocator) {
1505    const VkLayerDispatchTable *disp;
1506
1507    disp = loader_get_dispatch(device);
1508
1509    disp->DestroyPipelineLayout(device, pipelineLayout, pAllocator);
1510}
1511
1512LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1513vkCreateSampler(VkDevice device, const VkSamplerCreateInfo *pCreateInfo,
1514                const VkAllocationCallbacks *pAllocator, VkSampler *pSampler) {
1515    const VkLayerDispatchTable *disp;
1516
1517    disp = loader_get_dispatch(device);
1518
1519    return disp->CreateSampler(device, pCreateInfo, pAllocator, pSampler);
1520}
1521
1522LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1523vkDestroySampler(VkDevice device, VkSampler sampler,
1524                 const VkAllocationCallbacks *pAllocator) {
1525    const VkLayerDispatchTable *disp;
1526
1527    disp = loader_get_dispatch(device);
1528
1529    disp->DestroySampler(device, sampler, pAllocator);
1530}
1531
1532LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1533vkCreateDescriptorSetLayout(VkDevice device,
1534                            const VkDescriptorSetLayoutCreateInfo *pCreateInfo,
1535                            const VkAllocationCallbacks *pAllocator,
1536                            VkDescriptorSetLayout *pSetLayout) {
1537    const VkLayerDispatchTable *disp;
1538
1539    disp = loader_get_dispatch(device);
1540
1541    return disp->CreateDescriptorSetLayout(device, pCreateInfo, pAllocator,
1542                                           pSetLayout);
1543}
1544
1545LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1546vkDestroyDescriptorSetLayout(VkDevice device,
1547                             VkDescriptorSetLayout descriptorSetLayout,
1548                             const VkAllocationCallbacks *pAllocator) {
1549    const VkLayerDispatchTable *disp;
1550
1551    disp = loader_get_dispatch(device);
1552
1553    disp->DestroyDescriptorSetLayout(device, descriptorSetLayout, pAllocator);
1554}
1555
1556LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1557vkCreateDescriptorPool(VkDevice device,
1558                       const VkDescriptorPoolCreateInfo *pCreateInfo,
1559                       const VkAllocationCallbacks *pAllocator,
1560                       VkDescriptorPool *pDescriptorPool) {
1561    const VkLayerDispatchTable *disp;
1562
1563    disp = loader_get_dispatch(device);
1564
1565    return disp->CreateDescriptorPool(device, pCreateInfo, pAllocator,
1566                                      pDescriptorPool);
1567}
1568
1569LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1570vkDestroyDescriptorPool(VkDevice device, VkDescriptorPool descriptorPool,
1571                        const VkAllocationCallbacks *pAllocator) {
1572    const VkLayerDispatchTable *disp;
1573
1574    disp = loader_get_dispatch(device);
1575
1576    disp->DestroyDescriptorPool(device, descriptorPool, pAllocator);
1577}
1578
1579LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1580vkResetDescriptorPool(VkDevice device, VkDescriptorPool descriptorPool,
1581                      VkDescriptorPoolResetFlags flags) {
1582    const VkLayerDispatchTable *disp;
1583
1584    disp = loader_get_dispatch(device);
1585
1586    return disp->ResetDescriptorPool(device, descriptorPool, flags);
1587}
1588
1589LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1590vkAllocateDescriptorSets(VkDevice device,
1591                         const VkDescriptorSetAllocateInfo *pAllocateInfo,
1592                         VkDescriptorSet *pDescriptorSets) {
1593    const VkLayerDispatchTable *disp;
1594
1595    disp = loader_get_dispatch(device);
1596
1597    return disp->AllocateDescriptorSets(device, pAllocateInfo, pDescriptorSets);
1598}
1599
1600LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1601vkFreeDescriptorSets(VkDevice device, VkDescriptorPool descriptorPool,
1602                     uint32_t descriptorSetCount,
1603                     const VkDescriptorSet *pDescriptorSets) {
1604    const VkLayerDispatchTable *disp;
1605
1606    disp = loader_get_dispatch(device);
1607
1608    return disp->FreeDescriptorSets(device, descriptorPool, descriptorSetCount,
1609                                    pDescriptorSets);
1610}
1611
1612LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1613vkUpdateDescriptorSets(VkDevice device, uint32_t descriptorWriteCount,
1614                       const VkWriteDescriptorSet *pDescriptorWrites,
1615                       uint32_t descriptorCopyCount,
1616                       const VkCopyDescriptorSet *pDescriptorCopies) {
1617    const VkLayerDispatchTable *disp;
1618
1619    disp = loader_get_dispatch(device);
1620
1621    disp->UpdateDescriptorSets(device, descriptorWriteCount, pDescriptorWrites,
1622                               descriptorCopyCount, pDescriptorCopies);
1623}
1624
1625LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1626vkCreateFramebuffer(VkDevice device, const VkFramebufferCreateInfo *pCreateInfo,
1627                    const VkAllocationCallbacks *pAllocator,
1628                    VkFramebuffer *pFramebuffer) {
1629    const VkLayerDispatchTable *disp;
1630
1631    disp = loader_get_dispatch(device);
1632
1633    return disp->CreateFramebuffer(device, pCreateInfo, pAllocator,
1634                                   pFramebuffer);
1635}
1636
1637LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1638vkDestroyFramebuffer(VkDevice device, VkFramebuffer framebuffer,
1639                     const VkAllocationCallbacks *pAllocator) {
1640    const VkLayerDispatchTable *disp;
1641
1642    disp = loader_get_dispatch(device);
1643
1644    disp->DestroyFramebuffer(device, framebuffer, pAllocator);
1645}
1646
1647LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1648vkCreateRenderPass(VkDevice device, const VkRenderPassCreateInfo *pCreateInfo,
1649                   const VkAllocationCallbacks *pAllocator,
1650                   VkRenderPass *pRenderPass) {
1651    const VkLayerDispatchTable *disp;
1652
1653    disp = loader_get_dispatch(device);
1654
1655    return disp->CreateRenderPass(device, pCreateInfo, pAllocator, pRenderPass);
1656}
1657
1658LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1659vkDestroyRenderPass(VkDevice device, VkRenderPass renderPass,
1660                    const VkAllocationCallbacks *pAllocator) {
1661    const VkLayerDispatchTable *disp;
1662
1663    disp = loader_get_dispatch(device);
1664
1665    disp->DestroyRenderPass(device, renderPass, pAllocator);
1666}
1667
1668LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1669vkGetRenderAreaGranularity(VkDevice device, VkRenderPass renderPass,
1670                           VkExtent2D *pGranularity) {
1671    const VkLayerDispatchTable *disp;
1672
1673    disp = loader_get_dispatch(device);
1674
1675    disp->GetRenderAreaGranularity(device, renderPass, pGranularity);
1676}
1677
1678LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1679vkCreateCommandPool(VkDevice device, const VkCommandPoolCreateInfo *pCreateInfo,
1680                    const VkAllocationCallbacks *pAllocator,
1681                    VkCommandPool *pCommandPool) {
1682    const VkLayerDispatchTable *disp;
1683
1684    disp = loader_get_dispatch(device);
1685
1686    return disp->CreateCommandPool(device, pCreateInfo, pAllocator,
1687                                   pCommandPool);
1688}
1689
1690LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1691vkDestroyCommandPool(VkDevice device, VkCommandPool commandPool,
1692                     const VkAllocationCallbacks *pAllocator) {
1693    const VkLayerDispatchTable *disp;
1694
1695    disp = loader_get_dispatch(device);
1696
1697    disp->DestroyCommandPool(device, commandPool, pAllocator);
1698}
1699
1700LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1701vkResetCommandPool(VkDevice device, VkCommandPool commandPool,
1702                   VkCommandPoolResetFlags flags) {
1703    const VkLayerDispatchTable *disp;
1704
1705    disp = loader_get_dispatch(device);
1706
1707    return disp->ResetCommandPool(device, commandPool, flags);
1708}
1709
1710LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1711vkAllocateCommandBuffers(VkDevice device,
1712                         const VkCommandBufferAllocateInfo *pAllocateInfo,
1713                         VkCommandBuffer *pCommandBuffers) {
1714    const VkLayerDispatchTable *disp;
1715    VkResult res;
1716
1717    disp = loader_get_dispatch(device);
1718
1719    res = disp->AllocateCommandBuffers(device, pAllocateInfo, pCommandBuffers);
1720    if (res == VK_SUCCESS) {
1721        for (uint32_t i = 0; i < pAllocateInfo->commandBufferCount; i++) {
1722            if (pCommandBuffers[i]) {
1723                loader_init_dispatch(pCommandBuffers[i], disp);
1724            }
1725        }
1726    }
1727
1728    return res;
1729}
1730
1731LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1732vkFreeCommandBuffers(VkDevice device, VkCommandPool commandPool,
1733                     uint32_t commandBufferCount,
1734                     const VkCommandBuffer *pCommandBuffers) {
1735    const VkLayerDispatchTable *disp;
1736
1737    disp = loader_get_dispatch(device);
1738
1739    disp->FreeCommandBuffers(device, commandPool, commandBufferCount,
1740                             pCommandBuffers);
1741}
1742
1743LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1744vkBeginCommandBuffer(VkCommandBuffer commandBuffer,
1745                     const VkCommandBufferBeginInfo *pBeginInfo) {
1746    const VkLayerDispatchTable *disp;
1747
1748    disp = loader_get_dispatch(commandBuffer);
1749
1750    return disp->BeginCommandBuffer(commandBuffer, pBeginInfo);
1751}
1752
1753LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1754vkEndCommandBuffer(VkCommandBuffer commandBuffer) {
1755    const VkLayerDispatchTable *disp;
1756
1757    disp = loader_get_dispatch(commandBuffer);
1758
1759    return disp->EndCommandBuffer(commandBuffer);
1760}
1761
1762LOADER_EXPORT VKAPI_ATTR VkResult VKAPI_CALL
1763vkResetCommandBuffer(VkCommandBuffer commandBuffer,
1764                     VkCommandBufferResetFlags flags) {
1765    const VkLayerDispatchTable *disp;
1766
1767    disp = loader_get_dispatch(commandBuffer);
1768
1769    return disp->ResetCommandBuffer(commandBuffer, flags);
1770}
1771
1772LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1773vkCmdBindPipeline(VkCommandBuffer commandBuffer,
1774                  VkPipelineBindPoint pipelineBindPoint, VkPipeline pipeline) {
1775    const VkLayerDispatchTable *disp;
1776
1777    disp = loader_get_dispatch(commandBuffer);
1778
1779    disp->CmdBindPipeline(commandBuffer, pipelineBindPoint, pipeline);
1780}
1781
1782LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1783vkCmdSetViewport(VkCommandBuffer commandBuffer, uint32_t firstViewport,
1784                 uint32_t viewportCount, const VkViewport *pViewports) {
1785    const VkLayerDispatchTable *disp;
1786
1787    disp = loader_get_dispatch(commandBuffer);
1788
1789    disp->CmdSetViewport(commandBuffer, firstViewport, viewportCount,
1790                         pViewports);
1791}
1792
1793LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1794vkCmdSetScissor(VkCommandBuffer commandBuffer, uint32_t firstScissor,
1795                uint32_t scissorCount, const VkRect2D *pScissors) {
1796    const VkLayerDispatchTable *disp;
1797
1798    disp = loader_get_dispatch(commandBuffer);
1799
1800    disp->CmdSetScissor(commandBuffer, firstScissor, scissorCount, pScissors);
1801}
1802
1803LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1804vkCmdSetLineWidth(VkCommandBuffer commandBuffer, float lineWidth) {
1805    const VkLayerDispatchTable *disp;
1806
1807    disp = loader_get_dispatch(commandBuffer);
1808
1809    disp->CmdSetLineWidth(commandBuffer, lineWidth);
1810}
1811
1812LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1813vkCmdSetDepthBias(VkCommandBuffer commandBuffer, float depthBiasConstantFactor,
1814                  float depthBiasClamp, float depthBiasSlopeFactor) {
1815    const VkLayerDispatchTable *disp;
1816
1817    disp = loader_get_dispatch(commandBuffer);
1818
1819    disp->CmdSetDepthBias(commandBuffer, depthBiasConstantFactor,
1820                          depthBiasClamp, depthBiasSlopeFactor);
1821}
1822
1823LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1824vkCmdSetBlendConstants(VkCommandBuffer commandBuffer,
1825                       const float blendConstants[4]) {
1826    const VkLayerDispatchTable *disp;
1827
1828    disp = loader_get_dispatch(commandBuffer);
1829
1830    disp->CmdSetBlendConstants(commandBuffer, blendConstants);
1831}
1832
1833LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1834vkCmdSetDepthBounds(VkCommandBuffer commandBuffer, float minDepthBounds,
1835                    float maxDepthBounds) {
1836    const VkLayerDispatchTable *disp;
1837
1838    disp = loader_get_dispatch(commandBuffer);
1839
1840    disp->CmdSetDepthBounds(commandBuffer, minDepthBounds, maxDepthBounds);
1841}
1842
1843LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1844vkCmdSetStencilCompareMask(VkCommandBuffer commandBuffer,
1845                           VkStencilFaceFlags faceMask, uint32_t compareMask) {
1846    const VkLayerDispatchTable *disp;
1847
1848    disp = loader_get_dispatch(commandBuffer);
1849
1850    disp->CmdSetStencilCompareMask(commandBuffer, faceMask, compareMask);
1851}
1852
1853LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1854vkCmdSetStencilWriteMask(VkCommandBuffer commandBuffer,
1855                         VkStencilFaceFlags faceMask, uint32_t writeMask) {
1856    const VkLayerDispatchTable *disp;
1857
1858    disp = loader_get_dispatch(commandBuffer);
1859
1860    disp->CmdSetStencilWriteMask(commandBuffer, faceMask, writeMask);
1861}
1862
1863LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1864vkCmdSetStencilReference(VkCommandBuffer commandBuffer,
1865                         VkStencilFaceFlags faceMask, uint32_t reference) {
1866    const VkLayerDispatchTable *disp;
1867
1868    disp = loader_get_dispatch(commandBuffer);
1869
1870    disp->CmdSetStencilReference(commandBuffer, faceMask, reference);
1871}
1872
1873LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL vkCmdBindDescriptorSets(
1874    VkCommandBuffer commandBuffer, VkPipelineBindPoint pipelineBindPoint,
1875    VkPipelineLayout layout, uint32_t firstSet, uint32_t descriptorSetCount,
1876    const VkDescriptorSet *pDescriptorSets, uint32_t dynamicOffsetCount,
1877    const uint32_t *pDynamicOffsets) {
1878    const VkLayerDispatchTable *disp;
1879
1880    disp = loader_get_dispatch(commandBuffer);
1881
1882    disp->CmdBindDescriptorSets(commandBuffer, pipelineBindPoint, layout,
1883                                firstSet, descriptorSetCount, pDescriptorSets,
1884                                dynamicOffsetCount, pDynamicOffsets);
1885}
1886
1887LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1888vkCmdBindIndexBuffer(VkCommandBuffer commandBuffer, VkBuffer buffer,
1889                     VkDeviceSize offset, VkIndexType indexType) {
1890    const VkLayerDispatchTable *disp;
1891
1892    disp = loader_get_dispatch(commandBuffer);
1893
1894    disp->CmdBindIndexBuffer(commandBuffer, buffer, offset, indexType);
1895}
1896
1897LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1898vkCmdBindVertexBuffers(VkCommandBuffer commandBuffer, uint32_t firstBinding,
1899                       uint32_t bindingCount, const VkBuffer *pBuffers,
1900                       const VkDeviceSize *pOffsets) {
1901    const VkLayerDispatchTable *disp;
1902
1903    disp = loader_get_dispatch(commandBuffer);
1904
1905    disp->CmdBindVertexBuffers(commandBuffer, firstBinding, bindingCount,
1906                               pBuffers, pOffsets);
1907}
1908
1909LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1910vkCmdDraw(VkCommandBuffer commandBuffer, uint32_t vertexCount,
1911          uint32_t instanceCount, uint32_t firstVertex,
1912          uint32_t firstInstance) {
1913    const VkLayerDispatchTable *disp;
1914
1915    disp = loader_get_dispatch(commandBuffer);
1916
1917    disp->CmdDraw(commandBuffer, vertexCount, instanceCount, firstVertex,
1918                  firstInstance);
1919}
1920
1921LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1922vkCmdDrawIndexed(VkCommandBuffer commandBuffer, uint32_t indexCount,
1923                 uint32_t instanceCount, uint32_t firstIndex,
1924                 int32_t vertexOffset, uint32_t firstInstance) {
1925    const VkLayerDispatchTable *disp;
1926
1927    disp = loader_get_dispatch(commandBuffer);
1928
1929    disp->CmdDrawIndexed(commandBuffer, indexCount, instanceCount, firstIndex,
1930                         vertexOffset, firstInstance);
1931}
1932
1933LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1934vkCmdDrawIndirect(VkCommandBuffer commandBuffer, VkBuffer buffer,
1935                  VkDeviceSize offset, uint32_t drawCount, uint32_t stride) {
1936    const VkLayerDispatchTable *disp;
1937
1938    disp = loader_get_dispatch(commandBuffer);
1939
1940    disp->CmdDrawIndirect(commandBuffer, buffer, offset, drawCount, stride);
1941}
1942
1943LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1944vkCmdDrawIndexedIndirect(VkCommandBuffer commandBuffer, VkBuffer buffer,
1945                         VkDeviceSize offset, uint32_t drawCount,
1946                         uint32_t stride) {
1947    const VkLayerDispatchTable *disp;
1948
1949    disp = loader_get_dispatch(commandBuffer);
1950
1951    disp->CmdDrawIndexedIndirect(commandBuffer, buffer, offset, drawCount,
1952                                 stride);
1953}
1954
1955LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1956vkCmdDispatch(VkCommandBuffer commandBuffer, uint32_t x, uint32_t y,
1957              uint32_t z) {
1958    const VkLayerDispatchTable *disp;
1959
1960    disp = loader_get_dispatch(commandBuffer);
1961
1962    disp->CmdDispatch(commandBuffer, x, y, z);
1963}
1964
1965LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1966vkCmdDispatchIndirect(VkCommandBuffer commandBuffer, VkBuffer buffer,
1967                      VkDeviceSize offset) {
1968    const VkLayerDispatchTable *disp;
1969
1970    disp = loader_get_dispatch(commandBuffer);
1971
1972    disp->CmdDispatchIndirect(commandBuffer, buffer, offset);
1973}
1974
1975LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1976vkCmdCopyBuffer(VkCommandBuffer commandBuffer, VkBuffer srcBuffer,
1977                VkBuffer dstBuffer, uint32_t regionCount,
1978                const VkBufferCopy *pRegions) {
1979    const VkLayerDispatchTable *disp;
1980
1981    disp = loader_get_dispatch(commandBuffer);
1982
1983    disp->CmdCopyBuffer(commandBuffer, srcBuffer, dstBuffer, regionCount,
1984                        pRegions);
1985}
1986
1987LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
1988vkCmdCopyImage(VkCommandBuffer commandBuffer, VkImage srcImage,
1989               VkImageLayout srcImageLayout, VkImage dstImage,
1990               VkImageLayout dstImageLayout, uint32_t regionCount,
1991               const VkImageCopy *pRegions) {
1992    const VkLayerDispatchTable *disp;
1993
1994    disp = loader_get_dispatch(commandBuffer);
1995
1996    disp->CmdCopyImage(commandBuffer, srcImage, srcImageLayout, dstImage,
1997                       dstImageLayout, regionCount, pRegions);
1998}
1999
2000LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2001vkCmdBlitImage(VkCommandBuffer commandBuffer, VkImage srcImage,
2002               VkImageLayout srcImageLayout, VkImage dstImage,
2003               VkImageLayout dstImageLayout, uint32_t regionCount,
2004               const VkImageBlit *pRegions, VkFilter filter) {
2005    const VkLayerDispatchTable *disp;
2006
2007    disp = loader_get_dispatch(commandBuffer);
2008
2009    disp->CmdBlitImage(commandBuffer, srcImage, srcImageLayout, dstImage,
2010                       dstImageLayout, regionCount, pRegions, filter);
2011}
2012
2013LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2014vkCmdCopyBufferToImage(VkCommandBuffer commandBuffer, VkBuffer srcBuffer,
2015                       VkImage dstImage, VkImageLayout dstImageLayout,
2016                       uint32_t regionCount,
2017                       const VkBufferImageCopy *pRegions) {
2018    const VkLayerDispatchTable *disp;
2019
2020    disp = loader_get_dispatch(commandBuffer);
2021
2022    disp->CmdCopyBufferToImage(commandBuffer, srcBuffer, dstImage,
2023                               dstImageLayout, regionCount, pRegions);
2024}
2025
2026LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2027vkCmdCopyImageToBuffer(VkCommandBuffer commandBuffer, VkImage srcImage,
2028                       VkImageLayout srcImageLayout, VkBuffer dstBuffer,
2029                       uint32_t regionCount,
2030                       const VkBufferImageCopy *pRegions) {
2031    const VkLayerDispatchTable *disp;
2032
2033    disp = loader_get_dispatch(commandBuffer);
2034
2035    disp->CmdCopyImageToBuffer(commandBuffer, srcImage, srcImageLayout,
2036                               dstBuffer, regionCount, pRegions);
2037}
2038
2039LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2040vkCmdUpdateBuffer(VkCommandBuffer commandBuffer, VkBuffer dstBuffer,
2041                  VkDeviceSize dstOffset, VkDeviceSize dataSize,
2042                  const void *pData) {
2043    const VkLayerDispatchTable *disp;
2044
2045    disp = loader_get_dispatch(commandBuffer);
2046
2047    disp->CmdUpdateBuffer(commandBuffer, dstBuffer, dstOffset, dataSize, pData);
2048}
2049
2050LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2051vkCmdFillBuffer(VkCommandBuffer commandBuffer, VkBuffer dstBuffer,
2052                VkDeviceSize dstOffset, VkDeviceSize size, uint32_t data) {
2053    const VkLayerDispatchTable *disp;
2054
2055    disp = loader_get_dispatch(commandBuffer);
2056
2057    disp->CmdFillBuffer(commandBuffer, dstBuffer, dstOffset, size, data);
2058}
2059
2060LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2061vkCmdClearColorImage(VkCommandBuffer commandBuffer, VkImage image,
2062                     VkImageLayout imageLayout, const VkClearColorValue *pColor,
2063                     uint32_t rangeCount,
2064                     const VkImageSubresourceRange *pRanges) {
2065    const VkLayerDispatchTable *disp;
2066
2067    disp = loader_get_dispatch(commandBuffer);
2068
2069    disp->CmdClearColorImage(commandBuffer, image, imageLayout, pColor,
2070                             rangeCount, pRanges);
2071}
2072
2073LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2074vkCmdClearDepthStencilImage(VkCommandBuffer commandBuffer, VkImage image,
2075                            VkImageLayout imageLayout,
2076                            const VkClearDepthStencilValue *pDepthStencil,
2077                            uint32_t rangeCount,
2078                            const VkImageSubresourceRange *pRanges) {
2079    const VkLayerDispatchTable *disp;
2080
2081    disp = loader_get_dispatch(commandBuffer);
2082
2083    disp->CmdClearDepthStencilImage(commandBuffer, image, imageLayout,
2084                                    pDepthStencil, rangeCount, pRanges);
2085}
2086
2087LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2088vkCmdClearAttachments(VkCommandBuffer commandBuffer, uint32_t attachmentCount,
2089                      const VkClearAttachment *pAttachments, uint32_t rectCount,
2090                      const VkClearRect *pRects) {
2091    const VkLayerDispatchTable *disp;
2092
2093    disp = loader_get_dispatch(commandBuffer);
2094
2095    disp->CmdClearAttachments(commandBuffer, attachmentCount, pAttachments,
2096                              rectCount, pRects);
2097}
2098
2099LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2100vkCmdResolveImage(VkCommandBuffer commandBuffer, VkImage srcImage,
2101                  VkImageLayout srcImageLayout, VkImage dstImage,
2102                  VkImageLayout dstImageLayout, uint32_t regionCount,
2103                  const VkImageResolve *pRegions) {
2104    const VkLayerDispatchTable *disp;
2105
2106    disp = loader_get_dispatch(commandBuffer);
2107
2108    disp->CmdResolveImage(commandBuffer, srcImage, srcImageLayout, dstImage,
2109                          dstImageLayout, regionCount, pRegions);
2110}
2111
2112LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2113vkCmdSetEvent(VkCommandBuffer commandBuffer, VkEvent event,
2114              VkPipelineStageFlags stageMask) {
2115    const VkLayerDispatchTable *disp;
2116
2117    disp = loader_get_dispatch(commandBuffer);
2118
2119    disp->CmdSetEvent(commandBuffer, event, stageMask);
2120}
2121
2122LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2123vkCmdResetEvent(VkCommandBuffer commandBuffer, VkEvent event,
2124                VkPipelineStageFlags stageMask) {
2125    const VkLayerDispatchTable *disp;
2126
2127    disp = loader_get_dispatch(commandBuffer);
2128
2129    disp->CmdResetEvent(commandBuffer, event, stageMask);
2130}
2131
2132LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2133vkCmdWaitEvents(VkCommandBuffer commandBuffer, uint32_t eventCount,
2134                const VkEvent *pEvents, VkPipelineStageFlags sourceStageMask,
2135                VkPipelineStageFlags dstStageMask, uint32_t memoryBarrierCount,
2136                const VkMemoryBarrier *pMemoryBarriers,
2137                uint32_t bufferMemoryBarrierCount,
2138                const VkBufferMemoryBarrier *pBufferMemoryBarriers,
2139                uint32_t imageMemoryBarrierCount,
2140                const VkImageMemoryBarrier *pImageMemoryBarriers) {
2141    const VkLayerDispatchTable *disp;
2142
2143    disp = loader_get_dispatch(commandBuffer);
2144
2145    disp->CmdWaitEvents(commandBuffer, eventCount, pEvents, sourceStageMask,
2146                        dstStageMask, memoryBarrierCount, pMemoryBarriers,
2147                        bufferMemoryBarrierCount, pBufferMemoryBarriers,
2148                        imageMemoryBarrierCount, pImageMemoryBarriers);
2149}
2150
2151LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL vkCmdPipelineBarrier(
2152    VkCommandBuffer commandBuffer, VkPipelineStageFlags srcStageMask,
2153    VkPipelineStageFlags dstStageMask, VkDependencyFlags dependencyFlags,
2154    uint32_t memoryBarrierCount, const VkMemoryBarrier *pMemoryBarriers,
2155    uint32_t bufferMemoryBarrierCount,
2156    const VkBufferMemoryBarrier *pBufferMemoryBarriers,
2157    uint32_t imageMemoryBarrierCount,
2158    const VkImageMemoryBarrier *pImageMemoryBarriers) {
2159    const VkLayerDispatchTable *disp;
2160
2161    disp = loader_get_dispatch(commandBuffer);
2162
2163    disp->CmdPipelineBarrier(
2164        commandBuffer, srcStageMask, dstStageMask, dependencyFlags,
2165        memoryBarrierCount, pMemoryBarriers, bufferMemoryBarrierCount,
2166        pBufferMemoryBarriers, imageMemoryBarrierCount, pImageMemoryBarriers);
2167}
2168
2169LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2170vkCmdBeginQuery(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
2171                uint32_t slot, VkFlags flags) {
2172    const VkLayerDispatchTable *disp;
2173
2174    disp = loader_get_dispatch(commandBuffer);
2175
2176    disp->CmdBeginQuery(commandBuffer, queryPool, slot, flags);
2177}
2178
2179LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2180vkCmdEndQuery(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
2181              uint32_t slot) {
2182    const VkLayerDispatchTable *disp;
2183
2184    disp = loader_get_dispatch(commandBuffer);
2185
2186    disp->CmdEndQuery(commandBuffer, queryPool, slot);
2187}
2188
2189LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2190vkCmdResetQueryPool(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
2191                    uint32_t firstQuery, uint32_t queryCount) {
2192    const VkLayerDispatchTable *disp;
2193
2194    disp = loader_get_dispatch(commandBuffer);
2195
2196    disp->CmdResetQueryPool(commandBuffer, queryPool, firstQuery, queryCount);
2197}
2198
2199LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2200vkCmdWriteTimestamp(VkCommandBuffer commandBuffer,
2201                    VkPipelineStageFlagBits pipelineStage,
2202                    VkQueryPool queryPool, uint32_t slot) {
2203    const VkLayerDispatchTable *disp;
2204
2205    disp = loader_get_dispatch(commandBuffer);
2206
2207    disp->CmdWriteTimestamp(commandBuffer, pipelineStage, queryPool, slot);
2208}
2209
2210LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2211vkCmdCopyQueryPoolResults(VkCommandBuffer commandBuffer, VkQueryPool queryPool,
2212                          uint32_t firstQuery, uint32_t queryCount,
2213                          VkBuffer dstBuffer, VkDeviceSize dstOffset,
2214                          VkDeviceSize stride, VkFlags flags) {
2215    const VkLayerDispatchTable *disp;
2216
2217    disp = loader_get_dispatch(commandBuffer);
2218
2219    disp->CmdCopyQueryPoolResults(commandBuffer, queryPool, firstQuery,
2220                                  queryCount, dstBuffer, dstOffset, stride,
2221                                  flags);
2222}
2223
2224LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2225vkCmdPushConstants(VkCommandBuffer commandBuffer, VkPipelineLayout layout,
2226                   VkShaderStageFlags stageFlags, uint32_t offset,
2227                   uint32_t size, const void *pValues) {
2228    const VkLayerDispatchTable *disp;
2229
2230    disp = loader_get_dispatch(commandBuffer);
2231
2232    disp->CmdPushConstants(commandBuffer, layout, stageFlags, offset, size,
2233                           pValues);
2234}
2235
2236LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2237vkCmdBeginRenderPass(VkCommandBuffer commandBuffer,
2238                     const VkRenderPassBeginInfo *pRenderPassBegin,
2239                     VkSubpassContents contents) {
2240    const VkLayerDispatchTable *disp;
2241
2242    disp = loader_get_dispatch(commandBuffer);
2243
2244    disp->CmdBeginRenderPass(commandBuffer, pRenderPassBegin, contents);
2245}
2246
2247LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2248vkCmdNextSubpass(VkCommandBuffer commandBuffer, VkSubpassContents contents) {
2249    const VkLayerDispatchTable *disp;
2250
2251    disp = loader_get_dispatch(commandBuffer);
2252
2253    disp->CmdNextSubpass(commandBuffer, contents);
2254}
2255
2256LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2257vkCmdEndRenderPass(VkCommandBuffer commandBuffer) {
2258    const VkLayerDispatchTable *disp;
2259
2260    disp = loader_get_dispatch(commandBuffer);
2261
2262    disp->CmdEndRenderPass(commandBuffer);
2263}
2264
2265LOADER_EXPORT VKAPI_ATTR void VKAPI_CALL
2266vkCmdExecuteCommands(VkCommandBuffer commandBuffer,
2267                     uint32_t commandBuffersCount,
2268                     const VkCommandBuffer *pCommandBuffers) {
2269    const VkLayerDispatchTable *disp;
2270
2271    disp = loader_get_dispatch(commandBuffer);
2272
2273    disp->CmdExecuteCommands(commandBuffer, commandBuffersCount,
2274                             pCommandBuffers);
2275}
2276