Expression *Parser::ParseLet(bool rec) { Token* tk = lexer_->GetToken(); lexer_->Advance(); ELet::DefList defs = ParseDefs(); Advance(Token::IN); Expression* body = ParseExpr(); return new ELet(tk, rec, defs, body); }
void File::Parse(InputStream& s, LPCWSTR predef) { Reference* pRef = CreateRootRef(); SetPredefined(true); try {ParseDefs(WCharInputStream(predef), pRef);} catch(Exception& e) {ASSERT(0); TRACE(_T("%s\n"), e.ToString());} SetPredefined(false); ParseDefs(s, pRef); Commit(); if(s.PeekChar() != Stream::EOS) { TRACE(_T("Warning: parsing ended before EOF!\n")); } }
/* ============ CompileFile compiles the 0 terminated text, adding defintions to the pr structure ============ */ bool Compiler::CompileFile( const char *text, int filenum ) { filenumber = filenum; callthread = false; def_ret.ofs = OFS_RETURN; def_ret.localofs = def_ret.ofs; lex.SetSource( text ); // read first token lex.Lex(); while( lex.pr_token_type != tt_eof ) { try { // outside all functions pr_scope = NULL; ParseDefs(); } catch( ... ) { if ( ++program.pr_error_count > scr_maxerrors->integer ) { break; } if ( pr_scope ) { lex.SkipOutOfFunction(); } else { lex.SkipToSemicolon(); } } } return( program.pr_error_count == 0 ); }
void SubtitleFile::Append(InputStream& s, float start, float stop, bool fSetTime) { Reference* pRootRef = GetRootRef(); ParseDefs(s, pRootRef); CAtlList<Definition*> defs; GetNewDefs(defs); POSITION pos = defs.GetHeadPosition(); while(pos) { Definition* pDef = defs.GetNext(pos); if(pDef->m_parent == pRootRef && pDef->m_type == L"subtitle" && (*pDef)[L"@"].IsValue()) { m_segments.Insert(start, stop, pDef); if(fSetTime) { try { Definition::Time time; StringMapW<float> offset; pDef->GetAsTime(time, offset); if(time.start.value == start && time.stop.value == stop) continue; } catch(Exception&) { } CStringW str; str.Format(L"%.3f", start); pDef->SetChildAsNumber(L"time.start", str, L"s"); str.Format(L"%.3f", stop); pDef->SetChildAsNumber(L"time.stop", str, L"s"); } } } Commit(); }
void File::ParseRefs(InputStream& s, Definition* pParentDef, LPCWSTR term) { int c = s.SkipWhiteSpace(); do { if(pParentDef->IsValue()) s.ThrowError(_T("cannot mix references with other values")); if(c == '{') { s.GetChar(); ParseDefs(s, CreateRef(pParentDef)); } else if(iswcsym(c)) { CStringW str; ParseName(s, str); // TODO: allow spec references: parent.<type>, self.<type>, child.<type> Definition* pDef = GetDefByName(str); if(!pDef) s.ThrowError(_T("cannot find definition of '%s'"), CString(str)); if(!pParentDef->IsVisible(pDef)) s.ThrowError(_T("cannot access '%s' from here"), CString(str)); pParentDef->AddTail(pDef); } else if(!wcschr(term, c) && c != Stream::EOS) { s.ThrowError(_T("unexpected character '%c'"), (TCHAR)c); } c = s.SkipWhiteSpace(); } while(!wcschr(term, c) && c != Stream::EOS); }
/* ============ ParseStatement ============ */ void Compiler::ParseStatement( void ) { def_t *e; dstatement_t *patch1; dstatement_t *patch2; dstatement_t *patch3; dstatement_t *patch4; etype_t type_a; etype_t type_b; opcode_t *op; if ( lex.Check( "{" ) ) { do { ParseStatement(); } while( !lex.Check( "}" ) ); return; } if ( lex.Check( "return" ) ) { if ( lex.Check( ";" ) ) { if ( pr_scope->type->aux_type->type != ev_void ) { lex.ParseError( "expecting return value" ); } Statement( &pr_opcodes[ OP_RETURN ], 0, 0 ); return; } e = Expression( TOP_PRIORITY ); lex.Expect( ";" ); type_a = e->type->type; type_b = pr_scope->type->aux_type->type; if ( type_a == type_b ) { Statement( &pr_opcodes[ OP_RETURN ], e, 0 ); return; } for( op = pr_opcodes; op->name; op++ ) { if ( !strcmp( op->name, "=" ) ) { break; } } assert( op->name ); while( ( type_a != op->type_a->type->type ) || ( type_b != op->type_b->type->type ) ) { op++; if ( !op->name || strcmp( op->name, "=" ) ) { lex.ParseError( "type mismatch for return value" ); } } def_ret.type = pr_scope->type->aux_type; Statement( op, e, &def_ret ); Statement( &pr_opcodes[ OP_RETURN ], 0, 0 ); return; } if ( lex.Check( "while" ) ) { lex.Expect( "(" ); patch2 = &program.statements[ program.numstatements ]; e = Expression( TOP_PRIORITY ); lex.Expect( ")" ); patch1 = &program.statements[ program.numstatements ]; Statement( &pr_opcodes[ OP_IFNOT ], e, 0 ); ParseStatement(); junkdef.ofs = patch2 - &program.statements[ program.numstatements ]; junkdef.localofs = junkdef.ofs; Statement( &pr_opcodes[ OP_GOTO ], &junkdef, 0 ); patch1->b = &program.statements[ program.numstatements ] - patch1; return; } if ( lex.Check( "for" ) ) { lex.Expect( "(" ); // init if ( !lex.Check( ";" ) ) { do { Expression( TOP_PRIORITY ); } while( lex.Check( "," ) ); lex.Expect( ";" ); } // condition patch2 = &program.statements[ program.numstatements ]; e = Expression( TOP_PRIORITY ); lex.Expect( ";" ); patch1 = &program.statements[ program.numstatements ]; Statement( &pr_opcodes[ OP_IFNOT ], e, 0 ); // counter if ( !lex.Check( ")" ) ) { patch3 = &program.statements[ program.numstatements ]; Statement( &pr_opcodes[ OP_IF ], e, 0 ); patch4 = patch2; patch2 = &program.statements[ program.numstatements ]; do { Expression( TOP_PRIORITY ); } while( lex.Check( "," ) ); lex.Expect( ")" ); // goto patch4 junkdef.ofs = patch4 - &program.statements[ program.numstatements ]; junkdef.localofs = junkdef.ofs; Statement( &pr_opcodes[ OP_GOTO ], &junkdef, 0 ); // fixup patch3 patch3->b = &program.statements[ program.numstatements ] - patch3; } ParseStatement(); // goto patch2 junkdef.ofs = patch2 - &program.statements[ program.numstatements ]; junkdef.localofs = junkdef.ofs; Statement( &pr_opcodes[ OP_GOTO ], &junkdef, 0 ); // fixup patch1 patch1->b = &program.statements[ program.numstatements ] - patch1; return; } if ( lex.Check( "do" ) ) { patch1 = &program.statements[ program.numstatements ]; ParseStatement(); lex.Expect( "while" ); lex.Expect( "(" ); e = Expression( TOP_PRIORITY ); lex.Expect( ")" ); lex.Expect( ";" ); junkdef.ofs = patch1 - &program.statements[ program.numstatements ]; junkdef.localofs = junkdef.ofs; Statement( &pr_opcodes[ OP_IF ], e, &junkdef ); return; } if ( lex.CheckType() != NULL ) { ParseDefs(); program.locals_end = program.numpr_globals; return; } if ( lex.Check( "if" ) ) { lex.Expect( "(" ); e = Expression( TOP_PRIORITY ); lex.Expect( ")" ); patch1 = &program.statements[ program.numstatements ]; Statement( &pr_opcodes[ OP_IFNOT ], e, 0 ); ParseStatement(); if ( lex.Check( "else" ) ) { patch2 = &program.statements[ program.numstatements ]; Statement( &pr_opcodes[ OP_GOTO ], 0, 0 ); patch1->b = &program.statements[ program.numstatements ] - patch1; ParseStatement(); patch2->a = &program.statements[ program.numstatements ] - patch2; } else { patch1->b = &program.statements[ program.numstatements ] - patch1; } return; } Expression( TOP_PRIORITY ); lex.Expect(";"); }
void FuncDefs::Load() { Clear(); LoadFiles(); ParseDefs(); }