使用 vkEnumerateInstanceVersion 获取准确的 Vulkan API 版本
using vkEnumerateInstanceVersion to get exact Vulkan API version
我正在使用 vkEnumerateInstanceVersion
获取 vulkan api 版本并将其传递给 VkApplicationInfo
结构。我可以轻松区分 VK_VERSION_1_0
和 VK_VERSION_1_1
//query the api version in order to use the correct vulkan functionality
PFN_vkEnumerateInstanceVersion FN_vkEnumerateInstanceVersion =
PFN_vkEnumerateInstanceVersion(vkGetInstanceProcAddr(nullptr, "vkEnumerateInstanceVersion"));
uint32_t *instanceVersion = (uint32_t*)malloc(sizeof(uint32_t));
VkResult result = FN_vkEnumerateInstanceVersion(instanceVersion);
//check what is returned
if(result == VK_SUCCESS){
std::cout<<"RESULT(vkEnumerateInstanceVersion) : Intance version enumeration successful"<<std::endl;
if(instanceVersion!=nullptr){
std::cout<<"API_VERSION : VK_API_VERSION_1_1"<<std::endl;
appInfo.apiVersion = VK_API_VERSION_1_1;
}
else{
std::cout<<"API_VERSION : VK_API_VERSION_1_0"<<std::endl;
}
std::cout<<"Version number returned : "<<*instanceVersion<<std::endl;
}else if(result == VK_ERROR_OUT_OF_HOST_MEMORY){
std::cerr<<"RESULT(vkEnumerateInstanceVersion) : VK_ERROR_HOST_OUT_OF_MEMORY"<<std::endl;
}else{
std::cerr<<"RESULT(vkEnumerateInstanceVersion) : Something else returned while enumerating instance version"<<std::endl;
}
我正在使用上面的代码获取 api 版本。 vulkan 规范指出:
To query the version of instance-level functionality supported by the
implementation, call:
// Provided by VK_VERSION_1_1
VkResult vkEnumerateInstanceVersion(
uint32_t* pApiVersion);
上面块中的注释意味着这是由 VK_VERSION_1_1
提供的,而不是由 VK_VERSION_1_0
提供的。
现在,当我打开我的终端并输入:
vulkaninfo | head -n 5
我得到以下信息:
ERROR: [Loader Message] Code 0 : /usr/lib32/libvulkan_intel.so: wrong ELF class: ELFCLASS32
ERROR: [Loader Message] Code 0 : /usr/lib32/libvulkan_radeon.so: wrong ELF class: ELFCLASS32
==========
VULKANINFO
==========
Vulkan Instance Version: 1.2.159
这意味着我有 VK_API_VERSION_1_2。我想要做的是获得准确的 api 版本。
在执行第一段代码时,我得到:
RESULT(vkEnumerateInstanceVersion) : Intance version enumeration successful
API_VERSION : VK_API_VERSION_1_1
Version number returned : 4202655
有什么办法可以在程序中确定VK_VERSION_1_1或VK_VERSION_1_2。此外,我正在查看版本 1.2.165
的 vulkan 参考指南
I am using vkEnumerateInstanceVersion
to get the vulkan api version and pass it to VkApplicationInfo
struct.
不是 vkEnumerateInstanceVersion
的目的。
VkApplicationInfo::apiVersion
指定编写代码所针对的 Vulkan 版本。此版本应该是一个 固定值 ,因为您的代码不能针对 尚不存在 的 Vulkan 版本编写。也就是说,如果您正在编写一个针对 1.1 的应用程序,那么您指定 VK_VERSION_1_1
.
您可能仍会获得 1.2 版本,但这没关系,因为 Vulkan 主要版本都向后兼容较低的次要版本号。因此,如果您针对 Vulkan 1.1 编写代码,它将适用于任何 1.2 实现。
您还滥用了 实例 版本。实例版本是 Vulkan 实例机器的版本,而不是整个 Vulkan 实现 的版本。您可能连接到 1.2 实例机器,但 Vulkan 设备实现可能只为您提供 1.1。就 Vulkan 而言,这很好。
至于你的代码的细节:
此代码实际上并未正确区分 Vulkan 1.0 和 Vulkan 1.1。事实上,它包含许多错误和令人困惑的位。
第一个未解决的潜在问题是实例实现可能太旧而无法支持 vkEnumerateInstanceVersion
。由于 Vulkan 1.0 实例实现未提供此功能,您应首先确保该功能确实存在。也就是说,您应该在 调用它之前检查FN_vkEnumerateInstanceVersion
的值。如果该函数不存在,则实例版本必须为 1.0.
接下来,调用函数。但是函数不能失败;它只能 return 错误代码 VK_SUCCESS
。所以没有必要检查它的结果代码。
一旦你去检查有问题的实际值,你就会做一些奇怪的事情。你测试instanceVersion!=nullptr
。但是这样做没有意义,因为它 总是 指向有效内存。因此由此得出实例实现版本为1.1的结论是完全错误的。
Vulkan中版本号的值的含义是clearly specified in the specification。在你的情况下,如果你只是寻找主要和次要版本号,你可以砍掉补丁版本号。
所以获取实例版本的正确代码是:
auto FN_vkEnumerateInstanceVersion = PFN_vkEnumerateInstanceVersion(vkGetInstanceProcAddr(nullptr, "vkEnumerateInstanceVersion"));
if(FN_vkEnumerateInstanceVersion == nullptr)
return VK_API_VERSION_1_0;
else
{
uint32_t instanceVersion;
auto result = FN_vkEnumerateInstanceVersion(&instanceVersion);
return instanceVersion & 0xFFFFF000; //Remove the patch version.
}
您可以从 vkEnumerateInstanceVersion 返回的实例版本中获取 Vulkan 版本信息,其中包含 vulkan header.
中定义的 3 个宏
这是一个可以解决问题的片段:
uint32 instanceVersion = VK_API_VERSION_1_0;
auto FN_vkEnumerateInstanceVersion = PFN_vkEnumerateInstanceVersion(vkGetInstanceProcAddr(nullptr, "vkEnumerateInstanceVersion"));
if(vkEnumerateInstanceVersion){
vkEnumerateInstanceVersion(&instanceVersion );
}
// 3 macros to extract version info
uint32_t major = VK_VERSION_MAJOR(instanceVersion);
uint32_t minor = VK_VERSION_MINOR(instanceVersion);
uint32_t patch = VK_VERSION_PATCH(instanceVersion);
cout << "Vulkan Version:" << major << "." << minor << "." << patch << endl;
这将打印出如下内容:
Vulkan Version:1.1.121
我正在使用 vkEnumerateInstanceVersion
获取 vulkan api 版本并将其传递给 VkApplicationInfo
结构。我可以轻松区分 VK_VERSION_1_0
和 VK_VERSION_1_1
//query the api version in order to use the correct vulkan functionality
PFN_vkEnumerateInstanceVersion FN_vkEnumerateInstanceVersion =
PFN_vkEnumerateInstanceVersion(vkGetInstanceProcAddr(nullptr, "vkEnumerateInstanceVersion"));
uint32_t *instanceVersion = (uint32_t*)malloc(sizeof(uint32_t));
VkResult result = FN_vkEnumerateInstanceVersion(instanceVersion);
//check what is returned
if(result == VK_SUCCESS){
std::cout<<"RESULT(vkEnumerateInstanceVersion) : Intance version enumeration successful"<<std::endl;
if(instanceVersion!=nullptr){
std::cout<<"API_VERSION : VK_API_VERSION_1_1"<<std::endl;
appInfo.apiVersion = VK_API_VERSION_1_1;
}
else{
std::cout<<"API_VERSION : VK_API_VERSION_1_0"<<std::endl;
}
std::cout<<"Version number returned : "<<*instanceVersion<<std::endl;
}else if(result == VK_ERROR_OUT_OF_HOST_MEMORY){
std::cerr<<"RESULT(vkEnumerateInstanceVersion) : VK_ERROR_HOST_OUT_OF_MEMORY"<<std::endl;
}else{
std::cerr<<"RESULT(vkEnumerateInstanceVersion) : Something else returned while enumerating instance version"<<std::endl;
}
我正在使用上面的代码获取 api 版本。 vulkan 规范指出:
To query the version of instance-level functionality supported by the implementation, call:
// Provided by VK_VERSION_1_1 VkResult vkEnumerateInstanceVersion( uint32_t* pApiVersion);
上面块中的注释意味着这是由 VK_VERSION_1_1
提供的,而不是由 VK_VERSION_1_0
提供的。
现在,当我打开我的终端并输入:
vulkaninfo | head -n 5
我得到以下信息:
ERROR: [Loader Message] Code 0 : /usr/lib32/libvulkan_intel.so: wrong ELF class: ELFCLASS32
ERROR: [Loader Message] Code 0 : /usr/lib32/libvulkan_radeon.so: wrong ELF class: ELFCLASS32
==========
VULKANINFO
==========
Vulkan Instance Version: 1.2.159
这意味着我有 VK_API_VERSION_1_2。我想要做的是获得准确的 api 版本。 在执行第一段代码时,我得到:
RESULT(vkEnumerateInstanceVersion) : Intance version enumeration successful
API_VERSION : VK_API_VERSION_1_1
Version number returned : 4202655
有什么办法可以在程序中确定VK_VERSION_1_1或VK_VERSION_1_2。此外,我正在查看版本 1.2.165
I am using
vkEnumerateInstanceVersion
to get the vulkan api version and pass it toVkApplicationInfo
struct.
不是 vkEnumerateInstanceVersion
的目的。
VkApplicationInfo::apiVersion
指定编写代码所针对的 Vulkan 版本。此版本应该是一个 固定值 ,因为您的代码不能针对 尚不存在 的 Vulkan 版本编写。也就是说,如果您正在编写一个针对 1.1 的应用程序,那么您指定 VK_VERSION_1_1
.
您可能仍会获得 1.2 版本,但这没关系,因为 Vulkan 主要版本都向后兼容较低的次要版本号。因此,如果您针对 Vulkan 1.1 编写代码,它将适用于任何 1.2 实现。
您还滥用了 实例 版本。实例版本是 Vulkan 实例机器的版本,而不是整个 Vulkan 实现 的版本。您可能连接到 1.2 实例机器,但 Vulkan 设备实现可能只为您提供 1.1。就 Vulkan 而言,这很好。
至于你的代码的细节:
此代码实际上并未正确区分 Vulkan 1.0 和 Vulkan 1.1。事实上,它包含许多错误和令人困惑的位。
第一个未解决的潜在问题是实例实现可能太旧而无法支持 vkEnumerateInstanceVersion
。由于 Vulkan 1.0 实例实现未提供此功能,您应首先确保该功能确实存在。也就是说,您应该在 调用它之前检查FN_vkEnumerateInstanceVersion
的值。如果该函数不存在,则实例版本必须为 1.0.
接下来,调用函数。但是函数不能失败;它只能 return 错误代码 VK_SUCCESS
。所以没有必要检查它的结果代码。
一旦你去检查有问题的实际值,你就会做一些奇怪的事情。你测试instanceVersion!=nullptr
。但是这样做没有意义,因为它 总是 指向有效内存。因此由此得出实例实现版本为1.1的结论是完全错误的。
Vulkan中版本号的值的含义是clearly specified in the specification。在你的情况下,如果你只是寻找主要和次要版本号,你可以砍掉补丁版本号。
所以获取实例版本的正确代码是:
auto FN_vkEnumerateInstanceVersion = PFN_vkEnumerateInstanceVersion(vkGetInstanceProcAddr(nullptr, "vkEnumerateInstanceVersion"));
if(FN_vkEnumerateInstanceVersion == nullptr)
return VK_API_VERSION_1_0;
else
{
uint32_t instanceVersion;
auto result = FN_vkEnumerateInstanceVersion(&instanceVersion);
return instanceVersion & 0xFFFFF000; //Remove the patch version.
}
您可以从 vkEnumerateInstanceVersion 返回的实例版本中获取 Vulkan 版本信息,其中包含 vulkan header.
中定义的 3 个宏这是一个可以解决问题的片段:
uint32 instanceVersion = VK_API_VERSION_1_0;
auto FN_vkEnumerateInstanceVersion = PFN_vkEnumerateInstanceVersion(vkGetInstanceProcAddr(nullptr, "vkEnumerateInstanceVersion"));
if(vkEnumerateInstanceVersion){
vkEnumerateInstanceVersion(&instanceVersion );
}
// 3 macros to extract version info
uint32_t major = VK_VERSION_MAJOR(instanceVersion);
uint32_t minor = VK_VERSION_MINOR(instanceVersion);
uint32_t patch = VK_VERSION_PATCH(instanceVersion);
cout << "Vulkan Version:" << major << "." << minor << "." << patch << endl;
这将打印出如下内容:
Vulkan Version:1.1.121