Vulkan-Docs/appendices/spirvenv.txt
Jon Leech 26f0bdbf1e Change log for March 5, 2018 Vulkan 1.1.72 spec update:
* Update release number to 72.

Github Issues:

  * Restructure the repository to put the specification `Makefile` and
    associated spec source material at the top level, `vk.xml` and
    associated scripts material in `xml/`, and generated include and source
    files in `include/vulkan/` and `src/ext_loader/`, respectively (public
    issue 436).
  * Add missing bullet point markup to flink:vkCmdCopyImage valid usage
    statement, so it gets a VUID assigned (public issue 627).
  * Fix broken links in a couple of extension appendices (public pull
    request 665).
  * Add the \<platform> tag to the index in section 4.1 of the registry
    schema documentation, and add the protect= attribute of \<extension>
    tags to the comments in `registry.rnc` (public issues 673, 678).
  * Add missing valid usage statements for sparse image interactions to
    flink:VkImageCreateInfo (public pull request 675).
  * Fix improper usage and grammar of "`can: not`" (public pull request
    681).
  * Remove duplicate spec language and NOTE on present layout between the
    flink:vkAcquireNextImageKHR and flink:vkAcquireNextImage2KHR commands
    (public pull request 685).
  * Fix some typos and markup issues (public pull request 689; public issues
    642, 667, 687).
  * Fix typo etext:VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_FENCE_FD_BIT ->
    ename:VK_EXTERNAL_SEMAPHORE_HANDLE_TYPE_SYNC_FD_BIT in the
    <<external-semaphore-handle-types-compatibility, External semaphore
    handle types compatibility>> table (public pull request 691).

Internal Issues:

  * Remove the need for the "`noautovalidity`" attribute on extension
    structures in `vk.xml`. It is now implied by the "`structextends`"
    attribute instead (internal issue 942).
  * Replace uses of "`currently bound`" with "`bound`", since "`currently`"
    is redundant and distracting, and add a corresponding rule to the style
    guide (internal issue 993).
  * Fixed subtle issues with the last updates to flink:vkAcquireNextImageKHR
    language that had resulted in ambiguities (internal issue 1178).
  * Make it clear that only one query of a given type is allowed at a time
    by reordering valid usage statements for flink:vkCmdBeginQuery and
    flink:vkCmdEndQuery, and removing redundant ones (internal issue 1213).
  * Swapped OL1 and OL3 in `tessparamUL.svg` to match previous version, and
    fixed where "`(no edge)`" appears (internal issue 1215).

Other Issues:

  * Fixed a minor problem with the valid usage statement extraction script,
    and corresponding markup in the spec source.

New Extensions:

  * `VK_AMD_shader_core_properties`
  * `VK_EXT_descriptor_indexing`
  * `VK_NV_shader_subgroup_partitioned`
2018-04-05 04:24:56 -07:00

612 lines
31 KiB
Plaintext

// Copyright (c) 2015-2018 Khronos Group. This work is licensed under a
// Creative Commons Attribution 4.0 International License; see
// http://creativecommons.org/licenses/by/4.0/
[appendix]
[[spirvenv]]
= Vulkan Environment for SPIR-V
Shaders for Vulkan are defined by the <<spirv-spec,Khronos SPIR-V
Specification>> as well as the <<spirv-extended,Khronos SPIR-V Extended
Instructions for GLSL>> Specification.
This appendix defines additional SPIR-V requirements applying to Vulkan
shaders.
== Versions and Formats
ifdef::VK_VERSION_1_1[]
A Vulkan 1.1 implementation must: support the 1.0, 1.1, 1.2, and 1.3
versions of SPIR-V and the 1.0 version of the SPIR-V Extended Instructions
for GLSL.
endif::VK_VERSION_1_1[]
ifndef::VK_VERSION_1_1[]
A Vulkan 1.0 implementation must: support the 1.0 version of SPIR-V and the
1.0 version of the SPIR-V Extended Instructions for GLSL.
endif::VK_VERSION_1_1[]
A SPIR-V module passed into flink:vkCreateShaderModule is interpreted as a
series of 32-bit words in host endianness, with literal strings packed as
described in section 2.2 of the SPIR-V Specification.
The first few words of the SPIR-V module must: be a magic number and a
SPIR-V version number, as described in section 2.3 of the SPIR-V
Specification.
[[spirvenv-capabilities]]
== Capabilities
Implementations must: support the following capability operands declared by
code:OpCapability:
* code:Matrix
* code:Shader
* code:InputAttachment
* code:Sampled1D
* code:Image1D
* code:SampledBuffer
* code:ImageBuffer
* code:ImageQuery
* code:DerivativeControl
ifdef::VK_VERSION_1_1,VK_KHR_device_group[]
* code:DeviceGroup
endif::VK_VERSION_1_1,VK_KHR_device_group[]
ifdef::VK_VERSION_1_1,VK_KHR_multiview[]
* [[spirvenv-capabilities-multiview]] code:MultiView
endif::VK_VERSION_1_1,VK_KHR_multiview[]
If the implementation supports any of the optional: features described in
the <<features-features,Features>> chapter, then the capability operand(s)
corresponding to that feature must: also be supported.
[[spirvenv-capabilities-table]]
.List of optional: SPIR-V Capabilities and corresponding feature or extension names
[options="header"]
|====
| SPIR-V OpCapability | Vulkan feature or extension name
| code:Geometry | <<features-features-geometryShader,geometryShader>>
| code:Tessellation | <<features-features-tessellationShader,tessellationShader>>
| code:Float64 | <<features-features-shaderFloat64,shaderFloat64>>
| code:Int64 | <<features-features-shaderInt64,shaderInt64>>
| code:Int16 | <<features-features-shaderInt16,shaderInt16>>
| code:TessellationPointSize | <<features-features-shaderTessellationAndGeometryPointSize,shaderTessellationAndGeometryPointSize>>
| code:GeometryPointSize | <<features-features-shaderTessellationAndGeometryPointSize,shaderTessellationAndGeometryPointSize>>
| code:ImageGatherExtended | <<features-features-shaderImageGatherExtended,shaderImageGatherExtended>>
| code:StorageImageMultisample | <<features-features-shaderStorageImageMultisample,shaderStorageImageMultisample>>
| code:UniformBufferArrayDynamicIndexing | <<features-features-shaderUniformBufferArrayDynamicIndexing,shaderUniformBufferArrayDynamicIndexing>>
| code:SampledImageArrayDynamicIndexing | <<features-features-shaderSampledImageArrayDynamicIndexing,shaderSampledImageArrayDynamicIndexing>>
| code:StorageBufferArrayDynamicIndexing | <<features-features-shaderStorageBufferArrayDynamicIndexing,shaderStorageBufferArrayDynamicIndexing>>
| code:StorageImageArrayDynamicIndexing | <<features-features-shaderStorageImageArrayDynamicIndexing,shaderStorageImageArrayDynamicIndexing>>
| code:ClipDistance | <<features-features-shaderClipDistance,shaderClipDistance>>
| code:CullDistance | <<features-features-shaderCullDistance,shaderCullDistance>>
| code:ImageCubeArray | <<features-features-imageCubeArray,imageCubeArray>>
| code:SampleRateShading | <<features-features-sampleRateShading,sampleRateShading>>
| code:SparseResidency | <<features-features-shaderResourceResidency,shaderResourceResidency>>
| code:MinLod | <<features-features-shaderResourceMinLod,shaderResourceMinLod>>
| code:SampledCubeArray | <<features-features-imageCubeArray,imageCubeArray>>
| code:ImageMSArray | <<features-features-shaderStorageImageMultisample,shaderStorageImageMultisample>>
| code:StorageImageExtendedFormats | <<features-features-shaderStorageImageExtendedFormats,shaderStorageImageExtendedFormats>>
| code:InterpolationFunction | <<features-features-sampleRateShading,sampleRateShading>>
| code:StorageImageReadWithoutFormat | <<features-features-shaderStorageImageReadWithoutFormat,shaderStorageImageReadWithoutFormat>>
| code:StorageImageWriteWithoutFormat | <<features-features-shaderStorageImageWriteWithoutFormat,shaderStorageImageWriteWithoutFormat>>
| code:MultiViewport | <<features-features-multiViewport,multiViewport>>
ifdef::VK_VERSION_1_1,VK_KHR_shader_draw_parameters[]
| code:DrawParameters
| `<<VK_KHR_shader_draw_parameters>>`
ifdef::VK_VERSION_1_1[]
or <<features-features-shaderDrawParameters,shaderDrawParameters>>
endif::VK_VERSION_1_1[]
endif::VK_VERSION_1_1,VK_KHR_shader_draw_parameters[]
ifndef::VK_VERSION_1_1[]
ifdef::VK_KHR_multiview[]
[[spirvenv-capabilities-multiview]]
| code:MultiView | <<VK_KHR_multiview,VK_KHR_multiview>>
endif::VK_KHR_multiview[]
ifdef::VK_KHR_device_group[]
| code:DeviceGroup | <<VK_KHR_device_group,VK_KHR_device_group>>
endif::VK_KHR_device_group[]
endif::VK_VERSION_1_1[]
ifdef::VK_VERSION_1_1,VK_KHR_variable_pointers[]
[[spirvenv-capabilities-table-variablepointers]]
| code:VariablePointersStorageBuffer | <<features-features-variablePointersStorageBuffer,variablePointersStorageBuffer>>
| code:VariablePointers | <<features-features-variablePointers,variablePointers>>
endif::VK_VERSION_1_1,VK_KHR_variable_pointers[]
ifdef::VK_EXT_shader_stencil_export[]
[[spirvenv-capabilities-table-shaderstencilexportext]]
| code:StencilExportEXT | `<<VK_EXT_shader_stencil_export>>`
endif::VK_EXT_shader_stencil_export[]
ifdef::VK_EXT_shader_subgroup_ballot[]
[[spirvenv-capabilities-table-subgroupballot]]
| code:SubgroupBallotKHR | `<<VK_EXT_shader_subgroup_ballot>>`
endif::VK_EXT_shader_subgroup_ballot[]
ifdef::VK_EXT_shader_subgroup_vote[]
[[spirvenv-capabilities-table-subgroupvote]]
| code:SubgroupVoteKHR | `<<VK_EXT_shader_subgroup_vote>>`
endif::VK_EXT_shader_subgroup_vote[]
ifdef::VK_AMD_shader_image_load_store_lod[]
[[spirvenv-capabilities-table-imagereadwritelodamd]]
| code:ImageReadWriteLodAMD | `<<VK_AMD_shader_image_load_store_lod>>`
endif::VK_AMD_shader_image_load_store_lod[]
ifdef::VK_AMD_texture_gather_bias_lod[]
[[spirvenv-capabilities-table-imagegatherbiaslodamd]]
| code:ImageGatherBiasLodAMD | `<<VK_AMD_texture_gather_bias_lod>>`
endif::VK_AMD_texture_gather_bias_lod[]
ifdef::VK_AMD_shader_fragment_mask[]
[[spirvenv-capabilities-table-fragmentmaskamd]]
| code:FragmentMaskAMD | `<<VK_AMD_shader_fragment_mask>>`
endif::VK_AMD_shader_fragment_mask[]
ifdef::VK_NV_sample_mask_override_coverage[]
[[spirvenv-capabilities-table-samplemaskoverridecoverage]]
| code:SampleMaskOverrideCoverageNV | `<<VK_NV_sample_mask_override_coverage>>`
endif::VK_NV_sample_mask_override_coverage[]
ifdef::VK_NV_geometry_shader_passthrough[]
[[spirvenv-capabilities-table-geometryshaderpassthrough]]
| code:GeometryShaderPassthroughNV | `<<VK_NV_geometry_shader_passthrough>>`
endif::VK_NV_geometry_shader_passthrough[]
ifdef::VK_EXT_shader_viewport_index_layer[]
[[spirvenv-capabilities-table-shader-viewport-index-layer]]
| code:ShaderViewportIndexLayerEXT | `<<VK_EXT_shader_viewport_index_layer>>`
endif::VK_EXT_shader_viewport_index_layer[]
ifdef::VK_NV_viewport_array2[]
[[spirvenv-capabilities-table-viewportarray2]]
| code:ShaderViewportIndexLayerNV | `<<VK_NV_viewport_array2>>`
| code:ShaderViewportMaskNV | `<<VK_NV_viewport_array2>>`
endif::VK_NV_viewport_array2[]
ifdef::VK_NVX_multiview_per_view_attributes[]
[[spirvenv-capabilities-table-perviewattributes]]
| code:PerViewAttributesNV | `<<VK_NVX_multiview_per_view_attributes>>`
endif::VK_NVX_multiview_per_view_attributes[]
ifdef::VK_VERSION_1_1,VK_KHR_16bit_storage[]
[[spirvenv-capabilities-table-16bitstorage]]
| code:StorageBuffer16BitAccess | <<features-features-storageBuffer16BitAccess, StorageBuffer16BitAccess>>
| code:UniformAndStorageBuffer16BitAccess | <<features-features-uniformAndStorageBuffer16BitAccess,UniformAndStorageBuffer16BitAccess>>
| code:StoragePushConstant16 | <<features-features-storagePushConstant16,storagePushConstant16>>
| code:StorageInputOutput16 | <<features-features-storageInputOutput16,storageInputOutput16>>
endif::VK_VERSION_1_1,VK_KHR_16bit_storage[]
ifdef::VK_VERSION_1_1[]
[[spirvenv-capabilities-table-subgroup]]
| code:GroupNonUniform | <<features-features-subgroup-basic,VK_SUBGROUP_FEATURE_BASIC_BIT>>
| code:GroupNonUniformVote | <<features-features-subgroup-vote,VK_SUBGROUP_FEATURE_VOTE_BIT>>
| code:GroupNonUniformArithmetic | <<features-features-subgroup-arithmetic,VK_SUBGROUP_FEATURE_ARITHMETIC_BIT>>
| code:GroupNonUniformBallot | <<features-features-subgroup-ballot,VK_SUBGROUP_FEATURE_BALLOT_BIT>>
| code:GroupNonUniformShuffle | <<features-features-subgroup-shuffle,VK_SUBGROUP_FEATURE_SHUFFLE_BIT>>
| code:GroupNonUniformShuffleRelative | <<features-features-subgroup-shuffle-relative,VK_SUBGROUP_FEATURE_SHUFFLE_RELATIVE_BIT>>
| code:GroupNonUniformClustered | <<features-features-subgroup-clustered,VK_SUBGROUP_FEATURE_CLUSTERED_BIT>>
| code:GroupNonUniformQuad | <<features-features-subgroup-quad,VK_SUBGROUP_FEATURE_QUAD_BIT>>
ifdef::VK_NV_shader_subgroup_partitioned[]
| code:GroupNonUniformPartitionedNV | <<features-features-subgroup-partitioned,VK_SUBGROUP_FEATURE_PARTITIONED_BIT_NV>>
endif::VK_NV_shader_subgroup_partitioned[]
endif::VK_VERSION_1_1[]
ifdef::VK_EXT_post_depth_coverage[]
[[spirvenv-capabilities-table-postdepthcoverage]]
| code:SampleMaskPostDepthCoverage | `<<VK_EXT_post_depth_coverage>>`
endif::VK_EXT_post_depth_coverage[]
ifdef::VK_EXT_descriptor_indexing[]
[[spirvenv-capabilities-table-descriptorindexing]]
| code:ShaderNonUniformEXT | `<<VK_EXT_descriptor_indexing>>`
| code:RuntimeDescriptorArrayEXT | <<features-features-runtimeDescriptorArray,runtimeDescriptorArray>>
| code:InputAttachmentArrayDynamicIndexingEXT | <<features-features-shaderInputAttachmentArrayDynamicIndexing,shaderInputAttachmentArrayDynamicIndexing>>
| code:UniformTexelBufferArrayDynamicIndexingEXT | <<features-features-shaderUniformTexelBufferArrayDynamicIndexing,shaderUniformTexelBufferArrayDynamicIndexing>>
| code:StorageTexelBufferArrayDynamicIndexingEXT | <<features-features-shaderStorageTexelBufferArrayDynamicIndexing,shaderStorageTexelBufferArrayDynamicIndexing>>
| code:UniformBufferArrayNonUniformIndexingEXT | <<features-features-shaderUniformBufferArrayNonUniformIndexing,shaderUniformBufferArrayNonUniformIndexing>>
| code:SampledImageArrayNonUniformIndexingEXT | <<features-features-shaderSampledImageArrayNonUniformIndexing,shaderSampledImageArrayNonUniformIndexing>>
| code:StorageBufferArrayNonUniformIndexingEXT | <<features-features-shaderStorageBufferArrayNonUniformIndexing,shaderStorageBufferArrayNonUniformIndexing>>
| code:StorageImageArrayNonUniformIndexingEXT | <<features-features-shaderStorageImageArrayNonUniformIndexing,shaderStorageImageArrayNonUniformIndexing>>
| code:InputAttachmentArrayNonUniformIndexingEXT | <<features-features-shaderInputAttachmentArrayNonUniformIndexing,shaderInputAttachmentArrayNonUniformIndexing>>
| code:UniformTexelBufferArrayNonUniformIndexingEXT | <<features-features-shaderUniformTexelBufferArrayNonUniformIndexing,shaderUniformTexelBufferArrayNonUniformIndexing>>
| code:StorageTexelBufferArrayNonUniformIndexingEXT | <<features-features-shaderStorageTexelBufferArrayNonUniformIndexing,shaderStorageTexelBufferArrayNonUniformIndexing>>
endif::VK_EXT_descriptor_indexing[]
|====
ifdef::VK_VERSION_1_1,VK_KHR_variable_pointers[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_KHR_variable_pointers` SPIR-V extension.
endif::VK_VERSION_1_1,VK_KHR_variable_pointers[]
ifdef::VK_AMD_shader_explicit_vertex_parameter[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_shader_explicit_vertex_parameter` SPIR-V extension.
endif::VK_AMD_shader_explicit_vertex_parameter[]
ifdef::VK_AMD_gcn_shader[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_gcn_shader` SPIR-V extension.
endif::VK_AMD_gcn_shader[]
ifdef::VK_AMD_gpu_shader_half_float[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_gpu_shader_half_float` SPIR-V extension.
endif::VK_AMD_gpu_shader_half_float[]
ifdef::VK_AMD_gpu_shader_int16[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_gpu_shader_int16` SPIR-V extension.
endif::VK_AMD_gpu_shader_int16[]
ifdef::VK_AMD_shader_ballot[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_shader_ballot` SPIR-V extension.
endif::VK_AMD_shader_ballot[]
ifdef::VK_AMD_shader_fragment_mask[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_shader_fragment_mask` SPIR-V extension.
endif::VK_AMD_shader_fragment_mask[]
ifdef::VK_AMD_shader_image_load_store_lod[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_shader_image_load_store_lod` SPIR-V extension.
endif::VK_AMD_shader_image_load_store_lod[]
ifdef::VK_AMD_shader_trinary_minmax[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_shader_trinary_minmax` SPIR-V extension.
endif::VK_AMD_shader_trinary_minmax[]
ifdef::VK_AMD_texture_gather_bias_lod[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_AMD_texture_gather_bias_lod` SPIR-V extension.
endif::VK_AMD_texture_gather_bias_lod[]
ifdef::VK_VERSION_1_1,VK_KHR_shader_draw_parameters[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_KHR_shader_draw_parameters` SPIR-V extension.
endif::VK_VERSION_1_1,VK_KHR_shader_draw_parameters[]
ifdef::VK_VERSION_1_1,VK_KHR_16bit_storage[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the
https://www.khronos.org/registry/spir-v/extensions/KHR/SPV_KHR_16bit_storage.html[`SPV_KHR_16bit_storage`]
SPIR-V extension.
endif::VK_VERSION_1_1,VK_KHR_16bit_storage[]
ifdef::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the
https://www.khronos.org/registry/spir-v/extensions/KHR/SPV_KHR_storage_buffer_storage_class.html[`SPV_KHR_storage_buffer_storage_class`]
SPIR-V extension.
endif::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
ifdef::VK_EXT_post_depth_coverage[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_KHR_post_depth_coverage` SPIR-V extension.
endif::VK_EXT_post_depth_coverage[]
ifdef::VK_EXT_shader_stencil_export[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_EXT_shader_stencil_export` SPIR-V extension.
endif::VK_EXT_shader_stencil_export[]
ifdef::VK_EXT_shader_subgroup_ballot[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_KHR_shader_ballot` SPIR-V extension.
endif::VK_EXT_shader_subgroup_ballot[]
ifdef::VK_EXT_shader_subgroup_vote[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_KHR_subgroup_vote` SPIR-V extension.
endif::VK_EXT_shader_subgroup_vote[]
ifdef::VK_NV_sample_mask_override_coverage[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_NV_sample_mask_override_coverage` SPIR-V extension.
endif::VK_NV_sample_mask_override_coverage[]
ifdef::VK_NV_geometry_shader_passthrough[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_NV_geometry_shader_passthrough` SPIR-V extension.
endif::VK_NV_geometry_shader_passthrough[]
ifdef::VK_NV_viewport_array2[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_NV_viewport_array2` SPIR-V extension.
endif::VK_NV_viewport_array2[]
ifdef::VK_EXT_shader_viewport_index_layer[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_EXT_shader_viewport_index_layer` SPIR-V extension.
endif::VK_EXT_shader_viewport_index_layer[]
ifdef::VK_NVX_multiview_per_view_attributes[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the `SPV_NVX_multiview_per_view_attributes` SPIR-V extension.
endif::VK_NVX_multiview_per_view_attributes[]
ifdef::VK_EXT_descriptor_indexing[]
The application can: pass a SPIR-V module to flink:vkCreateShaderModule that
uses the +SPV_EXT_descriptor_indexing+ SPIR-V extension.
endif::VK_EXT_descriptor_indexing[]
The application must: not pass a SPIR-V module containing any of the
following to flink:vkCreateShaderModule:
* any OpCapability not listed above,
* an unsupported capability, or
* a capability which corresponds to a Vulkan feature or extension which
has not been enabled.
[[spirvenv-module-validation]]
== Validation Rules within a Module
A SPIR-V module passed to flink:vkCreateShaderModule must: conform to the
following rules:
* Every entry point must: have no return value and accept no arguments.
* Recursion: The static function-call graph for an entry point must: not
contain cycles.
* The *Logical* addressing model must: be selected.
* *Scope* for execution must: be limited to:
** *Workgroup*
** *Subgroup*
* *Scope* for memory must: be limited to:
** *Device*
** *Workgroup*
ifdef::VK_VERSION_1_1[]
** *Subgroup*
endif::VK_VERSION_1_1[]
** *Invocation*
ifdef::VK_VERSION_1_1[]
* *Scope* for *Non Uniform Group Operations* must: be limited to:
** *Subgroup*
endif::VK_VERSION_1_1[]
* *Storage Class* must: be limited to:
** *UniformConstant*
** *Input*
** *Uniform*
** *Output*
** *Workgroup*
** *Private*
** *Function*
** *PushConstant*
** *Image*
ifdef::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
** *StorageBuffer*
endif::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
* Memory semantics must: obey the following rules:
** *Acquire* must: not be used with code:OpAtomicStore.
** *Release* must: not be used with code:OpAtomicLoad.
** *AcquireRelease* must: not be used with code:OpAtomicStore or
code:OpAtomicLoad.
** Sequentially consistent atomics and barriers are not supported and
*SequentiallyConsistent* is treated as *AcquireRelease*.
*SequentiallyConsistent* should: not be used.
** code:OpMemoryBarrier must: use one of *Acquire*, *Release*,
*AcquireRelease*, or *SequentiallyConsistent* and must: include at
least one storage class.
** If the semantics for code:OpControlBarrier includes one of *Acquire*,
*Release*, *AcquireRelease*, or *SequentiallyConsistent*, then it must:
include at least one storage class.
** *SubgroupMemory*, *CrossWorkgroupMemory*, and *AtomicCounterMemory* are
ignored.
* Any code:OpVariable with an code:Initializer operand must: have one of
the following as its code:Storage code:Class operand:
** *Output*
** *Private*
** *Function*
* The code:OriginLowerLeft execution mode must: not be used; fragment
entry points must: declare code:OriginUpperLeft.
* The code:PixelCenterInteger execution mode must: not be used.
Pixels are always centered at half-integer coordinates.
* Images
** code:OpTypeImage must: declare a scalar 32-bit float or 32-bit integer
type for the "`Sampled Type`".
(code:RelaxedPrecision can: be applied to a sampling instruction and to
the variable holding the result of a sampling instruction.)
** code:OpSampledImage, code:OpImageQuerySizeLod, and
code:OpImageQueryLevels must: only consume an "`Image`" operand whose
type has its "`Sampled`" operand set to 1.
** The [eq]#(u,v)# coordinates used for a code:SubpassData must: be the
<id> of a constant vector [eq]#(0,0)#, or if a layer coordinate is
used, must: be a vector that was formed with constant 0 for the [eq]#u#
and [eq]#v# components.
** The "`Depth`" operand of code:OpTypeImage is ignored.
* Decorations
** The code:GLSLShared and code:GLSLPacked decorations must: not be used.
** The code:Flat, code:NoPerspective, code:Sample, and code:Centroid
decorations must: not be used on variables with storage class other
than code:Input or on variables used in the interface of non-fragment
shader entry points.
** The code:Patch decoration must: not be used on variables in the
interface of a vertex, geometry, or fragment shader stage's entry
point.
ifdef::VK_NV_viewport_array2[]
** The code:ViewportRelativeNV decoration must: only be used on a variable
decorated with code:Layer in the vertex, tessellation evaluation, or
geometry shader stages.
** The code:ViewportRelativeNV decoration must: not be used unless a
variable decorated with one of code:ViewportIndex or
code:ViewportMaskNV is also statically used by the same
code:OpEntryPoint.
** The code:ViewportMaskNV and code:ViewportIndex decorations must: not
both be statically used by one or more code:OpEntryPoint's that form
the vertex processing stages of a graphics pipeline.
endif::VK_NV_viewport_array2[]
ifdef::VK_VERSION_1_1,VK_KHR_16bit_storage[]
** Only the round-to-nearest-even and the round-to-zero rounding modes
can: be used for the code:FPRoundingMode decoration.
** The code:FPRoundingMode decoration can: only be used for the
floating-point conversion instructions as described in the
https://www.khronos.org/registry/spir-v/extensions/KHR/SPV_KHR_16bit_storage.html[`SPV_KHR_16bit_storage`]
SPIR-V extension.
endif::VK_VERSION_1_1,VK_KHR_16bit_storage[]
* code:OpTypeRuntimeArray must: only be used for:
** the last member of an code:OpTypeStruct
ifdef::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
that is in the code:StorageBuffer storage class decorated as
code:Block, or
endif::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
that is in the code:Uniform storage class decorated as
code:BufferBlock.
ifdef::VK_EXT_descriptor_indexing[]
** If the code:RuntimeDescriptorArrayEXT capability is supported, an array
of variables with storage class code:Uniform,
ifdef::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
code:StorageBuffer,
endif::VK_VERSION_1_1,VK_KHR_storage_buffer_storage_class[]
or code:UniformConstant, or for the outermost dimension of an array of
arrays of such variables.
endif::VK_EXT_descriptor_indexing[]
* Linkage: See <<interfaces,Shader Interfaces>> for additional linking and
validation rules.
ifdef::VK_VERSION_1_1[]
* If code:OpControlBarrier is used in fragment, vertex, tessellation
evaluation, or geometry stages, the execution Scope must: be
code:Subgroup.
endif::VK_VERSION_1_1[]
* Compute Shaders
** For each compute shader entry point, either a code:LocalSize execution
mode or an object decorated with the code:WorkgroupSize decoration
must: be specified.
ifdef::VK_VERSION_1_1[]
* "`Result Type`" for *Non Uniform Group Operations* must: be limited to
32-bit float, 32-bit integer, boolean, or vectors of these types.
If the code:Float64 capability is enabled, double and vector of double
types are also permitted.
* "`Mask`" for code:OpGroupNonUniformShuffleXor must: be a specialization
constant or a constant, or if the dynamic instance is called within a
loop construct it must: be one of:
. A specialization constant.
. A constant.
. An arthimetic operation whose operands are 1., 2., or 4.
. A phi node whose operands are 1., 2., or 3.
* If code:OpGroupNonUniformBallotBitCount is used, the group operation
must: be one of:
** *Reduce*
** *InclusiveScan*
** *ExclusiveScan*
endif::VK_VERSION_1_1[]
* Atomic instructions must: declare a scalar 32-bit integer type for the
_Result Type_ and the type of the value pointed to by _Pointer_.
ifdef::VK_EXT_descriptor_indexing[]
* If an instruction loads from or stores to a resource (including atomics
and image instructions) and the resource descriptor being accessed is
not dynamically uniform, then the operand corresponding to that resource
(e.g. the pointer or sampled image operand) must: be decorated with
code:NonUniformEXT.
endif::VK_EXT_descriptor_indexing[]
[[spirvenv-precision-operation]]
== Precision and Operation of SPIR-V Instructions
The following rules apply to both single and double-precision floating point
instructions:
* Positive and negative infinities and positive and negative zeros are
generated as dictated by <<ieee-754,IEEE 754>>, but subject to the
precisions allowed in the following table.
* Dividing a non-zero by a zero results in the appropriately signed
<<ieee-754,IEEE 754>> infinity.
* Any denormalized value input into a shader or potentially generated by
any instruction in a shader may: be flushed to 0.
* The rounding mode cannot: be set and is undefined.
* [eq]##NaN##s may: not be generated.
Instructions that operate on a [eq]#NaN# may: not result in a [eq]#NaN#.
* Support for signaling [eq]##NaN##s is optional: and exceptions are never
raised.
The precision of double-precision instructions is at least that of single
precision.
For single precision (32 bit) instructions, precisions are required: to be
at least as follows, unless decorated with RelaxedPrecision:
.Precision of core SPIR-V Instructions
[options="header"]
|====
| Instruction | Precision
| code:OpFAdd | Correctly rounded.
| code:OpFSub | Correctly rounded.
| code:OpFMul | Correctly rounded.
| code:OpFOrdEqual, code:OpFUnordEqual | Correct result.
| code:OpFOrdLessThan, code:OpFUnordLessThan | Correct result.
| code:OpFOrdGreaterThan, code:OpFUnordGreaterThan | Correct result.
| code:OpFOrdLessThanEqual, code:OpFUnordLessThanEqual | Correct result.
| code:OpFOrdGreaterThanEqual, code:OpFUnordGreaterThanEqual| Correct result.
| code:OpFDiv | 2.5 ULP for b in the range [2^-126^, 2^126^].
| conversions between types | Correctly rounded.
|====
.Precision of GLSL.std.450 Instructions
[options="header"]
|====
|Instruction | Precision
| code:fma() | Inherited from code:OpFMul followed by code:OpFAdd.
| code:exp(x), code:exp2(x) | [eq]#3 {plus} 2 {times} {vert}x{vert}# ULP.
| code:log(), code:log2() | 3 ULP outside the range [eq]#[0.5, 2.0]#. Absolute error < [eq]#2^-21^# inside the range [eq]#[0.5, 2.0]#.
| code:pow(x, y) | Inherited from code:exp2(y {times} code:log2(x)).
| code:sqrt() | Inherited from 1.0 / code:inversesqrt().
| code:inversesqrt() | 2 ULP.
|====
GLSL.std.450 extended instructions specifically defined in terms of the
above instructions inherit the above errors.
GLSL.std.450 extended instructions not listed above and not defined in terms
of the above have undefined precision.
These include, for example, the trigonometric functions and determinant.
For the code:OpSRem and code:OpSMod instructions, if either operand is
negative the result is undefined.
[NOTE]
.Note
====
While the code:OpSRem and code:OpSMod instructions are supported by the
Vulkan environment, they require non-negative values and thus do not enable
additional functionality beyond what code:OpUMod provides.
====
[[spirvenv-image-formats]]
.Compatibility Between SPIR-V Image Formats And Vulkan Formats
Images which are read from or written to by shaders must: have SPIR-V image
formats compatible with the Vulkan image formats backing the image under the
circumstances described for <<textures-operation-validation,texture image
validation>>.
The compatibile formats are:
.SPIR-V and Vulkan Image Format Compatibility
[cols="2*", options="header"]
|====
|SPIR-V Image Format |Compatible Vulkan Format
|code:Rgba32f |ename:VK_FORMAT_R32G32B32A32_SFLOAT
|code:Rgba16f |ename:VK_FORMAT_R16G16B16A16_SFLOAT
|code:R32f |ename:VK_FORMAT_R32_SFLOAT
|code:Rgba8 |ename:VK_FORMAT_R8G8B8A8_UNORM
|code:Rgba8Snorm |ename:VK_FORMAT_R8G8B8A8_SNORM
|code:Rg32f |ename:VK_FORMAT_R32G32_SFLOAT
|code:Rg16f |ename:VK_FORMAT_R16G16_SFLOAT
|code:R11fG11fB10f |ename:VK_FORMAT_B10G11R11_UFLOAT_PACK32
|code:R16f |ename:VK_FORMAT_R16_SFLOAT
|code:Rgba16 |ename:VK_FORMAT_R16G16B16A16_UNORM
|code:Rgb10A2 |ename:VK_FORMAT_A2B10G10R10_UNORM_PACK32
|code:Rg16 |ename:VK_FORMAT_R16G16_UNORM
|code:Rg8 |ename:VK_FORMAT_R8G8_UNORM
|code:R16 |ename:VK_FORMAT_R16_UNORM
|code:R8 |ename:VK_FORMAT_R8_UNORM
|code:Rgba16Snorm |ename:VK_FORMAT_R16G16B16A16_SNORM
|code:Rg16Snorm |ename:VK_FORMAT_R16G16_SNORM
|code:Rg8Snorm |ename:VK_FORMAT_R8G8_SNORM
|code:R16Snorm |ename:VK_FORMAT_R16_SNORM
|code:R8Snorm |ename:VK_FORMAT_R8_SNORM
|code:Rgba32i |ename:VK_FORMAT_R32G32B32A32_SINT
|code:Rgba16i |ename:VK_FORMAT_R16G16B16A16_SINT
|code:Rgba8i |ename:VK_FORMAT_R8G8B8A8_SINT
|code:R32i |ename:VK_FORMAT_R32_SINT
|code:Rg32i |ename:VK_FORMAT_R32G32_SINT
|code:Rg16i |ename:VK_FORMAT_R16G16_SINT
|code:Rg8i |ename:VK_FORMAT_R8G8_SINT
|code:R16i |ename:VK_FORMAT_R16_SINT
|code:R8i |ename:VK_FORMAT_R8_SINT
|code:Rgba32ui |ename:VK_FORMAT_R32G32B32A32_UINT
|code:Rgba16ui |ename:VK_FORMAT_R16G16B16A16_UINT
|code:Rgba8ui |ename:VK_FORMAT_R8G8B8A8_UINT
|code:R32ui |ename:VK_FORMAT_R32_UINT
|code:Rgb10a2ui |ename:VK_FORMAT_A2B10G10R10_UINT_PACK32
|code:Rg32ui |ename:VK_FORMAT_R32G32_UINT
|code:Rg16ui |ename:VK_FORMAT_R16G16_UINT
|code:Rg8ui |ename:VK_FORMAT_R8G8_UINT
|code:R16ui |ename:VK_FORMAT_R16_UINT
|code:R8ui |ename:VK_FORMAT_R8_UINT
|====