X-Git-Url: http://git.tdb.fi/?a=blobdiff_plain;f=source%2Fprogramparser.cpp;h=bf5d5dffb103fea9b554afa0940f607d12b21ac4;hb=0807680edd94a7f14560831db4dd52e4e48d0d19;hp=596ed0456b8e789ec2bd5ac636790a7d97bc8c4c;hpb=8812fe9fc71b997246ddfdedb8a91932b679d2d3;p=libs%2Fgl.git diff --git a/source/programparser.cpp b/source/programparser.cpp index 596ed045..bf5d5dff 100644 --- a/source/programparser.cpp +++ b/source/programparser.cpp @@ -95,7 +95,7 @@ void ProgramParser::parse_source() iter = source.begin(); while(1) { - while(Node *statement = parse_global_declaration()) + while(RefPtr statement = parse_global_declaration()) cur_stage->content.body.push_back(statement); parse_token(); @@ -329,7 +329,7 @@ bool ProgramParser::is_identifier(const string &token) return re.match(token); } -Node *ProgramParser::parse_global_declaration() +RefPtr ProgramParser::parse_global_declaration() { string token = peek_token(); if(token=="import") @@ -344,12 +344,12 @@ Node *ProgramParser::parse_global_declaration() iface_lo->layout.qualifiers = layout->qualifiers; iface_lo->interface = parse_token(); expect(";"); - return iface_lo.release(); + return iface_lo; } else { - VariableDeclaration *var = parse_variable_declaration(); - var->layout = layout.release(); + RefPtr var = parse_variable_declaration(); + var->layout = layout; return var; } } @@ -377,7 +377,7 @@ Node *ProgramParser::parse_global_declaration() throw runtime_error(format("Syntax error at '%s': expected a global declaration", token)); } -Node *ProgramParser::parse_statement() +RefPtr ProgramParser::parse_statement() { string token = peek_token(); if(token=="if") @@ -388,6 +388,14 @@ Node *ProgramParser::parse_statement() return parse_passthrough(); else if(token=="return") return parse_return(); + else if(token=="break" || token=="continue" || token=="discard") + { + RefPtr jump = new Jump; + jump->keyword = parse_token(); + expect(";"); + + return jump; + } else if(is_qualifier(token) || is_type(token)) return parse_variable_declaration(); else if(!token.empty()) @@ -396,13 +404,13 @@ Node *ProgramParser::parse_statement() expr->expression = parse_expression(); expect(";"); - return expr.release(); + return expr; } else throw runtime_error(format("Syntax error at '%s': expected a statement", token)); } -Import *ProgramParser::parse_import() +RefPtr ProgramParser::parse_import() { if(cur_stage->type!=SHARED) throw runtime_error("Imports are only allowed in the shared section"); @@ -411,10 +419,10 @@ Import *ProgramParser::parse_import() RefPtr import = new Import; import->module = parse_token(); expect(";"); - return import.release(); + return import; } -Layout *ProgramParser::parse_layout() +RefPtr ProgramParser::parse_layout() { expect("layout"); expect("("); @@ -439,7 +447,7 @@ Layout *ProgramParser::parse_layout() } expect(")"); - return layout.release(); + return layout; } void ProgramParser::parse_block(Block &block, bool require_braces) @@ -462,7 +470,7 @@ void ProgramParser::parse_block(Block &block, bool require_braces) expect("}"); } -Expression *ProgramParser::parse_expression(unsigned precedence) +RefPtr ProgramParser::parse_expression(unsigned precedence) { RefPtr left; VariableReference *left_var = 0; @@ -478,7 +486,7 @@ Expression *ProgramParser::parse_expression(unsigned precedence) if(token==";" || token==")" || token=="]" || token=="," || (oper && precedence && oper->precedence>=precedence)) { if(left) - return left.release(); + return left; else throw runtime_error(format("Parse error at '%s': expected an expression", token)); } @@ -488,12 +496,12 @@ Expression *ProgramParser::parse_expression(unsigned precedence) { if(!left_var) throw runtime_error(format("Parse error at '%s': function name must be an identifier", token)); - left = parse_function_call(left_var); + left = parse_function_call(*left_var); } else if(token==".") { RefPtr memacc = new MemberAccess; - memacc->left = left.release(); + memacc->left = left; parse_token(); memacc->member = expect_identifier(); left = memacc; @@ -503,11 +511,11 @@ Expression *ProgramParser::parse_expression(unsigned precedence) RefPtr unary = new UnaryExpression; unary->oper = parse_token(); unary->prefix = false; - unary->expression = left.release(); + unary->expression = left; left = unary; } else if(oper && oper->type==BINARY) - left = parse_binary(left.release(), oper); + left = parse_binary(left, oper); else throw runtime_error(format("Parse error at '%s': expected an operator", token)); left_var = 0; @@ -549,7 +557,7 @@ Expression *ProgramParser::parse_expression(unsigned precedence) } } -BinaryExpression *ProgramParser::parse_binary(Expression *left, const Operator *oper) +RefPtr ProgramParser::parse_binary(const RefPtr &left, const Operator *oper) { RefPtr binary = (oper->precedence==16 ? new Assignment : new BinaryExpression); binary->left = left; @@ -562,13 +570,13 @@ BinaryExpression *ProgramParser::parse_binary(Expression *left, const Operator * } else binary->right = parse_expression(oper->precedence+(oper->assoc==RIGHT_TO_LEFT)); - return binary.release(); + return binary; } -FunctionCall *ProgramParser::parse_function_call(VariableReference *var) +RefPtr ProgramParser::parse_function_call(const VariableReference &var) { RefPtr call = new FunctionCall; - call->name = var->name; + call->name = var.name; call->constructor = is_type(call->name); expect("("); while(peek_token()!=")") @@ -578,10 +586,10 @@ FunctionCall *ProgramParser::parse_function_call(VariableReference *var) call->arguments.push_back(parse_expression()); } expect(")"); - return call.release(); + return call; } -StructDeclaration *ProgramParser::parse_struct_declaration() +RefPtr ProgramParser::parse_struct_declaration() { expect("struct"); RefPtr strct = new StructDeclaration; @@ -591,10 +599,10 @@ StructDeclaration *ProgramParser::parse_struct_declaration() expect(";"); declared_types.insert(strct->name); - return strct.release(); + return strct; } -VariableDeclaration *ProgramParser::parse_variable_declaration() +RefPtr ProgramParser::parse_variable_declaration() { RefPtr var = new VariableDeclaration; @@ -632,10 +640,10 @@ VariableDeclaration *ProgramParser::parse_variable_declaration() var->init_expression = parse_expression(); expect(";"); - return var.release(); + return var; } -FunctionDeclaration *ProgramParser::parse_function_declaration() +RefPtr ProgramParser::parse_function_declaration() { RefPtr func = new FunctionDeclaration; @@ -650,7 +658,7 @@ FunctionDeclaration *ProgramParser::parse_function_declaration() RefPtr var = new VariableDeclaration; var->type = expect_type(); var->name = expect_identifier(); - func->parameters.push_back(var.release()); + func->parameters.push_back(var); } expect(")"); @@ -665,10 +673,10 @@ FunctionDeclaration *ProgramParser::parse_function_declaration() else throw runtime_error(format("Parse error at '%s': expected '{' or ';'", token)); - return func.release(); + return func; } -InterfaceBlock *ProgramParser::parse_interface_block() +RefPtr ProgramParser::parse_interface_block() { RefPtr iface = new InterfaceBlock; @@ -689,10 +697,10 @@ InterfaceBlock *ProgramParser::parse_interface_block() expect(";"); } - return iface.release(); + return iface; } -Conditional *ProgramParser::parse_conditional() +RefPtr ProgramParser::parse_conditional() { expect("if"); expect("("); @@ -709,10 +717,10 @@ Conditional *ProgramParser::parse_conditional() parse_block(cond->else_body, false); } - return cond.release(); + return cond; } -Iteration *ProgramParser::parse_iteration() +RefPtr ProgramParser::parse_iteration() { expect("for"); expect("("); @@ -725,7 +733,7 @@ Iteration *ProgramParser::parse_iteration() RefPtr expr = new ExpressionStatement; expr->expression = parse_expression(); expect(";"); - loop->init_statement = expr.release(); + loop->init_statement = expr; } loop->condition = parse_expression(); expect(";"); @@ -734,10 +742,10 @@ Iteration *ProgramParser::parse_iteration() parse_block(loop->body, false); - return loop.release(); + return loop; } -Passthrough *ProgramParser::parse_passthrough() +RefPtr ProgramParser::parse_passthrough() { expect("passthrough"); RefPtr pass = new Passthrough; @@ -748,17 +756,17 @@ Passthrough *ProgramParser::parse_passthrough() expect("]"); } expect(";"); - return pass.release(); + return pass; } -Return *ProgramParser::parse_return() +RefPtr ProgramParser::parse_return() { expect("return"); RefPtr ret = new Return; if(peek_token()!=";") ret->expression = parse_expression(); expect(";"); - return ret.release(); + return ret; } } // namespace GL