vulkaninfo.c revision ef72e2a7cf4fa5708fdbfbc1c972a24ad0dbf809
146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu/*
29cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter * Vulkan
346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu *
446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * Copyright (C) 2014 LunarG, Inc.
546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu *
646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * Permission is hereby granted, free of charge, to any person obtaining a
746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * copy of this software and associated documentation files (the "Software"),
846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * to deal in the Software without restriction, including without limitation
946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * the rights to use, copy, modify, merge, publish, distribute, sublicense,
1046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * and/or sell copies of the Software, and to permit persons to whom the
1146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * Software is furnished to do so, subject to the following conditions:
1246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu *
1346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * The above copyright notice and this permission notice shall be included
1446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * in all copies or substantial portions of the Software.
1546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu *
1646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
1746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
1846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
1946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
2046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
2146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
2246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu * DEALINGS IN THE SOFTWARE.
2346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu */
24d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu#include <stdlib.h>
25d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu#include <stdio.h>
26d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu#include <stdbool.h>
27d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu#include <string.h>
2846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu#include <assert.h>
29d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
30ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott#ifdef _WIN32
31ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott#include <Windows.h>
3218fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo#include <fcntl.h>
3318fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo#include <io.h>
34ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott#endif
35ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott
36e36b208f32a0959cd7590b1717aac3ef19631b1aIan Elliott#include "vk_wsi_swapchain.h"
37e36b208f32a0959cd7590b1717aac3ef19631b1aIan Elliott#include "vk_wsi_device_swapchain.h"
38e36b208f32a0959cd7590b1717aac3ef19631b1aIan Elliott
399cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter#include <vulkan.h>
4046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
4146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu#define ERR(err) printf("%s:%d: failed with %s\n", \
429cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    __FILE__, __LINE__, vk_result_string(err));
4346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
4418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo#ifdef _WIN32
4518fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
467c83aa210365e148877f0f3698292a1b509018ffIan Elliott#define snprintf _snprintf
477c83aa210365e148877f0f3698292a1b509018ffIan Elliott
4818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedobool consoleCreated = false;
4918fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
5018fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo#define WAIT_FOR_CONSOLE_DESTROY \
5118fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    do { \
5218fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        if (consoleCreated) \
5318fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo            Sleep(INFINITE); \
5418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    } while (0)
5518fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo#else
5618fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    #define WAIT_FOR_CONSOLE_DESTROY
5718fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo#endif
5818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
5918fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
6018fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo#define ERR_EXIT(err) \
6118fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    do { \
6218fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        ERR(err); \
6318fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        fflush(stdout); \
6418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        WAIT_FOR_CONSOLE_DESTROY; \
6518fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        exit(-1); \
6618fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo   } while (0)
6746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
6822a30866de6210d780995dfaaae39f1a73115aa0Tony Barbour#if defined(NDEBUG) && defined(__GNUC__)
6922a30866de6210d780995dfaaae39f1a73115aa0Tony Barbour#define U_ASSERT_ONLY __attribute__((unused))
7022a30866de6210d780995dfaaae39f1a73115aa0Tony Barbour#else
7122a30866de6210d780995dfaaae39f1a73115aa0Tony Barbour#define U_ASSERT_ONLY
7222a30866de6210d780995dfaaae39f1a73115aa0Tony Barbour#endif
7322a30866de6210d780995dfaaae39f1a73115aa0Tony Barbour
7446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu#define ARRAY_SIZE(a) (sizeof(a) / sizeof(a[0]))
7546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
7646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu#define MAX_GPUS 8
7746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
7846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu#define MAX_QUEUE_TYPES 5
794e19ed0ed322e45993bac7917a1a253dbaaf88f9Ian Elliott#define APP_SHORT_NAME "vulkaninfo"
8046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
8146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wustruct app_gpu;
8246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
8346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wustruct app_dev {
8446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    struct app_gpu *gpu; /* point back to the GPU */
8546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
86382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter    VkDevice obj;
8746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
8846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
89ab36aa63b05aaa4432fc0abc9b978601c74c9532Courtney Goeltzenleuchter    VkFormatProperties format_props[VK_FORMAT_NUM];
9046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu};
9146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
9218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchterstruct layer_extension_list {
9318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkLayerProperties layer_properties;
9418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t extension_count;
9518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkExtensionProperties *extension_properties;
9618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter};
9718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
983c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchterstruct app_instance {
993c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    VkInstance  instance;
10018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t global_layer_count;
10118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    struct layer_extension_list *global_layers;
1023c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    uint32_t global_extension_count;
1033c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    VkExtensionProperties *global_extensions;
1043c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter};
1053c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
10646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wustruct app_gpu {
107e2d07a5a3810d83d0ea7ecb396d61477893b74a4Mark Lobodzinski    uint32_t id;
1088205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    VkPhysicalDevice obj;
10946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
1108205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    VkPhysicalDeviceProperties props;
11146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
112e2d07a5a3810d83d0ea7ecb396d61477893b74a4Mark Lobodzinski    uint32_t queue_count;
113ef72e2a7cf4fa5708fdbfbc1c972a24ad0dbf809Cody Northrop    VkQueueFamilyProperties *queue_props;
114ddcb6192458d696a106f48eeb12fd0390a3ca63fCourtney Goeltzenleuchter    VkDeviceQueueCreateInfo *queue_reqs;
11546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
1168205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    VkPhysicalDeviceMemoryProperties memory_props;
117a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    VkPhysicalDeviceFeatures features;
118a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    VkPhysicalDeviceLimits limits;
11946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
12018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t device_layer_count;
12118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    struct layer_extension_list *device_layers;
12218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
1233c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    uint32_t device_extension_count;
1243c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    VkExtensionProperties *device_extensions;
12546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
12646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    struct app_dev dev;
12746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu};
12846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
129382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchterstatic const char *vk_result_string(VkResult err)
13046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu{
13146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    switch (err) {
13246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu#define STR(r) case r: return #r
1339cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_SUCCESS);
1349cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_UNSUPPORTED);
1359cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_NOT_READY);
1369cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_TIMEOUT);
1379cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_EVENT_SET);
1389cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_EVENT_RESET);
1399cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_UNKNOWN);
1409cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_UNAVAILABLE);
1419cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INITIALIZATION_FAILED);
1428205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    STR(VK_ERROR_OUT_OF_HOST_MEMORY);
1438205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    STR(VK_ERROR_OUT_OF_DEVICE_MEMORY);
1449cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_DEVICE_ALREADY_CREATED);
1459cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_DEVICE_LOST);
1469cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_POINTER);
1479cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_VALUE);
1489cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_HANDLE);
1499cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_ORDINAL);
1509cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_MEMORY_SIZE);
1519cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_EXTENSION);
1529cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_FLAGS);
1539cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_ALIGNMENT);
1549cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_FORMAT);
1559cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_IMAGE);
1569cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_DESCRIPTOR_SET_DATA);
1579cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INVALID_QUEUE_TYPE);
1589cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_UNSUPPORTED_SHADER_IL_VERSION);
1599cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_BAD_SHADER_CODE);
1609cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_BAD_PIPELINE_DATA);
1619cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_NOT_MAPPABLE);
1629cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_MEMORY_MAP_FAILED);
1639cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_MEMORY_UNMAP_FAILED);
1649cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INCOMPATIBLE_DEVICE);
1659cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INCOMPATIBLE_DRIVER);
1669cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INCOMPLETE_COMMAND_BUFFER);
1679cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_BUILDING_COMMAND_BUFFER);
1689cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_MEMORY_NOT_BOUND);
1699cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    STR(VK_ERROR_INCOMPATIBLE_QUEUE);
17046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu#undef STR
17146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    default: return "UNKNOWN_RESULT";
17246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    }
17346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu}
174d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
1758205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbourstatic const char *vk_physical_device_type_string(VkPhysicalDeviceType type)
176d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
177190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    switch (type) {
1788205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour#define STR(r) case VK_PHYSICAL_DEVICE_TYPE_ ##r: return #r
179190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    STR(OTHER);
1808205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    STR(INTEGRATED_GPU);
1818205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    STR(DISCRETE_GPU);
1828205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    STR(VIRTUAL_GPU);
183d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu#undef STR
1848205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    default: return "UNKNOWN_DEVICE";
185190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    }
186d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
187d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
188382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchterstatic const char *vk_format_string(VkFormat fmt)
189d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
1902b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    switch (fmt) {
1918205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour#define STR(r) case VK_FORMAT_ ##r: return #r
192190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    STR(UNDEFINED);
1932b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R4G4_UNORM);
1942b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R4G4_USCALED);
1952b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R4G4B4A4_UNORM);
1962b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R4G4B4A4_USCALED);
1972b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R5G6B5_UNORM);
1982b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R5G6B5_USCALED);
1992b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R5G5B5A1_UNORM);
2002b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R5G5B5A1_USCALED);
2012b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8_UNORM);
2022b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8_SNORM);
2032b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8_USCALED);
2042b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8_SSCALED);
2052b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8_UINT);
2062b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8_SINT);
2072b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8_SRGB);
2082b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8_UNORM);
2092b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8_SNORM);
2102b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8_USCALED);
2112b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8_SSCALED);
2122b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8_UINT);
2132b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8_SINT);
2142b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8_SRGB);
2152b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8_UNORM);
2162b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8_SNORM);
2172b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8_USCALED);
2182b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8_SSCALED);
2192b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8_UINT);
2202b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8_SINT);
2212b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8_SRGB);
2222b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8A8_UNORM);
2232b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8A8_SNORM);
2242b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8A8_USCALED);
2252b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8A8_SSCALED);
2262b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8A8_UINT);
2272b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8A8_SINT);
2282b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R8G8B8A8_SRGB);
2292b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R10G10B10A2_UNORM);
2302b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R10G10B10A2_SNORM);
2312b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R10G10B10A2_USCALED);
2322b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R10G10B10A2_SSCALED);
2332b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R10G10B10A2_UINT);
2342b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R10G10B10A2_SINT);
2352b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16_UNORM);
2362b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16_SNORM);
2372b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16_USCALED);
2382b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16_SSCALED);
2392b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16_UINT);
2402b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16_SINT);
2412b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16_SFLOAT);
2422b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16_UNORM);
2432b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16_SNORM);
2442b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16_USCALED);
2452b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16_SSCALED);
2462b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16_UINT);
2472b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16_SINT);
2482b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16_SFLOAT);
2492b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16_UNORM);
2502b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16_SNORM);
2512b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16_USCALED);
2522b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16_SSCALED);
2532b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16_UINT);
2542b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16_SINT);
2552b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16_SFLOAT);
2562b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16A16_UNORM);
2572b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16A16_SNORM);
2582b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16A16_USCALED);
2592b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16A16_SSCALED);
2602b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16A16_UINT);
2612b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16A16_SINT);
2622b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R16G16B16A16_SFLOAT);
2632b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32_UINT);
2642b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32_SINT);
2652b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32_SFLOAT);
2662b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32_UINT);
2672b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32_SINT);
2682b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32_SFLOAT);
2692b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32B32_UINT);
2702b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32B32_SINT);
2712b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32B32_SFLOAT);
2722b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32B32A32_UINT);
2732b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32B32A32_SINT);
2742b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R32G32B32A32_SFLOAT);
2752b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R64_SFLOAT);
2762b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R64G64_SFLOAT);
2772b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R64G64B64_SFLOAT);
2782b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R64G64B64A64_SFLOAT);
2792b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R11G11B10_UFLOAT);
2802b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(R9G9B9E5_UFLOAT);
2812b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(D16_UNORM);
2822b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(D24_UNORM);
2832b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(D32_SFLOAT);
2842b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(S8_UINT);
2852b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(D16_UNORM_S8_UINT);
2862b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(D24_UNORM_S8_UINT);
2872b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(D32_SFLOAT_S8_UINT);
288fe8a2e1259447466b5821fc9e067ebd735241f62Courtney Goeltzenleuchter    STR(BC1_RGB_UNORM);
289fe8a2e1259447466b5821fc9e067ebd735241f62Courtney Goeltzenleuchter    STR(BC1_RGB_SRGB);
2902b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC2_UNORM);
2912b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC2_SRGB);
2922b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC3_UNORM);
2932b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC3_SRGB);
2942b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC4_UNORM);
2952b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC4_SNORM);
2962b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC5_UNORM);
2972b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC5_SNORM);
2982b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC6H_UFLOAT);
2992b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC6H_SFLOAT);
3002b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC7_UNORM);
3012b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(BC7_SRGB);
3022b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ETC2_R8G8B8_UNORM);
3032b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ETC2_R8G8B8A1_UNORM);
3042b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ETC2_R8G8B8A8_UNORM);
3052b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(EAC_R11_UNORM);
3062b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(EAC_R11_SNORM);
3072b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(EAC_R11G11_UNORM);
3082b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(EAC_R11G11_SNORM);
3092b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_4x4_UNORM);
3102b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_4x4_SRGB);
311fe8a2e1259447466b5821fc9e067ebd735241f62Courtney Goeltzenleuchter    STR(ASTC_5x4_UNORM);
312fe8a2e1259447466b5821fc9e067ebd735241f62Courtney Goeltzenleuchter    STR(ASTC_5x4_SRGB);
3132b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_5x5_UNORM);
3142b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_5x5_SRGB);
3152b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_6x5_UNORM);
3162b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_6x5_SRGB);
3172b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_6x6_UNORM);
3182b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_6x6_SRGB);
3192b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_8x5_UNORM);
3202b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_8x5_SRGB);
3212b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_8x6_UNORM);
3222b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_8x6_SRGB);
3232b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_8x8_UNORM);
3242b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_8x8_SRGB);
3252b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x5_UNORM);
3262b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x5_SRGB);
3272b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x6_UNORM);
3282b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x6_SRGB);
3292b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x8_UNORM);
3302b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x8_SRGB);
3312b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x10_UNORM);
3322b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_10x10_SRGB);
3332b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_12x10_UNORM);
3342b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_12x10_SRGB);
3352b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_12x12_UNORM);
3362b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(ASTC_12x12_SRGB);
3372b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B5G6R5_UNORM);
3382b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B5G6R5_USCALED);
3392b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8_UNORM);
3402b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8_SNORM);
3412b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8_USCALED);
3422b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8_SSCALED);
3432b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8_UINT);
3442b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8_SINT);
3452b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8_SRGB);
3462b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8A8_UNORM);
3472b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8A8_SNORM);
3482b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8A8_USCALED);
3492b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8A8_SSCALED);
3502b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8A8_UINT);
3512b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8A8_SINT);
3522b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B8G8R8A8_SRGB);
3532b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B10G10R10A2_UNORM);
3542b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B10G10R10A2_SNORM);
3552b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B10G10R10A2_USCALED);
3562b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B10G10R10A2_SSCALED);
3572b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B10G10R10A2_UINT);
3582b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    STR(B10G10R10A2_SINT);
359d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu#undef STR
3602b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes    default: return "UNKNOWN_FORMAT";
361190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    }
362d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
363d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
36446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wustatic void app_dev_init_formats(struct app_dev *dev)
36546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu{
366382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter    VkFormat f;
3672b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes
368ab36aa63b05aaa4432fc0abc9b978601c74c9532Courtney Goeltzenleuchter    for (f = 0; f < VK_FORMAT_NUM; f++) {
369382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter        const VkFormat fmt = f;
370382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter        VkResult err;
3712b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes
3724da96aafe97eada8c0ab939dd8a8e94760b35649Courtney Goeltzenleuchter        err = vkGetPhysicalDeviceFormatProperties(dev->gpu->obj, fmt, &dev->format_props[f]);
3732b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes        if (err) {
3742b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes            memset(&dev->format_props[f], 0,
3752b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes                   sizeof(dev->format_props[f]));
3762b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes        }
37746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    }
37846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu}
37946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
38018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchterstatic void extract_version(uint32_t version, uint32_t *major, uint32_t *minor, uint32_t *patch)
38118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter{
38218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    *major = version >> 22;
38318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    *minor = (version >> 12) & 0x3ff;
38418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    *patch = version & 0xfff;
38518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter}
38618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
38718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchterstatic void app_get_physical_device_layer_extensions(
38818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        struct app_gpu *gpu,
38918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        char *layer_name,
39018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        uint32_t *extension_count,
39118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        VkExtensionProperties **extension_properties)
39218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter{
39318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkResult err;
39418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t ext_count = 0;
39518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkExtensionProperties *ext_ptr = NULL;
39618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
39718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    /* repeat get until VK_INCOMPLETE goes away */
39818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    do {
39918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetPhysicalDeviceExtensionProperties(gpu->obj, layer_name, &ext_count, NULL);
40018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(!err);
40118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
40218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (ext_ptr) {
40318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            free(ext_ptr);
40418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
40518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        ext_ptr = malloc(ext_count * sizeof(VkExtensionProperties));
40618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetPhysicalDeviceExtensionProperties(gpu->obj, layer_name, &ext_count, ext_ptr);
40718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    } while (err == VK_INCOMPLETE);
40818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    assert(!err);
40918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
41018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    *extension_count = ext_count;
41118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    *extension_properties = ext_ptr;
41218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter}
41318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
41446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wustatic void app_dev_init(struct app_dev *dev, struct app_gpu *gpu)
41546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu{
416ddcb6192458d696a106f48eeb12fd0390a3ca63fCourtney Goeltzenleuchter    VkDeviceCreateInfo info = {
4179cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter        .sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO,
41846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        .pNext = NULL,
41946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        .queueRecordCount = 0,
42046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        .pRequestedQueues = NULL,
42118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        .layerCount = 0,
42218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        .ppEnabledLayerNames = NULL,
42346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        .extensionCount = 0,
42418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        .ppEnabledExtensionNames = NULL,
42580d3b716eb7e4c2d4acab18e620298735672b268Jon Ashburn        .flags = 0,
42646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    };
4273c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    VkResult U_ASSERT_ONLY err;
4283c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    // Extensions to enable
42918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    static const char *known_extensions[] = {
430e36b208f32a0959cd7590b1717aac3ef19631b1aIan Elliott        VK_WSI_DEVICE_SWAPCHAIN_EXTENSION_NAME,
4313c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    };
432426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour
43318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t count = 0;
43418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
43518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    /* Scan layers */
43618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkLayerProperties *device_layer_properties = NULL;
43718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    struct layer_extension_list *device_layers = NULL;
43818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
43918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    do {
44018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetPhysicalDeviceLayerProperties(gpu->obj, &count, NULL);
44118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(!err);
44218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
44318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (device_layer_properties) {
44418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            free(device_layer_properties);
44518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
44618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        device_layer_properties = malloc(sizeof(VkLayerProperties) * count);
44718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(device_layer_properties);
44818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
44918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (device_layers) {
45018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            free(device_layers);
45118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
45218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        device_layers = malloc(sizeof(struct layer_extension_list) * count);
45318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(device_layers);
45418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
45518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetPhysicalDeviceLayerProperties(gpu->obj, &count, device_layer_properties);
45618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    } while (err == VK_INCOMPLETE);
4573c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    assert(!err);
4583c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
45918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    gpu->device_layer_count = count;
46018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    gpu->device_layers = device_layers;
46118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
46218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    for (uint32_t i = 0; i < gpu->device_layer_count; i++) {
46318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        VkLayerProperties *src_info = &device_layer_properties[i];
46418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        struct layer_extension_list *dst_info = &gpu->device_layers[i];
46518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        memcpy(&dst_info->layer_properties, src_info, sizeof(VkLayerProperties));
46618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
46718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        /* Save away layer extension info for report */
46818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        app_get_physical_device_layer_extensions(
46918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                    gpu,
47018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                    src_info->layerName,
47118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                    &dst_info->extension_count,
47218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                    &dst_info->extension_properties);
4733c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    }
47418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    free(device_layer_properties);
47518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
47618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    app_get_physical_device_layer_extensions(
47718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                gpu,
47818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                NULL,
47918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                &gpu->device_extension_count,
48018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                &gpu->device_extensions);
4813c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
4829e42b8882f26e897f0022f5ce800a04f4d2ad1cfCourtney Goeltzenleuchter    fflush(stdout);
4839e42b8882f26e897f0022f5ce800a04f4d2ad1cfCourtney Goeltzenleuchter
48418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t enabled_extension_count = 0;
48567a07414039ea03404711b0d9204ba35930d1d21Courtney Goeltzenleuchter    uint32_t known_extension_count = ARRAY_SIZE(known_extensions);
48618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
48767a07414039ea03404711b0d9204ba35930d1d21Courtney Goeltzenleuchter    for (uint32_t i = 0; i < known_extension_count; i++) {
4881f41f54bc20d57faed702aec3074eacdfc34680dCourtney Goeltzenleuchter        VkBool32 extension_found = 0;
48918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        for (uint32_t j = 0; j < gpu->device_extension_count; j++) {
49018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            VkExtensionProperties *ext_prop = &gpu->device_extensions[j];
49118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            if (!strcmp(known_extensions[i], ext_prop->extName)) {
49218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
49318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                extension_found = 1;
49418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                enabled_extension_count++;
4953c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter            }
4963c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        }
49718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (!extension_found) {
49818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            printf("Cannot find extension: %s\n", known_extensions[i]);
49918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            ERR_EXIT(VK_ERROR_INVALID_EXTENSION);
50018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
5013c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    }
50246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
50346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    /* request all queues */
50446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    info.queueRecordCount = gpu->queue_count;
50546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    info.pRequestedQueues = gpu->queue_reqs;
50646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
50718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    info.layerCount = 0;
50818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    info.ppEnabledLayerNames = NULL;
50918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    info.extensionCount = enabled_extension_count;
51018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    info.ppEnabledExtensionNames = (const char*const*) known_extensions;
5113c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    dev->gpu = gpu;
5123c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    err = vkCreateDevice(gpu->obj, &info, &dev->obj);
5133c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    if (err)
5143c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        ERR_EXIT(err);
51546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
51646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu}
51746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
51846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wustatic void app_dev_destroy(struct app_dev *dev)
51946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu{
5209cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    vkDestroyDevice(dev->obj);
52146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu}
52246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
52318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchterstatic void app_get_global_layer_extensions(
52418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        char *layer_name,
52518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        uint32_t *extension_count,
52618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        VkExtensionProperties **extension_properties)
52718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter{
52818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkResult err;
52918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t ext_count = 0;
53018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkExtensionProperties *ext_ptr = NULL;
53118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
53218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    /* repeat get until VK_INCOMPLETE goes away */
53318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    do {
53418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetGlobalExtensionProperties(layer_name, &ext_count, NULL);
53518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(!err);
53618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
53718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (ext_ptr) {
53818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            free(ext_ptr);
53918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
54018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        ext_ptr = malloc(ext_count * sizeof(VkExtensionProperties));
54118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetGlobalExtensionProperties(layer_name, &ext_count, ext_ptr);
54218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    } while (err == VK_INCOMPLETE);
54318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    assert(!err);
54418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
54518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    *extension_count = ext_count;
54618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    *extension_properties = ext_ptr;
54718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter}
54818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
5493c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchterstatic void app_create_instance(struct app_instance *inst)
55046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu{
5513c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    const VkApplicationInfo app_info = {
5523c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .sType = VK_STRUCTURE_TYPE_APPLICATION_INFO,
5533c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .pNext = NULL,
5543c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .pAppName = APP_SHORT_NAME,
5553c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .appVersion = 1,
5563c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .pEngineName = APP_SHORT_NAME,
5573c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .engineVersion = 1,
5583c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .apiVersion = VK_API_VERSION,
5593c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    };
5603c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    VkInstanceCreateInfo inst_info = {
5613c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO,
5623c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .pNext = NULL,
5633c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .pAppInfo = &app_info,
5643c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .pAllocCb = NULL,
56518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        .layerCount = 0,
56618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        .ppEnabledLayerNames = NULL,
5673c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        .extensionCount = 0,
56818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        .ppEnabledExtensionNames = NULL,
5693c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    };
57022a30866de6210d780995dfaaae39f1a73115aa0Tony Barbour    VkResult U_ASSERT_ONLY err;
5713c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    // Global Extensions to enable
572aae1a570a95ca8074d48698372694bb1ef2b5530Ian Elliott    static char *known_extensions[] = {
573e36b208f32a0959cd7590b1717aac3ef19631b1aIan Elliott        "VK_WSI_swapchain",
57446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    };
575426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour
5763c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    uint32_t global_extension_count = 0;
57718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    uint32_t count = 0;
57818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
57918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    /* Scan layers */
58018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    VkLayerProperties *global_layer_properties = NULL;
58118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    struct layer_extension_list *global_layers = NULL;
58218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
58318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    do {
58418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetGlobalLayerProperties(&count, NULL);
58518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(!err);
58618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
58718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (global_layer_properties) {
58818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            free(global_layer_properties);
58918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
59018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        global_layer_properties = malloc(sizeof(VkLayerProperties) * count);
59118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(global_layer_properties);
59218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
59318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (global_layers) {
59418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            free(global_layers);
59518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
59618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        global_layers = malloc(sizeof(struct layer_extension_list) * count);
59718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        assert(global_layers);
5983c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
59918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        err = vkGetGlobalLayerProperties(&count, global_layer_properties);
60018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    } while (err == VK_INCOMPLETE);
6013536b44d5d907e6ce3d97c40366f12a988c8036dTobin Ehlis    assert(!err);
6023536b44d5d907e6ce3d97c40366f12a988c8036dTobin Ehlis
60318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    inst->global_layer_count = count;
60418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    inst->global_layers = global_layers;
60518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
60618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    for (uint32_t i = 0; i < inst->global_layer_count; i++) {
60718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        VkLayerProperties *src_info = &global_layer_properties[i];
60818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        struct layer_extension_list *dst_info = &inst->global_layers[i];
60918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        memcpy(&dst_info->layer_properties, src_info, sizeof(VkLayerProperties));
61018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
61118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        /* Save away layer extension info for report */
61218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        app_get_global_layer_extensions(
61318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                    src_info->layerName,
61418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                    &dst_info->extension_count,
61518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                    &dst_info->extension_properties);
6163c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    }
61718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    free(global_layer_properties);
61818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
61918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    /* Collect global extensions */
62018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    inst->global_extension_count = 0;
62118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    app_get_global_layer_extensions(
62218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                NULL,
62318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                &inst->global_extension_count,
62418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                &inst->global_extensions);
6253c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
6263c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    for (uint32_t i = 0; i < ARRAY_SIZE(known_extensions); i++) {
6271f41f54bc20d57faed702aec3074eacdfc34680dCourtney Goeltzenleuchter        VkBool32 extension_found = 0;
62818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        for (uint32_t j = 0; j < inst->global_extension_count; j++) {
62918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            VkExtensionProperties *extension_prop = &inst->global_extensions[j];
63018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            if (!strcmp(known_extensions[i], extension_prop->extName)) {
63118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
63218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                extension_found = 1;
6333c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter                global_extension_count++;
6343c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter            }
6353536b44d5d907e6ce3d97c40366f12a988c8036dTobin Ehlis        }
63618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        if (!extension_found) {
63718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            printf("Cannot find extension: %s\n", known_extensions[i]);
63818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            ERR_EXIT(VK_ERROR_INVALID_EXTENSION);
63918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        }
64046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    }
64146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
6423c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    inst_info.extensionCount = global_extension_count;
64318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    inst_info.ppEnabledExtensionNames = (const char * const *) known_extensions;
64446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
6453c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    err = vkCreateInstance(&inst_info, &inst->instance);
6463c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    if (err == VK_ERROR_INCOMPATIBLE_DRIVER) {
6473c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        printf("Cannot create Vulkan instance.\n");
6483c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        ERR_EXIT(err);
6493c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    } else if (err) {
6503c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter        ERR_EXIT(err);
65146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    }
6523c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter}
6533c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
6543c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchterstatic void app_destroy_instance(struct app_instance *inst)
6553c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter{
6563c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    free(inst->global_extensions);
6573c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    vkDestroyInstance(inst->instance);
65846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu}
65946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
6603c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
6618205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbourstatic void app_gpu_init(struct app_gpu *gpu, uint32_t id, VkPhysicalDevice obj)
66246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu{
663382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter    VkResult err;
664aae1a570a95ca8074d48698372694bb1ef2b5530Ian Elliott    uint32_t i;
66546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
66646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    memset(gpu, 0, sizeof(*gpu));
66746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
66846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    gpu->id = id;
66946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    gpu->obj = obj;
670426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour
671426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour    err = vkGetPhysicalDeviceProperties(gpu->obj, &gpu->props);
672426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour    if (err)
67346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        ERR_EXIT(err);
67446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
67546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    /* get queue count */
676ef72e2a7cf4fa5708fdbfbc1c972a24ad0dbf809Cody Northrop    err = vkGetPhysicalDeviceQueueFamilyProperties(gpu->obj, &gpu->queue_count, NULL);
677426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour    if (err)
67846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        ERR_EXIT(err);
67946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
68046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    gpu->queue_props =
68146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu            malloc(sizeof(gpu->queue_props[0]) * gpu->queue_count);
682426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour
68346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    if (!gpu->queue_props)
6848205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour        ERR_EXIT(VK_ERROR_OUT_OF_HOST_MEMORY);
685ef72e2a7cf4fa5708fdbfbc1c972a24ad0dbf809Cody Northrop    err = vkGetPhysicalDeviceQueueFamilyProperties(gpu->obj, &gpu->queue_count, gpu->queue_props);
686426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour    if (err)
68746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        ERR_EXIT(err);
68846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
68946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    /* set up queue requests */
69046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    gpu->queue_reqs = malloc(sizeof(*gpu->queue_reqs) * gpu->queue_count);
69146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    if (!gpu->queue_reqs)
6928205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour        ERR_EXIT(VK_ERROR_OUT_OF_HOST_MEMORY);
69346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    for (i = 0; i < gpu->queue_count; i++) {
694fa6d36ea26354e4d68e81b05d1199a83c9fa3d6aChris Forbes        gpu->queue_reqs[i].queueFamilyIndex = i;
69546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        gpu->queue_reqs[i].queueCount = gpu->queue_props[i].queueCount;
69646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    }
69746c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
698426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour    err = vkGetPhysicalDeviceMemoryProperties(gpu->obj, &gpu->memory_props);
699426b90566abae5716741aade41184dc4dafe4aa4Tony Barbour    if (err)
70046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu        ERR_EXIT(err);
70146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
702a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    err = vkGetPhysicalDeviceFeatures(gpu->obj, &gpu->features);
703a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    if (err)
704a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes        ERR_EXIT(err);
705a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes
706a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    err = vkGetPhysicalDeviceLimits(gpu->obj, &gpu->limits);
707a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    if (err)
708a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes        ERR_EXIT(err);
709a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes
71046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    app_dev_init(&gpu->dev, gpu);
71146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    app_dev_init_formats(&gpu->dev);
71246c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu}
71346c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
71446c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wustatic void app_gpu_destroy(struct app_gpu *gpu)
71546c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu{
71646c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    app_dev_destroy(&gpu->dev);
7173c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    free(gpu->device_extensions);
71846c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    free(gpu->queue_reqs);
71946c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu    free(gpu->queue_props);
72046c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu}
72146c29ddef4360cac80d9dd533486aa1ab34776e1Chia-I Wu
722382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchterstatic void app_dev_dump_format_props(const struct app_dev *dev, VkFormat fmt)
723d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
724382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter    const VkFormatProperties *props = &dev->format_props[fmt];
725190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    struct {
726190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        const char *name;
727382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter        VkFlags flags;
728190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    } tilings[2];
729e2d07a5a3810d83d0ea7ecb396d61477893b74a4Mark Lobodzinski    uint32_t i;
730190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
731190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    if (!props->linearTilingFeatures && !props->optimalTilingFeatures)
732190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        return;
733190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
734190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    tilings[0].name = "linear";
735190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    tilings[0].flags = props->linearTilingFeatures;
736190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    tilings[1].name = "optimal";
737190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    tilings[1].flags = props->optimalTilingFeatures;
738190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
7399cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter    printf("FORMAT_%s\n", vk_format_string(fmt));
740190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    for (i = 0; i < ARRAY_SIZE(tilings); i++) {
741190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        if (!tilings[i].flags)
742190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu            continue;
743190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
744190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        printf("\t%s tiling image =%s%s%s\n", tilings[i].name,
7458205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT)      ? " sampled" : "",
7468205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_STORAGE_IMAGE_BIT)   ? " storage" : "",
7478205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_STORAGE_IMAGE_ATOMIC_BIT) ? " atomic" : "");
748ad870818fc61ad8dccc8af2c4992f15efa9c4c7fCourtney Goeltzenleuchter        printf("\t%s tiling texel =%s%s%s\n", tilings[i].name,
7498205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_UNIFORM_TEXEL_BUFFER_BIT)      ? " TBO" : "",
7508205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_BIT)   ? " IBO" : "",
7518205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_STORAGE_TEXEL_BUFFER_ATOMIC_BIT) ? " atomic" : "");
752ad870818fc61ad8dccc8af2c4992f15efa9c4c7fCourtney Goeltzenleuchter        printf("\t%s tiling attachment =%s%s%s\n", tilings[i].name,
7538205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BIT) ? " color" : "",
7548205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_COLOR_ATTACHMENT_BLEND_BIT) ? " blend" : "",
7558205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (tilings[i].flags & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT)       ? " depth/stencil" : "");
756ad870818fc61ad8dccc8af2c4992f15efa9c4c7fCourtney Goeltzenleuchter        printf("\t%s tiling vertex = %u\n", tilings[i].name,
7578205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (bool) (tilings[i].flags & VK_FORMAT_FEATURE_VERTEX_BUFFER_BIT));
758190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        printf("\t%s tiling conversion = %u\n", tilings[i].name,
7598205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour                (bool) (tilings[i].flags & VK_FORMAT_FEATURE_CONVERSION_BIT));
760190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    }
761d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
762d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
763d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
764d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wustatic void
765d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wuapp_dev_dump(const struct app_dev *dev)
766d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
767382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter    VkFormat fmt;
768190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
769ab36aa63b05aaa4432fc0abc9b978601c74c9532Courtney Goeltzenleuchter    for (fmt = 0; fmt < VK_FORMAT_NUM; fmt++) {
7702b7e88a1fdefc49d78e80765745e87e00034c2a0Jeremy Hayes        app_dev_dump_format_props(dev, fmt);
771190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    }
772d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
773d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
774009d8ca0c07c81adff475c48273207e170b4b5fbMike Stroyan#ifdef _WIN32
775009d8ca0c07c81adff475c48273207e170b4b5fbMike Stroyan#define PRINTF_SIZE_T_SPECIFIER    "%Iu"
776009d8ca0c07c81adff475c48273207e170b4b5fbMike Stroyan#else
777009d8ca0c07c81adff475c48273207e170b4b5fbMike Stroyan#define PRINTF_SIZE_T_SPECIFIER    "%zu"
778009d8ca0c07c81adff475c48273207e170b4b5fbMike Stroyan#endif
779009d8ca0c07c81adff475c48273207e170b4b5fbMike Stroyan
780a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbesstatic void app_gpu_dump_features(const struct app_gpu *gpu)
781a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes{
782a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    const VkPhysicalDeviceFeatures *features = &gpu->features;
783a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes
784a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("VkPhysicalDeviceFeatures\n");
785a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    /* TODO: add interesting features */
786a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("\tgeometryShader = %u\n",               features->geometryShader);
787a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes}
788a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes
789a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbesstatic void app_gpu_dump_limits(const struct app_gpu *gpu)
790a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes{
791a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    const VkPhysicalDeviceLimits *limits = &gpu->limits;
792a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes
793a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("VkPhysicalDeviceLimits\n");
794a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    /* TODO: add interesting limits */
795a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("\tmaxBoundDescriptorSets = %u\n",                               limits->maxBoundDescriptorSets);
796a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("\tmaxComputeWorkGroupInvocations = %u\n",                       limits->maxComputeWorkGroupInvocations);
797a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("\ttimestampFrequency = %lu\n",                                  limits->timestampFrequency);
798d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
799d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
80018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchterstatic void app_gpu_dump_props(const struct app_gpu *gpu)
80118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter{
80218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    const VkPhysicalDeviceProperties *props = &gpu->props;
80318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
80418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("VkPhysicalDeviceProperties\n");
80518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\tapiVersion = %u\n",                   props->apiVersion);
80618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\tdriverVersion = %u\n",                props->driverVersion);
80718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\tvendorId = 0x%04x\n",                 props->vendorId);
80818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\tdeviceId = 0x%04x\n",                 props->deviceId);
80918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\tdeviceType = %s\n",                   vk_physical_device_type_string(props->deviceType));
81018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\tdeviceName = %s\n",                   props->deviceName);
81118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    fflush(stdout);
81218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter}
81318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
81418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchterstatic void app_dump_extensions(
81518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        const char *indent,
81618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        const char *layer_name,
81718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        const uint32_t extension_count,
81818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        const VkExtensionProperties *extension_properties)
8193c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter{
8203c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    uint32_t i;
82118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    if (layer_name && (strlen(layer_name) > 0)) {
82218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        printf("%s%s Extensions", indent, layer_name);
82318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    } else {
82418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        printf("Extensions");
8253c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    }
82618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\tcount = %d\n", extension_count);
82718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    for (i=0; i< extension_count; i++) {
82818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        uint32_t major, minor, patch;
82973a21d311a3e905b8874b08ca6a54a2a5931b240Courtney Goeltzenleuchter        char spec_version[64];
83018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        VkExtensionProperties const *ext_prop = &extension_properties[i];
8313c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter
832ff87c822214d31c677026f8dcf53d8f953b395fdCourtney Goeltzenleuchter        if (i>0)
83318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter            printf("\n"); // separator between extensions
83418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
83518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        printf("%s\t", indent);
83618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        extract_version(ext_prop->specVersion, &major, &minor, &patch);
83718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        snprintf(spec_version, sizeof(spec_version), "%d.%d.%d", major, minor, patch);
83873a21d311a3e905b8874b08ca6a54a2a5931b240Courtney Goeltzenleuchter        printf("%s: extension version %s",
83973a21d311a3e905b8874b08ca6a54a2a5931b240Courtney Goeltzenleuchter                       ext_prop->extName, spec_version);
840ff87c822214d31c677026f8dcf53d8f953b395fdCourtney Goeltzenleuchter    }
841ff87c822214d31c677026f8dcf53d8f953b395fdCourtney Goeltzenleuchter    printf("\n");
84218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    fflush(stdout);
843ff87c822214d31c677026f8dcf53d8f953b395fdCourtney Goeltzenleuchter}
844ff87c822214d31c677026f8dcf53d8f953b395fdCourtney Goeltzenleuchter
845e2d07a5a3810d83d0ea7ecb396d61477893b74a4Mark Lobodzinskistatic void app_gpu_dump_queue_props(const struct app_gpu *gpu, uint32_t id)
846d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
847ef72e2a7cf4fa5708fdbfbc1c972a24ad0dbf809Cody Northrop    const VkQueueFamilyProperties *props = &gpu->queue_props[id];
848190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
849ef72e2a7cf4fa5708fdbfbc1c972a24ad0dbf809Cody Northrop    printf("VkQueueFamilyProperties[%d]\n", id);
850190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    printf("\tqueueFlags = %c%c%c%c\n",
8519cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter            (props->queueFlags & VK_QUEUE_GRAPHICS_BIT) ? 'G' : '.',
8529cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter            (props->queueFlags & VK_QUEUE_COMPUTE_BIT)  ? 'C' : '.',
8539cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter            (props->queueFlags & VK_QUEUE_DMA_BIT)      ? 'D' : '.',
8549cc421eb545767e22fd723dc573a7a3225261b1cCourtney Goeltzenleuchter            (props->queueFlags & VK_QUEUE_EXTENDED_BIT) ? 'X' : '.');
855190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    printf("\tqueueCount = %u\n",           props->queueCount);
856190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    printf("\tsupportsTimestamps = %u\n",   props->supportsTimestamps);
85718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    fflush(stdout);
858d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
859d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
860d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wustatic void app_gpu_dump_memory_props(const struct app_gpu *gpu)
861d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
8628205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    const VkPhysicalDeviceMemoryProperties *props = &gpu->memory_props;
863d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
8648205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    printf("VkPhysicalDeviceMemoryProperties\n");
865723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski    printf("\tmemoryTypeCount = %u\n",                props->memoryTypeCount);
866723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski    for (uint32_t i = 0; i < props->memoryTypeCount; i++) {
867723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski        printf("\tmemoryTypes[%u] : \n", i);
868723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski        printf("\t\tpropertyFlags = %u\n", props->memoryTypes[i].propertyFlags);
869723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski        printf("\t\theapIndex     = %u\n", props->memoryTypes[i].heapIndex);
870723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski    }
871723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski    printf("\tmemoryHeapCount = %u\n",                props->memoryHeapCount);
872723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski    for (uint32_t i = 0; i < props->memoryHeapCount; i++) {
873723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski        printf("\tmemoryHeaps[%u] : \n", i);
874723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski        printf("\t\tsize = " PRINTF_SIZE_T_SPECIFIER "\n", props->memoryHeaps[i].size);
875723462910ef2f9ed0255b74399c835020a75a0b1Mark Lobodzinski    }
87618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    fflush(stdout);
877d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
878d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
879d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wustatic void app_gpu_dump(const struct app_gpu *gpu)
880d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
881e2d07a5a3810d83d0ea7ecb396d61477893b74a4Mark Lobodzinski    uint32_t i;
882190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
883190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    printf("GPU%u\n", gpu->id);
884190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    app_gpu_dump_props(gpu);
885190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    printf("\n");
88618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    app_dump_extensions("", "", gpu->device_extension_count, gpu->device_extensions);
88718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("\n");
88818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("Layers\tcount = %d\n", gpu->device_layer_count);
88918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    for (uint32_t i = 0; i < gpu->device_layer_count; i++) {
89018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        uint32_t major, minor, patch;
89118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        char spec_version[64], layer_version[64];
89218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        struct layer_extension_list const *layer_info = &gpu->device_layers[i];
89318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
89418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        extract_version(layer_info->layer_properties.specVersion, &major, &minor, &patch);
89518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        snprintf(spec_version, sizeof(spec_version), "%d.%d.%d", major, minor, patch);
89618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        extract_version(layer_info->layer_properties.implVersion, &major, &minor, &patch);
89718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        snprintf(layer_version, sizeof(layer_version), "%d.%d.%d", major, minor, patch);
89818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        printf("\t%s (%s) Vulkan version %s, layer version %s\n",
89918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter               layer_info->layer_properties.layerName,
9003f26dee9c7577a32f4a104a8d2028f4b1f2aeae6Ian Elliott               (char*) layer_info->layer_properties.description,
90118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter               spec_version, layer_version);
90218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
90318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        app_dump_extensions("\t",
90418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                            layer_info->layer_properties.layerName,
90518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                            layer_info->extension_count,
90618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                            layer_info->extension_properties);
90718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        fflush(stdout);
90818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    }
909ff87c822214d31c677026f8dcf53d8f953b395fdCourtney Goeltzenleuchter    printf("\n");
910190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    for (i = 0; i < gpu->queue_count; i++) {
911190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        app_gpu_dump_queue_props(gpu, i);
912190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        printf("\n");
913190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    }
914190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    app_gpu_dump_memory_props(gpu);
915190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    printf("\n");
916a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    app_gpu_dump_features(gpu);
917a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("\n");
918a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    app_gpu_dump_limits(gpu);
919a048b3146ed9bc094adf4d6ba7355cd8a5ef7008Chris Forbes    printf("\n");
920190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    app_dev_dump(&gpu->dev);
921d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
922d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu
923d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wuint main(int argc, char **argv)
924d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu{
925190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    struct app_gpu gpus[MAX_GPUS];
9268205d901f17b1c76d89c956be235cf4e7a20a546Tony Barbour    VkPhysicalDevice objs[MAX_GPUS];
927e2d07a5a3810d83d0ea7ecb396d61477893b74a4Mark Lobodzinski    uint32_t gpu_count, i;
928382489d723fd0d3935da0dc7e1021c56c7b721d3Courtney Goeltzenleuchter    VkResult err;
9293c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    struct app_instance inst;
930190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
9313c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    app_create_instance(&inst);
93218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    app_dump_extensions("", "Global", inst.global_extension_count, inst.global_extensions);
93318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
93418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    printf("Global Layers\tcount = %d\n", inst.global_layer_count);
93518061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    for (uint32_t i = 0; i < inst.global_layer_count; i++) {
93618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        uint32_t major, minor, patch;
93718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        char spec_version[64], layer_version[64];
93818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        VkLayerProperties const *layer_prop = &inst.global_layers[i].layer_properties;
93918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
94018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        extract_version(layer_prop->specVersion, &major, &minor, &patch);
94118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        snprintf(spec_version, sizeof(spec_version), "%d.%d.%d", major, minor, patch);
94218061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        extract_version(layer_prop->implVersion, &major, &minor, &patch);
94318061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        snprintf(layer_version, sizeof(layer_version), "%d.%d.%d", major, minor, patch);
94418061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        printf("\t%s (%s) Vulkan version %s, layer version %s\n",
9453f26dee9c7577a32f4a104a8d2028f4b1f2aeae6Ian Elliott               layer_prop->layerName, (char*) layer_prop->description, spec_version, layer_version);
94618061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter
94718061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter        app_dump_extensions("\t",
94818061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                            inst.global_layers[i].layer_properties.layerName,
94918061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                            inst.global_layers[i].extension_count,
95018061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter                            inst.global_layers[i].extension_properties);
95118061cdee54b19cd628178d2924a7a914c62a10bCourtney Goeltzenleuchter    }
95229669a43755f6caa97c4c1d447f494514ba343d9Jon Ashburn
9533c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    err = vkEnumeratePhysicalDevices(inst.instance, &gpu_count, NULL);
95407b309a0cdfca1532ad14038682716ea7f77538dJon Ashburn    if (err)
95507b309a0cdfca1532ad14038682716ea7f77538dJon Ashburn        ERR_EXIT(err);
95607b309a0cdfca1532ad14038682716ea7f77538dJon Ashburn    if (gpu_count > MAX_GPUS) {
95718fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        printf("Too many GPUS found \n");
95818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        ERR_EXIT(VK_ERROR_UNKNOWN);
95907b309a0cdfca1532ad14038682716ea7f77538dJon Ashburn    }
9603c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    err = vkEnumeratePhysicalDevices(inst.instance, &gpu_count, objs);
961190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    if (err)
962190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        ERR_EXIT(err);
963190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
964190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    for (i = 0; i < gpu_count; i++) {
965190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        app_gpu_init(&gpus[i], i, objs[i]);
966190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        app_gpu_dump(&gpus[i]);
967190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        printf("\n\n");
968190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    }
969190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
970190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    for (i = 0; i < gpu_count; i++)
971190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu        app_gpu_destroy(&gpus[i]);
972190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu
9733c1ccf58f9f38b00cf0409e72fc65349aa11e742Courtney Goeltzenleuchter    app_destroy_instance(&inst);
9740b9a73720abbc3e1229507a4a97e0209976b7610Chia-I Wu
975190ebdcce84b767d8db7a42383c834dc067b3e77Chia-I Wu    return 0;
976d4bae362585dff8c456fb3b906512b4d2ef17fe8Chia-I Wu}
977ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott
978ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott#ifdef _WIN32
97918fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
98018fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo// Create a console window with a large scrollback size to which to send stdout.
98118fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo// Returns true if console window was successfully created, false otherwise.
98218fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedobool SetStdOutToNewConsole()
98318fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo{
98418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    // don't do anything if we already have a console
98518fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    if (GetStdHandle(STD_OUTPUT_HANDLE))
98618fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        return false;
98718fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
98818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    // allocate a console for this app
98918fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    AllocConsole();
99018fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
99118fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    // redirect unbuffered STDOUT to the console
99218fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    HANDLE consoleHandle = GetStdHandle(STD_OUTPUT_HANDLE);
99318fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    int fileDescriptor = _open_osfhandle((intptr_t)consoleHandle, _O_TEXT);
99418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    FILE *fp = _fdopen( fileDescriptor, "w" );
99518fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    *stdout = *fp;
99618fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    setvbuf( stdout, NULL, _IONBF, 0 );
99718fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
99818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    // make the console window bigger
99918fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    CONSOLE_SCREEN_BUFFER_INFO csbi;
100018fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    SMALL_RECT r;
100118fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    COORD bufferSize;
100218fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    if (!GetConsoleScreenBufferInfo(consoleHandle, &csbi))
100318fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        return false;
100418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    bufferSize.X = csbi.dwSize.X;
100518fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    bufferSize.Y = 1000;
100618fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    if (!SetConsoleScreenBufferSize(consoleHandle, bufferSize))
100718fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        return false;
100818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    r.Left = r.Top = 0;
100918fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    r.Right = csbi.dwSize.X-1;
101018fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    r.Bottom = 60;
101118fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    if (!SetConsoleWindowInfo(consoleHandle, true, &r))
101218fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        return false;
101318fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
101418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    // change the console window title
10154e19ed0ed322e45993bac7917a1a253dbaaf88f9Ian Elliott    if (!SetConsoleTitle(TEXT(APP_SHORT_NAME)))
101618fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        return false;
101718fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
101818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    return true;
101918fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo}
102018fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo
1021ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliottint WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR pCmdLine, int nCmdShow)
1022ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott{
1023ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott    char *argv = pCmdLine;
102418fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    consoleCreated = SetStdOutToNewConsole();
1025ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott    main(1, &argv);
1026ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott    fflush(stdout);
102718fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo    if (consoleCreated)
102818fb9239e51c9449fa072e3a398a55777f5c3c62David Pinedo        Sleep(INFINITE);
1029ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott}
1030ea95f5c3967480a57ceb03a98e8370225094ce42Ian Elliott#endif
1031