diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/compiler/translator/Compiler.h | 5 | ||||
-rw-r--r-- | src/compiler/translator/OutputHLSL.cpp | 63 | ||||
-rw-r--r-- | src/compiler/translator/OutputHLSL.h | 12 | ||||
-rw-r--r-- | src/compiler/translator/TranslatorHLSL.cpp | 8 | ||||
-rw-r--r-- | src/compiler/translator/UniformHLSL.cpp | 49 | ||||
-rw-r--r-- | src/compiler/translator/UniformHLSL.h | 8 | ||||
-rw-r--r-- | src/compiler/translator/VariableInfo.cpp | 80 | ||||
-rw-r--r-- | src/compiler/translator/util.cpp | 40 | ||||
-rw-r--r-- | src/compiler/translator/util.h | 3 | ||||
-rw-r--r-- | src/libGLESv2/ProgramBinary.cpp | 55 | ||||
-rw-r--r-- | src/libGLESv2/Shader.h | 1 | ||||
-rw-r--r-- | src/libGLESv2/renderer/d3d/DynamicHLSL.cpp | 25 | ||||
-rw-r--r-- | src/libGLESv2/renderer/d3d/DynamicHLSL.h | 2 | ||||
-rw-r--r-- | src/libGLESv2/renderer/d3d/ShaderD3D.cpp | 57 | ||||
-rw-r--r-- | src/libGLESv2/renderer/d3d/ShaderD3D.h | 1 |
15 files changed, 210 insertions, 199 deletions
diff --git a/src/compiler/translator/Compiler.h b/src/compiler/translator/Compiler.h index 6bef5c1a..ca0c1578 100644 --- a/src/compiler/translator/Compiler.h +++ b/src/compiler/translator/Compiler.h @@ -83,6 +83,9 @@ class TCompiler : public TShHandleBase ShShaderOutput getOutputType() const { return outputType; } std::string getBuiltInResourcesString() const { return builtInResourcesString; } + // Get the resources set by InitBuiltInSymbolTable + const ShBuiltInResources& getResources() const; + protected: sh::GLenum getShaderType() const { return shaderType; } // Initialize symbol-table with built-in symbols. @@ -128,8 +131,6 @@ class TCompiler : public TShHandleBase bool limitExpressionComplexity(TIntermNode* root); // Get built-in extensions with default behavior. const TExtensionBehavior& getExtensionBehavior() const; - // Get the resources set by InitBuiltInSymbolTable - const ShBuiltInResources& getResources() const; const ArrayBoundsClamper& getArrayBoundsClamper() const; ShArrayIndexClampingStrategy getArrayIndexClampingStrategy() const; diff --git a/src/compiler/translator/OutputHLSL.cpp b/src/compiler/translator/OutputHLSL.cpp index defb34a2..a5ea7159 100644 --- a/src/compiler/translator/OutputHLSL.cpp +++ b/src/compiler/translator/OutputHLSL.cpp @@ -21,6 +21,7 @@ #include "compiler/translator/util.h" #include "compiler/translator/UniformHLSL.h" #include "compiler/translator/StructureHLSL.h" +#include "compiler/translator/TranslatorHLSL.h" #include <algorithm> #include <cfloat> @@ -29,18 +30,6 @@ namespace sh { -static sh::Attribute MakeAttributeFromType(const TType &type, const TString &name) -{ - sh::Attribute attributeVar; - attributeVar.type = GLVariableType(type); - attributeVar.precision = GLVariablePrecision(type); - attributeVar.name = name.c_str(); - attributeVar.arraySize = static_cast<unsigned int>(type.getArraySize()); - attributeVar.location = type.getLayoutQualifier().location; - - return attributeVar; -} - TString OutputHLSL::TextureFunction::name() const { TString name = "gl_texture"; @@ -105,8 +94,10 @@ bool OutputHLSL::TextureFunction::operator<(const TextureFunction &rhs) const return false; } -OutputHLSL::OutputHLSL(TParseContext &context, const ShBuiltInResources& resources, ShShaderOutput outputType) - : TIntermTraverser(true, true, true), mContext(context), mOutputType(outputType) +OutputHLSL::OutputHLSL(TParseContext &context, TranslatorHLSL *parentTranslator) + : TIntermTraverser(true, true, true), + mContext(context), + mOutputType(parentTranslator->getOutputType()) { mUnfoldShortCircuit = new UnfoldShortCircuit(context, this); mInsideFunction = false; @@ -138,6 +129,7 @@ OutputHLSL::OutputHLSL(TParseContext &context, const ShBuiltInResources& resourc mUsesDiscardRewriting = false; mUsesNestedBreak = false; + const ShBuiltInResources &resources = parentTranslator->getResources(); mNumRenderTargets = resources.EXT_draw_buffers ? resources.MaxDrawBuffers : 1; mUniqueIndex = 0; @@ -150,7 +142,7 @@ OutputHLSL::OutputHLSL(TParseContext &context, const ShBuiltInResources& resourc mExcessiveLoopIndex = NULL; mStructureHLSL = new StructureHLSL; - mUniformHLSL = new UniformHLSL(mStructureHLSL, mOutputType); + mUniformHLSL = new UniformHLSL(mStructureHLSL, parentTranslator); if (mOutputType == SH_HLSL9_OUTPUT) { @@ -224,31 +216,6 @@ TInfoSinkBase &OutputHLSL::getBodyStream() return mBody; } -const std::vector<sh::Uniform> &OutputHLSL::getUniforms() -{ - return mUniformHLSL->getUniforms(); -} - -const std::vector<sh::InterfaceBlock> &OutputHLSL::getInterfaceBlocks() const -{ - return mUniformHLSL->getInterfaceBlocks(); -} - -const std::vector<sh::Attribute> &OutputHLSL::getOutputVariables() const -{ - return mActiveOutputVariables; -} - -const std::vector<sh::Attribute> &OutputHLSL::getAttributes() const -{ - return mActiveAttributes; -} - -const std::vector<sh::Varying> &OutputHLSL::getVaryings() const -{ - return mActiveVaryings; -} - const std::map<std::string, unsigned int> &OutputHLSL::getInterfaceBlockRegisterMap() const { return mUniformHLSL->getInterfaceBlockRegisterMap(); @@ -336,8 +303,6 @@ void OutputHLSL::header() // Program linking depends on this exact format varyings += "static " + InterpolationString(type.getQualifier()) + " " + TypeString(type) + " " + Decorate(name) + ArrayString(type) + " = " + initializer(type) + ";\n"; - - declareVaryingToList(type, type.getQualifier(), name, mActiveVaryings); } for (ReferencedSymbols::const_iterator attribute = mReferencedAttributes.begin(); attribute != mReferencedAttributes.end(); attribute++) @@ -346,9 +311,6 @@ void OutputHLSL::header() const TString &name = attribute->second->getSymbol(); attributes += "static " + TypeString(type) + " " + Decorate(name) + ArrayString(type) + " = " + initializer(type) + ";\n"; - - sh::Attribute attributeVar = MakeAttributeFromType(type, name); - mActiveAttributes.push_back(attributeVar); } out << mStructureHLSL->structsHeader(); @@ -384,9 +346,6 @@ void OutputHLSL::header() out << "static " + TypeString(variableType) + " out_" + variableName + ArrayString(variableType) + " = " + initializer(variableType) + ";\n"; - - sh::Attribute outputVar = MakeAttributeFromType(variableType, variableName); - mActiveOutputVariables.push_back(outputVar); } } else @@ -2922,12 +2881,4 @@ const ConstantUnion *OutputHLSL::writeConstantUnion(const TType &type, const Con return constUnion; } -void OutputHLSL::declareVaryingToList(const TType &type, TQualifier baseTypeQualifier, - const TString &name, std::vector<Varying> &fieldsOut) -{ - GetVariableTraverser traverser; - traverser.traverse(type, name, &fieldsOut); - fieldsOut.back().interpolation = GetInterpolationType(baseTypeQualifier); -} - } diff --git a/src/compiler/translator/OutputHLSL.h b/src/compiler/translator/OutputHLSL.h index 61afc41a..bec02479 100644 --- a/src/compiler/translator/OutputHLSL.h +++ b/src/compiler/translator/OutputHLSL.h @@ -27,17 +27,12 @@ typedef std::map<TString, TIntermSymbol*> ReferencedSymbols; class OutputHLSL : public TIntermTraverser { public: - OutputHLSL(TParseContext &context, const ShBuiltInResources& resources, ShShaderOutput outputType); + OutputHLSL(TParseContext &context, TranslatorHLSL *parentTranslator); ~OutputHLSL(); void output(); TInfoSinkBase &getBodyStream(); - const std::vector<sh::Uniform> &getUniforms(); - const std::vector<sh::InterfaceBlock> &getInterfaceBlocks() const; - const std::vector<sh::Attribute> &getOutputVariables() const; - const std::vector<sh::Attribute> &getAttributes() const; - const std::vector<sh::Varying> &getVaryings() const; const std::map<std::string, unsigned int> &getInterfaceBlockRegisterMap() const; const std::map<std::string, unsigned int> &getUniformRegisterMap() const; @@ -155,13 +150,8 @@ class OutputHLSL : public TIntermTraverser TIntermSymbol *mExcessiveLoopIndex; - void declareVaryingToList(const TType &type, TQualifier baseTypeQualifier, const TString &name, std::vector<sh::Varying>& fieldsOut); - TString structInitializerString(int indent, const TStructure &structure, const TString &rhsStructName); - std::vector<sh::Attribute> mActiveOutputVariables; - std::vector<sh::Attribute> mActiveAttributes; - std::vector<sh::Varying> mActiveVaryings; std::map<TIntermTyped*, TString> mFlaggedStructMappedNames; std::map<TIntermTyped*, TString> mFlaggedStructOriginalNames; diff --git a/src/compiler/translator/TranslatorHLSL.cpp b/src/compiler/translator/TranslatorHLSL.cpp index 52588e46..22bf60e8 100644 --- a/src/compiler/translator/TranslatorHLSL.cpp +++ b/src/compiler/translator/TranslatorHLSL.cpp @@ -17,16 +17,10 @@ TranslatorHLSL::TranslatorHLSL(sh::GLenum type, ShShaderSpec spec, ShShaderOutpu void TranslatorHLSL::translate(TIntermNode *root) { TParseContext& parseContext = *GetGlobalParseContext(); - sh::OutputHLSL outputHLSL(parseContext, getResources(), getOutputType()); + sh::OutputHLSL outputHLSL(parseContext, this); outputHLSL.output(); - attributes = outputHLSL.getAttributes(); - outputVariables = outputHLSL.getOutputVariables(); - uniforms = outputHLSL.getUniforms(); - varyings = outputHLSL.getVaryings(); - interfaceBlocks = outputHLSL.getInterfaceBlocks(); - mInterfaceBlockRegisterMap = outputHLSL.getInterfaceBlockRegisterMap(); mUniformRegisterMap = outputHLSL.getUniformRegisterMap(); } diff --git a/src/compiler/translator/UniformHLSL.cpp b/src/compiler/translator/UniformHLSL.cpp index 2c99a904..61b6ed74 100644 --- a/src/compiler/translator/UniformHLSL.cpp +++ b/src/compiler/translator/UniformHLSL.cpp @@ -14,6 +14,7 @@ #include "compiler/translator/StructureHLSL.h" #include "compiler/translator/util.h" #include "compiler/translator/UtilsHLSL.h" +#include "compiler/translator/TranslatorHLSL.h" namespace sh { @@ -60,12 +61,13 @@ static TString InterfaceBlockStructName(const TInterfaceBlock &interfaceBlock) return DecoratePrivate(interfaceBlock.name()) + "_type"; } -UniformHLSL::UniformHLSL(StructureHLSL *structureHLSL, ShShaderOutput outputType) +UniformHLSL::UniformHLSL(StructureHLSL *structureHLSL, TranslatorHLSL *translator) : mUniformRegister(0), mInterfaceBlockRegister(0), mSamplerRegister(0), mStructureHLSL(structureHLSL), - mOutputType(outputType) + mOutputType(translator->getOutputType()), + mUniforms(translator->getUniforms()) {} void UniformHLSL::reserveUniformRegisters(unsigned int registerCount) @@ -78,18 +80,32 @@ void UniformHLSL::reserveInterfaceBlockRegisters(unsigned int registerCount) mInterfaceBlockRegister = registerCount; } +const Uniform *UniformHLSL::findUniformByName(const TString &name) const +{ + for (size_t uniformIndex = 0; uniformIndex < mUniforms.size(); ++uniformIndex) + { + if (mUniforms[uniformIndex].name == name.c_str()) + { + return &mUniforms[uniformIndex]; + } + } + + UNREACHABLE(); + return NULL; +} + unsigned int UniformHLSL::declareUniformAndAssignRegister(const TType &type, const TString &name) { unsigned int registerIndex = (IsSampler(type.getBasicType()) ? mSamplerRegister : mUniformRegister); - GetVariableTraverser traverser; - traverser.traverse(type, name, &mActiveUniforms); + const Uniform *uniform = findUniformByName(name); + ASSERT(uniform); - const sh::Uniform &activeUniform = mActiveUniforms.back(); - mUniformRegisterMap[activeUniform.name] = registerIndex; + mUniformRegisterMap[uniform->name] = registerIndex; - unsigned int registerCount = HLSLVariableRegisterCount(activeUniform, mOutputType); - if (IsSampler(type.getBasicType())) + unsigned int registerCount = HLSLVariableRegisterCount(*uniform, mOutputType); + + if (gl::IsSampler(uniform->type)) { mSamplerRegister += registerCount; } @@ -154,23 +170,10 @@ TString UniformHLSL::interfaceBlocksHeader(const ReferencedSymbols &referencedIn unsigned int arraySize = static_cast<unsigned int>(interfaceBlock.arraySize()); unsigned int activeRegister = mInterfaceBlockRegister; - InterfaceBlock activeBlock; - activeBlock.name = interfaceBlock.name().c_str(); - activeBlock.arraySize = arraySize; - - GetInterfaceBlockFields(interfaceBlock, &activeBlock.fields); - - mInterfaceBlockRegisterMap[activeBlock.name] = activeRegister; + mInterfaceBlockRegisterMap[interfaceBlock.name().c_str()] = activeRegister; mInterfaceBlockRegister += std::max(1u, arraySize); - activeBlock.layout = GetBlockLayoutType(interfaceBlock.blockStorage()); - - if (interfaceBlock.matrixPacking() == EmpRowMajor) - { - activeBlock.isRowMajorLayout = true; - } - - mActiveInterfaceBlocks.push_back(activeBlock); + // FIXME: interface block field names if (interfaceBlock.hasInstanceName()) { diff --git a/src/compiler/translator/UniformHLSL.h b/src/compiler/translator/UniformHLSL.h index d61457d2..91fa5158 100644 --- a/src/compiler/translator/UniformHLSL.h +++ b/src/compiler/translator/UniformHLSL.h @@ -19,7 +19,7 @@ class StructureHLSL; class UniformHLSL { public: - UniformHLSL(StructureHLSL *structureHLSL, ShShaderOutput outputType); + UniformHLSL(StructureHLSL *structureHLSL, TranslatorHLSL *translator); void reserveUniformRegisters(unsigned int registerCount); void reserveInterfaceBlockRegisters(unsigned int registerCount); @@ -29,8 +29,6 @@ class UniformHLSL // Used for direct index references static TString interfaceBlockInstanceString(const TInterfaceBlock& interfaceBlock, unsigned int arrayIndex); - const std::vector<Uniform> &getUniforms() const { return mActiveUniforms; } - const std::vector<InterfaceBlock> &getInterfaceBlocks() const { return mActiveInterfaceBlocks; } const std::map<std::string, unsigned int> &getInterfaceBlockRegisterMap() const { return mInterfaceBlockRegisterMap; @@ -44,6 +42,7 @@ class UniformHLSL TString interfaceBlockString(const TInterfaceBlock &interfaceBlock, unsigned int registerIndex, unsigned int arrayIndex); TString interfaceBlockMembersString(const TInterfaceBlock &interfaceBlock, TLayoutBlockStorage blockStorage); TString interfaceBlockStructString(const TInterfaceBlock &interfaceBlock); + const Uniform *findUniformByName(const TString &name) const; // Returns the uniform's register index unsigned int declareUniformAndAssignRegister(const TType &type, const TString &name); @@ -54,8 +53,7 @@ class UniformHLSL StructureHLSL *mStructureHLSL; ShShaderOutput mOutputType; - std::vector<Uniform> mActiveUniforms; - std::vector<InterfaceBlock> mActiveInterfaceBlocks; + const std::vector<Uniform> &mUniforms; std::map<std::string, unsigned int> mInterfaceBlockRegisterMap; std::map<std::string, unsigned int> mUniformRegisterMap; }; diff --git a/src/compiler/translator/VariableInfo.cpp b/src/compiler/translator/VariableInfo.cpp index b023c29c..d58770f2 100644 --- a/src/compiler/translator/VariableInfo.cpp +++ b/src/compiler/translator/VariableInfo.cpp @@ -9,17 +9,43 @@ #include "compiler/translator/util.h" #include "common/utilities.h" -static void ExpandUserDefinedVariable(const sh::ShaderVariable &variable, - const std::string &name, - const std::string &mappedName, - bool markStaticUse, - std::vector<sh::ShaderVariable> *expanded); - -static void ExpandVariable(const sh::ShaderVariable &variable, - const std::string &name, - const std::string &mappedName, - bool markStaticUse, - std::vector<sh::ShaderVariable> *expanded) +namespace +{ + +TString InterfaceBlockFieldName(const TInterfaceBlock &interfaceBlock, const TField &field) +{ + if (interfaceBlock.hasInstanceName()) + { + return interfaceBlock.name() + "." + field.name(); + } + else + { + return field.name(); + } +} + +sh::BlockLayoutType GetBlockLayoutType(TLayoutBlockStorage blockStorage) +{ + switch (blockStorage) + { + case EbsPacked: return sh::BLOCKLAYOUT_PACKED; + case EbsShared: return sh::BLOCKLAYOUT_SHARED; + case EbsStd140: return sh::BLOCKLAYOUT_STANDARD; + default: UNREACHABLE(); return sh::BLOCKLAYOUT_SHARED; + } +} + +void ExpandUserDefinedVariable(const sh::ShaderVariable &variable, + const std::string &name, + const std::string &mappedName, + bool markStaticUse, + std::vector<sh::ShaderVariable> *expanded); + +void ExpandVariable(const sh::ShaderVariable &variable, + const std::string &name, + const std::string &mappedName, + bool markStaticUse, + std::vector<sh::ShaderVariable> *expanded) { if (variable.isStruct()) { @@ -60,11 +86,11 @@ static void ExpandVariable(const sh::ShaderVariable &variable, } } -static void ExpandUserDefinedVariable(const sh::ShaderVariable &variable, - const std::string &name, - const std::string &mappedName, - bool markStaticUse, - std::vector<sh::ShaderVariable> *expanded) +void ExpandUserDefinedVariable(const sh::ShaderVariable &variable, + const std::string &name, + const std::string &mappedName, + bool markStaticUse, + std::vector<sh::ShaderVariable> *expanded) { ASSERT(variable.isStruct()); @@ -82,8 +108,8 @@ static void ExpandUserDefinedVariable(const sh::ShaderVariable &variable, } template <class VarT> -static VarT *FindVariable(const TString &name, - std::vector<VarT> *infoList) +VarT *FindVariable(const TString &name, + std::vector<VarT> *infoList) { // TODO(zmo): optimize this function. for (size_t ii = 0; ii < infoList->size(); ++ii) @@ -95,6 +121,8 @@ static VarT *FindVariable(const TString &name, return NULL; } +} + CollectVariables::CollectVariables(std::vector<sh::Attribute> *attribs, std::vector<sh::Attribute> *outputVariables, std::vector<sh::Uniform> *uniforms, @@ -270,10 +298,22 @@ void CollectVariables::visitVariable(const TIntermSymbol *variable, interfaceBlock.instanceName = (blockType->hasInstanceName() ? blockType->instanceName().c_str() : ""); interfaceBlock.arraySize = variable->getArraySize(); interfaceBlock.isRowMajorLayout = (blockType->matrixPacking() == EmpRowMajor); - interfaceBlock.layout = sh::GetBlockLayoutType(blockType->blockStorage()); + interfaceBlock.layout = GetBlockLayoutType(blockType->blockStorage()); // Gather field information - sh::GetInterfaceBlockFields(*blockType, &interfaceBlock.fields); + const TFieldList &fieldList = blockType->fields(); + + for (size_t fieldIndex = 0; fieldIndex < fieldList.size(); ++fieldIndex) + { + const TField &field = *fieldList[fieldIndex]; + const TString &fullFieldName = InterfaceBlockFieldName(*blockType, field); + const TType &fieldType = *field.type(); + + sh::GetVariableTraverser traverser; + traverser.traverse(fieldType, fullFieldName, &interfaceBlock.fields); + + interfaceBlock.fields.back().isRowMajorLayout = (fieldType.getLayoutQualifier().matrixPacking == EmpRowMajor); + } infoList->push_back(interfaceBlock); } diff --git a/src/compiler/translator/util.cpp b/src/compiler/translator/util.cpp index 40c90d8f..f74c7d11 100644 --- a/src/compiler/translator/util.cpp +++ b/src/compiler/translator/util.cpp @@ -320,44 +320,4 @@ template void GetVariableTraverser::traverse(const TType &, const TString &, std template void GetVariableTraverser::traverse(const TType &, const TString &, std::vector<Varying> *); template void GetVariableTraverser::traverse(const TType &, const TString &, std::vector<InterfaceBlockField> *); -BlockLayoutType GetBlockLayoutType(TLayoutBlockStorage blockStorage) -{ - switch (blockStorage) - { - case EbsPacked: return BLOCKLAYOUT_PACKED; - case EbsShared: return BLOCKLAYOUT_SHARED; - case EbsStd140: return BLOCKLAYOUT_STANDARD; - default: UNREACHABLE(); return BLOCKLAYOUT_SHARED; - } -} - -static TString InterfaceBlockFieldName(const TInterfaceBlock &interfaceBlock, const TField &field) -{ - if (interfaceBlock.hasInstanceName()) - { - return interfaceBlock.name() + "." + field.name(); - } - else - { - return field.name(); - } -} - -void GetInterfaceBlockFields(const TInterfaceBlock &interfaceBlock, std::vector<InterfaceBlockField> *fieldsOut) -{ - const TFieldList &fieldList = interfaceBlock.fields(); - - for (size_t fieldIndex = 0; fieldIndex < fieldList.size(); ++fieldIndex) - { - const TField &field = *fieldList[fieldIndex]; - const TString &fullFieldName = InterfaceBlockFieldName(interfaceBlock, field); - const TType &fieldType = *field.type(); - - GetVariableTraverser traverser; - traverser.traverse(fieldType, fullFieldName, fieldsOut); - - fieldsOut->back().isRowMajorLayout = (fieldType.getLayoutQualifier().matrixPacking == EmpRowMajor); - } -} - } diff --git a/src/compiler/translator/util.h b/src/compiler/translator/util.h index 6a39d564..241e2cc1 100644 --- a/src/compiler/translator/util.h +++ b/src/compiler/translator/util.h @@ -33,7 +33,6 @@ bool IsVaryingIn(TQualifier qualifier); bool IsVaryingOut(TQualifier qualifier); bool IsVarying(TQualifier qualifier); InterpolationType GetInterpolationType(TQualifier qualifier); -BlockLayoutType GetBlockLayoutType(TLayoutBlockStorage blockStorage); TString ArrayString(const TType &type); class GetVariableTraverser @@ -52,8 +51,6 @@ class GetVariableTraverser DISALLOW_COPY_AND_ASSIGN(GetVariableTraverser); }; -void GetInterfaceBlockFields(const TInterfaceBlock &interfaceBlock, std::vector<InterfaceBlockField> *fieldsOut); - } #endif // COMPILER_UTIL_H diff --git a/src/libGLESv2/ProgramBinary.cpp b/src/libGLESv2/ProgramBinary.cpp index 65b3c14e..97672759 100644 --- a/src/libGLESv2/ProgramBinary.cpp +++ b/src/libGLESv2/ProgramBinary.cpp @@ -1068,6 +1068,12 @@ bool ProgramBinary::linkVaryings(InfoLog &infoLog, Shader *fragmentShader, Shade PackedVarying *input = &fragmentVaryings[fragVaryingIndex]; bool matched = false; + // Built-in varyings obey special rules + if (input->isBuiltIn()) + { + continue; + } + for (size_t vertVaryingIndex = 0; vertVaryingIndex < vertexVaryings.size(); vertVaryingIndex++) { PackedVarying *output = &vertexVaryings[vertVaryingIndex]; @@ -1085,7 +1091,8 @@ bool ProgramBinary::linkVaryings(InfoLog &infoLog, Shader *fragmentShader, Shade } } - if (!matched) + // We permit unmatched, unreferenced varyings + if (!matched && input->staticUse) { infoLog.append("Fragment varying %s does not match any vertex varying", input->name.c_str()); return false; @@ -1721,12 +1728,15 @@ bool ProgramBinary::linkAttributes(InfoLog &infoLog, const AttributeBindings &at const rx::ShaderD3D *vertexShaderD3D = rx::ShaderD3D::makeShaderD3D(vertexShader->getImplementation()); unsigned int usedLocations = 0; - const std::vector<sh::Attribute> &activeAttributes = vertexShader->getActiveAttributes(); + const std::vector<sh::Attribute> &shaderAttributes = vertexShader->getActiveAttributes(); // Link attributes that have a binding location - for (unsigned int attributeIndex = 0; attributeIndex < activeAttributes.size(); attributeIndex++) + for (unsigned int attributeIndex = 0; attributeIndex < shaderAttributes.size(); attributeIndex++) { - const sh::Attribute &attribute = activeAttributes[attributeIndex]; + const sh::Attribute &attribute = shaderAttributes[attributeIndex]; + + ASSERT(attribute.staticUse); + const int location = attribute.location == -1 ? attributeBindings.getAttributeBinding(attribute.name) : attribute.location; mShaderAttributes[attributeIndex] = attribute; @@ -1765,9 +1775,12 @@ bool ProgramBinary::linkAttributes(InfoLog &infoLog, const AttributeBindings &at } // Link attributes that don't have a binding location - for (unsigned int attributeIndex = 0; attributeIndex < activeAttributes.size(); attributeIndex++) + for (unsigned int attributeIndex = 0; attributeIndex < shaderAttributes.size(); attributeIndex++) { - const sh::Attribute &attribute = activeAttributes[attributeIndex]; + const sh::Attribute &attribute = shaderAttributes[attributeIndex]; + + ASSERT(attribute.staticUse); + const int location = attribute.location == -1 ? attributeBindings.getAttributeBinding(attribute.name) : attribute.location; if (location == -1) // Not set by glBindAttribLocation or by location layout qualifier @@ -1930,13 +1943,21 @@ bool ProgramBinary::linkUniforms(InfoLog &infoLog, const Shader &vertexShader, c for (unsigned int uniformIndex = 0; uniformIndex < vertexUniforms.size(); uniformIndex++) { const sh::Uniform &uniform = vertexUniforms[uniformIndex]; - defineUniformBase(GL_VERTEX_SHADER, uniform, vertexShaderD3D->getUniformRegister(uniform.name)); + + if (uniform.staticUse) + { + defineUniformBase(GL_VERTEX_SHADER, uniform, vertexShaderD3D->getUniformRegister(uniform.name)); + } } for (unsigned int uniformIndex = 0; uniformIndex < fragmentUniforms.size(); uniformIndex++) { const sh::Uniform &uniform = fragmentUniforms[uniformIndex]; - defineUniformBase(GL_FRAGMENT_SHADER, uniform, fragmentShaderD3D->getUniformRegister(uniform.name)); + + if (uniform.staticUse) + { + defineUniformBase(GL_FRAGMENT_SHADER, uniform, fragmentShaderD3D->getUniformRegister(uniform.name)); + } } if (!indexUniforms(infoLog, caps)) @@ -2197,17 +2218,27 @@ bool ProgramBinary::linkUniformBlocks(InfoLog &infoLog, const Shader &vertexShad for (unsigned int blockIndex = 0; blockIndex < vertexInterfaceBlocks.size(); blockIndex++) { - if (!defineUniformBlock(infoLog, vertexShader, vertexInterfaceBlocks[blockIndex], caps)) + const sh::InterfaceBlock &interfaceBlock = vertexInterfaceBlocks[blockIndex]; + + if (interfaceBlock.staticUse) { - return false; + if (!defineUniformBlock(infoLog, vertexShader, interfaceBlock, caps)) + { + return false; + } } } for (unsigned int blockIndex = 0; blockIndex < fragmentInterfaceBlocks.size(); blockIndex++) { - if (!defineUniformBlock(infoLog, fragmentShader, fragmentInterfaceBlocks[blockIndex], caps)) + const sh::InterfaceBlock &interfaceBlock = fragmentInterfaceBlocks[blockIndex]; + + if (interfaceBlock.staticUse) { - return false; + if (!defineUniformBlock(infoLog, fragmentShader, interfaceBlock, caps)) + { + return false; + } } } diff --git a/src/libGLESv2/Shader.h b/src/libGLESv2/Shader.h index 44f0500d..f28b805b 100644 --- a/src/libGLESv2/Shader.h +++ b/src/libGLESv2/Shader.h @@ -42,6 +42,7 @@ struct PackedVarying : public sh::Varying {} bool registerAssigned() const { return registerIndex != GL_INVALID_INDEX; } + bool isBuiltIn() const { return name.compare(0, 3, "gl_") == 0; } void resetRegisterAssignment() { diff --git a/src/libGLESv2/renderer/d3d/DynamicHLSL.cpp b/src/libGLESv2/renderer/d3d/DynamicHLSL.cpp index 404525ce..6aa0d137 100644 --- a/src/libGLESv2/renderer/d3d/DynamicHLSL.cpp +++ b/src/libGLESv2/renderer/d3d/DynamicHLSL.cpp @@ -223,6 +223,13 @@ int DynamicHLSL::packVaryings(InfoLog &infoLog, VaryingPacking packing, rx::Shad for (unsigned int varyingIndex = 0; varyingIndex < fragmentVaryings.size(); varyingIndex++) { PackedVarying *varying = &fragmentVaryings[varyingIndex]; + + // Do not assign registers to built-in or unreferenced varyings + if (varying->isBuiltIn() || !varying->staticUse) + { + continue; + } + if (packVarying(varying, maxVaryingVectors, packing)) { packedVaryings.insert(varying->name); @@ -278,17 +285,19 @@ int DynamicHLSL::packVaryings(InfoLog &infoLog, VaryingPacking packing, rx::Shad return registers; } -std::string DynamicHLSL::generateVaryingHLSL(rx::ShaderD3D *shader) const +std::string DynamicHLSL::generateVaryingHLSL(const ShaderD3D *shader) const { std::string varyingSemantic = getVaryingSemantic(shader->mUsesPointSize); std::string varyingHLSL; - std::vector<gl::PackedVarying> &varyings = shader->getVaryings(); + const std::vector<gl::PackedVarying> &varyings = shader->getVaryings(); + for (unsigned int varyingIndex = 0; varyingIndex < varyings.size(); varyingIndex++) { const PackedVarying &varying = varyings[varyingIndex]; if (varying.registerAssigned()) { + ASSERT(!varying.isBuiltIn()); GLenum transposedType = TransposeMatrixType(varying.type); int variableRows = (varying.isStruct() ? 1 : VariableRowCount(transposedType)); @@ -616,8 +625,10 @@ void DynamicHLSL::storeUserLinkedVaryings(const rx::ShaderD3D *vertexShader, for (unsigned int varyingIndex = 0; varyingIndex < varyings.size(); varyingIndex++) { const PackedVarying &varying = varyings[varyingIndex]; + if (varying.registerAssigned()) { + ASSERT(!varying.isBuiltIn()); GLenum transposedType = TransposeMatrixType(varying.type); int variableRows = (varying.isStruct() ? 1 : VariableRowCount(transposedType)); @@ -825,6 +836,8 @@ bool DynamicHLSL::generateShaderLinkHLSL(InfoLog &infoLog, int registers, const const std::string &variableName = "out_" + outputLocation.name; const std::string &elementString = (outputLocation.element == GL_INVALID_INDEX ? "" : Str(outputLocation.element)); + ASSERT(outputVariable.staticUse); + PixelShaderOuputVariable outputKeyVariable; outputKeyVariable.type = outputVariable.type; outputKeyVariable.name = variableName + elementString; @@ -907,6 +920,7 @@ bool DynamicHLSL::generateShaderLinkHLSL(InfoLog &infoLog, int registers, const const PackedVarying &varying = fragmentVaryings[varyingIndex]; if (varying.registerAssigned()) { + ASSERT(!varying.isBuiltIn()); for (unsigned int elementIndex = 0; elementIndex < varying.elementCount(); elementIndex++) { GLenum transposedType = TransposeMatrixType(varying.type); @@ -944,7 +958,10 @@ bool DynamicHLSL::generateShaderLinkHLSL(InfoLog &infoLog, int registers, const } } } - else UNREACHABLE(); + else + { + ASSERT(varying.isBuiltIn() || !varying.staticUse); + } } pixelHLSL += "\n" @@ -965,6 +982,8 @@ void DynamicHLSL::defineOutputVariables(rx::ShaderD3D *fragmentShader, std::map< const sh::Attribute &outputVariable = shaderOutputVars[outputVariableIndex]; const int baseLocation = outputVariable.location == -1 ? 0 : outputVariable.location; + ASSERT(outputVariable.staticUse); + if (outputVariable.arraySize > 0) { for (unsigned int elementIndex = 0; elementIndex < outputVariable.arraySize; elementIndex++) diff --git a/src/libGLESv2/renderer/d3d/DynamicHLSL.h b/src/libGLESv2/renderer/d3d/DynamicHLSL.h index cf619952..6242012f 100644 --- a/src/libGLESv2/renderer/d3d/DynamicHLSL.h +++ b/src/libGLESv2/renderer/d3d/DynamicHLSL.h @@ -87,7 +87,7 @@ class DynamicHLSL SemanticInfo getSemanticInfo(int startRegisters, bool fragCoord, bool pointCoord, bool pointSize, bool pixelShader) const; std::string generateVaryingLinkHLSL(const SemanticInfo &info, const std::string &varyingHLSL) const; - std::string generateVaryingHLSL(rx::ShaderD3D *shader) const; + std::string generateVaryingHLSL(const ShaderD3D *shader) const; void storeUserLinkedVaryings(const rx::ShaderD3D *vertexShader, std::vector<gl::LinkedVarying> *linkedVaryings) const; void storeBuiltinLinkedVaryings(const SemanticInfo &info, std::vector<gl::LinkedVarying> *linkedVaryings) const; void defineOutputVariables(rx::ShaderD3D *fragmentShader, std::map<int, gl::VariableLocation> *programOutputVars) const; diff --git a/src/libGLESv2/renderer/d3d/ShaderD3D.cpp b/src/libGLESv2/renderer/d3d/ShaderD3D.cpp index a6d5266a..57edb290 100644 --- a/src/libGLESv2/renderer/d3d/ShaderD3D.cpp +++ b/src/libGLESv2/renderer/d3d/ShaderD3D.cpp @@ -16,13 +16,30 @@ namespace rx { +template <typename VarT> +void FilterInactiveVariables(std::vector<VarT> *variableList) +{ + ASSERT(variableList); + + for (size_t varIndex = 0; varIndex < variableList->size();) + { + if (!(*variableList)[varIndex].staticUse) + { + variableList->erase(variableList->begin() + varIndex); + } + else + { + varIndex++; + } + } +} + void *ShaderD3D::mFragmentCompiler = NULL; void *ShaderD3D::mVertexCompiler = NULL; template <typename VarT> const std::vector<VarT> *GetShaderVariables(const std::vector<VarT> *variableList) { - // TODO: handle staticUse. for now, assume all returned variables are active. ASSERT(variableList); return variableList; } @@ -111,12 +128,12 @@ void ShaderD3D::parseVaryings(void *compiler) { if (!mHlsl.empty()) { - const std::vector<sh::Varying> *activeVaryings = ShGetVaryings(compiler); - ASSERT(activeVaryings); + const std::vector<sh::Varying> *varyings = ShGetVaryings(compiler); + ASSERT(varyings); - for (size_t varyingIndex = 0; varyingIndex < activeVaryings->size(); varyingIndex++) + for (size_t varyingIndex = 0; varyingIndex < varyings->size(); varyingIndex++) { - mVaryings.push_back(gl::PackedVarying((*activeVaryings)[varyingIndex])); + mVaryings.push_back(gl::PackedVarying((*varyings)[varyingIndex])); } mUsesMultipleRenderTargets = mHlsl.find("GL_USES_MRT") != std::string::npos; @@ -173,7 +190,7 @@ void ShaderD3D::compileToHLSL(void *compiler, const std::string &source) // ensure the compiler is loaded initializeCompiler(); - int compileOptions = SH_OBJECT_CODE; + int compileOptions = (SH_OBJECT_CODE | SH_VARIABLES); std::string sourcePath; if (gl::perfActive()) { @@ -251,12 +268,15 @@ void ShaderD3D::compileToHLSL(void *compiler, const std::string &source) { const sh::Uniform &uniform = mUniforms[uniformIndex]; - unsigned int index = -1; - bool result = ShGetUniformRegister(compiler, uniform.name.c_str(), &index); - UNUSED_ASSERTION_VARIABLE(result); - ASSERT(result); + if (uniform.staticUse) + { + unsigned int index = -1; + bool result = ShGetUniformRegister(compiler, uniform.name.c_str(), &index); + UNUSED_ASSERTION_VARIABLE(result); + ASSERT(result); - mUniformRegisterMap[uniform.name] = index; + mUniformRegisterMap[uniform.name] = index; + } } mInterfaceBlocks = *GetShaderVariables(ShGetInterfaceBlocks(compiler)); @@ -265,12 +285,15 @@ void ShaderD3D::compileToHLSL(void *compiler, const std::string &source) { const sh::InterfaceBlock &interfaceBlock = mInterfaceBlocks[blockIndex]; - unsigned int index = -1; - bool result = ShGetInterfaceBlockRegister(compiler, interfaceBlock.name.c_str(), &index); - UNUSED_ASSERTION_VARIABLE(result); - ASSERT(result); + if (interfaceBlock.staticUse) + { + unsigned int index = -1; + bool result = ShGetInterfaceBlockRegister(compiler, interfaceBlock.name.c_str(), &index); + UNUSED_ASSERTION_VARIABLE(result); + ASSERT(result); - mInterfaceBlockRegisterMap[interfaceBlock.name] = index; + mInterfaceBlockRegisterMap[interfaceBlock.name] = index; + } } } else @@ -393,6 +416,7 @@ bool ShaderD3D::compile(const std::string &source) if (!hlsl.empty()) { mActiveOutputVariables = *GetShaderVariables(ShGetOutputVariables(compiler)); + FilterInactiveVariables(&mActiveOutputVariables); } } @@ -405,6 +429,7 @@ void ShaderD3D::parseAttributes(void *compiler) if (!hlsl.empty()) { mActiveAttributes = *GetShaderVariables(ShGetAttributes(compiler)); + FilterInactiveVariables(&mActiveAttributes); } } diff --git a/src/libGLESv2/renderer/d3d/ShaderD3D.h b/src/libGLESv2/renderer/d3d/ShaderD3D.h index 9f7dc0b8..40e64cf3 100644 --- a/src/libGLESv2/renderer/d3d/ShaderD3D.h +++ b/src/libGLESv2/renderer/d3d/ShaderD3D.h @@ -16,6 +16,7 @@ namespace rx { +class DynamicHLSL; class Renderer; class ShaderD3D : public ShaderImpl |