jitcraft/Parser.cpp
author David Anderson <dvander@alliedmods.net>
Sun Jul 08 16:49:17 2012 -0700 (2012-07-08)
changeset 63 dd57743d220e
parent 59 b7d61ddb3c8d
child 66 cbba1997dc71
permissions -rw-r--r--
Added support for forwards.
     1 /* vim: set ts=4 sw=4 tw=99 et:
     2  *
     3  * Copyright (C) 2012 David Anderson
     4  *
     5  * This file is part of JITCraft.
     6  *
     7  * JITCraft is free software: you can redistribute it and/or modify it under
     8  * the terms of the GNU General Public License as published by the Free
     9  * Software Foundation, either version 3 of the License, or (at your option)
    10  * any later version.
    11  * 
    12  * Foobar is distributed in the hope that it will be useful, but WITHOUT ANY
    13  * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
    14  * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
    15  *
    16  * You should have received a copy of the GNU General Public License along with
    17  * JITCraft. If not, see http://www.gnu.org/licenses/.
    18  */
    19 #include "Zone.h"
    20 #include "Parser.h"
    21 #include "FixedArray.h"
    22 #include "Heap.h"
    23 #include "Strings.h"
    24 #include "Heap-inl.h"
    25 
    26 using namespace ke;
    27 
    28 Parser::Parser(Zone *zone, CompileContext &cc, const char *stream, size_t length)
    29   : zone_(zone),
    30     cc_(cc),
    31     pool_(zone_->pool()),
    32     scanner_(cc, stream, length),
    33     scope_(NULL),
    34     unbound_(NULL)
    35 {
    36     unbound_ = new (pool_) PoolList<NameProxy *>();
    37 }
    38 
    39 bool
    40 Parser::match(TokenKind kind)
    41 {
    42     if (scanner_.peek() != kind)
    43         return false;
    44     scanner_.scan();
    45     return true;
    46 }
    47 
    48 bool
    49 Parser::matchSemicolon()
    50 {
    51     return expect(TOK_SEMICOLON);
    52 }
    53 
    54 bool
    55 Parser::expect(TokenKind kind)
    56 {
    57     TokenKind got = scanner_.scan();
    58     if (got == kind)
    59         return true;
    60     cc_.reportError(scanner_.begin(), Message_WrongToken, TokenNames[kind], TokenNames[got]);
    61     return false;
    62 }
    63 
    64 Scope *
    65 Parser::enterScope(Scope::Kind kind)
    66 {
    67     scope_ = new (pool_) Scope(pool_, kind, scope_);
    68     if (!scope_->initialize())
    69         return NULL;
    70     return scope_;
    71 }
    72 
    73 NameProxy *
    74 Parser::bind(Handle<String> name)
    75 {
    76     BoundName *bound = scope_->lookup(name);
    77     NameProxy *proxy = new (pool_) NameProxy(scanner_.begin(), name, bound);
    78     if (!bound && !unbound_->append(proxy))
    79         return NULL;
    80     return proxy;
    81 }
    82 
    83 bool
    84 Parser::matchName(String **name, TokenKind kind)
    85 {
    86     assert(kind == TOK_NAME || kind == TOK_LABEL);
    87     *name = NULL;
    88     if (!match(kind))
    89         return false;
    90     *name = zone_->makeSymbol(scanner_.literal(), scanner_.literal_length());
    91     return true;
    92 }
    93 
    94 String *
    95 Parser::expectName()
    96 {
    97     if (!expect(TOK_NAME))
    98         return NULL;
    99     return zone_->makeSymbol(scanner_.literal(), scanner_.literal_length());
   100 }
   101 
   102 void
   103 Parser::redeclarationError(BoundName *other)
   104 {
   105     cc_.reportError(scanner_.begin(), Message_RedeclaredName, other->name()->chars(),
   106                     other->pos().line, other->pos().col);
   107 }
   108 
   109 Expression *
   110 Parser::primitive()
   111 {
   112     TokenKind kind = scanner_.peek();
   113     switch (kind) {
   114       case TOK_NAME:
   115       {
   116         Local<String> name(zone_, expectName());
   117         if (!name)
   118             return NULL;
   119         return bind(name);
   120       }
   121 
   122       case TOK_FLOAT_LITERAL:
   123       {
   124         scanner_.scan();
   125         double value = Scanner::ParseDouble(scanner_.literal());
   126         return new (pool_) FloatLiteral(scanner_.begin(), value);
   127       }
   128 
   129       case TOK_INTEGER_LITERAL:
   130       {
   131         scanner_.scan();
   132         int value = atoi(scanner_.literal());
   133         return new (pool_) IntegerLiteral(scanner_.begin(), value);
   134       }
   135 
   136       case TOK_STRING_LITERAL:
   137       {
   138         scanner_.scan();
   139         Local<ByteArray> array(zone_, ByteArray::New(zone_, scanner_.literal_length() + 1));
   140         if (!array)
   141             return NULL;
   142         memcpy(array->raw(), scanner_.literal(), scanner_.literal_length() + 1);
   143         return new (pool_) StringLiteral(scanner_.begin(), array);
   144       }
   145 
   146       default:
   147       {
   148         if (kind != TOK_ERROR)
   149             cc_.reportError(scanner_.begin(), Message_ExpectedExpression, TokenNames[kind]);
   150         return NULL;
   151       }
   152     }
   153 }
   154 
   155 Expression *
   156 Parser::prefix()
   157 {
   158     switch (scanner_.peek()) {
   159       case TOK_LPAREN:
   160       {
   161         scanner_.scan();
   162         Expression *expr = expression();
   163         if (!expr)
   164             return NULL;
   165         if (!expect(TOK_RPAREN))
   166             return NULL;
   167         return expr;
   168       }
   169 
   170       default:
   171         return primitive();
   172     }
   173 }
   174 
   175 Expression *
   176 Parser::call(Expression *callee)
   177 {
   178     ExpressionList *arguments = new (pool_) ExpressionList();
   179 
   180     SourcePosition pos = scanner_.begin();
   181     expect(TOK_LPAREN);
   182     
   183     if (!match(TOK_RPAREN)) {
   184         while (true) {
   185             Expression *expr = expression();
   186             if (!expr)
   187                 return NULL;
   188 
   189             if (!arguments->append(expr))
   190                 return NULL;
   191 
   192             if (!match(TOK_COMMA))
   193                 break;
   194         }
   195 
   196         if (!expect(TOK_RPAREN))
   197             return NULL;
   198     }
   199 
   200     return new (pool_) CallExpression(pos, callee, arguments);
   201 }
   202 
   203 Expression *
   204 Parser::index(Expression *left)
   205 {
   206     expect(TOK_LBRACKET);
   207     
   208     SourcePosition pos = scanner_.begin();
   209     Expression *expr = expression();
   210     if (!expr)
   211         return NULL;
   212 
   213     if (!expect(TOK_RBRACKET))
   214         return NULL;
   215 
   216     return new (pool_) IndexExpression(pos, left, expr);
   217 }
   218 
   219 Expression *
   220 Parser::primary()
   221 {
   222     Expression *expr = prefix();
   223     if (!expr)
   224         return NULL;
   225 
   226     for (;;) {
   227         switch (scanner_.peek()) {
   228           case TOK_LPAREN:
   229             expr = call(expr);
   230             if (!expr)
   231                 return NULL;
   232             break;
   233 
   234           case TOK_LBRACKET:
   235             expr = index(expr);
   236             if (!expr)
   237                 return NULL;
   238             break;
   239 
   240           default:
   241             return expr;
   242         }
   243     }
   244 }
   245 
   246 Expression *
   247 Parser::unary()
   248 {
   249     TokenKind token = scanner_.peek();
   250 
   251     SourcePosition pos = scanner_.begin();
   252     switch (token) {
   253       case TOK_INCREMENT:
   254       case TOK_DECREMENT:
   255       {
   256         scanner_.scan();
   257         Expression *expr = expression();
   258         if (!expr)
   259             return NULL;
   260 
   261         return new (pool_) IncDecExpression(pos, token, expr, false);
   262       }
   263       default:
   264         break;
   265     }
   266 
   267 
   268     Expression *expr = primary();
   269 
   270     token = scanner_.peek();
   271     if (token == TOK_INCREMENT || token == TOK_DECREMENT) {
   272         scanner_.scan();
   273         return new (pool_) IncDecExpression(pos, token, expr, true);
   274     }
   275 
   276     return expr;
   277 }
   278 
   279 Expression *
   280 Parser::multiplication()
   281 {
   282     Expression *left = unary();
   283     do {
   284         if (!match(TOK_SLASH) && !match(TOK_STAR))
   285             break;
   286         SourcePosition pos = scanner_.begin();
   287         TokenKind kind = scanner_.last();
   288         Expression *right = unary();
   289         if (!right)
   290             return NULL;
   291         left = new (pool_) BinaryExpression(pos, kind, left, right);
   292     } while (left);
   293     return left;
   294 }
   295 
   296 Expression *
   297 Parser::addition()
   298 {
   299     Expression *left = multiplication();
   300     while (left) {
   301         if (!match(TOK_PLUS) && !match(TOK_MINUS))
   302             break;
   303         SourcePosition pos = scanner_.begin();
   304         TokenKind kind = scanner_.last();
   305         Expression *right = multiplication();
   306         if (!right)
   307             return NULL;
   308         left = new (pool_) BinaryExpression(pos, kind, left, right);
   309     }
   310     return left;
   311 }
   312 
   313 Expression *
   314 Parser::shift()
   315 {
   316     Expression *left = addition();
   317     while (left) {
   318         if (!match(TOK_SHL) && !match(TOK_SHR) && !match(TOK_USHR))
   319             break;
   320         SourcePosition pos = scanner_.begin();
   321         TokenKind kind = scanner_.last();
   322         Expression *right = addition();
   323         if (!right)
   324             return NULL;
   325         left = new (pool_) BinaryExpression(pos, kind, left, right);
   326     }
   327     return left;
   328 }
   329 
   330 Expression *
   331 Parser::bitand_()
   332 {
   333     Expression *left = shift();
   334     while (left) {
   335         if (!match(TOK_BITAND))
   336             break;
   337         SourcePosition pos = scanner_.begin();
   338         Expression *right = shift();
   339         if (!right)
   340             return NULL;
   341         left = new (pool_) BinaryExpression(pos, TOK_BITAND, left, right);
   342     }
   343     return left;
   344 }
   345 
   346 Expression *
   347 Parser::bitxor()
   348 {
   349     Expression *left = bitand_();
   350     while (left) {
   351         if (!match(TOK_BITXOR))
   352             break;
   353         SourcePosition pos = scanner_.begin();
   354         Expression *right = shift();
   355         if (!right)
   356             return NULL;
   357         left = new (pool_) BinaryExpression(pos, TOK_BITXOR, left, right);
   358     }
   359     return left;
   360 }
   361 
   362 Expression *
   363 Parser::bitor_()
   364 {
   365     Expression *left = bitxor();
   366     while (left) {
   367         if (!match(TOK_BITOR))
   368             break;
   369         SourcePosition pos = scanner_.begin();
   370         Expression *right = shift();
   371         if (!right)
   372             return NULL;
   373         left = new (pool_) BinaryExpression(pos, TOK_BITOR, left, right);
   374     }
   375     return left;
   376 }
   377 
   378 Expression *
   379 Parser::relational()
   380 {
   381     Expression *left = bitor_();
   382     while (left) {
   383         TokenKind kind = scanner_.peek();
   384         if (kind < TOK_LT || kind > TOK_GE)
   385             break;
   386         scanner_.scan();
   387         SourcePosition pos = scanner_.begin();
   388         Expression *right = shift();
   389         if (!right)
   390             return NULL;
   391         left = new (pool_) BinaryExpression(pos, kind, left, right);
   392     }
   393     return left;
   394 }
   395 
   396 Expression *
   397 Parser::equals()
   398 {
   399     Expression *left = relational();
   400     while (left) {
   401         if (!match(TOK_EQUALS) && !match(TOK_NOTEQUALS))
   402             break;
   403         TokenKind kind = scanner_.last();
   404         SourcePosition pos = scanner_.begin();
   405         Expression *right = relational();
   406         if (!right)
   407             return NULL;
   408         left = new (pool_) BinaryExpression(pos, kind, left, right);
   409     }
   410     return left;
   411 }
   412 
   413 Expression *
   414 Parser::assignment()
   415 {
   416     Expression *left = equals();
   417     while (left) {
   418         TokenKind token = scanner_.peek();
   419         if (token != TOK_ASSIGN && (token < TOK_ASSIGN_ADD || token > TOK_ASSIGN_SHL))
   420             break;
   421         scanner_.scan();
   422         SourcePosition pos = scanner_.begin();
   423         Expression *expr = equals();
   424         if (!expr)
   425             return NULL;
   426 
   427         left = new (pool_) Assignment(pos, token, left, expr);
   428     }
   429     return left;
   430 }
   431 
   432 Expression *
   433 Parser::expression()
   434 {
   435     return assignment();
   436 }
   437 
   438 Statement *
   439 Parser::while_()
   440 {
   441     SourcePosition pos = scanner_.begin();
   442     scanner_.scan();
   443 
   444     if (!expect(TOK_LPAREN))
   445         return NULL;
   446 
   447     Expression *condition = expression();
   448     if (!condition)
   449         return NULL;
   450 
   451     if (!expect(TOK_RPAREN))
   452         return NULL;
   453 
   454     // Inside a loop, we force the creation of a scope object. Normally, we
   455     // will cull scopes if they have no variables. However inside a loop,
   456     // function calls that take references may compute a LIFO object, and to
   457     // avoid temporarily leaking many such objects, we ensure that a scope
   458     // is present so a LIFO slot can be allocated.
   459     if (!enterScope(Scope::BLOCK))
   460         return NULL;
   461 
   462     Statement *body;
   463     if (scanner_.peek() == TOK_LBRACE)
   464         body = block(scope_);
   465     else
   466         body = localStatement();
   467     if (!body)
   468         return NULL;
   469 
   470     scope_ = scope_->enclosing();
   471     return new (pool_) WhileStatement(pos, TOK_WHILE, condition, body);
   472 }
   473 
   474 Statement *
   475 Parser::do_()
   476 {
   477     SourcePosition pos = scanner_.begin();
   478     scanner_.scan();
   479 
   480     // See the comment in ::while_() as to why we force a scope.
   481     if (!enterScope(Scope::BLOCK))
   482         return NULL;
   483 
   484     Statement *body;
   485     if (scanner_.peek() == TOK_LBRACE)
   486         body = block(scope_);
   487     else
   488         body = localStatement();
   489     if (!body)
   490         return NULL;
   491 
   492     scope_ = scope_->enclosing();
   493 
   494     if (!expect(TOK_WHILE))
   495         return NULL;
   496 
   497     if (!expect(TOK_LPAREN))
   498         return NULL;
   499     Expression *condition = expression();
   500     if (!condition)
   501         return NULL;
   502     if (!expect(TOK_RPAREN))
   503         return NULL;
   504 
   505     return new (pool_) WhileStatement(pos, TOK_DO, condition, body);
   506 }
   507 
   508 Statement *
   509 Parser::forStatement()
   510 {
   511     SourcePosition pos = scanner_.begin();
   512     scanner_.scan();
   513     if (!expect(TOK_LPAREN))
   514         return NULL;
   515 
   516     Statement *decl = NULL;
   517     if (!match(TOK_SEMICOLON)) {
   518         if (scanner_.peek() == TOK_NEW) {
   519             if (!enterScope(Scope::BLOCK))
   520                 return NULL;
   521             if ((decl = variableDeclaration()) == NULL)
   522                 return NULL;
   523         } else {
   524             if ((decl = expressionStatement()) == NULL)
   525                 return NULL;
   526         }
   527         if (!expect(TOK_SEMICOLON))
   528             return NULL;
   529     }
   530 
   531     Expression *condition = NULL;
   532     if (!match(TOK_SEMICOLON)) {
   533         if ((condition = expression()) == NULL)
   534             return NULL;
   535         if (!expect(TOK_SEMICOLON))
   536             return NULL;
   537     }
   538 
   539     Statement *update = NULL;
   540     if (!match(TOK_RPAREN)) {
   541         if ((update = expressionStatement()) == NULL)
   542             return NULL;
   543         if (!expect(TOK_RPAREN))
   544             return NULL;
   545     }
   546 
   547     // See the comment in ::while_() as to why we force a scope.
   548     if (!enterScope(Scope::BLOCK))
   549         return NULL;
   550 
   551     Statement *body;
   552     if (scanner_.peek() == TOK_LBRACE)
   553         body = block(scope_);
   554     else
   555         body = localStatement();
   556     if (!body)
   557         return NULL;
   558 
   559     scope_ = scope_->enclosing();
   560 
   561     Scope *declScope = NULL;
   562     if (decl && decl->isVariableDeclaration()) {
   563         declScope = scope_->unlinkIfEmpty();
   564         scope_ = scope_->enclosing();
   565     }
   566     return new (pool_) ForStatement(pos, declScope, decl, condition, update, body);
   567 }
   568 
   569 VariableDeclaration *
   570 Parser::variableDeclaration()
   571 {
   572     if (!expect(TOK_NEW))
   573         return NULL;
   574 
   575     Local<String> tag(zone_);
   576     if (matchName(tag.ref(), TOK_LABEL) && !tag)
   577         return NULL;
   578 
   579     Local<String> name(zone_, expectName());
   580     if (!name)
   581         return NULL;
   582 
   583     if (BoundName *other = scope_->localLookup(name)) {
   584         redeclarationError(other);
   585         return NULL;
   586     }
   587 
   588     Variable *var = scope_->declareVariable(name, scanner_.begin());
   589     if (!var)
   590         return NULL;
   591 
   592     ExpressionList *postDimensions = NULL;
   593     if (scanner_.peek() == TOK_LBRACKET) {
   594         postDimensions = new (pool_) ExpressionList();
   595         while (match(TOK_LBRACKET)) {
   596             Expression *dim = expression();
   597             if (!dim)
   598                 return NULL;
   599 
   600             if (!expect(TOK_RBRACKET))
   601                 return NULL;
   602 
   603             if (!postDimensions->append(dim))
   604                 return NULL;
   605         }
   606     }
   607     
   608     Expression *expr = NULL;
   609     if (match(TOK_ASSIGN)) {
   610         if ((expr = expression()) == NULL)
   611             return NULL;
   612     }
   613 
   614     return new (pool_) VariableDeclaration(var->pos(), var, tag, postDimensions, expr);
   615 }
   616 
   617 Statement *
   618 Parser::returnStatement()
   619 {
   620     SourcePosition pos = scanner_.begin();
   621     if (!expect(TOK_RETURN))
   622         return NULL;
   623 
   624     Expression *expr = expression();
   625     if (!expr)
   626         return NULL;
   627 
   628     return new (pool_) ReturnStatement(pos, expr);
   629 }
   630 
   631 Statement *
   632 Parser::expressionStatement()
   633 {
   634     Expression *left = assignment();
   635     if (!left)
   636         return NULL;
   637 
   638     return new (pool_) ExpressionStatement(left);
   639 }
   640 
   641 Statement *
   642 Parser::block(Scope *scope)
   643 {
   644     if (!expect(TOK_LBRACE))
   645         return NULL;
   646 
   647     SourcePosition pos = scanner_.begin();
   648     if (!scope && !enterScope(Scope::BLOCK))
   649         return NULL;
   650 
   651     StatementList *statements = new (pool_) StatementList();
   652     while (!match(TOK_RBRACE)) {
   653         Statement *statement = localStatement();
   654         if (statement == NULL)
   655             return NULL;
   656         if (!statements->append(statement))
   657             return NULL;
   658     }
   659 
   660     if (!scope) {
   661     	scope = scope_->unlinkIfEmpty();
   662         scope_ = scope_->enclosing();
   663     }
   664     BlockStatement *block = new (pool_) BlockStatement(pos, scope, statements);
   665     return block;
   666 }
   667 
   668 Statement *
   669 Parser::if_()
   670 {
   671     expect(TOK_IF);
   672     
   673     SourcePosition pos = scanner_.begin();
   674     if (!expect(TOK_LPAREN))
   675         return NULL;
   676 
   677     Expression *cond = expression();
   678     if (!cond)
   679         return NULL;
   680 
   681     if (!expect(TOK_RPAREN))
   682         return NULL;
   683 
   684     Statement *ifTrue = localStatement();
   685     if (!ifTrue)
   686         return NULL;
   687 
   688     IfStatement *outer = new (pool_) IfStatement(pos, cond, ifTrue);
   689 
   690     IfStatement *last = outer;
   691     while (match(TOK_ELSE)) {
   692         if (!match(TOK_IF)) {
   693             Statement *ifFalse = localStatement();
   694             if (!ifFalse)
   695                 return NULL;
   696 
   697             last->setIfFalse(ifFalse);
   698             break;
   699         }
   700 
   701         if (!expect(TOK_IF))
   702             return NULL;
   703 
   704         SourcePosition pos = scanner_.begin();
   705         if (!expect(TOK_LPAREN))
   706             return NULL;
   707 
   708         Expression *otherCond = expression();
   709         if (!otherCond)
   710             return NULL;
   711 
   712         if (!expect(TOK_RPAREN))
   713             return NULL;
   714 
   715         Statement *otherIfTrue = localStatement();
   716         if (!otherIfTrue)
   717             return NULL;
   718 
   719         IfStatement *inner = new (pool_) IfStatement(pos, otherCond, otherIfTrue);
   720         last->setIfFalse(inner);
   721         last = inner;
   722     }
   723 
   724     return outer;
   725 }
   726 
   727 Statement *
   728 Parser::localStatement()
   729 {
   730     Statement *statement = NULL;
   731 
   732     // Statements which must be followed by a semicolon will break out of the
   733     // switch. If they may end in BlockStatements, they'll immediately return.
   734 
   735     switch (scanner_.peek()) {
   736         case TOK_NEW:
   737           if ((statement = variableDeclaration()) == NULL)
   738               return NULL;
   739           break;
   740 
   741         case TOK_FOR:
   742           return forStatement();
   743 
   744         case TOK_WHILE:
   745           return while_();
   746 
   747         case TOK_BREAK:
   748           scanner_.scan();
   749           statement = new (pool_) BreakStatement(scanner_.begin());
   750           break;
   751 
   752         case TOK_CONTINUE:
   753           scanner_.scan();
   754           statement = new (pool_) ContinueStatement(scanner_.begin());
   755           break;
   756 
   757         case TOK_DO:
   758           if ((statement = do_()) == NULL)
   759               return NULL;
   760           break;
   761 
   762         case TOK_RETURN:
   763           if ((statement = returnStatement()) == NULL)
   764               return NULL;
   765           break;
   766 
   767         case TOK_ENUM:
   768           if ((statement = enum_()) == NULL)
   769               return NULL;
   770           break;
   771 
   772         case TOK_IF:
   773           return if_();
   774 
   775         case TOK_LBRACE:
   776           return block();
   777 
   778 	default:
   779 	  break;
   780     }
   781 
   782     if (!statement) {
   783         if ((statement = expressionStatement()) == NULL)
   784             return NULL;
   785     }
   786 
   787     if (!expect(TOK_SEMICOLON))
   788         return NULL;
   789 
   790     return statement;
   791 }
   792 
   793 Statement *
   794 Parser::enum_()
   795 {
   796     expect(TOK_ENUM);
   797 
   798     SourcePosition pos = scanner_.begin();
   799 
   800     Local<String> name(zone_);
   801     if (matchName(name.ref())) {
   802         if (!name)
   803             return NULL;
   804 
   805         if (BoundName *other = scope_->localLookup(name)) {
   806             redeclarationError(other);
   807             return NULL;
   808         }
   809 
   810         if (!scope_->declareEnum(name, scanner_.begin()))
   811             return NULL;
   812     }
   813 
   814     EnumStatement::EntryList *entries = new (pool_) EnumStatement::EntryList();
   815 
   816     if (!expect(TOK_LBRACE))
   817         return NULL;
   818 
   819     do {
   820         if (scanner_.peek() == TOK_RBRACE)
   821             break;
   822 
   823         Local<String> name(zone_, expectName());
   824         if (!name)
   825             return NULL;
   826 
   827         if (BoundName *other = scope_->localLookup(name)) {
   828             redeclarationError(other);
   829             return NULL;
   830         }
   831 
   832         NamedConstant *constant = scope_->declareConstant(name, scanner_.begin());
   833         if (!constant)
   834             return NULL;
   835 
   836         Expression *expr = NULL;
   837         if (match(TOK_ASSIGN)) {
   838             if ((expr = expression()) == NULL)
   839                 return NULL;
   840         }
   841 
   842         if (!entries->append(EnumStatement::Entry(constant, expr)))
   843             return NULL;
   844     } while (match(TOK_COMMA));
   845     if (!expect(TOK_RBRACE))
   846         return NULL;
   847 
   848     return new (pool_) EnumStatement(pos, name, entries);
   849 }
   850 
   851 Statement *
   852 Parser::function(TokenKind token)
   853 {
   854     Local<String> name(zone_, expectName());
   855     if (!name)
   856         return NULL;
   857 
   858     SourcePosition pos = scanner_.begin();
   859 
   860     // The function name goes into the outer (global) scope.
   861     assert(!scope_->enclosing());
   862 
   863     NamedFunction *fun;
   864     if (BoundName *other = scope_->localLookup(name)) {
   865         // We allow a redeclaration if the new type is a public, and the old
   866         // type was a forward. However, the forward must come first.
   867         if (other->kind() != BoundName::FUNCTION) {
   868             redeclarationError(other);
   869             return NULL;
   870         }
   871 
   872         fun = other->toNamedFunction();
   873         if (!fun->isForward() || token != TOK_PUBLIC) {
   874             redeclarationError(other);
   875             return NULL;
   876         }
   877         
   878         // We've got the same name, but the original is a forward, so let it
   879         // slide and re-use the original declaration.
   880         fun->setImplemented(scanner_.begin());
   881     } else {
   882         fun = scope_->declareFunction(name, scanner_.begin(), token);
   883         if (!fun)
   884             return NULL;
   885     }
   886 
   887     Scope *scope = enterScope(Scope::FUNCTION);
   888     if (!scope)
   889         return NULL;
   890 
   891     ParameterList *parameters = new (pool_) ParameterList();
   892 
   893     if (!expect(TOK_LPAREN))
   894         return NULL;
   895     if (!match(TOK_RPAREN)) {
   896         while (true) {
   897             bool ref = match(TOK_AMPERSAND);
   898 
   899             Local<String> name(zone_, expectName());
   900             if (!name)
   901                 return NULL;
   902 
   903             if (BoundName *other = scope_->localLookup(name)) {
   904                 redeclarationError(other);
   905                 return NULL;
   906             }
   907             Variable *arg = scope_->declareArgument(name, scanner_.begin());
   908             if (!arg)
   909                 return NULL;
   910 
   911             Local<String> tag(zone_);
   912             Parameter *parameter = new (pool_) Parameter(arg, tag, ref);
   913             if (!parameters->append(parameter))
   914                 return NULL;
   915 
   916             if (!match(TOK_COMMA))
   917                 break;
   918         }
   919         if (!expect(TOK_RPAREN))
   920             return NULL;
   921     }
   922 
   923     Statement *body = NULL;
   924     if (token != TOK_FORWARD) {
   925         body = block();
   926         if (!body)
   927             return NULL;
   928     }
   929 
   930     scope_ = scope_->enclosing();
   931     return new (pool_) FunctionStatement(pos, scope, fun, body, parameters);
   932 }
   933 
   934 ParseTree *
   935 Parser::parse()
   936 {
   937     StatementList *statements = new (pool_) StatementList();
   938 
   939     if (!enterScope(Scope::GLOBAL))
   940         return NULL;
   941 
   942     for (;;) {
   943         Statement *statement = NULL;
   944 
   945         switch (scanner_.peek()) {
   946           case TOK_ERROR:
   947             return NULL;
   948 
   949           case TOK_EOF:
   950             break;
   951 
   952           case TOK_NAME:
   953             if ((statement = function(TOK_NAME)) == NULL)
   954                 return NULL;
   955             break;
   956 
   957           case TOK_FORWARD:
   958           case TOK_PUBLIC:
   959           {
   960             TokenKind kind = scanner_.scan();
   961             if ((statement = function(kind)) == NULL)
   962                 return NULL;
   963             if (kind == TOK_FORWARD && !matchSemicolon())
   964                 return NULL;
   965             break;
   966           }
   967 
   968           case TOK_ENUM:
   969             if ((statement = enum_()) == NULL)
   970                 return NULL;
   971             if (!matchSemicolon())
   972                 return NULL;
   973             break;
   974 
   975           default:
   976             cc_.reportError(scanner_.begin(), Message_ExpectedGlobal);
   977             return NULL;
   978         }
   979 
   980         if (!statement)
   981             break;
   982 
   983         if (!statements->append(statement))
   984             return NULL;
   985     }
   986 
   987     return new (pool_) ParseTree(scope_, statements, unbound_);
   988 }
   989 
   990 class AstPrinter : public AstVisitor
   991 {
   992     FILE *fp_;
   993     size_t level_;
   994 
   995   private:
   996     void prefix() {
   997         for (size_t i = 0; i < level_; i++)
   998             fprintf(fp_, "  ");
   999     }
  1000     void indent() {
  1001         level_++;
  1002     }
  1003     void unindent() {
  1004         level_--;
  1005     }
  1006 
  1007   public:
  1008     AstPrinter(FILE *fp)
  1009       : fp_(fp),
  1010         level_(0)
  1011     {
  1012     }
  1013 
  1014     void visit(NameProxy *name) {
  1015         prefix();
  1016         fprintf(fp_, "[ NameProxy (%s)%s\n", name->name()->chars(),
  1017                 (name->binding() ? "" : " unbound"));
  1018     }
  1019     void visit(CallExpression *node) {
  1020         prefix();
  1021         fprintf(fp_, "[ CallExpression\n");
  1022         indent();
  1023         node->callee()->accept(this);
  1024         for (size_t i = 0; i < node->arguments()->length(); i++)
  1025             node->arguments()->at(i)->accept(this);
  1026         unindent();
  1027     }
  1028     void visit(FunctionStatement *node) {
  1029         prefix();
  1030         fprintf(fp_, "[ FunctionStatement (%s)\n", node->fun()->name()->chars());
  1031         indent();
  1032         if (node->body())
  1033             node->body()->accept(this);
  1034         unindent();
  1035     }
  1036     void visit(ExpressionStatement *node) {
  1037         prefix();
  1038         fprintf(fp_, "[ ExpressionStatement\n");
  1039         indent();
  1040         node->expression()->accept(this);
  1041         unindent();
  1042     }
  1043     void visit(Assignment *node) {
  1044         prefix();
  1045         fprintf(fp_, "[ Assignment\n");
  1046         indent();
  1047         node->lvalue()->accept(this);
  1048         node->expression()->accept(this);
  1049         unindent();
  1050     }
  1051     void visit(BinaryExpression *node) {
  1052         prefix();
  1053         fprintf(fp_, "[ BinaryExpression (%s)\n", TokenNames[node->token()]);
  1054         indent();
  1055         node->left()->accept(this);
  1056         node->right()->accept(this);
  1057         unindent();
  1058     }
  1059     void visit(ReturnStatement *node) {
  1060         prefix();
  1061         fprintf(fp_, "[ ReturnStatement\n");
  1062         indent();
  1063         node->expression()->accept(this);
  1064         unindent();
  1065     }
  1066     void visit(ForStatement *node) {
  1067         prefix();
  1068         fprintf(fp_, "[ ForStatement\n");
  1069         indent();
  1070         if (node->initialization())
  1071             node->initialization()->accept(this);
  1072         if (node->condition())
  1073             node->condition()->accept(this);
  1074         if (node->update())
  1075             node->update()->accept(this);
  1076         node->body()->accept(this);
  1077         unindent();
  1078     }
  1079     void visit(BlockStatement *node) {
  1080         prefix();
  1081         fprintf(fp_, "[ BlockStatement\n");
  1082         indent();
  1083         for (size_t i = 0; i < node->statements()->length(); i++)
  1084             node->statements()->at(i)->accept(this);
  1085         unindent();
  1086     }
  1087     void visit(VariableDeclaration *node) {
  1088         prefix();
  1089         fprintf(fp_, "[ VariableDeclaration (%s)\n", node->variable()->name()->chars());
  1090         indent();
  1091         if (node->initialization())
  1092             node->initialization()->accept(this);
  1093         unindent();
  1094     }
  1095     void visit(IntegerLiteral *node) {
  1096         prefix();
  1097         fprintf(fp_, "[ IntegerLiteral (%d)\n", node->value());
  1098     }
  1099     void visit(FloatLiteral *node) {
  1100         prefix();
  1101         fprintf(fp_, "[ FloatLiteral (%f)\n", node->value());
  1102     }
  1103     void visit(IfStatement *node) {
  1104         prefix();
  1105         fprintf(fp_, "[ IfStatement\n");
  1106         indent();
  1107         node->ifTrue()->accept(this);
  1108         if (node->ifFalse())
  1109             node->ifFalse()->accept(this);
  1110         unindent();
  1111     }
  1112     void visit(IndexExpression *node) {
  1113         prefix();
  1114         fprintf(fp_, "[ IndexExpression\n");
  1115         indent();
  1116         node->left()->accept(this);
  1117         node->right()->accept(this);
  1118         unindent();
  1119     }
  1120     void visit(EnumStatement *node) {
  1121         prefix();
  1122         fprintf(fp_, "[ EnumStatement (%s)\n", node->name() ? node->name()->chars() : "<anonymous>");
  1123         indent();
  1124         for (size_t i = 0; i < node->entries()->length(); i++) {
  1125             prefix();
  1126             fprintf(fp_, "%s =\n", node->entries()->at(i).name->name()->chars());
  1127             if (node->entries()->at(i).expr) {
  1128                 indent();
  1129                 node->entries()->at(i).expr->accept(this);
  1130                 unindent();
  1131             }
  1132         }
  1133         unindent();
  1134     }
  1135     void visit(WhileStatement *node) {
  1136         prefix();
  1137         fprintf(fp_, "[ WhileStatement (%s)\n",
  1138                 (node->token() == TOK_DO) ? "do" : "while");
  1139         indent();
  1140         if (node->token() == TOK_DO) {
  1141             node->condition()->accept(this);
  1142             node->body()->accept(this);
  1143         } else {
  1144             node->condition()->accept(this);
  1145             node->body()->accept(this);
  1146         }
  1147         unindent();
  1148     }
  1149     void visit(BreakStatement *node) {
  1150         prefix();
  1151         fprintf(fp_, "[ BreakStatement\n");
  1152     }
  1153     void visit(ContinueStatement *node) {
  1154         prefix();
  1155         fprintf(fp_, "[ ContinueStatement\n");
  1156     }
  1157     void visit(StringLiteral *node) {
  1158         prefix();
  1159         fprintf(fp_, "[ StringLiteral\n");
  1160     }
  1161     void visit(IncDecExpression *node) {
  1162         prefix();
  1163         fprintf(fp_, "[ IncDecExpression (postfix=%d)\n", node->postfix());
  1164         indent();
  1165         node->expression()->accept(this);
  1166         unindent();
  1167     }
  1168 };
  1169 
  1170 void
  1171 ParseTree::dump(FILE *fp)
  1172 {
  1173     AstPrinter printer(fp);
  1174 
  1175     for (size_t i = 0; i < statements_->length(); i++)
  1176         statements_->at(i)->accept(&printer);
  1177 }