Add gl_SemanticsVolatile to GL_KHR_memory_scope_semantics, and make volatile-qualifie...
authorJeff Bolz <jbolz@nvidia.com>
Fri, 14 Jun 2019 14:56:28 +0000 (09:56 -0500)
committerJeff Bolz <jbolz@nvidia.com>
Fri, 14 Jun 2019 14:57:01 +0000 (09:57 -0500)
SPIRV/GlslangToSpv.cpp
SPIRV/spirv.hpp
Test/baseResults/spv.memoryScopeSemantics.comp.out
Test/baseResults/spv.memoryScopeSemantics_Error.comp.out
Test/spv.memoryScopeSemantics.comp
Test/spv.memoryScopeSemantics_Error.comp
glslang/MachineIndependent/Initialize.cpp
glslang/MachineIndependent/ParseHelper.cpp

index 312e06a..9ad19b5 100644 (file)
@@ -169,7 +169,7 @@ protected:
     void makeGlobalInitializers(const glslang::TIntermSequence&);
     void visitFunctions(const glslang::TIntermSequence&);
     void handleFunctionEntry(const glslang::TIntermAggregate* node);
-    void translateArguments(const glslang::TIntermAggregate& node, std::vector<spv::Id>& arguments);
+    void translateArguments(const glslang::TIntermAggregate& node, std::vector<spv::Id>& arguments, spv::Builder::AccessChain::CoherentFlags &lvalueCoherentFlags);
     void translateArguments(glslang::TIntermUnary& node, std::vector<spv::Id>& arguments);
     spv::Id createImageTextureFunctionCall(glslang::TIntermOperator* node);
     spv::Id handleUserFunctionCall(const glslang::TIntermAggregate*);
@@ -178,14 +178,14 @@ protected:
                                   glslang::TBasicType typeProxy, bool reduceComparison = true);
     spv::Id createBinaryMatrixOperation(spv::Op, OpDecorations&, spv::Id typeId, spv::Id left, spv::Id right);
     spv::Id createUnaryOperation(glslang::TOperator op, OpDecorations&, spv::Id typeId, spv::Id operand,
-                                 glslang::TBasicType typeProxy);
+                                 glslang::TBasicType typeProxy, const spv::Builder::AccessChain::CoherentFlags &lvalueCoherentFlags);
     spv::Id createUnaryMatrixOperation(spv::Op op, OpDecorations&, spv::Id typeId, spv::Id operand,
                                        glslang::TBasicType typeProxy);
     spv::Id createConversion(glslang::TOperator op, OpDecorations&, spv::Id destTypeId, spv::Id operand,
                              glslang::TBasicType typeProxy);
     spv::Id createIntWidthConversion(glslang::TOperator op, spv::Id operand, int vectorSize);
     spv::Id makeSmearedConstant(spv::Id constant, int vectorSize);
-    spv::Id createAtomicOperation(glslang::TOperator op, spv::Decoration precision, spv::Id typeId, std::vector<spv::Id>& operands, glslang::TBasicType typeProxy);
+    spv::Id createAtomicOperation(glslang::TOperator op, spv::Decoration precision, spv::Id typeId, std::vector<spv::Id>& operands, glslang::TBasicType typeProxy, const spv::Builder::AccessChain::CoherentFlags &lvalueCoherentFlags);
     spv::Id createInvocationsOperation(glslang::TOperator op, spv::Id typeId, std::vector<spv::Id>& operands, glslang::TBasicType typeProxy);
     spv::Id CreateInvocationsVectorOperation(spv::Op op, spv::GroupOperation groupOperation, spv::Id typeId, std::vector<spv::Id>& operands);
     spv::Id createSubgroupOperation(glslang::TOperator op, spv::Id typeId, std::vector<spv::Id>& operands, glslang::TBasicType typeProxy);
@@ -1981,19 +1981,26 @@ bool TGlslangToSpvTraverser::visitUnary(glslang::TVisit /* visit */, glslang::TI
         invertedType = getInvertedSwizzleType(*node->getOperand());
 
     builder.clearAccessChain();
+    TIntermNode *operandNode;
     if (invertedType != spv::NoType)
-        node->getOperand()->getAsBinaryNode()->getLeft()->traverse(this);
+        operandNode = node->getOperand()->getAsBinaryNode()->getLeft();
     else
-        node->getOperand()->traverse(this);
+        operandNode = node->getOperand();
+    
+    operandNode->traverse(this);
 
     spv::Id operand = spv::NoResult;
 
+    spv::Builder::AccessChain::CoherentFlags lvalueCoherentFlags;
+
     if (node->getOp() == glslang::EOpAtomicCounterIncrement ||
         node->getOp() == glslang::EOpAtomicCounterDecrement ||
         node->getOp() == glslang::EOpAtomicCounter          ||
-        node->getOp() == glslang::EOpInterpolateAtCentroid)
+        node->getOp() == glslang::EOpInterpolateAtCentroid) {
         operand = builder.accessChainGetLValue(); // Special case l-value operands
-    else
+        lvalueCoherentFlags = builder.getAccessChain().coherentFlags;
+        lvalueCoherentFlags |= TranslateCoherent(operandNode->getAsTyped()->getType());
+    } else
         operand = accessChainLoad(node->getOperand()->getType());
 
     OpDecorations decorations = { TranslatePrecisionDecoration(node->getOperationPrecision()),
@@ -2006,7 +2013,7 @@ bool TGlslangToSpvTraverser::visitUnary(glslang::TVisit /* visit */, glslang::TI
 
     // if not, then possibly an operation
     if (! result)
-        result = createUnaryOperation(node->getOp(), decorations, resultType(), operand, node->getOperand()->getBasicType());
+        result = createUnaryOperation(node->getOp(), decorations, resultType(), operand, node->getOperand()->getBasicType(), lvalueCoherentFlags);
 
     if (result) {
         if (invertedType) {
@@ -2113,6 +2120,8 @@ bool TGlslangToSpvTraverser::visitAggregate(glslang::TVisit visit, glslang::TInt
     bool noReturnValue = false;
     bool atomic = false;
 
+    spv::Builder::AccessChain::CoherentFlags lvalueCoherentFlags;
+
     assert(node->getOp());
 
     spv::Decoration precision = TranslatePrecisionDecoration(node->getOperationPrecision());
@@ -2310,7 +2319,7 @@ bool TGlslangToSpvTraverser::visitAggregate(glslang::TVisit visit, glslang::TInt
     {
         builder.setLine(node->getLoc().line, node->getLoc().getFilename());
         std::vector<spv::Id> arguments;
-        translateArguments(*node, arguments);
+        translateArguments(*node, arguments, lvalueCoherentFlags);
         spv::Id constructed;
         if (node->getOp() == glslang::EOpConstructTextureSampler)
             constructed = builder.createOp(spv::OpSampledImage, resultType(), arguments);
@@ -2602,9 +2611,11 @@ bool TGlslangToSpvTraverser::visitAggregate(glslang::TVisit visit, glslang::TInt
             }
         }
 
-        if (lvalue)
+        if (lvalue) {
             operands.push_back(builder.accessChainGetLValue());
-        else {
+            lvalueCoherentFlags = builder.getAccessChain().coherentFlags;
+            lvalueCoherentFlags |= TranslateCoherent(glslangOperands[arg]->getAsTyped()->getType());
+        } else {
             builder.setLine(node->getLoc().line, node->getLoc().getFilename());
             operands.push_back(accessChainLoad(glslangOperands[arg]->getAsTyped()->getType()));
         }
@@ -2639,7 +2650,7 @@ bool TGlslangToSpvTraverser::visitAggregate(glslang::TVisit visit, glslang::TInt
         result = 0;
     } else if (atomic) {
         // Handle all atomics
-        result = createAtomicOperation(node->getOp(), precision, resultType(), operands, node->getBasicType());
+        result = createAtomicOperation(node->getOp(), precision, resultType(), operands, node->getBasicType(), lvalueCoherentFlags);
     } else {
         // Pass through to generic operations.
         switch (glslangOperands.size()) {
@@ -2654,7 +2665,7 @@ bool TGlslangToSpvTraverser::visitAggregate(glslang::TVisit visit, glslang::TInt
                 result = createUnaryOperation(
                     node->getOp(), decorations,
                     resultType(), operands.front(),
-                    glslangOperands[0]->getAsTyped()->getBasicType());
+                    glslangOperands[0]->getAsTyped()->getBasicType(), lvalueCoherentFlags);
             }
             break;
         default:
@@ -4052,7 +4063,7 @@ void TGlslangToSpvTraverser::handleFunctionEntry(const glslang::TIntermAggregate
     builder.setBuildPoint(functionBlock);
 }
 
-void TGlslangToSpvTraverser::translateArguments(const glslang::TIntermAggregate& node, std::vector<spv::Id>& arguments)
+void TGlslangToSpvTraverser::translateArguments(const glslang::TIntermAggregate& node, std::vector<spv::Id>& arguments, spv::Builder::AccessChain::CoherentFlags &lvalueCoherentFlags)
 {
     const glslang::TIntermSequence& glslangArguments = node.getSequence();
 
@@ -4210,9 +4221,11 @@ void TGlslangToSpvTraverser::translateArguments(const glslang::TIntermAggregate&
             break;
         }
 
-        if (lvalue)
+        if (lvalue) {
             arguments.push_back(builder.accessChainGetLValue());
-        else
+            lvalueCoherentFlags = builder.getAccessChain().coherentFlags;
+            lvalueCoherentFlags |= TranslateCoherent(glslangArguments[i]->getAsTyped()->getType());
+        } else
             arguments.push_back(accessChainLoad(glslangArguments[i]->getAsTyped()->getType()));
     }
 }
@@ -4253,9 +4266,11 @@ spv::Id TGlslangToSpvTraverser::createImageTextureFunctionCall(glslang::TIntermO
         return spv::ImageOperandsMaskNone;
     };
 
+    spv::Builder::AccessChain::CoherentFlags lvalueCoherentFlags;
+
     std::vector<spv::Id> arguments;
     if (node->getAsAggregate())
-        translateArguments(*node->getAsAggregate(), arguments);
+        translateArguments(*node->getAsAggregate(), arguments, lvalueCoherentFlags);
     else
         translateArguments(*node->getAsUnaryNode(), arguments);
     spv::Decoration precision = TranslatePrecisionDecoration(node->getOperationPrecision());
@@ -4536,7 +4551,7 @@ spv::Id TGlslangToSpvTraverser::createImageTextureFunctionCall(glslang::TIntermO
             for (; opIt != arguments.end(); ++opIt)
                 operands.push_back(*opIt);
 
-            return createAtomicOperation(node->getOp(), precision, resultType(), operands, node->getBasicType());
+            return createAtomicOperation(node->getOp(), precision, resultType(), operands, node->getBasicType(), lvalueCoherentFlags);
         }
     }
 
@@ -5292,7 +5307,7 @@ spv::Id TGlslangToSpvTraverser::createBinaryMatrixOperation(spv::Op op, OpDecora
 }
 
 spv::Id TGlslangToSpvTraverser::createUnaryOperation(glslang::TOperator op, OpDecorations& decorations, spv::Id typeId,
-                                                     spv::Id operand, glslang::TBasicType typeProxy)
+                                                     spv::Id operand, glslang::TBasicType typeProxy, const spv::Builder::AccessChain::CoherentFlags &lvalueCoherentFlags)
 {
     spv::Op unaryOp = spv::OpNop;
     int extBuiltins = -1;
@@ -5563,7 +5578,7 @@ spv::Id TGlslangToSpvTraverser::createUnaryOperation(glslang::TOperator op, OpDe
         // Handle all of the atomics in one place, in createAtomicOperation()
         std::vector<spv::Id> operands;
         operands.push_back(operand);
-        return createAtomicOperation(op, decorations.precision, typeId, operands, typeProxy);
+        return createAtomicOperation(op, decorations.precision, typeId, operands, typeProxy, lvalueCoherentFlags);
     }
 
     case glslang::EOpBitFieldReverse:
@@ -6171,7 +6186,7 @@ spv::Id TGlslangToSpvTraverser::makeSmearedConstant(spv::Id constant, int vector
 }
 
 // For glslang ops that map to SPV atomic opCodes
-spv::Id TGlslangToSpvTraverser::createAtomicOperation(glslang::TOperator op, spv::Decoration /*precision*/, spv::Id typeId, std::vector<spv::Id>& operands, glslang::TBasicType typeProxy)
+spv::Id TGlslangToSpvTraverser::createAtomicOperation(glslang::TOperator op, spv::Decoration /*precision*/, spv::Id typeId, std::vector<spv::Id>& operands, glslang::TBasicType typeProxy, const spv::Builder::AccessChain::CoherentFlags &lvalueCoherentFlags)
 {
     spv::Op opCode = spv::OpNop;
 
@@ -6257,7 +6272,7 @@ spv::Id TGlslangToSpvTraverser::createAtomicOperation(glslang::TOperator op, spv
         scopeId = builder.makeUintConstant(spv::ScopeDevice);
     }
     // semantics default to relaxed 
-    spv::Id semanticsId = builder.makeUintConstant(spv::MemorySemanticsMaskNone);
+    spv::Id semanticsId = builder.makeUintConstant(lvalueCoherentFlags.volatil ? spv::MemorySemanticsVolatileMask : spv::MemorySemanticsMaskNone);
     spv::Id semanticsId2 = semanticsId;
 
     pointerId = operands[0];
@@ -6287,7 +6302,10 @@ spv::Id TGlslangToSpvTraverser::createAtomicOperation(glslang::TOperator op, spv
 
     // Check for capabilities
     unsigned semanticsImmediate = builder.getConstantScalar(semanticsId) | builder.getConstantScalar(semanticsId2);
-    if (semanticsImmediate & (spv::MemorySemanticsMakeAvailableKHRMask | spv::MemorySemanticsMakeVisibleKHRMask | spv::MemorySemanticsOutputMemoryKHRMask)) {
+    if (semanticsImmediate & (spv::MemorySemanticsMakeAvailableKHRMask |
+                              spv::MemorySemanticsMakeVisibleKHRMask |
+                              spv::MemorySemanticsOutputMemoryKHRMask |
+                              spv::MemorySemanticsVolatileMask)) {
         builder.addCapability(spv::CapabilityVulkanMemoryModelKHR);
     }
 
@@ -7229,7 +7247,10 @@ spv::Id TGlslangToSpvTraverser::createMiscOperation(glslang::TOperator op, spv::
             unsigned int memoryScope = builder.getConstantScalar(operands[1]);
             unsigned int semantics = builder.getConstantScalar(operands[2]) | builder.getConstantScalar(operands[3]);
             builder.createControlBarrier((spv::Scope)executionScope, (spv::Scope)memoryScope, (spv::MemorySemanticsMask)semantics);
-            if (semantics & (spv::MemorySemanticsMakeAvailableKHRMask | spv::MemorySemanticsMakeVisibleKHRMask | spv::MemorySemanticsOutputMemoryKHRMask)) {
+            if (semantics & (spv::MemorySemanticsMakeAvailableKHRMask |
+                             spv::MemorySemanticsMakeVisibleKHRMask |
+                             spv::MemorySemanticsOutputMemoryKHRMask |
+                             spv::MemorySemanticsVolatileMask)) {
                 builder.addCapability(spv::CapabilityVulkanMemoryModelKHR);
             }
             if (glslangIntermediate->usingVulkanMemoryModel() && (executionScope == spv::ScopeDevice || memoryScope == spv::ScopeDevice)) {
@@ -7246,7 +7267,10 @@ spv::Id TGlslangToSpvTraverser::createMiscOperation(glslang::TOperator op, spv::
             unsigned int memoryScope = builder.getConstantScalar(operands[0]);
             unsigned int semantics = builder.getConstantScalar(operands[1]) | builder.getConstantScalar(operands[2]);
             builder.createMemoryBarrier((spv::Scope)memoryScope, (spv::MemorySemanticsMask)semantics);
-            if (semantics & (spv::MemorySemanticsMakeAvailableKHRMask | spv::MemorySemanticsMakeVisibleKHRMask | spv::MemorySemanticsOutputMemoryKHRMask)) {
+            if (semantics & (spv::MemorySemanticsMakeAvailableKHRMask |
+                             spv::MemorySemanticsMakeVisibleKHRMask |
+                             spv::MemorySemanticsOutputMemoryKHRMask |
+                             spv::MemorySemanticsVolatileMask)) {
                 builder.addCapability(spv::CapabilityVulkanMemoryModelKHR);
             }
             if (glslangIntermediate->usingVulkanMemoryModel() && memoryScope == spv::ScopeDevice) {
index 03ba767..bbaf47c 100644 (file)
@@ -632,6 +632,7 @@ enum MemorySemanticsShift {
     MemorySemanticsOutputMemoryKHRShift = 12,
     MemorySemanticsMakeAvailableKHRShift = 13,
     MemorySemanticsMakeVisibleKHRShift = 14,
+    MemorySemanticsVolatileShift = 15,\r
     MemorySemanticsMax = 0x7fffffff,
 };
 
@@ -649,7 +650,8 @@ enum MemorySemanticsMask {
     MemorySemanticsImageMemoryMask = 0x00000800,
     MemorySemanticsOutputMemoryKHRMask = 0x00001000,
     MemorySemanticsMakeAvailableKHRMask = 0x00002000,
-    MemorySemanticsMakeVisibleKHRMask = 0x00004000,
+    MemorySemanticsMakeVisibleKHRMask = 0x00004000,\r
+    MemorySemanticsVolatileMask = 0x00008000,\r
 };
 
 enum MemoryAccessShift {
index 9361e76..8c4e576 100644 (file)
@@ -1,7 +1,7 @@
 spv.memoryScopeSemantics.comp
 // Module Version 10300
 // Generated by (magic number): 80007
-// Id's are bound by 148
+// Id's are bound by 163
 
                               Capability Shader
                               Capability Int64
@@ -23,59 +23,66 @@ spv.memoryScopeSemantics.comp
                               Name 23  "atomu"
                               Name 24  "value"
                               Name 36  "imagei"
-                              Name 45  "imageu"
-                              Name 65  "BufferU"
-                              MemberName 65(BufferU) 0  "x"
-                              Name 67  "bufferu"
-                              Name 72  "y"
-                              Name 77  "BufferI"
-                              MemberName 77(BufferI) 0  "x"
-                              Name 79  "bufferi"
-                              Name 83  "A"
-                              MemberName 83(A) 0  "x"
-                              Name 84  "BufferJ"
-                              MemberName 84(BufferJ) 0  "a"
-                              Name 87  "bufferj"
-                              Name 98  "BufferK"
-                              MemberName 98(BufferK) 0  "x"
-                              Name 100  "bufferk"
-                              Name 110  "imagej"
-                              Name 122  "samp"
-                              Name 133  "atomu64"
-                              Name 138  "atomi64"
-                              Name 143  "BufferL"
-                              MemberName 143(BufferL) 0  "x"
-                              Name 145  "bufferl"
+                              Name 46  "imageu"
+                              Name 66  "BufferU"
+                              MemberName 66(BufferU) 0  "x"
+                              Name 68  "bufferu"
+                              Name 73  "y"
+                              Name 78  "BufferI"
+                              MemberName 78(BufferI) 0  "x"
+                              Name 80  "bufferi"
+                              Name 84  "A"
+                              MemberName 84(A) 0  "x"
+                              Name 85  "BufferJ"
+                              MemberName 85(BufferJ) 0  "a"
+                              Name 88  "bufferj"
+                              Name 99  "BufferK"
+                              MemberName 99(BufferK) 0  "x"
+                              Name 101  "bufferk"
+                              Name 111  "imagej"
+                              Name 123  "samp"
+                              Name 134  "atomu64"
+                              Name 139  "atomi64"
+                              Name 144  "BufferL"
+                              MemberName 144(BufferL) 0  "x"
+                              Name 146  "bufferl"
+                              Name 151  "BufferM"
+                              MemberName 151(BufferM) 0  "x"
+                              Name 153  "bufferm"
                               Decorate 36(imagei) DescriptorSet 0
                               Decorate 36(imagei) Binding 1
-                              Decorate 45(imageu) DescriptorSet 0
-                              Decorate 45(imageu) Binding 0
-                              MemberDecorate 65(BufferU) 0 Offset 0
-                              Decorate 65(BufferU) Block
-                              Decorate 67(bufferu) DescriptorSet 0
-                              Decorate 67(bufferu) Binding 2
-                              MemberDecorate 77(BufferI) 0 Offset 0
-                              Decorate 77(BufferI) Block
-                              Decorate 79(bufferi) DescriptorSet 0
-                              Decorate 79(bufferi) Binding 3
-                              Decorate 82 ArrayStride 4
-                              MemberDecorate 83(A) 0 Offset 0
-                              MemberDecorate 84(BufferJ) 0 Offset 0
-                              Decorate 84(BufferJ) Block
-                              Decorate 87(bufferj) DescriptorSet 0
-                              Decorate 87(bufferj) Binding 4
-                              MemberDecorate 98(BufferK) 0 Offset 0
-                              Decorate 98(BufferK) Block
-                              Decorate 100(bufferk) DescriptorSet 0
-                              Decorate 100(bufferk) Binding 7
-                              Decorate 110(imagej) DescriptorSet 0
-                              Decorate 110(imagej) Binding 5
-                              Decorate 122(samp) DescriptorSet 0
-                              Decorate 122(samp) Binding 6
-                              MemberDecorate 143(BufferL) 0 Offset 0
-                              Decorate 143(BufferL) Block
-                              Decorate 145(bufferl) DescriptorSet 0
-                              Decorate 145(bufferl) Binding 8
+                              Decorate 46(imageu) DescriptorSet 0
+                              Decorate 46(imageu) Binding 0
+                              MemberDecorate 66(BufferU) 0 Offset 0
+                              Decorate 66(BufferU) Block
+                              Decorate 68(bufferu) DescriptorSet 0
+                              Decorate 68(bufferu) Binding 2
+                              MemberDecorate 78(BufferI) 0 Offset 0
+                              Decorate 78(BufferI) Block
+                              Decorate 80(bufferi) DescriptorSet 0
+                              Decorate 80(bufferi) Binding 3
+                              Decorate 83 ArrayStride 4
+                              MemberDecorate 84(A) 0 Offset 0
+                              MemberDecorate 85(BufferJ) 0 Offset 0
+                              Decorate 85(BufferJ) Block
+                              Decorate 88(bufferj) DescriptorSet 0
+                              Decorate 88(bufferj) Binding 4
+                              MemberDecorate 99(BufferK) 0 Offset 0
+                              Decorate 99(BufferK) Block
+                              Decorate 101(bufferk) DescriptorSet 0
+                              Decorate 101(bufferk) Binding 7
+                              Decorate 111(imagej) DescriptorSet 0
+                              Decorate 111(imagej) Binding 5
+                              Decorate 123(samp) DescriptorSet 0
+                              Decorate 123(samp) Binding 6
+                              MemberDecorate 144(BufferL) 0 Offset 0
+                              Decorate 144(BufferL) Block
+                              Decorate 146(bufferl) DescriptorSet 0
+                              Decorate 146(bufferl) Binding 8
+                              MemberDecorate 151(BufferM) 0 Offset 0
+                              Decorate 151(BufferM) Block
+                              Decorate 153(bufferm) DescriptorSet 0
+                              Decorate 153(bufferm) Binding 9
                2:             TypeVoid
                3:             TypeFunction 2
                6:             TypeInt 32 1
@@ -106,67 +113,72 @@ spv.memoryScopeSemantics.comp
               38:      6(int) Constant 0
               39:   37(ivec2) ConstantComposite 38 38
               40:             TypePointer Image 6(int)
-              43:             TypeImage 15(int) 2D nonsampled format:R32ui
-              44:             TypePointer UniformConstant 43
-      45(imageu):     44(ptr) Variable UniformConstant
-              46:     15(int) Constant 3
-              47:             TypePointer Image 15(int)
-              50:     15(int) Constant 4
-              52:     15(int) Constant 7
-              57:      6(int) Constant 7
-              61:     15(int) Constant 10
-              63:     15(int) Constant 322
-     65(BufferU):             TypeStruct 15(int)
-              66:             TypePointer StorageBuffer 65(BufferU)
-     67(bufferu):     66(ptr) Variable StorageBuffer
-              68:             TypePointer StorageBuffer 15(int)
-              70:     15(int) Constant 1
-     77(BufferI):             TypeStruct 15(int)
-              78:             TypePointer StorageBuffer 77(BufferI)
-     79(bufferi):     78(ptr) Variable StorageBuffer
-              82:             TypeArray 15(int) 26
-           83(A):             TypeStruct 82
-     84(BufferJ):             TypeStruct 83(A)
-              85:             TypeArray 84(BufferJ) 26
-              86:             TypePointer StorageBuffer 85
-     87(bufferj):     86(ptr) Variable StorageBuffer
-              94:             TypePointer StorageBuffer 83(A)
-     98(BufferK):             TypeStruct 15(int)
-              99:             TypePointer Uniform 98(BufferK)
-    100(bufferk):     99(ptr) Variable Uniform
-             101:             TypePointer Uniform 15(int)
-             106:             TypeVector 6(int) 4
-             108:             TypeArray 34 26
-             109:             TypePointer UniformConstant 108
-     110(imagej):    109(ptr) Variable UniformConstant
-             116:  106(ivec4) ConstantComposite 38 38 38 38
-             117:             TypeFloat 32
-             118:             TypeImage 117(float) 2D sampled format:Unknown
-             119:             TypeSampledImage 118
-             120:             TypeArray 119 26
-             121:             TypePointer UniformConstant 120
-       122(samp):    121(ptr) Variable UniformConstant
-             123:             TypePointer UniformConstant 119
-             126:             TypeVector 117(float) 2
-             127:  117(float) Constant 0
-             128:  126(fvec2) ConstantComposite 127 127
-             129:             TypeVector 117(float) 4
-             131:             TypeInt 64 0
-             132:             TypePointer Workgroup 131(int64_t)
-    133(atomu64):    132(ptr) Variable Workgroup
-             134:131(int64_t) Constant 7 0
-             136:             TypeInt 64 1
-             137:             TypePointer Workgroup 136(int64_t)
-    138(atomi64):    137(ptr) Variable Workgroup
-             139:136(int64_t) Constant 10 0
-    143(BufferL):             TypeStruct 15(int)
-             144:             TypePointer StorageBuffer 143(BufferL)
-    145(bufferl):    144(ptr) Variable StorageBuffer
+              42:     15(int) Constant 32768
+              44:             TypeImage 15(int) 2D nonsampled format:R32ui
+              45:             TypePointer UniformConstant 44
+      46(imageu):     45(ptr) Variable UniformConstant
+              47:     15(int) Constant 3
+              48:             TypePointer Image 15(int)
+              51:     15(int) Constant 4
+              53:     15(int) Constant 7
+              58:      6(int) Constant 7
+              62:     15(int) Constant 10
+              64:     15(int) Constant 322
+     66(BufferU):             TypeStruct 15(int)
+              67:             TypePointer StorageBuffer 66(BufferU)
+     68(bufferu):     67(ptr) Variable StorageBuffer
+              69:             TypePointer StorageBuffer 15(int)
+              71:     15(int) Constant 1
+     78(BufferI):             TypeStruct 15(int)
+              79:             TypePointer StorageBuffer 78(BufferI)
+     80(bufferi):     79(ptr) Variable StorageBuffer
+              83:             TypeArray 15(int) 26
+           84(A):             TypeStruct 83
+     85(BufferJ):             TypeStruct 84(A)
+              86:             TypeArray 85(BufferJ) 26
+              87:             TypePointer StorageBuffer 86
+     88(bufferj):     87(ptr) Variable StorageBuffer
+              95:             TypePointer StorageBuffer 84(A)
+     99(BufferK):             TypeStruct 15(int)
+             100:             TypePointer Uniform 99(BufferK)
+    101(bufferk):    100(ptr) Variable Uniform
+             102:             TypePointer Uniform 15(int)
+             107:             TypeVector 6(int) 4
+             109:             TypeArray 34 26
+             110:             TypePointer UniformConstant 109
+     111(imagej):    110(ptr) Variable UniformConstant
+             117:  107(ivec4) ConstantComposite 38 38 38 38
+             118:             TypeFloat 32
+             119:             TypeImage 118(float) 2D sampled format:Unknown
+             120:             TypeSampledImage 119
+             121:             TypeArray 120 26
+             122:             TypePointer UniformConstant 121
+       123(samp):    122(ptr) Variable UniformConstant
+             124:             TypePointer UniformConstant 120
+             127:             TypeVector 118(float) 2
+             128:  118(float) Constant 0
+             129:  127(fvec2) ConstantComposite 128 128
+             130:             TypeVector 118(float) 4
+             132:             TypeInt 64 0
+             133:             TypePointer Workgroup 132(int64_t)
+    134(atomu64):    133(ptr) Variable Workgroup
+             135:132(int64_t) Constant 7 0
+             137:             TypeInt 64 1
+             138:             TypePointer Workgroup 137(int64_t)
+    139(atomi64):    138(ptr) Variable Workgroup
+             140:137(int64_t) Constant 10 0
+    144(BufferL):             TypeStruct 15(int)
+             145:             TypePointer StorageBuffer 144(BufferL)
+    146(bufferl):    145(ptr) Variable StorageBuffer
+    151(BufferM):             TypeStruct 15(int)
+             152:             TypePointer StorageBuffer 151(BufferM)
+    153(bufferm):    152(ptr) Variable StorageBuffer
+             161:      6(int) Constant 32768
          4(main):           2 Function None 3
                5:             Label
         8(origi):      7(ptr) Variable Function
        21(origu):     20(ptr) Variable Function
-           72(y):     20(ptr) Variable Function
+           73(y):     20(ptr) Variable Function
               19:      6(int) AtomicIAdd 10(atomi) 12 18 11
                               Store 8(origi) 19
               25:     15(int) Load 24(value) MakePointerVisibleKHR NonPrivatePointerKHR 26
@@ -177,77 +189,87 @@ spv.memoryScopeSemantics.comp
               32:     15(int) Load 24(value) MakePointerVisibleKHR NonPrivatePointerKHR 26
                               AtomicStore 23(atomu) 12 33 32
               41:     40(ptr) ImageTexelPointer 36(imagei) 39 17
-              42:      6(int) AtomicLoad 41 12 30
-                              Store 8(origi) 42
-              48:     47(ptr) ImageTexelPointer 45(imageu) 39 17
-              49:     15(int) AtomicIAdd 48 12 30 46
-                              Store 21(origu) 49
-              51:     47(ptr) ImageTexelPointer 45(imageu) 39 17
-                              AtomicStore 51 12 33 50
-              53:     15(int) AtomicOr 23(atomu) 12 17 52
-                              Store 21(origu) 53
-              54:     15(int) AtomicXor 23(atomu) 12 17 52
+              43:      6(int) AtomicLoad 41 12 30
+                              Store 8(origi) 43
+              49:     48(ptr) ImageTexelPointer 46(imageu) 39 17
+              50:     15(int) AtomicIAdd 49 12 30 47
+                              Store 21(origu) 50
+              52:     48(ptr) ImageTexelPointer 46(imageu) 39 17
+                              AtomicStore 52 12 33 51
+              54:     15(int) AtomicOr 23(atomu) 12 17 53
                               Store 21(origu) 54
-              55:     15(int) Load 24(value) MakePointerVisibleKHR NonPrivatePointerKHR 26
-              56:     15(int) AtomicUMin 23(atomu) 12 17 55
-                              Store 21(origu) 56
-              58:      6(int) AtomicSMax 10(atomi) 12 17 57
-                              Store 8(origi) 58
-              59:      6(int) Load 8(origi)
-              60:      6(int) AtomicExchange 10(atomi) 12 17 59
-                              Store 8(origi) 60
-              62:     15(int) Load 24(value) MakePointerVisibleKHR NonPrivatePointerKHR 26
-              64:     15(int) AtomicCompareExchange 23(atomu) 12 63 63 62 61
-                              Store 21(origu) 64
-              69:     68(ptr) AccessChain 67(bufferu) 38
-              71:     15(int) AtomicIAdd 69 12 18 70
+              55:     15(int) AtomicXor 23(atomu) 12 17 53
+                              Store 21(origu) 55
+              56:     15(int) Load 24(value) MakePointerVisibleKHR NonPrivatePointerKHR 26
+              57:     15(int) AtomicUMin 23(atomu) 12 17 56
+                              Store 21(origu) 57
+              59:      6(int) AtomicSMax 10(atomi) 12 17 58
+                              Store 8(origi) 59
+              60:      6(int) Load 8(origi)
+              61:      6(int) AtomicExchange 10(atomi) 12 17 60
+                              Store 8(origi) 61
+              63:     15(int) Load 24(value) MakePointerVisibleKHR NonPrivatePointerKHR 26
+              65:     15(int) AtomicCompareExchange 23(atomu) 12 64 64 63 62
+                              Store 21(origu) 65
+              70:     69(ptr) AccessChain 68(bufferu) 38
+              72:     15(int) AtomicIAdd 70 12 18 71
                               MemoryBarrier 26 18
-                              ControlBarrier 26 26 63
+                              ControlBarrier 26 26 64
                               ControlBarrier 26 26 17
-              73:     68(ptr) AccessChain 67(bufferu) 38
-              74:     15(int) Load 73 MakePointerVisibleKHR NonPrivatePointerKHR 26
-                              Store 72(y) 74
-              75:     15(int) Load 72(y)
-              76:     68(ptr) AccessChain 67(bufferu) 38
-                              Store 76 75 MakePointerAvailableKHR NonPrivatePointerKHR 26
-              80:     68(ptr) AccessChain 79(bufferi) 38
-              81:     15(int) Load 80 MakePointerVisibleKHR NonPrivatePointerKHR 16
-                              Store 72(y) 81
-              88:     68(ptr) AccessChain 87(bufferj) 38 38 38 12
-              89:     15(int) Load 88 Volatile MakePointerVisibleKHR NonPrivatePointerKHR 16
-                              Store 72(y) 89
-              90:     15(int) Load 72(y)
-              91:     68(ptr) AccessChain 79(bufferi) 38
-                              Store 91 90 MakePointerAvailableKHR NonPrivatePointerKHR 16
-              92:     15(int) Load 72(y)
-              93:     68(ptr) AccessChain 87(bufferj) 38 38 38 12
-                              Store 93 92 Volatile MakePointerAvailableKHR NonPrivatePointerKHR 16
-              95:     94(ptr) AccessChain 87(bufferj) 12 38
-              96:       83(A) Load 95 Volatile MakePointerVisibleKHR NonPrivatePointerKHR 16
-              97:     94(ptr) AccessChain 87(bufferj) 38 38
-                              Store 97 96 Volatile MakePointerAvailableKHR NonPrivatePointerKHR 16
-             102:    101(ptr) AccessChain 100(bufferk) 38
-             103:     15(int) Load 102 NonPrivatePointerKHR 
-             104:     68(ptr) AccessChain 79(bufferi) 38
-                              Store 104 103 MakePointerAvailableKHR NonPrivatePointerKHR 16
-             105:          34 Load 36(imagei)
-             107:  106(ivec4) ImageRead 105 39 MakeTexelVisibleKHR NonPrivateTexelKHR VolatileTexelKHR 16
-             111:     35(ptr) AccessChain 110(imagej) 38
-             112:          34 Load 111
-             113:  106(ivec4) ImageRead 112 39 NonPrivateTexelKHR 
-             114:     35(ptr) AccessChain 110(imagej) 12
-             115:          34 Load 114
-                              ImageWrite 115 39 116 NonPrivateTexelKHR 
-             124:    123(ptr) AccessChain 122(samp) 38
-             125:         119 Load 124
-             130:  129(fvec4) ImageSampleExplicitLod 125 128 Lod NonPrivateTexelKHR 127
-             135:131(int64_t) AtomicUMax 133(atomu64) 12 17 134
-                              Store 133(atomu64) 135 MakePointerAvailableKHR NonPrivatePointerKHR 26
-             140:131(int64_t) Load 133(atomu64) MakePointerVisibleKHR NonPrivatePointerKHR 26
-             141:136(int64_t) Bitcast 140
-             142:136(int64_t) AtomicCompareExchange 138(atomi64) 12 63 63 141 139
-             146:     68(ptr) AccessChain 145(bufferl) 38
-             147:     15(int) Load 146 Volatile MakePointerVisibleKHR NonPrivatePointerKHR 16
-                              Store 72(y) 147
+              74:     69(ptr) AccessChain 68(bufferu) 38
+              75:     15(int) Load 74 MakePointerVisibleKHR NonPrivatePointerKHR 26
+                              Store 73(y) 75
+              76:     15(int) Load 73(y)
+              77:     69(ptr) AccessChain 68(bufferu) 38
+                              Store 77 76 MakePointerAvailableKHR NonPrivatePointerKHR 26
+              81:     69(ptr) AccessChain 80(bufferi) 38
+              82:     15(int) Load 81 MakePointerVisibleKHR NonPrivatePointerKHR 16
+                              Store 73(y) 82
+              89:     69(ptr) AccessChain 88(bufferj) 38 38 38 12
+              90:     15(int) Load 89 Volatile MakePointerVisibleKHR NonPrivatePointerKHR 16
+                              Store 73(y) 90
+              91:     15(int) Load 73(y)
+              92:     69(ptr) AccessChain 80(bufferi) 38
+                              Store 92 91 MakePointerAvailableKHR NonPrivatePointerKHR 16
+              93:     15(int) Load 73(y)
+              94:     69(ptr) AccessChain 88(bufferj) 38 38 38 12
+                              Store 94 93 Volatile MakePointerAvailableKHR NonPrivatePointerKHR 16
+              96:     95(ptr) AccessChain 88(bufferj) 12 38
+              97:       84(A) Load 96 Volatile MakePointerVisibleKHR NonPrivatePointerKHR 16
+              98:     95(ptr) AccessChain 88(bufferj) 38 38
+                              Store 98 97 Volatile MakePointerAvailableKHR NonPrivatePointerKHR 16
+             103:    102(ptr) AccessChain 101(bufferk) 38
+             104:     15(int) Load 103 NonPrivatePointerKHR 
+             105:     69(ptr) AccessChain 80(bufferi) 38
+                              Store 105 104 MakePointerAvailableKHR NonPrivatePointerKHR 16
+             106:          34 Load 36(imagei)
+             108:  107(ivec4) ImageRead 106 39 MakeTexelVisibleKHR NonPrivateTexelKHR VolatileTexelKHR 16
+             112:     35(ptr) AccessChain 111(imagej) 38
+             113:          34 Load 112
+             114:  107(ivec4) ImageRead 113 39 NonPrivateTexelKHR 
+             115:     35(ptr) AccessChain 111(imagej) 12
+             116:          34 Load 115
+                              ImageWrite 116 39 117 NonPrivateTexelKHR 
+             125:    124(ptr) AccessChain 123(samp) 38
+             126:         120 Load 125
+             131:  130(fvec4) ImageSampleExplicitLod 126 129 Lod NonPrivateTexelKHR 128
+             136:132(int64_t) AtomicUMax 134(atomu64) 12 17 135
+                              Store 134(atomu64) 136 MakePointerAvailableKHR NonPrivatePointerKHR 26
+             141:132(int64_t) Load 134(atomu64) MakePointerVisibleKHR NonPrivatePointerKHR 26
+             142:137(int64_t) Bitcast 141
+             143:137(int64_t) AtomicCompareExchange 139(atomi64) 12 64 64 142 140
+             147:     69(ptr) AccessChain 146(bufferl) 38
+             148:     15(int) Load 147 Volatile MakePointerVisibleKHR NonPrivatePointerKHR 16
+                              Store 73(y) 148
+             149:     69(ptr) AccessChain 146(bufferl) 38
+             150:     15(int) AtomicIAdd 149 16 42 71
+             154:     69(ptr) AccessChain 153(bufferm) 38
+             155:     15(int) AtomicOr 154 16 42 26
+             156:     40(ptr) ImageTexelPointer 36(imagei) 39 17
+             157:      6(int) AtomicIAdd 156 16 42 11
+             158:     69(ptr) AccessChain 68(bufferu) 38
+             159:     15(int) AtomicIAdd 158 12 17 51
+             160:     69(ptr) AccessChain 68(bufferu) 38
+             162:     15(int) AtomicIAdd 160 12 42 16
                               Return
                               FunctionEnd
index c4149d8..6de93fd 100644 (file)
@@ -11,7 +11,9 @@ ERROR: 0:23: 'atomicAdd' : Semantics must not include multiple of gl_SemanticsRe
 ERROR: 0:24: 'atomicCompSwap' : semUnequal must not be gl_SemanticsRelease or gl_SemanticsAcquireRelease 
 ERROR: 0:25: 'memoryBarrier' : gl_SemanticsMakeVisible requires gl_SemanticsAcquire or gl_SemanticsAcquireRelease 
 ERROR: 0:26: 'memoryBarrier' : gl_SemanticsMakeAvailable requires gl_SemanticsRelease or gl_SemanticsAcquireRelease 
-ERROR: 12 compilation errors.  No code generated.
+ERROR: 0:27: 'memoryBarrier' : gl_SemanticsVolatile must not be used with memoryBarrier or controlBarrier 
+ERROR: 0:28: 'atomicCompSwap' : semEqual and semUnequal must either both include gl_SemanticsVolatile or neither 
+ERROR: 14 compilation errors.  No code generated.
 
 
 SPIR-V is not generated for failed compile or link
index 88f5481..037e6d7 100644 (file)
@@ -19,6 +19,7 @@ layout (binding = 7) nonprivate uniform BufferK { uint x; } bufferk;
 shared uint64_t atomu64;\r
 shared int64_t atomi64;\r
 layout (binding = 8) volatile buffer BufferL { uint x; } bufferl;\r
+layout (binding = 9) buffer BufferM { volatile uint x; } bufferm;\r
 \r
 \r
 void main()\r
@@ -60,5 +61,10 @@ void main()
     atomicCompSwap(atomi64, int64_t(10), int64_t(atomu64), gl_ScopeDevice, gl_StorageSemanticsBuffer | gl_StorageSemanticsShared, gl_SemanticsAcquire, gl_StorageSemanticsBuffer | gl_StorageSemanticsShared, gl_SemanticsAcquire);\r
 \r
     y = bufferl.x;\r
+    atomicAdd(bufferl.x, 1);\r
+    atomicOr(bufferm.x, 2);\r
+    imageAtomicAdd(imagei, ivec2(0,0), 3);\r
+    atomicAdd(bufferu.x, 4u, gl_ScopeDevice, 0, 0);\r
+    atomicAdd(bufferu.x, 5u, gl_ScopeDevice, 0, gl_SemanticsVolatile);\r
 }\r
 \r
index 4e18b2e..1b85671 100644 (file)
@@ -24,5 +24,7 @@ void main()
     uint origu = atomicCompSwap(atomu, 10u, value, gl_ScopeDevice, gl_StorageSemanticsBuffer | gl_StorageSemanticsShared, gl_SemanticsAcquire, gl_StorageSemanticsBuffer | gl_StorageSemanticsShared, gl_SemanticsAcquireRelease);\r
     memoryBarrier(gl_ScopeWorkgroup, gl_StorageSemanticsBuffer, gl_SemanticsRelease | gl_SemanticsMakeVisible);\r
     memoryBarrier(gl_ScopeWorkgroup, gl_StorageSemanticsBuffer, gl_SemanticsAcquire | gl_SemanticsMakeAvailable);\r
+    memoryBarrier(gl_ScopeWorkgroup, gl_StorageSemanticsBuffer, gl_SemanticsRelease | gl_SemanticsVolatile);\r
+    atomicCompSwap(bufferi.x, 10u, 10u, gl_ScopeDevice, gl_StorageSemanticsBuffer, gl_SemanticsAcquire | gl_SemanticsVolatile, gl_StorageSemanticsBuffer, gl_SemanticsAcquire);\r
 }\r
 \r
index afaf2d6..169fef0 100644 (file)
@@ -6309,6 +6309,7 @@ void TBuiltIns::initialize(int version, EProfile profile, const SpvVersion& spvV
         commonBuiltins.append("const int gl_SemanticsAcquireRelease  = 0x8;\n");
         commonBuiltins.append("const int gl_SemanticsMakeAvailable   = 0x2000;\n");
         commonBuiltins.append("const int gl_SemanticsMakeVisible     = 0x4000;\n");
+        commonBuiltins.append("const int gl_SemanticsVolatile        = 0x8000;\n");
 
         commonBuiltins.append("const int gl_StorageSemanticsNone     = 0x0;\n");
         commonBuiltins.append("const int gl_StorageSemanticsBuffer   = 0x40;\n");
@@ -8630,6 +8631,7 @@ void TBuiltIns::identifyBuiltIns(int version, EProfile profile, const SpvVersion
             symbolTable.setVariableExtensions("gl_SemanticsAcquireRelease", 1, &E_GL_KHR_memory_scope_semantics);
             symbolTable.setVariableExtensions("gl_SemanticsMakeAvailable",  1, &E_GL_KHR_memory_scope_semantics);
             symbolTable.setVariableExtensions("gl_SemanticsMakeVisible",    1, &E_GL_KHR_memory_scope_semantics);
+            symbolTable.setVariableExtensions("gl_SemanticsVolatile",       1, &E_GL_KHR_memory_scope_semantics);
 
             symbolTable.setVariableExtensions("gl_StorageSemanticsNone",    1, &E_GL_KHR_memory_scope_semantics);
             symbolTable.setVariableExtensions("gl_StorageSemanticsBuffer",  1, &E_GL_KHR_memory_scope_semantics);
index 8e570ae..57cc5f9 100644 (file)
@@ -1641,6 +1641,7 @@ void TParseContext::memorySemanticsCheck(const TSourceLoc& loc, const TFunction&
     const int gl_SemanticsAcquireRelease  = 0x8;
     const int gl_SemanticsMakeAvailable   = 0x2000;
     const int gl_SemanticsMakeVisible     = 0x4000;
+    const int gl_SemanticsVolatile        = 0x8000;
 
     //const int gl_StorageSemanticsNone     = 0x0;
     const int gl_StorageSemanticsBuffer   = 0x40;
@@ -1730,7 +1731,8 @@ void TParseContext::memorySemanticsCheck(const TSourceLoc& loc, const TFunction&
                                       gl_SemanticsRelease |
                                       gl_SemanticsAcquireRelease |
                                       gl_SemanticsMakeAvailable |
-                                      gl_SemanticsMakeVisible))) {
+                                      gl_SemanticsMakeVisible |
+                                      gl_SemanticsVolatile))) {
         error(loc, "Invalid semantics value", fnCandidate.getName().c_str(), "");
     }
     if (((storageClassSemantics | storageClassSemantics2) & ~(gl_StorageSemanticsBuffer |
@@ -1782,7 +1784,16 @@ void TParseContext::memorySemanticsCheck(const TSourceLoc& loc, const TFunction&
         error(loc, "gl_SemanticsMakeVisible requires gl_SemanticsAcquire or gl_SemanticsAcquireRelease",
               fnCandidate.getName().c_str(), "");
     }
-
+    if ((semantics & gl_SemanticsVolatile) &&
+        (callNode.getOp() == EOpMemoryBarrier || callNode.getOp() == EOpBarrier)) {
+        error(loc, "gl_SemanticsVolatile must not be used with memoryBarrier or controlBarrier",
+              fnCandidate.getName().c_str(), "");
+    }
+    if ((callNode.getOp() == EOpAtomicCompSwap || callNode.getOp() == EOpImageAtomicCompSwap) &&
+        ((semantics ^ semantics2) & gl_SemanticsVolatile)) {
+        error(loc, "semEqual and semUnequal must either both include gl_SemanticsVolatile or neither",
+              fnCandidate.getName().c_str(), "");
+    }
 }