1use std::process::Command;
2
3#[derive(Default)]
4pub struct ToolValidator {
5 target_env: crate::TargetEnv,
6}
7
8use super::Validator;
9
10impl Validator for ToolValidator {
11 fn with_env(target_env: crate::TargetEnv) -> Self {
12 Self { target_env }
13 }
14
15 fn validate(
16 &self,
17 binary: impl AsRef<[u32]>,
18 options: Option<super::ValidatorOptions>,
19 ) -> Result<(), crate::error::Error> {
20 let mut cmd = Command::new("spirv-val");
21
22 cmd.arg("--target-env").arg(self.target_env.to_string());
23
24 if let Some(opts) = options {
25 add_limits(&mut cmd, &opts.max_limits);
29 add_options(&mut cmd, opts);
30 }
31
32 let input = crate::binary::from_binary(binary.as_ref());
33
34 crate::cmd::exec(cmd, Some(input), crate::cmd::Output::Ignore)?;
35 Ok(())
36 }
37}
38
39pub(crate) fn add_options(cmd: &mut Command, opts: super::ValidatorOptions) {
40 if opts.relax_logical_pointer {
41 cmd.arg("--relax-logical-pointer");
42 }
43
44 if let Some(true) = opts.relax_block_layout {
45 cmd.arg("--relax-block-layout");
46 }
47
48 if opts.uniform_buffer_standard_layout {
49 cmd.arg("--uniform-buffer-standard-layout");
50 }
51
52 if opts.scalar_block_layout {
53 cmd.arg("--scalar-block-layout");
54 }
55
56 if opts.skip_block_layout {
57 cmd.arg("--skip-block-layout");
58 }
59
60 if opts.relax_struct_store {
61 cmd.arg("--relax-struct-store");
62 }
63
64 if opts.before_legalization {
65 cmd.arg("--before-hlsl-legalization");
66 }
67}
68
69fn add_limits(cmd: &mut Command, limits: &[(spirv_tools_sys::val::ValidatorLimits, u32)]) {
70 use spirv_tools_sys::val::ValidatorLimits;
71
72 for (limit, val) in limits {
73 cmd.arg(format!(
74 "--max-{}={}",
75 match limit {
76 ValidatorLimits::StructMembers => "struct-members",
77 ValidatorLimits::StructDepth => "struct-depth",
78 ValidatorLimits::LocalVariables => "local-variables",
79 ValidatorLimits::GlobalVariables => "global-variables",
80 ValidatorLimits::SwitchBranches => "switch-branches",
81 ValidatorLimits::FunctionArgs => "function-args",
82 ValidatorLimits::ControlFlowNestingDepth => "control-flow-nesting-depth",
83 ValidatorLimits::AccessChainIndexes => "access-chain-indexes",
84 ValidatorLimits::IdBound => "id-bound",
85 },
86 val
87 ));
88 }
89}