Add a transfer queue to VulkanoContext (#2573)

* Add a transfer queue to `VulkanoContext`

* Might as well
This commit is contained in:
Rua 2024-10-15 20:42:15 +02:00 committed by GitHub
parent a270468960
commit 9c358806be
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

View File

@ -93,8 +93,7 @@ pub struct VulkanoContext {
instance: Arc<Instance>,
_debug_utils_messenger: Option<DebugUtilsMessenger>,
device: Arc<Device>,
graphics_queue: Arc<Queue>,
compute_queue: Arc<Queue>,
queues: Queues,
memory_allocator: Arc<StandardMemoryAllocator>,
}
@ -166,20 +165,18 @@ impl VulkanoContext {
}
// Create device
let (device, graphics_queue, compute_queue) = Self::create_device(
let (device, queues) = Self::create_device(
physical_device,
config.device_extensions,
config.device_features,
);
let memory_allocator = Arc::new(StandardMemoryAllocator::new_default(device.clone()));
Self {
instance,
_debug_utils_messenger,
device,
graphics_queue,
compute_queue,
queues,
memory_allocator,
}
}
@ -190,7 +187,7 @@ impl VulkanoContext {
physical_device: Arc<PhysicalDevice>,
device_extensions: DeviceExtensions,
device_features: DeviceFeatures,
) -> (Arc<Device>, Arc<Queue>, Arc<Queue>) {
) -> (Arc<Device>, Queues) {
let queue_family_graphics = physical_device
.queue_family_properties()
.iter()
@ -209,25 +206,37 @@ impl VulkanoContext {
q.queue_flags.intersects(QueueFlags::COMPUTE) && *i != queue_family_graphics
})
.map(|(i, _)| i);
let is_separate_compute_queue = queue_family_compute.is_some();
// Try finding a separate queue for transfer
let queue_family_transfer = physical_device
.queue_family_properties()
.iter()
.enumerate()
.map(|(i, q)| (i as u32, q))
.find(|(_i, q)| {
q.queue_flags.intersects(QueueFlags::TRANSFER)
&& !q
.queue_flags
.intersects(QueueFlags::GRAPHICS | QueueFlags::COMPUTE)
})
.map(|(i, _)| i);
let queue_create_infos = if let Some(queue_family_compute) = queue_family_compute {
vec![
QueueCreateInfo {
let queue_create_infos: Vec<_> = [
Some(QueueCreateInfo {
queue_family_index: queue_family_graphics,
..Default::default()
},
QueueCreateInfo {
queue_family_index: queue_family_compute,
}),
queue_family_compute.map(|queue_family_index| QueueCreateInfo {
queue_family_index,
..Default::default()
},
}),
queue_family_transfer.map(|queue_family_index| QueueCreateInfo {
queue_family_index,
..Default::default()
}),
]
} else {
vec![QueueCreateInfo {
queue_family_index: queue_family_graphics,
..Default::default()
}]
};
.into_iter()
.flatten()
.collect();
let (device, mut queues) = {
Device::new(
@ -241,13 +250,24 @@ impl VulkanoContext {
)
.expect("failed to create device")
};
let gfx_queue = queues.next().unwrap();
let compute_queue = if is_separate_compute_queue {
queues.next().unwrap()
} else {
gfx_queue.clone()
};
(device, gfx_queue, compute_queue)
let graphics_queue = queues.next().unwrap();
let compute_queue = queue_family_compute
.is_some()
.then(|| queues.next().unwrap())
.unwrap_or(graphics_queue.clone());
let transfer_queue = queue_family_transfer
.is_some()
.then(|| queues.next().unwrap());
(
device,
Queues {
graphics_queue,
compute_queue,
transfer_queue,
},
)
}
/// Returns the name of the device.
@ -286,15 +306,22 @@ impl VulkanoContext {
/// Returns the graphics queue.
#[inline]
pub fn graphics_queue(&self) -> &Arc<Queue> {
&self.graphics_queue
&self.queues.graphics_queue
}
/// Returns the compute queue.
///
/// Depending on your device, this might be the same as graphics queue.
/// Depending on your device, this might be the same as the graphics queue.
#[inline]
pub fn compute_queue(&self) -> &Arc<Queue> {
&self.compute_queue
&self.queues.compute_queue
}
/// Returns the transfer queue, if the device has a queue family that is dedicated for
/// transfers (does not support graphics or compute).
#[inline]
pub fn transfer_queue(&self) -> Option<&Arc<Queue>> {
self.queues.transfer_queue.as_ref()
}
/// Returns the memory allocator.
@ -303,3 +330,9 @@ impl VulkanoContext {
&self.memory_allocator
}
}
struct Queues {
graphics_queue: Arc<Queue>,
compute_queue: Arc<Queue>,
transfer_queue: Option<Arc<Queue>>,
}