X-Git-Url: http://git.tdb.fi/?a=blobdiff_plain;f=source%2Fglsl%2Fparser.cpp;h=0f7122f50dae119283390b22f51bbae31ce245eb;hb=a82fcc462550d63a101aca4313807b1320789a5a;hp=b09d2b5550b47c321fba2a69feedc4d7c36f0293;hpb=734bc4a781ace5aecd98254ad1b50d52a06af0af;p=libs%2Fgl.git diff --git a/source/glsl/parser.cpp b/source/glsl/parser.cpp index b09d2b55..0f7122f5 100644 --- a/source/glsl/parser.cpp +++ b/source/glsl/parser.cpp @@ -188,6 +188,15 @@ bool Parser::is_identifier(const string &token) return re.match(token); } +template +RefPtr Parser::create_node() +{ + RefPtr node = new T; + node->source = source_index; + node->line = tokenizer.get_location().line; + return node; +} + template RefPtr Parser::parse_with_recovery(RefPtr (Parser::*parse_func)()) { @@ -247,9 +256,7 @@ RefPtr Parser::parse_global_declaration() token = tokenizer.peek_token(); if(is_interface_qualifier(token) && tokenizer.peek_token(1)==";") { - RefPtr iface_lo = new InterfaceLayout; - iface_lo->source = source_index; - iface_lo->line = tokenizer.get_location().line; + RefPtr iface_lo = create_node(); iface_lo->layout.qualifiers = layout->qualifiers; iface_lo->interface = tokenizer.parse_token(); tokenizer.expect(";"); @@ -302,9 +309,7 @@ RefPtr Parser::parse_statement() return parse_return(); else if(token=="break" || token=="continue" || token=="discard") { - RefPtr jump = new Jump; - jump->source = source_index; - jump->line = tokenizer.get_location().line; + RefPtr jump = create_node(); jump->keyword = tokenizer.parse_token(); tokenizer.expect(";"); @@ -319,9 +324,7 @@ RefPtr Parser::parse_statement() } else if(!token.empty()) { - RefPtr expr = new ExpressionStatement; - expr->source = source_index; - expr->line = tokenizer.get_location().line; + RefPtr expr = create_node(); expr->expression = parse_expression(); tokenizer.expect(";"); @@ -337,9 +340,7 @@ RefPtr Parser::parse_import() throw invalid_shader_source(tokenizer.get_location(), "Imports are only allowed in the shared section"); tokenizer.expect("import"); - RefPtr import = new Import; - import->source = source_index; - import->line = tokenizer.get_location().line; + RefPtr import = create_node(); import->module = expect_identifier(); tokenizer.expect(";"); return import; @@ -348,9 +349,7 @@ RefPtr Parser::parse_import() RefPtr Parser::parse_precision() { tokenizer.expect("precision"); - RefPtr precision = new Precision; - precision->source = source_index; - precision->line = tokenizer.get_location().line; + RefPtr precision = create_node(); precision->precision = tokenizer.parse_token(); if(!is_precision_qualifier(precision->precision)) @@ -370,7 +369,7 @@ RefPtr Parser::parse_layout() { tokenizer.expect("layout"); tokenizer.expect("("); - RefPtr layout = new Layout; + RefPtr layout = create_node(); while(1) { string token = tokenizer.parse_token(); @@ -454,7 +453,7 @@ RefPtr Parser::parse_expression(unsigned precedence) } else if(token==".") { - RefPtr memacc = new MemberAccess; + RefPtr memacc = create_node(); memacc->left = left; memacc->oper = oper; tokenizer.parse_token(); @@ -463,7 +462,7 @@ RefPtr Parser::parse_expression(unsigned precedence) } else if(oper && oper->type==Operator::POSTFIX) { - RefPtr unary = new UnaryExpression; + RefPtr unary = create_node(); unary->oper = oper; tokenizer.parse_token(); unary->expression = left; @@ -480,7 +479,7 @@ RefPtr Parser::parse_expression(unsigned precedence) if(token=="(") { tokenizer.parse_token(); - RefPtr parexpr = new ParenthesizedExpression; + RefPtr parexpr = create_node(); parexpr->expression = parse_expression(); tokenizer.expect(")"); left = parexpr; @@ -493,14 +492,14 @@ RefPtr Parser::parse_expression(unsigned precedence) } else if(is_identifier(token)) { - RefPtr var = new VariableReference; + RefPtr var = create_node(); var->name = expect_identifier(); left = var; left_var = var.get(); } else if(oper && oper->type==Operator::PREFIX) { - RefPtr unary = new UnaryExpression; + RefPtr unary = create_node(); unary->oper = oper; tokenizer.parse_token(); unary->expression = parse_expression(oper->precedence); @@ -514,7 +513,8 @@ RefPtr Parser::parse_expression(unsigned precedence) RefPtr Parser::parse_binary(const RefPtr &left, const Operator &oper) { - RefPtr binary = (oper.precedence==16 ? new Assignment : new BinaryExpression); + RefPtr binary = (oper.precedence==16 ? + static_cast >(create_node()) : create_node()); binary->left = left; binary->oper = &oper; tokenizer.expect(oper.token); @@ -530,7 +530,7 @@ RefPtr Parser::parse_binary(const RefPtr &left, co RefPtr Parser::parse_function_call(const VariableReference &var) { - RefPtr call = new FunctionCall; + RefPtr call = create_node(); call->name = var.name; call->constructor = is_type(call->name); call->oper = &Operator::get_operator("(", Operator::POSTFIX); @@ -548,9 +548,7 @@ RefPtr Parser::parse_function_call(const VariableReference &var) RefPtr Parser::parse_struct_declaration() { tokenizer.expect("struct"); - RefPtr strct = new StructDeclaration; - strct->source = source_index; - strct->line = tokenizer.get_location().line; + RefPtr strct = create_node(); strct->name = expect_identifier(); parse_block(strct->members, true, &Parser::parse_variable_declaration); @@ -562,9 +560,7 @@ RefPtr Parser::parse_struct_declaration() RefPtr Parser::parse_variable_declaration() { - RefPtr var = new VariableDeclaration; - var->source = source_index; - var->line = tokenizer.get_location().line; + RefPtr var = create_node(); string token = tokenizer.peek_token(); while(is_qualifier(token)) @@ -617,9 +613,7 @@ RefPtr Parser::parse_variable_declaration_with_layout() RefPtr Parser::parse_function_declaration() { - RefPtr func = new FunctionDeclaration; - func->source = source_index; - func->line = tokenizer.get_location().line; + RefPtr func = create_node(); func->return_type = expect_type(); func->name = expect_identifier(); @@ -629,7 +623,7 @@ RefPtr Parser::parse_function_declaration() if(!func->parameters.empty()) tokenizer.expect(","); - RefPtr var = new VariableDeclaration; + RefPtr var = create_node(); string token = tokenizer.peek_token(); if(token=="in" || token=="out" || token=="inout") var->interface = tokenizer.parse_token(); @@ -655,9 +649,7 @@ RefPtr Parser::parse_function_declaration() RefPtr Parser::parse_interface_block() { - RefPtr iface = new InterfaceBlock; - iface->source = source_index; - iface->line = tokenizer.get_location().line; + RefPtr iface = create_node(); iface->interface = tokenizer.parse_token(); if(!is_interface_qualifier(iface->interface)) @@ -682,9 +674,7 @@ RefPtr Parser::parse_interface_block() RefPtr Parser::parse_conditional() { tokenizer.expect("if"); - RefPtr cond = new Conditional; - cond->source = source_index; - cond->line = tokenizer.get_location().line; + RefPtr cond = create_node(); tokenizer.expect("("); cond->condition = parse_expression(); tokenizer.expect(")"); @@ -704,9 +694,7 @@ RefPtr Parser::parse_conditional() RefPtr Parser::parse_for() { tokenizer.expect("for"); - RefPtr loop = new Iteration; - loop->source = source_index; - loop->line = tokenizer.get_location().line; + RefPtr loop = create_node(); tokenizer.expect("("); string token = tokenizer.peek_token(); if(is_type(token)) @@ -715,7 +703,7 @@ RefPtr Parser::parse_for() { if(token!=";") { - RefPtr expr = new ExpressionStatement; + RefPtr expr = create_node(); expr->expression = parse_expression(); loop->init_statement = expr; } @@ -736,9 +724,7 @@ RefPtr Parser::parse_for() RefPtr Parser::parse_while() { tokenizer.expect("while"); - RefPtr loop = new Iteration; - loop->source = source_index; - loop->line = tokenizer.get_location().line; + RefPtr loop = create_node(); tokenizer.expect("("); loop->condition = parse_expression(); tokenizer.expect(")"); @@ -751,9 +737,7 @@ RefPtr Parser::parse_while() RefPtr Parser::parse_passthrough() { tokenizer.expect("passthrough"); - RefPtr pass = new Passthrough; - pass->source = source_index; - pass->line = tokenizer.get_location().line; + RefPtr pass = create_node(); if(cur_stage->type==Stage::GEOMETRY) { tokenizer.expect("["); @@ -767,9 +751,7 @@ RefPtr Parser::parse_passthrough() RefPtr Parser::parse_return() { tokenizer.expect("return"); - RefPtr ret = new Return; - ret->source = source_index; - ret->line = tokenizer.get_location().line; + RefPtr ret = create_node(); if(tokenizer.peek_token()!=";") ret->expression = parse_expression(); tokenizer.expect(";");