From: NeilBrown Date: Fri, 3 Oct 2014 04:01:45 +0000 (+1000) Subject: indent_test: integrate into Makefile scheme nicely. X-Git-Tag: workingparser~3 X-Git-Url: http://git.neil.brown.name/?a=commitdiff_plain;h=34189a207bc903e9ff96549ad222fa20f2e41508;p=ocean indent_test: integrate into Makefile scheme nicely. The test code is now included in indent_test.mdc, and there is a '.mk'. make tests will run the test. Signed-off-by: NeilBrown --- diff --git a/csrc/indent_test.cgm b/csrc/indent_test.cgm deleted file mode 100644 index 974c167..0000000 --- a/csrc/indent_test.cgm +++ /dev/null @@ -1,230 +0,0 @@ - -# header - -This parser is primarily for testing indent and linebreak handling. -It reads a very simple code fragment with if/else statements and -simple assignments with expressions, and then prints out the same -with complete bracketing and indenting. - - ./parsergen -o itest --LALR indent_test.cgm - cc -o itest itest.c lib*.o -licuuc -lgmp - ./itest itest.code - - struct expression { - struct text op; - struct expression *left, *right; - }; - struct statement { - struct statement *next; - struct expression *expr; - struct statement *thenpart; - struct statement *elsepart; - }; - -# code - #include - #include - #include - #include - #include "mdcode.h" - #include "scanner.h" - #include "parser.h" - #include "itest.h" - - static void free_expression(struct expression *e) - { - if (!e) - return; - free_expression(e->left); - free_expression(e->right); - free(e); - } - - static void free_statement(struct statement *s) - { - if (!s) - return; - free_statement(s->next); - free_expression(s->expr); - free_statement(s->thenpart); - free_statement(s->elsepart); - free(s); - } - - static void print_expression(struct expression *e) - { - if (e->left && e->right) printf("("); - if (e->left) - print_expression(e->left); - if (e->op.len) - printf("%.*s", e->op.len, e->op.txt); - if (e->right) - print_expression(e->right); - if (e->left && e->right) printf(")"); - } - - static void print_statement(struct statement *s, int depth) - { - if (!s) - return; - if (!s->thenpart) { - printf("%*.s", depth, ""); - print_expression(s->expr); - printf(";\n"); - } else { - printf("%*.sif ", depth, ""); - print_expression(s->expr); - printf(":\n"); - print_statement(s->thenpart, depth+4); - if (s->elsepart) { - printf("%*.selse:\n", depth, ""); - print_statement(s->elsepart, depth+4); - } - } - print_statement(s->next, depth); - } - - int main(int argc, char *argv[]) - { - int fd = open(argv[1], O_RDONLY); - int len = lseek(fd, 0, 2); - char *file = mmap(NULL, len, PROT_READ, MAP_SHARED, fd, 0); - struct section *s = code_extract(file, file+len, NULL); - struct token_config config = { - .ignored = (1 << TK_line_comment) - | (1 << TK_block_comment), - .number_chars = ".,_+-", - .word_start = "", - .word_cont = "", - }; - parse_itest(s->code, &config, argc > 2 ? stderr : NULL); - while (s) { - struct section *t = s->next; - code_free(s->code); - free(s); - s = t; - } - exit(0); - } - - -# grammar - -~~~~~~ - -Program -> Statementlist ${ print_statement($1, 0); }$ - -OptNL -> NEWLINE - | - -$*statement - Statementlist -> Statements ${ $0 = $<1; }$ - - Statements -> Statements Statement ${ - { - struct statement **s; - $0 = $<1; - s = &$0; - while (*s) - s = &(*s)->next; - *s = $<2; - } - }$ - | Statement ${ $0 = $<1; }$ - | ERROR ${ printf("statement ERROR\n"); $0 = NULL; }$ - - Open -> { - | NEWLINE { - Close -> } - | NEWLINE } - Block -> Open Statementlist Close ${ $0 = $<2; }$ - | Open SimpleStatements } ${ $0 = $<2; }$ - | : Statementlist ${ $0 = $2; $2 = NULL; }$ - - SimpleStatements -> SimpleStatements ; SimpleStatement ${ - { - struct statement **s; - $0 = $<1; - s = &$0; - while (*s) - s = &(*s)->next; - *s = $<3; - } - }$ - | SimpleStatement ${ $0 = $<1; }$ - | SimpleStatements ; ${ $0 = $<1; }$ - - SimpleStatement -> Factor = Expression ${ - $0 = calloc(1, sizeof(struct statement)); - $0->expr = calloc(1, sizeof(struct expression)); - $0->expr->left = $<1; - $0->expr->op = $2.txt; - $0->expr->right = $<3; - }$ - Statement -> SimpleStatements NEWLINE ${ - $0 = $<1; - }$ - | IfStatement ${ $0 = $<1; }$ - | Statement NEWLINE ${ $0 = $<1; }$ - - IfStatement -> if Expression Block OptNL ${ - $0 = calloc(1, sizeof(struct statement)); - $0->expr = $<2; - $0->thenpart = $<3; - }$ - | if Expression : SimpleStatements ${ - $0 = calloc(1, sizeof(struct statement)); - $0->expr = $<2; - $0->thenpart = $<4; - }$ - | if Expression Block OptNL else Block ${ - $0 = calloc(1, sizeof(struct statement)); - $0->expr = $<2; - $0->thenpart = $<3; - $0->elsepart = $<6; - }$ - | if Expression Block OptNL else : SimpleStatements ${ - $0 = calloc(1, sizeof(struct statement)); - $0->expr = $<2; - $0->thenpart = $<3; - $0->elsepart = $<7; - }$ - | if Expression Block OptNL else IfStatement ${ - $0 = calloc(1, sizeof(struct statement)); - $0->expr = $<2; - $0->thenpart = $<3; - $0->elsepart = $<6; - }$ - -$*expression - Expression -> Expression + Term ${ - $0 = calloc(1, sizeof(struct expression)); - $0->op = $2.txt; - $0->left = $<1; - $0->right = $<3; - }$ - | Expression - Term ${ - $0 = calloc(1, sizeof(struct expression)); - $0->op = $2.txt; - $0->left = $<1; - $0->right = $<3; - }$ - | Term ${ $0 = $1; $1 = NULL; }$ - Term -> Term * Factor ${ - $0 = calloc(1, sizeof(struct expression)); - $0->op = $2.txt; - $0->left = $<1; - $0->right = $<3; - }$ - | Term / Factor ${ - $0 = calloc(1, sizeof(struct expression)); - $0->op = $2.txt; - $0->left = $<1; - $0->right = $<3; - }$ - | Factor ${ $0 = $1; $1 = NULL; }$ - Factor -> IDENTIFIER ${ - $0 = calloc(1, sizeof(struct expression)); - $0->op = $1.txt; - }$ - diff --git a/csrc/indent_test.mdc b/csrc/indent_test.mdc new file mode 100644 index 0000000..792e152 --- /dev/null +++ b/csrc/indent_test.mdc @@ -0,0 +1,285 @@ +This parser is primarily for testing indent and linebreak handling. +It reads a very simple code fragment with if/else statements and +simple assignments with expressions, and then prints out the same +with complete bracketing and indenting. + +# File: indent_test.mk + myCFLAGS := -Wall -g -fplan9-extensions + CFLAGS := $(filter-out $(myCFLAGS),$(CFLAGS)) $(myCFLAGS) + LDLIBS:= libparser.o libscanner.o libmdcode.o -licuuc + + all :: itest + itest.c itest.h : indent_test.mdc parsergen libparser.o libscanner.o libmdcode.o + ./parsergen -o itest --LALR --tag indent indent_test.mdc + indent_test.mk: indent_test.mdc md2c + ./md2c indent_test.mdc + itest: itest.c + + tests:: itest itest.code + ./itest itest.code + +# indent: header + + ./parsergen -o itest --LALR indent_test.cgm + cc -o itest itest.c lib*.o -licuuc -lgmp + ./itest itest.code + + struct expression { + struct text op; + struct expression *left, *right; + }; + struct statement { + struct statement *next; + struct expression *expr; + struct statement *thenpart; + struct statement *elsepart; + }; + +# indent: code + #include + #include + #include + #include + #include + #include "mdcode.h" + #include "scanner.h" + #include "parser.h" + #include "itest.h" + + static void free_expression(struct expression *e) + { + if (!e) + return; + free_expression(e->left); + free_expression(e->right); + free(e); + } + + static void free_statement(struct statement *s) + { + if (!s) + return; + free_statement(s->next); + free_expression(s->expr); + free_statement(s->thenpart); + free_statement(s->elsepart); + free(s); + } + + static void print_expression(struct expression *e) + { + if (e->left && e->right) printf("("); + if (e->left) + print_expression(e->left); + if (e->op.len) + printf("%.*s", e->op.len, e->op.txt); + if (e->right) + print_expression(e->right); + if (e->left && e->right) printf(")"); + } + + static void print_statement(struct statement *s, int depth) + { + if (!s) + return; + if (!s->thenpart) { + printf("%*.s", depth, ""); + print_expression(s->expr); + printf(";\n"); + } else { + printf("%*.sif ", depth, ""); + print_expression(s->expr); + printf(":\n"); + print_statement(s->thenpart, depth+4); + if (s->elsepart) { + printf("%*.selse:\n", depth, ""); + print_statement(s->elsepart, depth+4); + } + } + print_statement(s->next, depth); + } + + int main(int argc, char *argv[]) + { + int fd = open(argv[1], O_RDONLY); + int len = lseek(fd, 0, 2); + char *file = mmap(NULL, len, PROT_READ, MAP_SHARED, fd, 0); + struct section *s = code_extract(file, file+len, NULL); + struct token_config config = { + .ignored = (1 << TK_line_comment) + | (1 << TK_block_comment), + .number_chars = ".,_+-", + .word_start = "", + .word_cont = "", + }; + parse_itest(s->code, &config, argc > 2 ? stderr : NULL); + while (s) { + struct section *t = s->next; + code_free(s->code); + free(s); + s = t; + } + exit(0); + } + + +# indent: grammar + +~~~~~~ + +Program -> Statementlist ${ print_statement($1, 0); }$ + +OptNL -> NEWLINE + | + +$*statement + Statementlist -> Statements ${ $0 = $<1; }$ + + Statements -> Statements Statement ${ + { + struct statement **s; + $0 = $<1; + s = &$0; + while (*s) + s = &(*s)->next; + *s = $<2; + } + }$ + | Statement ${ $0 = $<1; }$ + | ERROR ${ printf("statement ERROR\n"); $0 = NULL; }$ + + Open -> { + | NEWLINE { + Close -> } + | NEWLINE } + Block -> Open Statementlist Close ${ $0 = $<2; }$ + | Open SimpleStatements } ${ $0 = $<2; }$ + | : Statementlist ${ $0 = $2; $2 = NULL; }$ + + SimpleStatements -> SimpleStatements ; SimpleStatement ${ + { + struct statement **s; + $0 = $<1; + s = &$0; + while (*s) + s = &(*s)->next; + *s = $<3; + } + }$ + | SimpleStatement ${ $0 = $<1; }$ + | SimpleStatements ; ${ $0 = $<1; }$ + + SimpleStatement -> Factor = Expression ${ + $0 = calloc(1, sizeof(struct statement)); + $0->expr = calloc(1, sizeof(struct expression)); + $0->expr->left = $<1; + $0->expr->op = $2.txt; + $0->expr->right = $<3; + }$ + Statement -> SimpleStatements NEWLINE ${ + $0 = $<1; + }$ + | IfStatement ${ $0 = $<1; }$ + | Statement NEWLINE ${ $0 = $<1; }$ + + IfStatement -> if Expression Block OptNL ${ + $0 = calloc(1, sizeof(struct statement)); + $0->expr = $<2; + $0->thenpart = $<3; + }$ + | if Expression : SimpleStatements ${ + $0 = calloc(1, sizeof(struct statement)); + $0->expr = $<2; + $0->thenpart = $<4; + }$ + | if Expression Block OptNL else Block ${ + $0 = calloc(1, sizeof(struct statement)); + $0->expr = $<2; + $0->thenpart = $<3; + $0->elsepart = $<6; + }$ + | if Expression Block OptNL else : SimpleStatements ${ + $0 = calloc(1, sizeof(struct statement)); + $0->expr = $<2; + $0->thenpart = $<3; + $0->elsepart = $<7; + }$ + | if Expression Block OptNL else IfStatement ${ + $0 = calloc(1, sizeof(struct statement)); + $0->expr = $<2; + $0->thenpart = $<3; + $0->elsepart = $<6; + }$ + +$*expression + Expression -> Expression + Term ${ + $0 = calloc(1, sizeof(struct expression)); + $0->op = $2.txt; + $0->left = $<1; + $0->right = $<3; + }$ + | Expression - Term ${ + $0 = calloc(1, sizeof(struct expression)); + $0->op = $2.txt; + $0->left = $<1; + $0->right = $<3; + }$ + | Term ${ $0 = $1; $1 = NULL; }$ + Term -> Term * Factor ${ + $0 = calloc(1, sizeof(struct expression)); + $0->op = $2.txt; + $0->left = $<1; + $0->right = $<3; + }$ + | Term / Factor ${ + $0 = calloc(1, sizeof(struct expression)); + $0->op = $2.txt; + $0->left = $<1; + $0->right = $<3; + }$ + | Factor ${ $0 = $1; $1 = NULL; }$ + Factor -> IDENTIFIER ${ + $0 = calloc(1, sizeof(struct expression)); + $0->op = $1.txt; + }$ +~~~~~~ + +# File: itest.code + + # test code + ~~~~~~ + hello = yes; mister = no; + there = x; + all = y; + if cond + cond2 : + hello = x; + hello2 = x; + + sum = val + + val; + + if condX: + foo = x * + x + + y + / two; + else if cond2: + there1 =x + there1a=x + there2=x + there3=x; + all = y; + if true {yes=x;} else : no=x + if true: yes = no; no = yes; + + if false { + print = OK + } else { + print = not_OK + } + + if a: + if b: + c= d + x = y + diff --git a/csrc/itest.code b/csrc/itest.code deleted file mode 100644 index 86b71a4..0000000 --- a/csrc/itest.code +++ /dev/null @@ -1,38 +0,0 @@ - -# stuff - - hello = yes; mister = no; - there = x; - all = y; - if cond + cond2 : - hello = x; - hello2 = x; - - sum = val + - val; - - if condX: - foo = x * - x + - y - / two; - else if cond2: - there1 =x - there1a=x - there2=x - there3=x; - all = y; - if true {yes=x;} else : no=x - if true: yes = no; no = yes; - - if false { - print = OK - } else { - print = not_OK - } - - if a: - if b: - c= d - x = y -