spirv_tools/val/
compiled.rs

1use spirv_tools_sys::{shared, val};
2
3pub struct Options {
4    pub(crate) inner: *mut val::ValidatorOptions,
5}
6
7impl From<super::ValidatorOptions> for Options {
8    fn from(vo: super::ValidatorOptions) -> Self {
9        unsafe {
10            let inner = val::validator_options_create();
11
12            // This is AFAICT the only one that _can_ default to true based on our target
13            // so we treat it differently
14            if let Some(relax) = vo.relax_block_layout {
15                val::validator_options_set_relax_block_layout(inner, relax);
16            }
17
18            if vo.relax_struct_store {
19                val::validator_options_set_relax_store_struct(inner, true);
20            }
21
22            if vo.relax_logical_pointer {
23                val::validator_options_set_relax_logical_pointer(inner, true);
24            }
25
26            if vo.before_legalization {
27                val::validator_options_set_before_legalization(inner, true);
28            }
29
30            if vo.uniform_buffer_standard_layout {
31                val::validator_options_set_uniform_buffer_standard_layout(inner, true);
32            }
33
34            if vo.scalar_block_layout {
35                val::validator_options_set_scalar_block_layout(inner, true);
36            }
37
38            if vo.skip_block_layout {
39                val::validator_options_set_skip_block_layout(inner, true);
40            }
41
42            for (limit, val) in vo.max_limits {
43                val::validator_options_set_limit(inner, limit, val);
44            }
45
46            Self { inner }
47        }
48    }
49}
50
51impl Drop for Options {
52    fn drop(&mut self) {
53        unsafe { val::validator_options_destroy(self.inner) }
54    }
55}
56
57pub struct CompiledValidator {
58    inner: *mut shared::ToolContext,
59}
60
61use super::Validator;
62
63impl Validator for CompiledValidator {
64    fn with_env(target_env: crate::TargetEnv) -> Self {
65        Self {
66            inner: unsafe { shared::context_create(target_env) },
67        }
68    }
69
70    fn validate(
71        &self,
72        binary: impl AsRef<[u32]>,
73        options: Option<super::ValidatorOptions>,
74    ) -> Result<(), crate::error::Error> {
75        unsafe {
76            let mut diagnostic = std::ptr::null_mut();
77
78            let options = options.map(Options::from);
79
80            let binary = binary.as_ref();
81
82            let input = shared::Binary {
83                code: binary.as_ptr(),
84                size: binary.len(),
85            };
86
87            let res = match options {
88                Some(opts) => {
89                    val::validate_with_options(self.inner, opts.inner, &input, &mut diagnostic)
90                }
91                None => val::validate(self.inner, &input, &mut diagnostic),
92            };
93
94            let diagnostic = crate::error::Diagnostic::from_diag(diagnostic).ok();
95
96            match res {
97                shared::SpirvResult::Success => Ok(()),
98                other => Err(crate::error::Error {
99                    inner: other,
100                    diagnostic,
101                }),
102            }
103        }
104    }
105}
106
107impl Default for CompiledValidator {
108    fn default() -> Self {
109        Self::with_env(crate::TargetEnv::default())
110    }
111}
112
113impl Drop for CompiledValidator {
114    fn drop(&mut self) {
115        unsafe { shared::context_destroy(self.inner) }
116    }
117}