parser.cxx

changeset 59
891b9e6ee139
parent 58
bc9317d1b9c9
child 61
11451e7a2fe6
equal deleted inserted replaced
58:bc9317d1b9c9 59:891b9e6ee139
73 // Main parser code. Begins read of the script file, checks the syntax of it 73 // Main parser code. Begins read of the script file, checks the syntax of it
74 // and writes the data to the object file via ObjWriter - which also takes care 74 // and writes the data to the object file via ObjWriter - which also takes care
75 // of necessary buffering so stuff is written in the correct order. 75 // of necessary buffering so stuff is written in the correct order.
76 void ScriptReader::ParseBotScript (ObjWriter* w) { 76 void ScriptReader::ParseBotScript (ObjWriter* w) {
77 // Zero the entire block stack first 77 // Zero the entire block stack first
78 for (int i = 0; i < MAX_STRUCTSTACK; i++) 78 for (int i = 0; i < MAX_SCOPE; i++)
79 memset (&scopestack[i], 0, sizeof (BlockInformation)); 79 ZERO(scopestack[i]);
80 80
81 while (Next()) { 81 while (Next()) {
82 // Check if else is potentically valid 82 // Check if else is potentically valid
83 if (!token.compare ("else") && !g_CanElse) 83 if (!token.compare ("else") && !g_CanElse)
84 ParserError ("else without preceding if"); 84 ParserError ("else without preceding if");
246 MUST_NOT_TOPLEVEL 246 MUST_NOT_TOPLEVEL
247 MustNext ("{"); 247 MustNext ("{");
248 248
249 // Don't use PushScope that will reset the scope. 249 // Don't use PushScope that will reset the scope.
250 g_ScopeCursor++; 250 g_ScopeCursor++;
251 if (g_ScopeCursor >= MAX_STRUCTSTACK) 251 if (g_ScopeCursor >= MAX_SCOPE)
252 ParserError ("too deep scope"); 252 ParserError ("too deep scope");
253 253
254 if (SCOPE(0).type != SCOPETYPE_IF) 254 if (SCOPE(0).type != SCOPETYPE_IF)
255 ParserError ("else without preceding if"); 255 ParserError ("else without preceding if");
256 256
463 ParserError ("unexpected `break`"); 463 ParserError ("unexpected `break`");
464 break; 464 break;
465 } 465 }
466 466
467 MustNext (";"); 467 MustNext (";");
468 continue;
469 }
470
471 // ============================================================
472 // Continue
473 if (!token.compare ("continue")) {
474 MustNext (";");
475
476 int curs;
477 bool found = false;
478
479 // Drop through the scope until we find a loop block
480 for (curs = g_ScopeCursor; curs > 0 && !found; curs--) {
481 switch (scopestack[curs].type) {
482 case SCOPETYPE_FOR:
483 case SCOPETYPE_WHILE:
484 case SCOPETYPE_DO:
485 w->Write<word> (DH_GOTO);
486 w->AddReference (scopestack[curs].mark1);
487 found = true;
488 break;
489 }
490 }
491
492 // No loop blocks
493 if (!found)
494 ParserError ("`continue`-statement not inside a loop");
495
468 continue; 496 continue;
469 } 497 }
470 498
471 // ============================================================ 499 // ============================================================
472 // Label 500 // Label
989 return retbuf; 1017 return retbuf;
990 } 1018 }
991 1019
992 void ScriptReader::PushScope () { 1020 void ScriptReader::PushScope () {
993 g_ScopeCursor++; 1021 g_ScopeCursor++;
994 if (g_ScopeCursor >= MAX_STRUCTSTACK) 1022 if (g_ScopeCursor >= MAX_SCOPE)
995 ParserError ("too deep scope"); 1023 ParserError ("too deep scope");
996 1024
997 BlockInformation* info = &SCOPE(0); 1025 ScopeInfo* info = &SCOPE(0);
998 info->type = 0; 1026 info->type = 0;
999 info->mark1 = 0; 1027 info->mark1 = 0;
1000 info->mark2 = 0; 1028 info->mark2 = 0;
1001 info->buffer1 = NULL; 1029 info->buffer1 = NULL;
1002 info->casecursor = -1; 1030 info->casecursor = -1;
1018 DataBuffer* b = ParseExpression (TYPE_VOID); 1046 DataBuffer* b = ParseExpression (TYPE_VOID);
1019 return b; 1047 return b;
1020 } 1048 }
1021 1049
1022 void ScriptReader::AddSwitchCase (ObjWriter* w, DataBuffer* b) { 1050 void ScriptReader::AddSwitchCase (ObjWriter* w, DataBuffer* b) {
1023 BlockInformation* info = &SCOPE(0); 1051 ScopeInfo* info = &SCOPE(0);
1024 1052
1025 info->casecursor++; 1053 info->casecursor++;
1026 if (info->casecursor >= MAX_CASE) 1054 if (info->casecursor >= MAX_CASE)
1027 ParserError ("too many cases in one switch"); 1055 ParserError ("too many cases in one switch");
1028 1056

mercurial