vulkan: use sync objects if possible
This commit is contained in:
parent
2ac3519f2d
commit
3d3132fe39
23 changed files with 535 additions and 86 deletions
|
|
@ -1,4 +1,5 @@
|
|||
use {
|
||||
crate::{eventfd_cache::EventfdError, video::drm::DrmError},
|
||||
ahash::{AHashMap, AHashSet},
|
||||
ash::{
|
||||
Entry, Instance, LoadingError,
|
||||
|
|
@ -6,9 +7,13 @@ use {
|
|||
vk::{
|
||||
self, API_VERSION_1_3, ApplicationInfo, Bool32, DebugUtilsMessageSeverityFlagsEXT,
|
||||
DebugUtilsMessageTypeFlagsEXT, DebugUtilsMessengerCallbackDataEXT,
|
||||
DebugUtilsMessengerCreateInfoEXT, DebugUtilsMessengerEXT, ExtensionProperties, FALSE,
|
||||
InstanceCreateInfo, LayerProperties, ValidationFeaturesEXT, api_version_major,
|
||||
api_version_minor, api_version_patch, api_version_variant,
|
||||
DebugUtilsMessengerCreateInfoEXT, DebugUtilsMessengerEXT, ExtensionProperties,
|
||||
ExternalSemaphoreFeatureFlags, ExternalSemaphoreHandleTypeFlags,
|
||||
ExternalSemaphoreProperties, FALSE, InstanceCreateInfo, LayerProperties,
|
||||
PhysicalDevice, PhysicalDeviceExternalSemaphoreInfo, PhysicalDeviceFeatures,
|
||||
PhysicalDeviceFeatures2, PhysicalDeviceTimelineSemaphoreFeatures, SemaphoreType,
|
||||
SemaphoreTypeCreateInfo, ValidationFeaturesEXT, api_version_major, api_version_minor,
|
||||
api_version_patch, api_version_variant,
|
||||
},
|
||||
},
|
||||
isnt::std_1::collections::IsntHashMapExt,
|
||||
|
|
@ -28,6 +33,7 @@ use {
|
|||
pub mod device;
|
||||
pub mod fence;
|
||||
pub mod sync;
|
||||
pub mod timeline_semaphore;
|
||||
|
||||
static VULKAN_ENTRY: Lazy<Result<Entry, Arc<LoadingError>>> =
|
||||
Lazy::new(|| unsafe { Entry::load() }.map_err(Arc::new));
|
||||
|
|
@ -53,6 +59,22 @@ pub enum VulkanCoreError {
|
|||
CreateFence(#[source] vk::Result),
|
||||
#[error("Could not export a sync file from a semaphore")]
|
||||
ExportSyncFile(#[source] vk::Result),
|
||||
#[error("Could not create a semaphore")]
|
||||
CreateSemaphore(#[source] vk::Result),
|
||||
#[error("Device does not support timeline semaphore export")]
|
||||
TimelineExportNotSupported,
|
||||
#[error("Could not export an opaque fd from a semaphore")]
|
||||
ExportTimelineSemaphore(#[source] vk::Result),
|
||||
#[error("Could not signal the timeline semaphore")]
|
||||
SignalSemaphore(#[source] vk::Result),
|
||||
#[error("Could not query last signaled sync obj point")]
|
||||
QueryLastSignaled(#[source] DrmError),
|
||||
#[error("Mapping between syncobj points and timeline semaphore points is unexpected")]
|
||||
UnsupportedPointMapping,
|
||||
#[error("Could not acquire an eventfd")]
|
||||
AcquireEventfd(#[source] EventfdError),
|
||||
#[error("Could not create a sync obj eventfd wait")]
|
||||
CreateSyncobjWait(#[source] DrmError),
|
||||
}
|
||||
|
||||
pub struct VulkanCoreInstance {
|
||||
|
|
@ -61,6 +83,13 @@ pub struct VulkanCoreInstance {
|
|||
debug_utils: debug_utils::Instance,
|
||||
messenger: DebugUtilsMessengerEXT,
|
||||
pub log_level: Level,
|
||||
pub validation: bool,
|
||||
}
|
||||
|
||||
pub struct VulkanDeviceFeatures {
|
||||
#[expect(dead_code)]
|
||||
pub features: PhysicalDeviceFeatures,
|
||||
pub semaphore_features: PhysicalDeviceTimelineSemaphoreFeatures<'static>,
|
||||
}
|
||||
|
||||
impl VulkanCoreInstance {
|
||||
|
|
@ -86,7 +115,8 @@ impl VulkanCoreInstance {
|
|||
let mut severity = DebugUtilsMessageSeverityFlagsEXT::empty()
|
||||
| DebugUtilsMessageSeverityFlagsEXT::ERROR
|
||||
| DebugUtilsMessageSeverityFlagsEXT::WARNING;
|
||||
if *VULKAN_VALIDATION {
|
||||
let validation = *VULKAN_VALIDATION;
|
||||
if validation {
|
||||
severity |= DebugUtilsMessageSeverityFlagsEXT::INFO
|
||||
| DebugUtilsMessageSeverityFlagsEXT::VERBOSE;
|
||||
}
|
||||
|
|
@ -110,7 +140,7 @@ impl VulkanCoreInstance {
|
|||
.application_info(&app_info)
|
||||
.push_next(&mut debug_info);
|
||||
let validation_layer_name = VALIDATION_LAYER.as_ptr();
|
||||
if *VULKAN_VALIDATION {
|
||||
if validation {
|
||||
if get_available_layers(entry)?.contains(VALIDATION_LAYER) {
|
||||
create_info =
|
||||
create_info.enabled_layer_names(slice::from_ref(&validation_layer_name));
|
||||
|
|
@ -146,8 +176,49 @@ impl VulkanCoreInstance {
|
|||
debug_utils,
|
||||
messenger,
|
||||
log_level,
|
||||
validation,
|
||||
})
|
||||
}
|
||||
|
||||
pub fn get_features(&self, phy_dev: PhysicalDevice) -> VulkanDeviceFeatures {
|
||||
let mut semaphore_features = PhysicalDeviceTimelineSemaphoreFeatures::default();
|
||||
let mut features = PhysicalDeviceFeatures2::default().push_next(&mut semaphore_features);
|
||||
unsafe {
|
||||
self.instance
|
||||
.get_physical_device_features2(phy_dev, &mut features);
|
||||
}
|
||||
VulkanDeviceFeatures {
|
||||
features: features.features,
|
||||
semaphore_features,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn supports_timeline_opaque_export(
|
||||
&self,
|
||||
phy_dev: PhysicalDevice,
|
||||
features: &VulkanDeviceFeatures,
|
||||
) -> bool {
|
||||
if features.semaphore_features.timeline_semaphore == vk::TRUE {
|
||||
return self.supports_semaphore_opaque_export(phy_dev);
|
||||
}
|
||||
false
|
||||
}
|
||||
|
||||
fn supports_semaphore_opaque_export(&self, phy_dev: PhysicalDevice) -> bool {
|
||||
let mut props = ExternalSemaphoreProperties::default();
|
||||
let mut type_info =
|
||||
SemaphoreTypeCreateInfo::default().semaphore_type(SemaphoreType::TIMELINE);
|
||||
let info = PhysicalDeviceExternalSemaphoreInfo::default()
|
||||
.handle_type(ExternalSemaphoreHandleTypeFlags::OPAQUE_FD)
|
||||
.push_next(&mut type_info);
|
||||
unsafe {
|
||||
self.instance
|
||||
.get_physical_device_external_semaphore_properties(phy_dev, &info, &mut props);
|
||||
}
|
||||
props
|
||||
.external_semaphore_features
|
||||
.contains(ExternalSemaphoreFeatureFlags::EXPORTABLE)
|
||||
}
|
||||
}
|
||||
|
||||
impl Drop for VulkanCoreInstance {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue