]> ocean-lang.org Git - ocean/blobdiff - csrc/oceani.mdc
scanner: change the meaning of ignoring comment tokens.
[ocean] / csrc / oceani.mdc
index f5983440c25ea87ef0dcae5489b70012f40d3e12..ab6abe91f67156e03a0e81926897d320e652b04a 100644 (file)
@@ -171,9 +171,7 @@ structures can be used.
                char *section = NULL;
                struct parse_context context = {
                        .config = {
-                               .ignored = (1 << TK_line_comment)
-                                        | (1 << TK_block_comment)
-                                        | (1 << TK_mark),
+                               .ignored = (1 << TK_mark),
                                .number_chars = ".,_+- ",
                                .word_start = "_",
                                .word_cont = "_",
@@ -633,8 +631,8 @@ there are errors.
 
 ###### includes
        #include <gmp.h>
-       #include "string.h"
-       #include "number.h"
+       #include "parse_string.h"
+       #include "parse_number.h"
 
 ###### libs
        myLDLIBS := libnumber.o libstring.o -lgmp
@@ -1744,9 +1742,9 @@ make a copy of an array with controllable depth.
 
 ###### print binode cases
        case Index:
-               print_exec(b->left, -1, 0);
+               print_exec(b->left, -1, bracket);
                printf("[");
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
                printf("]");
                break;
 
@@ -1930,7 +1928,7 @@ function will be needed.
        case Xfieldref:
        {
                struct fieldref *f = cast(fieldref, e);
-               print_exec(f->left, -1, 0);
+               print_exec(f->left, -1, bracket);
                printf(".%.*s", f->name.len, f->name.txt);
                break;
        }
@@ -2001,41 +1999,50 @@ function will be needed.
 
 ###### top level grammar
        DeclareStruct -> struct IDENTIFIER FieldBlock ${ {
-               struct type *t =
-                       add_type(c, $2.txt, &structure_prototype);
-               int cnt = 0;
-               struct fieldlist *f;
-
-               for (f = $3; f; f=f->prev)
-                       cnt += 1;
-
-               t->structure.nfields = cnt;
-               t->structure.fields = calloc(cnt, sizeof(struct field));
-               f = $3;
-               while (cnt > 0) {
-                       cnt -= 1;
-                       t->structure.fields[cnt] = f->f;
-                       f->f.init = val_prepare(Tnone);
-                       f = f->prev;
-               }
-       } }$
+                       struct type *t =
+                               add_type(c, $2.txt, &structure_prototype);
+                       int cnt = 0;
+                       struct fieldlist *f;
+
+                       for (f = $3; f; f=f->prev)
+                               cnt += 1;
+
+                       t->structure.nfields = cnt;
+                       t->structure.fields = calloc(cnt, sizeof(struct field));
+                       f = $3;
+                       while (cnt > 0) {
+                               cnt -= 1;
+                               t->structure.fields[cnt] = f->f;
+                               f->f.init = val_prepare(Tnone);
+                               f = f->prev;
+                       }
+               } }$
+               | DeclareStruct NEWLINE
 
        $void
+       Newlines -> NEWLINE
+               | Newlines NEWLINE
        Open -> {
-               | NEWLINE Open
+               | Newlines {
        Close -> }
-               | NEWLINE Close
+               | Newlines }
        $*fieldlist
-       FieldBlock -> Open FieldList Close ${ $0 = $<2; }$
+       FieldBlock -> Open FieldList } ${ $0 = $<2; }$
                | Open SimpleFieldList } ${ $0 = $<2; }$
-               | : FieldList  ${ $0 = $<2; }$
+               | : FieldList $$NEWLINE ${ $0 = $<2; }$
 
-       FieldList -> SimpleFieldList NEWLINE ${ $0 = $<1; }$
-               | FieldList SimpleFieldList NEWLINE ${
+       FieldList -> FieldLines ${ $0 = $<1; }$
+               | Newlines FieldLines ${ $0 = $<2; }$
+       FieldLines -> SimpleFieldListLine ${ $0 = $<1; }$
+               | FieldLines SimpleFieldListLine ${
                        $2->prev = $<1;
                        $0 = $<2;
                }$
 
+       SimpleFieldListLine -> SimpleFieldList NEWLINE ${ $0 = $<1; }$
+               | SimpleFieldListLine NEWLINE ${ $0 = $<1; }$
+               | ERROR NEWLINE ${ tok_err(c, "Syntax error in struct field", &$1); }$
+
        SimpleFieldList -> Field ${ $0 = $<1; }$
                | SimpleFieldList ; Field ${
                        $3->prev = $<1;
@@ -2067,7 +2074,6 @@ function will be needed.
                        $0->f.type = $<3;
                        $0->f.init = val_init($3);
                }$
-               | ERROR ${ tok_err(c, "Syntax error in struct field", &$1); }$
 
 ###### forward decls
        static void structure_print_type(struct type *t, FILE *f);
@@ -2472,8 +2478,11 @@ room for ambiguity, so a full conditional expression is allowed in there.
 
 ###### Grammar
 
+       $LEFT if $$ifelse
+       ## expr precedence
+
        $*exec
-       Expression -> BoolExpr if Expression else Expression ${ {
+       Expression -> Expression if Expression else Expression $$ifelse ${ {
                        struct binode *b1 = new(binode);
                        struct binode *b2 = new(binode);
                        b1->op = CondExpr;
@@ -2484,17 +2493,19 @@ room for ambiguity, so a full conditional expression is allowed in there.
                        b2->right = $<5;
                        $0 = b1;
                } }$
-               | BoolExpr ${ $0 = $<1; }$
+               ## expression grammar
 
 ###### print binode cases
 
        case CondExpr:
                b2 = cast(binode, b->right);
-               print_exec(b2->left, -1, 0);
+               if (bracket) printf("(");
+               print_exec(b2->left, -1, bracket);
                printf(" if ");
-               print_exec(b->left, -1, 0);
+               print_exec(b->left, -1, bracket);
                printf(" else ");
-               print_exec(b2->right, -1, 0);
+               print_exec(b2->right, -1, bracket);
+               if (bracket) printf(")");
                break;
 
 ###### propagate binode cases
@@ -2540,73 +2551,83 @@ if the result would make a difference.
        OrElse,
        Not,
 
-###### Grammar
+###### expr precedence
+       $LEFT or
+       $LEFT and
+       $LEFT not
 
-       $*exec
-       BoolExpr -> BoolExpr or BTerm ${ {
+###### expression grammar
+               | Expression or Expression ${ {
                        struct binode *b = new(binode);
                        b->op = Or;
                        b->left = $<1;
                        b->right = $<3;
                        $0 = b;
                } }$
-               | BoolExpr or else BTerm ${ {
+               | Expression or else Expression ${ {
                        struct binode *b = new(binode);
                        b->op = OrElse;
                        b->left = $<1;
                        b->right = $<4;
                        $0 = b;
                } }$
-               | BTerm ${ $0 = $<1; }$
 
-       BTerm -> BTerm and BFact ${ {
+               | Expression and Expression ${ {
                        struct binode *b = new(binode);
                        b->op = And;
                        b->left = $<1;
                        b->right = $<3;
                        $0 = b;
                } }$
-               | BTerm and then BFact ${ {
+               | Expression and then Expression ${ {
                        struct binode *b = new(binode);
                        b->op = AndThen;
                        b->left = $<1;
                        b->right = $<4;
                        $0 = b;
                } }$
-               | BFact ${ $0 = $<1; }$
 
-       BFact -> not BFact ${ {
+               | not Expression ${ {
                        struct binode *b = new(binode);
                        b->op = Not;
                        b->right = $<2;
                        $0 = b;
                } }$
-               ## other BFact
 
 ###### print binode cases
        case And:
-               print_exec(b->left, -1, 0);
+               if (bracket) printf("(");
+               print_exec(b->left, -1, bracket);
                printf(" and ");
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
+               if (bracket) printf(")");
                break;
        case AndThen:
-               print_exec(b->left, -1, 0);
+               if (bracket) printf("(");
+               print_exec(b->left, -1, bracket);
                printf(" and then ");
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
+               if (bracket) printf(")");
                break;
        case Or:
-               print_exec(b->left, -1, 0);
+               if (bracket) printf("(");
+               print_exec(b->left, -1, bracket);
                printf(" or ");
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
+               if (bracket) printf(")");
                break;
        case OrElse:
-               print_exec(b->left, -1, 0);
+               if (bracket) printf("(");
+               print_exec(b->left, -1, bracket);
                printf(" or else ");
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
+               if (bracket) printf(")");
                break;
        case Not:
+               if (bracket) printf("(");
                printf("not ");
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
+               if (bracket) printf(")");
                break;
 
 ###### propagate binode cases
@@ -2679,15 +2700,17 @@ expression operator.
        Eql,
        NEql,
 
-###### other BFact
-       | Expr CMPop Expr ${ {
+###### expr precedence
+       $LEFT < > <= >= == != CMPop
+
+###### expression grammar
+       | Expression CMPop Expression ${ {
                struct binode *b = new(binode);
                b->op = $2.op;
                b->left = $<1;
                b->right = $<3;
                $0 = b;
        } }$
-       | Expr ${ $0 = $<1; }$
 
 ###### Grammar
 
@@ -2707,7 +2730,8 @@ expression operator.
        case GtrEq:
        case Eql:
        case NEql:
-               print_exec(b->left, -1, 0);
+               if (bracket) printf("(");
+               print_exec(b->left, -1, bracket);
                switch(b->op) {
                case Less:   printf(" < "); break;
                case LessEq: printf(" <= "); break;
@@ -2717,7 +2741,8 @@ expression operator.
                case NEql:   printf(" != "); break;
                default: abort();               // NOTEST
                }
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
+               if (bracket) printf(")");
                break;
 
 ###### propagate binode cases
@@ -2787,34 +2812,35 @@ precedence is handled better I might be able to discard this.
        Absolute, Negate,
        Bracket,
 
-###### Grammar
+###### expr precedence
+       $LEFT + - Eop
+       $LEFT * / % ++ Top
+       $LEFT Uop
 
-       $*exec
-       Expr -> Expr Eop Term ${ {
+###### expression grammar
+               | Expression Eop Expression ${ {
                        struct binode *b = new(binode);
                        b->op = $2.op;
                        b->left = $<1;
                        b->right = $<3;
                        $0 = b;
                } }$
-               | Term ${ $0 = $<1; }$
 
-       Term -> Term Top Factor ${ {
+               | Expression Top Expression ${ {
                        struct binode *b = new(binode);
                        b->op = $2.op;
                        b->left = $<1;
                        b->right = $<3;
                        $0 = b;
                } }$
-               | Factor ${ $0 = $<1; }$
 
-       Factor -> ( Expression ) ${ {
+               | ( Expression ) ${ {
                        struct binode *b = new_pos(binode, $1);
                        b->op = Bracket;
                        b->right = $<2;
                        $0 = b;
                } }$
-               | Uop Factor ${ {
+               | Uop Expression ${ {
                        struct binode *b = new(binode);
                        b->op = $1.op;
                        b->right = $<2;
@@ -2842,7 +2868,8 @@ precedence is handled better I might be able to discard this.
        case Divide:
        case Concat:
        case Rem:
-               print_exec(b->left, indent, 0);
+               if (bracket) printf("(");
+               print_exec(b->left, indent, bracket);
                switch(b->op) {
                case Plus:   fputs(" + ", stdout); break;
                case Minus:  fputs(" - ", stdout); break;
@@ -2852,19 +2879,24 @@ precedence is handled better I might be able to discard this.
                case Concat: fputs(" ++ ", stdout); break;
                default: abort();       // NOTEST
                }                       // NOTEST
-               print_exec(b->right, indent, 0);
+               print_exec(b->right, indent, bracket);
+               if (bracket) printf(")");
                break;
        case Absolute:
+               if (bracket) printf("(");
                printf("+");
-               print_exec(b->right, indent, 0);
+               print_exec(b->right, indent, bracket);
+               if (bracket) printf(")");
                break;
        case Negate:
+               if (bracket) printf("(");
                printf("-");
-               print_exec(b->right, indent, 0);
+               print_exec(b->right, indent, bracket);
+               if (bracket) printf(")");
                break;
        case Bracket:
                printf("(");
-               print_exec(b->right, indent, 0);
+               print_exec(b->right, indent, bracket);
                printf(")");
                break;
 
@@ -3022,17 +3054,14 @@ is in-place.
 
 ###### Grammar
 
-       $void
-       Newlines -> NEWLINE
-               | Newlines NEWLINE
-
        $*binode
        Block -> Open Statementlist Close ${ $0 = $<2; }$
                | Open SimpleStatements } ${ $0 = reorder_bilist($<2); }$
                | : SimpleStatements ${ $0 = reorder_bilist($<2); }$
-               | : Statementlist  ${ $0 = $<2; }$
+               | : Statementlist $$OUT ${ $0 = $<2; }$
 
        Statementlist -> ComplexStatements ${ $0 = reorder_bilist($<1); }$
+               | Newlines ComplexStatements ${ $0 = reorder_bilist($<2); }$
 
        ComplexStatements -> ComplexStatements ComplexStatement ${
                        if ($2 == NULL) {
@@ -3056,10 +3085,10 @@ is in-place.
                }$
 
        $*exec
-       ComplexStatement -> SimpleStatements NEWLINE ${
+       ComplexStatement -> SimpleStatementLine ${
                        $0 = reorder_bilist($<1);
                        }$
-               | Newlines ${ $0 = NULL; }$
+               | ComplexStatement NEWLINE ${ $0 = $<1; }$
                ## ComplexStatement Grammar
 
        $*binode
@@ -3075,7 +3104,10 @@ is in-place.
                        $0->left = NULL;
                        $0->right = $<1;
                        }$
-               | SimpleStatements ; ${ $0 = $<1; }$
+
+       SimpleStatementLine -> SimpleStatements NEWLINE ${ $0 = $<1; }$
+               | SimpleStatements ; NEWLINE ${ $0 = $<1; }$
+               | SimpleStatementLine NEWLINE ${ $0 = $<1; }$
 
        SimpleStatement -> pass ${ $0 = NULL; }$
                | ERROR ${ tok_err(c, "Syntax error in statement", &$1); }$
@@ -3088,10 +3120,10 @@ is in-place.
                        if (b->left == NULL)
                                printf("pass");
                        else
-                               print_exec(b->left, indent, 0);
+                               print_exec(b->left, indent, bracket);
                        if (b->right) {
                                printf("; ");
-                               print_exec(b->right, indent, 0);
+                               print_exec(b->right, indent, bracket);
                        }
                } else {
                        // block, one per line
@@ -3194,7 +3226,7 @@ same solution.
                while (b) {
                        if (b->left) {
                                printf(" ");
-                               print_exec(b->left, -1, 0);
+                               print_exec(b->left, -1, bracket);
                                if (b->right)
                                        printf(",");
                        }
@@ -3280,9 +3312,9 @@ it is declared, and error will be raised as the name is created as
 
        case Assign:
                do_indent(indent, "");
-               print_exec(b->left, indent, 0);
+               print_exec(b->left, indent, bracket);
                printf(" = ");
-               print_exec(b->right, indent, 0);
+               print_exec(b->right, indent, bracket);
                if (indent >= 0)
                        printf("\n");
                break;
@@ -3291,7 +3323,7 @@ it is declared, and error will be raised as the name is created as
                {
                struct variable *v = cast(var, b->left)->var;
                do_indent(indent, "");
-               print_exec(b->left, indent, 0);
+               print_exec(b->left, indent, bracket);
                if (cast(var, b->left)->var->constant) {
                        if (v->where_decl == v->where_set) {
                                printf("::");
@@ -3309,7 +3341,7 @@ it is declared, and error will be raised as the name is created as
                }
                if (b->right) {
                        printf("= ");
-                       print_exec(b->right, indent, 0);
+                       print_exec(b->right, indent, bracket);
                }
                if (indent >= 0)
                        printf("\n");
@@ -3404,7 +3436,7 @@ function.
 
        case Use:
                do_indent(indent, "use ");
-               print_exec(b->right, -1, 0);
+               print_exec(b->right, -1, bracket);
                if (indent >= 0)
                        printf("\n");
                break;
@@ -3531,14 +3563,14 @@ defined.
        case Xcond_statement: free_cond_statement(cast(cond_statement, e)); break;
 
 ###### ComplexStatement Grammar
-       | CondStatement ${ $0 = $<1; }$
+       | CondStatement $$NEWLINE ${ $0 = $<1; }$
 
 ###### Grammar
 
        $*cond_statement
        // both ForThen and Whilepart open scopes, and CondSuffix only
        // closes one - so in the first branch here we have another to close.
-       CondStatement -> forPart ThenPart WhilePart CondSuffix ${
+       CondStatement -> ForPart ThenPart WhilePart CondSuffix ${
                        $0 = $<4;
                        $0->forpart = $<1;
                        $0->thenpart = $<2;
@@ -3546,7 +3578,7 @@ defined.
                        $0->dopart = $3.dopart; $3.dopart = NULL;
                        var_block_close(c, CloseSequential);
                        }$
-               |  forPart WhilePart CondSuffix ${
+               |  ForPart WhilePart CondSuffix ${
                        $0 = $<3;
                        $0->forpart = $<1;
                        $0->thenpart = NULL;
@@ -3554,16 +3586,18 @@ defined.
                        $0->dopart = $2.dopart; $2.dopart = NULL;
                        var_block_close(c, CloseSequential);
                        }$
-               | whilePart CondSuffix ${
+               | WhilePart CondSuffix ${
                        $0 = $<2;
                        $0->condpart = $1.condpart; $1.condpart = NULL;
                        $0->dopart = $1.dopart; $1.dopart = NULL;
                        }$
-               | switchPart CondSuffix ${
-                       $0 = $<2;
+               | SwitchPart CasePart CondSuffix ${
+                       $0 = $<3;
                        $0->condpart = $<1;
+                       $2->next = $0->casepart;
+                       $0->casepart = $<2;
                        }$
-               | ifPart IfSuffix ${
+               | IfPart IfSuffix ${
                        $0 = $<2;
                        $0->condpart = $1.condpart; $1.condpart = NULL;
                        $0->thenpart = $1.thenpart; $1.thenpart = NULL;
@@ -3583,108 +3617,120 @@ defined.
                        $0->casepart = $<1;
                }$
 
-       $void
-       Case -> case
-               | NEWLINE Case
        $*casepart
-       CasePart -> Case Expression OpenScope Block ${
+       CasePart -> case Expression OpenScope Block ${
                        $0 = calloc(1,sizeof(struct casepart));
                        $0->value = $<2;
                        $0->action = $<4;
                        var_block_close(c, CloseParallel);
                }$
+               | CasePart NEWLINE ${ $0 = $<1; }$
 
        $*cond_statement
        IfSuffix ->  ${ $0 = new(cond_statement); }$
-               | NEWLINE IfSuffix ${ $0 = $<2; }$
+               | IfSuffix NEWLINE ${ $0 = $<1; }$
                | else OpenScope Block ${
                        $0 = new(cond_statement);
                        $0->elsepart = $<3;
                        var_block_close(c, CloseElse);
                }$
+               | else OpenScope SimpleStatements NEWLINE ${
+                       $0 = new(cond_statement);
+                       $0->elsepart = reorder_bilist($<3);
+                       var_block_close(c, CloseElse);
+               }$
                | else OpenScope CondStatement ${
                        $0 = new(cond_statement);
                        $0->elsepart = $<3;
                        var_block_close(c, CloseElse);
                }$
 
-       $void
-       Then -> then
-               | NEWLINE Then
-       While -> while
-               | NEWLINE While
-       Do -> do
-               | NEWLINE Do
        $*exec
        // These scopes are closed in CondSuffix
-       forPart -> for OpenScope SimpleStatements ${
+       ForPart -> for OpenScope SimpleStatements ; ${
+                       $0 = reorder_bilist($<3);
+               }$
+               | for OpenScope SimpleStatements NEWLINE ${
                        $0 = reorder_bilist($<3);
                }$
                |  for OpenScope Block ${
                        $0 = $<3;
                }$
+               |  ForPart NEWLINE ${ $0 = $<1; }$
 
-       ThenPart -> Then OpenScope SimpleStatements ${
+       ThenPart -> then OpenScope SimpleStatements ; ${
                        $0 = reorder_bilist($<3);
                        var_block_close(c, CloseSequential);
                }$
-               |  Then OpenScope Block ${
+               | then OpenScope SimpleStatements NEWLINE ${
+                       $0 = reorder_bilist($<3);
+                       var_block_close(c, CloseSequential);
+               }$
+               |  then OpenScope Block ${
                        $0 = $<3;
                        var_block_close(c, CloseSequential);
                }$
+               |  ThenPart NEWLINE ${ $0 = $<1; }$
 
        // This scope is closed in CondSuffix
-       WhileHead -> While OpenScope Block ${
-               $0 = $<3;
-               }$
-       whileHead -> while OpenScope Block ${
-               $0 = $<3;
-               }$
+       WhileHead -> while OpenScope Block ${ $0 = $<3; }$
+               | WhileHead NEWLINE ${ $0 = $<1; }$
 
        $cond_statement
        // This scope is closed in CondSuffix
-       whilePart -> while OpenScope Expression Block ${
+       WhilePart -> while OpenScope Expression Block ${
                        $0.type = Xcond_statement;
                        $0.condpart = $<3;
                        $0.dopart = $<4;
                }$
-               | whileHead Do Block ${
+               | WhileHead do Block ${
                        $0.type = Xcond_statement;
                        $0.condpart = $<1;
                        $0.dopart = $<3;
                }$
-       WhilePart -> While OpenScope Expression Block ${
+               | WhilePart NEWLINE ${ $0 = $<1; }$
+
+       IfPart -> if OpenScope Expression OpenScope Block ${
                        $0.type = Xcond_statement;
                        $0.condpart = $<3;
-                       $0.dopart = $<4;
+                       $0.thenpart = $<5;
+                       var_block_close(c, CloseParallel);
                }$
-               | WhileHead Do Block ${
+               | if OpenScope Expression OpenScope then Block ${
                        $0.type = Xcond_statement;
-                       $0.condpart = $<1;
-                       $0.dopart = $<3;
+                       $0.condpart = $<3;
+                       $0.thenpart = $<6;
+                       var_block_close(c, CloseParallel);
                }$
-
-       ifPart -> if OpenScope Expression OpenScope Block ${
+               | if OpenScope Expression OpenScope then SimpleStatements ; ${
                        $0.type = Xcond_statement;
                        $0.condpart = $<3;
-                       $0.thenpart = $<5;
+                       $0.thenpart = reorder_bilist($<6);
                        var_block_close(c, CloseParallel);
                }$
-               | if OpenScope Block Then OpenScope Block ${
+               | if OpenScope Expression OpenScope then SimpleStatements NEWLINE ${
+                       $0.type = Xcond_statement;
+                       $0.condpart = $<3;
+                       $0.thenpart = reorder_bilist($<6);
+                       var_block_close(c, CloseParallel);
+               }$
+               | if OpenScope Block then OpenScope Block ${
                        $0.type = Xcond_statement;
                        $0.condpart = $<3;
                        $0.thenpart = $<6;
                        var_block_close(c, CloseParallel);
                }$
+               | IfPart NEWLINE ${ $0 = $<1; }$
 
        $*exec
        // This scope is closed in CondSuffix
-       switchPart -> switch OpenScope Expression ${
+       SwitchPart -> switch OpenScope Expression ${
                        $0 = $<3;
                }$
                | switch OpenScope Block ${
                        $0 = $<3;
                }$
+               | SwitchPart NEWLINE ${ $0 = $<1; }$
 
 ###### print exec cases
 
@@ -3922,14 +3968,15 @@ various declarations in the parse context.
 
        $void
        Ocean -> DeclarationList
+               | Newlines DeclarationList
 
        DeclarationList -> Declaration
                | DeclarationList Declaration
 
-       Declaration -> DeclareConstant
+       Declaration -> Declaration NEWLINE
+               | DeclareConstant
                | DeclareProgram
                | DeclareStruct
-               | NEWLINE
                | ERROR NEWLINE ${
                        tok_err(c,
                                "error: unhandled parse error", &$1);
@@ -3964,17 +4011,19 @@ searching through for the Nth constant for decreasing N.
 
        DeclareConstant -> const Open ConstList Close
                | const Open SimpleConstList }
-               | const : ConstList
+               | const : ConstList $$NEWLINE
                | const SimpleConstList NEWLINE
 
-       ConstList -> ComplexConsts
-               | NEWLINE ConstList
-       ComplexConsts -> ComplexConst ComplexConsts
-               | ComplexConst
-       ComplexConst -> SimpleConstList NEWLINE
+       ConstList -> ConstLines
+               | Newlines ConstLines
+       ConstLines -> ConstLines SimpleConstLine
+               | SimpleConstLine
        SimpleConstList -> SimpleConstList ; Const
                | Const
                | SimpleConstList ;
+       SimpleConstLine -> SimpleConstList NEWLINE
+               | SimpleConstLine NEWLINE
+               | ERROR NEWLINE ${ tok_err(c, "Syntax error in constant", &$1); }$
 
        $*type
        CType -> Type   ${ $0 = $<1; }$
@@ -4007,7 +4056,6 @@ searching through for the Nth constant for decreasing N.
                        v->val = interp_exec($5);
                }
        } }$
-       | ERROR NEWLINE ${ tok_err(c, "Syntax error in constant", &$1); }$
 
 ###### print const decls
        {
@@ -4078,10 +4126,6 @@ analysis is a bit more interesting at this level.
                var_block_close(c, CloseSequential);
                if (c->scope_stack && !c->parse_error) abort();
                }$
-               | ERROR ${
-                       tok_err(c,
-                               "error: unhandled parse error", &$1);
-               }$
 
        Varlist -> Varlist ArgDecl ${
                        $0 = new(binode);
@@ -4310,6 +4354,8 @@ things which will likely grow as the languages grows.
                        print "", list[i],
                print
 
+               if 1 == 2 then print "yes"; else print "no"
+
                bob:fred
                bob.name = "Hello"
                bob.alive = (bob.name == "Hello")