diff options
Diffstat (limited to 'src/command_buffer/validity/dispatch.rs')
-rw-r--r-- | src/command_buffer/validity/dispatch.rs | 88 |
1 files changed, 88 insertions, 0 deletions
diff --git a/src/command_buffer/validity/dispatch.rs b/src/command_buffer/validity/dispatch.rs new file mode 100644 index 0000000..297c1f6 --- /dev/null +++ b/src/command_buffer/validity/dispatch.rs @@ -0,0 +1,88 @@ +// Copyright (c) 2017 The vulkano developers +// Licensed under the Apache License, Version 2.0 +// <LICENSE-APACHE or +// https://www.apache.org/licenses/LICENSE-2.0> or the MIT +// license <LICENSE-MIT or https://opensource.org/licenses/MIT>, +// at your option. All files in the project carrying such +// notice may not be copied, modified, or distributed except +// according to those terms. + +use std::error; +use std::fmt; + +use crate::device::Device; + +/// Checks whether the dispatch dimensions are supported by the device. +pub fn check_dispatch(device: &Device, dimensions: [u32; 3]) -> Result<(), CheckDispatchError> { + let max = device + .physical_device() + .properties() + .max_compute_work_group_count; + + if dimensions[0] > max[0] || dimensions[1] > max[1] || dimensions[2] > max[2] { + return Err(CheckDispatchError::UnsupportedDimensions { + requested: dimensions, + max_supported: max, + }); + } + + Ok(()) +} + +/// Error that can happen when checking dispatch command validity. +#[derive(Debug, Copy, Clone)] +pub enum CheckDispatchError { + /// The dimensions are too large for the device's limits. + UnsupportedDimensions { + /// The requested dimensions. + requested: [u32; 3], + /// The actual supported dimensions. + max_supported: [u32; 3], + }, +} + +impl error::Error for CheckDispatchError {} + +impl fmt::Display for CheckDispatchError { + #[inline] + fn fmt(&self, fmt: &mut fmt::Formatter) -> Result<(), fmt::Error> { + write!( + fmt, + "{}", + match *self { + CheckDispatchError::UnsupportedDimensions { .. } => { + "the dimensions are too large for the device's limits" + } + } + ) + } +} + +#[cfg(test)] +mod tests { + use crate::command_buffer::validity; + + #[test] + fn max_checked() { + let (device, _) = gfx_dev_and_queue!(); + + let attempted = [u32::MAX, u32::MAX, u32::MAX]; + + // Just in case the device is some kind of software implementation. + if device + .physical_device() + .properties() + .max_compute_work_group_count + == attempted + { + return; + } + + match validity::check_dispatch(&device, attempted) { + Err(validity::CheckDispatchError::UnsupportedDimensions { requested, .. }) => { + assert_eq!(requested, attempted); + } + _ => panic!(), + } + } +} |