Browse Source

Updated glslang.

Branimir Karadžić 9 years ago
parent
commit
0d93dd074d
54 changed files with 1700 additions and 1099 deletions
  1. 10 1
      3rdparty/glslang/CMakeLists.txt
  2. 5 0
      3rdparty/glslang/SPIRV/CMakeLists.txt
  3. 49 0
      3rdparty/glslang/SPIRV/GLSL.ext.NV.h
  4. 36 6
      3rdparty/glslang/SPIRV/GlslangToSpv.cpp
  5. 48 20
      3rdparty/glslang/SPIRV/SPVRemapper.cpp
  6. 2 2
      3rdparty/glslang/SPIRV/SPVRemapper.h
  7. 37 0
      3rdparty/glslang/SPIRV/disassemble.cpp
  8. 17 0
      3rdparty/glslang/SPIRV/doc.cpp
  9. 1 0
      3rdparty/glslang/SPIRV/spirv.hpp
  10. 6 5
      3rdparty/glslang/Test/baseResults/120.vert.out
  11. 5 5
      3rdparty/glslang/Test/baseResults/130.vert.out
  12. 2 1
      3rdparty/glslang/Test/baseResults/cppBad.vert.out
  13. 55 33
      3rdparty/glslang/Test/baseResults/hlsl.identifier.sample.frag.out
  14. 14 15
      3rdparty/glslang/Test/baseResults/remap.basic.dcefunc.frag.out
  15. 12 12
      3rdparty/glslang/Test/baseResults/remap.basic.none.frag.out
  16. 10 10
      3rdparty/glslang/Test/baseResults/remap.basic.strip.frag.out
  17. 11 11
      3rdparty/glslang/Test/baseResults/remap.hlsl.sample.basic.none.frag.out
  18. 5 5
      3rdparty/glslang/Test/baseResults/remap.hlsl.sample.basic.strip.frag.out
  19. 6 6
      3rdparty/glslang/Test/baseResults/remap.hlsl.templatetypes.none.frag.out
  20. 58 58
      3rdparty/glslang/Test/baseResults/remap.similar_1a.none.frag.out
  21. 60 60
      3rdparty/glslang/Test/baseResults/remap.similar_1b.none.frag.out
  22. 20 20
      3rdparty/glslang/Test/baseResults/remap.switch.none.frag.out
  23. 46 0
      3rdparty/glslang/Test/baseResults/spv.GeometryShaderPassthrough.geom.out
  24. 42 0
      3rdparty/glslang/Test/baseResults/spv.sampleMaskOverrideCoverage.frag.out
  25. 262 264
      3rdparty/glslang/Test/baseResults/spv.shaderBallot.comp.out
  26. 112 0
      3rdparty/glslang/Test/baseResults/tokenPaste.vert.out
  27. 2 2
      3rdparty/glslang/Test/hlsl.identifier.sample.frag
  28. 17 0
      3rdparty/glslang/Test/spv.GeometryShaderPassthrough.geom
  29. 7 0
      3rdparty/glslang/Test/spv.sampleMaskOverrideCoverage.frag
  30. 70 0
      3rdparty/glslang/Test/tokenPaste.vert
  31. 25 0
      3rdparty/glslang/glslang/Include/Types.h
  32. 2 2
      3rdparty/glslang/glslang/Include/revision.h
  33. 51 2
      3rdparty/glslang/glslang/MachineIndependent/ParseHelper.cpp
  34. 8 9
      3rdparty/glslang/glslang/MachineIndependent/ParseHelper.h
  35. 10 9
      3rdparty/glslang/glslang/MachineIndependent/Scan.cpp
  36. 13 9
      3rdparty/glslang/glslang/MachineIndependent/ShaderLang.cpp
  37. 10 0
      3rdparty/glslang/glslang/MachineIndependent/Versions.cpp
  38. 4 0
      3rdparty/glslang/glslang/MachineIndependent/Versions.h
  39. 10 2
      3rdparty/glslang/glslang/MachineIndependent/linkValidate.cpp
  40. 16 0
      3rdparty/glslang/glslang/MachineIndependent/localintermediate.h
  41. 177 127
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/Pp.cpp
  42. 11 50
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpAtom.cpp
  43. 1 7
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpContext.cpp
  44. 127 97
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpContext.h
  45. 0 80
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpMemory.cpp
  46. 113 49
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpScanner.cpp
  47. 0 57
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpSymbols.cpp
  48. 53 32
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpTokens.cpp
  49. 5 6
      3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpTokens.h
  50. 1 0
      3rdparty/glslang/gtests/AST.FromFile.cpp
  51. 2 0
      3rdparty/glslang/gtests/Spv.FromFile.cpp
  52. 14 6
      3rdparty/glslang/hlsl/hlslGrammar.cpp
  53. 9 9
      3rdparty/glslang/hlsl/hlslParseHelper.h
  54. 11 10
      3rdparty/glslang/hlsl/hlslScanContext.cpp

+ 10 - 1
3rdparty/glslang/CMakeLists.txt

@@ -2,6 +2,9 @@ cmake_minimum_required(VERSION 2.8.11)
 set_property(GLOBAL PROPERTY USE_FOLDERS ON)
 set_property(GLOBAL PROPERTY USE_FOLDERS ON)
 
 
 option(ENABLE_AMD_EXTENSIONS "Enables support of AMD-specific extensions" ON)
 option(ENABLE_AMD_EXTENSIONS "Enables support of AMD-specific extensions" ON)
+option(ENABLE_GLSLANG_BINARIES "Builds glslangValidator and spirv-remap" ON)
+
+option(ENABLE_NV_EXTENSIONS "Enables support of Nvidia-specific extensions" ON)
 
 
 enable_testing()
 enable_testing()
 
 
@@ -13,6 +16,10 @@ if(ENABLE_AMD_EXTENSIONS)
     add_definitions(-DAMD_EXTENSIONS)
     add_definitions(-DAMD_EXTENSIONS)
 endif(ENABLE_AMD_EXTENSIONS)
 endif(ENABLE_AMD_EXTENSIONS)
 
 
+if(ENABLE_NV_EXTENSIONS)
+    add_definitions(-DNV_EXTENSIONS)
+endif(ENABLE_NV_EXTENSIONS)
+
 if(WIN32)
 if(WIN32)
     set(CMAKE_DEBUG_POSTFIX "d")
     set(CMAKE_DEBUG_POSTFIX "d")
     include(ChooseMSVCCRT.cmake)
     include(ChooseMSVCCRT.cmake)
@@ -52,7 +59,9 @@ add_subdirectory(External)
 
 
 add_subdirectory(glslang)
 add_subdirectory(glslang)
 add_subdirectory(OGLCompilersDLL)
 add_subdirectory(OGLCompilersDLL)
-add_subdirectory(StandAlone)
+if(ENABLE_GLSLANG_BINARIES)
+	add_subdirectory(StandAlone)
+endif()
 add_subdirectory(SPIRV)
 add_subdirectory(SPIRV)
 add_subdirectory(hlsl)
 add_subdirectory(hlsl)
 add_subdirectory(gtests)
 add_subdirectory(gtests)

+ 5 - 0
3rdparty/glslang/SPIRV/CMakeLists.txt

@@ -33,6 +33,11 @@ if(ENABLE_AMD_EXTENSIONS)
          GLSL.ext.AMD.h)
          GLSL.ext.AMD.h)
 endif(ENABLE_AMD_EXTENSIONS)
 endif(ENABLE_AMD_EXTENSIONS)
 
 
+if(ENABLE_NV_EXTENSIONS)
+    set(HEADERS
+        GLSL.ext.NV.h)
+endif(ENABLE_NV_EXTENSIONS)
+
 add_library(SPIRV STATIC ${SOURCES} ${HEADERS})
 add_library(SPIRV STATIC ${SOURCES} ${HEADERS})
 set_property(TARGET SPIRV PROPERTY FOLDER glslang)
 set_property(TARGET SPIRV PROPERTY FOLDER glslang)
 
 

+ 49 - 0
3rdparty/glslang/SPIRV/GLSL.ext.NV.h

@@ -0,0 +1,49 @@
+/*
+** Copyright (c) 2014-2016 The Khronos Group Inc.
+**
+** Permission is hereby granted, free of charge, to any person obtaining a copy
+** of this software and/or associated documentation files (the "Materials"),
+** to deal in the Materials without restriction, including without limitation
+** the rights to use, copy, modify, merge, publish, distribute, sublicense,
+** and/or sell copies of the Materials, and to permit persons to whom the
+** Materials are furnished to do so, subject to the following conditions:
+**
+** The above copyright notice and this permission notice shall be included in
+** all copies or substantial portions of the Materials.
+**
+** MODIFICATIONS TO THIS FILE MAY MEAN IT NO LONGER ACCURATELY REFLECTS KHRONOS
+** STANDARDS. THE UNMODIFIED, NORMATIVE VERSIONS OF KHRONOS SPECIFICATIONS AND
+** HEADER INFORMATION ARE LOCATED AT https://www.khronos.org/registry/
+**
+** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+** OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+** FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+** THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+** LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+** FROM,OUT OF OR IN CONNECTION WITH THE MATERIALS OR THE USE OR OTHER DEALINGS
+** IN THE MATERIALS.
+*/
+
+#ifndef GLSLextNV_H
+#define GLSLextNV_H
+
+enum BuiltIn;
+enum Decoration;
+enum Op;
+
+static const int GLSLextNVVersion = 100;
+static const int GLSLextNVRevision = 2;
+
+//SPV_NV_sample_mask_override_coverage
+const char* const E_SPV_NV_sample_mask_override_coverage = "SPV_NV_sample_mask_override_coverage";
+
+static const Decoration OverrideCoverageNV = static_cast<Decoration>(5248);
+
+
+//SPV_NV_geometry_shader_passthrough
+const char* const E_SPV_NV_geometry_shader_passthrough = "SPV_NV_geometry_shader_passthrough";
+
+static const Decoration PassthroughNV = static_cast<Decoration>(5250);
+
+static const Capability GeometryShaderPassthroughNV = static_cast<Capability>(5251);
+#endif  // #ifndef GLSLextNV_H

+ 36 - 6
3rdparty/glslang/SPIRV/GlslangToSpv.cpp

@@ -47,6 +47,9 @@ namespace spv {
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
     #include "GLSL.ext.AMD.h"
     #include "GLSL.ext.AMD.h"
 #endif
 #endif
+#ifdef NV_EXTENSIONS
+    #include "GLSL.ext.NV.h"
+#endif
 }
 }
 
 
 // Glslang includes
 // Glslang includes
@@ -436,6 +439,7 @@ spv::Decoration TranslateNoContractionDecoration(const glslang::TQualifier& qual
         return spv::DecorationMax;
         return spv::DecorationMax;
 }
 }
 
 
+
 // Translate a glslang built-in variable to a SPIR-V built in decoration.  Also generate
 // Translate a glslang built-in variable to a SPIR-V built in decoration.  Also generate
 // associated capabilities when required.  For some built-in variables, a capability
 // associated capabilities when required.  For some built-in variables, a capability
 // is generated only when using the variable in an executable instruction, but not when
 // is generated only when using the variable in an executable instruction, but not when
@@ -4127,7 +4131,8 @@ spv::Id TGlslangToSpvTraverser::createInvocationsOperation(glslang::TOperator op
     spv::Op opCode = spv::OpNop;
     spv::Op opCode = spv::OpNop;
 
 
     std::vector<spv::Id> spvGroupOperands;
     std::vector<spv::Id> spvGroupOperands;
-    if (op == glslang::EOpBallot || op == glslang::EOpReadFirstInvocation) {
+    if (op == glslang::EOpBallot || op == glslang::EOpReadFirstInvocation ||
+        op == glslang::EOpReadInvocation) {
         builder.addExtension(spv::E_SPV_KHR_shader_ballot);
         builder.addExtension(spv::E_SPV_KHR_shader_ballot);
         builder.addCapability(spv::CapabilitySubgroupBallotKHR);
         builder.addCapability(spv::CapabilitySubgroupBallotKHR);
     } else {
     } else {
@@ -4167,7 +4172,7 @@ spv::Id TGlslangToSpvTraverser::createInvocationsOperation(glslang::TOperator op
     }
     }
 
 
     case glslang::EOpReadInvocation:
     case glslang::EOpReadInvocation:
-        opCode = spv::OpGroupBroadcast;
+        opCode = spv::OpSubgroupReadInvocationKHR;
         if (builder.isVectorType(typeId))
         if (builder.isVectorType(typeId))
             return CreateInvocationsVectorOperation(opCode, typeId, operands);
             return CreateInvocationsVectorOperation(opCode, typeId, operands);
         break;
         break;
@@ -4279,13 +4284,15 @@ spv::Id TGlslangToSpvTraverser::CreateInvocationsVectorOperation(spv::Op op, spv
     assert(op == spv::OpGroupFMin || op == spv::OpGroupUMin || op == spv::OpGroupSMin ||
     assert(op == spv::OpGroupFMin || op == spv::OpGroupUMin || op == spv::OpGroupSMin ||
            op == spv::OpGroupFMax || op == spv::OpGroupUMax || op == spv::OpGroupSMax ||
            op == spv::OpGroupFMax || op == spv::OpGroupUMax || op == spv::OpGroupSMax ||
            op == spv::OpGroupFAdd || op == spv::OpGroupIAdd || op == spv::OpGroupBroadcast ||
            op == spv::OpGroupFAdd || op == spv::OpGroupIAdd || op == spv::OpGroupBroadcast ||
+           op == spv::OpSubgroupReadInvocationKHR ||
            op == spv::OpGroupFMinNonUniformAMD || op == spv::OpGroupUMinNonUniformAMD || op == spv::OpGroupSMinNonUniformAMD ||
            op == spv::OpGroupFMinNonUniformAMD || op == spv::OpGroupUMinNonUniformAMD || op == spv::OpGroupSMinNonUniformAMD ||
            op == spv::OpGroupFMaxNonUniformAMD || op == spv::OpGroupUMaxNonUniformAMD || op == spv::OpGroupSMaxNonUniformAMD ||
            op == spv::OpGroupFMaxNonUniformAMD || op == spv::OpGroupUMaxNonUniformAMD || op == spv::OpGroupSMaxNonUniformAMD ||
            op == spv::OpGroupFAddNonUniformAMD || op == spv::OpGroupIAddNonUniformAMD);
            op == spv::OpGroupFAddNonUniformAMD || op == spv::OpGroupIAddNonUniformAMD);
 #else
 #else
     assert(op == spv::OpGroupFMin || op == spv::OpGroupUMin || op == spv::OpGroupSMin ||
     assert(op == spv::OpGroupFMin || op == spv::OpGroupUMin || op == spv::OpGroupSMin ||
            op == spv::OpGroupFMax || op == spv::OpGroupUMax || op == spv::OpGroupSMax ||
            op == spv::OpGroupFMax || op == spv::OpGroupUMax || op == spv::OpGroupSMax ||
-           op == spv::OpGroupFAdd || op == spv::OpGroupIAdd || op == spv::OpGroupBroadcast);
+           op == spv::OpGroupFAdd || op == spv::OpGroupIAdd || op == spv::OpGroupBroadcast ||
+           op == spv::OpSubgroupReadInvocationKHR);
 #endif
 #endif
 
 
     // Handle group invocation operations scalar by scalar.
     // Handle group invocation operations scalar by scalar.
@@ -4305,13 +4312,16 @@ spv::Id TGlslangToSpvTraverser::CreateInvocationsVectorOperation(spv::Op op, spv
         std::vector<unsigned int> indexes;
         std::vector<unsigned int> indexes;
         indexes.push_back(comp);
         indexes.push_back(comp);
         spv::Id scalar = builder.createCompositeExtract(operands[0], scalarType, indexes);
         spv::Id scalar = builder.createCompositeExtract(operands[0], scalarType, indexes);
-
         std::vector<spv::Id> spvGroupOperands;
         std::vector<spv::Id> spvGroupOperands;
-        spvGroupOperands.push_back(builder.makeUintConstant(spv::ScopeSubgroup));
-        if (op == spv::OpGroupBroadcast) {
+        if (op == spv::OpSubgroupReadInvocationKHR) {
+            spvGroupOperands.push_back(scalar);
+            spvGroupOperands.push_back(operands[1]);
+        } else if (op == spv::OpGroupBroadcast) {
+            spvGroupOperands.push_back(builder.makeUintConstant(spv::ScopeSubgroup));
             spvGroupOperands.push_back(scalar);
             spvGroupOperands.push_back(scalar);
             spvGroupOperands.push_back(operands[1]);
             spvGroupOperands.push_back(operands[1]);
         } else {
         } else {
+            spvGroupOperands.push_back(builder.makeUintConstant(spv::ScopeSubgroup));
             spvGroupOperands.push_back(spv::GroupOperationReduce);
             spvGroupOperands.push_back(spv::GroupOperationReduce);
             spvGroupOperands.push_back(scalar);
             spvGroupOperands.push_back(scalar);
         }
         }
@@ -4721,6 +4731,26 @@ spv::Id TGlslangToSpvTraverser::getSymbolId(const glslang::TIntermSymbol* symbol
     if (builtIn != spv::BuiltInMax)
     if (builtIn != spv::BuiltInMax)
         addDecoration(id, spv::DecorationBuiltIn, (int)builtIn);
         addDecoration(id, spv::DecorationBuiltIn, (int)builtIn);
 
 
+#ifdef NV_EXTENSIONS 
+    if (builtIn == spv::BuiltInSampleMask) {
+          spv::Decoration decoration;
+          // GL_NV_sample_mask_override_coverage extension
+          if (glslangIntermediate->getLayoutOverrideCoverage())
+              decoration = (spv::Decoration)spv::OverrideCoverageNV;
+          else
+              decoration = (spv::Decoration)spv::DecorationMax;
+        addDecoration(id, decoration);
+        if (decoration != spv::DecorationMax) {
+            builder.addExtension(spv::E_SPV_NV_sample_mask_override_coverage);
+        }
+    }
+    if (symbol->getQualifier().layoutPassthrough) {
+        addDecoration(id, spv::PassthroughNV);
+        builder.addCapability(spv::GeometryShaderPassthroughNV);
+        builder.addExtension(spv::E_SPV_NV_geometry_shader_passthrough);
+    }
+#endif
+
     return id;
     return id;
 }
 }
 
 

+ 48 - 20
3rdparty/glslang/SPIRV/SPVRemapper.cpp

@@ -327,12 +327,10 @@ namespace spv {
         bound(maxBound); // reset header ID bound to as big as it now needs to be
         bound(maxBound); // reset header ID bound to as big as it now needs to be
     }
     }
 
 
+    // Mark debug instructions for stripping
     void spirvbin_t::stripDebug()
     void spirvbin_t::stripDebug()
     {
     {
-        if ((options & STRIP) == 0)
-            return;
-
-        // build local Id and name maps
+        // Strip instructions in the stripOp set: debug info.
         process(
         process(
             [&](spv::Op opCode, unsigned start) {
             [&](spv::Op opCode, unsigned start) {
                 // remember opcodes we want to strip later
                 // remember opcodes we want to strip later
@@ -343,6 +341,32 @@ namespace spv {
             op_fn_nop);
             op_fn_nop);
     }
     }
 
 
+    // Mark instructions that refer to now-removed IDs for stripping
+    void spirvbin_t::stripDeadRefs()
+    {
+        process(
+            [&](spv::Op opCode, unsigned start) {
+                // strip opcodes pointing to removed data
+                switch (opCode) {
+                case spv::OpName:
+                case spv::OpMemberName:
+                case spv::OpDecorate:
+                case spv::OpMemberDecorate:
+                    if (idPosR.find(asId(start+1)) == idPosR.end())
+                        stripInst(start);
+                    break;
+                default: 
+                    break; // leave it alone
+                }
+
+                return true;
+            },
+            op_fn_nop);
+
+        strip();
+    }
+
+    // Update local maps of ID, type, etc positions
     void spirvbin_t::buildLocalMaps()
     void spirvbin_t::buildLocalMaps()
     {
     {
         msg(2, 2, std::string("build local maps: "));
         msg(2, 2, std::string("build local maps: "));
@@ -351,7 +375,6 @@ namespace spv {
         idMapL.clear();
         idMapL.clear();
 //      preserve nameMap, so we don't clear that.
 //      preserve nameMap, so we don't clear that.
         fnPos.clear();
         fnPos.clear();
-        fnPosDCE.clear();
         fnCalls.clear();
         fnCalls.clear();
         typeConstPos.clear();
         typeConstPos.clear();
         idPosR.clear();
         idPosR.clear();
@@ -366,10 +389,6 @@ namespace spv {
         // build local Id and name maps
         // build local Id and name maps
         process(
         process(
             [&](spv::Op opCode, unsigned start) {
             [&](spv::Op opCode, unsigned start) {
-                // remember opcodes we want to strip later
-                if ((options & STRIP) && isStripOp(opCode))
-                    stripInst(start);
-
                 unsigned word = start+1;
                 unsigned word = start+1;
                 spv::Id  typeId = spv::NoResult;
                 spv::Id  typeId = spv::NoResult;
 
 
@@ -957,7 +976,6 @@ namespace spv {
                 if (call_it == fnCalls.end() || call_it->second == 0) {
                 if (call_it == fnCalls.end() || call_it->second == 0) {
                     changed = true;
                     changed = true;
                     stripRange.push_back(fn->second);
                     stripRange.push_back(fn->second);
-                    fnPosDCE.insert(*fn);
 
 
                     // decrease counts of called functions
                     // decrease counts of called functions
                     process(
                     process(
@@ -1011,11 +1029,15 @@ namespace spv {
         // Remove single-use function variables + associated decorations and names
         // Remove single-use function variables + associated decorations and names
         process(
         process(
             [&](spv::Op opCode, unsigned start) {
             [&](spv::Op opCode, unsigned start) {
-                if ((opCode == spv::OpVariable && varUseCount[asId(start+2)] == 1)  ||
-                    (opCode == spv::OpDecorate && varUseCount[asId(start+1)] == 1)  ||
-                    (opCode == spv::OpName     && varUseCount[asId(start+1)] == 1)) {
-                        stripInst(start);
-                }
+                spv::Id id = spv::NoResult;
+                if (opCode == spv::OpVariable)
+                    id = asId(start+2);
+                if (opCode == spv::OpDecorate || opCode == spv::OpName)
+                    id = asId(start+1);
+
+                if (id != spv::NoResult && varUseCount[id] == 1)
+                    stripInst(start);
+
                 return true;
                 return true;
             },
             },
             op_fn_nop);
             op_fn_nop);
@@ -1276,25 +1298,31 @@ namespace spv {
         // Set up opcode tables from SpvDoc
         // Set up opcode tables from SpvDoc
         spv::Parameterize();
         spv::Parameterize();
 
 
-        validate();  // validate header
-        buildLocalMaps();
+        validate();       // validate header
+        buildLocalMaps(); // build ID maps
 
 
         msg(3, 4, std::string("ID bound: ") + std::to_string(bound()));
         msg(3, 4, std::string("ID bound: ") + std::to_string(bound()));
 
 
+        if (options & STRIP)         stripDebug();
         strip();        // strip out data we decided to eliminate
         strip();        // strip out data we decided to eliminate
         if (options & OPT_LOADSTORE) optLoadStore();
         if (options & OPT_LOADSTORE) optLoadStore();
         if (options & OPT_FWD_LS)    forwardLoadStores();
         if (options & OPT_FWD_LS)    forwardLoadStores();
         if (options & DCE_FUNCS)     dceFuncs();
         if (options & DCE_FUNCS)     dceFuncs();
         if (options & DCE_VARS)      dceVars();
         if (options & DCE_VARS)      dceVars();
         if (options & DCE_TYPES)     dceTypes();
         if (options & DCE_TYPES)     dceTypes();
-        strip();        // strip out data we decided to eliminate
+
+        strip();         // strip out data we decided to eliminate
+        stripDeadRefs(); // remove references to things we DCEed
+        // after the last strip, we must clean any debug info referring to now-deleted data
 
 
         if (options & MAP_TYPES)     mapTypeConst();
         if (options & MAP_TYPES)     mapTypeConst();
         if (options & MAP_NAMES)     mapNames();
         if (options & MAP_NAMES)     mapNames();
         if (options & MAP_FUNCS)     mapFnBodies();
         if (options & MAP_FUNCS)     mapFnBodies();
 
 
-        mapRemainder(); // map any unmapped IDs
-        applyMap();     // Now remap each shader to the new IDs we've come up with
+        if (options & MAP_ALL) {
+            mapRemainder(); // map any unmapped IDs
+            applyMap();     // Now remap each shader to the new IDs we've come up with
+        }
     }
     }
 
 
     // remap from a memory image
     // remap from a memory image

+ 2 - 2
3rdparty/glslang/SPIRV/SPVRemapper.h

@@ -239,7 +239,8 @@ private:
 
 
    void        applyMap();            // remap per local name map
    void        applyMap();            // remap per local name map
    void        mapRemainder();        // map any IDs we haven't touched yet
    void        mapRemainder();        // map any IDs we haven't touched yet
-   void        stripDebug();          // strip debug info
+   void        stripDebug();          // strip all debug info
+   void        stripDeadRefs();       // strips debug info for now-dead references after DCE
    void        strip();               // remove debug symbols
    void        strip();               // remove debug symbols
    
    
    std::vector<spirword_t> spv;      // SPIR words
    std::vector<spirword_t> spv;      // SPIR words
@@ -264,7 +265,6 @@ private:
    // Function start and end.  use unordered_map because we'll have
    // Function start and end.  use unordered_map because we'll have
    // many fewer functions than IDs.
    // many fewer functions than IDs.
    std::unordered_map<spv::Id, range_t> fnPos;
    std::unordered_map<spv::Id, range_t> fnPos;
-   std::unordered_map<spv::Id, range_t> fnPosDCE; // deleted functions
 
 
    // Which functions are called, anywhere in the module, with a call count
    // Which functions are called, anywhere in the module, with a call count
    std::unordered_map<spv::Id, int> fnCalls;
    std::unordered_map<spv::Id, int> fnCalls;

+ 37 - 0
3rdparty/glslang/SPIRV/disassemble.cpp

@@ -53,6 +53,9 @@ namespace spv {
         #include "GLSL.std.450.h"
         #include "GLSL.std.450.h"
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
         #include "GLSL.ext.AMD.h"
         #include "GLSL.ext.AMD.h"
+#endif
+#ifdef NV_EXTENSIONS
+        #include "GLSL.ext.NV.h"
 #endif
 #endif
     }
     }
 }
 }
@@ -64,6 +67,10 @@ namespace spv {
 static const char* GLSLextAMDGetDebugNames(const char*, unsigned);
 static const char* GLSLextAMDGetDebugNames(const char*, unsigned);
 #endif
 #endif
 
 
+#ifdef NV_EXTENSIONS
+static const char* GLSLextNVGetDebugNames(const char*, unsigned);
+#endif
+
 static void Kill(std::ostream& out, const char* message)
 static void Kill(std::ostream& out, const char* message)
 {
 {
     out << std::endl << "Disassembly failed: " << message << std::endl;
     out << std::endl << "Disassembly failed: " << message << std::endl;
@@ -75,6 +82,9 @@ enum ExtInstSet {
     GLSL450Inst,
     GLSL450Inst,
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
     GLSLextAMDInst,
     GLSLextAMDInst,
+#endif
+#ifdef NV_EXTENSIONS
+    GLSLextNVInst,
 #endif
 #endif
     OpenCLExtInst,
     OpenCLExtInst,
 };
 };
@@ -469,6 +479,11 @@ void SpirvStream::disassembleInstruction(Id resultId, Id /*typeId*/, Op opCode,
                            strcmp(spv::E_SPV_AMD_shader_explicit_vertex_parameter, name) == 0 ||
                            strcmp(spv::E_SPV_AMD_shader_explicit_vertex_parameter, name) == 0 ||
                            strcmp(spv::E_SPV_AMD_gcn_shader, name) == 0) {
                            strcmp(spv::E_SPV_AMD_gcn_shader, name) == 0) {
                     extInstSet = GLSLextAMDInst;
                     extInstSet = GLSLextAMDInst;
+#endif
+#ifdef NV_EXTENSIONS
+                }else if (strcmp(spv::E_SPV_NV_sample_mask_override_coverage, name) == 0 ||
+                          strcmp(spv::E_SPV_NV_geometry_shader_passthrough, name) == 0) {
+                    extInstSet = GLSLextNVInst;
 #endif
 #endif
                 }
                 }
                 unsigned entrypoint = stream[word - 1];
                 unsigned entrypoint = stream[word - 1];
@@ -479,6 +494,11 @@ void SpirvStream::disassembleInstruction(Id resultId, Id /*typeId*/, Op opCode,
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
                 } else if (extInstSet == GLSLextAMDInst) {
                 } else if (extInstSet == GLSLextAMDInst) {
                     out << "(" << GLSLextAMDGetDebugNames(name, entrypoint) << ")";
                     out << "(" << GLSLextAMDGetDebugNames(name, entrypoint) << ")";
+#endif
+#ifdef NV_EXTENSIONS
+                }
+                else if (extInstSet == GLSLextNVInst) {
+                    out << "(" << GLSLextNVGetDebugNames(name, entrypoint) << ")";
 #endif
 #endif
                 }
                 }
             }
             }
@@ -631,6 +651,23 @@ static const char* GLSLextAMDGetDebugNames(const char* name, unsigned entrypoint
 }
 }
 #endif
 #endif
 
 
+
+#ifdef NV_EXTENSIONS
+static const char* GLSLextNVGetDebugNames(const char* name, unsigned entrypoint)
+{
+    if (strcmp(name, spv::E_SPV_NV_sample_mask_override_coverage) == 0 ||
+        strcmp(name, spv::E_SPV_NV_geometry_shader_passthrough) == 0) {
+        switch (entrypoint) {
+        case OverrideCoverageNV:          return "OverrideCoverageNV";
+        case PassthroughNV:               return "PassthroughNV";
+        case GeometryShaderPassthroughNV: return "GeometryShaderPassthroughNV";
+        default:                          return "Bad";
+        }
+    }
+    return "Bad";
+}
+#endif
+
 void Disassemble(std::ostream& out, const std::vector<unsigned int>& stream)
 void Disassemble(std::ostream& out, const std::vector<unsigned int>& stream)
 {
 {
     SpirvStream SpirvStream(out, stream);
     SpirvStream SpirvStream(out, stream);

+ 17 - 0
3rdparty/glslang/SPIRV/doc.cpp

@@ -50,6 +50,9 @@ namespace spv {
         // Include C-based headers that don't have a namespace
         // Include C-based headers that don't have a namespace
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
         #include "GLSL.ext.AMD.h"
         #include "GLSL.ext.AMD.h"
+#endif
+#ifdef NV_EXTENSIONS
+        #include "GLSL.ext.NV.h"
 #endif
 #endif
     }
     }
 }
 }
@@ -255,6 +258,10 @@ const char* DecorationString(int decoration)
 
 
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
     case 4999: return "ExplicitInterpAMD";
     case 4999: return "ExplicitInterpAMD";
+#endif
+#ifdef NV_EXTENSIONS
+    case 5248: return "OverrideCoverageNV";
+    case 5250: return "PassthroughNV";
 #endif
 #endif
     }
     }
 }
 }
@@ -812,6 +819,11 @@ const char* CapabilityString(int info)
 
 
     case 4423: return "SubgroupBallotKHR";
     case 4423: return "SubgroupBallotKHR";
     case 4427: return "DrawParameters";
     case 4427: return "DrawParameters";
+
+#ifdef NV_EXTENSIONS
+    case 5251: return "GeometryShaderPassthroughNV";
+#endif
+
     }
     }
 }
 }
 
 
@@ -1146,6 +1158,7 @@ const char* OpcodeString(int op)
 
 
     case 4421: return "OpSubgroupBallotKHR";
     case 4421: return "OpSubgroupBallotKHR";
     case 4422: return "OpSubgroupFirstInvocationKHR";
     case 4422: return "OpSubgroupFirstInvocationKHR";
+    case 4432: return "OpSubgroupReadInvocationKHR";
 
 
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
     case 5000: return "OpGroupIAddNonUniformAMD";
     case 5000: return "OpGroupIAddNonUniformAMD";
@@ -2758,6 +2771,10 @@ void Parameterize()
 
 
     InstructionDesc[OpSubgroupFirstInvocationKHR].operands.push(OperandId, "'Value'");
     InstructionDesc[OpSubgroupFirstInvocationKHR].operands.push(OperandId, "'Value'");
 
 
+    InstructionDesc[OpSubgroupReadInvocationKHR].capabilities.push_back(CapabilityGroups);
+    InstructionDesc[OpSubgroupReadInvocationKHR].operands.push(OperandId, "'Value'");
+    InstructionDesc[OpSubgroupReadInvocationKHR].operands.push(OperandId, "'Index'");
+
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
     InstructionDesc[OpGroupIAddNonUniformAMD].capabilities.push_back(CapabilityGroups);
     InstructionDesc[OpGroupIAddNonUniformAMD].capabilities.push_back(CapabilityGroups);
     InstructionDesc[OpGroupIAddNonUniformAMD].operands.push(OperandScope, "'Execution'");
     InstructionDesc[OpGroupIAddNonUniformAMD].operands.push(OperandScope, "'Execution'");

+ 1 - 0
3rdparty/glslang/SPIRV/spirv.hpp

@@ -905,6 +905,7 @@ enum Op {
     OpImageSparseRead = 320,
     OpImageSparseRead = 320,
     OpSubgroupBallotKHR = 4421,
     OpSubgroupBallotKHR = 4421,
     OpSubgroupFirstInvocationKHR = 4422,
     OpSubgroupFirstInvocationKHR = 4422,
+    OpSubgroupReadInvocationKHR = 4432,
     OpMax = 0x7fffffff,
     OpMax = 0x7fffffff,
 };
 };
 
 

+ 6 - 5
3rdparty/glslang/Test/baseResults/120.vert.out

@@ -77,9 +77,8 @@ ERROR: 0:192: 'gl_ClipDistance' :  left of '[' is not of type array, matrix, or
 ERROR: 0:192: 'assign' :  l-value required (can't modify a const)
 ERROR: 0:192: 'assign' :  l-value required (can't modify a const)
 ERROR: 0:195: 'gl_ModelViewMatrix' : identifiers starting with "gl_" are reserved 
 ERROR: 0:195: 'gl_ModelViewMatrix' : identifiers starting with "gl_" are reserved 
 ERROR: 0:200: 'token pasting (##)' : not supported for this version or the enabled extensions 
 ERROR: 0:200: 'token pasting (##)' : not supported for this version or the enabled extensions 
-ERROR: 0:200: '##' : token pasting not implemented (internal error) 
-ERROR: 0:200: '' :  syntax error
-ERROR: 80 compilation errors.  No code generated.
+ERROR: 0:203: 'token pasting (##)' : not supported for this version or the enabled extensions 
+ERROR: 79 compilation errors.  No code generated.
 
 
 
 
 Shader version: 120
 Shader version: 120
@@ -427,7 +426,8 @@ ERROR: node is still EOpNull!
 0:?     'c2D' (in 2-component vector of float)
 0:?     'c2D' (in 2-component vector of float)
 0:?     'c3D' (in 3-component vector of float)
 0:?     'c3D' (in 3-component vector of float)
 0:?     'v4' (uniform 4-component vector of float)
 0:?     'v4' (uniform 4-component vector of float)
-0:?     'abc' (global int)
+0:?     'abcdef' (global int)
+0:?     'qrstuv' (global int)
 
 
 
 
 Linked vertex stage:
 Linked vertex stage:
@@ -499,5 +499,6 @@ ERROR: node is still EOpNull!
 0:?     'c2D' (in 2-component vector of float)
 0:?     'c2D' (in 2-component vector of float)
 0:?     'c3D' (in 3-component vector of float)
 0:?     'c3D' (in 3-component vector of float)
 0:?     'v4' (uniform 4-component vector of float)
 0:?     'v4' (uniform 4-component vector of float)
-0:?     'abc' (global int)
+0:?     'abcdef' (global int)
+0:?     'qrstuv' (global int)
 
 

+ 5 - 5
3rdparty/glslang/Test/baseResults/130.vert.out

@@ -3,9 +3,7 @@ ERROR: 0:59: 'gl_InstanceID' : undeclared identifier
 ERROR: 0:59: '=' :  cannot convert from 'temp float' to 'temp int'
 ERROR: 0:59: '=' :  cannot convert from 'temp float' to 'temp int'
 ERROR: 0:61: 'texelFetch' : no matching overloaded function found 
 ERROR: 0:61: 'texelFetch' : no matching overloaded function found 
 ERROR: 0:61: 'assign' :  cannot convert from 'const float' to 'temp int'
 ERROR: 0:61: 'assign' :  cannot convert from 'const float' to 'temp int'
-ERROR: 0:75: '##' : token pasting not implemented (internal error) 
-ERROR: 0:75: '' :  syntax error
-ERROR: 6 compilation errors.  No code generated.
+ERROR: 4 compilation errors.  No code generated.
 
 
 
 
 Shader version: 130
 Shader version: 130
@@ -149,7 +147,8 @@ ERROR: node is still EOpNull!
 0:?     'v4' (uniform 4-component vector of float)
 0:?     'v4' (uniform 4-component vector of float)
 0:?     'gl_ClipDistance' (smooth out implicitly-sized array of float ClipDistance)
 0:?     'gl_ClipDistance' (smooth out implicitly-sized array of float ClipDistance)
 0:?     'gl_TexCoord' (smooth out implicitly-sized array of 4-component vector of float TexCoord)
 0:?     'gl_TexCoord' (smooth out implicitly-sized array of 4-component vector of float TexCoord)
-0:?     'abc' (global int)
+0:?     'abcdef' (global int)
+0:?     'qrstuv' (global int)
 0:?     'gl_VertexID' (gl_VertexId int VertexId)
 0:?     'gl_VertexID' (gl_VertexId int VertexId)
 
 
 
 
@@ -281,6 +280,7 @@ ERROR: node is still EOpNull!
 0:?     'v4' (uniform 4-component vector of float)
 0:?     'v4' (uniform 4-component vector of float)
 0:?     'gl_ClipDistance' (smooth out 2-element array of float ClipDistance)
 0:?     'gl_ClipDistance' (smooth out 2-element array of float ClipDistance)
 0:?     'gl_TexCoord' (smooth out 1-element array of 4-component vector of float TexCoord)
 0:?     'gl_TexCoord' (smooth out 1-element array of 4-component vector of float TexCoord)
-0:?     'abc' (global int)
+0:?     'abcdef' (global int)
+0:?     'qrstuv' (global int)
 0:?     'gl_VertexID' (gl_VertexId int VertexId)
 0:?     'gl_VertexID' (gl_VertexId int VertexId)
 
 

+ 2 - 1
3rdparty/glslang/Test/baseResults/cppBad.vert.out

@@ -3,8 +3,9 @@ ERROR: 0:2: 'preprocessor evaluation' : bad expression
 ERROR: 0:2: '#if' : unexpected tokens following directive 
 ERROR: 0:2: '#if' : unexpected tokens following directive 
 ERROR: 0:5: 'string' : End of line in string 
 ERROR: 0:5: 'string' : End of line in string 
 ERROR: 0:5: 'macro expansion' : expected '(' following n
 ERROR: 0:5: 'macro expansion' : expected '(' following n
+ERROR: 0:5: '""' : string literals not supported 
 ERROR: 0:5: '' :  syntax error
 ERROR: 0:5: '' :  syntax error
-ERROR: 5 compilation errors.  No code generated.
+ERROR: 6 compilation errors.  No code generated.
 
 
 
 
 Shader version: 100
 Shader version: 100

+ 55 - 33
3rdparty/glslang/Test/baseResults/hlsl.identifier.sample.frag.out

@@ -12,18 +12,27 @@ gl_FragCoord origin is upper left
 0:12    Function Parameters: 
 0:12    Function Parameters: 
 0:?     Sequence
 0:?     Sequence
 0:15      Sequence
 0:15      Sequence
-0:15        move second child to first child (temp int)
-0:15          'sample' (temp int)
-0:15          Constant:
-0:15            3 (const int)
+0:15        move second child to first child (temp 4-component vector of float)
+0:15          'sample' (temp 4-component vector of float)
+0:?           Constant:
+0:?             3.000000
+0:?             4.000000
+0:?             5.000000
+0:?             6.000000
 0:17      Sequence
 0:17      Sequence
 0:17        move second child to first child (temp 4-component vector of float)
 0:17        move second child to first child (temp 4-component vector of float)
 0:?           '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
 0:?           '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
-0:?           Constant:
-0:?             0.000000
-0:?             0.000000
-0:?             0.000000
-0:?             0.000000
+0:17          vector swizzle (temp 4-component vector of float)
+0:17            'sample' (temp 4-component vector of float)
+0:17            Sequence
+0:17              Constant:
+0:17                0 (const int)
+0:17              Constant:
+0:17                1 (const int)
+0:17              Constant:
+0:17                2 (const int)
+0:17              Constant:
+0:17                3 (const int)
 0:17        Branch: Return
 0:17        Branch: Return
 0:?   Linker Objects
 0:?   Linker Objects
 0:?     '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
 0:?     '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
@@ -45,54 +54,67 @@ gl_FragCoord origin is upper left
 0:12    Function Parameters: 
 0:12    Function Parameters: 
 0:?     Sequence
 0:?     Sequence
 0:15      Sequence
 0:15      Sequence
-0:15        move second child to first child (temp int)
-0:15          'sample' (temp int)
-0:15          Constant:
-0:15            3 (const int)
+0:15        move second child to first child (temp 4-component vector of float)
+0:15          'sample' (temp 4-component vector of float)
+0:?           Constant:
+0:?             3.000000
+0:?             4.000000
+0:?             5.000000
+0:?             6.000000
 0:17      Sequence
 0:17      Sequence
 0:17        move second child to first child (temp 4-component vector of float)
 0:17        move second child to first child (temp 4-component vector of float)
 0:?           '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
 0:?           '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
-0:?           Constant:
-0:?             0.000000
-0:?             0.000000
-0:?             0.000000
-0:?             0.000000
+0:17          vector swizzle (temp 4-component vector of float)
+0:17            'sample' (temp 4-component vector of float)
+0:17            Sequence
+0:17              Constant:
+0:17                0 (const int)
+0:17              Constant:
+0:17                1 (const int)
+0:17              Constant:
+0:17                2 (const int)
+0:17              Constant:
+0:17                3 (const int)
 0:17        Branch: Return
 0:17        Branch: Return
 0:?   Linker Objects
 0:?   Linker Objects
 0:?     '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
 0:?     '@entryPointOutput' (layout(location=0 ) out 4-component vector of float)
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 24
+// Id's are bound by 28
 
 
                               Capability Shader
                               Capability Shader
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
                               MemoryModel Logical GLSL450
                               MemoryModel Logical GLSL450
-                              EntryPoint Fragment 4  "main" 20
+                              EntryPoint Fragment 4  "main" 25
                               ExecutionMode 4 OriginUpperLeft
                               ExecutionMode 4 OriginUpperLeft
                               Name 4  "main"
                               Name 4  "main"
                               Name 10  "sample(i1;"
                               Name 10  "sample(i1;"
                               Name 9  "x"
                               Name 9  "x"
-                              Name 15  "sample"
-                              Name 20  "@entryPointOutput"
-                              Decorate 20(@entryPointOutput) Location 0
+                              Name 18  "sample"
+                              Name 25  "@entryPointOutput"
+                              Decorate 25(@entryPointOutput) Location 0
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeInt 32 1
                6:             TypeInt 32 1
                7:             TypePointer Function 6(int)
                7:             TypePointer Function 6(int)
                8:             TypeFunction 6(int) 7(ptr)
                8:             TypeFunction 6(int) 7(ptr)
-              16:      6(int) Constant 3
-              17:             TypeFloat 32
-              18:             TypeVector 17(float) 4
-              19:             TypePointer Output 18(fvec4)
-20(@entryPointOutput):     19(ptr) Variable Output
-              21:   17(float) Constant 0
-              22:   18(fvec4) ConstantComposite 21 21 21 21
+              15:             TypeFloat 32
+              16:             TypeVector 15(float) 4
+              17:             TypePointer Function 16(fvec4)
+              19:   15(float) Constant 1077936128
+              20:   15(float) Constant 1082130432
+              21:   15(float) Constant 1084227584
+              22:   15(float) Constant 1086324736
+              23:   16(fvec4) ConstantComposite 19 20 21 22
+              24:             TypePointer Output 16(fvec4)
+25(@entryPointOutput):     24(ptr) Variable Output
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
-      15(sample):      7(ptr) Variable Function
-                              Store 15(sample) 16
-                              Store 20(@entryPointOutput) 22
+      18(sample):     17(ptr) Variable Function
+                              Store 18(sample) 23
+              26:   16(fvec4) Load 18(sample)
+                              Store 25(@entryPointOutput) 26
                               Return
                               Return
                               FunctionEnd
                               FunctionEnd
   10(sample(i1;):      6(int) Function None 8
   10(sample(i1;):      6(int) Function None 8

+ 14 - 15
3rdparty/glslang/Test/baseResults/remap.basic.dcefunc.frag.out

@@ -3,34 +3,33 @@ Warning, version 450 is not yet complete; most version-specific features are pre
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 19
+// Id's are bound by 22
 
 
                               Capability Shader
                               Capability Shader
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
                               MemoryModel Logical GLSL450
                               MemoryModel Logical GLSL450
-                              EntryPoint Fragment 4  "main" 14 16
+                              EntryPoint Fragment 4  "main" 17 19
                               ExecutionMode 4 OriginUpperLeft
                               ExecutionMode 4 OriginUpperLeft
                               Source GLSL 450
                               Source GLSL 450
                               Name 4  "main"
                               Name 4  "main"
-                              Name 9  "dead_fn("
-                              Name 14  "outf4"
-                              Name 16  "inf"
+                              Name 17  "outf4"
+                              Name 19  "inf"
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeFloat 32
                6:             TypeFloat 32
                7:             TypeVector 6(float) 3
                7:             TypeVector 6(float) 3
                8:             TypeFunction 7(fvec3)
                8:             TypeFunction 7(fvec3)
-              10:    6(float) Constant 0
-              11:    7(fvec3) ConstantComposite 10 10 10
-              12:             TypeVector 6(float) 4
-              13:             TypePointer Output 12(fvec4)
-       14(outf4):     13(ptr) Variable Output
-              15:             TypePointer Input 6(float)
-         16(inf):     15(ptr) Variable Input
+              11:    6(float) Constant 0
+              12:    7(fvec3) ConstantComposite 11 11 11
+              15:             TypeVector 6(float) 4
+              16:             TypePointer Output 15(fvec4)
+       17(outf4):     16(ptr) Variable Output
+              18:             TypePointer Input 6(float)
+         19(inf):     18(ptr) Variable Input
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
-              17:    6(float) Load 16(inf)
-              18:   12(fvec4) CompositeConstruct 17 17 17 17
-                              Store 14(outf4) 18
+              20:    6(float) Load 19(inf)
+              21:   15(fvec4) CompositeConstruct 20 20 20 20
+                              Store 17(outf4) 21
                               Return
                               Return
                               FunctionEnd
                               FunctionEnd

+ 12 - 12
3rdparty/glslang/Test/baseResults/remap.basic.none.frag.out

@@ -3,18 +3,18 @@ Warning, version 450 is not yet complete; most version-specific features are pre
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 20
+// Id's are bound by 22
 
 
                               Capability Shader
                               Capability Shader
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
                               MemoryModel Logical GLSL450
                               MemoryModel Logical GLSL450
-                              EntryPoint Fragment 4  "main" 15 17
+                              EntryPoint Fragment 4  "main" 17 19
                               ExecutionMode 4 OriginUpperLeft
                               ExecutionMode 4 OriginUpperLeft
                               Source GLSL 450
                               Source GLSL 450
                               Name 4  "main"
                               Name 4  "main"
                               Name 9  "dead_fn("
                               Name 9  "dead_fn("
-                              Name 15  "outf4"
-                              Name 17  "inf"
+                              Name 17  "outf4"
+                              Name 19  "inf"
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeFloat 32
                6:             TypeFloat 32
@@ -22,16 +22,16 @@ Warning, version 450 is not yet complete; most version-specific features are pre
                8:             TypeFunction 7(fvec3)
                8:             TypeFunction 7(fvec3)
               11:    6(float) Constant 0
               11:    6(float) Constant 0
               12:    7(fvec3) ConstantComposite 11 11 11
               12:    7(fvec3) ConstantComposite 11 11 11
-              13:             TypeVector 6(float) 4
-              14:             TypePointer Output 13(fvec4)
-       15(outf4):     14(ptr) Variable Output
-              16:             TypePointer Input 6(float)
-         17(inf):     16(ptr) Variable Input
+              15:             TypeVector 6(float) 4
+              16:             TypePointer Output 15(fvec4)
+       17(outf4):     16(ptr) Variable Output
+              18:             TypePointer Input 6(float)
+         19(inf):     18(ptr) Variable Input
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
-              18:    6(float) Load 17(inf)
-              19:   13(fvec4) CompositeConstruct 18 18 18 18
-                              Store 15(outf4) 19
+              20:    6(float) Load 19(inf)
+              21:   15(fvec4) CompositeConstruct 20 20 20 20
+                              Store 17(outf4) 21
                               Return
                               Return
                               FunctionEnd
                               FunctionEnd
      9(dead_fn():    7(fvec3) Function None 8
      9(dead_fn():    7(fvec3) Function None 8

+ 10 - 10
3rdparty/glslang/Test/baseResults/remap.basic.strip.frag.out

@@ -3,12 +3,12 @@ Warning, version 450 is not yet complete; most version-specific features are pre
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 20
+// Id's are bound by 22
 
 
                               Capability Shader
                               Capability Shader
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
                               MemoryModel Logical GLSL450
                               MemoryModel Logical GLSL450
-                              EntryPoint Fragment 4  "main" 15 17
+                              EntryPoint Fragment 4  "main" 17 19
                               ExecutionMode 4 OriginUpperLeft
                               ExecutionMode 4 OriginUpperLeft
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
@@ -17,16 +17,16 @@ Warning, version 450 is not yet complete; most version-specific features are pre
                8:             TypeFunction 7(fvec3)
                8:             TypeFunction 7(fvec3)
               11:    6(float) Constant 0
               11:    6(float) Constant 0
               12:    7(fvec3) ConstantComposite 11 11 11
               12:    7(fvec3) ConstantComposite 11 11 11
-              13:             TypeVector 6(float) 4
-              14:             TypePointer Output 13(fvec4)
-              15:     14(ptr) Variable Output
-              16:             TypePointer Input 6(float)
-              17:     16(ptr) Variable Input
+              15:             TypeVector 6(float) 4
+              16:             TypePointer Output 15(fvec4)
+              17:     16(ptr) Variable Output
+              18:             TypePointer Input 6(float)
+              19:     18(ptr) Variable Input
                4:           2 Function None 3
                4:           2 Function None 3
                5:             Label
                5:             Label
-              18:    6(float) Load 17
-              19:   13(fvec4) CompositeConstruct 18 18 18 18
-                              Store 15 19
+              20:    6(float) Load 19
+              21:   15(fvec4) CompositeConstruct 20 20 20 20
+                              Store 17 21
                               Return
                               Return
                               FunctionEnd
                               FunctionEnd
                9:    7(fvec3) Function None 8
                9:    7(fvec3) Function None 8

+ 11 - 11
3rdparty/glslang/Test/baseResults/remap.hlsl.sample.basic.none.frag.out

@@ -3,7 +3,7 @@ WARNING: 0:4: 'immediate sampler state' : unimplemented
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 190
+// Id's are bound by 191
 
 
                               Capability Shader
                               Capability Shader
                               Capability Sampled1D
                               Capability Sampled1D
@@ -57,9 +57,9 @@ WARNING: 0:4: 'immediate sampler state' : unimplemented
                               Name 173  "psout"
                               Name 173  "psout"
                               Name 180  "Color"
                               Name 180  "Color"
                               Name 184  "Depth"
                               Name 184  "Depth"
-                              Name 187  "g_sSamp2d"
-                              Name 188  "g_sSamp2D_b"
-                              Name 189  "g_tTex1df4a"
+                              Name 188  "g_sSamp2d"
+                              Name 189  "g_sSamp2D_b"
+                              Name 190  "g_tTex1df4a"
                               Decorate 41(g_tTex1df4) DescriptorSet 0
                               Decorate 41(g_tTex1df4) DescriptorSet 0
                               Decorate 41(g_tTex1df4) Binding 0
                               Decorate 41(g_tTex1df4) Binding 0
                               Decorate 45(g_sSamp) DescriptorSet 0
                               Decorate 45(g_sSamp) DescriptorSet 0
@@ -77,10 +77,10 @@ WARNING: 0:4: 'immediate sampler state' : unimplemented
                               Decorate 165(g_tTexcdu4) DescriptorSet 0
                               Decorate 165(g_tTexcdu4) DescriptorSet 0
                               Decorate 180(Color) Location 0
                               Decorate 180(Color) Location 0
                               Decorate 184(Depth) BuiltIn FragDepth
                               Decorate 184(Depth) BuiltIn FragDepth
-                              Decorate 187(g_sSamp2d) DescriptorSet 0
-                              Decorate 188(g_sSamp2D_b) DescriptorSet 0
-                              Decorate 189(g_tTex1df4a) DescriptorSet 0
-                              Decorate 189(g_tTex1df4a) Binding 1
+                              Decorate 188(g_sSamp2d) DescriptorSet 0
+                              Decorate 189(g_sSamp2D_b) DescriptorSet 0
+                              Decorate 190(g_tTex1df4a) DescriptorSet 0
+                              Decorate 190(g_tTex1df4a) Binding 1
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeInt 32 1
                6:             TypeInt 32 1
@@ -184,9 +184,9 @@ WARNING: 0:4: 'immediate sampler state' : unimplemented
       180(Color):    179(ptr) Variable Output
       180(Color):    179(ptr) Variable Output
              183:             TypePointer Output 35(float)
              183:             TypePointer Output 35(float)
       184(Depth):    183(ptr) Variable Output
       184(Depth):    183(ptr) Variable Output
-  187(g_sSamp2d):     44(ptr) Variable UniformConstant
-188(g_sSamp2D_b):     44(ptr) Variable UniformConstant
-189(g_tTex1df4a):     40(ptr) Variable UniformConstant
+  188(g_sSamp2d):     44(ptr) Variable UniformConstant
+189(g_sSamp2D_b):     44(ptr) Variable UniformConstant
+190(g_tTex1df4a):     40(ptr) Variable UniformConstant
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
         9(mtest):      8(ptr) Variable Function
         9(mtest):      8(ptr) Variable Function

+ 5 - 5
3rdparty/glslang/Test/baseResults/remap.hlsl.sample.basic.strip.frag.out

@@ -3,7 +3,7 @@ WARNING: 0:4: 'immediate sampler state' : unimplemented
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 190
+// Id's are bound by 191
 
 
                               Capability Shader
                               Capability Shader
                               Capability Sampled1D
                               Capability Sampled1D
@@ -28,10 +28,10 @@ WARNING: 0:4: 'immediate sampler state' : unimplemented
                               Decorate 165 DescriptorSet 0
                               Decorate 165 DescriptorSet 0
                               Decorate 180 Location 0
                               Decorate 180 Location 0
                               Decorate 184 BuiltIn FragDepth
                               Decorate 184 BuiltIn FragDepth
-                              Decorate 187 DescriptorSet 0
                               Decorate 188 DescriptorSet 0
                               Decorate 188 DescriptorSet 0
                               Decorate 189 DescriptorSet 0
                               Decorate 189 DescriptorSet 0
-                              Decorate 189 Binding 1
+                              Decorate 190 DescriptorSet 0
+                              Decorate 190 Binding 1
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeInt 32 1
                6:             TypeInt 32 1
@@ -135,9 +135,9 @@ WARNING: 0:4: 'immediate sampler state' : unimplemented
              180:    179(ptr) Variable Output
              180:    179(ptr) Variable Output
              183:             TypePointer Output 35(float)
              183:             TypePointer Output 35(float)
              184:    183(ptr) Variable Output
              184:    183(ptr) Variable Output
-             187:     44(ptr) Variable UniformConstant
              188:     44(ptr) Variable UniformConstant
              188:     44(ptr) Variable UniformConstant
-             189:     40(ptr) Variable UniformConstant
+             189:     44(ptr) Variable UniformConstant
+             190:     40(ptr) Variable UniformConstant
                4:           2 Function None 3
                4:           2 Function None 3
                5:             Label
                5:             Label
                9:      8(ptr) Variable Function
                9:      8(ptr) Variable Function

+ 6 - 6
3rdparty/glslang/Test/baseResults/remap.hlsl.templatetypes.none.frag.out

@@ -1,13 +1,13 @@
 remap.hlsl.templatetypes.none.frag
 remap.hlsl.templatetypes.none.frag
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 149
+// Id's are bound by 150
 
 
                               Capability Shader
                               Capability Shader
                               Capability Float64
                               Capability Float64
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
                               MemoryModel Logical GLSL450
                               MemoryModel Logical GLSL450
-                              EntryPoint Fragment 4  "main" 146 148
+                              EntryPoint Fragment 4  "main" 146 149
                               ExecutionMode 4 OriginUpperLeft
                               ExecutionMode 4 OriginUpperLeft
                               Name 4  "main"
                               Name 4  "main"
                               Name 9  "r00"
                               Name 9  "r00"
@@ -39,9 +39,9 @@ remap.hlsl.templatetypes.none.frag
                               Name 136  "r65"
                               Name 136  "r65"
                               Name 141  "r66"
                               Name 141  "r66"
                               Name 146  "@entryPointOutput"
                               Name 146  "@entryPointOutput"
-                              Name 148  "input"
+                              Name 149  "input"
                               Decorate 146(@entryPointOutput) Location 0
                               Decorate 146(@entryPointOutput) Location 0
-                              Decorate 148(input) Location 0
+                              Decorate 149(input) Location 0
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeFloat 32
                6:             TypeFloat 32
@@ -157,8 +157,8 @@ remap.hlsl.templatetypes.none.frag
              144:         139 ConstantComposite 72 126 142 143
              144:         139 ConstantComposite 72 126 142 143
              145:             TypePointer Output 6(float)
              145:             TypePointer Output 6(float)
 146(@entryPointOutput):    145(ptr) Variable Output
 146(@entryPointOutput):    145(ptr) Variable Output
-             147:             TypePointer Input 7(fvec4)
-      148(input):    147(ptr) Variable Input
+             148:             TypePointer Input 7(fvec4)
+      149(input):    148(ptr) Variable Input
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
           9(r00):      8(ptr) Variable Function
           9(r00):      8(ptr) Variable Function

+ 58 - 58
3rdparty/glslang/Test/baseResults/remap.similar_1a.none.frag.out

@@ -3,12 +3,12 @@ Warning, version 450 is not yet complete; most version-specific features are pre
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 82
+// Id's are bound by 86
 
 
                               Capability Shader
                               Capability Shader
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
                               MemoryModel Logical GLSL450
                               MemoryModel Logical GLSL450
-                              EntryPoint Fragment 4  "main" 50 69 71
+                              EntryPoint Fragment 4  "main" 53 73 75
                               ExecutionMode 4 OriginUpperLeft
                               ExecutionMode 4 OriginUpperLeft
                               Source GLSL 450
                               Source GLSL 450
                               Name 4  "main"
                               Name 4  "main"
@@ -18,13 +18,13 @@ Warning, version 450 is not yet complete; most version-specific features are pre
                               Name 13  "bound"
                               Name 13  "bound"
                               Name 17  "r"
                               Name 17  "r"
                               Name 19  "x"
                               Name 19  "x"
-                              Name 42  "param"
-                              Name 50  "ini4"
-                              Name 69  "outf4"
-                              Name 71  "inf"
-                              Name 74  "param"
+                              Name 44  "param"
+                              Name 53  "ini4"
+                              Name 73  "outf4"
+                              Name 75  "inf"
                               Name 78  "param"
                               Name 78  "param"
-                              Decorate 50(ini4) Flat
+                              Name 82  "param"
+                              Decorate 53(ini4) Flat
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeInt 32 1
                6:             TypeInt 32 1
@@ -37,35 +37,35 @@ Warning, version 450 is not yet complete; most version-specific features are pre
               28:             TypeBool
               28:             TypeBool
               30:    8(float) Constant 1056964608
               30:    8(float) Constant 1056964608
               34:      6(int) Constant 1
               34:      6(int) Constant 1
-              38:      6(int) Constant 2
-              48:             TypeVector 6(int) 4
-              49:             TypePointer Input 48(ivec4)
-        50(ini4):     49(ptr) Variable Input
-              51:             TypeInt 32 0
-              52:     51(int) Constant 1
-              53:             TypePointer Input 6(int)
-              56:     51(int) Constant 2
-              61:     51(int) Constant 0
-              67:             TypeVector 8(float) 4
-              68:             TypePointer Output 67(fvec4)
-       69(outf4):     68(ptr) Variable Output
-              70:             TypePointer Input 8(float)
-         71(inf):     70(ptr) Variable Input
+              40:      6(int) Constant 2
+              51:             TypeVector 6(int) 4
+              52:             TypePointer Input 51(ivec4)
+        53(ini4):     52(ptr) Variable Input
+              54:             TypeInt 32 0
+              55:     54(int) Constant 1
+              56:             TypePointer Input 6(int)
+              59:     54(int) Constant 2
+              64:     54(int) Constant 0
+              71:             TypeVector 8(float) 4
+              72:             TypePointer Output 71(fvec4)
+       73(outf4):     72(ptr) Variable Output
+              74:             TypePointer Input 8(float)
+         75(inf):     74(ptr) Variable Input
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
-       74(param):      7(ptr) Variable Function
        78(param):      7(ptr) Variable Function
        78(param):      7(ptr) Variable Function
-              72:    8(float) Load 71(inf)
-              73:      6(int) ConvertFToS 72
-                              Store 74(param) 73
-              75:    8(float) FunctionCall 11(Test1(i1;) 74(param)
-              76:    8(float) Load 71(inf)
+       82(param):      7(ptr) Variable Function
+              76:    8(float) Load 75(inf)
               77:      6(int) ConvertFToS 76
               77:      6(int) ConvertFToS 76
                               Store 78(param) 77
                               Store 78(param) 77
-              79:    8(float) FunctionCall 14(Test2(i1;) 78(param)
-              80:    8(float) FAdd 75 79
-              81:   67(fvec4) CompositeConstruct 80 80 80 80
-                              Store 69(outf4) 81
+              79:    8(float) FunctionCall 11(Test1(i1;) 78(param)
+              80:    8(float) Load 75(inf)
+              81:      6(int) ConvertFToS 80
+                              Store 82(param) 81
+              83:    8(float) FunctionCall 14(Test2(i1;) 82(param)
+              84:    8(float) FAdd 79 83
+              85:   71(fvec4) CompositeConstruct 84 84 84 84
+                              Store 73(outf4) 85
                               Return
                               Return
                               FunctionEnd
                               FunctionEnd
    11(Test1(i1;):    8(float) Function None 9
    11(Test1(i1;):    8(float) Function None 9
@@ -101,31 +101,31 @@ Warning, version 450 is not yet complete; most version-specific features are pre
    14(Test2(i1;):    8(float) Function None 9
    14(Test2(i1;):    8(float) Function None 9
        13(bound):      7(ptr) FunctionParameter
        13(bound):      7(ptr) FunctionParameter
               15:             Label
               15:             Label
-       42(param):      7(ptr) Variable Function
-              37:      6(int) Load 13(bound)
-              39:    28(bool) SGreaterThan 37 38
-                              SelectionMerge 41 None
-                              BranchConditional 39 40 45
-              40:               Label
-              43:      6(int)   Load 13(bound)
-                                Store 42(param) 43
-              44:    8(float)   FunctionCall 11(Test1(i1;) 42(param)
-                                ReturnValue 44
-              45:               Label
-              46:      6(int)   Load 13(bound)
-              47:      6(int)   IMul 46 38
-              54:     53(ptr)   AccessChain 50(ini4) 52
-              55:      6(int)   Load 54
-              57:     53(ptr)   AccessChain 50(ini4) 56
+       44(param):      7(ptr) Variable Function
+              39:      6(int) Load 13(bound)
+              41:    28(bool) SGreaterThan 39 40
+                              SelectionMerge 43 None
+                              BranchConditional 41 42 48
+              42:               Label
+              45:      6(int)   Load 13(bound)
+                                Store 44(param) 45
+              46:    8(float)   FunctionCall 11(Test1(i1;) 44(param)
+                                ReturnValue 46
+              48:               Label
+              49:      6(int)   Load 13(bound)
+              50:      6(int)   IMul 49 40
+              57:     56(ptr)   AccessChain 53(ini4) 55
               58:      6(int)   Load 57
               58:      6(int)   Load 57
-              59:      6(int)   IMul 55 58
-              60:      6(int)   IAdd 47 59
-              62:     53(ptr)   AccessChain 50(ini4) 61
-              63:      6(int)   Load 62
-              64:      6(int)   IAdd 60 63
-              65:    8(float)   ConvertSToF 64
-                                ReturnValue 65
-              41:             Label
-              66:    8(float) Undef
-                              ReturnValue 66
+              60:     56(ptr)   AccessChain 53(ini4) 59
+              61:      6(int)   Load 60
+              62:      6(int)   IMul 58 61
+              63:      6(int)   IAdd 50 62
+              65:     56(ptr)   AccessChain 53(ini4) 64
+              66:      6(int)   Load 65
+              67:      6(int)   IAdd 63 66
+              68:    8(float)   ConvertSToF 67
+                                ReturnValue 68
+              43:             Label
+              70:    8(float) Undef
+                              ReturnValue 70
                               FunctionEnd
                               FunctionEnd

+ 60 - 60
3rdparty/glslang/Test/baseResults/remap.similar_1b.none.frag.out

@@ -3,12 +3,12 @@ Warning, version 450 is not yet complete; most version-specific features are pre
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 87
+// Id's are bound by 91
 
 
                               Capability Shader
                               Capability Shader
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
                               MemoryModel Logical GLSL450
                               MemoryModel Logical GLSL450
-                              EntryPoint Fragment 4  "main" 55 74 76
+                              EntryPoint Fragment 4  "main" 58 78 80
                               ExecutionMode 4 OriginUpperLeft
                               ExecutionMode 4 OriginUpperLeft
                               Source GLSL 450
                               Source GLSL 450
                               Name 4  "main"
                               Name 4  "main"
@@ -18,13 +18,13 @@ Warning, version 450 is not yet complete; most version-specific features are pre
                               Name 13  "bound"
                               Name 13  "bound"
                               Name 17  "r"
                               Name 17  "r"
                               Name 19  "x"
                               Name 19  "x"
-                              Name 47  "param"
-                              Name 55  "ini4"
-                              Name 74  "outf4"
-                              Name 76  "inf"
-                              Name 79  "param"
+                              Name 49  "param"
+                              Name 58  "ini4"
+                              Name 78  "outf4"
+                              Name 80  "inf"
                               Name 83  "param"
                               Name 83  "param"
-                              Decorate 55(ini4) Flat
+                              Name 87  "param"
+                              Decorate 58(ini4) Flat
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeInt 32 1
                6:             TypeInt 32 1
@@ -38,36 +38,36 @@ Warning, version 450 is not yet complete; most version-specific features are pre
               30:    8(float) Constant 1056964608
               30:    8(float) Constant 1056964608
               34:      6(int) Constant 1
               34:      6(int) Constant 1
               36:    8(float) Constant 1045220557
               36:    8(float) Constant 1045220557
-              41:      6(int) Constant 2
-              51:      6(int) Constant 4
-              53:             TypeVector 6(int) 4
-              54:             TypePointer Input 53(ivec4)
-        55(ini4):     54(ptr) Variable Input
-              56:             TypeInt 32 0
-              57:     56(int) Constant 1
-              58:             TypePointer Input 6(int)
-              61:     56(int) Constant 2
-              66:     56(int) Constant 0
-              72:             TypeVector 8(float) 4
-              73:             TypePointer Output 72(fvec4)
-       74(outf4):     73(ptr) Variable Output
-              75:             TypePointer Input 8(float)
-         76(inf):     75(ptr) Variable Input
+              43:      6(int) Constant 2
+              54:      6(int) Constant 4
+              56:             TypeVector 6(int) 4
+              57:             TypePointer Input 56(ivec4)
+        58(ini4):     57(ptr) Variable Input
+              59:             TypeInt 32 0
+              60:     59(int) Constant 1
+              61:             TypePointer Input 6(int)
+              64:     59(int) Constant 2
+              69:     59(int) Constant 0
+              76:             TypeVector 8(float) 4
+              77:             TypePointer Output 76(fvec4)
+       78(outf4):     77(ptr) Variable Output
+              79:             TypePointer Input 8(float)
+         80(inf):     79(ptr) Variable Input
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
-       79(param):      7(ptr) Variable Function
        83(param):      7(ptr) Variable Function
        83(param):      7(ptr) Variable Function
-              77:    8(float) Load 76(inf)
-              78:      6(int) ConvertFToS 77
-                              Store 79(param) 78
-              80:    8(float) FunctionCall 11(Test1(i1;) 79(param)
-              81:    8(float) Load 76(inf)
+       87(param):      7(ptr) Variable Function
+              81:    8(float) Load 80(inf)
               82:      6(int) ConvertFToS 81
               82:      6(int) ConvertFToS 81
                               Store 83(param) 82
                               Store 83(param) 82
-              84:    8(float) FunctionCall 14(Test2(i1;) 83(param)
-              85:    8(float) FAdd 80 84
-              86:   72(fvec4) CompositeConstruct 85 85 85 85
-                              Store 74(outf4) 86
+              84:    8(float) FunctionCall 11(Test1(i1;) 83(param)
+              85:    8(float) Load 80(inf)
+              86:      6(int) ConvertFToS 85
+                              Store 87(param) 86
+              88:    8(float) FunctionCall 14(Test2(i1;) 87(param)
+              89:    8(float) FAdd 84 88
+              90:   76(fvec4) CompositeConstruct 89 89 89 89
+                              Store 78(outf4) 90
                               Return
                               Return
                               FunctionEnd
                               FunctionEnd
    11(Test1(i1;):    8(float) Function None 9
    11(Test1(i1;):    8(float) Function None 9
@@ -106,32 +106,32 @@ Warning, version 450 is not yet complete; most version-specific features are pre
    14(Test2(i1;):    8(float) Function None 9
    14(Test2(i1;):    8(float) Function None 9
        13(bound):      7(ptr) FunctionParameter
        13(bound):      7(ptr) FunctionParameter
               15:             Label
               15:             Label
-       47(param):      7(ptr) Variable Function
-              40:      6(int) Load 13(bound)
-              42:    28(bool) SGreaterThan 40 41
-                              SelectionMerge 44 None
-                              BranchConditional 42 43 49
-              43:               Label
-              45:      6(int)   Load 13(bound)
-              46:      6(int)   IMul 45 41
-                                Store 47(param) 46
-              48:    8(float)   FunctionCall 11(Test1(i1;) 47(param)
-                                ReturnValue 48
-              49:               Label
-              50:      6(int)   Load 13(bound)
-              52:      6(int)   IMul 50 51
-              59:     58(ptr)   AccessChain 55(ini4) 57
-              60:      6(int)   Load 59
-              62:     58(ptr)   AccessChain 55(ini4) 61
+       49(param):      7(ptr) Variable Function
+              42:      6(int) Load 13(bound)
+              44:    28(bool) SGreaterThan 42 43
+                              SelectionMerge 46 None
+                              BranchConditional 44 45 52
+              45:               Label
+              47:      6(int)   Load 13(bound)
+              48:      6(int)   IMul 47 43
+                                Store 49(param) 48
+              50:    8(float)   FunctionCall 11(Test1(i1;) 49(param)
+                                ReturnValue 50
+              52:               Label
+              53:      6(int)   Load 13(bound)
+              55:      6(int)   IMul 53 54
+              62:     61(ptr)   AccessChain 58(ini4) 60
               63:      6(int)   Load 62
               63:      6(int)   Load 62
-              64:      6(int)   IMul 60 63
-              65:      6(int)   IAdd 52 64
-              67:     58(ptr)   AccessChain 55(ini4) 66
-              68:      6(int)   Load 67
-              69:      6(int)   IAdd 65 68
-              70:    8(float)   ConvertSToF 69
-                                ReturnValue 70
-              44:             Label
-              71:    8(float) Undef
-                              ReturnValue 71
+              65:     61(ptr)   AccessChain 58(ini4) 64
+              66:      6(int)   Load 65
+              67:      6(int)   IMul 63 66
+              68:      6(int)   IAdd 55 67
+              70:     61(ptr)   AccessChain 58(ini4) 69
+              71:      6(int)   Load 70
+              72:      6(int)   IAdd 68 71
+              73:    8(float)   ConvertSToF 72
+                                ReturnValue 73
+              46:             Label
+              75:    8(float) Undef
+                              ReturnValue 75
                               FunctionEnd
                               FunctionEnd

+ 20 - 20
3rdparty/glslang/Test/baseResults/remap.switch.none.frag.out

@@ -5,7 +5,7 @@ WARNING: 0:5: '' : all default precisions are highp; use precision statements to
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 44
+// Id's are bound by 48
 
 
                               Capability Shader
                               Capability Shader
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
@@ -20,8 +20,8 @@ WARNING: 0:5: '' : all default precisions are highp; use precision statements to
                               Decorate 23(FragColor) RelaxedPrecision
                               Decorate 23(FragColor) RelaxedPrecision
                               Decorate 23(FragColor) Location 0
                               Decorate 23(FragColor) Location 0
                               Decorate 29 RelaxedPrecision
                               Decorate 29 RelaxedPrecision
-                              Decorate 35 RelaxedPrecision
-                              Decorate 41 RelaxedPrecision
+                              Decorate 36 RelaxedPrecision
+                              Decorate 43 RelaxedPrecision
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeFloat 32
                6:             TypeFloat 32
@@ -36,12 +36,12 @@ WARNING: 0:5: '' : all default precisions are highp; use precision statements to
    23(FragColor):     22(ptr) Variable Output
    23(FragColor):     22(ptr) Variable Output
               24:     10(int) Constant 0
               24:     10(int) Constant 0
               27:    6(float) Constant 0
               27:    6(float) Constant 0
-              30:     10(int) Constant 1
-              33:    6(float) Constant 1065353216
-              36:     10(int) Constant 2
-              39:    6(float) Constant 1073741824
-              42:    6(float) Constant 3212836864
-              43:    7(fvec4) ConstantComposite 42 42 42 42
+              31:     10(int) Constant 1
+              34:    6(float) Constant 1065353216
+              38:     10(int) Constant 2
+              41:    6(float) Constant 1073741824
+              45:    6(float) Constant 3212836864
+              46:    7(fvec4) ConstantComposite 45 45 45 45
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
               13:     12(ptr) AccessChain 9(in0) 11
               13:     12(ptr) AccessChain 9(in0) 11
@@ -53,7 +53,7 @@ WARNING: 0:5: '' : all default precisions are highp; use precision statements to
                                      case 1: 18
                                      case 1: 18
                                      case 2: 19
                                      case 2: 19
               20:               Label
               20:               Label
-                                Store 23(FragColor) 43
+                                Store 23(FragColor) 46
                                 Branch 21
                                 Branch 21
               17:               Label
               17:               Label
               25:     12(ptr)   AccessChain 9(in0) 24
               25:     12(ptr)   AccessChain 9(in0) 24
@@ -63,18 +63,18 @@ WARNING: 0:5: '' : all default precisions are highp; use precision statements to
                                 Store 23(FragColor) 29
                                 Store 23(FragColor) 29
                                 Branch 21
                                 Branch 21
               18:               Label
               18:               Label
-              31:     12(ptr)   AccessChain 9(in0) 30
-              32:    6(float)   Load 31
-              34:    6(float)   FAdd 32 33
-              35:    7(fvec4)   CompositeConstruct 34 34 34 34
-                                Store 23(FragColor) 35
+              32:     12(ptr)   AccessChain 9(in0) 31
+              33:    6(float)   Load 32
+              35:    6(float)   FAdd 33 34
+              36:    7(fvec4)   CompositeConstruct 35 35 35 35
+                                Store 23(FragColor) 36
                                 Branch 21
                                 Branch 21
               19:               Label
               19:               Label
-              37:     12(ptr)   AccessChain 9(in0) 36
-              38:    6(float)   Load 37
-              40:    6(float)   FAdd 38 39
-              41:    7(fvec4)   CompositeConstruct 40 40 40 40
-                                Store 23(FragColor) 41
+              39:     12(ptr)   AccessChain 9(in0) 38
+              40:    6(float)   Load 39
+              42:    6(float)   FAdd 40 41
+              43:    7(fvec4)   CompositeConstruct 42 42 42 42
+                                Store 23(FragColor) 43
                                 Branch 21
                                 Branch 21
               21:             Label
               21:             Label
                               Return
                               Return

+ 46 - 0
3rdparty/glslang/Test/baseResults/spv.GeometryShaderPassthrough.geom.out

@@ -0,0 +1,46 @@
+spv.GeometryShaderPassthrough.geom
+Warning, version 450 is not yet complete; most version-specific features are present, but some are missing.
+
+// Module Version 10000
+// Generated by (magic number): 80001
+// Id's are bound by 15
+
+                              Capability Geometry
+                              Capability GeometryShaderPassthroughNV
+                              Extension  "SPV_NV_geometry_shader_passthrough"
+               1:             ExtInstImport  "GLSL.std.450"
+                              MemoryModel Logical GLSL450
+                              EntryPoint Geometry 4  "main" 10 14
+                              ExecutionMode 4 Triangles
+                              ExecutionMode 4 Invocations 1
+                              ExecutionMode 4 OutputVertices
+                              Source GLSL 450
+                              SourceExtension  "GL_NV_geometry_shader_passthrough"
+                              Name 4  "main"
+                              Name 8  "gl_PerVertex"
+                              MemberName 8(gl_PerVertex) 0  "gl_Position"
+                              Name 10  ""
+                              Name 12  "Inputs"
+                              MemberName 12(Inputs) 0  "texcoord"
+                              MemberName 12(Inputs) 1  "baseColor"
+                              Name 14  ""
+                              MemberDecorate 8(gl_PerVertex) 0 BuiltIn Position
+                              Decorate 8(gl_PerVertex) Block
+                              Decorate 10 PassthroughNV
+                              Decorate 12(Inputs) Block
+                              Decorate 14 PassthroughNV
+               2:             TypeVoid
+               3:             TypeFunction 2
+               6:             TypeFloat 32
+               7:             TypeVector 6(float) 4
+ 8(gl_PerVertex):             TypeStruct 7(fvec4)
+               9:             TypePointer Input 8(gl_PerVertex)
+              10:      9(ptr) Variable Input
+              11:             TypeVector 6(float) 2
+      12(Inputs):             TypeStruct 11(fvec2) 7(fvec4)
+              13:             TypePointer Input 12(Inputs)
+              14:     13(ptr) Variable Input
+         4(main):           2 Function None 3
+               5:             Label
+                              Return
+                              FunctionEnd

+ 42 - 0
3rdparty/glslang/Test/baseResults/spv.sampleMaskOverrideCoverage.frag.out

@@ -0,0 +1,42 @@
+spv.sampleMaskOverrideCoverage.frag
+Warning, version 450 is not yet complete; most version-specific features are present, but some are missing.
+
+// Module Version 10000
+// Generated by (magic number): 80001
+// Id's are bound by 20
+
+                              Capability Shader
+                              Capability SampleRateShading
+                              Extension  "SPV_NV_sample_mask_override_coverage"
+               1:             ExtInstImport  "GLSL.std.450"
+                              MemoryModel Logical GLSL450
+                              EntryPoint Fragment 4  "main" 11 19
+                              ExecutionMode 4 OriginUpperLeft
+                              Source GLSL 450
+                              SourceExtension  "GL_NV_sample_mask_override_coverage"
+                              Name 4  "main"
+                              Name 11  "gl_SampleMask"
+                              Name 19  "color"
+                              Decorate 11(gl_SampleMask) BuiltIn SampleMask
+                              Decorate 11(gl_SampleMask) OverrideCoverageNV
+               2:             TypeVoid
+               3:             TypeFunction 2
+               6:             TypeInt 32 1
+               7:             TypeInt 32 0
+               8:      7(int) Constant 1
+               9:             TypeArray 6(int) 8
+              10:             TypePointer Output 9
+11(gl_SampleMask):     10(ptr) Variable Output
+              12:      6(int) Constant 0
+              13:      6(int) Constant 4294967295
+              14:             TypePointer Output 6(int)
+              16:             TypeFloat 32
+              17:             TypeVector 16(float) 4
+              18:             TypePointer Input 17(fvec4)
+       19(color):     18(ptr) Variable Input
+         4(main):           2 Function None 3
+               5:             Label
+              15:     14(ptr) AccessChain 11(gl_SampleMask) 12
+                              Store 15 13
+                              Return
+                              FunctionEnd

+ 262 - 264
3rdparty/glslang/Test/baseResults/spv.shaderBallot.comp.out

@@ -3,11 +3,10 @@ Warning, version 450 is not yet complete; most version-specific features are pre
 
 
 // Module Version 10000
 // Module Version 10000
 // Generated by (magic number): 80001
 // Generated by (magic number): 80001
-// Id's are bound by 299
+// Id's are bound by 298
 
 
                               Capability Shader
                               Capability Shader
                               Capability Int64
                               Capability Int64
-                              Capability Groups
                               Capability SubgroupBallotKHR
                               Capability SubgroupBallotKHR
                               Extension  "SPV_KHR_shader_ballot"
                               Extension  "SPV_KHR_shader_ballot"
                1:             ExtInstImport  "GLSL.std.450"
                1:             ExtInstImport  "GLSL.std.450"
@@ -45,7 +44,7 @@ Warning, version 450 is not yet complete; most version-specific features are pre
                               Decorate 52(Buffers) BufferBlock
                               Decorate 52(Buffers) BufferBlock
                               Decorate 55(data) DescriptorSet 0
                               Decorate 55(data) DescriptorSet 0
                               Decorate 55(data) Binding 0
                               Decorate 55(data) Binding 0
-                              Decorate 298 BuiltIn WorkgroupSize
+                              Decorate 297 BuiltIn WorkgroupSize
                2:             TypeVoid
                2:             TypeVoid
                3:             TypeFunction 2
                3:             TypeFunction 2
                6:             TypeInt 32 0
                6:             TypeInt 32 0
@@ -77,23 +76,22 @@ Warning, version 450 is not yet complete; most version-specific features are pre
               57:     50(int) Constant 0
               57:     50(int) Constant 0
               58:      6(int) Constant 0
               58:      6(int) Constant 0
               59:             TypePointer Uniform 48(float)
               59:             TypePointer Uniform 48(float)
-              63:      6(int) Constant 3
-              67:     50(int) Constant 1
-              68:             TypeVector 48(float) 2
-              69:             TypePointer Uniform 49(fvec4)
-              83:     50(int) Constant 2
-              84:             TypeVector 48(float) 3
-             100:     50(int) Constant 3
-             115:             TypePointer Uniform 50(int)
-             122:             TypeVector 50(int) 2
-             123:             TypePointer Uniform 51(ivec4)
-             137:             TypeVector 50(int) 3
-             167:             TypePointer Uniform 6(int)
-             174:             TypePointer Uniform 38(ivec4)
-             188:             TypeVector 6(int) 3
-             296:      6(int) Constant 8
-             297:      6(int) Constant 1
-             298:  188(ivec3) ConstantComposite 296 296 297
+              66:     50(int) Constant 1
+              67:             TypeVector 48(float) 2
+              68:             TypePointer Uniform 49(fvec4)
+              82:     50(int) Constant 2
+              83:             TypeVector 48(float) 3
+              99:     50(int) Constant 3
+             114:             TypePointer Uniform 50(int)
+             121:             TypeVector 50(int) 2
+             122:             TypePointer Uniform 51(ivec4)
+             136:             TypeVector 50(int) 3
+             166:             TypePointer Uniform 6(int)
+             173:             TypePointer Uniform 38(ivec4)
+             187:             TypeVector 6(int) 3
+             295:      6(int) Constant 8
+             296:      6(int) Constant 1
+             297:  187(ivec3) ConstantComposite 295 295 296
          4(main):           2 Function None 3
          4(main):           2 Function None 3
                5:             Label
                5:             Label
    8(invocation):      7(ptr) Variable Function
    8(invocation):      7(ptr) Variable Function
@@ -121,256 +119,256 @@ Warning, version 450 is not yet complete; most version-specific features are pre
               44:     17(int) Bitcast 43
               44:     17(int) Bitcast 43
               45:    36(bool) IEqual 35 44
               45:    36(bool) IEqual 35 44
                               SelectionMerge 47 None
                               SelectionMerge 47 None
-                              BranchConditional 45 46 217
+                              BranchConditional 45 46 216
               46:               Label
               46:               Label
               56:      6(int)   Load 8(invocation)
               56:      6(int)   Load 8(invocation)
               60:     59(ptr)   AccessChain 55(data) 57 57 58
               60:     59(ptr)   AccessChain 55(data) 57 57 58
               61:   48(float)   Load 60
               61:   48(float)   Load 60
               62:      6(int)   Load 8(invocation)
               62:      6(int)   Load 8(invocation)
-              64:   48(float)   GroupBroadcast 63 61 62
-              65:     59(ptr)   AccessChain 55(data) 56 57 58
-                                Store 65 64
-              66:      6(int)   Load 8(invocation)
-              70:     69(ptr)   AccessChain 55(data) 67 57
-              71:   49(fvec4)   Load 70
-              72:   68(fvec2)   VectorShuffle 71 71 0 1
-              73:      6(int)   Load 8(invocation)
-              74:   48(float)   CompositeExtract 72 0
-              75:   48(float)   GroupBroadcast 63 74 73
-              76:   48(float)   CompositeExtract 72 1
-              77:   48(float)   GroupBroadcast 63 76 73
-              78:   68(fvec2)   CompositeConstruct 75 77
-              79:     69(ptr)   AccessChain 55(data) 66 57
-              80:   49(fvec4)   Load 79
-              81:   49(fvec4)   VectorShuffle 80 78 4 5 2 3
-                                Store 79 81
-              82:      6(int)   Load 8(invocation)
-              85:     69(ptr)   AccessChain 55(data) 83 57
-              86:   49(fvec4)   Load 85
-              87:   84(fvec3)   VectorShuffle 86 86 0 1 2
-              88:      6(int)   Load 8(invocation)
-              89:   48(float)   CompositeExtract 87 0
-              90:   48(float)   GroupBroadcast 63 89 88
-              91:   48(float)   CompositeExtract 87 1
-              92:   48(float)   GroupBroadcast 63 91 88
-              93:   48(float)   CompositeExtract 87 2
-              94:   48(float)   GroupBroadcast 63 93 88
-              95:   84(fvec3)   CompositeConstruct 90 92 94
-              96:     69(ptr)   AccessChain 55(data) 82 57
-              97:   49(fvec4)   Load 96
-              98:   49(fvec4)   VectorShuffle 97 95 4 5 6 3
-                                Store 96 98
-              99:      6(int)   Load 8(invocation)
-             101:     69(ptr)   AccessChain 55(data) 100 57
-             102:   49(fvec4)   Load 101
-             103:      6(int)   Load 8(invocation)
-             104:   48(float)   CompositeExtract 102 0
-             105:   48(float)   GroupBroadcast 63 104 103
-             106:   48(float)   CompositeExtract 102 1
-             107:   48(float)   GroupBroadcast 63 106 103
-             108:   48(float)   CompositeExtract 102 2
-             109:   48(float)   GroupBroadcast 63 108 103
-             110:   48(float)   CompositeExtract 102 3
-             111:   48(float)   GroupBroadcast 63 110 103
-             112:   49(fvec4)   CompositeConstruct 105 107 109 111
-             113:     69(ptr)   AccessChain 55(data) 99 57
-                                Store 113 112
-             114:      6(int)   Load 8(invocation)
-             116:    115(ptr)   AccessChain 55(data) 57 67 58
-             117:     50(int)   Load 116
-             118:      6(int)   Load 8(invocation)
-             119:     50(int)   GroupBroadcast 63 117 118
-             120:    115(ptr)   AccessChain 55(data) 114 67 58
-                                Store 120 119
-             121:      6(int)   Load 8(invocation)
-             124:    123(ptr)   AccessChain 55(data) 67 67
-             125:   51(ivec4)   Load 124
-             126:  122(ivec2)   VectorShuffle 125 125 0 1
-             127:      6(int)   Load 8(invocation)
-             128:     50(int)   CompositeExtract 126 0
-             129:     50(int)   GroupBroadcast 63 128 127
-             130:     50(int)   CompositeExtract 126 1
-             131:     50(int)   GroupBroadcast 63 130 127
-             132:  122(ivec2)   CompositeConstruct 129 131
-             133:    123(ptr)   AccessChain 55(data) 121 67
-             134:   51(ivec4)   Load 133
-             135:   51(ivec4)   VectorShuffle 134 132 4 5 2 3
-                                Store 133 135
-             136:      6(int)   Load 8(invocation)
-             138:    123(ptr)   AccessChain 55(data) 83 67
-             139:   51(ivec4)   Load 138
-             140:  137(ivec3)   VectorShuffle 139 139 0 1 2
-             141:      6(int)   Load 8(invocation)
-             142:     50(int)   CompositeExtract 140 0
-             143:     50(int)   GroupBroadcast 63 142 141
-             144:     50(int)   CompositeExtract 140 1
-             145:     50(int)   GroupBroadcast 63 144 141
-             146:     50(int)   CompositeExtract 140 2
-             147:     50(int)   GroupBroadcast 63 146 141
-             148:  137(ivec3)   CompositeConstruct 143 145 147
-             149:    123(ptr)   AccessChain 55(data) 136 67
-             150:   51(ivec4)   Load 149
-             151:   51(ivec4)   VectorShuffle 150 148 4 5 6 3
-                                Store 149 151
-             152:      6(int)   Load 8(invocation)
-             153:    123(ptr)   AccessChain 55(data) 100 67
-             154:   51(ivec4)   Load 153
-             155:      6(int)   Load 8(invocation)
-             156:     50(int)   CompositeExtract 154 0
-             157:     50(int)   GroupBroadcast 63 156 155
-             158:     50(int)   CompositeExtract 154 1
-             159:     50(int)   GroupBroadcast 63 158 155
-             160:     50(int)   CompositeExtract 154 2
-             161:     50(int)   GroupBroadcast 63 160 155
-             162:     50(int)   CompositeExtract 154 3
-             163:     50(int)   GroupBroadcast 63 162 155
-             164:   51(ivec4)   CompositeConstruct 157 159 161 163
-             165:    123(ptr)   AccessChain 55(data) 152 67
-                                Store 165 164
-             166:      6(int)   Load 8(invocation)
-             168:    167(ptr)   AccessChain 55(data) 57 83 58
-             169:      6(int)   Load 168
-             170:      6(int)   Load 8(invocation)
-             171:      6(int)   GroupBroadcast 63 169 170
-             172:    167(ptr)   AccessChain 55(data) 166 83 58
-                                Store 172 171
-             173:      6(int)   Load 8(invocation)
-             175:    174(ptr)   AccessChain 55(data) 67 83
-             176:   38(ivec4)   Load 175
-             177:   42(ivec2)   VectorShuffle 176 176 0 1
-             178:      6(int)   Load 8(invocation)
-             179:      6(int)   CompositeExtract 177 0
-             180:      6(int)   GroupBroadcast 63 179 178
-             181:      6(int)   CompositeExtract 177 1
-             182:      6(int)   GroupBroadcast 63 181 178
-             183:   42(ivec2)   CompositeConstruct 180 182
-             184:    174(ptr)   AccessChain 55(data) 173 83
-             185:   38(ivec4)   Load 184
-             186:   38(ivec4)   VectorShuffle 185 183 4 5 2 3
-                                Store 184 186
-             187:      6(int)   Load 8(invocation)
-             189:    174(ptr)   AccessChain 55(data) 83 83
-             190:   38(ivec4)   Load 189
-             191:  188(ivec3)   VectorShuffle 190 190 0 1 2
-             192:      6(int)   Load 8(invocation)
-             193:      6(int)   CompositeExtract 191 0
-             194:      6(int)   GroupBroadcast 63 193 192
-             195:      6(int)   CompositeExtract 191 1
-             196:      6(int)   GroupBroadcast 63 195 192
-             197:      6(int)   CompositeExtract 191 2
-             198:      6(int)   GroupBroadcast 63 197 192
-             199:  188(ivec3)   CompositeConstruct 194 196 198
-             200:    174(ptr)   AccessChain 55(data) 187 83
-             201:   38(ivec4)   Load 200
-             202:   38(ivec4)   VectorShuffle 201 199 4 5 6 3
-                                Store 200 202
-             203:      6(int)   Load 8(invocation)
-             204:    174(ptr)   AccessChain 55(data) 100 83
-             205:   38(ivec4)   Load 204
-             206:      6(int)   Load 8(invocation)
-             207:      6(int)   CompositeExtract 205 0
-             208:      6(int)   GroupBroadcast 63 207 206
-             209:      6(int)   CompositeExtract 205 1
-             210:      6(int)   GroupBroadcast 63 209 206
-             211:      6(int)   CompositeExtract 205 2
-             212:      6(int)   GroupBroadcast 63 211 206
-             213:      6(int)   CompositeExtract 205 3
-             214:      6(int)   GroupBroadcast 63 213 206
-             215:   38(ivec4)   CompositeConstruct 208 210 212 214
-             216:    174(ptr)   AccessChain 55(data) 203 83
-                                Store 216 215
+              63:   48(float)   SubgroupReadInvocationKHR 61 62
+              64:     59(ptr)   AccessChain 55(data) 56 57 58
+                                Store 64 63
+              65:      6(int)   Load 8(invocation)
+              69:     68(ptr)   AccessChain 55(data) 66 57
+              70:   49(fvec4)   Load 69
+              71:   67(fvec2)   VectorShuffle 70 70 0 1
+              72:      6(int)   Load 8(invocation)
+              73:   48(float)   CompositeExtract 71 0
+              74:   48(float)   SubgroupReadInvocationKHR 73 72
+              75:   48(float)   CompositeExtract 71 1
+              76:   48(float)   SubgroupReadInvocationKHR 75 72
+              77:   67(fvec2)   CompositeConstruct 74 76
+              78:     68(ptr)   AccessChain 55(data) 65 57
+              79:   49(fvec4)   Load 78
+              80:   49(fvec4)   VectorShuffle 79 77 4 5 2 3
+                                Store 78 80
+              81:      6(int)   Load 8(invocation)
+              84:     68(ptr)   AccessChain 55(data) 82 57
+              85:   49(fvec4)   Load 84
+              86:   83(fvec3)   VectorShuffle 85 85 0 1 2
+              87:      6(int)   Load 8(invocation)
+              88:   48(float)   CompositeExtract 86 0
+              89:   48(float)   SubgroupReadInvocationKHR 88 87
+              90:   48(float)   CompositeExtract 86 1
+              91:   48(float)   SubgroupReadInvocationKHR 90 87
+              92:   48(float)   CompositeExtract 86 2
+              93:   48(float)   SubgroupReadInvocationKHR 92 87
+              94:   83(fvec3)   CompositeConstruct 89 91 93
+              95:     68(ptr)   AccessChain 55(data) 81 57
+              96:   49(fvec4)   Load 95
+              97:   49(fvec4)   VectorShuffle 96 94 4 5 6 3
+                                Store 95 97
+              98:      6(int)   Load 8(invocation)
+             100:     68(ptr)   AccessChain 55(data) 99 57
+             101:   49(fvec4)   Load 100
+             102:      6(int)   Load 8(invocation)
+             103:   48(float)   CompositeExtract 101 0
+             104:   48(float)   SubgroupReadInvocationKHR 103 102
+             105:   48(float)   CompositeExtract 101 1
+             106:   48(float)   SubgroupReadInvocationKHR 105 102
+             107:   48(float)   CompositeExtract 101 2
+             108:   48(float)   SubgroupReadInvocationKHR 107 102
+             109:   48(float)   CompositeExtract 101 3
+             110:   48(float)   SubgroupReadInvocationKHR 109 102
+             111:   49(fvec4)   CompositeConstruct 104 106 108 110
+             112:     68(ptr)   AccessChain 55(data) 98 57
+                                Store 112 111
+             113:      6(int)   Load 8(invocation)
+             115:    114(ptr)   AccessChain 55(data) 57 66 58
+             116:     50(int)   Load 115
+             117:      6(int)   Load 8(invocation)
+             118:     50(int)   SubgroupReadInvocationKHR 116 117
+             119:    114(ptr)   AccessChain 55(data) 113 66 58
+                                Store 119 118
+             120:      6(int)   Load 8(invocation)
+             123:    122(ptr)   AccessChain 55(data) 66 66
+             124:   51(ivec4)   Load 123
+             125:  121(ivec2)   VectorShuffle 124 124 0 1
+             126:      6(int)   Load 8(invocation)
+             127:     50(int)   CompositeExtract 125 0
+             128:     50(int)   SubgroupReadInvocationKHR 127 126
+             129:     50(int)   CompositeExtract 125 1
+             130:     50(int)   SubgroupReadInvocationKHR 129 126
+             131:  121(ivec2)   CompositeConstruct 128 130
+             132:    122(ptr)   AccessChain 55(data) 120 66
+             133:   51(ivec4)   Load 132
+             134:   51(ivec4)   VectorShuffle 133 131 4 5 2 3
+                                Store 132 134
+             135:      6(int)   Load 8(invocation)
+             137:    122(ptr)   AccessChain 55(data) 82 66
+             138:   51(ivec4)   Load 137
+             139:  136(ivec3)   VectorShuffle 138 138 0 1 2
+             140:      6(int)   Load 8(invocation)
+             141:     50(int)   CompositeExtract 139 0
+             142:     50(int)   SubgroupReadInvocationKHR 141 140
+             143:     50(int)   CompositeExtract 139 1
+             144:     50(int)   SubgroupReadInvocationKHR 143 140
+             145:     50(int)   CompositeExtract 139 2
+             146:     50(int)   SubgroupReadInvocationKHR 145 140
+             147:  136(ivec3)   CompositeConstruct 142 144 146
+             148:    122(ptr)   AccessChain 55(data) 135 66
+             149:   51(ivec4)   Load 148
+             150:   51(ivec4)   VectorShuffle 149 147 4 5 6 3
+                                Store 148 150
+             151:      6(int)   Load 8(invocation)
+             152:    122(ptr)   AccessChain 55(data) 99 66
+             153:   51(ivec4)   Load 152
+             154:      6(int)   Load 8(invocation)
+             155:     50(int)   CompositeExtract 153 0
+             156:     50(int)   SubgroupReadInvocationKHR 155 154
+             157:     50(int)   CompositeExtract 153 1
+             158:     50(int)   SubgroupReadInvocationKHR 157 154
+             159:     50(int)   CompositeExtract 153 2
+             160:     50(int)   SubgroupReadInvocationKHR 159 154
+             161:     50(int)   CompositeExtract 153 3
+             162:     50(int)   SubgroupReadInvocationKHR 161 154
+             163:   51(ivec4)   CompositeConstruct 156 158 160 162
+             164:    122(ptr)   AccessChain 55(data) 151 66
+                                Store 164 163
+             165:      6(int)   Load 8(invocation)
+             167:    166(ptr)   AccessChain 55(data) 57 82 58
+             168:      6(int)   Load 167
+             169:      6(int)   Load 8(invocation)
+             170:      6(int)   SubgroupReadInvocationKHR 168 169
+             171:    166(ptr)   AccessChain 55(data) 165 82 58
+                                Store 171 170
+             172:      6(int)   Load 8(invocation)
+             174:    173(ptr)   AccessChain 55(data) 66 82
+             175:   38(ivec4)   Load 174
+             176:   42(ivec2)   VectorShuffle 175 175 0 1
+             177:      6(int)   Load 8(invocation)
+             178:      6(int)   CompositeExtract 176 0
+             179:      6(int)   SubgroupReadInvocationKHR 178 177
+             180:      6(int)   CompositeExtract 176 1
+             181:      6(int)   SubgroupReadInvocationKHR 180 177
+             182:   42(ivec2)   CompositeConstruct 179 181
+             183:    173(ptr)   AccessChain 55(data) 172 82
+             184:   38(ivec4)   Load 183
+             185:   38(ivec4)   VectorShuffle 184 182 4 5 2 3
+                                Store 183 185
+             186:      6(int)   Load 8(invocation)
+             188:    173(ptr)   AccessChain 55(data) 82 82
+             189:   38(ivec4)   Load 188
+             190:  187(ivec3)   VectorShuffle 189 189 0 1 2
+             191:      6(int)   Load 8(invocation)
+             192:      6(int)   CompositeExtract 190 0
+             193:      6(int)   SubgroupReadInvocationKHR 192 191
+             194:      6(int)   CompositeExtract 190 1
+             195:      6(int)   SubgroupReadInvocationKHR 194 191
+             196:      6(int)   CompositeExtract 190 2
+             197:      6(int)   SubgroupReadInvocationKHR 196 191
+             198:  187(ivec3)   CompositeConstruct 193 195 197
+             199:    173(ptr)   AccessChain 55(data) 186 82
+             200:   38(ivec4)   Load 199
+             201:   38(ivec4)   VectorShuffle 200 198 4 5 6 3
+                                Store 199 201
+             202:      6(int)   Load 8(invocation)
+             203:    173(ptr)   AccessChain 55(data) 99 82
+             204:   38(ivec4)   Load 203
+             205:      6(int)   Load 8(invocation)
+             206:      6(int)   CompositeExtract 204 0
+             207:      6(int)   SubgroupReadInvocationKHR 206 205
+             208:      6(int)   CompositeExtract 204 1
+             209:      6(int)   SubgroupReadInvocationKHR 208 205
+             210:      6(int)   CompositeExtract 204 2
+             211:      6(int)   SubgroupReadInvocationKHR 210 205
+             212:      6(int)   CompositeExtract 204 3
+             213:      6(int)   SubgroupReadInvocationKHR 212 205
+             214:   38(ivec4)   CompositeConstruct 207 209 211 213
+             215:    173(ptr)   AccessChain 55(data) 202 82
+                                Store 215 214
                                 Branch 47
                                 Branch 47
-             217:               Label
-             218:      6(int)   Load 8(invocation)
-             219:     59(ptr)   AccessChain 55(data) 57 57 58
-             220:   48(float)   Load 219
-             221:   48(float)   SubgroupFirstInvocationKHR 220
-             222:     59(ptr)   AccessChain 55(data) 218 57 58
-                                Store 222 221
-             223:      6(int)   Load 8(invocation)
-             224:     69(ptr)   AccessChain 55(data) 67 57
-             225:   49(fvec4)   Load 224
-             226:   68(fvec2)   VectorShuffle 225 225 0 1
-             227:   68(fvec2)   SubgroupFirstInvocationKHR 226
-             228:     69(ptr)   AccessChain 55(data) 223 57
-             229:   49(fvec4)   Load 228
-             230:   49(fvec4)   VectorShuffle 229 227 4 5 2 3
-                                Store 228 230
-             231:      6(int)   Load 8(invocation)
-             232:     69(ptr)   AccessChain 55(data) 83 57
-             233:   49(fvec4)   Load 232
-             234:   84(fvec3)   VectorShuffle 233 233 0 1 2
-             235:   84(fvec3)   SubgroupFirstInvocationKHR 234
-             236:     69(ptr)   AccessChain 55(data) 231 57
-             237:   49(fvec4)   Load 236
-             238:   49(fvec4)   VectorShuffle 237 235 4 5 6 3
-                                Store 236 238
-             239:      6(int)   Load 8(invocation)
-             240:     69(ptr)   AccessChain 55(data) 100 57
-             241:   49(fvec4)   Load 240
-             242:   49(fvec4)   SubgroupFirstInvocationKHR 241
-             243:     69(ptr)   AccessChain 55(data) 239 57
-                                Store 243 242
-             244:      6(int)   Load 8(invocation)
-             245:    115(ptr)   AccessChain 55(data) 57 67 58
-             246:     50(int)   Load 245
-             247:     50(int)   SubgroupFirstInvocationKHR 246
-             248:    115(ptr)   AccessChain 55(data) 244 67 58
-                                Store 248 247
-             249:      6(int)   Load 8(invocation)
-             250:    123(ptr)   AccessChain 55(data) 67 67
-             251:   51(ivec4)   Load 250
-             252:  122(ivec2)   VectorShuffle 251 251 0 1
-             253:  122(ivec2)   SubgroupFirstInvocationKHR 252
-             254:    123(ptr)   AccessChain 55(data) 249 67
-             255:   51(ivec4)   Load 254
-             256:   51(ivec4)   VectorShuffle 255 253 4 5 2 3
-                                Store 254 256
-             257:      6(int)   Load 8(invocation)
-             258:    123(ptr)   AccessChain 55(data) 83 67
-             259:   51(ivec4)   Load 258
-             260:  137(ivec3)   VectorShuffle 259 259 0 1 2
-             261:  137(ivec3)   SubgroupFirstInvocationKHR 260
-             262:    123(ptr)   AccessChain 55(data) 257 67
-             263:   51(ivec4)   Load 262
-             264:   51(ivec4)   VectorShuffle 263 261 4 5 6 3
-                                Store 262 264
-             265:      6(int)   Load 8(invocation)
-             266:    123(ptr)   AccessChain 55(data) 100 67
-             267:   51(ivec4)   Load 266
-             268:   51(ivec4)   SubgroupFirstInvocationKHR 267
-             269:    123(ptr)   AccessChain 55(data) 265 67
-                                Store 269 268
-             270:      6(int)   Load 8(invocation)
-             271:    167(ptr)   AccessChain 55(data) 57 83 58
-             272:      6(int)   Load 271
-             273:      6(int)   SubgroupFirstInvocationKHR 272
-             274:    167(ptr)   AccessChain 55(data) 270 83 58
-                                Store 274 273
-             275:      6(int)   Load 8(invocation)
-             276:    174(ptr)   AccessChain 55(data) 67 83
-             277:   38(ivec4)   Load 276
-             278:   42(ivec2)   VectorShuffle 277 277 0 1
-             279:   42(ivec2)   SubgroupFirstInvocationKHR 278
-             280:    174(ptr)   AccessChain 55(data) 275 83
-             281:   38(ivec4)   Load 280
-             282:   38(ivec4)   VectorShuffle 281 279 4 5 2 3
-                                Store 280 282
-             283:      6(int)   Load 8(invocation)
-             284:    174(ptr)   AccessChain 55(data) 83 83
-             285:   38(ivec4)   Load 284
-             286:  188(ivec3)   VectorShuffle 285 285 0 1 2
-             287:  188(ivec3)   SubgroupFirstInvocationKHR 286
-             288:    174(ptr)   AccessChain 55(data) 283 83
-             289:   38(ivec4)   Load 288
-             290:   38(ivec4)   VectorShuffle 289 287 4 5 6 3
-                                Store 288 290
-             291:      6(int)   Load 8(invocation)
-             292:    174(ptr)   AccessChain 55(data) 100 83
-             293:   38(ivec4)   Load 292
-             294:   38(ivec4)   SubgroupFirstInvocationKHR 293
-             295:    174(ptr)   AccessChain 55(data) 291 83
-                                Store 295 294
+             216:               Label
+             217:      6(int)   Load 8(invocation)
+             218:     59(ptr)   AccessChain 55(data) 57 57 58
+             219:   48(float)   Load 218
+             220:   48(float)   SubgroupFirstInvocationKHR 219
+             221:     59(ptr)   AccessChain 55(data) 217 57 58
+                                Store 221 220
+             222:      6(int)   Load 8(invocation)
+             223:     68(ptr)   AccessChain 55(data) 66 57
+             224:   49(fvec4)   Load 223
+             225:   67(fvec2)   VectorShuffle 224 224 0 1
+             226:   67(fvec2)   SubgroupFirstInvocationKHR 225
+             227:     68(ptr)   AccessChain 55(data) 222 57
+             228:   49(fvec4)   Load 227
+             229:   49(fvec4)   VectorShuffle 228 226 4 5 2 3
+                                Store 227 229
+             230:      6(int)   Load 8(invocation)
+             231:     68(ptr)   AccessChain 55(data) 82 57
+             232:   49(fvec4)   Load 231
+             233:   83(fvec3)   VectorShuffle 232 232 0 1 2
+             234:   83(fvec3)   SubgroupFirstInvocationKHR 233
+             235:     68(ptr)   AccessChain 55(data) 230 57
+             236:   49(fvec4)   Load 235
+             237:   49(fvec4)   VectorShuffle 236 234 4 5 6 3
+                                Store 235 237
+             238:      6(int)   Load 8(invocation)
+             239:     68(ptr)   AccessChain 55(data) 99 57
+             240:   49(fvec4)   Load 239
+             241:   49(fvec4)   SubgroupFirstInvocationKHR 240
+             242:     68(ptr)   AccessChain 55(data) 238 57
+                                Store 242 241
+             243:      6(int)   Load 8(invocation)
+             244:    114(ptr)   AccessChain 55(data) 57 66 58
+             245:     50(int)   Load 244
+             246:     50(int)   SubgroupFirstInvocationKHR 245
+             247:    114(ptr)   AccessChain 55(data) 243 66 58
+                                Store 247 246
+             248:      6(int)   Load 8(invocation)
+             249:    122(ptr)   AccessChain 55(data) 66 66
+             250:   51(ivec4)   Load 249
+             251:  121(ivec2)   VectorShuffle 250 250 0 1
+             252:  121(ivec2)   SubgroupFirstInvocationKHR 251
+             253:    122(ptr)   AccessChain 55(data) 248 66
+             254:   51(ivec4)   Load 253
+             255:   51(ivec4)   VectorShuffle 254 252 4 5 2 3
+                                Store 253 255
+             256:      6(int)   Load 8(invocation)
+             257:    122(ptr)   AccessChain 55(data) 82 66
+             258:   51(ivec4)   Load 257
+             259:  136(ivec3)   VectorShuffle 258 258 0 1 2
+             260:  136(ivec3)   SubgroupFirstInvocationKHR 259
+             261:    122(ptr)   AccessChain 55(data) 256 66
+             262:   51(ivec4)   Load 261
+             263:   51(ivec4)   VectorShuffle 262 260 4 5 6 3
+                                Store 261 263
+             264:      6(int)   Load 8(invocation)
+             265:    122(ptr)   AccessChain 55(data) 99 66
+             266:   51(ivec4)   Load 265
+             267:   51(ivec4)   SubgroupFirstInvocationKHR 266
+             268:    122(ptr)   AccessChain 55(data) 264 66
+                                Store 268 267
+             269:      6(int)   Load 8(invocation)
+             270:    166(ptr)   AccessChain 55(data) 57 82 58
+             271:      6(int)   Load 270
+             272:      6(int)   SubgroupFirstInvocationKHR 271
+             273:    166(ptr)   AccessChain 55(data) 269 82 58
+                                Store 273 272
+             274:      6(int)   Load 8(invocation)
+             275:    173(ptr)   AccessChain 55(data) 66 82
+             276:   38(ivec4)   Load 275
+             277:   42(ivec2)   VectorShuffle 276 276 0 1
+             278:   42(ivec2)   SubgroupFirstInvocationKHR 277
+             279:    173(ptr)   AccessChain 55(data) 274 82
+             280:   38(ivec4)   Load 279
+             281:   38(ivec4)   VectorShuffle 280 278 4 5 2 3
+                                Store 279 281
+             282:      6(int)   Load 8(invocation)
+             283:    173(ptr)   AccessChain 55(data) 82 82
+             284:   38(ivec4)   Load 283
+             285:  187(ivec3)   VectorShuffle 284 284 0 1 2
+             286:  187(ivec3)   SubgroupFirstInvocationKHR 285
+             287:    173(ptr)   AccessChain 55(data) 282 82
+             288:   38(ivec4)   Load 287
+             289:   38(ivec4)   VectorShuffle 288 286 4 5 6 3
+                                Store 287 289
+             290:      6(int)   Load 8(invocation)
+             291:    173(ptr)   AccessChain 55(data) 99 82
+             292:   38(ivec4)   Load 291
+             293:   38(ivec4)   SubgroupFirstInvocationKHR 292
+             294:    173(ptr)   AccessChain 55(data) 290 82
+                                Store 294 293
                                 Branch 47
                                 Branch 47
               47:             Label
               47:             Label
                               Return
                               Return

+ 112 - 0
3rdparty/glslang/Test/baseResults/tokenPaste.vert.out

@@ -0,0 +1,112 @@
+tokenPaste.vert
+Warning, version 450 is not yet complete; most version-specific features are present, but some are missing.
+ERROR: 0:38: '##' : unexpected location 
+ERROR: 0:40: '##' : unexpected location; end of replacement list 
+ERROR: 0:49: '##' : combined tokens are too long 
+ERROR: 0:52: '##' : not supported for these tokens 
+ERROR: 0:69: '##' : combined token is invalid 
+ERROR: 5 compilation errors.  No code generated.
+
+
+Shader version: 450
+ERROR: node is still EOpNull!
+0:52  Sequence
+0:52    move second child to first child (temp int)
+0:52      'a' (global int)
+0:52      Constant:
+0:52        11 (const int)
+0:58  Sequence
+0:58    move second child to first child (temp int)
+0:58      'cop' (global int)
+0:58      Constant:
+0:58        160 (const int)
+0:59  Sequence
+0:59    move second child to first child (temp bool)
+0:59      'dop' (global bool)
+0:59      Constant:
+0:59        true (const bool)
+0:63  Function Definition: ShouldntExpandToThis( (global void)
+0:63    Function Parameters: 
+0:65    Sequence
+0:65      Sequence
+0:65        move second child to first child (temp int)
+0:65          'e' (temp int)
+0:65          Constant:
+0:65            16 (const int)
+0:66      right shift second child into first child (temp int)
+0:66        'e' (temp int)
+0:66        Constant:
+0:66          2 (const int)
+0:69      Sequence
+0:69        move second child to first child (temp bool)
+0:69          'f' (temp bool)
+0:69          Compare Greater Than (temp bool)
+0:69            'e' (temp int)
+0:69            Constant:
+0:69              5 (const int)
+0:?   Linker Objects
+0:?     'SecondExpansion' (global int)
+0:?     'PostPasteExpansion' (global int)
+0:?     'foo27' (global float)
+0:?     'foo155' (uniform float)
+0:?     'foo719' (global float)
+0:?     'barfoo' (uniform float)
+0:?     'argless' (global float)
+0:?     'dc1' (global float)
+0:?     'dc2' (global float)
+0:?     'foo875' (uniform float)
+0:?     'ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF012345' (global float)
+0:?     'a' (global int)
+0:?     'aop' (const int)
+0:?       10 (const int)
+0:?     'bop' (const int)
+0:?       4 (const int)
+0:?     'cop' (global int)
+0:?     'dop' (global bool)
+0:?     'gl_VertexID' (gl_VertexId int VertexId)
+0:?     'gl_InstanceID' (gl_InstanceId int InstanceId)
+
+
+Linked vertex stage:
+
+ERROR: Linking vertex stage: Missing entry point: Each stage requires one entry point
+
+Shader version: 450
+ERROR: node is still EOpNull!
+0:52  Sequence
+0:52    move second child to first child (temp int)
+0:52      'a' (global int)
+0:52      Constant:
+0:52        11 (const int)
+0:58  Sequence
+0:58    move second child to first child (temp int)
+0:58      'cop' (global int)
+0:58      Constant:
+0:58        160 (const int)
+0:59  Sequence
+0:59    move second child to first child (temp bool)
+0:59      'dop' (global bool)
+0:59      Constant:
+0:59        true (const bool)
+0:?   Linker Objects
+0:?     'SecondExpansion' (global int)
+0:?     'PostPasteExpansion' (global int)
+0:?     'foo27' (global float)
+0:?     'foo155' (uniform float)
+0:?     'foo719' (global float)
+0:?     'barfoo' (uniform float)
+0:?     'argless' (global float)
+0:?     'dc1' (global float)
+0:?     'dc2' (global float)
+0:?     'foo875' (uniform float)
+0:?     'ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF012345' (global float)
+0:?     'a' (global int)
+0:?     'aop' (const int)
+0:?       10 (const int)
+0:?     'bop' (const int)
+0:?       4 (const int)
+0:?     'cop' (global int)
+0:?     'dop' (global bool)
+0:?     'gl_VertexID' (gl_VertexId int VertexId)
+0:?     'gl_InstanceID' (gl_InstanceId int InstanceId)
+

+ 2 - 2
3rdparty/glslang/Test/hlsl.identifier.sample.frag

@@ -12,7 +12,7 @@ float4 main() : SV_Target0
 {
 {
     // HLSL allows this as an identifier as well.
     // HLSL allows this as an identifier as well.
     // However, this is not true of other qualifier keywords such as "linear".
     // However, this is not true of other qualifier keywords such as "linear".
-    int sample = 3;
+    float4 sample = float4(3,4,5,6);
 
 
-    return float4(0,0,0,0);
+    return sample.rgba; // 'sample' can participate in an expression.
 }
 }

+ 17 - 0
3rdparty/glslang/Test/spv.GeometryShaderPassthrough.geom

@@ -0,0 +1,17 @@
+#version 450
+#extension GL_NV_geometry_shader_passthrough : require
+
+layout(triangles) in;
+
+layout(passthrough) in gl_PerVertex {
+    vec4 gl_Position;
+};
+
+layout(passthrough) in Inputs {
+vec2 texcoord;
+vec4 baseColor;
+};
+
+void main()
+{
+}

+ 7 - 0
3rdparty/glslang/Test/spv.sampleMaskOverrideCoverage.frag

@@ -0,0 +1,7 @@
+#version 450
+#extension GL_NV_sample_mask_override_coverage : enable
+in vec4 color;
+layout(override_coverage) out int gl_SampleMask[];
+void main() {
+    gl_SampleMask[0] = int(0xFFFFFFFF);
+}

+ 70 - 0
3rdparty/glslang/Test/tokenPaste.vert

@@ -0,0 +1,70 @@
+#version 450
+
+// side test verifies multiple rounds of argument expansion
+#define bear SecondExpansion
+#define mmmB bear
+#define mmmA(a) a
+int mmmA(mmmB);                    // mmmB -> bear, and then in mmmA(), bear -> SecondExpansion
+
+// pasting skips the first round of expansion
+#define mmcatmmdog PostPasteExpansion
+#define mmcat cat
+#define mmdog dog
+#define mmp(a,b) a## b
+int mmp(mmcat, mmdog);             // mmcat/mmdog not expanded, mmcatmmdog -> PostPasteExpansion
+
+// multi-token pre
+#define mmtokpastepre(a) a##27
+mmtokpastepre(float foo);          // should declare "float foo27;"
+
+// multi-token post
+#define mmtokpastepost(a) uni ##a
+mmtokpastepost(form float foo155); // should declare "uniform float foo155;"
+
+// non-first argument
+#define foo ShouldntExpandToThis
+#define semi ;
+#define bothpaste(a,b) a##b
+float bothpaste(foo, 719);          // should declare "float foo719;"
+#define secpaste(a,b) a bar ## b
+secpaste(uniform float, foo semi)   // should declare "uniform float barfoo;"
+
+// no args
+#define noArg fl##oat
+noArg argless;
+
+// bad location
+#define bad1 ## float
+bad1 dc1;
+#define bad2 float ##
+bad2 dc2;
+
+// multiple ##
+#define multiPaste(a, b, c) a##or##b flo##at foo##c
+multiPaste(unif, m, 875);
+
+// too long
+#define simplePaste(a,b) a##b
+// 1020 + 5 characters
+float simplePaste(ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF012345, 12345);
+
+// non-identifiers
+int a = simplePaste(11,12);
+
+// operators
+#define MAKE_OP(L, R) L ## R
+const int aop = 10;
+const int bop = 4;
+int cop = aop MAKE_OP(<, <) bop;
+bool dop = aop MAKE_OP(!,=) bop;
+
+#define MAKE_OP3(L, M, R) L ## M ## R
+
+void foo()
+{
+    int e = 16;
+    e MAKE_OP3(>,>,=) 2;
+
+    // recovery from bad op
+    bool f = e MAKE_OP(>,!) 5;
+}

+ 25 - 0
3rdparty/glslang/glslang/Include/Types.h

@@ -599,6 +599,9 @@ public:
         layoutFormat = ElfNone;
         layoutFormat = ElfNone;
 
 
         layoutPushConstant = false;
         layoutPushConstant = false;
+#ifdef NV_EXTENSIONS
+        layoutPassthrough = false;
+#endif
     }
     }
     bool hasLayout() const
     bool hasLayout() const
     {
     {
@@ -652,6 +655,10 @@ public:
 
 
     bool layoutPushConstant;
     bool layoutPushConstant;
 
 
+#ifdef NV_EXTENSIONS
+    bool layoutPassthrough;
+#endif
+
     bool hasUniformLayout() const
     bool hasUniformLayout() const
     {
     {
         return hasMatrix() ||
         return hasMatrix() ||
@@ -920,6 +927,10 @@ struct TShaderQualifiers {
     TLayoutDepth layoutDepth;
     TLayoutDepth layoutDepth;
     bool blendEquation;       // true if any blend equation was specified
     bool blendEquation;       // true if any blend equation was specified
 
 
+#ifdef NV_EXTENSIONS 
+    bool layoutOverrideCoverage;    // true if layout override_coverage set
+#endif 
+
     void init()
     void init()
     {
     {
         geometry = ElgNone;
         geometry = ElgNone;
@@ -939,6 +950,9 @@ struct TShaderQualifiers {
         earlyFragmentTests = false;
         earlyFragmentTests = false;
         layoutDepth = EldNone;
         layoutDepth = EldNone;
         blendEquation = false;
         blendEquation = false;
+#ifdef NV_EXTENSIONS 
+        layoutOverrideCoverage = false;
+#endif
     }
     }
 
 
     // Merge in characteristics from the 'src' qualifier.  They can override when
     // Merge in characteristics from the 'src' qualifier.  They can override when
@@ -975,6 +989,10 @@ struct TShaderQualifiers {
             layoutDepth = src.layoutDepth;
             layoutDepth = src.layoutDepth;
         if (src.blendEquation)
         if (src.blendEquation)
             blendEquation = src.blendEquation;
             blendEquation = src.blendEquation;
+#ifdef NV_EXTENSIONS 
+        if (src.layoutOverrideCoverage)
+            layoutOverrideCoverage = src.layoutOverrideCoverage;
+#endif 
     }
     }
 };
 };
 
 
@@ -1525,6 +1543,13 @@ public:
                     p += snprintf(p, end - p, "constant_id=%d ", qualifier.layoutSpecConstantId);
                     p += snprintf(p, end - p, "constant_id=%d ", qualifier.layoutSpecConstantId);
                 if (qualifier.layoutPushConstant)
                 if (qualifier.layoutPushConstant)
                     p += snprintf(p, end - p, "push_constant ");
                     p += snprintf(p, end - p, "push_constant ");
+
+#ifdef NV_EXTENSIONS
+                if (qualifier.layoutPassthrough)
+                    p += snprintf(p, end - p, "passthrough ");
+#endif
+
+
                 p += snprintf(p, end - p, ") ");
                 p += snprintf(p, end - p, ") ");
             }
             }
         }
         }

+ 2 - 2
3rdparty/glslang/glslang/Include/revision.h

@@ -2,5 +2,5 @@
 // For the version, it uses the latest git tag followed by the number of commits.
 // For the version, it uses the latest git tag followed by the number of commits.
 // For the date, it uses the current date (when then script is run).
 // For the date, it uses the current date (when then script is run).
 
 
-#define GLSLANG_REVISION "Overload400-PrecQual.1695"
-#define GLSLANG_DATE "16-Dec-2016"
+#define GLSLANG_REVISION "Overload400-PrecQual.1721"
+#define GLSLANG_DATE "21-Dec-2016"

+ 51 - 2
3rdparty/glslang/glslang/MachineIndependent/ParseHelper.cpp

@@ -604,7 +604,11 @@ void TParseContext::fixIoArraySize(const TSourceLoc& loc, TType& type)
 void TParseContext::ioArrayCheck(const TSourceLoc& loc, const TType& type, const TString& identifier)
 void TParseContext::ioArrayCheck(const TSourceLoc& loc, const TType& type, const TString& identifier)
 {
 {
     if (! type.isArray() && ! symbolTable.atBuiltInLevel()) {
     if (! type.isArray() && ! symbolTable.atBuiltInLevel()) {
-        if (type.getQualifier().isArrayedIo(language))
+        if (type.getQualifier().isArrayedIo(language)
+#ifdef NV_EXTENSIONS
+            && !type.getQualifier().layoutPassthrough
+#endif
+           )
             error(loc, "type must be an array:", type.getStorageQualifierString(), identifier.c_str());
             error(loc, "type must be an array:", type.getStorageQualifierString(), identifier.c_str());
     }
     }
 }
 }
@@ -3304,6 +3308,9 @@ TSymbol* TParseContext::redeclareBuiltinVariable(const TSourceLoc& loc, const TS
          identifier == "gl_BackSecondaryColor"                                                      ||
          identifier == "gl_BackSecondaryColor"                                                      ||
          identifier == "gl_SecondaryColor"                                                          ||
          identifier == "gl_SecondaryColor"                                                          ||
         (identifier == "gl_Color"               && language == EShLangFragment)                     ||
         (identifier == "gl_Color"               && language == EShLangFragment)                     ||
+#ifdef NV_EXTENSIONS
+         identifier == "gl_SampleMask"                                                              ||
+#endif
          identifier == "gl_TexCoord") {
          identifier == "gl_TexCoord") {
 
 
         // Find the existing symbol, if any.
         // Find the existing symbol, if any.
@@ -3381,8 +3388,16 @@ TSymbol* TParseContext::redeclareBuiltinVariable(const TSourceLoc& loc, const TS
                 if (! intermediate.setDepth(publicType.layoutDepth))
                 if (! intermediate.setDepth(publicType.layoutDepth))
                     error(loc, "all redeclarations must use the same depth layout on", "redeclaration", symbol->getName().c_str());
                     error(loc, "all redeclarations must use the same depth layout on", "redeclaration", symbol->getName().c_str());
             }
             }
-
         }
         }
+#ifdef NV_EXTENSIONS 
+        else if (identifier == "gl_SampleMask") {
+            if (!publicType.layoutOverrideCoverage) {
+                error(loc, "redeclaration only allowed for override_coverage layout", "redeclaration", symbol->getName().c_str());
+            }
+            intermediate.setLayoutOverrideCoverage();
+        }
+#endif
+
         // TODO: semantics quality: separate smooth from nothing declared, then use IsInterpolation for several tests above
         // TODO: semantics quality: separate smooth from nothing declared, then use IsInterpolation for several tests above
 
 
         return symbol;
         return symbol;
@@ -3448,6 +3463,20 @@ void TParseContext::redeclareBuiltinBlock(const TSourceLoc& loc, TTypeList& newT
     //  - remove unused members
     //  - remove unused members
     //  - ensure remaining qualifiers/types match
     //  - ensure remaining qualifiers/types match
     TType& type = block->getWritableType();
     TType& type = block->getWritableType();
+
+#ifdef NV_EXTENSIONS
+    // if gl_PerVertex is redeclared for the purpose of passing through "gl_Position"
+    // for passthrough purpose, the redclared block should have the same qualifers as
+    // the current one
+    if (currentBlockQualifier.layoutPassthrough)
+    {
+        type.getQualifier().layoutPassthrough = currentBlockQualifier.layoutPassthrough;
+        type.getQualifier().storage = currentBlockQualifier.storage;
+        type.getQualifier().layoutStream = currentBlockQualifier.layoutStream;
+        type.getQualifier().layoutXfbBuffer = currentBlockQualifier.layoutXfbBuffer;
+    }
+#endif
+
     TTypeList::iterator member = type.getWritableStruct()->begin();
     TTypeList::iterator member = type.getWritableStruct()->begin();
     size_t numOriginalMembersFound = 0;
     size_t numOriginalMembersFound = 0;
     while (member != type.getStruct()->end()) {
     while (member != type.getStruct()->end()) {
@@ -3917,6 +3946,14 @@ void TParseContext::setLayoutQualifier(const TSourceLoc& loc, TPublicType& publi
                 publicType.shaderQualifiers.geometry = ElgTriangleStrip;
                 publicType.shaderQualifiers.geometry = ElgTriangleStrip;
                 return;
                 return;
             }
             }
+#ifdef NV_EXTENSIONS
+            if (id == "passthrough") {
+               requireExtensions(loc, 1, &E_SPV_NV_geometry_shader_passthrough, "geometry shader passthrough");
+               publicType.qualifier.layoutPassthrough = true;
+               intermediate.setGeoPassthroughEXT();
+               return;
+            }
+#endif
         } else {
         } else {
             assert(language == EShLangTessEvaluation);
             assert(language == EShLangTessEvaluation);
 
 
@@ -4005,6 +4042,13 @@ void TParseContext::setLayoutQualifier(const TSourceLoc& loc, TPublicType& publi
                 error(loc, "unknown blend equation", "blend_support", "");
                 error(loc, "unknown blend equation", "blend_support", "");
             return;
             return;
         }
         }
+#ifdef NV_EXTENSIONS 
+        if (id == "override_coverage") {
+            requireExtensions(loc, 1, &E_GL_NV_sample_mask_override_coverage, "sample mask override coverage");
+            publicType.shaderQualifiers.layoutOverrideCoverage = true;
+            return;
+        }
+#endif
     }
     }
     error(loc, "unrecognized layout identifier, or qualifier requires assignment (e.g., binding = 4)", id.c_str(), "");
     error(loc, "unrecognized layout identifier, or qualifier requires assignment (e.g., binding = 4)", id.c_str(), "");
 }
 }
@@ -4310,6 +4354,11 @@ void TParseContext::mergeObjectLayoutQualifiers(TQualifier& dst, const TQualifie
 
 
         if (src.layoutPushConstant)
         if (src.layoutPushConstant)
             dst.layoutPushConstant = true;
             dst.layoutPushConstant = true;
+
+#ifdef NV_EXTENSIONS
+        if (src.layoutPassthrough)
+            dst.layoutPassthrough = true;
+#endif
     }
     }
 }
 }
 
 

+ 8 - 9
3rdparty/glslang/glslang/MachineIndependent/ParseHelper.h

@@ -49,8 +49,7 @@
 #include "SymbolTable.h"
 #include "SymbolTable.h"
 #include "localintermediate.h"
 #include "localintermediate.h"
 #include "Scan.h"
 #include "Scan.h"
-#include <functional>
-
+#include <cstdarg>
 #include <functional>
 #include <functional>
 
 
 namespace glslang {
 namespace glslang {
@@ -238,23 +237,23 @@ public:
     bool obeyPrecisionQualifiers() const { return precisionManager.respectingPrecisionQualifiers(); };
     bool obeyPrecisionQualifiers() const { return precisionManager.respectingPrecisionQualifiers(); };
     void setPrecisionDefaults();
     void setPrecisionDefaults();
 
 
-    void setLimits(const TBuiltInResource&);
-    bool parseShaderStrings(TPpContext&, TInputScanner& input, bool versionWillBeError = false);
+    void setLimits(const TBuiltInResource&) override;
+    bool parseShaderStrings(TPpContext&, TInputScanner& input, bool versionWillBeError = false) override;
     void parserError(const char* s);     // for bison's yyerror
     void parserError(const char* s);     // for bison's yyerror
 
 
     void reservedErrorCheck(const TSourceLoc&, const TString&);
     void reservedErrorCheck(const TSourceLoc&, const TString&);
-    void reservedPpErrorCheck(const TSourceLoc&, const char* name, const char* op);
-    bool lineContinuationCheck(const TSourceLoc&, bool endOfComment);
-    bool lineDirectiveShouldSetNextLine() const;
+    void reservedPpErrorCheck(const TSourceLoc&, const char* name, const char* op) override;
+    bool lineContinuationCheck(const TSourceLoc&, bool endOfComment) override;
+    bool lineDirectiveShouldSetNextLine() const override;
     bool builtInName(const TString&);
     bool builtInName(const TString&);
 
 
-    void handlePragma(const TSourceLoc&, const TVector<TString>&);
+    void handlePragma(const TSourceLoc&, const TVector<TString>&) override;
     TIntermTyped* handleVariable(const TSourceLoc&, TSymbol* symbol, const TString* string);
     TIntermTyped* handleVariable(const TSourceLoc&, TSymbol* symbol, const TString* string);
     TIntermTyped* handleBracketDereference(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
     TIntermTyped* handleBracketDereference(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
     void checkIndex(const TSourceLoc&, const TType&, int& index);
     void checkIndex(const TSourceLoc&, const TType&, int& index);
     void handleIndexLimits(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
     void handleIndexLimits(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
 
 
-    void makeEditable(TSymbol*&);
+    void makeEditable(TSymbol*&) override;
     bool isIoResizeArray(const TType&) const;
     bool isIoResizeArray(const TType&) const;
     void fixIoArraySize(const TSourceLoc&, TType&);
     void fixIoArraySize(const TSourceLoc&, TType&);
     void ioArrayCheck(const TSourceLoc&, const TType&, const TString& identifier);
     void ioArrayCheck(const TSourceLoc&, const TType&, const TString& identifier);

+ 10 - 9
3rdparty/glslang/glslang/MachineIndependent/Scan.cpp

@@ -638,13 +638,14 @@ int TScanContext::tokenize(TPpContext* pp, TParserToken& token)
     do {
     do {
         parserToken = &token;
         parserToken = &token;
         TPpToken ppToken;
         TPpToken ppToken;
-        tokenText = pp->tokenize(&ppToken);
-        if (tokenText == nullptr || tokenText[0] == 0)
+        int token = pp->tokenize(ppToken);
+        if (token == EndOfInput)
             return 0;
             return 0;
 
 
+        tokenText = ppToken.name;
         loc = ppToken.loc;
         loc = ppToken.loc;
         parserToken->sType.lex.loc = loc;
         parserToken->sType.lex.loc = loc;
-        switch (ppToken.token) {
+        switch (token) {
         case ';':  afterType = false;   return SEMICOLON;
         case ';':  afterType = false;   return SEMICOLON;
         case ',':  afterType = false;   return COMMA;
         case ',':  afterType = false;   return COMMA;
         case ':':                       return COLON;
         case ':':                       return COLON;
@@ -673,11 +674,11 @@ int TScanContext::tokenize(TPpContext* pp, TParserToken& token)
             parseContext.error(loc, "illegal use of escape character", "\\", "");
             parseContext.error(loc, "illegal use of escape character", "\\", "");
             break;
             break;
 
 
-        case PpAtomAdd:                return ADD_ASSIGN;
-        case PpAtomSub:                return SUB_ASSIGN;
-        case PpAtomMul:                return MUL_ASSIGN;
-        case PpAtomDiv:                return DIV_ASSIGN;
-        case PpAtomMod:                return MOD_ASSIGN;
+        case PPAtomAddAssign:          return ADD_ASSIGN;
+        case PPAtomSubAssign:          return SUB_ASSIGN;
+        case PPAtomMulAssign:          return MUL_ASSIGN;
+        case PPAtomDivAssign:          return DIV_ASSIGN;
+        case PPAtomModAssign:          return MOD_ASSIGN;
 
 
         case PpAtomRight:              return RIGHT_OP;
         case PpAtomRight:              return RIGHT_OP;
         case PpAtomLeft:               return LEFT_OP;
         case PpAtomLeft:               return LEFT_OP;
@@ -720,7 +721,7 @@ int TScanContext::tokenize(TPpContext* pp, TParserToken& token)
 
 
         default:
         default:
             char buf[2];
             char buf[2];
-            buf[0] = (char)ppToken.token;
+            buf[0] = token;
             buf[1] = 0;
             buf[1] = 0;
             parseContext.error(loc, "unexpected token", buf, "");
             parseContext.error(loc, "unexpected token", buf, "");
             break;
             break;

+ 13 - 9
3rdparty/glslang/glslang/MachineIndependent/ShaderLang.cpp

@@ -868,7 +868,7 @@ struct DoPreprocessing {
         // This is a list of tokens that do not require a space before or after.
         // This is a list of tokens that do not require a space before or after.
         static const std::string unNeededSpaceTokens = ";()[]";
         static const std::string unNeededSpaceTokens = ";()[]";
         static const std::string noSpaceBeforeTokens = ",";
         static const std::string noSpaceBeforeTokens = ",";
-        glslang::TPpToken token;
+        glslang::TPpToken ppToken;
 
 
         parseContext.setScanner(&input);
         parseContext.setScanner(&input);
         ppContext.setInput(input, versionWillBeError);
         ppContext.setInput(input, versionWillBeError);
@@ -931,29 +931,33 @@ struct DoPreprocessing {
         });
         });
 
 
         int lastToken = EndOfInput; // lastToken records the last token processed.
         int lastToken = EndOfInput; // lastToken records the last token processed.
-        while (const char* tok = ppContext.tokenize(&token)) {
+        do {
+            int token = ppContext.tokenize(ppToken);
+            if (token == EndOfInput)
+                break;
+
             bool isNewString = lineSync.syncToMostRecentString();
             bool isNewString = lineSync.syncToMostRecentString();
-            bool isNewLine = lineSync.syncToLine(token.loc.line);
+            bool isNewLine = lineSync.syncToLine(ppToken.loc.line);
 
 
             if (isNewLine) {
             if (isNewLine) {
                 // Don't emit whitespace onto empty lines.
                 // Don't emit whitespace onto empty lines.
                 // Copy any whitespace characters at the start of a line
                 // Copy any whitespace characters at the start of a line
                 // from the input to the output.
                 // from the input to the output.
-                outputStream << std::string(token.loc.column - 1, ' ');
+                outputStream << std::string(ppToken.loc.column - 1, ' ');
             }
             }
 
 
             // Output a space in between tokens, but not at the start of a line,
             // Output a space in between tokens, but not at the start of a line,
             // and also not around special tokens. This helps with readability
             // and also not around special tokens. This helps with readability
             // and consistency.
             // and consistency.
             if (!isNewString && !isNewLine && lastToken != EndOfInput &&
             if (!isNewString && !isNewLine && lastToken != EndOfInput &&
-                (unNeededSpaceTokens.find((char)token.token) == std::string::npos) &&
+                (unNeededSpaceTokens.find((char)token) == std::string::npos) &&
                 (unNeededSpaceTokens.find((char)lastToken) == std::string::npos) &&
                 (unNeededSpaceTokens.find((char)lastToken) == std::string::npos) &&
-                (noSpaceBeforeTokens.find((char)token.token) == std::string::npos)) {
+                (noSpaceBeforeTokens.find((char)token) == std::string::npos)) {
                 outputStream << " ";
                 outputStream << " ";
             }
             }
-            lastToken = token.token;
-            outputStream << tok;
-        }
+            lastToken = token;
+            outputStream << ppToken.name;
+        } while (true);
         outputStream << std::endl;
         outputStream << std::endl;
         *outputString = outputStream.str();
         *outputString = outputStream.str();
 
 

+ 10 - 0
3rdparty/glslang/glslang/MachineIndependent/Versions.cpp

@@ -195,6 +195,11 @@ void TParseVersions::initializeExtensionBehavior()
     extensionBehavior[E_GL_AMD_gpu_shader_half_float]                = EBhDisable;
     extensionBehavior[E_GL_AMD_gpu_shader_half_float]                = EBhDisable;
 #endif
 #endif
 
 
+#ifdef NV_EXTENSIONS 
+    extensionBehavior[E_GL_NV_sample_mask_override_coverage]         = EBhDisable;
+    extensionBehavior[E_SPV_NV_geometry_shader_passthrough]          = EBhDisable;
+#endif
+
     // AEP
     // AEP
     extensionBehavior[E_GL_ANDROID_extension_pack_es31a]             = EBhDisable;
     extensionBehavior[E_GL_ANDROID_extension_pack_es31a]             = EBhDisable;
     extensionBehavior[E_GL_KHR_blend_equation_advanced]              = EBhDisable;
     extensionBehavior[E_GL_KHR_blend_equation_advanced]              = EBhDisable;
@@ -302,6 +307,11 @@ void TParseVersions::getPreamble(std::string& preamble)
             "#define GL_AMD_gcn_shader 1\n"
             "#define GL_AMD_gcn_shader 1\n"
             "#define GL_AMD_gpu_shader_half_float 1\n"
             "#define GL_AMD_gpu_shader_half_float 1\n"
 #endif
 #endif
+
+#ifdef NV_EXTENSIONS 
+            "#define GL_NV_sample_mask_override_coverage 1\n"
+            "#define GL_NV_geometry_shader_passthrough 1\n"
+#endif
             ;
             ;
     }
     }
 
 

+ 4 - 0
3rdparty/glslang/glslang/MachineIndependent/Versions.h

@@ -142,6 +142,10 @@ const char* const E_GL_AMD_shader_explicit_vertex_parameter     = "GL_AMD_shader
 const char* const E_GL_AMD_gcn_shader                           = "GL_AMD_gcn_shader";
 const char* const E_GL_AMD_gcn_shader                           = "GL_AMD_gcn_shader";
 const char* const E_GL_AMD_gpu_shader_half_float                = "GL_AMD_gpu_shader_half_float";
 const char* const E_GL_AMD_gpu_shader_half_float                = "GL_AMD_gpu_shader_half_float";
 #endif
 #endif
+#ifdef NV_EXTENSIONS
+const char* const E_GL_NV_sample_mask_override_coverage = "GL_NV_sample_mask_override_coverage";
+const char* const E_SPV_NV_geometry_shader_passthrough = "GL_NV_geometry_shader_passthrough";
+#endif
 
 
 // AEP
 // AEP
 const char* const E_GL_ANDROID_extension_pack_es31a             = "GL_ANDROID_extension_pack_es31a";
 const char* const E_GL_ANDROID_extension_pack_es31a             = "GL_ANDROID_extension_pack_es31a";

+ 10 - 2
3rdparty/glslang/glslang/MachineIndependent/linkValidate.cpp

@@ -469,9 +469,17 @@ void TIntermediate::finalCheck(TInfoSink& infoSink, bool keepUncalled)
     case EShLangGeometry:
     case EShLangGeometry:
         if (inputPrimitive == ElgNone)
         if (inputPrimitive == ElgNone)
             error(infoSink, "At least one shader must specify an input layout primitive");
             error(infoSink, "At least one shader must specify an input layout primitive");
-        if (outputPrimitive == ElgNone)
+        if (outputPrimitive == ElgNone
+#ifdef NV_EXTENSIONS
+            && !getGeoPassthroughEXT()
+#endif
+            )
             error(infoSink, "At least one shader must specify an output layout primitive");
             error(infoSink, "At least one shader must specify an output layout primitive");
-        if (vertices == TQualifier::layoutNotSet)
+        if (vertices == TQualifier::layoutNotSet
+#ifdef NV_EXTENSIONS
+            && !getGeoPassthroughEXT()
+#endif
+           )
             error(infoSink, "At least one shader must specify a layout(max_vertices = value)");
             error(infoSink, "At least one shader must specify a layout(max_vertices = value)");
         break;
         break;
     case EShLangFragment:
     case EShLangFragment:

+ 16 - 0
3rdparty/glslang/glslang/MachineIndependent/localintermediate.h

@@ -151,6 +151,10 @@ public:
         shiftUboBinding(0),
         shiftUboBinding(0),
         autoMapBindings(false),
         autoMapBindings(false),
         flattenUniformArrays(false),
         flattenUniformArrays(false),
+#ifdef NV_EXTENSIONS 
+        layoutOverrideCoverage(false),
+        geoPassthroughEXT(false),
+#endif
         useUnknownFormat(false)
         useUnknownFormat(false)
     {
     {
         localSize[0] = 1;
         localSize[0] = 1;
@@ -387,6 +391,13 @@ public:
     static int getBaseAlignment(const TType&, int& size, int& stride, bool std140, bool rowMajor);
     static int getBaseAlignment(const TType&, int& size, int& stride, bool std140, bool rowMajor);
     bool promote(TIntermOperator*);
     bool promote(TIntermOperator*);
 
 
+#ifdef NV_EXTENSIONS 
+    void setLayoutOverrideCoverage() { layoutOverrideCoverage = true; }
+    bool getLayoutOverrideCoverage() const { return layoutOverrideCoverage; }
+    void setGeoPassthroughEXT() { geoPassthroughEXT = true; }
+    bool getGeoPassthroughEXT() const { return geoPassthroughEXT; }
+#endif
+
 protected:
 protected:
     TIntermSymbol* addSymbol(int Id, const TString&, const TType&, const TConstUnionArray&, TIntermTyped* subtree, const TSourceLoc&);
     TIntermSymbol* addSymbol(int Id, const TString&, const TType&, const TConstUnionArray&, TIntermTyped* subtree, const TSourceLoc&);
     void error(TInfoSink& infoSink, const char*);
     void error(TInfoSink& infoSink, const char*);
@@ -447,6 +458,11 @@ protected:
     bool xfbMode;
     bool xfbMode;
     bool multiStream;
     bool multiStream;
 
 
+#ifdef NV_EXTENSIONS 
+    bool layoutOverrideCoverage;
+    bool geoPassthroughEXT;
+#endif
+
     typedef std::list<TCall> TGraph;
     typedef std::list<TCall> TGraph;
     TGraph callGraph;
     TGraph callGraph;
 
 

+ 177 - 127
3rdparty/glslang/glslang/MachineIndependent/preprocessor/Pp.cpp

@@ -75,9 +75,6 @@ NVIDIA SOFTWARE, HOWEVER CAUSED AND WHETHER UNDER THEORY OF CONTRACT,
 TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 \****************************************************************************/
 \****************************************************************************/
-//
-// cpp.c
-//
 
 
 #define _CRT_SECURE_NO_WARNINGS
 #define _CRT_SECURE_NO_WARNINGS
 
 
@@ -91,20 +88,12 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
 
 namespace glslang {
 namespace glslang {
 
 
-int TPpContext::InitCPP()
-{
-    pool = mem_CreatePool(0, 0);
-
-    return 1;
-}
-
 // Handle #define
 // Handle #define
 int TPpContext::CPPdefine(TPpToken* ppToken)
 int TPpContext::CPPdefine(TPpToken* ppToken)
 {
 {
     MacroSymbol mac;
     MacroSymbol mac;
-    Symbol *symb;
 
 
-    // get macro name
+    // get the macro name
     int token = scanToken(ppToken);
     int token = scanToken(ppToken);
     if (token != PpAtomIdentifier) {
     if (token != PpAtomIdentifier) {
         parseContext.ppError(ppToken->loc, "must be followed by macro name", "#define", "");
         parseContext.ppError(ppToken->loc, "must be followed by macro name", "#define", "");
@@ -115,38 +104,36 @@ int TPpContext::CPPdefine(TPpToken* ppToken)
         parseContext.reservedPpErrorCheck(ppToken->loc, ppToken->name, "#define");
         parseContext.reservedPpErrorCheck(ppToken->loc, ppToken->name, "#define");
     }
     }
 
 
-    // save the original atom
-    const int defAtom = ppToken->atom;
+    // save the macro name
+    const int defAtom = atomStrings.getAddAtom(ppToken->name);
 
 
     // gather parameters to the macro, between (...)
     // gather parameters to the macro, between (...)
     token = scanToken(ppToken);
     token = scanToken(ppToken);
     if (token == '(' && ! ppToken->space) {
     if (token == '(' && ! ppToken->space) {
-        int argc = 0;
-        int args[maxMacroArgs];
+        mac.emptyArgs = 1;
         do {
         do {
             token = scanToken(ppToken);
             token = scanToken(ppToken);
-            if (argc == 0 && token == ')') 
+            if (mac.args.size() == 0 && token == ')') 
                 break;
                 break;
             if (token != PpAtomIdentifier) {
             if (token != PpAtomIdentifier) {
                 parseContext.ppError(ppToken->loc, "bad argument", "#define", "");
                 parseContext.ppError(ppToken->loc, "bad argument", "#define", "");
 
 
                 return token;
                 return token;
             }
             }
+            mac.emptyArgs = 0;
+            const int argAtom = atomStrings.getAddAtom(ppToken->name);
+
             // check for duplication of parameter name
             // check for duplication of parameter name
             bool duplicate = false;
             bool duplicate = false;
-            for (int a = 0; a < argc; ++a) {
-                if (args[a] == ppToken->atom) {
+            for (size_t a = 0; a < mac.args.size(); ++a) {
+                if (mac.args[a] == argAtom) {
                     parseContext.ppError(ppToken->loc, "duplicate macro parameter", "#define", "");
                     parseContext.ppError(ppToken->loc, "duplicate macro parameter", "#define", "");
                     duplicate = true;
                     duplicate = true;
                     break;
                     break;
                 }
                 }
             }
             }
-            if (! duplicate) {
-                if (argc < maxMacroArgs)
-                    args[argc++] = ppToken->atom;
-                else
-                    parseContext.ppError(ppToken->loc, "too many macro parameters", "#define", "");
-            }
+            if (! duplicate)
+                mac.args.push_back(argAtom);
             token = scanToken(ppToken);
             token = scanToken(ppToken);
         } while (token == ',');
         } while (token == ',');
         if (token != ')') {
         if (token != ')') {
@@ -154,15 +141,12 @@ int TPpContext::CPPdefine(TPpToken* ppToken)
 
 
             return token;
             return token;
         }
         }
-        mac.argc = argc;
-        mac.args = (int*)mem_Alloc(pool, argc * sizeof(int));
-        memcpy(mac.args, args, argc * sizeof(int));
+
         token = scanToken(ppToken);
         token = scanToken(ppToken);
     }
     }
 
 
     // record the definition of the macro
     // record the definition of the macro
     TSourceLoc defineLoc = ppToken->loc; // because ppToken is going to go to the next line before we report errors
     TSourceLoc defineLoc = ppToken->loc; // because ppToken is going to go to the next line before we report errors
-    mac.body = new TokenStream;
     while (token != '\n' && token != EndOfInput) {
     while (token != '\n' && token != EndOfInput) {
         RecordToken(mac.body, token, ppToken);
         RecordToken(mac.body, token, ppToken);
         token = scanToken(ppToken);
         token = scanToken(ppToken);
@@ -171,40 +155,36 @@ int TPpContext::CPPdefine(TPpToken* ppToken)
     }
     }
 
 
     // check for duplicate definition
     // check for duplicate definition
-    symb = LookUpSymbol(defAtom);
-    if (symb) {
-        if (! symb->mac.undef) {
+    MacroSymbol* existing = lookupMacroDef(defAtom);
+    if (existing != nullptr) {
+        if (! existing->undef) {
             // Already defined -- need to make sure they are identical:
             // Already defined -- need to make sure they are identical:
             // "Two replacement lists are identical if and only if the preprocessing tokens in both have the same number,
             // "Two replacement lists are identical if and only if the preprocessing tokens in both have the same number,
             // ordering, spelling, and white-space separation, where all white-space separations are considered identical."
             // ordering, spelling, and white-space separation, where all white-space separations are considered identical."
-            if (symb->mac.argc != mac.argc)
-                parseContext.ppError(defineLoc, "Macro redefined; different number of arguments:", "#define", GetAtomString(defAtom));
+            if (existing->args.size() != mac.args.size() || existing->emptyArgs != mac.emptyArgs)
+                parseContext.ppError(defineLoc, "Macro redefined; different number of arguments:", "#define", atomStrings.getString(defAtom));
             else {
             else {
-                for (int argc = 0; argc < mac.argc; argc++) {
-                    if (symb->mac.args[argc] != mac.args[argc])
-                        parseContext.ppError(defineLoc, "Macro redefined; different argument names:", "#define", GetAtomString(defAtom));
-                }
-                RewindTokenStream(symb->mac.body);
+                if (existing->args != mac.args)
+                    parseContext.ppError(defineLoc, "Macro redefined; different argument names:", "#define", atomStrings.getString(defAtom));
+                RewindTokenStream(existing->body);
                 RewindTokenStream(mac.body);
                 RewindTokenStream(mac.body);
                 int newToken;
                 int newToken;
                 do {
                 do {
                     int oldToken;
                     int oldToken;
                     TPpToken oldPpToken;
                     TPpToken oldPpToken;
                     TPpToken newPpToken;
                     TPpToken newPpToken;
-                    oldToken = ReadToken(symb->mac.body, &oldPpToken);
+                    oldToken = ReadToken(existing->body, &oldPpToken);
                     newToken = ReadToken(mac.body, &newPpToken);
                     newToken = ReadToken(mac.body, &newPpToken);
                     if (oldToken != newToken || oldPpToken != newPpToken) {
                     if (oldToken != newToken || oldPpToken != newPpToken) {
-                        parseContext.ppError(defineLoc, "Macro redefined; different substitutions:", "#define", GetAtomString(defAtom));
+                        parseContext.ppError(defineLoc, "Macro redefined; different substitutions:", "#define", atomStrings.getString(defAtom));
                         break; 
                         break; 
                     }
                     }
                 } while (newToken > 0);
                 } while (newToken > 0);
             }
             }
         }
         }
+        *existing = mac;
     } else
     } else
-        symb = AddSymbol(defAtom);
-
-    delete symb->mac.body;
-    symb->mac = mac;
+        addMacroDef(defAtom, mac);
 
 
     return '\n';
     return '\n';
 }
 }
@@ -213,7 +193,6 @@ int TPpContext::CPPdefine(TPpToken* ppToken)
 int TPpContext::CPPundef(TPpToken* ppToken)
 int TPpContext::CPPundef(TPpToken* ppToken)
 {
 {
     int token = scanToken(ppToken);
     int token = scanToken(ppToken);
-    Symbol *symb;
     if (token != PpAtomIdentifier) {
     if (token != PpAtomIdentifier) {
         parseContext.ppError(ppToken->loc, "must be followed by macro name", "#undef", "");
         parseContext.ppError(ppToken->loc, "must be followed by macro name", "#undef", "");
 
 
@@ -222,10 +201,9 @@ int TPpContext::CPPundef(TPpToken* ppToken)
 
 
     parseContext.reservedPpErrorCheck(ppToken->loc, ppToken->name, "#undef");
     parseContext.reservedPpErrorCheck(ppToken->loc, ppToken->name, "#undef");
 
 
-    symb = LookUpSymbol(ppToken->atom);
-    if (symb) {
-        symb->mac.undef = 1;
-    }
+    MacroSymbol* macro = lookupMacroDef(atomStrings.getAtom(ppToken->name));
+    if (macro != nullptr)
+        macro->undef = 1;
     token = scanToken(ppToken);
     token = scanToken(ppToken);
     if (token != '\n')
     if (token != '\n')
         parseContext.ppError(ppToken->loc, "can only be followed by a single macro name", "#undef", "");
         parseContext.ppError(ppToken->loc, "can only be followed by a single macro name", "#undef", "");
@@ -240,7 +218,6 @@ int TPpContext::CPPundef(TPpToken* ppToken)
 */
 */
 int TPpContext::CPPelse(int matchelse, TPpToken* ppToken)
 int TPpContext::CPPelse(int matchelse, TPpToken* ppToken)
 {
 {
-    int atom;
     int depth = 0;
     int depth = 0;
     int token = scanToken(ppToken);
     int token = scanToken(ppToken);
 
 
@@ -259,13 +236,13 @@ int TPpContext::CPPelse(int matchelse, TPpToken* ppToken)
         if ((token = scanToken(ppToken)) != PpAtomIdentifier)
         if ((token = scanToken(ppToken)) != PpAtomIdentifier)
             continue;
             continue;
 
 
-        atom = ppToken->atom;
-        if (atom == PpAtomIf || atom == PpAtomIfdef || atom == PpAtomIfndef) {
+        int nextAtom = atomStrings.getAtom(ppToken->name);
+        if (nextAtom == PpAtomIf || nextAtom == PpAtomIfdef || nextAtom == PpAtomIfndef) {
             depth++; 
             depth++; 
             ifdepth++; 
             ifdepth++; 
             elsetracker++;
             elsetracker++;
-        } else if (atom == PpAtomEndif) {
-            token = extraTokenCheck(atom, ppToken, scanToken(ppToken));
+        } else if (nextAtom == PpAtomEndif) {
+            token = extraTokenCheck(nextAtom, ppToken, scanToken(ppToken));
             elseSeen[elsetracker] = false;
             elseSeen[elsetracker] = false;
             --elsetracker;
             --elsetracker;
             if (depth == 0) {
             if (depth == 0) {
@@ -277,12 +254,12 @@ int TPpContext::CPPelse(int matchelse, TPpToken* ppToken)
             --depth;
             --depth;
             --ifdepth;
             --ifdepth;
         } else if (matchelse && depth == 0) {
         } else if (matchelse && depth == 0) {
-            if (atom == PpAtomElse) {
+            if (nextAtom == PpAtomElse) {
                 elseSeen[elsetracker] = true;
                 elseSeen[elsetracker] = true;
-                token = extraTokenCheck(atom, ppToken, scanToken(ppToken));
+                token = extraTokenCheck(nextAtom, ppToken, scanToken(ppToken));
                 // found the #else we are looking for
                 // found the #else we are looking for
                 break;
                 break;
-            } else if (atom == PpAtomElif) {
+            } else if (nextAtom == PpAtomElif) {
                 if (elseSeen[elsetracker])
                 if (elseSeen[elsetracker])
                     parseContext.ppError(ppToken->loc, "#elif after #else", "#elif", "");
                     parseContext.ppError(ppToken->loc, "#elif after #else", "#elif", "");
                 /* we decrement ifdepth here, because CPPif will increment
                 /* we decrement ifdepth here, because CPPif will increment
@@ -295,13 +272,13 @@ int TPpContext::CPPelse(int matchelse, TPpToken* ppToken)
 
 
                 return CPPif(ppToken);
                 return CPPif(ppToken);
             }
             }
-        } else if (atom == PpAtomElse) {
+        } else if (nextAtom == PpAtomElse) {
             if (elseSeen[elsetracker])
             if (elseSeen[elsetracker])
                 parseContext.ppError(ppToken->loc, "#else after #else", "#else", "");
                 parseContext.ppError(ppToken->loc, "#else after #else", "#else", "");
             else
             else
                 elseSeen[elsetracker] = true;
                 elseSeen[elsetracker] = true;
-            token = extraTokenCheck(atom, ppToken, scanToken(ppToken));
-        } else if (atom == PpAtomElif) {
+            token = extraTokenCheck(nextAtom, ppToken, scanToken(ppToken));
+        } else if (nextAtom == PpAtomElif) {
             if (elseSeen[elsetracker])
             if (elseSeen[elsetracker])
                 parseContext.ppError(ppToken->loc, "#elif after #else", "#elif", "");
                 parseContext.ppError(ppToken->loc, "#elif after #else", "#elif", "");
         }
         }
@@ -311,21 +288,21 @@ int TPpContext::CPPelse(int matchelse, TPpToken* ppToken)
 }
 }
 
 
 // Call when there should be no more tokens left on a line.
 // Call when there should be no more tokens left on a line.
-int TPpContext::extraTokenCheck(int atom, TPpToken* ppToken, int token)
+int TPpContext::extraTokenCheck(int contextAtom, TPpToken* ppToken, int token)
 {
 {
     if (token != '\n' && token != EndOfInput) {
     if (token != '\n' && token != EndOfInput) {
         static const char* message = "unexpected tokens following directive";
         static const char* message = "unexpected tokens following directive";
 
 
         const char* label;
         const char* label;
-        if (atom == PpAtomElse)
+        if (contextAtom == PpAtomElse)
             label = "#else";
             label = "#else";
-        else if (atom == PpAtomElif)
+        else if (contextAtom == PpAtomElif)
             label = "#elif";
             label = "#elif";
-        else if (atom == PpAtomEndif)
+        else if (contextAtom == PpAtomEndif)
             label = "#endif";
             label = "#endif";
-        else if (atom == PpAtomIf)
+        else if (contextAtom == PpAtomIf)
             label = "#if";
             label = "#if";
-        else if (atom == PpAtomLine)
+        else if (contextAtom == PpAtomLine)
             label = "#line";
             label = "#line";
         else
         else
             label = "";
             label = "";
@@ -413,7 +390,7 @@ int TPpContext::eval(int token, int precedence, bool shortCircuit, int& res, boo
 {
 {
     TSourceLoc loc = ppToken->loc;  // because we sometimes read the newline before reporting the error
     TSourceLoc loc = ppToken->loc;  // because we sometimes read the newline before reporting the error
     if (token == PpAtomIdentifier) {
     if (token == PpAtomIdentifier) {
-        if (ppToken->atom == PpAtomDefined) {
+        if (strcmp("defined", ppToken->name) == 0) {
             bool needclose = 0;
             bool needclose = 0;
             token = scanToken(ppToken);
             token = scanToken(ppToken);
             if (token == '(') {
             if (token == '(') {
@@ -427,8 +404,9 @@ int TPpContext::eval(int token, int precedence, bool shortCircuit, int& res, boo
 
 
                 return token;
                 return token;
             }
             }
-            Symbol* s = LookUpSymbol(ppToken->atom);
-            res = s ? ! s->mac.undef : 0;
+
+            MacroSymbol* macro = lookupMacroDef(atomStrings.getAtom(ppToken->name));
+            res = macro != nullptr ? !macro->undef : 0;
             token = scanToken(ppToken);
             token = scanToken(ppToken);
             if (needclose) {
             if (needclose) {
                 if (token != ')') {
                 if (token != ')') {
@@ -520,8 +498,8 @@ int TPpContext::eval(int token, int precedence, bool shortCircuit, int& res, boo
 // Expand macros, skipping empty expansions, to get to the first real token in those expansions.
 // Expand macros, skipping empty expansions, to get to the first real token in those expansions.
 int TPpContext::evalToToken(int token, bool shortCircuit, int& res, bool& err, TPpToken* ppToken)
 int TPpContext::evalToToken(int token, bool shortCircuit, int& res, bool& err, TPpToken* ppToken)
 {
 {
-    while (token == PpAtomIdentifier && ppToken->atom != PpAtomDefined) {
-        int macroReturn = MacroExpand(ppToken->atom, ppToken, true, false);
+    while (token == PpAtomIdentifier && strcmp("defined", ppToken->name) != 0) {
+        int macroReturn = MacroExpand(ppToken, true, false);
         if (macroReturn == 0) {
         if (macroReturn == 0) {
             parseContext.ppError(ppToken->loc, "can't evaluate expression", "preprocessor evaluation", "");
             parseContext.ppError(ppToken->loc, "can't evaluate expression", "preprocessor evaluation", "");
             err = true;
             err = true;
@@ -568,7 +546,6 @@ int TPpContext::CPPif(TPpToken* ppToken)
 int TPpContext::CPPifdef(int defined, TPpToken* ppToken)
 int TPpContext::CPPifdef(int defined, TPpToken* ppToken)
 {
 {
     int token = scanToken(ppToken);
     int token = scanToken(ppToken);
-    int name = ppToken->atom;
     if (++ifdepth > maxIfNesting) {
     if (++ifdepth > maxIfNesting) {
         parseContext.ppError(ppToken->loc, "maximum nesting depth exceeded", "#ifdef", "");
         parseContext.ppError(ppToken->loc, "maximum nesting depth exceeded", "#ifdef", "");
         return 0;
         return 0;
@@ -580,14 +557,14 @@ int TPpContext::CPPifdef(int defined, TPpToken* ppToken)
         else 
         else 
             parseContext.ppError(ppToken->loc, "must be followed by macro name", "#ifndef", "");
             parseContext.ppError(ppToken->loc, "must be followed by macro name", "#ifndef", "");
     } else {
     } else {
-        Symbol *s = LookUpSymbol(name);
+        MacroSymbol* macro = lookupMacroDef(atomStrings.getAtom(ppToken->name));
         token = scanToken(ppToken);
         token = scanToken(ppToken);
         if (token != '\n') {
         if (token != '\n') {
             parseContext.ppError(ppToken->loc, "unexpected tokens following #ifdef directive - expected a newline", "#ifdef", "");
             parseContext.ppError(ppToken->loc, "unexpected tokens following #ifdef directive - expected a newline", "#ifdef", "");
             while (token != '\n' && token != EndOfInput)
             while (token != '\n' && token != EndOfInput)
                 token = scanToken(ppToken);
                 token = scanToken(ppToken);
         }
         }
-        if (((s && !s->mac.undef) ? 1 : 0) != defined)
+        if (((macro != nullptr && !macro->undef) ? 1 : 0) != defined)
             token = CPPelse(1, ppToken);
             token = CPPelse(1, ppToken);
     }
     }
 
 
@@ -674,7 +651,7 @@ int TPpContext::CPPline(TPpToken* ppToken)
                 // We need to save a copy of the string instead of pointing
                 // We need to save a copy of the string instead of pointing
                 // to the name field of the token since the name field
                 // to the name field of the token since the name field
                 // will likely be overwritten by the next token scan.
                 // will likely be overwritten by the next token scan.
-                sourceName = GetAtomString(LookUpAddString(ppToken->name));
+                sourceName = atomStrings.getString(atomStrings.getAddAtom(ppToken->name));
                 parseContext.setCurrentSourceName(sourceName);
                 parseContext.setCurrentSourceName(sourceName);
                 hasFile = true;
                 hasFile = true;
                 token = scanToken(ppToken);
                 token = scanToken(ppToken);
@@ -713,7 +690,7 @@ int TPpContext::CPPerror(TPpToken* ppToken)
         } else if (token == PpAtomIdentifier || token == PpAtomConstString) {
         } else if (token == PpAtomIdentifier || token == PpAtomConstString) {
             message.append(ppToken->name);
             message.append(ppToken->name);
         } else {
         } else {
-            message.append(GetAtomString(token));
+            message.append(atomStrings.getString(token));
         }
         }
         message.append(" ");
         message.append(" ");
         token = scanToken(ppToken);
         token = scanToken(ppToken);
@@ -790,9 +767,10 @@ int TPpContext::CPPversion(TPpToken* ppToken)
         parseContext.notifyVersion(line, versionNumber, nullptr);
         parseContext.notifyVersion(line, versionNumber, nullptr);
         return token;
         return token;
     } else {
     } else {
-        if (ppToken->atom != PpAtomCore &&
-            ppToken->atom != PpAtomCompatibility &&
-            ppToken->atom != PpAtomEs)
+        int profileAtom = atomStrings.getAtom(ppToken->name);
+        if (profileAtom != PpAtomCore &&
+            profileAtom != PpAtomCompatibility &&
+            profileAtom != PpAtomEs)
             parseContext.ppError(ppToken->loc, "bad profile name; use es, core, or compatibility", "#version", "");
             parseContext.ppError(ppToken->loc, "bad profile name; use es, core, or compatibility", "#version", "");
         parseContext.notifyVersion(line, versionNumber, ppToken->name);
         parseContext.notifyVersion(line, versionNumber, ppToken->name);
         token = scanToken(ppToken);
         token = scanToken(ppToken);
@@ -853,7 +831,7 @@ int TPpContext::readCPPline(TPpToken* ppToken)
     int token = scanToken(ppToken);
     int token = scanToken(ppToken);
 
 
     if (token == PpAtomIdentifier) {
     if (token == PpAtomIdentifier) {
-        switch (ppToken->atom) {
+        switch (atomStrings.getAtom(ppToken->name)) {
         case PpAtomDefine:
         case PpAtomDefine:
             token = CPPdefine(ppToken);
             token = CPPdefine(ppToken);
             break;
             break;
@@ -933,36 +911,42 @@ int TPpContext::readCPPline(TPpToken* ppToken)
     return token;
     return token;
 }
 }
 
 
-TPpContext::TokenStream* TPpContext::PrescanMacroArg(TokenStream* a, TPpToken* ppToken, bool newLineOkay)
+// Macro-expand a macro argument 'arg' to create 'expandedArg'.
+// Does not replace 'arg'.
+// Returns nullptr if no expanded argument is created.
+TPpContext::TokenStream* TPpContext::PrescanMacroArg(TokenStream& arg, TPpToken* ppToken, bool newLineOkay)
 {
 {
+    // pre-check, to see if anything in the argument needs to be expanded,
+    // to see if we can kick out early
     int token;
     int token;
-    TokenStream *n;
-    RewindTokenStream(a);
+    RewindTokenStream(arg);
     do {
     do {
-        token = ReadToken(a, ppToken);
-        if (token == PpAtomIdentifier && LookUpSymbol(ppToken->atom))
+        token = ReadToken(arg, ppToken);
+        if (token == PpAtomIdentifier && lookupMacroDef(atomStrings.getAtom(ppToken->name)) != nullptr)
             break;
             break;
     } while (token != EndOfInput);
     } while (token != EndOfInput);
 
 
+    // if nothing needs to be expanded, kick out early
     if (token == EndOfInput)
     if (token == EndOfInput)
-        return a;
+        return nullptr;
 
 
-    n = new TokenStream;
+    // expand the argument
+    TokenStream* expandedArg = new TokenStream;
     pushInput(new tMarkerInput(this));
     pushInput(new tMarkerInput(this));
-    pushTokenStreamInput(a);
+    pushTokenStreamInput(arg);
     while ((token = scanToken(ppToken)) != tMarkerInput::marker) {
     while ((token = scanToken(ppToken)) != tMarkerInput::marker) {
-        if (token == PpAtomIdentifier && MacroExpand(ppToken->atom, ppToken, false, newLineOkay) != 0)
+        if (token == PpAtomIdentifier && MacroExpand(ppToken, false, newLineOkay) != 0)
             continue;
             continue;
-        RecordToken(n, token, ppToken);
+        RecordToken(*expandedArg, token, ppToken);
     }
     }
     popInput();
     popInput();
-    delete a;
 
 
-    return n;
+    return expandedArg;
 }
 }
 
 
 // 
 // 
-// Return the next token for a macro expansion, handling macro args.
+// Return the next token for a macro expansion, handling macro arguments,
+// whose semantics are dependent on being adjacent to ##.
 //
 //
 int TPpContext::tMacroInput::scan(TPpToken* ppToken)
 int TPpContext::tMacroInput::scan(TPpToken* ppToken)
 {
 {
@@ -971,14 +955,50 @@ int TPpContext::tMacroInput::scan(TPpToken* ppToken)
         token = pp->ReadToken(mac->body, ppToken);
         token = pp->ReadToken(mac->body, ppToken);
     } while (token == ' ');  // handle white space in macro
     } while (token == ' ');  // handle white space in macro
 
 
+    // Hash operators basically turn off a round of macro substitution
+    // (the round done on the argument before the round done on the RHS of the
+    // macro definition):
+    //
+    // "A parameter in the replacement list, unless preceded by a # or ##
+    // preprocessing token or followed by a ## preprocessing token (see below),
+    // is replaced by the corresponding argument after all macros contained
+    // therein have been expanded."
+    //
+    // "If, in the replacement list, a parameter is immediately preceded or
+    // followed by a ## preprocessing token, the parameter is replaced by the
+    // corresponding argument's preprocessing token sequence."
+
+    bool pasting = false;
+    if (postpaste) {
+        // don't expand next token
+        pasting = true;
+        postpaste = false;
+    }
+
+    if (prepaste) {
+        // already know we should be on a ##, verify
+        assert(token == PpAtomPaste);
+        prepaste = false;
+        postpaste = true;
+    }
+
+    // see if are preceding a ##
+    if (peekMacPasting()) {
+        prepaste = true;
+        pasting = true;
+    }
+
     // TODO: preprocessor:  properly handle whitespace (or lack of it) between tokens when expanding
     // TODO: preprocessor:  properly handle whitespace (or lack of it) between tokens when expanding
     if (token == PpAtomIdentifier) {
     if (token == PpAtomIdentifier) {
         int i;
         int i;
-        for (i = mac->argc - 1; i >= 0; i--)
-            if (mac->args[i] == ppToken->atom) 
+        for (i = mac->args.size() - 1; i >= 0; i--)
+            if (strcmp(pp->atomStrings.getString(mac->args[i]), ppToken->name) == 0)
                 break;
                 break;
         if (i >= 0) {
         if (i >= 0) {
-            pp->pushTokenStreamInput(args[i]);
+            TokenStream* arg = expandedArgs[i];
+            if (arg == nullptr || pasting)
+                arg = args[i];
+            pp->pushTokenStreamInput(*arg, prepaste);
 
 
             return pp->scanToken(ppToken);
             return pp->scanToken(ppToken);
         }
         }
@@ -990,6 +1010,31 @@ int TPpContext::tMacroInput::scan(TPpToken* ppToken)
     return token;
     return token;
 }
 }
 
 
+// See if the next non-white-space token in the macro is ##
+bool TPpContext::tMacroInput::peekMacPasting()
+{
+    // don't return early, have to restore this
+    size_t savePos = mac->body.current;
+
+    // skip white-space
+    int ltoken;
+    do {
+        ltoken = pp->lReadByte(mac->body);
+    } while (ltoken == ' ');
+
+    // check for ##
+    bool pasting = false;
+    if (ltoken == '#') {
+        ltoken = pp->lReadByte(mac->body);
+        if (ltoken == '#')
+            pasting = true;
+    }
+
+    mac->body.current = savePos;
+
+    return pasting;
+}
+
 // return a textual zero, for scanning a macro that was never defined
 // return a textual zero, for scanning a macro that was never defined
 int TPpContext::tZeroInput::scan(TPpToken* ppToken)
 int TPpContext::tZeroInput::scan(TPpToken* ppToken)
 {
 {
@@ -1005,17 +1050,18 @@ int TPpContext::tZeroInput::scan(TPpToken* ppToken)
 }
 }
 
 
 //
 //
-// Check an identifier (atom) to see if it is a macro that should be expanded.
+// Check a token to see if it is a macro that should be expanded.
 // If it is, and defined, push a tInput that will produce the appropriate expansion
 // If it is, and defined, push a tInput that will produce the appropriate expansion
 // and return 1.
 // and return 1.
 // If it is, but undefined, and expandUndef is requested, push a tInput that will 
 // If it is, but undefined, and expandUndef is requested, push a tInput that will 
 // expand to 0 and return -1.
 // expand to 0 and return -1.
 // Otherwise, return 0 to indicate no expansion, which is not necessarily an error.
 // Otherwise, return 0 to indicate no expansion, which is not necessarily an error.
 //
 //
-int TPpContext::MacroExpand(int atom, TPpToken* ppToken, bool expandUndef, bool newLineOkay)
+int TPpContext::MacroExpand(TPpToken* ppToken, bool expandUndef, bool newLineOkay)
 {
 {
     ppToken->space = false;
     ppToken->space = false;
-    switch (atom) {
+    int macroAtom = atomStrings.getAtom(ppToken->name);
+    switch (macroAtom) {
     case PpAtomLineMacro:
     case PpAtomLineMacro:
         ppToken->ival = parseContext.getCurrentLoc().line;
         ppToken->ival = parseContext.getCurrentLoc().line;
         snprintf(ppToken->name, sizeof(ppToken->name), "%d", ppToken->ival);
         snprintf(ppToken->name, sizeof(ppToken->name), "%d", ppToken->ival);
@@ -1041,20 +1087,20 @@ int TPpContext::MacroExpand(int atom, TPpToken* ppToken, bool expandUndef, bool
         break;
         break;
     }
     }
 
 
-    Symbol *sym = LookUpSymbol(atom);
+    MacroSymbol* macro = macroAtom == 0 ? nullptr : lookupMacroDef(macroAtom);
     int token;
     int token;
     int depth = 0;
     int depth = 0;
 
 
     // no recursive expansions
     // no recursive expansions
-    if (sym && sym->mac.busy)
+    if (macro != nullptr && macro->busy)
         return 0;
         return 0;
 
 
     // not expanding undefined macros
     // not expanding undefined macros
-    if ((! sym || sym->mac.undef) && ! expandUndef)
+    if ((macro == nullptr || macro->undef) && ! expandUndef)
         return 0;
         return 0;
 
 
     // 0 is the value of an undefined macro
     // 0 is the value of an undefined macro
-    if ((! sym || sym->mac.undef) && expandUndef) {
+    if ((macro == nullptr || macro->undef) && expandUndef) {
         pushInput(new tZeroInput(this));
         pushInput(new tZeroInput(this));
         return -1;
         return -1;
     }
     }
@@ -1062,49 +1108,50 @@ int TPpContext::MacroExpand(int atom, TPpToken* ppToken, bool expandUndef, bool
     tMacroInput *in = new tMacroInput(this);
     tMacroInput *in = new tMacroInput(this);
 
 
     TSourceLoc loc = ppToken->loc;  // in case we go to the next line before discovering the error
     TSourceLoc loc = ppToken->loc;  // in case we go to the next line before discovering the error
-    in->mac = &sym->mac;
-    if (sym->mac.args) {
+    in->mac = macro;
+    if (macro->args.size() > 0 || macro->emptyArgs) {
         token = scanToken(ppToken);
         token = scanToken(ppToken);
         if (newLineOkay) {
         if (newLineOkay) {
             while (token == '\n')
             while (token == '\n')
                 token = scanToken(ppToken);
                 token = scanToken(ppToken);
         }
         }
         if (token != '(') {
         if (token != '(') {
-            parseContext.ppError(loc, "expected '(' following", "macro expansion", GetAtomString(atom));
+            parseContext.ppError(loc, "expected '(' following", "macro expansion", atomStrings.getString(macroAtom));
             UngetToken(token, ppToken);
             UngetToken(token, ppToken);
-            ppToken->atom = atom;
-
             delete in;
             delete in;
             return 0;
             return 0;
         }
         }
-        in->args.resize(in->mac->argc);
-        for (int i = 0; i < in->mac->argc; i++)
+        in->args.resize(in->mac->args.size());
+        for (size_t i = 0; i < in->mac->args.size(); i++)
             in->args[i] = new TokenStream;
             in->args[i] = new TokenStream;
-        int arg = 0;
+        in->expandedArgs.resize(in->mac->args.size());
+        for (size_t i = 0; i < in->mac->args.size(); i++)
+            in->expandedArgs[i] = nullptr;
+        size_t arg = 0;
         bool tokenRecorded = false;
         bool tokenRecorded = false;
         do {
         do {
             depth = 0;
             depth = 0;
             while (1) {
             while (1) {
                 token = scanToken(ppToken);
                 token = scanToken(ppToken);
                 if (token == EndOfInput) {
                 if (token == EndOfInput) {
-                    parseContext.ppError(loc, "End of input in macro", "macro expansion", GetAtomString(atom));
+                    parseContext.ppError(loc, "End of input in macro", "macro expansion", atomStrings.getString(macroAtom));
                     delete in;
                     delete in;
                     return 0;
                     return 0;
                 }
                 }
                 if (token == '\n') {
                 if (token == '\n') {
                     if (! newLineOkay) {
                     if (! newLineOkay) {
-                        parseContext.ppError(loc, "End of line in macro substitution:", "macro expansion", GetAtomString(atom));
+                        parseContext.ppError(loc, "End of line in macro substitution:", "macro expansion", atomStrings.getString(macroAtom));
                         delete in;
                         delete in;
                         return 0;
                         return 0;
                     }
                     }
                     continue;
                     continue;
                 }
                 }
                 if (token == '#') {
                 if (token == '#') {
-                    parseContext.ppError(ppToken->loc, "unexpected '#'", "macro expansion", GetAtomString(atom));
+                    parseContext.ppError(ppToken->loc, "unexpected '#'", "macro expansion", atomStrings.getString(macroAtom));
                     delete in;
                     delete in;
                     return 0;
                     return 0;
                 }
                 }
-                if (in->mac->argc == 0 && token != ')')
+                if (in->mac->args.size() == 0 && token != ')')
                     break;
                     break;
                 if (depth == 0 && (token == ',' || token == ')'))
                 if (depth == 0 && (token == ',' || token == ')'))
                     break;
                     break;
@@ -1112,20 +1159,20 @@ int TPpContext::MacroExpand(int atom, TPpToken* ppToken, bool expandUndef, bool
                     depth++;
                     depth++;
                 if (token == ')')
                 if (token == ')')
                     depth--;
                     depth--;
-                RecordToken(in->args[arg], token, ppToken);
+                RecordToken(*in->args[arg], token, ppToken);
                 tokenRecorded = true;
                 tokenRecorded = true;
             }
             }
             if (token == ')') {
             if (token == ')') {
-                if (in->mac->argc == 1 && tokenRecorded == 0)
+                if (in->mac->args.size() == 1 && tokenRecorded == 0)
                     break;
                     break;
                 arg++;
                 arg++;
                 break;
                 break;
             }
             }
             arg++;
             arg++;
-        } while (arg < in->mac->argc);
+        } while (arg < in->mac->args.size());
 
 
-        if (arg < in->mac->argc)
-            parseContext.ppError(loc, "Too few args in Macro", "macro expansion", GetAtomString(atom));
+        if (arg < in->mac->args.size())
+            parseContext.ppError(loc, "Too few args in Macro", "macro expansion", atomStrings.getString(macroAtom));
         else if (token != ')') {
         else if (token != ')') {
             depth=0;
             depth=0;
             while (token != EndOfInput && (depth > 0 || token != ')')) {
             while (token != EndOfInput && (depth > 0 || token != ')')) {
@@ -1137,19 +1184,22 @@ int TPpContext::MacroExpand(int atom, TPpToken* ppToken, bool expandUndef, bool
             }
             }
 
 
             if (token == EndOfInput) {
             if (token == EndOfInput) {
-                parseContext.ppError(loc, "End of input in macro", "macro expansion", GetAtomString(atom));
+                parseContext.ppError(loc, "End of input in macro", "macro expansion", atomStrings.getString(macroAtom));
                 delete in;
                 delete in;
                 return 0;
                 return 0;
             }
             }
-            parseContext.ppError(loc, "Too many args in macro", "macro expansion", GetAtomString(atom));
+            parseContext.ppError(loc, "Too many args in macro", "macro expansion", atomStrings.getString(macroAtom));
         }
         }
-        for (int i = 0; i < in->mac->argc; i++)
-            in->args[i] = PrescanMacroArg(in->args[i], ppToken, newLineOkay);
+
+        // We need both expanded and non-expanded forms of the argument, for whether or
+        // not token pasting is in play.
+        for (size_t i = 0; i < in->mac->args.size(); i++)
+            in->expandedArgs[i] = PrescanMacroArg(*in->args[i], ppToken, newLineOkay);
     }
     }
 
 
     pushInput(in);
     pushInput(in);
-    sym->mac.busy = 1;
-    RewindTokenStream(sym->mac.body);
+    macro->busy = 1;
+    RewindTokenStream(macro->body);
 
 
     return 1;
     return 1;
 }
 }

+ 11 - 50
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpAtom.cpp

@@ -76,10 +76,6 @@ TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 \****************************************************************************/
 \****************************************************************************/
 
 
-//
-// atom.c
-//
-
 #define _CRT_SECURE_NO_WARNINGS
 #define _CRT_SECURE_NO_WARNINGS
 
 
 #include <cassert>
 #include <cassert>
@@ -98,11 +94,12 @@ const struct {
     const char* str;
     const char* str;
 } tokens[] = {
 } tokens[] = {
 
 
-    { PpAtomAdd,            "+=" },
-    { PpAtomSub,            "-=" },
-    { PpAtomMul,            "*=" },
-    { PpAtomDiv,            "/=" },
-    { PpAtomMod,            "%=" },
+    { PPAtomAddAssign,      "+=" },
+    { PPAtomSubAssign,      "-=" },
+    { PPAtomMulAssign,      "*=" },
+    { PPAtomDivAssign,      "/=" },
+    { PPAtomModAssign,      "%=" },
+
     { PpAtomRight,          ">>" },
     { PpAtomRight,          ">>" },
     { PpAtomLeft,           "<<" },
     { PpAtomLeft,           "<<" },
     { PpAtomAnd,            "&&" },
     { PpAtomAnd,            "&&" },
@@ -124,7 +121,6 @@ const struct {
     { PpAtomIncrement,      "++" },
     { PpAtomIncrement,      "++" },
 
 
     { PpAtomDefine,         "define" },
     { PpAtomDefine,         "define" },
-    { PpAtomDefined,        "defined" },
     { PpAtomUndef,          "undef" },
     { PpAtomUndef,          "undef" },
     { PpAtomIf,             "if" },
     { PpAtomIf,             "if" },
     { PpAtomElif,           "elif" },
     { PpAtomElif,           "elif" },
@@ -153,48 +149,13 @@ const struct {
 
 
 namespace glslang {
 namespace glslang {
 
 
-//
-// Map a new or existing string to an atom, inventing a new atom if necessary.
-//
-int TPpContext::LookUpAddString(const char* s)
-{
-    auto it = atomMap.find(s);
-    if (it == atomMap.end()) {
-        AddAtomFixed(s, nextAtom);
-        return nextAtom++;
-    } else
-        return it->second;
-}
-
-//
-// Map an already created atom to its string.
-//
-const char* TPpContext::GetAtomString(int atom)
-{
-    if ((size_t)atom >= stringMap.size())
-        return "<bad token>";
-
-    const TString* atomString = stringMap[atom];
-
-    return atomString ? atomString->c_str() : "<bad token>";
-}
-
-//
-// Add forced mapping of string to atom.
-//
-void TPpContext::AddAtomFixed(const char* s, int atom)
-{
-    auto it = atomMap.insert(std::pair<TString, int>(s, atom)).first;
-    if (stringMap.size() < (size_t)atom + 1)
-        stringMap.resize(atom + 100, 0);
-    stringMap[atom] = &it->first;
-}
-
 //
 //
 // Initialize the atom table.
 // Initialize the atom table.
 //
 //
-void TPpContext::InitAtomTable()
+TStringAtomMap::TStringAtomMap()
 {
 {
+    badToken.assign("<bad token>");
+
     // Add single character tokens to the atom table:
     // Add single character tokens to the atom table:
     const char* s = "~!%^&*()-+=|,.<>/?;:[]{}#\\";
     const char* s = "~!%^&*()-+=|,.<>/?;:[]{}#\\";
     char t[2];
     char t[2];
@@ -202,13 +163,13 @@ void TPpContext::InitAtomTable()
     t[1] = '\0';
     t[1] = '\0';
     while (*s) {
     while (*s) {
         t[0] = *s;
         t[0] = *s;
-        AddAtomFixed(t, s[0]);
+        addAtomFixed(t, s[0]);
         s++;
         s++;
     }
     }
 
 
     // Add multiple character scanner tokens :
     // Add multiple character scanner tokens :
     for (size_t ii = 0; ii < sizeof(tokens)/sizeof(tokens[0]); ii++)
     for (size_t ii = 0; ii < sizeof(tokens)/sizeof(tokens[0]); ii++)
-        AddAtomFixed(tokens[ii].str, tokens[ii].val);
+        addAtomFixed(tokens[ii].str, tokens[ii].val);
 
 
     nextAtom = PpAtomLast;
     nextAtom = PpAtomLast;
 }
 }

+ 1 - 7
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpContext.cpp

@@ -83,13 +83,10 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 namespace glslang {
 namespace glslang {
 
 
 TPpContext::TPpContext(TParseContextBase& pc, const std::string& rootFileName, TShader::Includer& inclr) : 
 TPpContext::TPpContext(TParseContextBase& pc, const std::string& rootFileName, TShader::Includer& inclr) : 
-    preamble(0), strings(0), parseContext(pc), includer(inclr), inComment(false),
+    preamble(0), strings(0), previous_token('\n'), parseContext(pc), includer(inclr), inComment(false),
     rootFileName(rootFileName),
     rootFileName(rootFileName),
     currentSourceFile(rootFileName)
     currentSourceFile(rootFileName)
 {
 {
-    InitAtomTable();
-    InitScanner();
-
     ifdepth = 0;
     ifdepth = 0;
     for (elsetracker = 0; elsetracker < maxIfNesting; elsetracker++)
     for (elsetracker = 0; elsetracker < maxIfNesting; elsetracker++)
         elseSeen[elsetracker] = false;
         elseSeen[elsetracker] = false;
@@ -98,9 +95,6 @@ TPpContext::TPpContext(TParseContextBase& pc, const std::string& rootFileName, T
 
 
 TPpContext::~TPpContext()
 TPpContext::~TPpContext()
 {
 {
-    for (TSymbolMap::iterator it = symbols.begin(); it != symbols.end(); ++it)
-        delete it->second->mac.body;
-    mem_FreePool(pool);
     delete [] preamble;
     delete [] preamble;
 
 
     // free up the inputStack
     // free up the inputStack

+ 127 - 97
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpContext.h

@@ -92,30 +92,85 @@ namespace glslang {
 
 
 class TPpToken {
 class TPpToken {
 public:
 public:
-    TPpToken() : token(0), space(false), ival(0), dval(0.0), atom(0)
+    TPpToken() : space(false), ival(0), dval(0.0), i64val(0)
     {
     {
         loc.init(); 
         loc.init(); 
         name[0] = 0;
         name[0] = 0;
     }
     }
 
 
+    // This is used for comparing macro definitions, so checks what is relevant for that.
     bool operator==(const TPpToken& right)
     bool operator==(const TPpToken& right)
     {
     {
-        return token == right.token && atom == right.atom &&
-               ival == right.ival && dval == right.dval &&
-               strcmp(name, right.name) == 0;
+        return space == right.space &&
+               ival == right.ival && dval == right.dval && i64val == right.i64val &&
+               strncmp(name, right.name, MaxTokenLength) == 0;
     }
     }
     bool operator!=(const TPpToken& right) { return ! operator==(right); }
     bool operator!=(const TPpToken& right) { return ! operator==(right); }
 
 
     TSourceLoc loc;
     TSourceLoc loc;
-    int    token;
     bool   space;  // true if a space (for white space or a removed comment) should also be recognized, in front of the token returned
     bool   space;  // true if a space (for white space or a removed comment) should also be recognized, in front of the token returned
     int    ival;
     int    ival;
     double dval;
     double dval;
     long long i64val;
     long long i64val;
-    int    atom;
     char   name[MaxTokenLength + 1];
     char   name[MaxTokenLength + 1];
 };
 };
 
 
+class TStringAtomMap {
+//
+// Implementation is in PpAtom.cpp
+//
+// Maintain a bi-directional mapping between relevant preprocessor strings and
+// "atoms" which a unique integers (small, contiguous, not hash-like) per string.
+//
+public:
+    TStringAtomMap();
+
+    // Map string -> atom.
+    // Return 0 if no existing string.
+    int getAtom(const char* s) const
+    {
+        auto it = atomMap.find(s);
+        return it == atomMap.end() ? 0 : it->second;
+    }
+
+    // Map a new or existing string -> atom, inventing a new atom if necessary.
+    int getAddAtom(const char* s)
+    {
+        int atom = getAtom(s);
+        if (atom == 0) {
+            atom = nextAtom++;
+            addAtomFixed(s, atom);
+        }
+        return atom;
+    }
+
+    // Map atom -> string.
+    const char* getString(int atom) const { return stringMap[atom]->c_str(); }
+
+protected:
+    TStringAtomMap(TStringAtomMap&);
+    TStringAtomMap& operator=(TStringAtomMap&);
+
+    TUnorderedMap<TString, int> atomMap;
+    TVector<const TString*> stringMap;    // these point into the TString in atomMap
+    int nextAtom;
+
+    // Bad source characters can lead to bad atoms, so gracefully handle those by
+    // pre-filling the table with them (to avoid if tests later).
+    TString badToken;
+
+    // Add bi-directional mappings:
+    //  - string -> atom
+    //  - atom -> string
+    void addAtomFixed(const char* s, int atom)
+    {
+        auto it = atomMap.insert(std::pair<TString, int>(s, atom)).first;
+        if (stringMap.size() < (size_t)atom + 1)
+            stringMap.resize(atom + 100, &badToken);
+        stringMap[atom] = &it->first;
+    }
+};
+
 class TInputScanner;
 class TInputScanner;
 
 
 // This class is the result of turning a huge pile of C code communicating through globals
 // This class is the result of turning a huge pile of C code communicating through globals
@@ -128,7 +183,8 @@ public:
 
 
     void setPreamble(const char* preamble, size_t length);
     void setPreamble(const char* preamble, size_t length);
 
 
-    const char* tokenize(TPpToken* ppToken);
+    int tokenize(TPpToken& ppToken);
+    int tokenPaste(int token, TPpToken&);
 
 
     class tInput {
     class tInput {
     public:
     public:
@@ -138,6 +194,8 @@ public:
         virtual int scan(TPpToken*) = 0;
         virtual int scan(TPpToken*) = 0;
         virtual int getch() = 0;
         virtual int getch() = 0;
         virtual void ungetch() = 0;
         virtual void ungetch() = 0;
+        virtual bool peekPasting() { return false; }          // true when about to see ##
+        virtual bool endOfReplacementList() { return false; } // true when at the end of a macro replacement list (RHS of #define)
 
 
         // Will be called when we start reading tokens from this instance
         // Will be called when we start reading tokens from this instance
         virtual void notifyActivated() {}
         virtual void notifyActivated() {}
@@ -168,44 +226,33 @@ public:
         size_t current;
         size_t current;
     };
     };
 
 
-    struct MemoryPool {
-        struct chunk        *next;
-        uintptr_t           free, end;
-        size_t              chunksize;
-        uintptr_t           alignmask;
-    };
-
     //
     //
     // From Pp.cpp
     // From Pp.cpp
     //
     //
 
 
     struct MacroSymbol {
     struct MacroSymbol {
-        MacroSymbol() : argc(0), args(0), body(0), busy(0), undef(0) { }
-        int argc;
-        int *args;
-        TokenStream *body;
-        unsigned busy:1;
-        unsigned undef:1;
-    };
-
-    struct Symbol {
-        int atom;
-        MacroSymbol mac;
+        MacroSymbol() : emptyArgs(0), busy(0), undef(0) { }
+        TVector<int> args;
+        TokenStream body;
+        unsigned emptyArgs : 1;
+        unsigned busy      : 1;
+        unsigned undef     : 1;
     };
     };
 
 
-    struct SymbolList {
-        struct SymbolList_Rec *next;
-        Symbol *symb;
-    };
-
-    MemoryPool *pool;
-    typedef TMap<int, Symbol*> TSymbolMap;
-    TSymbolMap symbols; // this has light use... just defined macros
+    typedef TMap<int, MacroSymbol> TSymbolMap;
+    TSymbolMap macroDefs;  // map atoms to macro definitions
+    MacroSymbol* lookupMacroDef(int atom)
+    {
+        auto existingMacroIt = macroDefs.find(atom);
+        return (existingMacroIt == macroDefs.end()) ? nullptr : &(existingMacroIt->second);
+    }
+    void addMacroDef(int atom, MacroSymbol& macroDef) { macroDefs[atom] = macroDef; }
 
 
 protected:
 protected:
     TPpContext(TPpContext&);
     TPpContext(TPpContext&);
     TPpContext& operator=(TPpContext&);
     TPpContext& operator=(TPpContext&);
 
 
+    TStringAtomMap atomStrings;
     char*   preamble;               // string to parse, all before line 1 of string 0, it is 0 if no preamble
     char*   preamble;               // string to parse, all before line 1 of string 0, it is 0 if no preamble
     int     preambleLength;
     int     preambleLength;
     char**  strings;                // official strings of shader, starting a string 0 line 1
     char**  strings;                // official strings of shader, starting a string 0 line 1
@@ -235,8 +282,9 @@ protected:
     }
     }
     int  getChar() { return inputStack.back()->getch(); }
     int  getChar() { return inputStack.back()->getch(); }
     void ungetChar() { inputStack.back()->ungetch(); }
     void ungetChar() { inputStack.back()->ungetch(); }
+    bool peekPasting() { return !inputStack.empty() && inputStack.back()->peekPasting(); }
+    bool endOfReplacementList() { return inputStack.empty() || inputStack.back()->endOfReplacementList(); }
 
 
-    static const int maxMacroArgs = 64;
     static const int maxIfNesting = 64;
     static const int maxIfNesting = 64;
 
 
     int ifdepth;                  // current #if-#else-#endif nesting in the cpp.c file (pre-processor)    
     int ifdepth;                  // current #if-#else-#endif nesting in the cpp.c file (pre-processor)    
@@ -245,24 +293,35 @@ protected:
 
 
     class tMacroInput : public tInput {
     class tMacroInput : public tInput {
     public:
     public:
-        tMacroInput(TPpContext* pp) : tInput(pp) { }
+        tMacroInput(TPpContext* pp) : tInput(pp), prepaste(false), postpaste(false) { }
         virtual ~tMacroInput()
         virtual ~tMacroInput()
         {
         {
             for (size_t i = 0; i < args.size(); ++i)
             for (size_t i = 0; i < args.size(); ++i)
                 delete args[i];
                 delete args[i];
+            for (size_t i = 0; i < expandedArgs.size(); ++i)
+                delete expandedArgs[i];
         }
         }
 
 
-        virtual int scan(TPpToken*);
-        virtual int getch() { assert(0); return EndOfInput; }
-        virtual void ungetch() { assert(0); }
+        virtual int scan(TPpToken*) override;
+        virtual int getch() override { assert(0); return EndOfInput; }
+        virtual void ungetch() override { assert(0); }
+        bool peekPasting() override { return prepaste; }
+        bool endOfReplacementList() override { return mac->body.current >= mac->body.data.size(); }
+
         MacroSymbol *mac;
         MacroSymbol *mac;
         TVector<TokenStream*> args;
         TVector<TokenStream*> args;
+        TVector<TokenStream*> expandedArgs;
+
+    protected:
+        bool peekMacPasting();
+        bool prepaste;         // true if we are just before ##
+        bool postpaste;        // true if we are right after ##
     };
     };
 
 
     class tMarkerInput : public tInput {
     class tMarkerInput : public tInput {
     public:
     public:
         tMarkerInput(TPpContext* pp) : tInput(pp) { }
         tMarkerInput(TPpContext* pp) : tInput(pp) { }
-        virtual int scan(TPpToken*)
+        virtual int scan(TPpToken*) override
         {
         {
             if (done)
             if (done)
                 return EndOfInput;
                 return EndOfInput;
@@ -270,17 +329,17 @@ protected:
 
 
             return marker;
             return marker;
         }
         }
-        virtual int getch() { assert(0); return EndOfInput; }
-        virtual void ungetch() { assert(0); }
+        virtual int getch() override { assert(0); return EndOfInput; }
+        virtual void ungetch() override { assert(0); }
         static const int marker = -3;
         static const int marker = -3;
     };
     };
 
 
     class tZeroInput : public tInput {
     class tZeroInput : public tInput {
     public:
     public:
         tZeroInput(TPpContext* pp) : tInput(pp) { }
         tZeroInput(TPpContext* pp) : tInput(pp) { }
-        virtual int scan(TPpToken*);
-        virtual int getch() { assert(0); return EndOfInput; }
-        virtual void ungetch() { assert(0); }
+        virtual int scan(TPpToken*) override;
+        virtual int getch() override { assert(0); return EndOfInput; }
+        virtual void ungetch() override { assert(0); }
     };
     };
 
 
     std::vector<tInput*> inputStack;
     std::vector<tInput*> inputStack;
@@ -294,7 +353,6 @@ protected:
     // Used to obtain #include content.
     // Used to obtain #include content.
     TShader::Includer& includer;
     TShader::Includer& includer;
 
 
-    int InitCPP();
     int CPPdefine(TPpToken * ppToken);
     int CPPdefine(TPpToken * ppToken);
     int CPPundef(TPpToken * ppToken);
     int CPPundef(TPpToken * ppToken);
     int CPPelse(int matchelse, TPpToken * ppToken);
     int CPPelse(int matchelse, TPpToken * ppToken);
@@ -310,44 +368,39 @@ protected:
     int CPPversion(TPpToken * ppToken);
     int CPPversion(TPpToken * ppToken);
     int CPPextension(TPpToken * ppToken);
     int CPPextension(TPpToken * ppToken);
     int readCPPline(TPpToken * ppToken);
     int readCPPline(TPpToken * ppToken);
-    TokenStream* PrescanMacroArg(TokenStream *a, TPpToken * ppToken, bool newLineOkay);
-    int MacroExpand(int atom, TPpToken* ppToken, bool expandUndef, bool newLineOkay);
-
-    //
-    // from PpSymbols.cpp
-    //
-    Symbol *NewSymbol(int name);
-    Symbol *AddSymbol(int atom);
-    Symbol *LookUpSymbol(int atom);
+    TokenStream* PrescanMacroArg(TokenStream&, TPpToken*, bool newLineOkay);
+    int MacroExpand(TPpToken* ppToken, bool expandUndef, bool newLineOkay);
 
 
     //
     //
     // From PpTokens.cpp
     // From PpTokens.cpp
     //
     //
-    void lAddByte(TokenStream *fTok, unsigned char fVal);
-    int lReadByte(TokenStream *pTok);
-    void lUnreadByte(TokenStream *pTok);
-    void RecordToken(TokenStream* pTok, int token, TPpToken* ppToken);
-    void RewindTokenStream(TokenStream *pTok);
-    int ReadToken(TokenStream* pTok, TPpToken* ppToken);
-    void pushTokenStreamInput(TokenStream *ts);
-    void UngetToken(int token, TPpToken* ppToken);
+    void lAddByte(TokenStream&, unsigned char fVal);
+    int lReadByte(TokenStream&);
+    void lUnreadByte(TokenStream&);
+    void RecordToken(TokenStream&, int token, TPpToken* ppToken);
+    void RewindTokenStream(TokenStream&);
+    int ReadToken(TokenStream&, TPpToken*);
+    void pushTokenStreamInput(TokenStream&, bool pasting = false);
+    void UngetToken(int token, TPpToken*);
     
     
     class tTokenInput : public tInput {
     class tTokenInput : public tInput {
     public:
     public:
-        tTokenInput(TPpContext* pp, TokenStream* t) : tInput(pp), tokens(t) { }
-        virtual int scan(TPpToken *);
-        virtual int getch() { assert(0); return EndOfInput; }
-        virtual void ungetch() { assert(0); }
+        tTokenInput(TPpContext* pp, TokenStream* t, bool prepasting) : tInput(pp), tokens(t), lastTokenPastes(prepasting) { }
+        virtual int scan(TPpToken *) override;
+        virtual int getch() override { assert(0); return EndOfInput; }
+        virtual void ungetch() override { assert(0); }
+        virtual bool peekPasting() override;
     protected:
     protected:
-        TokenStream *tokens;
+        TokenStream* tokens;
+        bool lastTokenPastes;     // true if the last token in the input is to be pasted, rather than consumed as a token
     };
     };
 
 
     class tUngotTokenInput : public tInput {
     class tUngotTokenInput : public tInput {
     public:
     public:
         tUngotTokenInput(TPpContext* pp, int t, TPpToken* p) : tInput(pp), token(t), lval(*p) { }
         tUngotTokenInput(TPpContext* pp, int t, TPpToken* p) : tInput(pp), token(t), lval(*p) { }
-        virtual int scan(TPpToken *);
-        virtual int getch() { assert(0); return EndOfInput; }
-        virtual void ungetch() { assert(0); }
+        virtual int scan(TPpToken *) override;
+        virtual int getch() override { assert(0); return EndOfInput; }
+        virtual void ungetch() override { assert(0); }
     protected:
     protected:
         int token;
         int token;
         TPpToken lval;
         TPpToken lval;
@@ -359,12 +412,12 @@ protected:
     class tStringInput : public tInput {
     class tStringInput : public tInput {
     public:
     public:
         tStringInput(TPpContext* pp, TInputScanner& i) : tInput(pp), input(&i) { }
         tStringInput(TPpContext* pp, TInputScanner& i) : tInput(pp), input(&i) { }
-        virtual int scan(TPpToken*);
+        virtual int scan(TPpToken*) override;
 
 
         // Scanner used to get source stream characters.
         // Scanner used to get source stream characters.
         //  - Escaped newlines are handled here, invisibly to the caller.
         //  - Escaped newlines are handled here, invisibly to the caller.
         //  - All forms of newline are handled, and turned into just a '\n'.
         //  - All forms of newline are handled, and turned into just a '\n'.
-        int getch()
+        int getch() override
         {
         {
             int ch = input->get();
             int ch = input->get();
 
 
@@ -402,7 +455,7 @@ protected:
         // handled here, invisibly to the caller, meaning have to undo exactly
         // handled here, invisibly to the caller, meaning have to undo exactly
         // what getch() above does (e.g., don't leave things in the middle of a
         // what getch() above does (e.g., don't leave things in the middle of a
         // sequence of escaped newlines).
         // sequence of escaped newlines).
-        void ungetch()
+        void ungetch() override
         {
         {
             input->unget();
             input->unget();
 
 
@@ -516,7 +569,6 @@ protected:
         tStringInput stringInput;
         tStringInput stringInput;
     };
     };
 
 
-    int InitScanner();
     int ScanFromString(char* s);
     int ScanFromString(char* s);
     void missingEndifCheck();
     void missingEndifCheck();
     int lFloatConst(int len, int ch, TPpToken* ppToken);
     int lFloatConst(int len, int ch, TPpToken* ppToken);
@@ -540,31 +592,9 @@ protected:
     }
     }
 
 
     bool inComment;
     bool inComment;
-
-    //
-    // From PpAtom.cpp
-    //
-    typedef TUnorderedMap<TString, int> TAtomMap;
-    typedef TVector<const TString*> TStringMap;
-
-    TAtomMap atomMap;
-    TStringMap stringMap;
+    std::string rootFileName;
     std::stack<TShader::Includer::IncludeResult*> includeStack;
     std::stack<TShader::Includer::IncludeResult*> includeStack;
     std::string currentSourceFile;
     std::string currentSourceFile;
-    std::string rootFileName;
-    int nextAtom;
-    void InitAtomTable();
-    void AddAtomFixed(const char* s, int atom);
-    int LookUpAddString(const char* s);
-    const char* GetAtomString(int atom);
-
-    //
-    // From PpMemory.cpp
-    //
-    MemoryPool *mem_CreatePool(size_t chunksize, unsigned align);
-    void mem_FreePool(MemoryPool*);
-    void *mem_Alloc(MemoryPool* p, size_t size);
-    int mem_AddCleanup(MemoryPool* p, void (*fn)(void *, void*), void* arg1, void* arg2);
 };
 };
 
 
 } // end namespace glslang
 } // end namespace glslang

+ 0 - 80
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpMemory.cpp

@@ -76,86 +76,6 @@ TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 \****************************************************************************/
 \****************************************************************************/
 
 
-#include <cstddef>
-#include <cstdlib>
-#include <cstring>
-
-#include "PpContext.h"
-
-// default alignment and chunksize, if called with 0 arguments
-#define CHUNKSIZE       (64*1024)
-#define ALIGN           8
-
 namespace glslang {
 namespace glslang {
 
 
-struct chunk {
-    struct chunk        *next;
-};
-
-TPpContext::MemoryPool* TPpContext::mem_CreatePool(size_t chunksize, unsigned int align)
-{
-    if (align == 0)
-        align = ALIGN;
-    if (chunksize == 0)
-        chunksize = CHUNKSIZE;
-    if (align & (align - 1))
-        return nullptr;
-    if (chunksize < sizeof(MemoryPool))
-        return nullptr;
-    if (chunksize & (align - 1))
-        return nullptr;
-
-    MemoryPool *pool = (MemoryPool*)malloc(chunksize);
-    if (! pool)
-        return nullptr;
-
-    pool->next = 0;
-    pool->chunksize = chunksize;
-    pool->alignmask = (uintptr_t)(align) - 1;  
-    pool->free = ((uintptr_t)(pool + 1) + pool->alignmask) & ~pool->alignmask;
-    pool->end = (uintptr_t)pool + chunksize;
-    
-    return pool;
-}
-
-void TPpContext::mem_FreePool(MemoryPool *pool)
-{
-    struct chunk *p, *next;
-
-    for (p = (struct chunk *)pool; p; p = next) {
-        next = p->next;
-        free(p);
-    }
-}
-
-void* TPpContext::mem_Alloc(MemoryPool *pool, size_t size)
-{
-    struct chunk *ch;
-    void *rv = (void *)pool->free;
-    size = (size + pool->alignmask) & ~pool->alignmask;
-    if (size <= 0) size = pool->alignmask;
-    pool->free += size;
-    if (pool->free > pool->end || pool->free < (uintptr_t)rv) {
-        size_t minreq = (size + sizeof(struct chunk) + pool->alignmask) & ~pool->alignmask;
-        pool->free = (uintptr_t)rv;
-        if (minreq >= pool->chunksize) {
-            // request size is too big for the chunksize, so allocate it as
-            // a single chunk of the right size
-            ch = (struct chunk*)malloc(minreq);
-            if (! ch)
-                return nullptr;
-        } else {
-            ch = (struct chunk*)malloc(pool->chunksize);
-            if (! ch)
-                return nullptr;
-            pool->free = (uintptr_t)ch + minreq;
-            pool->end = (uintptr_t)ch + pool->chunksize;
-        }
-        ch->next = pool->next;
-        pool->next = ch;
-        rv = (void *)(((uintptr_t)(ch+1) + pool->alignmask) & ~pool->alignmask);
-    }
-    return rv;
-}
-
 } // end namespace glslang
 } // end namespace glslang

+ 113 - 49
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpScanner.cpp

@@ -75,9 +75,6 @@ NVIDIA SOFTWARE, HOWEVER CAUSED AND WHETHER UNDER THEORY OF CONTRACT,
 TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 \****************************************************************************/
 \****************************************************************************/
-//
-// scanner.c
-//
 
 
 #define _CRT_SECURE_NO_WARNINGS
 #define _CRT_SECURE_NO_WARNINGS
 
 
@@ -90,17 +87,6 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
 
 namespace glslang {
 namespace glslang {
 
 
-int TPpContext::InitScanner()
-{
-    // Add various atoms needed by the CPP line scanner:
-    if (!InitCPP())
-        return 0;
-
-    previous_token = '\n';
-
-    return 1;
-}
-
 ///////////////////////////////////////////////////////////////////////////////////////////////
 ///////////////////////////////////////////////////////////////////////////////////////////////
 /////////////////////////////////// Floating point constants: /////////////////////////////////
 /////////////////////////////////// Floating point constants: /////////////////////////////////
 ///////////////////////////////////////////////////////////////////////////////////////////////
 ///////////////////////////////////////////////////////////////////////////////////////////////
@@ -261,7 +247,6 @@ int TPpContext::lFloatConst(int len, int ch, TPpToken* ppToken)
 //
 //
 int TPpContext::tStringInput::scan(TPpToken* ppToken)
 int TPpContext::tStringInput::scan(TPpToken* ppToken)
 {
 {
-    char* tokenText = ppToken->name;
     int AlreadyComplained = 0;
     int AlreadyComplained = 0;
     int len = 0;
     int len = 0;
     int ch = 0;
     int ch = 0;
@@ -300,7 +285,7 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
         case 'z':
         case 'z':
             do {
             do {
                 if (len < MaxTokenLength) {
                 if (len < MaxTokenLength) {
-                    tokenText[len++] = (char)ch;
+                    ppToken->name[len++] = (char)ch;
                     ch = getch();
                     ch = getch();
                 } else {
                 } else {
                     if (! AlreadyComplained) {
                     if (! AlreadyComplained) {
@@ -318,9 +303,8 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
             if (len == 0)
             if (len == 0)
                 continue;
                 continue;
 
 
-            tokenText[len] = '\0';
+            ppToken->name[len] = '\0';
             ungetch();
             ungetch();
-            ppToken->atom = pp->LookUpAddString(tokenText);
             return PpAtomIdentifier;
             return PpAtomIdentifier;
         case '0':
         case '0':
             ppToken->name[len++] = (char)ch;
             ppToken->name[len++] = (char)ch;
@@ -545,7 +529,7 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
             if (ch == '-') {
             if (ch == '-') {
                 return PpAtomDecrement;
                 return PpAtomDecrement;
             } else if (ch == '=') {
             } else if (ch == '=') {
-                return PpAtomSub;
+                return PPAtomSubAssign;
             } else {
             } else {
                 ungetch();
                 ungetch();
                 return '-';
                 return '-';
@@ -555,7 +539,7 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
             if (ch == '+') {
             if (ch == '+') {
                 return PpAtomIncrement;
                 return PpAtomIncrement;
             } else if (ch == '=') {
             } else if (ch == '=') {
-                return PpAtomAdd;
+                return PPAtomAddAssign;
             } else {
             } else {
                 ungetch();
                 ungetch();
                 return '+';
                 return '+';
@@ -563,7 +547,7 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
         case '*':
         case '*':
             ch = getch();
             ch = getch();
             if (ch == '=') {
             if (ch == '=') {
-                return PpAtomMul;
+                return PPAtomMulAssign;
             } else {
             } else {
                 ungetch();
                 ungetch();
                 return '*';
                 return '*';
@@ -571,7 +555,7 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
         case '%':
         case '%':
             ch = getch();
             ch = getch();
             if (ch == '=') {
             if (ch == '=') {
-                return PpAtomMod;
+                return PPAtomModAssign;
             } else {
             } else {
                 ungetch();
                 ungetch();
                 return '%';
                 return '%';
@@ -697,7 +681,7 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
                 // loop again to get the next token...
                 // loop again to get the next token...
                 break;
                 break;
             } else if (ch == '=') {
             } else if (ch == '=') {
-                return PpAtomDiv;
+                return PPAtomDivAssign;
             } else {
             } else {
                 ungetch();
                 ungetch();
                 return '/';
                 return '/';
@@ -707,13 +691,13 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
             ch = getch();
             ch = getch();
             while (ch != '"' && ch != '\n' && ch != EndOfInput) {
             while (ch != '"' && ch != '\n' && ch != EndOfInput) {
                 if (len < MaxTokenLength) {
                 if (len < MaxTokenLength) {
-                    tokenText[len] = (char)ch;
+                    ppToken->name[len] = (char)ch;
                     len++;
                     len++;
                     ch = getch();
                     ch = getch();
                 } else
                 } else
                     break;
                     break;
             };
             };
-            tokenText[len] = '\0';
+            ppToken->name[len] = '\0';
             if (ch != '"') {
             if (ch != '"') {
                 ungetch();
                 ungetch();
                 pp->parseContext.ppError(ppToken->loc, "End of line in string", "string", "");
                 pp->parseContext.ppError(ppToken->loc, "End of line in string", "string", "");
@@ -729,31 +713,31 @@ int TPpContext::tStringInput::scan(TPpToken* ppToken)
 // The main functional entry point into the preprocessor, which will
 // The main functional entry point into the preprocessor, which will
 // scan the source strings to figure out and return the next processing token.
 // scan the source strings to figure out and return the next processing token.
 //
 //
-// Return string pointer to next token.
-// Return 0 when no more tokens.
+// Return the token, or EndOfInput when no more tokens.
 //
 //
-const char* TPpContext::tokenize(TPpToken* ppToken)
+int TPpContext::tokenize(TPpToken& ppToken)
 {
 {
-    int token = '\n';
-
     for(;;) {
     for(;;) {
-        token = scanToken(ppToken);
-        ppToken->token = token;
+        int token = scanToken(&ppToken);
+
+        // Handle token-pasting logic
+        token = tokenPaste(token, ppToken);
+
         if (token == EndOfInput) {
         if (token == EndOfInput) {
             missingEndifCheck();
             missingEndifCheck();
-            return nullptr;
+            return EndOfInput;
         }
         }
         if (token == '#') {
         if (token == '#') {
             if (previous_token == '\n') {
             if (previous_token == '\n') {
-                token = readCPPline(ppToken);
+                token = readCPPline(&ppToken);
                 if (token == EndOfInput) {
                 if (token == EndOfInput) {
                     missingEndifCheck();
                     missingEndifCheck();
-                    return nullptr;
+                    return EndOfInput;
                 }
                 }
                 continue;
                 continue;
             } else {
             } else {
-                parseContext.ppError(ppToken->loc, "preprocessor directive cannot be preceded by another token", "#", "");
-                return nullptr;
+                parseContext.ppError(ppToken.loc, "preprocessor directive cannot be preceded by another token", "#", "");
+                return EndOfInput;
             }
             }
         }
         }
         previous_token = token;
         previous_token = token;
@@ -762,10 +746,9 @@ const char* TPpContext::tokenize(TPpToken* ppToken)
             continue;
             continue;
 
 
         // expand macros
         // expand macros
-        if (token == PpAtomIdentifier && MacroExpand(ppToken->atom, ppToken, false, true) != 0)
+        if (token == PpAtomIdentifier && MacroExpand(&ppToken, false, true) != 0)
             continue;
             continue;
 
 
-        const char* tokenString = nullptr;
         switch (token) {
         switch (token) {
         case PpAtomIdentifier:
         case PpAtomIdentifier:
         case PpAtomConstInt:
         case PpAtomConstInt:
@@ -777,27 +760,108 @@ const char* TPpContext::tokenize(TPpToken* ppToken)
 #ifdef AMD_EXTENSIONS
 #ifdef AMD_EXTENSIONS
         case PpAtomConstFloat16:
         case PpAtomConstFloat16:
 #endif
 #endif
-            tokenString = ppToken->name;
+            if (ppToken.name[0] == '\0')
+                continue;
             break;
             break;
         case PpAtomConstString:
         case PpAtomConstString:
-            if (parseContext.intermediate.getSource() == EShSourceHlsl) {
+            if (parseContext.intermediate.getSource() != EShSourceHlsl) {
                 // HLSL allows string literals.
                 // HLSL allows string literals.
-                tokenString = ppToken->name;
-            } else {
-                parseContext.ppError(ppToken->loc, "string literals not supported", "\"\"", "");
+                parseContext.ppError(ppToken.loc, "string literals not supported", "\"\"", "");
+                continue;
             }
             }
             break;
             break;
         case '\'':
         case '\'':
-            parseContext.ppError(ppToken->loc, "character literals not supported", "\'", "");
-            break;
+            parseContext.ppError(ppToken.loc, "character literals not supported", "\'", "");
+            continue;
         default:
         default:
-            tokenString = GetAtomString(token);
+            strcpy(ppToken.name, atomStrings.getString(token));
+            break;
+        }
+
+        return token;
+    }
+}
+
+//
+// Do all token-pasting related combining of two pasted tokens when getting a
+// stream of tokens from a replacement list. Degenerates to no processing if a
+// replacement list is not the source of the token stream.
+//
+int TPpContext::tokenPaste(int token, TPpToken& ppToken)
+{
+    // starting with ## is illegal, skip to next token
+    if (token == PpAtomPaste) {
+        parseContext.ppError(ppToken.loc, "unexpected location", "##", "");
+        return scanToken(&ppToken);
+    }
+
+    int resultToken = token; // "foo" pasted with "35" is an identifier, not a number
+
+    // ## can be chained, process all in the chain at once
+    while (peekPasting()) {
+        TPpToken pastedPpToken;
+
+        // next token has to be ##
+        token = scanToken(&pastedPpToken);
+        assert(token == PpAtomPaste);
+
+        if (endOfReplacementList()) {
+            parseContext.ppError(ppToken.loc, "unexpected location; end of replacement list", "##", "");
+            break;
+        }
+
+        // get the token after the ##
+        token = scanToken(&pastedPpToken);
+
+        // get the token text
+        switch (resultToken) {
+        case PpAtomIdentifier:
+            // already have the correct text in token.names
+            break;
+        case '=':
+        case '!':
+        case '-':
+        case '~':
+        case '+':
+        case '*':
+        case '/':
+        case '%':
+        case '<':
+        case '>':
+        case '|':
+        case '^':
+        case '&':
+        case PpAtomRight:
+        case PpAtomLeft:
+        case PpAtomAnd:
+        case PpAtomOr:
+        case PpAtomXor:
+            strcpy(ppToken.name, atomStrings.getString(resultToken));
+            strcpy(pastedPpToken.name, atomStrings.getString(token));
             break;
             break;
+        default:
+            parseContext.ppError(ppToken.loc, "not supported for these tokens", "##", "");
+            return resultToken;
         }
         }
 
 
-        if (tokenString)
-            return tokenString;
+        // combine the tokens
+        if (strlen(ppToken.name) + strlen(pastedPpToken.name) > MaxTokenLength) {
+            parseContext.ppError(ppToken.loc, "combined tokens are too long", "##", "");
+            return resultToken;
+        }
+        strncat(ppToken.name, pastedPpToken.name, MaxTokenLength - strlen(ppToken.name));
+
+        // correct the kind of token we are making, if needed (identifiers stay identifiers)
+        if (resultToken != PpAtomIdentifier) {
+            int newToken = atomStrings.getAtom(ppToken.name);
+            if (newToken > 0)
+                resultToken = newToken;
+            else
+                parseContext.ppError(ppToken.loc, "combined token is invalid", "##", "");
+        }
     }
     }
+
+    return resultToken;
 }
 }
 
 
 // Checks if we've seen balanced #if...#endif
 // Checks if we've seen balanced #if...#endif

+ 0 - 57
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpSymbols.cpp

@@ -75,60 +75,3 @@ NVIDIA SOFTWARE, HOWEVER CAUSED AND WHETHER UNDER THEORY OF CONTRACT,
 TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 \****************************************************************************/
 \****************************************************************************/
-//
-// symbols.c
-//
-
-#include <cassert>
-#include <cstdlib>
-#include <cstring>
-
-#include "PpContext.h"
-
-///////////////////////////////////////////////////////////////////////////////////////////////
-/////////////////////////////////// Symbol Table Variables: ///////////////////////////////////
-///////////////////////////////////////////////////////////////////////////////////////////////
-
-namespace glslang {
-
-/*
-* Allocate a new symbol node;
-*
-*/
-TPpContext::Symbol* TPpContext::NewSymbol(int atom)
-{
-    Symbol* lSymb;
-    char* pch;
-    size_t ii;
-
-    lSymb = (Symbol *) mem_Alloc(pool, sizeof(Symbol));
-    lSymb->atom = atom;
-
-    // Clear macro
-    pch = (char*) &lSymb->mac;
-    for (ii = 0; ii < sizeof(lSymb->mac); ii++)
-        *pch++ = 0;
-
-    return lSymb;
-}
-
-TPpContext::Symbol* TPpContext::AddSymbol(int atom)
-{
-    Symbol *lSymb;
-
-    lSymb = NewSymbol(atom);
-    symbols[lSymb->atom] = lSymb;
-
-    return lSymb;
-}
-
-TPpContext::Symbol* TPpContext::LookUpSymbol(int atom)
-{
-    TSymbolMap::iterator it = symbols.find(atom);
-    if (it == symbols.end())
-        return nullptr;
-    else
-        return it->second;
-}
-
-} // end namespace glslang

+ 53 - 32
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpTokens.cpp

@@ -95,32 +95,32 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
 
 namespace glslang {
 namespace glslang {
 
 
-void TPpContext::lAddByte(TokenStream *fTok, unsigned char fVal)
+void TPpContext::lAddByte(TokenStream& fTok, unsigned char fVal)
 {
 {
-    fTok->data.push_back(fVal);
+    fTok.data.push_back(fVal);
 }
 }
 
 
 /*
 /*
 * Get the next byte from a stream.
 * Get the next byte from a stream.
 */
 */
-int TPpContext::lReadByte(TokenStream *pTok)
+int TPpContext::lReadByte(TokenStream& pTok)
 {
 {
-    if (pTok->current < pTok->data.size())
-        return pTok->data[pTok->current++];
+    if (pTok.current < pTok.data.size())
+        return pTok.data[pTok.current++];
     else
     else
         return EndOfInput;
         return EndOfInput;
 }
 }
 
 
-void TPpContext::lUnreadByte(TokenStream *pTok)
+void TPpContext::lUnreadByte(TokenStream& pTok)
 {
 {
-    if (pTok->current > 0)
-        --pTok->current;
+    if (pTok.current > 0)
+        --pTok.current;
 }
 }
 
 
 /*
 /*
 * Add a token to the end of a list for later playback.
 * Add a token to the end of a list for later playback.
 */
 */
-void TPpContext::RecordToken(TokenStream *pTok, int token, TPpToken* ppToken)
+void TPpContext::RecordToken(TokenStream& pTok, int token, TPpToken* ppToken)
 {
 {
     const char* s;
     const char* s;
     char* str = NULL;
     char* str = NULL;
@@ -160,19 +160,18 @@ void TPpContext::RecordToken(TokenStream *pTok, int token, TPpToken* ppToken)
 }
 }
 
 
 /*
 /*
-* Reset a token stream in preperation for reading.
+* Reset a token stream in preparation for reading.
 */
 */
-void TPpContext::RewindTokenStream(TokenStream *pTok)
+void TPpContext::RewindTokenStream(TokenStream& pTok)
 {
 {
-    pTok->current = 0;
+    pTok.current = 0;
 }
 }
 
 
 /*
 /*
 * Read the next token from a token stream (not the source stream, but stream used to hold a tokenized macro).
 * Read the next token from a token stream (not the source stream, but stream used to hold a tokenized macro).
 */
 */
-int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
+int TPpContext::ReadToken(TokenStream& pTok, TPpToken *ppToken)
 {
 {
-    char* tokenText = ppToken->name;
     int ltoken, len;
     int ltoken, len;
     int ch;
     int ch;
 
 
@@ -183,13 +182,11 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
     switch (ltoken) {
     switch (ltoken) {
     case '#':
     case '#':
         // Check for ##, unless the current # is the last character
         // Check for ##, unless the current # is the last character
-        if (pTok->current < pTok->data.size()) {
+        if (pTok.current < pTok.data.size()) {
             if (lReadByte(pTok) == '#') {
             if (lReadByte(pTok) == '#') {
                 parseContext.requireProfile(ppToken->loc, ~EEsProfile, "token pasting (##)");
                 parseContext.requireProfile(ppToken->loc, ~EEsProfile, "token pasting (##)");
                 parseContext.profileRequires(ppToken->loc, ~EEsProfile, 130, 0, "token pasting (##)");
                 parseContext.profileRequires(ppToken->loc, ~EEsProfile, 130, 0, "token pasting (##)");
-                parseContext.error(ppToken->loc, "token pasting not implemented (internal error)", "##", "");
-                //return PpAtomPaste;
-                return ReadToken(pTok, ppToken);
+                ltoken = PpAtomPaste;
             } else
             } else
                 lUnreadByte(pTok);
                 lUnreadByte(pTok);
         }
         }
@@ -209,7 +206,7 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
         ch = lReadByte(pTok);
         ch = lReadByte(pTok);
         while (ch != 0 && ch != EndOfInput) {
         while (ch != 0 && ch != EndOfInput) {
             if (len < MaxTokenLength) {
             if (len < MaxTokenLength) {
-                tokenText[len] = (char)ch;
+                ppToken->name[len] = (char)ch;
                 len++;
                 len++;
                 ch = lReadByte(pTok);
                 ch = lReadByte(pTok);
             } else {
             } else {
@@ -217,11 +214,10 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
                 break;
                 break;
             }
             }
         }
         }
-        tokenText[len] = 0;
+        ppToken->name[len] = 0;
 
 
         switch (ltoken) {
         switch (ltoken) {
         case PpAtomIdentifier:
         case PpAtomIdentifier:
-            ppToken->atom = LookUpAddString(tokenText);
             break;
             break;
         case PpAtomConstString:
         case PpAtomConstString:
             break;
             break;
@@ -233,8 +229,8 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
             ppToken->dval = atof(ppToken->name);
             ppToken->dval = atof(ppToken->name);
             break;
             break;
         case PpAtomConstInt:
         case PpAtomConstInt:
-            if (len > 0 && tokenText[0] == '0') {
-                if (len > 1 && (tokenText[1] == 'x' || tokenText[1] == 'X'))
+            if (len > 0 && ppToken->name[0] == '0') {
+                if (len > 1 && (ppToken->name[1] == 'x' || ppToken->name[1] == 'X'))
                     ppToken->ival = (int)strtol(ppToken->name, 0, 16);
                     ppToken->ival = (int)strtol(ppToken->name, 0, 16);
                 else
                 else
                     ppToken->ival = (int)strtol(ppToken->name, 0, 8);
                     ppToken->ival = (int)strtol(ppToken->name, 0, 8);
@@ -242,8 +238,8 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
                 ppToken->ival = atoi(ppToken->name);
                 ppToken->ival = atoi(ppToken->name);
             break;
             break;
         case PpAtomConstUint:
         case PpAtomConstUint:
-            if (len > 0 && tokenText[0] == '0') {
-                if (len > 1 && (tokenText[1] == 'x' || tokenText[1] == 'X'))
+            if (len > 0 && ppToken->name[0] == '0') {
+                if (len > 1 && (ppToken->name[1] == 'x' || ppToken->name[1] == 'X'))
                     ppToken->ival = (int)strtoul(ppToken->name, 0, 16);
                     ppToken->ival = (int)strtoul(ppToken->name, 0, 16);
                 else
                 else
                     ppToken->ival = (int)strtoul(ppToken->name, 0, 8);
                     ppToken->ival = (int)strtoul(ppToken->name, 0, 8);
@@ -251,8 +247,8 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
                 ppToken->ival = (int)strtoul(ppToken->name, 0, 10);
                 ppToken->ival = (int)strtoul(ppToken->name, 0, 10);
             break;
             break;
         case PpAtomConstInt64:
         case PpAtomConstInt64:
-            if (len > 0 && tokenText[0] == '0') {
-                if (len > 1 && (tokenText[1] == 'x' || tokenText[1] == 'X'))
+            if (len > 0 && ppToken->name[0] == '0') {
+                if (len > 1 && (ppToken->name[1] == 'x' || ppToken->name[1] == 'X'))
                     ppToken->i64val = strtoll(ppToken->name, nullptr, 16);
                     ppToken->i64val = strtoll(ppToken->name, nullptr, 16);
                 else
                 else
                     ppToken->i64val = strtoll(ppToken->name, nullptr, 8);
                     ppToken->i64val = strtoll(ppToken->name, nullptr, 8);
@@ -260,8 +256,8 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
                 ppToken->i64val = atoll(ppToken->name);
                 ppToken->i64val = atoll(ppToken->name);
             break;
             break;
         case PpAtomConstUint64:
         case PpAtomConstUint64:
-            if (len > 0 && tokenText[0] == '0') {
-                if (len > 1 && (tokenText[1] == 'x' || tokenText[1] == 'X'))
+            if (len > 0 && ppToken->name[0] == '0') {
+                if (len > 1 && (ppToken->name[1] == 'x' || ppToken->name[1] == 'X'))
                     ppToken->i64val = (long long)strtoull(ppToken->name, nullptr, 16);
                     ppToken->i64val = (long long)strtoull(ppToken->name, nullptr, 16);
                 else
                 else
                     ppToken->i64val = (long long)strtoull(ppToken->name, nullptr, 8);
                     ppToken->i64val = (long long)strtoull(ppToken->name, nullptr, 8);
@@ -276,12 +272,37 @@ int TPpContext::ReadToken(TokenStream *pTok, TPpToken *ppToken)
 
 
 int TPpContext::tTokenInput::scan(TPpToken* ppToken)
 int TPpContext::tTokenInput::scan(TPpToken* ppToken)
 {
 {
-    return pp->ReadToken(tokens, ppToken);
+    return pp->ReadToken(*tokens, ppToken);
 }
 }
 
 
-void TPpContext::pushTokenStreamInput(TokenStream* ts)
+// We are pasting if the entire macro is preceding a pasting operator
+// (lastTokenPastes) and we are also on the last token.
+bool TPpContext::tTokenInput::peekPasting()
 {
 {
-    pushInput(new tTokenInput(this, ts));
+    if (! lastTokenPastes)
+        return false;
+    // Getting here means the last token will be pasted.
+
+    // Are we at the last non-whitespace token?
+    size_t savePos = tokens->current;
+    bool moreTokens = false;
+    do {
+        int byte = pp->lReadByte(*tokens);
+        if (byte == EndOfInput)
+            break;
+        if (byte != ' ') {
+            moreTokens = true;
+            break;
+        }
+    } while (true);
+    tokens->current = savePos;
+
+    return !moreTokens;
+}
+
+void TPpContext::pushTokenStreamInput(TokenStream& ts, bool prepasting)
+{
+    pushInput(new tTokenInput(this, &ts, prepasting));
     RewindTokenStream(ts);
     RewindTokenStream(ts);
 }
 }
 
 

+ 5 - 6
3rdparty/glslang/glslang/MachineIndependent/preprocessor/PpTokens.h

@@ -86,11 +86,11 @@ enum EFixedAtoms {
 
 
     // Operators
     // Operators
 
 
-    PpAtomAdd,
-    PpAtomSub,
-    PpAtomMul,
-    PpAtomDiv,
-    PpAtomMod,
+    PPAtomAddAssign,
+    PPAtomSubAssign,
+    PPAtomMulAssign,
+    PPAtomDivAssign,
+    PPAtomModAssign,
 
 
     PpAtomRight,
     PpAtomRight,
     PpAtomLeft,
     PpAtomLeft,
@@ -134,7 +134,6 @@ enum EFixedAtoms {
     // preprocessor "keywords"
     // preprocessor "keywords"
 
 
     PpAtomDefine,
     PpAtomDefine,
-    PpAtomDefined,
     PpAtomUndef,
     PpAtomUndef,
 
 
     PpAtomIf,
     PpAtomIf,

+ 1 - 0
3rdparty/glslang/gtests/AST.FromFile.cpp

@@ -178,6 +178,7 @@ INSTANTIATE_TEST_CASE_P(
         "syntaxError.frag",
         "syntaxError.frag",
         "test.frag",
         "test.frag",
         "texture.frag",
         "texture.frag",
+        "tokenPaste.vert",
         "types.frag",
         "types.frag",
         "uniformArray.frag",
         "uniformArray.frag",
         "variableArrayIndex.frag",
         "variableArrayIndex.frag",

+ 2 - 0
3rdparty/glslang/gtests/Spv.FromFile.cpp

@@ -216,6 +216,7 @@ INSTANTIATE_TEST_CASE_P(
         "spv.forwardFun.frag",
         "spv.forwardFun.frag",
         "spv.functionCall.frag",
         "spv.functionCall.frag",
         "spv.functionSemantics.frag",
         "spv.functionSemantics.frag",
+        "spv.GeometryShaderPassthrough.geom",
         "spv.interpOps.frag",
         "spv.interpOps.frag",
         "spv.int64.frag",
         "spv.int64.frag",
         "spv.layoutNested.vert",
         "spv.layoutNested.vert",
@@ -240,6 +241,7 @@ INSTANTIATE_TEST_CASE_P(
         "spv.precision.frag",
         "spv.precision.frag",
         "spv.prepost.frag",
         "spv.prepost.frag",
         "spv.qualifiers.vert",
         "spv.qualifiers.vert",
+        "spv.sampleMaskOverrideCoverage.frag",
         "spv.shaderBallot.comp",
         "spv.shaderBallot.comp",
         "spv.shaderDrawParams.vert",
         "spv.shaderDrawParams.vert",
         "spv.shaderGroupVote.comp",
         "spv.shaderGroupVote.comp",

+ 14 - 6
3rdparty/glslang/hlsl/hlslGrammar.cpp

@@ -90,10 +90,11 @@ bool HlslGrammar::acceptIdentifier(HlslToken& idToken)
     // as "linear" or "centroid" NOT valid identifiers.  This code special cases "sample",
     // as "linear" or "centroid" NOT valid identifiers.  This code special cases "sample",
     // so e.g, "int sample;" is accepted.
     // so e.g, "int sample;" is accepted.
     if (peekTokenClass(EHTokSample)) {
     if (peekTokenClass(EHTokSample)) {
-        idToken.string     = NewPoolTString("sample");
-        idToken.tokenClass = EHTokIdentifier;
-        idToken.symbol     = nullptr;
-        idToken.loc        = token.loc;
+        token.string     = NewPoolTString("sample");
+        token.tokenClass = EHTokIdentifier;
+        token.symbol     = nullptr;
+
+        idToken          = token;
         advanceToken();
         advanceToken();
         return true;
         return true;
     }
     }
@@ -475,8 +476,15 @@ bool HlslGrammar::acceptFullySpecifiedType(TType& type)
     TSourceLoc loc = token.loc;
     TSourceLoc loc = token.loc;
 
 
     // type_specifier
     // type_specifier
-    if (! acceptType(type))
+    if (! acceptType(type)) {
+        // If this is not a type, we may have inadvertently gone down a wrong path
+        // py parsing "sample", which can be treated like either an identifier or a
+        // qualifier.  Back it out, if we did.
+        if (qualifier.sample)
+            recedeToken();
+
         return false;
         return false;
+    }
     if (type.getBasicType() == EbtBlock) {
     if (type.getBasicType() == EbtBlock) {
         // the type was a block, which set some parts of the qualifier
         // the type was a block, which set some parts of the qualifier
         parseContext.mergeQualifiers(type.getQualifier(), qualifier);
         parseContext.mergeQualifiers(type.getQualifier(), qualifier);
@@ -2203,7 +2211,7 @@ bool HlslGrammar::acceptPostfixExpression(TIntermTyped*& node)
     } else if (acceptIdentifier(idToken)) {
     } else if (acceptIdentifier(idToken)) {
         // identifier or function_call name
         // identifier or function_call name
         if (! peekTokenClass(EHTokLeftParen)) {
         if (! peekTokenClass(EHTokLeftParen)) {
-            node = parseContext.handleVariable(idToken.loc, idToken.symbol, token.string);
+            node = parseContext.handleVariable(idToken.loc, idToken.symbol, idToken.string);
         } else if (acceptFunctionCall(idToken, node)) {
         } else if (acceptFunctionCall(idToken, node)) {
             // function_call (nothing else to do yet)
             // function_call (nothing else to do yet)
         } else {
         } else {

+ 9 - 9
3rdparty/glslang/hlsl/hlslParseHelper.h

@@ -50,18 +50,18 @@ public:
                      const TString sourceEntryPointName,
                      const TString sourceEntryPointName,
                      bool forwardCompatible = false, EShMessages messages = EShMsgDefault);
                      bool forwardCompatible = false, EShMessages messages = EShMsgDefault);
     virtual ~HlslParseContext();
     virtual ~HlslParseContext();
-    void initializeExtensionBehavior();
+    void initializeExtensionBehavior() override;
 
 
-    void setLimits(const TBuiltInResource&);
-    bool parseShaderStrings(TPpContext&, TInputScanner& input, bool versionWillBeError = false);
-    virtual const char* getGlobalUniformBlockName() { return "$Global"; }
+    void setLimits(const TBuiltInResource&) override;
+    bool parseShaderStrings(TPpContext&, TInputScanner& input, bool versionWillBeError = false) override;
+    virtual const char* getGlobalUniformBlockName() override { return "$Global"; }
 
 
-    void reservedPpErrorCheck(const TSourceLoc&, const char* /*name*/, const char* /*op*/) { }
-    bool lineContinuationCheck(const TSourceLoc&, bool /*endOfComment*/) { return true; }
-    bool lineDirectiveShouldSetNextLine() const { return true; }
+    void reservedPpErrorCheck(const TSourceLoc&, const char* /*name*/, const char* /*op*/) override { }
+    bool lineContinuationCheck(const TSourceLoc&, bool /*endOfComment*/) override { return true; }
+    bool lineDirectiveShouldSetNextLine() const override { return true; }
     bool builtInName(const TString&);
     bool builtInName(const TString&);
 
 
-    void handlePragma(const TSourceLoc&, const TVector<TString>&);
+    void handlePragma(const TSourceLoc&, const TVector<TString>&) override;
     TIntermTyped* handleVariable(const TSourceLoc&, TSymbol* symbol,  const TString* string);
     TIntermTyped* handleVariable(const TSourceLoc&, TSymbol* symbol,  const TString* string);
     TIntermTyped* handleBracketDereference(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
     TIntermTyped* handleBracketDereference(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
     TIntermTyped* handleBracketOperator(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
     TIntermTyped* handleBracketOperator(const TSourceLoc&, TIntermTyped* base, TIntermTyped* index);
@@ -134,7 +134,7 @@ public:
     TIntermTyped* constructAggregate(TIntermNode*, const TType&, int, const TSourceLoc&);
     TIntermTyped* constructAggregate(TIntermNode*, const TType&, int, const TSourceLoc&);
     TIntermTyped* constructBuiltIn(const TType&, TOperator, TIntermTyped*, const TSourceLoc&, bool subset);
     TIntermTyped* constructBuiltIn(const TType&, TOperator, TIntermTyped*, const TSourceLoc&, bool subset);
     void declareBlock(const TSourceLoc&, TType&, const TString* instanceName = 0, TArraySizes* arraySizes = 0);
     void declareBlock(const TSourceLoc&, TType&, const TString* instanceName = 0, TArraySizes* arraySizes = 0);
-    void finalizeGlobalUniformBlockLayout(TVariable& block);
+    void finalizeGlobalUniformBlockLayout(TVariable& block) override;
     void fixBlockLocations(const TSourceLoc&, TQualifier&, TTypeList&, bool memberWithLocation, bool memberWithoutLocation);
     void fixBlockLocations(const TSourceLoc&, TQualifier&, TTypeList&, bool memberWithLocation, bool memberWithoutLocation);
     void fixBlockXfbOffsets(TQualifier&, TTypeList&);
     void fixBlockXfbOffsets(TQualifier&, TTypeList&);
     void fixBlockUniformOffsets(const TQualifier&, TTypeList&);
     void fixBlockUniformOffsets(const TQualifier&, TTypeList&);

+ 11 - 10
3rdparty/glslang/hlsl/hlslScanContext.cpp

@@ -394,13 +394,14 @@ EHlslTokenClass HlslScanContext::tokenizeClass(HlslToken& token)
     do {
     do {
         parserToken = &token;
         parserToken = &token;
         TPpToken ppToken;
         TPpToken ppToken;
-        tokenText = ppContext.tokenize(&ppToken);
-        if (tokenText == nullptr)
+        int token = ppContext.tokenize(ppToken);
+        if (token == EndOfInput)
             return EHTokNone;
             return EHTokNone;
 
 
+        tokenText = ppToken.name;
         loc = ppToken.loc;
         loc = ppToken.loc;
         parserToken->loc = loc;
         parserToken->loc = loc;
-        switch (ppToken.token) {
+        switch (token) {
         case ';':                       return EHTokSemicolon;
         case ';':                       return EHTokSemicolon;
         case ',':                       return EHTokComma;
         case ',':                       return EHTokComma;
         case ':':                       return EHTokColon;
         case ':':                       return EHTokColon;
@@ -429,11 +430,11 @@ EHlslTokenClass HlslScanContext::tokenizeClass(HlslToken& token)
             parseContext.error(loc, "illegal use of escape character", "\\", "");
             parseContext.error(loc, "illegal use of escape character", "\\", "");
             break;
             break;
 
 
-        case PpAtomAdd:                return EHTokAddAssign;
-        case PpAtomSub:                return EHTokSubAssign;
-        case PpAtomMul:                return EHTokMulAssign;
-        case PpAtomDiv:                return EHTokDivAssign;
-        case PpAtomMod:                return EHTokModAssign;
+        case PPAtomAddAssign:          return EHTokAddAssign;
+        case PPAtomSubAssign:          return EHTokSubAssign;
+        case PPAtomMulAssign:          return EHTokMulAssign;
+        case PPAtomDivAssign:          return EHTokDivAssign;
+        case PPAtomModAssign:          return EHTokModAssign;
 
 
         case PpAtomRight:              return EHTokRightOp;
         case PpAtomRight:              return EHTokRightOp;
         case PpAtomLeft:               return EHTokLeftOp;
         case PpAtomLeft:               return EHTokLeftOp;
@@ -467,7 +468,7 @@ EHlslTokenClass HlslScanContext::tokenizeClass(HlslToken& token)
         }
         }
 
 
         case PpAtomConstString: {
         case PpAtomConstString: {
-            parserToken->string = NewPoolTString(ppToken.name);
+            parserToken->string = NewPoolTString(tokenText);
             return EHTokStringConstant;
             return EHTokStringConstant;
         }
         }
 
 
@@ -475,7 +476,7 @@ EHlslTokenClass HlslScanContext::tokenizeClass(HlslToken& token)
 
 
         default:
         default:
             char buf[2];
             char buf[2];
-            buf[0] = (char)ppToken.token;
+            buf[0] = (char)token;
             buf[1] = 0;
             buf[1] = 0;
             parseContext.error(loc, "unexpected token", buf, "");
             parseContext.error(loc, "unexpected token", buf, "");
             break;
             break;