Ubuntu环境下Vulkan视频扩展函数全局加载问题求助
解决Vulkan视频扩展函数全局加载问题
核心思路
因为vkGetPhysicalDeviceVideoCapabilitiesKHR属于Vulkan扩展函数,libvulkan.so中没有导出该符号,且vulkan头文件将其声明为普通函数而非指针,无法直接全局赋值。解决方法是:自己定义全局函数指针,在Vulkan实例初始化后加载该指针,之后通过指针在任意函数中调用。
具体实现步骤
定义全局函数指针
先匹配原函数的原型定义指针类型,再声明全局指针:#include <vulkan/vulkan.h> // 匹配原函数的类型定义 typedef VkResult (VKAPI_PTR *PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR)( VkPhysicalDevice physicalDevice, const VkPhysicalDeviceVideoCapabilitiesInfoKHR* pVideoCapabilitiesInfo, VkVideoCapabilitiesKHR* pVideoCapabilities ); // 声明全局函数指针,初始化为nullptr PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR g_vkGetPhysicalDeviceVideoCapabilitiesKHR = nullptr;在初始化阶段加载函数指针
在创建Vulkan实例、确认扩展启用后,通过vkGetPhysicalDeviceProcAddr加载函数地址,并检查加载结果:int main() { // ... 初始化Vulkan实例、获取物理设备等步骤 ... // 加载扩展函数地址 g_vkGetPhysicalDeviceVideoCapabilitiesKHR = (PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR) vkGetPhysicalDeviceProcAddr(physicalDevice, "vkGetPhysicalDeviceVideoCapabilitiesKHR"); // 必须检查加载是否成功 if (!g_vkGetPhysicalDeviceVideoCapabilitiesKHR) { fprintf(stderr, "Failed to load vkGetPhysicalDeviceVideoCapabilitiesKHR\n"); return EXIT_FAILURE; } // ... 后续初始化或调用其他模块 ... }注:使用
vkGetPhysicalDeviceProcAddr比vkGetInstanceProcAddr更准确,因为该函数是物理设备级别的扩展函数。全局调用函数指针
在任意函数中,直接使用全局指针调用,用法与原函数完全一致:void some_other_function(VkPhysicalDevice physicalDevice) { VkPhysicalDeviceVideoCapabilitiesInfoKHR capabilitiesInfo = { .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VIDEO_CAPABILITIES_INFO_KHR, // ... 填充其他参数 ... }; VkVideoCapabilitiesKHR videoCapabilities = { .sType = VK_STRUCTURE_TYPE_VIDEO_CAPABILITIES_KHR }; VkResult result = g_vkGetPhysicalDeviceVideoCapabilitiesKHR( physicalDevice, &capabilitiesInfo, &videoCapabilities ); // ... 处理调用结果 ... }
多文件项目注意事项
如果项目分为多个源文件,需要在公共头文件中声明全局指针为extern,确保所有文件都能访问:
// common_vulkan.h #pragma once #include <vulkan/vulkan.h> typedef VkResult (VKAPI_PTR *PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR)( VkPhysicalDevice physicalDevice, const VkPhysicalDeviceVideoCapabilitiesInfoKHR* pVideoCapabilitiesInfo, VkVideoCapabilitiesKHR* pVideoCapabilities ); extern PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR g_vkGetPhysicalDeviceVideoCapabilitiesKHR;
然后在初始化源文件中定义并加载该指针即可。
内容的提问来源于stack exchange,提问作者El Sampsa
相关产品推荐
相关产品推荐

