Copyright 2014-2023 The Khronos Group Inc.
This Specification is protected by copyright laws and contains material proprietary to Khronos. Except as described by these terms, it or any components may not be reproduced, republished, distributed, transmitted, displayed, broadcast or otherwise exploited in any manner without the express prior written permission of Khronos.
This Specification has been created under the Khronos Intellectual Property Rights Policy, which is Attachment A of the Khronos Group Membership Agreement available at www.khronos.org/files/member_agreement.pdf.
Khronos grants a conditional copyright license to use and reproduce the unmodified Specification for any purpose, without fee or royalty, EXCEPT no licenses to any patent, trademark or other intellectual property rights are granted under these terms. Parties desiring to implement the Specification and make use of Khronos trademarks in relation to that implementation, and receive reciprocal patent license protection under the Khronos Intellectual Property Rights Policy must become Adopters and confirm the implementation as conformant under the process defined by Khronos for this Specification; see https://www.khronos.org/adopters.
Khronos makes no, and expressly disclaims any, representations or warranties, express or implied, regarding this Specification, including, without limitation: merchantability, fitness for a particular purpose, non-infringement of any intellectual property, correctness, accuracy, completeness, timeliness, and reliability. Under no circumstances will Khronos, or any of its Promoters, Contributors or Members, or their respective partners, officers, directors, employees, agents or representatives be liable for any damages, whether direct, indirect, special or consequential damages for lost revenues, lost profits, or otherwise, arising from or in connection with these materials.
This Specification contains substantially unmodified functionality from, and is a successor to, Khronos specifications including all versions of "The SPIR Specification", "The OpenGL Shading Language", "The OpenGL ES Shading Language", as well as all Khronos OpenCL API and OpenCL programming language specifications.
The Khronos Intellectual Property Rights Policy defines the terms Scope, Compliant Portion, and Necessary Patent Claims.
Where this Specification uses technical terminology, defined in the Glossary or otherwise, that refer to enabling technologies that are not expressly set forth in this Specification, those enabling technologies are EXCLUDED from the Scope of this Specification. For clarity, enabling technologies not disclosed with particularity in this Specification (e.g. semiconductor manufacturing technology, hardware architecture, processor architecture or microarchitecture, memory architecture, compiler technology, object oriented technology, basic operating system technology, compression technology, algorithms, and so on) are NOT to be considered expressly set forth; only those application program interfaces and data structures disclosed with particularity are included in the Scope of this Specification.
For purposes of the Khronos Intellectual Property Rights Policy as it relates to the definition of Necessary Patent Claims, all recommended or optional features, behaviors and functionality set forth in this Specification, if implemented, are considered to be included as Compliant Portions.
Khronos® and Vulkan® are registered trademarks, and ANARI™, WebGL™, glTF™, NNEF™, OpenVX™, SPIR™, SPIR-V™, SYCL™, OpenVG™, Vulkan SC™, 3D Commerce™ and Kamaros™ are trademarks of The Khronos Group Inc. OpenXR™ is a trademark owned by The Khronos Group Inc. and is registered as a trademark in China, the European Union, Japan and the United Kingdom. OpenCL™ is a trademark of Apple Inc. used under license by Khronos. OpenGL® is a registered trademark and the OpenGL ES™ and OpenGL SC™ logos are trademarks of Hewlett Packard Enterprise used under license by Khronos. ASTC is a trademark of ARM Holdings PLC. All other product names, trademarks, and/or company names are used solely for identification and belong to their respective owners.
1. Introduction
This specifies the GLSL.std.450 extended instruction set. It provides instructions for the GLSL built-in functions that do not directly map to native SPIR-V instructions.
Import this extended instruction set using an OpExtInstImport "GLSL.std.450" instruction.
2. Binary Form
Documentation form for each extended instruction:
Extended Instruction Name Instruction description. Result Type will describe the Result Type for the OpExtInst instruction. Number is the extended instruction number to use in the OpExtInst instruction. Operand 1, Operand 2,… are the operands listed for the OpExtInst instruction. Any Capability restrictions. |
|||
Number |
Operand 1 |
Operand 2 |
… |
Extended instructions:
Round |
|
1 |
<id> |
RoundEven |
|
2 |
<id> |
Trunc |
|
3 |
<id> |
FAbs |
|
4 |
<id> |
SAbs |
|
5 |
<id> |
FSign |
|
6 |
<id> |
SSign |
|
7 |
<id> |
Floor |
|
8 |
<id> |
Ceil |
|
9 |
<id> |
Fract |
|
10 |
<id> |
Radians |
|
11 |
<id> |
Degrees |
|
12 |
<id> |
Sin |
|
13 |
<id> |
Cos |
|
14 |
<id> |
Tan |
|
15 |
<id> |
Asin |
|
16 |
<id> |
Acos |
|
17 |
<id> |
Atan |
|
18 |
<id> |
Sinh |
|
19 |
<id> |
Cosh |
|
20 |
<id> |
Tanh |
|
21 |
<id> |
Asinh |
|
22 |
<id> |
Acosh |
|
23 |
<id> |
Atanh |
|
24 |
<id> |
Atan2 |
||
25 |
<id> |
<id> |
Pow |
||
26 |
<id> |
<id> |
Exp |
|
27 |
<id> |
Log |
|
28 |
<id> |
Exp2 |
|
29 |
<id> |
Log2 |
|
30 |
<id> |
Sqrt |
|
31 |
<id> |
InverseSqrt |
|
32 |
<id> |
Determinant |
|
33 |
<id> |
MatrixInverse |
|
34 |
<id> |
Modf |
||
35 |
<id> |
<id> |
ModfStruct |
|
36 |
<id> |
FMin |
||
37 |
<id> |
<id> |
UMin |
||
38 |
<id> |
<id> |
SMin |
||
39 |
<id> |
<id> |
FMax |
||
40 |
<id> |
<id> |
UMax |
||
41 |
<id> |
<id> |
SMax |
||
42 |
<id> |
<id> |
FClamp |
|||
43 |
<id> |
<id> |
<id> |
UClamp |
|||
44 |
<id> |
<id> |
<id> |
SClamp |
|||
45 |
<id> |
<id> |
<id> |
FMix |
|||
46 |
<id> |
<id> |
<id> |
Step |
||
48 |
<id> |
<id> |
SmoothStep |
|||
49 |
<id> |
<id> |
<id> |
Fma |
|||
50 |
<id> |
<id> |
<id> |
Frexp x = significand * 2exponent The significand is the instruction result. An x of -0.0 results in a significand -0.0, while an x of 0.0 results in 0.0. For a floating-point value that is an infinity or is not a number, the significand is undefined. |
||
51 |
<id> |
<id> |
FrexpStruct x = significand * 2exponent If x is a zero, the exponent is 0.0. If x is an infinity or a NaN, the exponent is undefined. If x is 0.0, the significand is 0.0. If x is -0.0, the significand is -0.0 |
|
52 |
<id> |
Ldexp significand * 2exponent If this product is too large to be finitely represented in the floating-point type, the resulting value is undefined. If exp is greater than +128 (single precision) or +1024 (double precision), the resulting value is undefined. If exp is less than -126 (single precision) or -1022 (double precision), the result may be flushed to zero. Additionally, splitting the value into a significand and exponent using frexp and then reconstructing a floating-point value using ldexp should yield the original input for zero and all finite non-denormalized values. |
||
53 |
<id> |
<id> |
PackSnorm4x8 The conversion for component c of v to fixed point is done as follows: round(clamp(c, -1, +1) * 127.0) The first component of the vector is written to the least significant bits of the output; the last component is written to the most significant bits. |
|
54 |
<id> |
PackUnorm4x8 The conversion for component c of v to fixed point is done as follows: round(clamp(c, 0, +1) * 255.0) The first component of the vector is written to the least significant bits of the output; the last component is written to the most significant bits. |
|
55 |
<id> |
PackSnorm2x16 The conversion for component c of v to fixed point is done as follows: round(clamp(c, -1, +1) * 32767.0) The first component of the vector is written to the least significant bits of the output; the last component is written to the most significant bits. |
|
56 |
<id> |
PackUnorm2x16 The conversion for component c of v to fixed point is done as follows: round(clamp(c, 0, +1) * 65535.0) The first component of the vector is written to the least significant bits of the output; the last component is written to the most significant bits. |
|
57 |
<id> |
PackHalf2x16 |
|
58 |
<id> |
PackDouble2x32 |
|
59 |
<id> |
UnpackSnorm2x16 clamp(f / 32767.0, -1, +1) The first component of the result is extracted from the least significant bits of the input; the last component is extracted from the most significant bits. |
|
60 |
<id> |
UnpackUnorm2x16 f / 65535.0 The first component of the result is extracted from the least significant bits of the input; the last component is extracted from the most significant bits. |
|
61 |
<id> |
UnpackHalf2x16 The first component of the vector is obtained from the 16 least-significant bits of v; the second component is obtained from the 16 most-significant bits of v. |
|
62 |
<id> |
UnpackSnorm4x8 clamp(f / 127.0, -1, +1) The first component of the result is extracted from the least significant bits of the input; the last component is extracted from the most significant bits. |
|
63 |
<id> |
UnpackUnorm4x8 f / 255.0 The first component of the result is extracted from the least significant bits of the input; the last component is extracted from the most significant bits. |
|
64 |
<id> |
UnpackDouble2x32 |
|
65 |
<id> |
Length |
|
66 |
<id> |
Distance |
||
67 |
<id> |
<id> |
Cross x[1] * y[2] - y[1] * x[2] x[2] * y[0] - y[2] * x[0] x[0] * y[1] - y[0] * x[1] |
||
68 |
<id> |
<id> |
Normalize |
|
69 |
<id> |
FaceForward |
|||
70 |
<id> |
<id> |
<id> |
Reflect |
||
71 |
<id> |
<id> |
Refract k = 1.0 - eta * eta * (1.0 - dot(N, I) * dot(N, I)) if k < 0.0 the result is 0.0 otherwise, the result is eta * I - (eta * dot(N, I) + sqrt(k)) * N This computation assumes the input parameters for the incident vector I and the surface normal N are already normalized. |
|||
72 |
<id> |
<id> |
<id> |
FindILsb |
|
73 |
<id> |
FindSMsb |
|
74 |
<id> |
FindUMsb |
|
75 |
<id> |
InterpolateAtCentroid |
|
76 |
<id> |
InterpolateAtSample |
||
77 |
<id> |
<id> |
InterpolateAtOffset |
||
78 |
<id> |
<id> |
NMin |
||
79 |
<id> |
<id> |
NMax |
||
80 |
<id> |
<id> |
NClamp |
|||
81 |
<id> |
<id> |
<id> |
3. Appendix A: Changes
3.1. Changes from Version 0.99, Revision 1
-
Fork the revision stream, changes section, etc. from the core specification, so this specification has its own, starting numbering at revision 1. This document now lives independently.
-
Added integer versions of abs, sign, min, max, and clamp.
-
Removed floatBitsToInt, floatBitsToUint, intBitsToFloat, and uintBitsToFloat; these can be handled with OpBitcast.
-
Removed fTransform, not needed.
-
Fixed internal bugs
-
13721: Add OpTypeStruct-result versions of Modf and Frexp: ModfStruct and FrexpStruct.
-
-
Fixed public bugs
-
1322: GLSL.std.450 frexp wasn’t saying the exp argument was a pointer to the result
-
3.2. Changes from Version 0.99, Revision 2
-
Moved AddCarry, SubBorrow, and MulExtended type of instructions to the core specification.
-
Added integer variant of Mix, creating FMix and IMix (14480).
-
Modified spellings to be more regular (14614).
3.3. Changes from Version 0.99, Revision 3
-
Add "N" version of Min, Max, and Clamp, creating a version that favors non-NaN operands over NaN operands.
-
Bug 15452 Remove IMix.
-
Bug 15300 Be more consistent that the InterpolateAt instructions take a pointer.
-
Bug 14548 Document the Capability needed for Double2x32 and InterpolateAt instructions.
3.4. Changes from Version 1.00, Revision 1
-
Bug 14548 Document the Capability needed for UnpackDouble2x32.
3.5. Changes from Version 1.00, Revision 2
-
Change precise to NoContraction
3.6. Changes from Version 1.00, Revision 3
-
Allow both 16-bit and 32-bit floating-point types in most places where before only 32-bit floating-point types were allowed. This does not effect whether 16-bit floating point types are allowed, which is selected independently. Since 16-bit types were historically disallowed, this is a backward compatible change.
-
Fix Khronos internal issue #109: be more clear for NMin/NMax: If both operands are NaN, the result is a NaN.
3.7. Changes from Version 1.00, Revision 4
-
Be clear about UnpackHalf2x16 denorm rules.
3.8. Changes from Version 1.00, Revision 5
Fixed:
-
Khronos SPIR-V Issue #211: As with FindSMsb and FindUMsb, FindILsb needs 32-bit components.
3.9. Changes from Version 1.00, Revision 6
Fixed:
-
Khronos SPIR-V Issue #337: The component types of the operands for Refract must all be the same.
-
Khronos SPIR-V Issue #331: Correct the types in ModfStruct.
3.10. Changes from Version 1.00, Revision 7
Support SPV_KHR_no_integer_wrap_decoration, in the SAbs instruction.
3.11. Changes from Version 1.00, Revision 8
Fixed:
-
Khronos SPIR-V Issue #466: FAbs of -0.0 is +0.0, FSign of -0.0 can be either ±0.0. FMin, FMax, NMin, and NMax are allowed to return either operand when both are zeros.
-
Khronos SPIR-V Issue #458: For Frexp, be more clear about negative values, and also about which returned value is being discussed.
3.12. Changes from Version 1.00, Revision 9
-
Corrected the output range of Atan.
3.13. Changes from Version 1.00, Revision 10
-
State what FSign of ±NaN is.
3.14. Changes from Version 1.00, Revision 11
-
Khronos SPIR-V Issue #555: Deprecate Modf, use ModfStruct instead. Deprecate Frexp, use FrexpStruct instead.
-
Khronos SPIR-V Issue #284: Say all bits are set, instead of saying -1, for some results of FindILsb, FindSMsb, and FindUMsb.
-
Khronos SPIR-V MR #181: Use "fragment" instead of "pixel" in InterpolateAtCentroid, InterpolateAtSample, and InterpolateAtOffset.
3.15. Changes from Version 1.00, Revision 12
-
Khronos SPIR-V Issue #705: Clarify the computation provided for Reflect is used regardless of input normalization.