spirv_cross/
spirv.rs

1use crate::{compiler, ErrorCode};
2use std::marker::PhantomData;
3
4/// A stage or compute kernel.
5#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq)]
6pub struct CombinedImageSampler {
7    pub combined_id: u32,
8    pub image_id: u32,
9    pub sampler_id: u32,
10}
11
12/// A stage or compute kernel.
13#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq, Ord, PartialOrd)]
14pub enum ExecutionModel {
15    Vertex,
16    TessellationControl,
17    TessellationEvaluation,
18    Geometry,
19    Fragment,
20    GlCompute,
21    Kernel,
22}
23
24/// A decoration.
25#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq)]
26pub enum Decoration {
27    RelaxedPrecision,
28    SpecId,
29    Block,
30    BufferBlock,
31    RowMajor,
32    ColMajor,
33    ArrayStride,
34    MatrixStride,
35    GlslShared,
36    GlslPacked,
37    CPacked,
38    BuiltIn,
39    NoPerspective,
40    Flat,
41    Patch,
42    Centroid,
43    Sample,
44    Invariant,
45    Restrict,
46    Aliased,
47    Volatile,
48    Constant,
49    Coherent,
50    NonWritable,
51    NonReadable,
52    Uniform,
53    SaturatedConversion,
54    Stream,
55    Location,
56    Component,
57    Index,
58    Binding,
59    DescriptorSet,
60    Offset,
61    XfbBuffer,
62    XfbStride,
63    FuncParamAttr,
64    FpRoundingMode,
65    FpFastMathMode,
66    LinkageAttributes,
67    NoContraction,
68    InputAttachmentIndex,
69    Alignment,
70    OverrideCoverageNv,
71    PassthroughNv,
72    ViewportRelativeNv,
73    SecondaryViewportRelativeNv,
74}
75
76#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq)]
77pub enum VertexAttributeStep {
78    Vertex,
79    Instance,
80}
81
82#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq)]
83pub enum BuiltIn {
84    Position,
85    PointSize,
86    ClipDistance,
87    CullDistance,
88    VertexId,
89    InstanceId,
90    PrimitiveId,
91    InvocationId,
92    Layer,
93    ViewportIndex,
94    TessLevelOuter,
95    TessLevelInner,
96    TessCoord,
97    PatchVertices,
98    FragCoord,
99    PointCoord,
100    FrontFacing,
101    SampleId,
102    SamplePosition,
103    SampleMask,
104    FragDepth,
105    HelperInvocation,
106    NumWorkgroups,
107    WorkgroupSize,
108    WorkgroupId,
109    LocalInvocationId,
110    GlobalInvocationId,
111    LocalInvocationIndex,
112    WorkDim,
113    GlobalSize,
114    EnqueuedWorkgroupSize,
115    GlobalOffset,
116    GlobalLinearId,
117    SubgroupSize,
118    SubgroupMaxSize,
119    NumSubgroups,
120    NumEnqueuedSubgroups,
121    SubgroupId,
122    SubgroupLocalInvocationId,
123    VertexIndex,
124    InstanceIndex,
125    SubgroupEqMask,
126    SubgroupGeMask,
127    SubgroupGtMask,
128    SubgroupLeMask,
129    SubgroupLtMask,
130    BaseVertex,
131    BaseInstance,
132    DrawIndex,
133    DeviceIndex,
134    ViewIndex,
135    BaryCoordNoPerspAmd,
136    BaryCoordNoPerspCentroidAmd,
137    BaryCoordNoPerspSampleAmd,
138    BaryCoordSmoothAmd,
139    BaryCoordSmoothCentroidAmd,
140    BaryCoordSmoothSampleAmd,
141    BaryCoordPullModelAmd,
142    FragStencilRefExt,
143    ViewportMaskNv,
144    SecondaryPositionNv,
145    SecondaryViewportMaskNv,
146    PositionPerViewNv,
147    ViewportMaskPerViewNv,
148    FullyCoveredExt,
149    TaskCountNv,
150    PrimitiveCountNv,
151    PrimitiveIndicesNv,
152    ClipDistancePerViewNv,
153    CullDistancePerViewNv,
154    LayerPerViewNv,
155    MeshViewCountNv,
156    MeshViewIndicesNv,
157    BaryCoordNv,
158    BaryCoordNoPerspNv,
159    FragSizeExt,
160    FragInvocationCountExt,
161    LaunchIdNv,
162    LaunchSizeNv,
163    WorldRayOriginNv,
164    WorldRayDirectionNv,
165    ObjectRayOriginNv,
166    ObjectRayDirectionNv,
167    RayTminNv,
168    RayTmaxNv,
169    InstanceCustomIndexNv,
170    ObjectToWorldNv,
171    WorldToObjectNv,
172    HitTNv,
173    HitKindNv,
174    IncomingRayFlagsNv,
175}
176
177#[cfg(feature = "msl")]
178pub(crate) fn built_in_as_raw(built_in: Option<BuiltIn>) -> crate::bindings::spv::BuiltIn {
179    use crate::bindings as br;
180    use BuiltIn::*;
181    match built_in {
182        None => br::spv::BuiltIn::BuiltInMax,
183        Some(Position) => br::spv::BuiltIn::BuiltInPosition,
184        Some(PointSize) => br::spv::BuiltIn::BuiltInPointSize,
185        Some(ClipDistance) => br::spv::BuiltIn::BuiltInClipDistance,
186        Some(CullDistance) => br::spv::BuiltIn::BuiltInCullDistance,
187        Some(VertexId) => br::spv::BuiltIn::BuiltInVertexId,
188        Some(InstanceId) => br::spv::BuiltIn::BuiltInInstanceId,
189        Some(PrimitiveId) => br::spv::BuiltIn::BuiltInPrimitiveId,
190        Some(InvocationId) => br::spv::BuiltIn::BuiltInInvocationId,
191        Some(Layer) => br::spv::BuiltIn::BuiltInLayer,
192        Some(ViewportIndex) => br::spv::BuiltIn::BuiltInViewportIndex,
193        Some(TessLevelOuter) => br::spv::BuiltIn::BuiltInTessLevelOuter,
194        Some(TessLevelInner) => br::spv::BuiltIn::BuiltInTessLevelInner,
195        Some(TessCoord) => br::spv::BuiltIn::BuiltInTessCoord,
196        Some(PatchVertices) => br::spv::BuiltIn::BuiltInPatchVertices,
197        Some(FragCoord) => br::spv::BuiltIn::BuiltInFragCoord,
198        Some(PointCoord) => br::spv::BuiltIn::BuiltInPointCoord,
199        Some(FrontFacing) => br::spv::BuiltIn::BuiltInFrontFacing,
200        Some(SampleId) => br::spv::BuiltIn::BuiltInSampleId,
201        Some(SamplePosition) => br::spv::BuiltIn::BuiltInSamplePosition,
202        Some(SampleMask) => br::spv::BuiltIn::BuiltInSampleMask,
203        Some(FragDepth) => br::spv::BuiltIn::BuiltInFragDepth,
204        Some(HelperInvocation) => br::spv::BuiltIn::BuiltInHelperInvocation,
205        Some(NumWorkgroups) => br::spv::BuiltIn::BuiltInNumWorkgroups,
206        Some(WorkgroupSize) => br::spv::BuiltIn::BuiltInWorkgroupSize,
207        Some(WorkgroupId) => br::spv::BuiltIn::BuiltInWorkgroupId,
208        Some(LocalInvocationId) => br::spv::BuiltIn::BuiltInLocalInvocationId,
209        Some(GlobalInvocationId) => br::spv::BuiltIn::BuiltInGlobalInvocationId,
210        Some(LocalInvocationIndex) => br::spv::BuiltIn::BuiltInLocalInvocationIndex,
211        Some(WorkDim) => br::spv::BuiltIn::BuiltInWorkDim,
212        Some(GlobalSize) => br::spv::BuiltIn::BuiltInGlobalSize,
213        Some(EnqueuedWorkgroupSize) => br::spv::BuiltIn::BuiltInEnqueuedWorkgroupSize,
214        Some(GlobalOffset) => br::spv::BuiltIn::BuiltInGlobalOffset,
215        Some(GlobalLinearId) => br::spv::BuiltIn::BuiltInGlobalLinearId,
216        Some(SubgroupSize) => br::spv::BuiltIn::BuiltInSubgroupSize,
217        Some(SubgroupMaxSize) => br::spv::BuiltIn::BuiltInSubgroupMaxSize,
218        Some(NumSubgroups) => br::spv::BuiltIn::BuiltInNumSubgroups,
219        Some(NumEnqueuedSubgroups) => br::spv::BuiltIn::BuiltInNumEnqueuedSubgroups,
220        Some(SubgroupId) => br::spv::BuiltIn::BuiltInSubgroupId,
221        Some(SubgroupLocalInvocationId) => br::spv::BuiltIn::BuiltInSubgroupLocalInvocationId,
222        Some(VertexIndex) => br::spv::BuiltIn::BuiltInVertexIndex,
223        Some(InstanceIndex) => br::spv::BuiltIn::BuiltInInstanceIndex,
224        Some(SubgroupEqMask) => br::spv::BuiltIn::BuiltInSubgroupEqMask,
225        Some(SubgroupGeMask) => br::spv::BuiltIn::BuiltInSubgroupGeMask,
226        Some(SubgroupGtMask) => br::spv::BuiltIn::BuiltInSubgroupGtMask,
227        Some(SubgroupLeMask) => br::spv::BuiltIn::BuiltInSubgroupLeMask,
228        Some(SubgroupLtMask) => br::spv::BuiltIn::BuiltInSubgroupLtMask,
229        Some(BaseVertex) => br::spv::BuiltIn::BuiltInBaseVertex,
230        Some(BaseInstance) => br::spv::BuiltIn::BuiltInBaseInstance,
231        Some(DrawIndex) => br::spv::BuiltIn::BuiltInDrawIndex,
232        Some(DeviceIndex) => br::spv::BuiltIn::BuiltInDeviceIndex,
233        Some(ViewIndex) => br::spv::BuiltIn::BuiltInViewIndex,
234        Some(BaryCoordNoPerspAmd) => br::spv::BuiltIn::BuiltInBaryCoordNoPerspAMD,
235        Some(BaryCoordNoPerspCentroidAmd) => br::spv::BuiltIn::BuiltInBaryCoordNoPerspCentroidAMD,
236        Some(BaryCoordNoPerspSampleAmd) => br::spv::BuiltIn::BuiltInBaryCoordNoPerspSampleAMD,
237        Some(BaryCoordSmoothAmd) => br::spv::BuiltIn::BuiltInBaryCoordSmoothAMD,
238        Some(BaryCoordSmoothCentroidAmd) => br::spv::BuiltIn::BuiltInBaryCoordSmoothCentroidAMD,
239        Some(BaryCoordSmoothSampleAmd) => br::spv::BuiltIn::BuiltInBaryCoordSmoothSampleAMD,
240        Some(BaryCoordPullModelAmd) => br::spv::BuiltIn::BuiltInBaryCoordPullModelAMD,
241        Some(FragStencilRefExt) => br::spv::BuiltIn::BuiltInFragStencilRefEXT,
242        Some(ViewportMaskNv) => br::spv::BuiltIn::BuiltInViewportMaskNV,
243        Some(SecondaryPositionNv) => br::spv::BuiltIn::BuiltInSecondaryPositionNV,
244        Some(SecondaryViewportMaskNv) => br::spv::BuiltIn::BuiltInSecondaryViewportMaskNV,
245        Some(PositionPerViewNv) => br::spv::BuiltIn::BuiltInPositionPerViewNV,
246        Some(ViewportMaskPerViewNv) => br::spv::BuiltIn::BuiltInViewportMaskPerViewNV,
247        Some(FullyCoveredExt) => br::spv::BuiltIn::BuiltInFullyCoveredEXT,
248        Some(TaskCountNv) => br::spv::BuiltIn::BuiltInTaskCountNV,
249        Some(PrimitiveCountNv) => br::spv::BuiltIn::BuiltInPrimitiveCountNV,
250        Some(PrimitiveIndicesNv) => br::spv::BuiltIn::BuiltInPrimitiveIndicesNV,
251        Some(ClipDistancePerViewNv) => br::spv::BuiltIn::BuiltInClipDistancePerViewNV,
252        Some(CullDistancePerViewNv) => br::spv::BuiltIn::BuiltInCullDistancePerViewNV,
253        Some(LayerPerViewNv) => br::spv::BuiltIn::BuiltInLayerPerViewNV,
254        Some(MeshViewCountNv) => br::spv::BuiltIn::BuiltInMeshViewCountNV,
255        Some(MeshViewIndicesNv) => br::spv::BuiltIn::BuiltInMeshViewIndicesNV,
256        Some(BaryCoordNv) => br::spv::BuiltIn::BuiltInBaryCoordNV,
257        Some(BaryCoordNoPerspNv) => br::spv::BuiltIn::BuiltInBaryCoordNoPerspNV,
258        Some(FragSizeExt) => br::spv::BuiltIn::BuiltInFragSizeEXT,
259        Some(FragInvocationCountExt) => br::spv::BuiltIn::BuiltInFragInvocationCountEXT,
260        Some(LaunchIdNv) => br::spv::BuiltIn::BuiltInLaunchIdNV,
261        Some(LaunchSizeNv) => br::spv::BuiltIn::BuiltInLaunchSizeNV,
262        Some(WorldRayOriginNv) => br::spv::BuiltIn::BuiltInWorldRayOriginNV,
263        Some(WorldRayDirectionNv) => br::spv::BuiltIn::BuiltInWorldRayDirectionNV,
264        Some(ObjectRayOriginNv) => br::spv::BuiltIn::BuiltInObjectRayOriginNV,
265        Some(ObjectRayDirectionNv) => br::spv::BuiltIn::BuiltInObjectRayDirectionNV,
266        Some(RayTminNv) => br::spv::BuiltIn::BuiltInRayTminNV,
267        Some(RayTmaxNv) => br::spv::BuiltIn::BuiltInRayTmaxNV,
268        Some(InstanceCustomIndexNv) => br::spv::BuiltIn::BuiltInInstanceCustomIndexNV,
269        Some(ObjectToWorldNv) => br::spv::BuiltIn::BuiltInObjectToWorldNV,
270        Some(WorldToObjectNv) => br::spv::BuiltIn::BuiltInWorldToObjectNV,
271        Some(HitTNv) => br::spv::BuiltIn::BuiltInHitTNV,
272        Some(HitKindNv) => br::spv::BuiltIn::BuiltInHitKindNV,
273        Some(IncomingRayFlagsNv) => br::spv::BuiltIn::BuiltInIncomingRayFlagsNV,
274    }
275}
276
277/// A work group size.
278#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq)]
279pub struct WorkGroupSize {
280    pub x: u32,
281    pub y: u32,
282    pub z: u32,
283}
284
285/// An entry point for a SPIR-V module.
286#[derive(Clone, Debug, Hash, Eq, PartialEq)]
287pub struct EntryPoint {
288    pub name: String,
289    pub execution_model: ExecutionModel,
290    pub work_group_size: WorkGroupSize,
291}
292
293/// Description of struct member's range.
294#[derive(Clone, Debug, Hash, Eq, PartialEq)]
295pub struct BufferRange {
296    /// An index. Useful for passing to `get_member_name` and `get_member_decoration`.
297    pub index: u32,
298    /// Bytes from start of buffer not beginning of struct.
299    pub offset: usize,
300    /// Size of field in bytes.
301    pub range: usize,
302}
303
304/// A resource.
305#[derive(Clone, Debug, Hash, Eq, PartialEq)]
306pub struct Resource {
307    pub id: u32,
308    pub type_id: u32,
309    pub base_type_id: u32,
310    pub name: String,
311}
312
313/// Specialization constant reference.
314#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq)]
315pub struct SpecializationConstant {
316    pub id: u32,
317    pub constant_id: u32,
318}
319
320/// Work group size specialization constants.
321#[derive(Copy, Clone, Debug, Hash, Eq, PartialEq)]
322pub struct WorkGroupSizeSpecializationConstants {
323    pub x: SpecializationConstant,
324    pub y: SpecializationConstant,
325    pub z: SpecializationConstant,
326}
327
328/// Shader resources.
329#[derive(Debug, Clone)]
330pub struct ShaderResources {
331    pub uniform_buffers: Vec<Resource>,
332    pub storage_buffers: Vec<Resource>,
333    pub stage_inputs: Vec<Resource>,
334    pub stage_outputs: Vec<Resource>,
335    pub subpass_inputs: Vec<Resource>,
336    pub storage_images: Vec<Resource>,
337    pub sampled_images: Vec<Resource>,
338    pub atomic_counters: Vec<Resource>,
339    pub push_constant_buffers: Vec<Resource>,
340    pub separate_images: Vec<Resource>,
341    pub separate_samplers: Vec<Resource>,
342}
343
344#[derive(Debug, Clone)]
345#[non_exhaustive]
346pub enum Type {
347    // TODO: Add missing fields to relevant variants from SPIRType
348    Unknown,
349    Void,
350    Boolean {
351        vecsize: u32,
352        columns: u32,
353        array: Vec<u32>,
354    },
355    Char {
356        array: Vec<u32>,
357    },
358    Int {
359        vecsize: u32,
360        columns: u32,
361        array: Vec<u32>,
362    },
363    UInt {
364        vecsize: u32,
365        columns: u32,
366        array: Vec<u32>,
367    },
368    Int64 {
369        vecsize: u32,
370        array: Vec<u32>,
371    },
372    UInt64 {
373        vecsize: u32,
374        array: Vec<u32>,
375    },
376    AtomicCounter {
377        array: Vec<u32>,
378    },
379    Half {
380        vecsize: u32,
381        columns: u32,
382        array: Vec<u32>,
383    },
384    Float {
385        vecsize: u32,
386        columns: u32,
387        array: Vec<u32>,
388    },
389    Double {
390        vecsize: u32,
391        columns: u32,
392        array: Vec<u32>,
393    },
394    Struct {
395        member_types: Vec<u32>,
396        array: Vec<u32>,
397    },
398    Image {
399        array: Vec<u32>,
400    },
401    SampledImage {
402        array: Vec<u32>,
403    },
404    Sampler {
405        array: Vec<u32>,
406    },
407    SByte {
408        vecsize: u32,
409        array: Vec<u32>,
410    },
411    UByte {
412        vecsize: u32,
413        array: Vec<u32>,
414    },
415    Short {
416        vecsize: u32,
417        array: Vec<u32>,
418    },
419    UShort {
420        vecsize: u32,
421        array: Vec<u32>,
422    },
423    ControlPointArray,
424    AccelerationStructure,
425    RayQuery,
426    Interpolant,
427}
428
429/// A SPIR-V shader module.
430#[derive(Debug, Clone)]
431pub struct Module<'a> {
432    pub(crate) words: &'a [u32],
433}
434
435impl<'a> Module<'a> {
436    /// Creates a shader module from SPIR-V words.
437    pub fn from_words(words: &[u32]) -> Module {
438        Module { words }
439    }
440}
441
442pub trait Target {
443    type Data;
444}
445
446/// An abstract syntax tree that corresponds to a SPIR-V module.
447pub struct Ast<TTarget>
448where
449    TTarget: Target,
450{
451    pub(crate) compiler: compiler::Compiler<TTarget::Data>,
452    pub(crate) target_type: PhantomData<TTarget>,
453}
454
455pub trait Parse<TTarget>: Sized {
456    fn parse(module: &Module) -> Result<Self, ErrorCode>;
457}
458
459pub trait Compile<TTarget> {
460    type CompilerOptions;
461
462    fn set_compiler_options(
463        &mut self,
464        compiler_options: &Self::CompilerOptions,
465    ) -> Result<(), ErrorCode>;
466    fn compile(&mut self) -> Result<String, ErrorCode>;
467}
468
469impl<TTarget> Ast<TTarget>
470where
471    Self: Parse<TTarget> + Compile<TTarget>,
472    TTarget: Target,
473{
474    /// Gets a decoration.
475    pub fn get_decoration(&self, id: u32, decoration: Decoration) -> Result<u32, ErrorCode> {
476        self.compiler.get_decoration(id, decoration)
477    }
478
479    /// Gets a name. If not defined, an empty string will be returned.
480    pub fn get_name(&mut self, id: u32) -> Result<String, ErrorCode> {
481        self.compiler.get_name(id)
482    }
483
484    /// Sets a name.
485    pub fn set_name(&mut self, id: u32, name: &str) -> Result<(), ErrorCode> {
486        self.compiler.set_name(id, name)
487    }
488
489    /// Unsets a decoration.
490    pub fn unset_decoration(&mut self, id: u32, decoration: Decoration) -> Result<(), ErrorCode> {
491        self.compiler.unset_decoration(id, decoration)
492    }
493
494    /// Sets a decoration.
495    pub fn set_decoration(
496        &mut self,
497        id: u32,
498        decoration: Decoration,
499        argument: u32,
500    ) -> Result<(), ErrorCode> {
501        self.compiler.set_decoration(id, decoration, argument)
502    }
503
504    /// Gets entry points.
505    pub fn get_entry_points(&self) -> Result<Vec<EntryPoint>, ErrorCode> {
506        self.compiler.get_entry_points()
507    }
508
509    /// Gets cleansed entry point names. `compile` must be called first.
510    pub fn get_cleansed_entry_point_name(
511        &self,
512        entry_point_name: &str,
513        execution_model: ExecutionModel,
514    ) -> Result<String, ErrorCode> {
515        if self.compiler.has_been_compiled {
516            self.compiler
517                .get_cleansed_entry_point_name(entry_point_name, execution_model)
518        } else {
519            Err(ErrorCode::CompilationError(String::from(
520                "`compile` must be called first",
521            )))
522        }
523    }
524
525    /// Gets active buffer ragnes.  Useful for push constants.
526    pub fn get_active_buffer_ranges(&self, id: u32) -> Result<Vec<BufferRange>, ErrorCode> {
527        self.compiler.get_active_buffer_ranges(id)
528    }
529
530    /// Gets all specialization constants.
531    pub fn get_specialization_constants(&self) -> Result<Vec<SpecializationConstant>, ErrorCode> {
532        self.compiler.get_specialization_constants()
533    }
534
535    /// Set reference of a scalar constant to a value, overriding the default.
536    ///
537    /// Can be used to override specialization constants.
538    pub fn set_scalar_constant(&mut self, id: u32, value: u64) -> Result<(), ErrorCode> {
539        self.compiler.set_scalar_constant(id, value)
540    }
541
542    /// Gets shader resources.
543    pub fn get_shader_resources(&self) -> Result<ShaderResources, ErrorCode> {
544        self.compiler.get_shader_resources()
545    }
546
547    /// Gets the SPIR-V type associated with an ID.
548    pub fn get_type(&self, id: u32) -> Result<Type, ErrorCode> {
549        self.compiler.get_type(id)
550    }
551
552    /// Gets the identifier for a member located at `index` within an `OpTypeStruct`.
553    pub fn get_member_name(&self, id: u32, index: u32) -> Result<String, ErrorCode> {
554        self.compiler.get_member_name(id, index)
555    }
556
557    /// Gets a decoration for a member located at `index` within an `OpTypeStruct`.
558    pub fn get_member_decoration(
559        &self,
560        id: u32,
561        index: u32,
562        decoration: Decoration,
563    ) -> Result<u32, ErrorCode> {
564        self.compiler.get_member_decoration(id, index, decoration)
565    }
566
567    /// Sets a decoration for a member located at `index` within an `OpTypeStruct`.
568    pub fn set_member_decoration(
569        &mut self,
570        id: u32,
571        index: u32,
572        decoration: Decoration,
573        argument: u32,
574    ) -> Result<(), ErrorCode> {
575        self.compiler
576            .set_member_decoration(id, index, decoration, argument)
577    }
578
579    /// Gets the effective size of a buffer block.
580    pub fn get_declared_struct_size(&self, id: u32) -> Result<u32, ErrorCode> {
581        self.compiler.get_declared_struct_size(id)
582    }
583
584    /// Gets the effective size of a buffer block struct member.
585    pub fn get_declared_struct_member_size(&self, id: u32, index: u32) -> Result<u32, ErrorCode> {
586        self.compiler.get_declared_struct_member_size(id, index)
587    }
588
589    /// Renames an interface variable.
590    pub fn rename_interface_variable(
591        &mut self,
592        resources: &[Resource],
593        location: u32,
594        name: &str,
595    ) -> Result<(), ErrorCode> {
596        self.compiler
597            .rename_interface_variable(resources, location, name)
598    }
599
600    /// Gets work group size specialization constants.
601    pub fn get_work_group_size_specialization_constants(
602        &self,
603    ) -> Result<WorkGroupSizeSpecializationConstants, ErrorCode> {
604        self.compiler.get_work_group_size_specialization_constants()
605    }
606
607    /// Parses a module into `Ast`.
608    pub fn parse(module: &Module) -> Result<Self, ErrorCode> {
609        Parse::<TTarget>::parse(&module)
610    }
611
612    /// Sets compile options.
613    pub fn set_compiler_options(
614        &mut self,
615        options: &<Self as Compile<TTarget>>::CompilerOptions,
616    ) -> Result<(), ErrorCode> {
617        Compile::<TTarget>::set_compiler_options(self, options)
618    }
619
620    /// Compiles an abstract syntax tree to a `String` in the specified `TTarget` language.
621    pub fn compile(&mut self) -> Result<String, ErrorCode> {
622        self.compiler.has_been_compiled = true;
623        Compile::<TTarget>::compile(self)
624    }
625}