diff --git a/glslang/Include/revision.h b/glslang/Include/revision.h index e8acb4b4188c4354551aa21850bded720688c1f8..d6678ff84cf9a5919f4dc8c757114dedc3ac9958 100644 --- a/glslang/Include/revision.h +++ b/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 date, it uses the current date (when then script is run). -#define GLSLANG_REVISION "Overload400-PrecQual.1899" +#define GLSLANG_REVISION "Overload400-PrecQual.1901" #define GLSLANG_DATE "11-Mar-2017" diff --git a/hlsl/hlslAttributes.h b/hlsl/hlslAttributes.h index 5a7c033d45300a4fdc9b6f66788a068201f85741..e093760cb229bf0d588f574d4e3ee20342f23079 100644 --- a/hlsl/hlslAttributes.h +++ b/hlsl/hlslAttributes.h @@ -92,6 +92,14 @@ namespace glslang { std::unordered_map<TAttributeType, TIntermAggregate*> attributes; }; + + class TFunctionDeclarator { + public: + TSourceLoc loc; + TFunction* function; + TAttributeMap attributes; + }; + } // end namespace glslang diff --git a/hlsl/hlslGrammar.cpp b/hlsl/hlslGrammar.cpp index a5fc9e6d78d6f3dfe03736a0057237d4ea14bc75..39de92e70e2eed438fcb68feee5fa094ee9d00d1 100755 --- a/hlsl/hlslGrammar.cpp +++ b/hlsl/hlslGrammar.cpp @@ -301,8 +301,8 @@ bool HlslGrammar::acceptDeclaration(TIntermNode*& nodeList) bool declarator_list = false; // true when processing comma separation // attributes - TAttributeMap attributes; - acceptAttributes(attributes); + TFunctionDeclarator declarator; + acceptAttributes(declarator.attributes); // typedef bool typedefDecl = acceptTokenClass(EHTokTypedef); @@ -334,26 +334,27 @@ bool HlslGrammar::acceptDeclaration(TIntermNode*& nodeList) parseContext.renameShaderFunction(fnName); // function_parameters - TFunction& function = *new TFunction(fnName, declaredType); - if (!acceptFunctionParameters(function)) { + declarator.function = new TFunction(fnName, declaredType); + if (!acceptFunctionParameters(*declarator.function)) { expected("function parameter list"); return false; } // post_decls - acceptPostDecls(function.getWritableType().getQualifier()); + acceptPostDecls(declarator.function->getWritableType().getQualifier()); // compound_statement (function body definition) or just a prototype? + declarator.loc = token.loc; if (peekTokenClass(EHTokLeftBrace)) { if (declarator_list) parseContext.error(idToken.loc, "function body can't be in a declarator list", "{", ""); if (typedefDecl) parseContext.error(idToken.loc, "function body can't be in a typedef", "{", ""); - return acceptFunctionDefinition(function, nodeList, attributes); + return acceptFunctionDefinition(declarator, nodeList); } else { if (typedefDecl) parseContext.error(idToken.loc, "function typedefs not implemented", "{", ""); - parseContext.handleFunctionDeclarator(idToken.loc, function, true); + parseContext.handleFunctionDeclarator(declarator.loc, *declarator.function, true); } } else { // A variable declaration. Fix the storage qualifier if it's a global. @@ -1962,7 +1963,8 @@ bool HlslGrammar::acceptStructDeclarationList(TTypeList*& typeList, TIntermNode* if (peekTokenClass(EHTokLeftParen)) { // function_parameters if (!declarator_list) { - functionDefinitionAccepted = acceptMemberFunctionDefinition(nodeList, typeName, memberType, *idToken.string); + functionDefinitionAccepted = acceptMemberFunctionDefinition(nodeList, typeName, memberType, + *idToken.string); if (functionDefinitionAccepted) break; } @@ -2029,22 +2031,23 @@ bool HlslGrammar::acceptMemberFunctionDefinition(TIntermNode*& nodeList, const T bool accepted = false; TString* functionName = parseContext.getFullMemberFunctionName(memberName, type.getQualifier().storage == EvqGlobal); - TFunction& function = *new TFunction(functionName, type); + TFunctionDeclarator declarator; + declarator.function = new TFunction(functionName, type); // function_parameters - if (acceptFunctionParameters(function)) { + if (acceptFunctionParameters(*declarator.function)) { // post_decls - acceptPostDecls(function.getWritableType().getQualifier()); + acceptPostDecls(declarator.function->getWritableType().getQualifier()); // compound_statement (function body definition) if (peekTokenClass(EHTokLeftBrace)) { - if (function.getType().getQualifier().storage != EvqGlobal) { + if (declarator.function->getType().getQualifier().storage != EvqGlobal) { expected("only static member functions are accepted"); return false; } - TAttributeMap attributes; - accepted = acceptFunctionDefinition(function, nodeList, attributes); + declarator.loc = token.loc; + accepted = acceptFunctionDefinition(declarator, nodeList); } } else expected("function parameter list"); @@ -2180,17 +2183,21 @@ bool HlslGrammar::acceptParameterDeclaration(TFunction& function) // Do the work to create the function definition in addition to // parsing the body (compound_statement). -bool HlslGrammar::acceptFunctionDefinition(TFunction& function, TIntermNode*& nodeList, const TAttributeMap& attributes) +bool HlslGrammar::acceptFunctionDefinition(TFunctionDeclarator& declarator, TIntermNode*& nodeList) { - TFunction& functionDeclarator = parseContext.handleFunctionDeclarator(token.loc, function, false /* not prototype */); - TSourceLoc loc = token.loc; + parseContext.handleFunctionDeclarator(declarator.loc, *declarator.function, false /* not prototype */); - // we might get back and entry-point + return acceptFunctionBody(declarator, nodeList); +} + +bool HlslGrammar::acceptFunctionBody(TFunctionDeclarator& declarator, TIntermNode*& nodeList) +{ + // we might get back an entry-point TIntermNode* entryPointNode = nullptr; // This does a pushScope() - TIntermNode* functionNode = parseContext.handleFunctionDefinition(loc, functionDeclarator, attributes, - entryPointNode); + TIntermNode* functionNode = parseContext.handleFunctionDefinition(declarator.loc, *declarator.function, + declarator.attributes, entryPointNode); // compound_statement TIntermNode* functionBody = nullptr; @@ -2198,7 +2205,7 @@ bool HlslGrammar::acceptFunctionDefinition(TFunction& function, TIntermNode*& no return false; // this does a popScope() - parseContext.handleFunctionBody(loc, functionDeclarator, functionBody, functionNode); + parseContext.handleFunctionBody(declarator.loc, *declarator.function, functionBody, functionNode); // Hook up the 1 or 2 function definitions. nodeList = intermediate.growAggregate(nodeList, functionNode); diff --git a/hlsl/hlslGrammar.h b/hlsl/hlslGrammar.h index 6da2ea139ef7ac82b6d051064feff9527f47d11f..05b7206b98715bc9d011f0c56097036614c6e186 100755 --- a/hlsl/hlslGrammar.h +++ b/hlsl/hlslGrammar.h @@ -43,7 +43,8 @@ namespace glslang { - class TAttributeMap; // forward declare + class TAttributeMap; + class TFunctionDeclarator; // Should just be the grammar aspect of HLSL. // Described in more detail in hlslGrammar.cpp. @@ -91,7 +92,8 @@ namespace glslang { const TType&, const TString& memberName); bool acceptFunctionParameters(TFunction&); bool acceptParameterDeclaration(TFunction&); - bool acceptFunctionDefinition(TFunction&, TIntermNode*& nodeList, const TAttributeMap&); + bool acceptFunctionDefinition(TFunctionDeclarator&, TIntermNode*& nodeList); + bool acceptFunctionBody(TFunctionDeclarator& declarator, TIntermNode*& nodeList); bool acceptParenExpression(TIntermTyped*&); bool acceptExpression(TIntermTyped*&); bool acceptInitializer(TIntermTyped*&); diff --git a/hlsl/hlslParseHelper.cpp b/hlsl/hlslParseHelper.cpp index e16865e6bc8caf955a24ebdb9a59778a08c758d9..952529802bd1e62520f2cdb01244612b1a59a853 100755 --- a/hlsl/hlslParseHelper.cpp +++ b/hlsl/hlslParseHelper.cpp @@ -1414,7 +1414,7 @@ void HlslParseContext::assignLocations(TVariable& variable) // Handle seeing a function declarator in the grammar. This is the precursor // to recognizing a function prototype or function definition. // -TFunction& HlslParseContext::handleFunctionDeclarator(const TSourceLoc& loc, TFunction& function, bool prototype) +void HlslParseContext::handleFunctionDeclarator(const TSourceLoc& loc, TFunction& function, bool prototype) { // // Multiple declarations of the same function name are allowed. @@ -1442,13 +1442,6 @@ TFunction& HlslParseContext::handleFunctionDeclarator(const TSourceLoc& loc, TFu // other forms of name collisions. if (! symbolTable.insert(function)) error(loc, "function name is redeclaration of existing name", function.getName().c_str(), ""); - - // - // If this is a redeclaration, it could also be a definition, - // in which case, we need to use the parameter names from this one, and not the one that's - // being redeclared. So, pass back this declaration, not the one in the symbol table. - // - return function; } // Add interstage IO variables to the linkage in canonical order. diff --git a/hlsl/hlslParseHelper.h b/hlsl/hlslParseHelper.h index 8f0ea6cb0c489c2fbc986d0f448537c769415a2c..2f6f24c7ecc2e90dc8cb925de21ac36f88039947 100755 --- a/hlsl/hlslParseHelper.h +++ b/hlsl/hlslParseHelper.h @@ -72,7 +72,7 @@ public: TIntermTyped* handleDotDereference(const TSourceLoc&, TIntermTyped* base, const TString& field); bool isBuiltInMethod(const TSourceLoc&, TIntermTyped* base, const TString& field); void assignLocations(TVariable& variable); - TFunction& handleFunctionDeclarator(const TSourceLoc&, TFunction& function, bool prototype); + void handleFunctionDeclarator(const TSourceLoc&, TFunction& function, bool prototype); TIntermAggregate* handleFunctionDefinition(const TSourceLoc&, TFunction&, const TAttributeMap&, TIntermNode*& entryPointTree); TIntermNode* transformEntryPoint(const TSourceLoc&, TFunction&, const TAttributeMap&); void handleFunctionBody(const TSourceLoc&, TFunction&, TIntermNode* functionBody, TIntermNode*& node);