首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >Vulkan MacOS-无法设置调试信使

Vulkan MacOS-无法设置调试信使
EN

Stack Overflow用户
提问于 2022-07-04 16:20:20
回答 1查看 159关注 0票数 0

我正在学习教程https://vulkan-tutorial.com/Drawing_a_triangle/Setup/Validation_layers

代码语言:javascript
运行
复制
auto func = (PFN_vkCreateDebugUtilsMessengerEXT)vkGetInstanceProcAddr(instance, "vkCreateDebugUtilsMessengerEXT");

"func“在CreateDebugUtilsMessengerEXT函数中返回nullptr。在调用要设置调试信使的函数之前,将成功创建Vulkan实例。我在用Xcode。我已经将环境变量VK_LOADER_DEBUG设置为all,但是没有输出导致问题的原因。

全码

代码语言:javascript
运行
复制
#define GLFW_INCLUDE_VULKAN
#include <GLFW/glfw3.h>

#include <iostream>
#include <stdexcept>
#include <vector>
#include <cstring>
#include <cstdlib>
#include <cstdlib>
#include <unistd.h>

const std::vector<const char*> validationLayers={"VK_LAYER_KHRONOS_validation"};
#ifdef NDEUBG
const bool enableValidationLayers=false;
#else
const bool enableValidationLayers=true;
#endif

VkResult CreateDebugUtilsMessengerEXT(VkInstance instance, const VkDebugUtilsMessengerCreateInfoEXT* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkDebugUtilsMessengerEXT* pDebugMessenger) {
    auto func = (PFN_vkCreateDebugUtilsMessengerEXT)vkGetInstanceProcAddr(instance, "vkCreateDebugUtilsMessengerEXT");
    if (func != nullptr) {
        return func(instance, pCreateInfo, pAllocator, pDebugMessenger);
    } else {
        return VK_ERROR_EXTENSION_NOT_PRESENT;
    }
}


void DestroyDebugUtilsMessengerEXT(VkInstance instance, VkDebugUtilsMessengerEXT debugMessenger, const VkAllocationCallbacks* pAllocator) {
    auto func = (PFN_vkDestroyDebugUtilsMessengerEXT)vkGetInstanceProcAddr(instance, "vkDestroyDebugUtilsMessengerEXT");
    if (func != nullptr) {
        func(instance, debugMessenger, pAllocator);
    }
}

class Application{
public:
void run(){
    initWindow();
    initVulkan();
    mainLoop();
    cleanUp();
    
}
private:
    GLFWwindow* window;
    VkInstance instanceVK;
    VkDebugUtilsMessengerEXT debugMessenger;
    void initWindow(){
        glfwWindowHint(GLFW_CLIENT_API, GLFW_NO_API);
        glfwWindowHint(GLFW_RESIZABLE, GLFW_FALSE);
        const uint32_t HEIGHT=600;
        const uint32_t WIDTH=800;
        window=glfwCreateWindow(WIDTH, HEIGHT, "VULKAN!", nullptr, nullptr);
        
        
    }
    void initVulkan(){
        createInstance();
        setupDebugMessenger();
        
    }
    void populateDebugMessengerCreateInfo(VkDebugUtilsMessengerCreateInfoEXT& createInfo) {
        createInfo = {};
        createInfo.sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_MESSENGER_CREATE_INFO_EXT;
        createInfo.messageSeverity = VK_DEBUG_UTILS_MESSAGE_SEVERITY_VERBOSE_BIT_EXT | VK_DEBUG_UTILS_MESSAGE_SEVERITY_WARNING_BIT_EXT | VK_DEBUG_UTILS_MESSAGE_SEVERITY_ERROR_BIT_EXT;
        createInfo.messageType = VK_DEBUG_UTILS_MESSAGE_TYPE_GENERAL_BIT_EXT | VK_DEBUG_UTILS_MESSAGE_TYPE_VALIDATION_BIT_EXT | VK_DEBUG_UTILS_MESSAGE_TYPE_PERFORMANCE_BIT_EXT;
        createInfo.pfnUserCallback = debugCallback;
    }
    void setupDebugMessenger(){
        if(!enableValidationLayers) return;
        VkDebugUtilsMessengerCreateInfoEXT createInfo;
        populateDebugMessengerCreateInfo(createInfo);
        if (CreateDebugUtilsMessengerEXT(instanceVK, &createInfo, nullptr, &debugMessenger) != VK_SUCCESS) {
            throw std::runtime_error("failed to set up debug messenger!");
        }
        
    };
    void createInstance(){
        if (enableValidationLayers && !checkValidationLayerSupport()) {
                throw std::runtime_error("validation layers requested, but not available!");
        }
        VkApplicationInfo appInfo{};
        appInfo.sType=VK_STRUCTURE_TYPE_APPLICATION_INFO;
        appInfo.pApplicationName="Testing";
        appInfo.applicationVersion = VK_MAKE_VERSION(1, 0, 0);
        appInfo.pEngineName = "No Engine";
        appInfo.engineVersion = VK_MAKE_VERSION(1, 0, 0);
        appInfo.apiVersion = VK_API_VERSION_1_0;
        VkInstanceCreateInfo createInfo{};
        createInfo.sType=VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
        createInfo.pApplicationInfo=&appInfo;
        VkDebugUtilsMessengerCreateInfoEXT debugCreateInfo{};
            if (enableValidationLayers) {
                std::cout<<"apinspifnsfponasof\n\n\n\n\n\n\n\n\n\n";
                createInfo.enabledLayerCount = static_cast<uint32_t>(validationLayers.size());
                createInfo.ppEnabledLayerNames = validationLayers.data();

                populateDebugMessengerCreateInfo(debugCreateInfo);
                createInfo.pNext = (VkDebugUtilsMessengerCreateInfoEXT*) &debugCreateInfo;
            } else {
                createInfo.enabledLayerCount = 0;

                createInfo.pNext = nullptr;
            }
        
        uint32_t glfwExtensionCount = 0;
        const char** glfwExtensions;

        glfwExtensions = glfwGetRequiredInstanceExtensions(&glfwExtensionCount);
        createInfo.flags = VK_INSTANCE_CREATE_ENUMERATE_PORTABILITY_BIT_KHR;
        if(enableValidationLayers){
            createInfo.enabledLayerCount=static_cast<uint32_t>(validationLayers.size());
            createInfo.ppEnabledLayerNames = validationLayers.data();
        } else {
                createInfo.enabledLayerCount = 0;
            }
    
        uint32_t extensionCount = 0;
        vkEnumerateInstanceExtensionProperties(nullptr, &extensionCount, nullptr);
        std::vector<VkExtensionProperties> extensions(extensionCount);
        vkEnumerateInstanceExtensionProperties(nullptr, &extensionCount, extensions.data());
        std::cout << "available extensions:\n";

        for (const auto& extension : extensions) {
            std::cout << '\t' << extension.extensionName << '\n';
        }
        // Make useable on MACOS
        std::vector<const char*> instanceExtensions(glfwExtensionCount);
        memcpy(instanceExtensions.data(), glfwExtensions, sizeof(const char*) * glfwExtensionCount);
        instanceExtensions.push_back("VK_KHR_portability_enumeration");
        createInfo.enabledExtensionCount = static_cast<uint32_t>(instanceExtensions.size());
        createInfo.ppEnabledExtensionNames = instanceExtensions.data();
        
        VkResult result= vkCreateInstance(&createInfo, nullptr, &instanceVK);
        if(result!= VK_SUCCESS){
            std::cout<<result;
            throw std::runtime_error("Falied to create Instance");
        }else{
            std::cout<<"SUCCESS";
        }
        for (const auto& extension : extensions) {
            std::cout << '\t' << extension.extensionName << '\n';
        }
    }
    void mainLoop(){
        while (!glfwWindowShouldClose(window)) {
            glfwPollEvents();
  
        }
    }
    void cleanUp(){
        if (enableValidationLayers) {
            DestroyDebugUtilsMessengerEXT(instanceVK, debugMessenger, nullptr);
        }
        vkDestroyInstance(instanceVK, nullptr);
        glfwDestroyWindow(window);

        glfwTerminate();

    };
    bool checkValidationLayerSupport(){
        uint32_t layerCount;
        vkEnumerateInstanceLayerProperties(&layerCount,nullptr);
        std::vector<VkLayerProperties> avaiableLayers(layerCount);
        vkEnumerateInstanceLayerProperties(&layerCount, avaiableLayers.data());
        for(const char* layerName:validationLayers){
            bool layerFound=false;
            for(const auto& layerProperties:avaiableLayers){
                if(strcmp(layerName, layerProperties.layerName)==0){
                    layerFound=true;
                    break;
                }
            }
            if(!layerFound){
                return false;
            }
        };
        return true;
        
    };
    std::vector<const char*> getRequiredExtensions() {
        uint32_t glfwExtensionCount = 0;
        const char** glfwExtensions;
        glfwExtensions = glfwGetRequiredInstanceExtensions(&glfwExtensionCount);

        std::vector<const char*> extensions(glfwExtensions, glfwExtensions + glfwExtensionCount);

        if (enableValidationLayers) {
            extensions.push_back(VK_EXT_DEBUG_UTILS_EXTENSION_NAME);
        }

        return extensions;
    }
    static VKAPI_ATTR VkBool32 VKAPI_CALL debugCallback(
        VkDebugUtilsMessageSeverityFlagBitsEXT messageSeverity,
        VkDebugUtilsMessageTypeFlagsEXT messageType,
        const VkDebugUtilsMessengerCallbackDataEXT* pCallbackData,
        void* pUserData) {

        std::cerr << "validation layer: " << pCallbackData->pMessage << std::endl;

        return VK_FALSE;
    }
};
int main(){
    Application app;
    try {
        app.run();
    } catch (const std::exception& e) {
        std::cout<<"here";
        std::cerr << e.what() << std::endl;
        return EXIT_FAILURE;
    }
};
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2022-07-05 09:21:48

您还没有预先启用VK_EXT_debug_utils扩展:

代码语言:javascript
运行
复制
std::vector<const char*> instanceExtensions(glfwExtensionCount);
memcpy(instanceExtensions.data(), glfwExtensions, sizeof(const char*) * glfwExtensionCount);
instanceExtensions.push_back("VK_KHR_portability_enumeration");
createInfo.enabledExtensionCount = static_cast<uint32_t>(instanceExtensions.size());
createInfo.ppEnabledExtensionNames = instanceExtensions.data();

添加扩展的getRequiredExtensions()仍然没有调用。

下次您向StackOverflow提交问题时,请注意一下。总是发布一个最小的完整示例,而不是完整的代码库。原因是90 %的时候,你发现自己的问题是通过形成一个最小的例子本身,所以你节省了其他人的时间。然后,该示例将尽可能简短地暴露问题,因此您可以在他们阅读时为他们节省第二次时间。在您的例子中,它实际上可以是一些简单的东西,如:

代码语言:javascript
运行
复制
int main(){
    vkCreateInstance();
    pvkCreateDebugUtilsMessengerEXT = vkGetProcAddr();
    assert(pvkCreateDebugUtilsMessengerEXT);
}
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72859635

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档