forked from qt-creator/qt-creator
GLSL AST nodes for function and struct decls
This commit is contained in:
@@ -292,7 +292,8 @@ public:
|
||||
Type *type;
|
||||
const std::string *name;
|
||||
} param_declarator;
|
||||
// ### ast nodes...
|
||||
ParameterDeclaration *param_declaration;
|
||||
FunctionDeclaration *function_declaration;
|
||||
};
|
||||
|
||||
Parser(Engine *engine, const char *source, unsigned size, int variant);
|
||||
@@ -308,6 +309,7 @@ private:
|
||||
Expression *&expression(int n) { return _symStack[_tos + n - 1].expression; }
|
||||
Statement *&statement(int n) { return _symStack[_tos + n - 1].statement; }
|
||||
Type *&type(int n) { return _symStack[_tos + n - 1].type; }
|
||||
FunctionDeclaration *&function(int n) { return _symStack[_tos + n - 1].function_declaration; }
|
||||
|
||||
inline int consumeToken() { return _index++; }
|
||||
inline const Token &tokenAt(int index) const { return _tokens.at(index); }
|
||||
@@ -1123,7 +1125,7 @@ case $rule_number: {
|
||||
declaration ::= function_prototype SEMICOLON ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
// nothing to do.
|
||||
} break;
|
||||
./
|
||||
|
||||
@@ -1144,77 +1146,124 @@ case $rule_number: {
|
||||
declaration ::= type_qualifier IDENTIFIER LEFT_BRACE struct_declaration_list RIGHT_BRACE SEMICOLON ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
if (sym(1).type_qualifier.qualifier != QualifiedType::Struct) {
|
||||
// TODO: issue an error if the qualifier is not "struct".
|
||||
}
|
||||
Type *type = makeAstNode<StructType>(string(2), sym(4).field_list);
|
||||
ast(1) = makeAstNode<TypeDeclaration>(type);
|
||||
} break;
|
||||
./
|
||||
|
||||
declaration ::= type_qualifier IDENTIFIER LEFT_BRACE struct_declaration_list RIGHT_BRACE IDENTIFIER SEMICOLON ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
if ((sym(1).type_qualifier.qualifier & QualifiedType::Struct) == 0) {
|
||||
// TODO: issue an error if the qualifier does not contain "struct".
|
||||
}
|
||||
Type *type = makeAstNode<StructType>(string(2), sym(4).field_list);
|
||||
Type *qualtype = type;
|
||||
if (sym(1).type_qualifier.qualifier != QualifiedType::Struct) {
|
||||
qualtype = makeAstNode<QualifiedType>
|
||||
(sym(1).type_qualifier.qualifier & ~QualifiedType::Struct, qualtype,
|
||||
sym(1).type_qualifier.layout_list);
|
||||
}
|
||||
ast(1) = makeAstNode<TypeAndVariableDeclaration>
|
||||
(makeAstNode<TypeDeclaration>(type),
|
||||
makeAstNode<VariableDeclaration>(qualtype, string(6)));
|
||||
} break;
|
||||
./
|
||||
|
||||
declaration ::= type_qualifier IDENTIFIER LEFT_BRACE struct_declaration_list RIGHT_BRACE IDENTIFIER LEFT_BRACKET RIGHT_BRACKET SEMICOLON ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
if ((sym(1).type_qualifier.qualifier & QualifiedType::Struct) == 0) {
|
||||
// TODO: issue an error if the qualifier does not contain "struct".
|
||||
}
|
||||
Type *type = makeAstNode<StructType>(string(2), sym(4).field_list);
|
||||
Type *qualtype = type;
|
||||
if (sym(1).type_qualifier.qualifier != QualifiedType::Struct) {
|
||||
qualtype = makeAstNode<QualifiedType>
|
||||
(sym(1).type_qualifier.qualifier & ~QualifiedType::Struct, qualtype,
|
||||
sym(1).type_qualifier.layout_list);
|
||||
}
|
||||
ast(1) = makeAstNode<TypeAndVariableDeclaration>
|
||||
(makeAstNode<TypeDeclaration>(type),
|
||||
makeAstNode<VariableDeclaration>
|
||||
(makeAstNode<ArrayType>(qualtype), string(6)));
|
||||
} break;
|
||||
./
|
||||
|
||||
declaration ::= type_qualifier IDENTIFIER LEFT_BRACE struct_declaration_list RIGHT_BRACE IDENTIFIER LEFT_BRACKET constant_expression RIGHT_BRACKET SEMICOLON ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
if ((sym(1).type_qualifier.qualifier & QualifiedType::Struct) == 0) {
|
||||
// TODO: issue an error if the qualifier does not contain "struct".
|
||||
}
|
||||
Type *type = makeAstNode<StructType>(string(2), sym(4).field_list);
|
||||
Type *qualtype = type;
|
||||
if (sym(1).type_qualifier.qualifier != QualifiedType::Struct) {
|
||||
qualtype = makeAstNode<QualifiedType>
|
||||
(sym(1).type_qualifier.qualifier & ~QualifiedType::Struct, qualtype,
|
||||
sym(1).type_qualifier.layout_list);
|
||||
}
|
||||
ast(1) = makeAstNode<TypeAndVariableDeclaration>
|
||||
(makeAstNode<TypeDeclaration>(type),
|
||||
makeAstNode<VariableDeclaration>
|
||||
(makeAstNode<ArrayType>(qualtype, expression(8)), string(6)));
|
||||
} break;
|
||||
./
|
||||
|
||||
declaration ::= type_qualifier SEMICOLON ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
Type *type = makeAstNode<QualifiedType>
|
||||
(sym(1).type_qualifier.qualifier, (Type *)0,
|
||||
sym(1).type_qualifier.layout_list);
|
||||
ast(1) = makeAstNode<TypeDeclaration>(type);
|
||||
} break;
|
||||
./
|
||||
|
||||
function_prototype ::= function_declarator RIGHT_PAREN ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
function(1)->finishParams();
|
||||
} break;
|
||||
./
|
||||
|
||||
function_declarator ::= function_header ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
// nothing to do.
|
||||
} break;
|
||||
./
|
||||
|
||||
function_declarator ::= function_header_with_parameters ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
// nothing to do.
|
||||
} break;
|
||||
./
|
||||
|
||||
function_header_with_parameters ::= function_header parameter_declaration ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
function(1)->params = makeAstNode< List<ParameterDeclaration *> >
|
||||
(sym(2).param_declaration);
|
||||
} break;
|
||||
./
|
||||
|
||||
function_header_with_parameters ::= function_header_with_parameters COMMA parameter_declaration ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
function(1)->params = makeAstNode< List<ParameterDeclaration *> >
|
||||
(function(1)->params, sym(3).param_declaration);
|
||||
} break;
|
||||
./
|
||||
|
||||
function_header ::= fully_specified_type IDENTIFIER LEFT_PAREN ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
function(1) = makeAstNode<FunctionDeclaration>(type(1), string(2));
|
||||
} break;
|
||||
./
|
||||
|
||||
@@ -2801,7 +2850,7 @@ case $rule_number: {
|
||||
external_declaration ::= function_definition ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
// nothing to do.
|
||||
} break;
|
||||
./
|
||||
|
||||
@@ -2822,7 +2871,7 @@ case $rule_number: {
|
||||
function_definition ::= function_prototype compound_statement_no_new_scope ;
|
||||
/.
|
||||
case $rule_number: {
|
||||
// ast(1) = new ...AST(...);
|
||||
function(1)->body = statement(2);
|
||||
} break;
|
||||
./
|
||||
|
||||
|
||||
@@ -394,6 +394,15 @@ void TypeDeclaration::accept0(Visitor *visitor)
|
||||
visitor->endVisit(this);
|
||||
}
|
||||
|
||||
void TypeAndVariableDeclaration::accept0(Visitor *visitor)
|
||||
{
|
||||
if (visitor->visit(this)) {
|
||||
accept(typeDecl, visitor);
|
||||
accept(varDecl, visitor);
|
||||
}
|
||||
visitor->endVisit(this);
|
||||
}
|
||||
|
||||
void InvariantDeclaration::accept0(Visitor *visitor)
|
||||
{
|
||||
visitor->visit(this);
|
||||
@@ -406,3 +415,13 @@ void InitDeclaration::accept0(Visitor *visitor)
|
||||
accept(decls, visitor);
|
||||
visitor->endVisit(this);
|
||||
}
|
||||
|
||||
void FunctionDeclaration::accept0(Visitor *visitor)
|
||||
{
|
||||
if (visitor->visit(this)) {
|
||||
accept(returnType, visitor);
|
||||
accept(params, visitor);
|
||||
accept(body, visitor);
|
||||
}
|
||||
visitor->endVisit(this);
|
||||
}
|
||||
|
||||
@@ -71,8 +71,10 @@ class PrecisionDeclaration;
|
||||
class ParameterDeclaration;
|
||||
class VariableDeclaration;
|
||||
class TypeDeclaration;
|
||||
class TypeAndVariableDeclaration;
|
||||
class InvariantDeclaration;
|
||||
class InitDeclaration;
|
||||
class FunctionDeclaration;
|
||||
class Visitor;
|
||||
|
||||
template <typename T>
|
||||
@@ -215,8 +217,10 @@ public:
|
||||
Kind_ParameterDeclaration,
|
||||
Kind_VariableDeclaration,
|
||||
Kind_TypeDeclaration,
|
||||
Kind_TypeAndVariableDeclaration,
|
||||
Kind_InvariantDeclaration,
|
||||
Kind_InitDeclaration
|
||||
Kind_InitDeclaration,
|
||||
Kind_FunctionDeclaration
|
||||
};
|
||||
|
||||
virtual TranslationUnit *asTranslationUnit() { return 0; }
|
||||
@@ -258,8 +262,10 @@ public:
|
||||
virtual ParameterDeclaration *asParameterDeclaration() { return 0; }
|
||||
virtual VariableDeclaration *asVariableDeclaration() { return 0; }
|
||||
virtual TypeDeclaration *asTypeDeclaration() { return 0; }
|
||||
virtual TypeAndVariableDeclaration *asTypeAndVariableDeclaration() { return 0; }
|
||||
virtual InvariantDeclaration *asInvariantDeclaration() { return 0; }
|
||||
virtual InitDeclaration *asInitDeclaration() { return 0; }
|
||||
virtual FunctionDeclaration *asFunctionDeclaration() { return 0; }
|
||||
|
||||
void accept(Visitor *visitor);
|
||||
static void accept(AST *ast, Visitor *visitor);
|
||||
@@ -953,6 +959,23 @@ public: // attributes
|
||||
Type *type;
|
||||
};
|
||||
|
||||
class TypeAndVariableDeclaration: public Declaration
|
||||
{
|
||||
public:
|
||||
TypeAndVariableDeclaration(TypeDeclaration *_typeDecl,
|
||||
VariableDeclaration *_varDecl)
|
||||
: Declaration(Kind_TypeAndVariableDeclaration)
|
||||
, typeDecl(_typeDecl), varDecl(_varDecl) {}
|
||||
|
||||
virtual TypeAndVariableDeclaration *asTypeAndVariableDeclaration() { return this; }
|
||||
|
||||
virtual void accept0(Visitor *visitor);
|
||||
|
||||
public: // attributes
|
||||
TypeDeclaration *typeDecl;
|
||||
VariableDeclaration *varDecl;
|
||||
};
|
||||
|
||||
class InvariantDeclaration: public Declaration
|
||||
{
|
||||
public:
|
||||
@@ -981,6 +1004,28 @@ public: // attributes
|
||||
List<Declaration *> *decls;
|
||||
};
|
||||
|
||||
class FunctionDeclaration : public Declaration
|
||||
{
|
||||
public:
|
||||
FunctionDeclaration(Type *_returnType, const std::string *_name)
|
||||
: Declaration(Kind_FunctionDeclaration), returnType(_returnType)
|
||||
, name(_name), params(0), body(0) {}
|
||||
|
||||
virtual FunctionDeclaration *asFunctionDeclaration() { return this; }
|
||||
|
||||
virtual void accept0(Visitor *visitor);
|
||||
|
||||
void finishParams() { params = finish(params); }
|
||||
|
||||
bool isPrototype() const { return body == 0; }
|
||||
|
||||
public: // attributes
|
||||
Type *returnType;
|
||||
const std::string *name;
|
||||
List<ParameterDeclaration *> *params;
|
||||
Statement *body;
|
||||
};
|
||||
|
||||
} // namespace GLSL
|
||||
|
||||
#endif // GLSLAST_H
|
||||
|
||||
@@ -138,11 +138,17 @@ public:
|
||||
virtual bool visit(TypeDeclaration *) { return true; }
|
||||
virtual void endVisit(TypeDeclaration *) {}
|
||||
|
||||
virtual bool visit(TypeAndVariableDeclaration *) { return true; }
|
||||
virtual void endVisit(TypeAndVariableDeclaration *) {}
|
||||
|
||||
virtual bool visit(InvariantDeclaration *) { return true; }
|
||||
virtual void endVisit(InvariantDeclaration *) {}
|
||||
|
||||
virtual bool visit(InitDeclaration *) { return true; }
|
||||
virtual void endVisit(InitDeclaration *) {}
|
||||
|
||||
virtual bool visit(FunctionDeclaration *) { return true; }
|
||||
virtual void endVisit(FunctionDeclaration *) {}
|
||||
};
|
||||
|
||||
} // namespace GLSL
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -83,7 +83,8 @@ public:
|
||||
Type *type;
|
||||
const std::string *name;
|
||||
} param_declarator;
|
||||
// ### ast nodes...
|
||||
ParameterDeclaration *param_declaration;
|
||||
FunctionDeclaration *function_declaration;
|
||||
};
|
||||
|
||||
Parser(Engine *engine, const char *source, unsigned size, int variant);
|
||||
@@ -99,6 +100,7 @@ private:
|
||||
Expression *&expression(int n) { return _symStack[_tos + n - 1].expression; }
|
||||
Statement *&statement(int n) { return _symStack[_tos + n - 1].statement; }
|
||||
Type *&type(int n) { return _symStack[_tos + n - 1].type; }
|
||||
FunctionDeclaration *&function(int n) { return _symStack[_tos + n - 1].function_declaration; }
|
||||
|
||||
inline int consumeToken() { return _index++; }
|
||||
inline const Token &tokenAt(int index) const { return _tokens.at(index); }
|
||||
|
||||
Reference in New Issue
Block a user