From d094c72e1006346adf1c60760fe79e248f6f1d96 Mon Sep 17 00:00:00 2001 From: David Walter Seikel Date: Wed, 1 Feb 2012 23:37:17 +1000 Subject: Parse and output for statements. Also, take care of ignorables on left parens of flow controls. --- LuaSL/src/LuaSL_LSL_tree.h | 3 ++- LuaSL/src/LuaSL_compile.c | 61 +++++++++++++++++++++++++++++++++++++++++- LuaSL/src/LuaSL_lemon_yaccer.y | 4 +-- 3 files changed, 64 insertions(+), 4 deletions(-) (limited to 'LuaSL/src') diff --git a/LuaSL/src/LuaSL_LSL_tree.h b/LuaSL/src/LuaSL_LSL_tree.h index 33f860c..cff2bab 100644 --- a/LuaSL/src/LuaSL_LSL_tree.h +++ b/LuaSL/src/LuaSL_LSL_tree.h @@ -219,7 +219,7 @@ struct _LSL_Statement Eina_Clist statement; // For block statement lists, this is the entry. LSL_Identifier *identifier; LSL_Parenthesis *parenthesis; - LSL_Leaf *expressions; // A for statement will have three expressions, everything else has zero or one. + LSL_Leaf *expressions; // A for statement will have three expressions, and two semicolons, everything else has zero or one. LSL_Block *block; LSL_Statement *elseBlock; LSL_Type type; // Expression type. @@ -395,6 +395,7 @@ typedef struct void burnLeaf(void *data); LSL_Leaf *addBlock(LuaSL_compiler *compiler, LSL_Leaf *left, LSL_Leaf *lval, LSL_Leaf *right); LSL_Leaf *addCrement(LuaSL_compiler *compiler, LSL_Leaf *variable, LSL_Leaf *crement); +LSL_Leaf *addFor(LuaSL_compiler *compiler, LSL_Leaf *lval, LSL_Leaf *flow, LSL_Leaf *left, LSL_Leaf *expr0, LSL_Leaf *stat0, LSL_Leaf *expr1, LSL_Leaf *stat1, LSL_Leaf *expr2, LSL_Leaf *right, LSL_Leaf *block); LSL_Leaf *addFunction(LuaSL_compiler *compiler, LSL_Leaf *type, LSL_Leaf *identifier, LSL_Leaf *open, LSL_Leaf *params, LSL_Leaf *close); LSL_Leaf *addFunctionBody(LuaSL_compiler *compiler, LSL_Leaf *function, LSL_Leaf *block); LSL_Leaf *addFunctionCall(LuaSL_compiler *compiler, LSL_Leaf *identifier, LSL_Leaf *open, LSL_Leaf *params, LSL_Leaf *close); diff --git a/LuaSL/src/LuaSL_compile.c b/LuaSL/src/LuaSL_compile.c index 0183599..c61f900 100644 --- a/LuaSL/src/LuaSL_compile.c +++ b/LuaSL/src/LuaSL_compile.c @@ -742,6 +742,23 @@ LSL_Leaf *addIfElse(LuaSL_compiler *compiler, LSL_Leaf *ifBlock, LSL_Leaf *elseB return ifBlock; } +LSL_Leaf *addFor(LuaSL_compiler *compiler, LSL_Leaf *lval, LSL_Leaf *flow, LSL_Leaf *left, LSL_Leaf *expr0, LSL_Leaf *stat0, LSL_Leaf *expr1, LSL_Leaf *stat1, LSL_Leaf *expr2, LSL_Leaf *right, LSL_Leaf *block) +{ + LSL_Leaf **exprs = calloc(5, sizeof(LSL_Leaf *)); + + if (exprs) + { + lval = addStatement(compiler, lval, flow, left, expr0, right, block, NULL); + exprs[0] = expr0; + exprs[1] = stat0; + exprs[2] = expr1; + exprs[3] = stat1; + exprs[4] = expr2; + lval->value.statementValue->expressions = (LSL_Leaf *) exprs; + } + return lval; +} + LSL_Leaf *addStatement(LuaSL_compiler *compiler, LSL_Leaf *lval, LSL_Leaf *flow, LSL_Leaf *left, LSL_Leaf *expr, LSL_Leaf *right, LSL_Leaf *block, LSL_Leaf *identifier) { gameGlobals *game = compiler->game; @@ -784,6 +801,7 @@ LSL_Leaf *addStatement(LuaSL_compiler *compiler, LSL_Leaf *lval, LSL_Leaf *flow, } case LSL_FOR : { + justOne = TRUE; break; } case LSL_IF : @@ -861,6 +879,21 @@ LSL_Leaf *addStatement(LuaSL_compiler *compiler, LSL_Leaf *lval, LSL_Leaf *flow, #endif lval->value.statementValue = stat; } + +#if LUASL_DIFF_CHECK + if (left) + { + if (NULL == stat->ignorable) + stat->ignorable = calloc(3, sizeof(Eina_Strbuf *)); + else + stat->ignorable = realloc(stat->ignorable, 3 * sizeof(Eina_Strbuf *)); + if (stat->ignorable) + { + stat->ignorable[2] = left->ignorable; + left->ignorable = NULL; + } + } +#endif } return lval; @@ -1427,6 +1460,10 @@ static void outputRawStatement(FILE *file, outputMode mode, LSL_Statement *state case LSL_FOR : { isBlock = TRUE; +#if LUASL_DIFF_CHECK + if ((statement->ignorable) && (statement->ignorable[1])) + fwrite(eina_strbuf_string_get(statement->ignorable[1]), 1, eina_strbuf_length_get(statement->ignorable[1]), file); +#endif fprintf(file, "%s", tokens[statement->type - lowestToken]->toKen); break; } @@ -1506,7 +1543,29 @@ static void outputRawStatement(FILE *file, outputMode mode, LSL_Statement *state } } - if (statement->parenthesis) +#if LUASL_DIFF_CHECK + if ((statement->ignorable) && (statement->ignorable[2])) + fwrite(eina_strbuf_string_get(statement->ignorable[2]), 1, eina_strbuf_length_get(statement->ignorable[2]), file); +#endif + if (LSL_FOR == statement->type) + { + LSL_Leaf **exprs = (LSL_Leaf **) statement->expressions; + int i; + + fprintf(file, "("); + for (i = 0; i < 5; i++) + { + outputLeaf(file, mode, exprs[i]); + if (i % 2) + fprintf(file, ";"); + } +#if LUASL_DIFF_CHECK + fprintf(file, "%s)", eina_strbuf_string_get(statement->parenthesis->rightIgnorable)); +#else + fprintf(file, ")"); +#endif + } + else if (statement->parenthesis) outputRawParenthesisToken(file, mode, statement->parenthesis, ""); else outputLeaf(file, mode, statement->expressions); diff --git a/LuaSL/src/LuaSL_lemon_yaccer.y b/LuaSL/src/LuaSL_lemon_yaccer.y index 1d28ec5..ba32692 100644 --- a/LuaSL/src/LuaSL_lemon_yaccer.y +++ b/LuaSL/src/LuaSL_lemon_yaccer.y @@ -68,8 +68,8 @@ statementList(A) ::= . { A = collectStatements(compiler, NULL, NULL); } %nonassoc LSL_DO LSL_FOR LSL_IF LSL_JUMP LSL_RETURN LSL_STATE_CHANGE LSL_WHILE. %nonassoc LSL_ELSE. statement(A) ::= LSL_DO(F) block(B) LSL_WHILE(W) LSL_PARENTHESIS_OPEN(L) expr(E) LSL_PARENTHESIS_CLOSE(R) LSL_STATEMENT(S). { A = addStatement(compiler, S, F, L, E, R, B, W); } -statement(A) ::= LSL_FOR(F) LSL_PARENTHESIS_OPEN(L) expr(E0) LSL_STATEMENT(S0) expr(E1) LSL_STATEMENT(S1) expr(E2) LSL_PARENTHESIS_CLOSE(R) block(B). { A = addStatement(compiler, NULL, F, L, E1, R, B, NULL); } // three expressions, two semi colons -statement(A) ::= LSL_FOR(F) LSL_PARENTHESIS_OPEN(L) expr(E0) LSL_STATEMENT(S0) expr(E1) LSL_STATEMENT(S1) expr(E2) LSL_PARENTHESIS_CLOSE(R) statement(S). { A = addStatement(compiler, S, F, L, E1, R, NULL, NULL); } // three expressions, two semi colons +statement(A) ::= LSL_FOR(F) LSL_PARENTHESIS_OPEN(L) expr(E0) LSL_STATEMENT(S0) expr(E1) LSL_STATEMENT(S1) expr(E2) LSL_PARENTHESIS_CLOSE(R) block(B). { A = addFor(compiler, NULL, F, L, E0, S0, E1, S1, E2, R, B); } +statement(A) ::= LSL_FOR(F) LSL_PARENTHESIS_OPEN(L) expr(E0) LSL_STATEMENT(S0) expr(E1) LSL_STATEMENT(S1) expr(E2) LSL_PARENTHESIS_CLOSE(R) statement(S). { A = addFor(compiler, S, F, L, E0, S0, E1, S1, E2, R, NULL); } statement(A) ::= ifBlock(B). { A = B; } ifBlock(A) ::= ifBlock(B) elseBlock(E). { A = addIfElse(compiler, B, E); } -- cgit v1.1