mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2025-12-24 21:50:12 +01:00
zink: make physical device functions use a dynamic function pointers.
vkGetPhysicalDeviceFeatures2 and vkGetPhysicalDeviceProperties2 are not present on some MoltenVK versions. VK_KHR_get_physical_device_properties2 exposes the KHR versions of the same functions. These cannot be used via static linking, so we have to dynamically detect the loader version and then the extension to work out which pointers to use. Reviewed-By: Mike Blumenkrantz <michael.blumenkrantz@gmail.com> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/7447>
This commit is contained in:
parent
91f9bc18e0
commit
d377d84496
3 changed files with 94 additions and 29 deletions
|
|
@ -170,53 +170,69 @@ zink_get_physical_device_info(struct zink_screen *screen)
|
|||
}
|
||||
}
|
||||
|
||||
// check for device extension features
|
||||
info->feats.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2;
|
||||
if (screen->vk_GetPhysicalDeviceFeatures2) {
|
||||
// check for device extension features
|
||||
info->feats.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2;
|
||||
|
||||
%for ext in extensions:
|
||||
%if ext.feature_field is not None or ext.has_features:
|
||||
${ext.guard_start()}
|
||||
if (support_${ext.name_with_vendor()}) {
|
||||
info->${ext.field("feats")}.sType = ${ext.stype("FEATURES")};
|
||||
info->${ext.field("feats")}.pNext = info->feats.pNext;
|
||||
info->feats.pNext = &info->${ext.field("feats")};
|
||||
}
|
||||
${ext.guard_end()}
|
||||
${ext.guard_start()}
|
||||
if (support_${ext.name_with_vendor()}) {
|
||||
info->${ext.field("feats")}.sType = ${ext.stype("FEATURES")};
|
||||
info->${ext.field("feats")}.pNext = info->feats.pNext;
|
||||
info->feats.pNext = &info->${ext.field("feats")};
|
||||
}
|
||||
${ext.guard_end()}
|
||||
%endif
|
||||
%endfor
|
||||
|
||||
vkGetPhysicalDeviceFeatures2(screen->pdev, &info->feats);
|
||||
screen->vk_GetPhysicalDeviceFeatures2(screen->pdev, &info->feats);
|
||||
|
||||
%for ext in extensions:
|
||||
${ext.guard_start()}
|
||||
${ext.guard_start()}
|
||||
%if ext.feature_field is None:
|
||||
info->have_${ext.name_with_vendor()} = support_${ext.name_with_vendor()};
|
||||
info->have_${ext.name_with_vendor()} = support_${ext.name_with_vendor()};
|
||||
%else:
|
||||
if (support_${ext.name_with_vendor()} && info->${ext.field("feats")}.${ext.feature_field}) {
|
||||
info->have_${ext.name_with_vendor()} = true;
|
||||
}
|
||||
if (support_${ext.name_with_vendor()} && info->${ext.field("feats")}.${ext.feature_field}) {
|
||||
info->have_${ext.name_with_vendor()} = true;
|
||||
}
|
||||
%endif
|
||||
${ext.guard_end()}
|
||||
${ext.guard_end()}
|
||||
%endfor
|
||||
} else {
|
||||
vkGetPhysicalDeviceFeatures(screen->pdev, &info->feats.features);
|
||||
|
||||
%for ext in extensions:
|
||||
${ext.guard_start()}
|
||||
%if ext.feature_field is None:
|
||||
info->have_${ext.name_with_vendor()} = support_${ext.name_with_vendor()};
|
||||
%endif
|
||||
${ext.guard_end()}
|
||||
%endfor
|
||||
}
|
||||
|
||||
// check for device properties
|
||||
VkPhysicalDeviceProperties2 props = {};
|
||||
props.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROPERTIES_2;
|
||||
if (screen->vk_GetPhysicalDeviceProperties2) {
|
||||
VkPhysicalDeviceProperties2 props = {};
|
||||
props.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROPERTIES_2;
|
||||
|
||||
%for ext in extensions:
|
||||
%if ext.has_properties:
|
||||
${ext.guard_start()}
|
||||
if (info->have_${ext.name_with_vendor()}) {
|
||||
info->${ext.field("props")}.sType = ${ext.stype("PROPERTIES")};
|
||||
info->${ext.field("props")}.pNext = props.pNext;
|
||||
props.pNext = &info->${ext.field("props")};
|
||||
}
|
||||
${ext.guard_end()}
|
||||
${ext.guard_start()}
|
||||
if (info->have_${ext.name_with_vendor()}) {
|
||||
info->${ext.field("props")}.sType = ${ext.stype("PROPERTIES")};
|
||||
info->${ext.field("props")}.pNext = props.pNext;
|
||||
props.pNext = &info->${ext.field("props")};
|
||||
}
|
||||
${ext.guard_end()}
|
||||
%endif
|
||||
%endfor
|
||||
|
||||
vkGetPhysicalDeviceProperties2(screen->pdev, &props);
|
||||
memcpy(&info->props, &props.properties, sizeof(info->props));
|
||||
screen->vk_GetPhysicalDeviceProperties2(screen->pdev, &props);
|
||||
memcpy(&info->props, &props.properties, sizeof(info->props));
|
||||
} else {
|
||||
vkGetPhysicalDeviceProperties(screen->pdev, &info->props);
|
||||
}
|
||||
|
||||
// generate extension list
|
||||
num_extensions = 0;
|
||||
|
|
|
|||
|
|
@ -672,6 +672,7 @@ create_instance(struct zink_screen *screen)
|
|||
}
|
||||
if (!strcmp(extension_props[i].extensionName, VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME)) {
|
||||
extensions[num_extensions++] = VK_KHR_GET_PHYSICAL_DEVICE_PROPERTIES_2_EXTENSION_NAME;
|
||||
screen->have_physical_device_prop2_ext = true;
|
||||
}
|
||||
if (!strcmp(extension_props[i].extensionName, VK_KHR_EXTERNAL_MEMORY_CAPABILITIES_EXTENSION_NAME)) {
|
||||
extensions[num_extensions++] = VK_KHR_EXTERNAL_MEMORY_CAPABILITIES_EXTENSION_NAME;
|
||||
|
|
@ -873,6 +874,42 @@ zink_flush_frontbuffer(struct pipe_screen *pscreen,
|
|||
} \
|
||||
} while (0)
|
||||
|
||||
#define GET_PROC_ADDR_INSTANCE_LOCAL(instance, x) PFN_vk##x vk_##x = (PFN_vk##x)vkGetInstanceProcAddr(instance, "vk"#x)
|
||||
|
||||
static bool
|
||||
load_instance_extensions(struct zink_screen *screen)
|
||||
{
|
||||
screen->loader_version = VK_API_VERSION_1_0;
|
||||
{
|
||||
// Get the Loader version
|
||||
GET_PROC_ADDR_INSTANCE_LOCAL(NULL, EnumerateInstanceVersion);
|
||||
if (vk_EnumerateInstanceVersion) {
|
||||
uint32_t loader_version_temp = VK_API_VERSION_1_0;
|
||||
if (VK_SUCCESS == (*vk_EnumerateInstanceVersion)( &loader_version_temp)) {
|
||||
screen->loader_version = loader_version_temp;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (zink_debug & ZINK_DEBUG_VALIDATION) {
|
||||
printf("zink: Loader %d.%d.%d \n", VK_VERSION_MAJOR(screen->loader_version), VK_VERSION_MINOR(screen->loader_version), VK_VERSION_PATCH(screen->loader_version));
|
||||
}
|
||||
|
||||
if (VK_MAKE_VERSION(1,1,0) <= screen->loader_version) {
|
||||
// Get Vk 1.1+ Instance functions
|
||||
GET_PROC_ADDR_INSTANCE(GetPhysicalDeviceFeatures2);
|
||||
GET_PROC_ADDR_INSTANCE(GetPhysicalDeviceProperties2);
|
||||
} else
|
||||
if (screen->have_physical_device_prop2_ext) {
|
||||
// Not Vk 1.1+ so if VK_KHR_get_physical_device_properties2 the use it
|
||||
GET_PROC_ADDR_INSTANCE_LOCAL(screen->instance, GetPhysicalDeviceFeatures2KHR);
|
||||
GET_PROC_ADDR_INSTANCE_LOCAL(screen->instance, GetPhysicalDeviceProperties2KHR);
|
||||
screen->vk_GetPhysicalDeviceFeatures2 = vk_GetPhysicalDeviceFeatures2KHR;
|
||||
screen->vk_GetPhysicalDeviceProperties2 = vk_GetPhysicalDeviceProperties2KHR;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool
|
||||
load_device_extensions(struct zink_screen *screen)
|
||||
{
|
||||
|
|
@ -1041,7 +1078,10 @@ zink_internal_create_screen(struct sw_winsys *winsys, int fd, const struct pipe_
|
|||
zink_debug = debug_get_option_zink_debug();
|
||||
|
||||
screen->instance = create_instance(screen);
|
||||
if(!screen->instance)
|
||||
if (!screen->instance)
|
||||
goto fail;
|
||||
|
||||
if (!load_instance_extensions(screen))
|
||||
goto fail;
|
||||
|
||||
if (screen->have_debug_utils_ext && !create_debug(screen))
|
||||
|
|
@ -1088,7 +1128,11 @@ zink_internal_create_screen(struct sw_winsys *winsys, int fd, const struct pipe_
|
|||
/* extensions don't have bool members in pEnabledFeatures.
|
||||
* this requires us to pass the whole VkPhysicalDeviceFeatures2 struct
|
||||
*/
|
||||
dci.pNext = &screen->info.feats;
|
||||
if (screen->info.feats.sType == VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2) {
|
||||
dci.pNext = &screen->info.feats;
|
||||
} else {
|
||||
dci.pEnabledFeatures = &screen->info.feats.features;
|
||||
}
|
||||
|
||||
dci.ppEnabledExtensionNames = screen->info.extensions;
|
||||
dci.enabledExtensionCount = screen->info.num_extensions;
|
||||
|
|
|
|||
|
|
@ -64,11 +64,16 @@ struct zink_screen {
|
|||
VkDevice dev;
|
||||
VkDebugUtilsMessengerEXT debugUtilsCallbackHandle;
|
||||
|
||||
uint32_t loader_version;
|
||||
bool have_physical_device_prop2_ext;
|
||||
bool have_debug_utils_ext;
|
||||
#if defined(MVK_VERSION)
|
||||
bool have_moltenvk;
|
||||
#endif
|
||||
|
||||
PFN_vkGetPhysicalDeviceFeatures2 vk_GetPhysicalDeviceFeatures2;
|
||||
PFN_vkGetPhysicalDeviceProperties2 vk_GetPhysicalDeviceProperties2;
|
||||
|
||||
PFN_vkGetMemoryFdKHR vk_GetMemoryFdKHR;
|
||||
PFN_vkCmdBeginConditionalRenderingEXT vk_CmdBeginConditionalRenderingEXT;
|
||||
PFN_vkCmdEndConditionalRenderingEXT vk_CmdEndConditionalRenderingEXT;
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue