首先:我已经使用 vulkan 进行了大量工作,并且在验证层方面没有遇到任何问题。他们工作得很好,如果我忘记破坏 vulkan handle ,他们就会提示。
后来(目前没有进行代码重构)它不起作用。我有点忘了如何设置验证层。我隔离了一个快速而肮脏的项目(一个文件)来测试它是否独立工作:
#include <Windows.h>
#include <vulkan/vulkan.h>
#include <vector>
#include <iostream>
HINSTANCE g_hInstance;
HWND g_hWnd;
bool g_running = true;
const char* const APPLICATION_NAME = "debugTest";
VkInstance g_instance{ VK_NULL_HANDLE };
VkPhysicalDevice g_physicalDevice{ VK_NULL_HANDLE };
VkDevice g_device{ VK_NULL_HANDLE };
VkDebugReportCallbackEXT g_callback;
PFN_vkCreateDebugReportCallbackEXT fpCreateDebugReportCallbackEXT;
PFN_vkDestroyDebugReportCallbackEXT fpDestroyDebugReportCallbackEXT;
void loop()
{
MSG msg;
while (g_running)
{
if (PeekMessage(&msg, nullptr, 0u, 0u, PM_REMOVE))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
}
LRESULT CALLBACK wndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch (uMsg)
{
case WM_KEYDOWN:
if (wParam == VK_ESCAPE)
{
g_running = false;
DestroyWindow(hWnd);
UnregisterClass(APPLICATION_NAME, g_hInstance);
}
break;
case WM_CLOSE:
g_running = false;
DestroyWindow(hWnd);
UnregisterClass(APPLICATION_NAME, g_hInstance);
break;
default:
return DefWindowProc(hWnd, uMsg, wParam, lParam);
}
}
void win32_createWindow(int nCmdShow)
{
g_hInstance = GetModuleHandle(nullptr);
// REGISTER APPLICATION CLASS
WNDCLASSEX wc;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = wndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = g_hInstance;
wc.hIcon = LoadIcon(nullptr, IDI_WINLOGO);
wc.hCursor = LoadCursor(nullptr, IDC_ARROW);
wc.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH);
wc.lpszMenuName = nullptr;
wc.lpszClassName = APPLICATION_NAME;
wc.hIconSm = wc.hIcon;
RegisterClassEx(&wc);
g_hWnd = CreateWindowEx(
0,
APPLICATION_NAME,
"Ich bin ein Titel",
WS_OVERLAPPEDWINDOW,
100, 100,
800, 600,
nullptr, nullptr, g_hInstance, nullptr);
ShowWindow(g_hWnd, nCmdShow);
SetFocus(g_hWnd);
SetForegroundWindow(g_hWnd);
printf("WINDOW CREATED\n");
}
VKAPI_ATTR VkBool32 VKAPI_CALL debugCallback(
VkDebugReportFlagsEXT flags,
VkDebugReportObjectTypeEXT objectType,
uint64_t object,
size_t location,
int32_t messageCode,
const char* pLayerPrefix,
const char* pMessage,
void* pUserData)
{
printf("%s\n", pMessage);
return VK_FALSE;
}
void vk_init()
{
// INSTANCE
{
VkApplicationInfo appInfo;
appInfo.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO;
appInfo.pNext = nullptr;
appInfo.pApplicationName = APPLICATION_NAME;
appInfo.applicationVersion = VK_MAKE_VERSION(1, 0, 0);
appInfo.pEngineName = APPLICATION_NAME;
appInfo.engineVersion = VK_MAKE_VERSION(1, 0, 0);
appInfo.apiVersion = VK_API_VERSION_1_0;
// LAYER
std::vector<const char*> layers = {
"VK_LAYER_LUNARG_standard_validation"
};
// EXTENSIONS
std::vector<const char*> extensions = {
"VK_KHR_surface",
"VK_KHR_win32_surface",
"VK_EXT_debug_report"
};
VkInstanceCreateInfo instanceCInfo;
instanceCInfo.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
instanceCInfo.pNext = nullptr;
instanceCInfo.flags = 0;
instanceCInfo.pApplicationInfo = &appInfo;
instanceCInfo.enabledLayerCount = static_cast<uint32_t>(layers.size());
instanceCInfo.ppEnabledLayerNames = layers.data();
instanceCInfo.enabledExtensionCount = static_cast<uint32_t>(extensions.size());
instanceCInfo.ppEnabledExtensionNames = extensions.data();
if (vkCreateInstance(&instanceCInfo, nullptr, &g_instance) != VK_SUCCESS)
{
printf("INSTANCE CREATION FAILED\n");
return;
}
printf("INSTANCE CREATED\n");
}
// DEBUG
{
fpCreateDebugReportCallbackEXT = reinterpret_cast<PFN_vkCreateDebugReportCallbackEXT>(vkGetInstanceProcAddr(g_instance, "vkCreateDebugReportCallbackEXT"));
fpDestroyDebugReportCallbackEXT = reinterpret_cast<PFN_vkDestroyDebugReportCallbackEXT>(vkGetInstanceProcAddr(g_instance, "vkDestroyDebugReportCallbackEXT"));
VkDebugReportCallbackCreateInfoEXT debugReportCallbackCInfo;
debugReportCallbackCInfo.sType = VK_STRUCTURE_TYPE_DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT;
debugReportCallbackCInfo.pNext = nullptr;
debugReportCallbackCInfo.flags = VK_DEBUG_REPORT_WARNING_BIT_EXT | VK_DEBUG_REPORT_ERROR_BIT_EXT;
debugReportCallbackCInfo.pfnCallback = debugCallback;
debugReportCallbackCInfo.pUserData = nullptr;
if (fpCreateDebugReportCallbackEXT(g_instance, &debugReportCallbackCInfo, nullptr, &g_callback) != VK_SUCCESS)
{
printf("DEBUG CREATION FAILED\n");
}
printf("DEBUG CALLBACK CREATED\n");
}
// GPU
{
uint32_t count{ 0u };
vkEnumeratePhysicalDevices(g_instance, &count, nullptr);
std::vector<VkPhysicalDevice> physicalDevices(count);
vkEnumeratePhysicalDevices(g_instance, &count, physicalDevices.data());
g_physicalDevice = physicalDevices[0];
printf("PHYSICAL DEVICE PICKED\n");
}
// DEVICE
{
float defaultQueuePriorities[] = { 0.0f, 0.0f, 0.0f, 0.0f };
std::vector<VkDeviceQueueCreateInfo> deviceQueueCreateInfos(1);
deviceQueueCreateInfos[0].sType = VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
deviceQueueCreateInfos[0].pNext = nullptr;
deviceQueueCreateInfos[0].flags = 0;
deviceQueueCreateInfos[0].queueFamilyIndex = 0u;
deviceQueueCreateInfos[0].queueCount = 1u;
deviceQueueCreateInfos[0].pQueuePriorities = defaultQueuePriorities;
// LAYERS
std::vector<const char*> layers(0);
// EXTENSIONS
std::vector<const char*> extensions(0);
// DEVICE FEATURES
VkPhysicalDeviceFeatures enabledFeatures{};
VkDeviceCreateInfo deviceCInfo;
deviceCInfo.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO;
deviceCInfo.pNext = nullptr;
deviceCInfo.flags = 0;
deviceCInfo.queueCreateInfoCount = static_cast<uint32_t>(deviceQueueCreateInfos.size());
deviceCInfo.pQueueCreateInfos = deviceQueueCreateInfos.data();
deviceCInfo.enabledLayerCount = static_cast<uint32_t>(layers.size());
deviceCInfo.ppEnabledLayerNames = layers.data();
deviceCInfo.enabledExtensionCount = static_cast<uint32_t>(extensions.size());
deviceCInfo.ppEnabledExtensionNames = extensions.data();
deviceCInfo.pEnabledFeatures = &enabledFeatures;
if (vkCreateDevice(g_physicalDevice, &deviceCInfo, nullptr, &g_device) != VK_SUCCESS)
{
printf("LOGICAL DEVICE CREATION FAILED!\n");
}
printf("LOGICAL DEVICE CREATED\n");
}
}
int main(int argc, char** argv)
{
win32_createWindow(SW_SHOWDEFAULT);
vk_init();
loop();
system("PAUSE");
return 0;
}
它不适合我,但它应该适合我,因为我没有破坏逻辑设备。
那我做错了什么?我想我激活了正确的层和扩展。我检查了 GPU Open: How to use validation layers为此。
请帮帮我,我想我完全瞎了。
我是一名优秀的程序员,十分优秀!