diff --git a/Import/GacUI.cpp b/Import/GacUI.cpp index 78bc30d5..ae4a127c 100644 --- a/Import/GacUI.cpp +++ b/Import/GacUI.cpp @@ -4254,6 +4254,7 @@ Event Receiver ,lostFocus(_sender) ,caretNotify(_sender) ,clipboardNotify(_sender) + ,renderTargetChanged(_sender) { } diff --git a/Import/VlppGlrParser.cpp b/Import/VlppGlrParser.cpp index d0023eea..46f80500 100644 --- a/Import/VlppGlrParser.cpp +++ b/Import/VlppGlrParser.cpp @@ -2632,7 +2632,13 @@ Input // if competitions happen between new surviving traces // remove traces that known to have lost the competition - CheckBackupTracesBeforeSwapping(currentTokenIndex); + if (CheckBackupTracesBeforeSwapping(currentTokenIndex)) + { + // after competition are closed + // different surviving traces might be mergable + // merge them and remove unnecessary traces + TryMergeSurvivingTraces(); + } EndSwap(); @@ -2806,6 +2812,7 @@ namespace vl { namespace automaton { + using namespace collections; /*********************************************************************** EnsureTraceWithValidStates @@ -2831,7 +2838,7 @@ AreTwoEndingInputTraceEqual { // two traces equal to each other if // 1) they are in the same state - // 2) they have the same executedReturnStack (and therefore the same returnStack) + // 2) they have the same executedReturnStack and returnStack // 3) they are attending same competitions // 4) they have the same switchValues // 5) the candidate has an ending input @@ -2850,7 +2857,7 @@ AreTwoEndingInputTraceEqual MergeTwoEndingInputTrace ***********************************************************************/ - void TraceManager::MergeTwoEndingInputTrace(Trace* newTrace, Trace* candidate) + Trace* TraceManager::MergeTwoEndingInputTrace(Trace* newTrace, Trace* candidate) { // goal of this function is to create a structure // NEWTRACE ---+->AMBIGUITY @@ -2861,9 +2868,14 @@ MergeTwoEndingInputTrace // a former trace will copy CANDIDATE and insert before CANDIDATE // and CANDIDATE will be initialized to an empty trace + // if a former trace is created to replace the candidate + // in which case the candidate becomes a merge trace + // the former trace is returned + if (candidate->state == -1) { AddTraceToCollection(candidate, newTrace, &Trace::predecessors); + return nullptr; } else { @@ -2879,8 +2891,211 @@ MergeTwoEndingInputTrace AddTraceToCollection(candidate, formerTrace, &Trace::predecessors); AddTraceToCollection(candidate, newTrace, &Trace::predecessors); + return formerTrace; } } + +/*********************************************************************** +TryMergeSurvivingTraces +***********************************************************************/ + + void TraceManager::TryMergeSurvivingTraces() + { +#define ERROR_MESSAGE_PREFIX L"vl::glr::automaton::TraceManager::TryMergeSurvivingTraces()#" + if (concurrentCount == 0) return; + + struct EndingOrMergeTraceData + { + bool surviving = true; // becomes false when this trace does not survive anymore + }; + + vint32_t removedTracesCount = 0; + Dictionary endingOrMergeTraces; + Group endingOrMergeTracesByState; + + // index surviving traces + for (vint32_t i = 0; i < concurrentCount; i++) + { + auto trace = backupTraces->Get(i); + endingOrMergeTraces.Add(trace, {}); + + if (trace->state == -1) + { + endingOrMergeTracesByState.Add(EnsureTraceWithValidStates(trace)->state, trace); + } + else if (trace->byInput == Executable::EndingInput) + { + endingOrMergeTracesByState.Add(trace->state, trace); + } + } + +#if defined VCZH_MSVC && defined _DEBUG + // check assumptions + for (vint32_t i = 0; i < concurrentCount; i++) + { + auto trace = backupTraces->Get(i); + if (trace->state == -1) + { + auto predecessorId = trace->predecessors.first; + while (predecessorId != nullref) + { + auto predecessor = GetTrace(predecessorId); + predecessorId = predecessor->predecessors.siblingNext; + + CHECK_ERROR(endingOrMergeTraces.Keys().IndexOf(predecessor) == -1, ERROR_MESSAGE_PREFIX L"Internal error: Predecessors of a merge trace should not survive."); + } + } + else if (trace->byInput == Executable::EndingInput) + { + CHECK_ERROR(trace->predecessors.first == trace->predecessors.last, ERROR_MESSAGE_PREFIX L"Internal error: Executable::EndingInput trace could not have multiple predecessors."); + } + } +#endif + + // unsurvive a trace + auto unsurviveTrace = [&](Trace* trace, EndingOrMergeTraceData& data) + { + if (data.surviving) + { + data.surviving = false; + removedTracesCount++; + } + }; + + // check if a trace survived + // if an Executable::EndingInput trace survived but its only predecessor does not + // it becomes not survived + auto ensureEndingTraceSurvived = [&](Trace* trace) + { + if (trace == initialTrace) return true; + + auto& data = const_cast(endingOrMergeTraces[trace]); + if (!data.surviving) return false; + + if (trace->state != -1) + { + auto predecessorId = trace->predecessors.first; + if (predecessorId != nullref) + { + auto predecessor = GetTrace(predecessorId); + if (!endingOrMergeTraces[predecessor].surviving) + { + unsurviveTrace(trace, data); + } + } + } + return data.surviving; + }; + + // find surviving traces that merge + for (vint32_t i = 0; i < concurrentCount; i++) + { + // get the next surviving Executable::EndingInput trace + auto trace = backupTraces->Get(i); + if (trace->state != -1 && trace->byInput != Executable::EndingInput) continue; + if (!ensureEndingTraceSurvived(trace)) continue; + auto realTrace = EnsureTraceWithValidStates(trace); + + // find all traces Executable::EndingInput traces with the same state that after it + auto&& candidates = endingOrMergeTracesByState[realTrace->state]; + vint index = candidates.IndexOf(trace); + for (vint j = index + 1; j < candidates.Count(); j++) + { + // ensure the candidate also survived + auto candidate = candidates[j]; + if (!ensureEndingTraceSurvived(candidate)) continue; + auto realCandidate = EnsureTraceWithValidStates(candidate); + + if (AreTwoEndingInputTraceEqual(realTrace, realCandidate)) + { + // merge two traces + if (trace == realTrace) + { + // if trace is an ordinary trace + if (candidate == realCandidate) + { + // if candidate is an ordinary trace + // turn trace into a merge trace + auto formerTrace = MergeTwoEndingInputTrace(candidate, trace); + CHECK_ERROR(formerTrace != nullptr, ERROR_MESSAGE_PREFIX L"Internal error: formerTrace should not be null."); + realTrace = formerTrace; + } + else + { + // if candidate is a merge trace + // turn trace into a merge trace + // give the rest of predecessors of candidate to trace + auto candidateHead = GetTrace(candidate->predecessors.first); + auto candidateNextId = candidateHead->predecessors.siblingNext; + + candidateHead->predecessors.siblingNext = nullref; + auto formerTrace = MergeTwoEndingInputTrace(candidateHead, trace); + CHECK_ERROR(formerTrace != nullptr, ERROR_MESSAGE_PREFIX L"Internal error: formerTrace should not be null."); + realTrace = formerTrace; + + candidateHead->predecessors.siblingNext = candidateNextId; + trace->predecessors.last = candidate->predecessors.last; + candidate->predecessors.first = nullref; + candidate->predecessors.last = nullref; + } + } + else + { + // if trace is a merge trace + if (candidate == realCandidate) + { + // if candidate is an ordinary trace + // merge candidate into trace + auto formerTrace = MergeTwoEndingInputTrace(candidate, trace); + CHECK_ERROR(formerTrace == nullptr, ERROR_MESSAGE_PREFIX L"Internal error: formerTrace should be null."); + } + else + { + // if candidate is an ordinary trace + // give all predecessors of candidate to trace + auto traceTail = GetTrace(trace->predecessors.last); + auto candidateHead = GetTrace(candidate->predecessors.first); + + traceTail->predecessors.siblingNext = candidateHead; + candidateHead->predecessors.siblingPrev = traceTail; + + trace->predecessors.last = candidate->predecessors.last; + candidate->predecessors.first = nullref; + candidate->predecessors.last = nullref; + } + } + + auto& data = const_cast(endingOrMergeTraces[candidate]); + unsurviveTrace(candidate, data); + } + } + } + + if (removedTracesCount > 0) + { + // mark all unsurviving traces + for (vint32_t i = 0; i < concurrentCount; i++) + { + auto trace = backupTraces->Get(i); + vint index = endingOrMergeTraces.Keys().IndexOf(trace); + if (index == -1) continue; + if (endingOrMergeTraces.Values()[index].surviving) continue; + backupTraces->Set(i, nullptr); + } + + // clean up surviving trace list + vint writing = 0; + for (vint32_t i = 0; i < concurrentCount; i++) + { + auto trace = backupTraces->Get(i); + if (!trace) continue; + backupTraces->Set(writing++, trace); + } + concurrentCount -= removedTracesCount; + } + +#undef ERROR_MESSAGE_PREFIX + } } } } @@ -3080,8 +3295,9 @@ CheckAttendingCompetitionsOnEndingEdge CheckBackupTracesBeforeSwapping ***********************************************************************/ - void TraceManager::CheckBackupTracesBeforeSwapping(vint32_t currentTokenIndex) + bool TraceManager::CheckBackupTracesBeforeSwapping(vint32_t currentTokenIndex) { + bool closedCompetitions = false; // try to find if any competition could be settled at this moment { @@ -3193,6 +3409,7 @@ CheckBackupTracesBeforeSwapping for (vint i = 0; i < concurrentCount; i++) { auto trace = EnsureTraceWithValidStates(backupTraces->Get(i)); + auto attendingCompetitions = trace->competitionRouting.attendingCompetitions; auto* pnext = &trace->competitionRouting.attendingCompetitions; while (*pnext != nullref) { @@ -3206,7 +3423,15 @@ CheckBackupTracesBeforeSwapping pnext = &ac->nextActiveAC; } } + + if (trace->competitionRouting.attendingCompetitions != attendingCompetitions) + { + // only check the head node since this could trigger merging + closedCompetitions = true; + } } + + return closedCompetitions; } } } diff --git a/Import/VlppGlrParser.h b/Import/VlppGlrParser.h index bab744ec..53509f94 100644 --- a/Import/VlppGlrParser.h +++ b/Import/VlppGlrParser.h @@ -567,6 +567,10 @@ IAstInsReceiver (Code Generation Templates) Ptr AssemblerResolveAmbiguity(vint32_t type, collections::Array>& candidates, const wchar_t* cppTypeName) { auto ast = Ptr(new TAmbiguity()); + if (candidates.Count() > 0) + { + ast->codeRange = candidates[0]->codeRange; + } for (auto candidate : candidates) { if (auto typedAst = candidate.Cast()) @@ -2287,13 +2291,14 @@ TraceManager // Ambiguity Trace* EnsureTraceWithValidStates(Trace* trace); bool AreTwoEndingInputTraceEqual(Trace* newTrace, Trace* candidate); - void MergeTwoEndingInputTrace(Trace* newTrace, Trace* candidate); + Trace* MergeTwoEndingInputTrace(Trace* newTrace, Trace* candidate); + void TryMergeSurvivingTraces(); // Competition void AttendCompetition(Trace* trace, Ref& newAttendingCompetitions, Ref& newCarriedCompetitions, Ref returnStack, vint32_t ruleId, vint32_t clauseId, bool forHighPriority); void AttendCompetitionIfNecessary(Trace* trace, vint32_t currentTokenIndex, EdgeDesc& edgeDesc, Ref& newAttendingCompetitions, Ref& newCarriedCompetitions, Ref& newReturnStack); void CheckAttendingCompetitionsOnEndingEdge(Trace* trace, EdgeDesc& edgeDesc, Ref acId, Ref returnStack); - void CheckBackupTracesBeforeSwapping(vint32_t currentTokenIndex); + bool CheckBackupTracesBeforeSwapping(vint32_t currentTokenIndex); // ReturnStack ReturnStackSuccessors* GetCurrentSuccessorInReturnStack(Ref base, vint32_t currentTokenIndex); diff --git a/Import/VlppGlrParserCompiler.cpp b/Import/VlppGlrParserCompiler.cpp index 5823e38e..5787e387 100644 --- a/Import/VlppGlrParserCompiler.cpp +++ b/Import/VlppGlrParserCompiler.cpp @@ -23,22 +23,23 @@ GenerateAstFileNames void GenerateAstFileNames(AstSymbolManager& manager, Ptr parserOutput) { - for (auto file : manager.Files().Values()) + auto globalName = manager.Global().name; + for (auto group : manager.FileGroups().Values()) { auto astOutput = Ptr(new CppAstGenOutput); - astOutput->astH = file->Owner()->Global().name + file->Name() + L".h"; - astOutput->astCpp = file->Owner()->Global().name + file->Name() + L".cpp"; - astOutput->builderH = file->Owner()->Global().name + file->Name() + L"_Builder.h"; - astOutput->builderCpp = file->Owner()->Global().name + file->Name() + L"_Builder.cpp"; - astOutput->emptyH = file->Owner()->Global().name + file->Name() + L"_Empty.h"; - astOutput->emptyCpp = file->Owner()->Global().name + file->Name() + L"_Empty.cpp"; - astOutput->copyH = file->Owner()->Global().name + file->Name() + L"_Copy.h"; - astOutput->copyCpp = file->Owner()->Global().name + file->Name() + L"_Copy.cpp"; - astOutput->traverseH = file->Owner()->Global().name + file->Name() + L"_Traverse.h"; - astOutput->traverseCpp = file->Owner()->Global().name + file->Name() + L"_Traverse.cpp"; - astOutput->jsonH = file->Owner()->Global().name + file->Name() + L"_Json.h"; - astOutput->jsonCpp = file->Owner()->Global().name + file->Name() + L"_Json.cpp"; - parserOutput->astOutputs.Add(file, astOutput); + astOutput->astH = globalName + group->Name() + L".h"; + astOutput->astCpp = globalName + group->Name() + L".cpp"; + astOutput->builderH = globalName + group->Name() + L"_Builder.h"; + astOutput->builderCpp = globalName + group->Name() + L"_Builder.cpp"; + astOutput->emptyH = globalName + group->Name() + L"_Empty.h"; + astOutput->emptyCpp = globalName + group->Name() + L"_Empty.cpp"; + astOutput->copyH = globalName + group->Name() + L"_Copy.h"; + astOutput->copyCpp = globalName + group->Name() + L"_Copy.cpp"; + astOutput->traverseH = globalName + group->Name() + L"_Traverse.h"; + astOutput->traverseCpp = globalName + group->Name() + L"_Traverse.cpp"; + astOutput->jsonH = globalName + group->Name() + L"_Json.h"; + astOutput->jsonCpp = globalName + group->Name() + L"_Json.cpp"; + parserOutput->astOutputs.Add(group, astOutput); } } @@ -46,11 +47,11 @@ GenerateAstFileNames Utility ***********************************************************************/ - void CollectVisitorsAndConcreteClasses(AstDefFile* file, List& visitors, List& concreteClasses) + void CollectVisitorsAndConcreteClasses(AstDefFileGroup* group, List& visitors, List& concreteClasses) { - for (auto name : file->SymbolOrder()) + for (auto name : group->SymbolOrder()) { - if (auto classSymbol = dynamic_cast(file->Symbols()[name])) + if (auto classSymbol = dynamic_cast(group->Symbols()[name])) { if (classSymbol->derivedClasses.Count() > 0) { @@ -68,33 +69,33 @@ Utility Forward Declarations ***********************************************************************/ - extern void WriteTypeForwardDefinitions(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer); - extern void WriteTypeDefinitions(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer); - extern void WriteVisitorImpl(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer); - extern void WriteTypeReflectionDeclaration(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer); - extern void WriteTypeReflectionImplementation(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer); + extern void WriteTypeForwardDefinitions(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer); + extern void WriteTypeDefinitions(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer); + extern void WriteVisitorImpl(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer); + extern void WriteTypeReflectionDeclaration(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer); + extern void WriteTypeReflectionImplementation(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer); /*********************************************************************** WriteAstHeaderFile ***********************************************************************/ - void WriteAstHeaderFile(AstDefFile* file, stream::StreamWriter& writer) + void WriteAstHeaderFile(AstDefFileGroup* group, stream::StreamWriter& writer) { - WriteFileComment(file->Name(), writer); - auto&& headerGuard = file->Owner()->Global().headerGuard; + WriteFileComment(group->Name(), writer); + auto&& headerGuard = group->Owner()->Global().headerGuard; if (headerGuard != L"") { writer.WriteString(L"#ifndef "); - writer.WriteLine(headerGuard + L"_" + wupper(file->Name()) + L"_AST"); + writer.WriteLine(headerGuard + L"_" + wupper(group->Name()) + L"_AST"); writer.WriteString(L"#define "); - writer.WriteLine(headerGuard + L"_" + wupper(file->Name()) + L"_AST"); + writer.WriteLine(headerGuard + L"_" + wupper(group->Name()) + L"_AST"); } else { writer.WriteLine(L"#pragma once"); } writer.WriteLine(L""); - for (auto include : file->Owner()->Global().includes) + for (auto include : group->Owner()->Global().includes) { if (include.Length() > 0 && include[0] == L'<') { @@ -108,10 +109,10 @@ WriteAstHeaderFile writer.WriteLine(L""); { - WString prefix = WriteNssBegin(file->cppNss, writer); - WriteTypeForwardDefinitions(file, prefix, writer); - WriteTypeDefinitions(file, prefix, writer); - WriteNssEnd(file->cppNss, writer); + WString prefix = WriteNssBegin(group->cppNss, writer); + WriteTypeForwardDefinitions(group, prefix, writer); + WriteTypeDefinitions(group, prefix, writer); + WriteNssEnd(group->cppNss, writer); } { List refNss; @@ -119,7 +120,7 @@ WriteAstHeaderFile refNss.Add(L"reflection"); refNss.Add(L"description"); WString prefix = WriteNssBegin(refNss, writer); - WriteTypeReflectionDeclaration(file, prefix, writer); + WriteTypeReflectionDeclaration(group, prefix, writer); WriteNssEnd(refNss, writer); } @@ -133,18 +134,18 @@ WriteAstHeaderFile WriteAstCppFile ***********************************************************************/ - void WriteAstCppFile(AstDefFile* file, const WString& astHeaderName, stream::StreamWriter& writer) + void WriteAstCppFile(AstDefFileGroup* group, const WString& astHeaderName, stream::StreamWriter& writer) { - WriteFileComment(file->Name(), writer); + WriteFileComment(group->Name(), writer); writer.WriteLine(L"#include \"" + astHeaderName + L"\""); writer.WriteLine(L""); { - WString prefix = WriteNssBegin(file->cppNss, writer); + WString prefix = WriteNssBegin(group->cppNss, writer); writer.WriteLine(L"/***********************************************************************"); writer.WriteLine(L"Visitor Pattern Implementation"); writer.WriteLine(L"***********************************************************************/"); - WriteVisitorImpl(file, prefix, writer); - WriteNssEnd(file->cppNss, writer); + WriteVisitorImpl(group, prefix, writer); + WriteNssEnd(group->cppNss, writer); } { List refNss; @@ -152,7 +153,7 @@ WriteAstCppFile refNss.Add(L"reflection"); refNss.Add(L"description"); WString prefix = WriteNssBegin(refNss, writer); - WriteTypeReflectionImplementation(file, prefix, writer); + WriteTypeReflectionImplementation(group, prefix, writer); WriteNssEnd(refNss, writer); } } @@ -162,21 +163,21 @@ WriteAstUtilityHeaderFile ***********************************************************************/ void WriteAstUtilityHeaderFile( - AstDefFile* file, + AstDefFileGroup* group, Ptr output, const WString& extraNss, stream::StreamWriter& writer, Func callback ) { - WriteFileComment(file->Name(), writer); - auto&& headerGuard = file->Owner()->Global().headerGuard; + WriteFileComment(group->Name(), writer); + auto&& headerGuard = group->Owner()->Global().headerGuard; if (headerGuard != L"") { writer.WriteString(L"#ifndef "); - writer.WriteLine(headerGuard + L"_" + wupper(file->Name()) + L"_AST_" + wupper(extraNss)); + writer.WriteLine(headerGuard + L"_" + wupper(group->Name()) + L"_AST_" + wupper(extraNss)); writer.WriteString(L"#define "); - writer.WriteLine(headerGuard + L"_" + wupper(file->Name()) + L"_AST_" + wupper(extraNss)); + writer.WriteLine(headerGuard + L"_" + wupper(group->Name()) + L"_AST_" + wupper(extraNss)); } else { @@ -187,7 +188,7 @@ WriteAstUtilityHeaderFile writer.WriteLine(L""); { List cppNss; - CopyFrom(cppNss, file->cppNss); + CopyFrom(cppNss, group->cppNss); cppNss.Add(extraNss); WString prefix = WriteNssBegin(cppNss, writer); callback(prefix); @@ -204,19 +205,19 @@ WriteAstUtilityCppFile ***********************************************************************/ void WriteAstUtilityCppFile( - AstDefFile* file, + AstDefFileGroup* group, const WString& utilityHeaderFile, const WString& extraNss, stream::StreamWriter& writer, Func callback ) { - WriteFileComment(file->Name(), writer); + WriteFileComment(group->Name(), writer); writer.WriteLine(L"#include \"" + utilityHeaderFile + L"\""); writer.WriteLine(L""); { List cppNss; - CopyFrom(cppNss, file->cppNss); + CopyFrom(cppNss, group->cppNss); cppNss.Add(extraNss); WString prefix = WriteNssBegin(cppNss, writer); callback(prefix); @@ -250,9 +251,9 @@ WriteParserUtilityHeaderFile } writer.WriteLine(L""); - for (auto file : manager.Files().Values()) + for (auto group : manager.FileGroups().Values()) { - writer.WriteLine(L"#include \"" + output->astOutputs[file]->astH + L"\""); + writer.WriteLine(L"#include \"" + output->astOutputs[group]->astH + L"\""); } writer.WriteLine(L""); @@ -289,17 +290,17 @@ WriteParserUtilityCppFile WriteAstFiles ***********************************************************************/ - void WriteAstFiles(AstDefFile* file, Ptr output, collections::Dictionary& files) + void WriteAstFiles(AstDefFileGroup* group, Ptr output, collections::Dictionary& files) { { WString fileH = GenerateToStream([&](StreamWriter& writer) { - WriteAstHeaderFile(file, writer); + WriteAstHeaderFile(group, writer); }); WString fileCpp = GenerateToStream([&](StreamWriter& writer) { - WriteAstCppFile(file, output->astH, writer); + WriteAstCppFile(group, output->astH, writer); }); files.Add(output->astH, fileH); @@ -309,12 +310,12 @@ WriteAstFiles { WString fileH = GenerateToStream([&](StreamWriter& writer) { - WriteAstBuilderHeaderFile(file, output, writer); + WriteAstBuilderHeaderFile(group, output, writer); }); WString fileCpp = GenerateToStream([&](StreamWriter& writer) { - WriteAstBuilderCppFile(file, output, writer); + WriteAstBuilderCppFile(group, output, writer); }); files.Add(output->builderH, fileH); @@ -324,12 +325,12 @@ WriteAstFiles { WString fileH = GenerateToStream([&](StreamWriter& writer) { - WriteEmptyVisitorHeaderFile(file, output, writer); + WriteEmptyVisitorHeaderFile(group, output, writer); }); WString fileCpp = GenerateToStream([&](StreamWriter& writer) { - WriteEmptyVisitorCppFile(file, output, writer); + WriteEmptyVisitorCppFile(group, output, writer); }); files.Add(output->emptyH, fileH); @@ -339,12 +340,12 @@ WriteAstFiles { WString fileH = GenerateToStream([&](StreamWriter& writer) { - WriteCopyVisitorHeaderFile(file, output, writer); + WriteCopyVisitorHeaderFile(group, output, writer); }); WString fileCpp = GenerateToStream([&](StreamWriter& writer) { - WriteCopyVisitorCppFile(file, output, writer); + WriteCopyVisitorCppFile(group, output, writer); }); files.Add(output->copyH, fileH); @@ -354,12 +355,12 @@ WriteAstFiles { WString fileH = GenerateToStream([&](StreamWriter& writer) { - WriteTraverseVisitorHeaderFile(file, output, writer); + WriteTraverseVisitorHeaderFile(group, output, writer); }); WString fileCpp = GenerateToStream([&](StreamWriter& writer) { - WriteTraverseVisitorCppFile(file, output, writer); + WriteTraverseVisitorCppFile(group, output, writer); }); files.Add(output->traverseH, fileH); @@ -369,12 +370,12 @@ WriteAstFiles { WString fileH = GenerateToStream([&](StreamWriter& writer) { - WriteJsonVisitorHeaderFile(file, output, writer); + WriteJsonVisitorHeaderFile(group, output, writer); }); WString fileCpp = GenerateToStream([&](StreamWriter& writer) { - WriteJsonVisitorCppFile(file, output, writer); + WriteJsonVisitorCppFile(group, output, writer); }); files.Add(output->jsonH, fileH); @@ -384,9 +385,9 @@ WriteAstFiles void WriteAstFiles(AstSymbolManager& manager, Ptr output, collections::Dictionary& files) { - for (auto file : manager.Files().Values()) + for (auto group : manager.FileGroups().Values()) { - WriteAstFiles(file, output->astOutputs[file], files); + WriteAstFiles(group, output->astOutputs[group], files); } { @@ -421,7 +422,14 @@ namespace vl using namespace collections; using namespace stream; - extern void PrintCppType(AstDefFile* fileContext, AstSymbol* propSymbol, stream::StreamWriter& writer); + extern void PrintCppType(AstDefFileGroup* fileGroupContext, AstSymbol* propSymbol, stream::StreamWriter& writer); + + LazyList GetAllSymbols(AstSymbolManager& manager) + { + return Range(0, manager.Symbols().Count()) + .SelectMany([&manager](vint index) { return From(manager.Symbols().GetByIndex(index)); }) + ; + } /*********************************************************************** WriteAstAssemblerHeaderFile @@ -435,7 +443,7 @@ WriteAstAssemblerHeaderFile vint index = 0; writer.WriteLine(prefix + L"enum class " + manager.Global().name + L"Classes : vl::vint32_t"); writer.WriteLine(prefix + L"{"); - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -451,7 +459,7 @@ WriteAstAssemblerHeaderFile writer.WriteLine(L""); writer.WriteLine(prefix + L"enum class " + manager.Global().name + L"Fields : vl::vint32_t"); writer.WriteLine(prefix + L"{"); - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -511,7 +519,7 @@ WriteAstAssemblerCppFile writer.WriteLine(prefix + L"\tauto cppTypeName = " + manager.Global().name + L"CppTypeName((" + manager.Global().name + L"Classes)type);"); writer.WriteLine(prefix + L"\tswitch((" + manager.Global().name + L"Classes)type)"); writer.WriteLine(prefix + L"\t{"); - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -541,7 +549,7 @@ WriteAstAssemblerCppFile writer.WriteLine(prefix + L"\tauto cppFieldName = " + manager.Global().name + L"CppFieldName((" + manager.Global().name + L"Fields)field);"); List props; - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -594,7 +602,7 @@ WriteAstAssemblerCppFile writer.WriteLine(prefix + L"\tauto cppFieldName = " + manager.Global().name + L"CppFieldName((" + manager.Global().name + L"Fields)field);"); List props; - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -644,7 +652,7 @@ WriteAstAssemblerCppFile writer.WriteLine(prefix + L"\tauto cppFieldName = " + manager.Global().name + L"CppFieldName((" + manager.Global().name + L"Fields)field);"); List props; - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -824,16 +832,16 @@ WriteAstAssemblerCppFile writer.WriteLine(prefix + L"\tauto cppTypeName = " + manager.Global().name + L"CppTypeName((" + manager.Global().name + L"Classes)type);"); Dictionary resolvables; - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { auto current = classSymbol; while (current) { - if (current->ambiguousDerivedClass) + if (current->derivedClass_ToResolve) { - resolvables.Add(classSymbol, current->ambiguousDerivedClass); + resolvables.Add(classSymbol, current->derivedClass_ToResolve); break; } current = current->baseClass; @@ -846,7 +854,7 @@ WriteAstAssemblerCppFile writer.WriteLine(prefix + L"\tswitch((" + manager.Global().name + L"Classes)type)"); writer.WriteLine(prefix + L"\t{"); - for (auto typeSymbol : manager.Symbols().Values()) + for (auto typeSymbol : GetAllSymbols(manager)) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -892,17 +900,17 @@ namespace vl using namespace collections; using namespace stream; - extern void PrintCppType(AstDefFile* fileContext, AstSymbol* propSymbol, stream::StreamWriter& writer); + extern void PrintCppType(AstDefFileGroup* fileGroupContext, AstSymbol* propSymbol, stream::StreamWriter& writer); /*********************************************************************** WriteAstBuilderHeaderFile ***********************************************************************/ - void WriteAstBuilderHeaderFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteAstBuilderHeaderFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityHeaderFile(file, output, L"builder", writer, [&](const WString& prefix) + WriteAstUtilityHeaderFile(group, output, L"builder", writer, [&](const WString& prefix) { - for(auto typeSymbol : file->Symbols().Values()) + for(auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -911,7 +919,7 @@ WriteAstBuilderHeaderFile WString className = L"Make" + classSymbol->Name(); writer.WriteString(prefix + L"class " + className); writer.WriteString(L" : public vl::glr::ParsingAstBuilder<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L">"); writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"public:"); @@ -930,13 +938,13 @@ WriteAstBuilderHeaderFile if (dynamic_cast(propSymbol->propSymbol)) { writer.WriteString(prefix + L"\t" + className + L"& " + propSymbol->Name() + L"("); - PrintCppType(file, propSymbol->propSymbol, writer); + PrintCppType(group, propSymbol->propSymbol, writer); writer.WriteLine(L" value);"); break; } case AstPropType::Array: writer.WriteString(prefix + L"\t" + className + L"& " + propSymbol->Name() + L"(const vl::Ptr<"); - PrintCppType(file, propSymbol->propSymbol, writer); + PrintCppType(group, propSymbol->propSymbol, writer); writer.WriteLine(L">& value);"); break; } @@ -955,11 +963,11 @@ WriteAstBuilderHeaderFile WriteAstBuilderCppFile ***********************************************************************/ - void WriteAstBuilderCppFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteAstBuilderCppFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityCppFile(file, output->builderH, L"builder", writer, [&](const WString& prefix) + WriteAstUtilityCppFile(group, output->builderH, L"builder", writer, [&](const WString& prefix) { - for (auto typeSymbol : file->Symbols().Values()) + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { @@ -990,13 +998,13 @@ WriteAstBuilderCppFile if (dynamic_cast(propSymbol->propSymbol)) { writer.WriteString(prefix + className + L"& " + className + L"::" + propSymbol->Name() + L"("); - PrintCppType(file, propSymbol->propSymbol, writer); + PrintCppType(group, propSymbol->propSymbol, writer); writer.WriteLine(L" value)"); } if (dynamic_cast(propSymbol->propSymbol)) { writer.WriteString(prefix + className + L"& " + className + L"::" + propSymbol->Name() + L"(const vl::Ptr<"); - PrintCppType(file, propSymbol->propSymbol, writer); + PrintCppType(group, propSymbol->propSymbol, writer); writer.WriteLine(L">& value)"); } writer.WriteLine(prefix + L"{"); @@ -1006,7 +1014,7 @@ WriteAstBuilderCppFile break; case AstPropType::Array: writer.WriteString(prefix + className + L"& " + className + L"::" + propSymbol->Name() + L"(const vl::Ptr<"); - PrintCppType(file, propSymbol->propSymbol, writer); + PrintCppType(group, propSymbol->propSymbol, writer); writer.WriteLine(L">& value)"); writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"\tnode->" + propSymbol->Name() + L".Add(value);"); @@ -1043,15 +1051,15 @@ namespace vl WriteTypeForwardDefinitions ***********************************************************************/ - void WriteTypeForwardDefinitions(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer) + void WriteTypeForwardDefinitions(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer) { - for (auto [name, index] : indexed(file->Symbols().Keys())) + for (auto [name, index] : indexed(group->Symbols().Keys())) { - if (dynamic_cast(file->Symbols().Values()[index])) + if (dynamic_cast(group->Symbols().Values()[index])) { writer.WriteString(prefix); writer.WriteString(L"class "); - writer.WriteString(file->classPrefix); + writer.WriteString(group->classPrefix); writer.WriteString(name); writer.WriteLine(L";"); } @@ -1078,7 +1086,7 @@ PrintCppType Value, }; - void PrintAstType(AstDefFile* fileContext, AstPropType propType, AstSymbol* propSymbol, PrintTypePurpose purpose, stream::StreamWriter& writer) + void PrintAstType(AstDefFileGroup* fileGroupContext, AstPropType propType, AstSymbol* propSymbol, PrintTypePurpose purpose, stream::StreamWriter& writer) { if (propType == AstPropType::Token) { @@ -1095,19 +1103,19 @@ PrintCppType writer.WriteString(L"vl::Ptr<"); } - auto file = propSymbol->Owner(); + auto group = propSymbol->Owner()->Owner(); if (purpose == PrintTypePurpose::ReflectionName) { - PrintNss(file->refNss, writer); + PrintNss(group->refNss, writer); } else { - if (fileContext != file) + if (fileGroupContext != group) { - PrintNss(file->cppNss, writer); + PrintNss(group->cppNss, writer); } } - writer.WriteString(file->classPrefix); + writer.WriteString(group->classPrefix); writer.WriteString(propSymbol->Name()); if (propType == AstPropType::Array) @@ -1120,31 +1128,31 @@ PrintCppType } } - void PrintFieldType(AstDefFile* fileContext, AstPropType propType, AstSymbol* propSymbol, stream::StreamWriter& writer) + void PrintFieldType(AstDefFileGroup* fileGroupContext, AstPropType propType, AstSymbol* propSymbol, stream::StreamWriter& writer) { - PrintAstType(fileContext, propType, propSymbol, PrintTypePurpose::Value, writer); + PrintAstType(fileGroupContext, propType, propSymbol, PrintTypePurpose::Value, writer); } - void PrintCppType(AstDefFile* fileContext, AstSymbol* propSymbol, stream::StreamWriter& writer) + void PrintCppType(AstDefFileGroup* fileGroupContext, AstSymbol* propSymbol, stream::StreamWriter& writer) { - PrintAstType(fileContext, AstPropType::Type, propSymbol, PrintTypePurpose::TypeName, writer); + PrintAstType(fileGroupContext, AstPropType::Type, propSymbol, PrintTypePurpose::TypeName, writer); } /*********************************************************************** WriteTypeDefinitions ***********************************************************************/ - void WriteTypeDefinitions(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer) + void WriteTypeDefinitions(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer) { - for (auto name : file->SymbolOrder()) + for (auto name : group->SymbolOrder()) { - auto typeSymbol = file->Symbols()[name]; + auto typeSymbol = group->Symbols()[name]; if (auto enumSymbol = dynamic_cast(typeSymbol)) { writer.WriteLine(L""); writer.WriteString(prefix); writer.WriteString(L"enum class "); - writer.WriteString(file->classPrefix); + writer.WriteString(group->classPrefix); writer.WriteLine(name); writer.WriteString(prefix); writer.WriteLine(L"{"); @@ -1170,15 +1178,15 @@ WriteTypeDefinitions } } - for (auto name : file->SymbolOrder()) + for (auto name : group->SymbolOrder()) { - auto typeSymbol = file->Symbols()[name]; + auto typeSymbol = group->Symbols()[name]; if (auto classSymbol = dynamic_cast(typeSymbol)) { writer.WriteLine(L""); writer.WriteString(prefix); writer.WriteString(L"class "); - writer.WriteString(file->classPrefix); + writer.WriteString(group->classPrefix); writer.WriteString(name); if (classSymbol->derivedClasses.Count() > 0) { @@ -1187,14 +1195,14 @@ WriteTypeDefinitions writer.WriteString(L" : public "); if (classSymbol->baseClass) { - PrintCppType(file, classSymbol->baseClass, writer); + PrintCppType(group, classSymbol->baseClass, writer); } else { writer.WriteString(L"vl::glr::ParsingAstBase"); } writer.WriteString(L", vl::reflection::Description<"); - writer.WriteString(file->classPrefix); + writer.WriteString(group->classPrefix); writer.WriteString(name); writer.WriteLine(L">"); @@ -1216,7 +1224,7 @@ WriteTypeDefinitions { writer.WriteString(prefix); writer.WriteString(L"\t\tvirtual void Visit("); - PrintCppType(file, childSymbol, writer); + PrintCppType(group, childSymbol, writer); writer.WriteLine(L"* node) = 0;"); } @@ -1225,7 +1233,7 @@ WriteTypeDefinitions writer.WriteLine(L""); writer.WriteString(prefix); writer.WriteString(L"\tvirtual void Accept("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor* visitor) = 0;"); writer.WriteLine(L""); } @@ -1235,13 +1243,13 @@ WriteTypeDefinitions auto propSymbol = classSymbol->Props()[propName]; writer.WriteString(prefix); writer.WriteString(L"\t"); - PrintFieldType(file, propSymbol->propType, propSymbol->propSymbol, writer); + PrintFieldType(group, propSymbol->propType, propSymbol->propSymbol, writer); writer.WriteString(L" "); writer.WriteString(propName); if (dynamic_cast(propSymbol->propSymbol)) { writer.WriteString(L" = "); - PrintCppType(file, propSymbol->propSymbol, writer); + PrintCppType(group, propSymbol->propSymbol, writer); writer.WriteString(L"::UNDEFINED_ENUM_ITEM_VALUE"); } writer.WriteLine(L";"); @@ -1252,7 +1260,7 @@ WriteTypeDefinitions writer.WriteLine(L""); writer.WriteString(prefix); writer.WriteString(L"\tvoid Accept("); - PrintCppType(file, classSymbol->baseClass, writer); + PrintCppType(group, classSymbol->baseClass, writer); writer.WriteLine(L"::IVisitor* visitor) override;"); } @@ -1266,20 +1274,20 @@ WriteTypeDefinitions WriteVisitorImpl ***********************************************************************/ - void WriteVisitorImpl(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer) + void WriteVisitorImpl(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer) { - for (auto name : file->SymbolOrder()) + for (auto name : group->SymbolOrder()) { - if (auto classSymbol = dynamic_cast(file->Symbols()[name])) + if (auto classSymbol = dynamic_cast(group->Symbols()[name])) { if (classSymbol->baseClass) { writer.WriteLine(L""); writer.WriteString(prefix); writer.WriteString(L"void "); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteString(L"::Accept("); - PrintCppType(file, classSymbol->baseClass, writer); + PrintCppType(group, classSymbol->baseClass, writer); writer.WriteLine(L"::IVisitor* visitor)"); writer.WriteString(prefix); writer.WriteLine(L"{"); @@ -1296,13 +1304,13 @@ WriteVisitorImpl WriteTypeReflectionDeclaration ***********************************************************************/ - void WriteTypeReflectionDeclaration(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer) + void WriteTypeReflectionDeclaration(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer) { writer.WriteLine(L"#ifndef VCZH_DEBUG_NO_REFLECTION"); - for (auto&& name : file->SymbolOrder()) + for (auto&& name : group->SymbolOrder()) { - auto typeSymbol = file->Symbols()[name]; + auto typeSymbol = group->Symbols()[name]; writer.WriteString(prefix); writer.WriteString(L"DECL_TYPE_INFO("); PrintCppType(nullptr, typeSymbol, writer); @@ -1323,9 +1331,9 @@ WriteTypeReflectionDeclaration writer.WriteLine(L""); writer.WriteLine(L"#ifdef VCZH_DESCRIPTABLEOBJECT_WITH_METADATA"); writer.WriteLine(L""); - for (auto&& name : file->SymbolOrder()) + for (auto&& name : group->SymbolOrder()) { - if (auto classSymbol = dynamic_cast(file->Symbols()[name])) + if (auto classSymbol = dynamic_cast(group->Symbols()[name])) { if (classSymbol->derivedClasses.Count() > 0) { @@ -1368,8 +1376,8 @@ WriteTypeReflectionDeclaration writer.WriteString(prefix); writer.WriteString(L"extern bool "); - writer.WriteString(file->Owner()->Global().name); - writer.WriteString(file->Name()); + writer.WriteString(group->Owner()->Global().name); + writer.WriteString(group->Name()); writer.WriteLine(L"LoadTypes();"); } @@ -1377,15 +1385,15 @@ WriteTypeReflectionDeclaration WriteTypeReflectionImplementation ***********************************************************************/ - void WriteTypeReflectionImplementation(AstDefFile* file, const WString& prefix, stream::StreamWriter& writer) + void WriteTypeReflectionImplementation(AstDefFileGroup* group, const WString& prefix, stream::StreamWriter& writer) { writer.WriteLine(L"#ifndef VCZH_DEBUG_NO_REFLECTION"); writer.WriteLine(L""); - for (auto&& name : file->SymbolOrder()) + for (auto&& name : group->SymbolOrder()) { - auto typeSymbol = file->Symbols()[name]; + auto typeSymbol = group->Symbols()[name]; writer.WriteString(prefix); writer.WriteString(L"IMPL_TYPE_INFO_RENAME("); PrintCppType(nullptr, typeSymbol, writer); @@ -1411,9 +1419,9 @@ WriteTypeReflectionImplementation writer.WriteLine(L""); writer.WriteLine(L"#ifdef VCZH_DESCRIPTABLEOBJECT_WITH_METADATA"); - for (auto&& name : file->SymbolOrder()) + for (auto&& name : group->SymbolOrder()) { - auto typeSymbol = file->Symbols()[name]; + auto typeSymbol = group->Symbols()[name]; writer.WriteLine(L""); if (auto enumSymbol = dynamic_cast(typeSymbol)) @@ -1487,9 +1495,9 @@ WriteTypeReflectionImplementation } } - for (auto&& name : file->SymbolOrder()) + for (auto&& name : group->SymbolOrder()) { - if (auto classSymbol = dynamic_cast(file->Symbols()[name])) + if (auto classSymbol = dynamic_cast(group->Symbols()[name])) { if (classSymbol->derivedClasses.Count() > 0) { @@ -1524,8 +1532,8 @@ WriteTypeReflectionImplementation writer.WriteLine(L"#ifdef VCZH_DESCRIPTABLEOBJECT_WITH_METADATA"); writer.WriteString(prefix); writer.WriteString(L"class "); - writer.WriteString(file->Owner()->Global().name); - writer.WriteString(file->Name()); + writer.WriteString(group->Owner()->Global().name); + writer.WriteString(group->Name()); writer.WriteLine(L"TypeLoader : public vl::Object, public ITypeLoader"); writer.WriteString(prefix); writer.WriteLine(L"{"); @@ -1537,9 +1545,9 @@ WriteTypeReflectionImplementation writer.WriteString(prefix); writer.WriteLine(L"\t{"); - for (auto&& name : file->SymbolOrder()) + for (auto&& name : group->SymbolOrder()) { - auto typeSymbol = file->Symbols()[name]; + auto typeSymbol = group->Symbols()[name]; writer.WriteString(prefix); writer.WriteString(L"\t\tADD_TYPE_INFO("); PrintCppType(nullptr, typeSymbol, writer); @@ -1577,8 +1585,8 @@ WriteTypeReflectionImplementation writer.WriteLine(L""); writer.WriteString(prefix); writer.WriteString(L"bool "); - writer.WriteString(file->Owner()->Global().name); - writer.WriteString(file->Name()); + writer.WriteString(group->Owner()->Global().name); + writer.WriteString(group->Name()); writer.WriteLine(L"LoadTypes()"); writer.WriteString(prefix); writer.WriteLine(L"{"); @@ -1590,8 +1598,8 @@ WriteTypeReflectionImplementation writer.WriteLine(L"\t{"); writer.WriteString(prefix); writer.WriteString(L"\t\tauto loader = Ptr(new "); - writer.WriteString(file->Owner()->Global().name); - writer.WriteString(file->Name()); + writer.WriteString(group->Owner()->Global().name); + writer.WriteString(group->Name()); writer.WriteLine(L"TypeLoader);"); writer.WriteString(prefix); writer.WriteLine(L"\t\treturn manager->AddTypeLoader(loader);"); @@ -1621,21 +1629,21 @@ namespace vl using namespace collections; using namespace stream; - extern void PrintCppType(AstDefFile* fileContext, AstSymbol* propSymbol, stream::StreamWriter& writer); - extern void CollectVisitorsAndConcreteClasses(AstDefFile* file, List& visitors, List& concreteClasses); + extern void PrintCppType(AstDefFileGroup* fileGroupContext, AstSymbol* propSymbol, stream::StreamWriter& writer); + extern void CollectVisitorsAndConcreteClasses(AstDefFileGroup* group, List& visitors, List& concreteClasses); /*********************************************************************** WriteCopyFieldFunctionBody ***********************************************************************/ - void WriteCopyFieldFunctionBody(AstDefFile* file, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) + void WriteCopyFieldFunctionBody(AstDefFileGroup* group, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) { if (fieldSymbol->baseClass) { writer.WriteString(prefix + L"\tCopyFields(static_cast<"); - PrintCppType(file, fieldSymbol->baseClass, writer); + PrintCppType(group, fieldSymbol->baseClass, writer); writer.WriteString(L"*>(from), static_cast<"); - PrintCppType(file, fieldSymbol->baseClass, writer); + PrintCppType(group, fieldSymbol->baseClass, writer); writer.WriteLine(L"*>(to));"); } @@ -1670,33 +1678,33 @@ WriteCopyFieldFunctionBody WriteCopyVisitorHeaderFile ***********************************************************************/ - void WriteCopyVisitorHeaderFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteCopyVisitorHeaderFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityHeaderFile(file, output, L"copy_visitor", writer, [&](const WString& prefix) + WriteAstUtilityHeaderFile(group, output, L"copy_visitor", writer, [&](const WString& prefix) { List visitors, concreteClasses; - CollectVisitorsAndConcreteClasses(file, visitors, concreteClasses); + CollectVisitorsAndConcreteClasses(group, visitors, concreteClasses); writer.WriteLine(prefix + L"/// A copy visitor, overriding all abstract methods with AST copying code."); - writer.WriteLine(prefix + L"class " + file->Name() + L"Visitor"); + writer.WriteLine(prefix + L"class " + group->Name() + L"Visitor"); writer.WriteLine(prefix + L"\t: public virtual vl::glr::CopyVisitorBase"); for (auto visitorSymbol : visitors) { writer.WriteString(prefix + L"\t, protected virtual "); - PrintCppType(file, visitorSymbol, writer); + PrintCppType(group, visitorSymbol, writer); writer.WriteLine(L"::IVisitor"); } writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"protected:"); - for (auto typeSymbol : file->Symbols().Values()) + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { writer.WriteString(prefix + L"\tvoid CopyFields("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteString(L"* from, "); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* to);"); } } @@ -1706,7 +1714,7 @@ WriteCopyVisitorHeaderFile for (auto classSymbol : concreteClasses) { writer.WriteString(prefix + L"\tvirtual void Visit("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } writer.WriteLine(L""); @@ -1715,7 +1723,7 @@ WriteCopyVisitorHeaderFile for (auto classSymbol : visitorSymbol->derivedClasses) { writer.WriteString(prefix + L"\tvoid Visit("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node) override;"); } writer.WriteLine(L""); @@ -1729,23 +1737,23 @@ WriteCopyVisitorHeaderFile ) { writer.WriteString(prefix + L"\tvirtual vl::Ptr<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteString(L"> CopyNode("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } writer.WriteLine(L""); for (auto classSymbol : - From(file->Symbols().Values()) + From(group->Symbols().Values()) .Select([](AstSymbol* derivedClass) { return dynamic_cast(derivedClass); }) .Where([](AstClassSymbol* derivedClass) { return derivedClass && derivedClass->baseClass != nullptr; }) ) { writer.WriteString(prefix + L"\tvl::Ptr<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteString(L"> CopyNode("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } writer.WriteLine(prefix + L"};"); @@ -1756,24 +1764,24 @@ WriteCopyVisitorHeaderFile WriteCopyVisitorCppFile ***********************************************************************/ - void WriteCopyVisitorCppFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteCopyVisitorCppFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityCppFile(file, output->copyH, L"copy_visitor", writer, [&](const WString& prefix) + WriteAstUtilityCppFile(group, output->copyH, L"copy_visitor", writer, [&](const WString& prefix) { List visitors, concreteClasses; - CollectVisitorsAndConcreteClasses(file, visitors, concreteClasses); + CollectVisitorsAndConcreteClasses(group, visitors, concreteClasses); - for (auto typeSymbol : file->Symbols().Values()) + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::CopyFields("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::CopyFields("); + PrintCppType(group, classSymbol, writer); writer.WriteString(L"* from, "); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* to)"); writer.WriteLine(prefix + L"{"); - WriteCopyFieldFunctionBody(file, classSymbol, prefix, writer); + WriteCopyFieldFunctionBody(group, classSymbol, prefix, writer); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); } @@ -1781,12 +1789,12 @@ WriteCopyVisitorCppFile for (auto classSymbol : concreteClasses) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Visit("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Visit("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); writer.WriteString(prefix + L"\tauto newNode = vl::Ptr(new "); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L");"); writer.WriteLine(prefix + L"\tCopyFields(node, newNode.Obj());"); writer.WriteLine(prefix + L"\tthis->result = newNode;"); @@ -1798,14 +1806,14 @@ WriteCopyVisitorCppFile { for (auto classSymbol : visitorSymbol->derivedClasses) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Visit("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Visit("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); if (classSymbol->derivedClasses.Count() == 0) { writer.WriteString(prefix + L"\tauto newNode = vl::Ptr(new "); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L");"); writer.WriteLine(prefix + L"\tCopyFields(node, newNode.Obj());"); writer.WriteLine(prefix + L"\tthis->result = newNode;"); @@ -1813,7 +1821,7 @@ WriteCopyVisitorCppFile else { writer.WriteString(prefix + L"\tnode->Accept(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor*>(this));"); } writer.WriteLine(prefix + L"}"); @@ -1826,18 +1834,18 @@ WriteCopyVisitorCppFile if (!classSymbol->baseClass) { writer.WriteString(prefix + L"vl::Ptr<"); - PrintCppType(file, classSymbol, writer); - writer.WriteString(L"> " + file->Name() + L"Visitor::CopyNode("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); + writer.WriteString(L"> " + group->Name() + L"Visitor::CopyNode("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"\tif (!node) return nullptr;"); writer.WriteString(prefix + L"\tnode->Accept(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor*>(this));"); writer.WriteLine(prefix + L"\tthis->result->codeRange = node->codeRange;"); writer.WriteString(prefix + L"\treturn this->result.Cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L">();"); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); @@ -1847,23 +1855,23 @@ WriteCopyVisitorCppFile for (auto classSymbol : concreteClasses) { writer.WriteString(prefix + L"vl::Ptr<"); - PrintCppType(file, classSymbol, writer); - writer.WriteString(L"> " + file->Name() + L"Visitor::CopyNode("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); + writer.WriteString(L"> " + group->Name() + L"Visitor::CopyNode("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"\tif (!node) return nullptr;"); writer.WriteLine(prefix + L"\tVisit(node);"); writer.WriteLine(prefix + L"\tthis->result->codeRange = node->codeRange;"); writer.WriteString(prefix + L"\treturn this->result.Cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L">();"); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); } for (auto classSymbol : - From(file->Symbols().Values()) + From(group->Symbols().Values()) .Select([](AstSymbol* derivedClass) { return dynamic_cast(derivedClass); }) .Where([](AstClassSymbol* derivedClass) { return derivedClass && derivedClass->baseClass != nullptr; }) ) @@ -1875,16 +1883,16 @@ WriteCopyVisitorCppFile } writer.WriteString(prefix + L"vl::Ptr<"); - PrintCppType(file, classSymbol, writer); - writer.WriteString(L"> " + file->Name() + L"Visitor::CopyNode("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); + writer.WriteString(L"> " + group->Name() + L"Visitor::CopyNode("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"\tif (!node) return nullptr;"); writer.WriteString(prefix + L"\treturn CopyNode(static_cast<"); - PrintCppType(file, rootBaseClass, writer); + PrintCppType(group, rootBaseClass, writer); writer.WriteString(L"*>(node)).Cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L">();"); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); @@ -1908,25 +1916,25 @@ namespace vl using namespace collections; using namespace stream; - extern void PrintCppType(AstDefFile* fileContext, AstSymbol* propSymbol, stream::StreamWriter& writer); + extern void PrintCppType(AstDefFileGroup* fileGroupContext, AstSymbol* propSymbol, stream::StreamWriter& writer); /*********************************************************************** WriteEmptyVisitorHeaderFile ***********************************************************************/ - void WriteEmptyVisitorHeaderFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteEmptyVisitorHeaderFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityHeaderFile(file, output, L"empty_visitor", writer, [&](const WString& prefix) + WriteAstUtilityHeaderFile(group, output, L"empty_visitor", writer, [&](const WString& prefix) { - for (auto name : file->SymbolOrder()) + for (auto name : group->SymbolOrder()) { - if (auto classSymbol = dynamic_cast(file->Symbols()[name])) + if (auto classSymbol = dynamic_cast(group->Symbols()[name])) { if (classSymbol->derivedClasses.Count() > 0) { writer.WriteLine(prefix + L"/// An empty visitor, overriding all abstract methods with empty implementations."); writer.WriteString(prefix + L"class " + name + L"Visitor : public vl::Object, public "); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor"); writer.WriteLine(prefix + L"{"); @@ -1937,7 +1945,7 @@ WriteEmptyVisitorHeaderFile if (childSymbol->derivedClasses.Count() > 0) { writer.WriteString(prefix + L"\tvirtual void Dispatch("); - PrintCppType(file, childSymbol, writer); + PrintCppType(group, childSymbol, writer); writer.WriteLine(L"* node) = 0;"); } } @@ -1948,7 +1956,7 @@ WriteEmptyVisitorHeaderFile for (auto childSymbol : classSymbol->derivedClasses) { writer.WriteString(prefix + L"\tvoid Visit("); - PrintCppType(file, childSymbol, writer); + PrintCppType(group, childSymbol, writer); writer.WriteLine(L"* node) override;"); } @@ -1964,13 +1972,13 @@ WriteEmptyVisitorHeaderFile WriteEmptyVisitorCppFile ***********************************************************************/ - void WriteEmptyVisitorCppFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteEmptyVisitorCppFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityCppFile(file, output->emptyH, L"empty_visitor", writer, [&](const WString& prefix) + WriteAstUtilityCppFile(group, output->emptyH, L"empty_visitor", writer, [&](const WString& prefix) { - for (auto name : file->SymbolOrder()) + for (auto name : group->SymbolOrder()) { - if (auto classSymbol = dynamic_cast(file->Symbols()[name])) + if (auto classSymbol = dynamic_cast(group->Symbols()[name])) { if (classSymbol->derivedClasses.Count() > 0) { @@ -1985,7 +1993,7 @@ WriteEmptyVisitorCppFile { writer.WriteLine(L""); writer.WriteString(prefix + L"void " + classSymbol->Name() + L"Visitor::Visit("); - PrintCppType(file, childSymbol, writer); + PrintCppType(group, childSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); if (childSymbol->derivedClasses.Count() > 0) @@ -2016,14 +2024,14 @@ namespace vl using namespace collections; using namespace stream; - extern void PrintCppType(AstDefFile* fileContext, AstSymbol* propSymbol, stream::StreamWriter& writer); - extern void CollectVisitorsAndConcreteClasses(AstDefFile* file, List& visitors, List& concreteClasses); + extern void PrintCppType(AstDefFileGroup* fileGroupContext, AstSymbol* propSymbol, stream::StreamWriter& writer); + extern void CollectVisitorsAndConcreteClasses(AstDefFileGroup* group, List& visitors, List& concreteClasses); /*********************************************************************** WriteVisitFieldFunctionBody ***********************************************************************/ - void WritePrintFieldsFunctionBody(AstDefFile* file, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) + void WritePrintFieldsFunctionBody(AstDefFileGroup* group, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) { for (auto propSymbol : fieldSymbol->Props().Values()) { @@ -2079,7 +2087,7 @@ WriteVisitFieldFunctionBody writer.WriteLine(prefix + L"\t}"); } - void WriteVisitFunctionBody(AstDefFile* file, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) + void WriteVisitFunctionBody(AstDefFileGroup* group, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) { WriteNullAndReturn(prefix, writer); List order; @@ -2097,7 +2105,7 @@ WriteVisitFieldFunctionBody for (auto classSymbol : From(order).Reverse()) { writer.WriteString(prefix + L"\tPrintFields(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"*>(node));"); } writer.WriteLine(prefix + L"\tEndObject();"); @@ -2107,31 +2115,31 @@ WriteVisitFieldFunctionBody WriteJsonVisitorHeaderFile ***********************************************************************/ - void WriteJsonVisitorHeaderFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteJsonVisitorHeaderFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityHeaderFile(file, output, L"json_visitor", writer, [&](const WString& prefix) + WriteAstUtilityHeaderFile(group, output, L"json_visitor", writer, [&](const WString& prefix) { List visitors, concreteClasses; - CollectVisitorsAndConcreteClasses(file, visitors, concreteClasses); + CollectVisitorsAndConcreteClasses(group, visitors, concreteClasses); writer.WriteLine(prefix + L"/// A JSON visitor, overriding all abstract methods with AST to JSON serialization code."); - writer.WriteLine(prefix + L"class " + file->Name() + L"Visitor"); + writer.WriteLine(prefix + L"class " + group->Name() + L"Visitor"); writer.WriteLine(prefix + L"\t: public vl::glr::JsonVisitorBase"); for (auto visitorSymbol : visitors) { writer.WriteString(prefix + L"\t, protected virtual "); - PrintCppType(file, visitorSymbol, writer); + PrintCppType(group, visitorSymbol, writer); writer.WriteLine(L"::IVisitor"); } writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"protected:"); - for (auto typeSymbol : file->Symbols().Values()) + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { writer.WriteString(prefix + L"\tvirtual void PrintFields("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } } @@ -2143,14 +2151,14 @@ WriteJsonVisitorHeaderFile for (auto classSymbol : visitorSymbol->derivedClasses) { writer.WriteString(prefix + L"\tvoid Visit("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node) override;"); } writer.WriteLine(L""); } writer.WriteLine(prefix + L"public:"); - writer.WriteLine(prefix + L"\t" + file->Name() + L"Visitor(vl::stream::StreamWriter& _writer);"); + writer.WriteLine(prefix + L"\t" + group->Name() + L"Visitor(vl::stream::StreamWriter& _writer);"); writer.WriteLine(L""); for (auto classSymbol : From(visitors) @@ -2159,7 +2167,7 @@ WriteJsonVisitorHeaderFile ) { writer.WriteString(prefix + L"\tvoid Print("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } writer.WriteLine(prefix + L"};"); @@ -2170,22 +2178,22 @@ WriteJsonVisitorHeaderFile WriteJsonVisitorCppFile ***********************************************************************/ - void WriteJsonVisitorCppFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteJsonVisitorCppFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityCppFile(file, output->jsonH, L"json_visitor", writer, [&](const WString& prefix) + WriteAstUtilityCppFile(group, output->jsonH, L"json_visitor", writer, [&](const WString& prefix) { List visitors, concreteClasses; - CollectVisitorsAndConcreteClasses(file, visitors, concreteClasses); + CollectVisitorsAndConcreteClasses(group, visitors, concreteClasses); - for (auto typeSymbol : file->Symbols().Values()) + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::PrintFields("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::PrintFields("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); - WritePrintFieldsFunctionBody(file, classSymbol, prefix, writer); + WritePrintFieldsFunctionBody(group, classSymbol, prefix, writer); writer.WriteLine(prefix + L"}"); } } @@ -2195,18 +2203,18 @@ WriteJsonVisitorCppFile { for (auto classSymbol : visitorSymbol->derivedClasses) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Visit("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Visit("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); if (classSymbol->derivedClasses.Count() == 0) { - WriteVisitFunctionBody(file, classSymbol, prefix, writer); + WriteVisitFunctionBody(group, classSymbol, prefix, writer); } else { writer.WriteString(prefix + L"\tnode->Accept(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor*>(this));"); } writer.WriteLine(prefix + L"}"); @@ -2214,7 +2222,7 @@ WriteJsonVisitorCppFile } } - writer.WriteLine(prefix + file->Name() + L"Visitor::" + file->Name() + L"Visitor(vl::stream::StreamWriter& _writer)"); + writer.WriteLine(prefix + group->Name() + L"Visitor::" + group->Name() + L"Visitor(vl::stream::StreamWriter& _writer)"); writer.WriteLine(prefix + L"\t: vl::glr::JsonVisitorBase(_writer)"); writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"}"); @@ -2224,13 +2232,13 @@ WriteJsonVisitorCppFile { if (!classSymbol->baseClass) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Print("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Print("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); WriteNullAndReturn(prefix, writer); writer.WriteString(prefix + L"\tnode->Accept(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor*>(this));"); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); @@ -2239,11 +2247,11 @@ WriteJsonVisitorCppFile for (auto classSymbol : concreteClasses) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Print("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Print("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); - WriteVisitFunctionBody(file, classSymbol, prefix, writer); + WriteVisitFunctionBody(group, classSymbol, prefix, writer); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); } @@ -2266,14 +2274,14 @@ namespace vl using namespace collections; using namespace stream; - extern void PrintCppType(AstDefFile* fileContext, AstSymbol* propSymbol, stream::StreamWriter& writer); - extern void CollectVisitorsAndConcreteClasses(AstDefFile* file, List& visitors, List& concreteClasses); + extern void PrintCppType(AstDefFileGroup* fileGroupContext, AstSymbol* propSymbol, stream::StreamWriter& writer); + extern void CollectVisitorsAndConcreteClasses(AstDefFileGroup* group, List& visitors, List& concreteClasses); /*********************************************************************** WriteVisitFieldFunctionBody ***********************************************************************/ - void WriteVisitFieldFunctionBody(AstDefFile* file, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) + void WriteVisitFieldFunctionBody(AstDefFileGroup* group, AstClassSymbol* fieldSymbol, const WString& prefix, stream::StreamWriter& writer) { writer.WriteLine(prefix + L"\tif (!node) return;"); List order; @@ -2290,7 +2298,7 @@ WriteVisitFieldFunctionBody for (auto classSymbol : From(order).Reverse()) { writer.WriteString(prefix + L"\tTraverse(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"*>(node));"); } @@ -2326,7 +2334,7 @@ WriteVisitFieldFunctionBody for (auto classSymbol : order) { writer.WriteString(prefix + L"\tFinishing(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"*>(node));"); } writer.WriteLine(prefix + L"\tFinishing(static_cast(node));"); @@ -2336,20 +2344,20 @@ WriteVisitFieldFunctionBody WriteTraverseVisitorHeaderFile ***********************************************************************/ - void WriteTraverseVisitorHeaderFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteTraverseVisitorHeaderFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityHeaderFile(file, output, L"traverse_visitor", writer, [&](const WString& prefix) + WriteAstUtilityHeaderFile(group, output, L"traverse_visitor", writer, [&](const WString& prefix) { List visitors, concreteClasses; - CollectVisitorsAndConcreteClasses(file, visitors, concreteClasses); + CollectVisitorsAndConcreteClasses(group, visitors, concreteClasses); writer.WriteLine(prefix + L"/// A traverse visitor, overriding all abstract methods with AST visiting code."); - writer.WriteLine(prefix + L"class " + file->Name() + L"Visitor"); + writer.WriteLine(prefix + L"class " + group->Name() + L"Visitor"); writer.WriteLine(prefix + L"\t: public vl::Object"); for (auto visitorSymbol : visitors) { writer.WriteString(prefix + L"\t, protected virtual "); - PrintCppType(file, visitorSymbol, writer); + PrintCppType(group, visitorSymbol, writer); writer.WriteLine(L"::IVisitor"); } writer.WriteLine(prefix + L"{"); @@ -2357,12 +2365,12 @@ WriteTraverseVisitorHeaderFile writer.WriteLine(prefix + L"protected:"); writer.WriteLine(prefix + L"\tvirtual void Traverse(vl::glr::ParsingToken& token);"); writer.WriteLine(prefix + L"\tvirtual void Traverse(vl::glr::ParsingAstBase* node);"); - for (auto typeSymbol : file->Symbols().Values()) + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { writer.WriteString(prefix + L"\tvirtual void Traverse("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } } @@ -2370,12 +2378,12 @@ WriteTraverseVisitorHeaderFile writer.WriteLine(prefix + L"protected:"); writer.WriteLine(prefix + L"\tvirtual void Finishing(vl::glr::ParsingAstBase* node);"); - for (auto typeSymbol : file->Symbols().Values()) + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { writer.WriteString(prefix + L"\tvirtual void Finishing("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } } @@ -2387,7 +2395,7 @@ WriteTraverseVisitorHeaderFile for (auto classSymbol : visitorSymbol->derivedClasses) { writer.WriteString(prefix + L"\tvoid Visit("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node) override;"); } writer.WriteLine(L""); @@ -2401,7 +2409,7 @@ WriteTraverseVisitorHeaderFile ) { writer.WriteString(prefix + L"\tvoid InspectInto("); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node);"); } writer.WriteLine(prefix + L"};"); @@ -2412,33 +2420,33 @@ WriteTraverseVisitorHeaderFile WriteTraverseVisitorCppFile ***********************************************************************/ - void WriteTraverseVisitorCppFile(AstDefFile* file, Ptr output, stream::StreamWriter& writer) + void WriteTraverseVisitorCppFile(AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer) { - WriteAstUtilityCppFile(file, output->traverseH, L"traverse_visitor", writer, [&](const WString& prefix) + WriteAstUtilityCppFile(group, output->traverseH, L"traverse_visitor", writer, [&](const WString& prefix) { List visitors, concreteClasses; - CollectVisitorsAndConcreteClasses(file, visitors, concreteClasses); + CollectVisitorsAndConcreteClasses(group, visitors, concreteClasses); - writer.WriteLine(prefix + L"void " + file->Name() + L"Visitor::Traverse(vl::glr::ParsingToken& token) {}"); - writer.WriteLine(prefix + L"void " + file->Name() + L"Visitor::Traverse(vl::glr::ParsingAstBase* node) {}"); - for (auto typeSymbol : file->Symbols().Values()) + writer.WriteLine(prefix + L"void " + group->Name() + L"Visitor::Traverse(vl::glr::ParsingToken& token) {}"); + writer.WriteLine(prefix + L"void " + group->Name() + L"Visitor::Traverse(vl::glr::ParsingAstBase* node) {}"); + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Traverse("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Traverse("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node) {}"); } } writer.WriteLine(L""); - writer.WriteLine(prefix + L"void " + file->Name() + L"Visitor::Finishing(vl::glr::ParsingAstBase* node) {}"); - for (auto typeSymbol : file->Symbols().Values()) + writer.WriteLine(prefix + L"void " + group->Name() + L"Visitor::Finishing(vl::glr::ParsingAstBase* node) {}"); + for (auto typeSymbol : group->Symbols().Values()) { if (auto classSymbol = dynamic_cast(typeSymbol)) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Finishing("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Finishing("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node) {}"); } } @@ -2448,18 +2456,18 @@ WriteTraverseVisitorCppFile { for (auto classSymbol : visitorSymbol->derivedClasses) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::Visit("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::Visit("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); if (classSymbol->derivedClasses.Count() == 0) { - WriteVisitFieldFunctionBody(file, classSymbol, prefix, writer); + WriteVisitFieldFunctionBody(group, classSymbol, prefix, writer); } else { writer.WriteString(prefix + L"\tnode->Accept(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor*>(this));"); } writer.WriteLine(prefix + L"}"); @@ -2471,13 +2479,13 @@ WriteTraverseVisitorCppFile { if (!classSymbol->baseClass) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::InspectInto("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::InspectInto("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); writer.WriteLine(prefix + L"\tif (!node) return;"); writer.WriteString(prefix + L"\tnode->Accept(static_cast<"); - PrintCppType(file, classSymbol, writer); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"::IVisitor*>(this));"); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); @@ -2486,11 +2494,11 @@ WriteTraverseVisitorCppFile for (auto classSymbol : concreteClasses) { - writer.WriteString(prefix + L"void " + file->Name() + L"Visitor::InspectInto("); - PrintCppType(file, classSymbol, writer); + writer.WriteString(prefix + L"void " + group->Name() + L"Visitor::InspectInto("); + PrintCppType(group, classSymbol, writer); writer.WriteLine(L"* node)"); writer.WriteLine(prefix + L"{"); - WriteVisitFieldFunctionBody(file, classSymbol, prefix, writer); + WriteVisitFieldFunctionBody(group, classSymbol, prefix, writer); writer.WriteLine(prefix + L"}"); writer.WriteLine(L""); } @@ -2573,7 +2581,7 @@ AstClassPropSymbol propType = _type; if (_type == AstPropType::Token) return true; - auto& symbols = parent->Owner()->Symbols(); + auto& symbols = parent->Owner()->Owner()->Symbols(); vint index = symbols.Keys().IndexOf(typeName); if (index == -1) { @@ -2588,6 +2596,19 @@ AstClassPropSymbol } propSymbol = symbols.Values()[index]; + + if (parent->Owner() != propSymbol->Owner() && !propSymbol->isPublic) + { + ownerFile->AddError( + ParserErrorType::FieldTypeNotPublic, + codeRange, + ownerFile->Name(), + parent->Name(), + name + ); + return false; + } + if (_type == AstPropType::Type) return true; if (!dynamic_cast(propSymbol)) @@ -2615,7 +2636,7 @@ AstClassSymbol bool AstClassSymbol::SetBaseClass(const WString& typeName, ParsingTextRange codeRange) { - auto& symbols = ownerFile->Symbols(); + auto& symbols = ownerFile->Owner()->Symbols(); vint index = symbols.Keys().IndexOf(typeName); if (index == -1) { @@ -2641,6 +2662,22 @@ AstClassSymbol ); return false; } + else if (ownerFile != newBaseClass->Owner() && !newBaseClass->isPublic) + { + ownerFile->AddError( + ParserErrorType::BaseClassNotPublic, + codeRange, + ownerFile->Name(), + name, + typeName + ); + return false; + } + + if (newBaseClass->derivedClass_Common) + { + newBaseClass = newBaseClass->derivedClass_Common; + } List visited; visited.Add(newBaseClass); @@ -2670,11 +2707,12 @@ AstClassSymbol return true; } - AstClassSymbol* AstClassSymbol::CreateAmbiguousDerivedClass(ParsingTextRange codeRange) + AstClassSymbol* AstClassSymbol::CreateDerivedClass_ToResolve(ParsingTextRange codeRange) { - if (!ambiguousDerivedClass) + if (!derivedClass_ToResolve) { - auto derived = ownerFile->CreateClass(name + L"ToResolve", codeRange); + auto derived = ownerFile->CreateClass(name + L"ToResolve", false, codeRange); + derived->classType = AstClassType::Generated_ToResolve; derived->baseClass = this; derivedClasses.Add(derived); @@ -2682,9 +2720,23 @@ AstClassSymbol prop->propType = AstPropType::Array; prop->propSymbol = this; - ambiguousDerivedClass = derived; + derivedClass_ToResolve = derived; } - return ambiguousDerivedClass; + return derivedClass_ToResolve; + } + + AstClassSymbol* AstClassSymbol::CreateDerivedClass_Common(ParsingTextRange codeRange) + { + if (!derivedClass_Common) + { + auto derived = ownerFile->CreateClass(name + L"Common", isPublic, codeRange); + derived->classType = AstClassType::Generated_Common; + derived->baseClass = this; + derivedClasses.Add(derived); + + derivedClass_Common = derived; + } + return derivedClass_Common; } AstClassPropSymbol* AstClassSymbol::CreateProp(const WString& propName, ParsingTextRange codeRange) @@ -2782,44 +2834,68 @@ AstDefFile if (!symbols.Add(symbolName, symbol)) { AddError( - ParserErrorType::DuplicatedSymbol, + ParserErrorType::DuplicatedSymbolInFile, codeRange, name, symbolName ); } - else if (!ownerManager->symbolMap.Keys().Contains(symbolName)) - { - ownerManager->symbolMap.Add(symbolName, symbol); - } - else + else if (ownerGroup->symbolMap.Keys().Contains(symbolName)) { AddError( - ParserErrorType::DuplicatedSymbolGlobally, + ParserErrorType::DuplicatedSymbolInFileGroup, codeRange, name, symbolName, - ownerManager->symbolMap[symbolName]->Owner()->name + ownerGroup->symbolMap[symbolName]->Owner()->name ); } + else + { + ownerGroup->symbolMap.Add(symbolName, symbol); + ownerGroup->ownerManager->symbolGroup.Add(symbolName, symbol); + } return symbol; } - AstDefFile::AstDefFile(ParserSymbolManager* _global, AstSymbolManager* _ownerManager, const WString& _name) - : global(_global) - , ownerManager(_ownerManager) + AstDefFile::AstDefFile(AstDefFileGroup* _ownerGroup, const WString& _name) + : ownerGroup(_ownerGroup) , name(_name) { } - bool AstDefFile::AddDependency(const WString& dependency, ParsingTextRange codeRange) + AstEnumSymbol* AstDefFile::CreateEnum(const WString& symbolName, bool isPublic, ParsingTextRange codeRange) + { + auto symbol = CreateSymbol(symbolName, codeRange); + symbol->isPublic = isPublic; + return symbol; + } + + AstClassSymbol* AstDefFile::CreateClass(const WString& symbolName, bool isPublic, ParsingTextRange codeRange) + { + auto symbol = CreateSymbol(symbolName, codeRange); + symbol->isPublic = isPublic; + return symbol; + } + +/*********************************************************************** +AstDefFileGroup +***********************************************************************/ + + AstDefFileGroup::AstDefFileGroup(AstSymbolManager* _ownerManager, const WString& _name) + : ownerManager(_ownerManager) + , name(_name) + { + } + + bool AstDefFileGroup::AddDependency(const WString& dependency, ParsingTextRange codeRange) { if (dependencies.Contains(dependency)) return true; - if (!ownerManager->Files().Keys().Contains(dependency)) + if (!ownerManager->FileGroups().Keys().Contains(dependency)) { AddError( - ParserErrorType::FileDependencyNotExists, + ParserErrorType::FileGroupDependencyNotExists, codeRange, name, dependency @@ -2836,14 +2912,14 @@ AstDefFile if (currentName == name) { AddError( - ParserErrorType::FileCyclicDependency, + ParserErrorType::FileGroupCyclicDependency, codeRange, name, dependency ); return false; } - auto current = ownerManager->Files()[currentName]; + auto current = ownerManager->FileGroups()[currentName]; // TODO: (enumerable) foreach for (vint j = 0; j < current->dependencies.Count(); j++) { @@ -2859,14 +2935,18 @@ AstDefFile return true; } - AstEnumSymbol* AstDefFile::CreateEnum(const WString& symbolName, ParsingTextRange codeRange) + AstDefFile* AstDefFileGroup::CreateFile(const WString& name) { - return CreateSymbol(symbolName, codeRange); - } - - AstClassSymbol* AstDefFile::CreateClass(const WString& symbolName, ParsingTextRange codeRange) - { - return CreateSymbol(symbolName, codeRange); + auto file = new AstDefFile(this, name); + if (!files.Add(name, file)) + { + AddError( + ParserErrorType::DuplicatedFile, + {}, + name + ); + } + return file; } /*********************************************************************** @@ -2878,18 +2958,18 @@ AstSymbolManager { } - AstDefFile* AstSymbolManager::CreateFile(const WString& name) + AstDefFileGroup* AstSymbolManager::CreateFileGroup(const WString& name) { - auto file = new AstDefFile(&global, this, name); - if (!files.Add(name, file)) + auto fileGroup = new AstDefFileGroup(this, name); + if (!fileGroups.Add(name, fileGroup)) { - file->AddError( - ParserErrorType::DuplicatedFile, - {}, + global.AddError( + ParserErrorType::DuplicatedFileGroup, + { ParserDefFileType::AstGroup,name }, name ); } - return file; + return fileGroup; } } } @@ -2913,10 +2993,11 @@ CreateParserGenRuleAst AstDefFile* CreateParserGenRuleAst(AstSymbolManager& manager) { - auto _ast = manager.CreateFile(L"RuleAst"); - Fill(_ast->cppNss, L"vl", L"glr", L"parsergen"); - Fill(_ast->refNss, L"glr", L"parsergen"); - _ast->classPrefix = L"Glr"; + auto _group = manager.CreateFileGroup(L"RuleAst"); + auto _ast = _group->CreateFile(L"Ast"); + Fill(_group->cppNss, L"vl", L"glr", L"parsergen"); + Fill(_group->refNss, L"glr", L"parsergen"); + _group->classPrefix = L"Glr"; /////////////////////////////////////////////////////////////////////////////////// // Condition @@ -3127,10 +3208,11 @@ CreateParserGenTypeAst AstDefFile* CreateParserGenTypeAst(AstSymbolManager& manager) { - auto _ast = manager.CreateFile(L"TypeAst"); - Fill(_ast->cppNss, L"vl", L"glr", L"parsergen"); - Fill(_ast->refNss, L"glr", L"parsergen"); - _ast->classPrefix = L"Glr"; + auto _group = manager.CreateFileGroup(L"TypeAst"); + auto _ast = _group->CreateFile(L"Ast"); + Fill(_group->cppNss, L"vl", L"glr", L"parsergen"); + Fill(_group->refNss, L"glr", L"parsergen"); + _group->classPrefix = L"Glr"; auto _type = _ast->CreateClass(L"Type"); _type->CreateProp(L"attPublic")->SetPropType(AstPropType::Token); @@ -3587,6 +3669,7 @@ namespace vl { namespace parsergen { + using namespace collections; /*********************************************************************** CompileAst @@ -3604,14 +3687,23 @@ CompileAst void Visit(GlrEnum* node) override { - auto symbol = astDefFile->CreateEnum(node->name.value, node->name.codeRange); + auto symbol = astDefFile->CreateEnum(node->name.value, node->attPublic, node->name.codeRange); symbol->isPublic = node->attPublic; } void Visit(GlrClass* node) override { - auto symbol = astDefFile->CreateClass(node->name.value, node->name.codeRange); + auto symbol = astDefFile->CreateClass(node->name.value, node->attPublic, node->name.codeRange); symbol->isPublic = node->attPublic; + + if (node->attAmbiguous) + { + symbol->CreateDerivedClass_ToResolve(node->name.codeRange); + if (node->props.Count() > 0) + { + symbol->CreateDerivedClass_Common(node->name.codeRange); + } + } } }; @@ -3634,17 +3726,16 @@ CompileAst } } - void Visit(GlrClass* node) override + void FillClassSymbolBaseClass(GlrClass* node, AstClassSymbol* classSymbol) { - auto classSymbol = dynamic_cast(astDefFile->Symbols()[node->name.value]); if (node->baseClass) { classSymbol->SetBaseClass(node->baseClass.value, node->baseClass.codeRange); } - if (node->attAmbiguous) - { - classSymbol->CreateAmbiguousDerivedClass(node->name.codeRange); - } + } + + void FillClassSymbolProps(GlrClass* node, AstClassSymbol* classSymbol) + { for (auto prop : node->props) { auto propSymbol = classSymbol->CreateProp(prop->name.value, prop->name.codeRange); @@ -3663,10 +3754,23 @@ CompileAst } } } + + void Visit(GlrClass* node) override + { + auto classSymbol = dynamic_cast(astDefFile->Symbols()[node->name.value]); + FillClassSymbolBaseClass(node, classSymbol); + + if (node->attAmbiguous && classSymbol->derivedClass_Common) + { + classSymbol = classSymbol->derivedClass_Common; + } + FillClassSymbolProps(node, classSymbol); + } }; - void CompileAst(AstSymbolManager& astManager, AstDefFile* astDefFile, Ptr file) + void CompileAst(AstSymbolManager& astManager, collections::List>>& files) { + for (auto [astDefFile, file] : files) { CreateAstSymbolVisitor visitor(astDefFile); for (auto type : file->types) @@ -3676,13 +3780,23 @@ CompileAst } if (astManager.Global().Errors().Count() == 0) { - FillAstSymbolVisitor visitor(astDefFile); - for (auto type : file->types) + for (auto [astDefFile, file] : files) { - type->Accept(&visitor); + FillAstSymbolVisitor visitor(astDefFile); + for (auto type : file->types) + { + type->Accept(&visitor); + } } } } + + void CompileAst(AstSymbolManager& astManager, AstDefFile* astDefFile, Ptr file) + { + List>> files; + files.Add({ astDefFile,file }); + CompileAst(astManager, files); + } } } } @@ -3876,7 +3990,7 @@ CompileSyntax .IsEmpty(); } - void CreateSyntaxSymbols(LexerSymbolManager& lexerManager, SyntaxSymbolManager& syntaxManager, Ptr syntaxFile) + void CreateSyntaxSymbols(LexerSymbolManager& lexerManager, SyntaxSymbolManager& syntaxManager, vint fileIndex, Ptr syntaxFile) { for (auto rule : syntaxFile->rules) { @@ -3890,9 +4004,13 @@ CompileSyntax } else { - auto ruleSymbol = syntaxManager.CreateRule(rule->name.value, rule->codeRange); - ruleSymbol->isPublic = rule->attPublic; - ruleSymbol->isParser = rule->attParser; + auto ruleSymbol = syntaxManager.CreateRule( + rule->name.value, + fileIndex, + rule->attPublic, + rule->attParser, + rule->codeRange + ); } for (auto clause : rule->clauses) @@ -3949,15 +4067,14 @@ CompileSyntax { // merge files to single syntax file auto syntaxFile = Ptr(new GlrSyntaxFile); - for (auto file : files) + for (auto [file, index] : indexed(files)) { CopyFrom(syntaxFile->switches, file->switches, true); CopyFrom(syntaxFile->rules, file->rules, true); + CreateSyntaxSymbols(lexerManager, syntaxManager, index, file); } auto rawSyntaxFile = syntaxFile; - - CreateSyntaxSymbols(lexerManager, syntaxManager, syntaxFile); if (syntaxManager.Global().Errors().Count() > 0) goto FINISHED_COMPILING; if (NeedRewritten_Switch(syntaxFile)) @@ -3991,6 +4108,13 @@ CompileSyntax FINISHED_COMPILING: return rawSyntaxFile == syntaxFile ? nullptr : syntaxFile; } + + Ptr CompileSyntax(AstSymbolManager& astManager, LexerSymbolManager& lexerManager, SyntaxSymbolManager& syntaxManager, Ptr output, Ptr file) + { + List> files; + files.Add(file); + return CompileSyntax(astManager, lexerManager, syntaxManager, output, files); + } } } } @@ -4453,6 +4577,7 @@ CalculateRuleAndClauseTypes auto updateRuleType = [&context, &explicitlyTypedRules](RuleSymbol* rule, AstClassSymbol* newClauseType, bool promptIfNull, bool* ruleTypeChanged = nullptr) { auto newRuleType = FindCommonBaseClass(rule->ruleType, newClauseType); + if (explicitlyTypedRules.Contains(rule)) { if (rule->ruleType != newRuleType) @@ -5042,7 +5167,19 @@ ResolveNameVisitor return nullptr; } - auto classSymbol = dynamic_cast(context.astManager.Symbols().Values()[index]); + auto&& resolvedSymbols = context.astManager.Symbols().GetByIndex(index); + if (resolvedSymbols.Count() > 1) + { + context.syntaxManager.AddError( + ParserErrorType::TypeNotUniqueInRule, + typeName.codeRange, + ruleSymbol->Name(), + typeName.value + ); + return nullptr; + } + + auto classSymbol = dynamic_cast(resolvedSymbols[0]); if (!classSymbol) { context.syntaxManager.AddError( @@ -5051,6 +5188,12 @@ ResolveNameVisitor ruleSymbol->Name(), typeName.value ); + return nullptr; + } + + if (classSymbol->derivedClass_Common) + { + classSymbol = classSymbol->derivedClass_Common; } return classSymbol; } @@ -5084,6 +5227,19 @@ ResolveNameVisitor node->literal.value ); } + else if (ruleIndex != -1) + { + auto refRuleSymbol = context.syntaxManager.Rules().Values()[ruleIndex]; + if (ruleSymbol->fileIndex != refRuleSymbol->fileIndex && !refRuleSymbol->isPublic) + { + context.syntaxManager.AddError( + ParserErrorType::ReferencedRuleNotPublicInRuleOfDifferentFile, + node->codeRange, + ruleSymbol->Name(), + node->literal.value + ); + } + } } break; case GlrRefType::Literal: @@ -5181,6 +5337,16 @@ ResolveNameVisitor else { auto usedRuleSymbol = context.syntaxManager.Rules().Values()[ruleIndex]; + if (ruleSymbol->fileIndex != usedRuleSymbol->fileIndex && !usedRuleSymbol->isPublic) + { + context.syntaxManager.AddError( + ParserErrorType::ReferencedRuleNotPublicInRuleOfDifferentFile, + name.codeRange, + ruleSymbol->Name(), + name.value + ); + } + if (addRuleReuseDependency) { if (!context.ruleReuseDependencies.Contains(ruleSymbol, usedRuleSymbol)) @@ -5547,6 +5713,7 @@ namespace vl struct RewritingContext { List pmRules; // all rules that need to be rewritten + Dictionary skippedRules; // skipped RuleSymbol -> GlrRule Dictionary originRules; // rewritten RuleSymbol -> GlrRule ends with _LRI_Original, which is the same GlrRule object before rewritten Dictionary lriRules; // rewritten RuleSymbol -> GlrRule containing left_recursion_inject clauses Dictionary fixedAstRules; // RuleSymbol -> GlrRule relationship after rewritten @@ -5641,9 +5808,13 @@ FillMissingPrefixMergeClauses RemoveDirectReferences(vContext.directSimpleUseRules, ruleSymbol, clause.Obj()); // fix rule and clause symbols - auto newRuleSymbol = syntaxManager.CreateRule(newRule->name.value, ruleRaw->name.codeRange); - newRuleSymbol->isPublic = ruleSymbol->isPublic; - newRuleSymbol->isParser = ruleSymbol->isParser; + auto newRuleSymbol = syntaxManager.CreateRule( + newRule->name.value, + ruleSymbol->fileIndex, + true, + ruleSymbol->isParser, + ruleRaw->name.codeRange + ); newRuleSymbol->isPartial = ruleSymbol->isPartial; newRuleSymbol->ruleType = vContext.clauseTypes[clause.Obj()]; vContext.astRules.Add(newRuleSymbol, newRule.Obj()); @@ -5690,6 +5861,48 @@ CollectRewritingTargets auto ruleSymbol = vContext.syntaxManager.Rules()[rule->name.value]; if (vContext.indirectPmClauses.Keys().Contains(ruleSymbol)) { + // when a rule has + // no direct prefix_merge clause + // only one clause which starts with prefix_merge clause + // such clause is not a simple use clause + // skip rewriting it + if (!vContext.directPmClauses.Keys().Contains(ruleSymbol)) + { + bool found = false; + for (auto clause : rule->clauses) + { + vint index = vContext.clauseToStartRules.Keys().IndexOf(clause.Obj()); + if (index == -1) continue; + + auto&& startRules = vContext.clauseToStartRules.GetByIndex(index); + for (auto startRule : startRules) + { + if (vContext.indirectPmClauses.Keys().Contains(startRule)) + { + if (vContext.simpleUseClauseToReferencedRules.Keys().Contains(clause.Obj())) + { + goto DO_NOT_SKIP; + } + + if (!found) + { + found = true; + break; + } + else + { + goto DO_NOT_SKIP; + } + break; + } + } + } + + rContext.skippedRules.Add(ruleSymbol, rule.Obj()); + continue; + DO_NOT_SKIP:; + } + rContext.pmRules.Add(ruleSymbol); vint indexStart = vContext.directStartRules.Keys().IndexOf(ruleSymbol); @@ -5777,8 +5990,14 @@ CreateRewrittenRules rewritten->rules.Add(lri); rContext.lriRules.Add(ruleSymbol, lri.Obj()); + lri->codeRange = originRule->codeRange; + lri->attPublic = originRule->attPublic; + lri->attParser = originRule->attParser; lri->codeRange = originRule->name.codeRange; lri->name = originRule->name; + + originRule->attPublic = {}; + originRule->attParser = {}; originRule->name.value += L"_LRI_Original"; } @@ -5815,10 +6034,14 @@ FixRuleTypes { auto originRule = rContext.originRules[ruleSymbol]; auto lriRule = rContext.lriRules[ruleSymbol]; - auto originSymbol = syntaxManager.CreateRule(originRule->name.value, originRule->codeRange); + auto originSymbol = syntaxManager.CreateRule( + originRule->name.value, + ruleSymbol->fileIndex, + ruleSymbol->isPublic, + ruleSymbol->isParser, + originRule->codeRange + ); - originSymbol->isPublic = ruleSymbol->isPublic; - originSymbol->isParser = ruleSymbol->isParser; originSymbol->isPartial = ruleSymbol->isPartial; originSymbol->ruleType = ruleSymbol->ruleType; rContext.fixedAstRules.Set(originSymbol, originRule); @@ -5828,7 +6051,13 @@ FixRuleTypes for (auto [pair, epRule] : rContext.extractedPrefixRules) { auto originRule = rContext.originRules[pair.key]; - auto epRuleSymbol = syntaxManager.CreateRule(epRule->name.value, originRule->codeRange); + auto epRuleSymbol = syntaxManager.CreateRule( + epRule->name.value, + pair.key->fileIndex, + false, + false, + originRule->codeRange + ); epRuleSymbol->ruleType = pair.value->ruleType; rContext.fixedAstRules.Add(epRuleSymbol, epRule); } @@ -6135,7 +6364,12 @@ RewriteRules (AST Creation) lriCont->flags.Add(lriContFlag); lriContFlag->flag.value = flag; - auto lriContTarget = CreateLriClause(rContext.originRules[pmInjectRecord.injectIntoRule]->name.value); + vint injectIntoOriginIndex = rContext.originRules.Keys().IndexOf(pmInjectRecord.injectIntoRule); + auto lriContTargetName = injectIntoOriginIndex == -1 + ? pmInjectRecord.injectIntoRule->Name() + : rContext.originRules.Values()[injectIntoOriginIndex]->name.value + ; + auto lriContTarget = CreateLriClause(lriContTargetName); lriCont->injectionTargets.Add(lriContTarget); return lriCont; @@ -6743,7 +6977,7 @@ RenamePrefix void RenamePrefix(RewritingContext& rContext, const SyntaxSymbolManager& syntaxManager) { - for (auto [ruleSymbol, originRule] : rContext.originRules) + for (auto [ruleSymbol, originRule] : From(rContext.originRules).Concat(rContext.skippedRules)) { RenamePrefixVisitor visitor(rContext, ruleSymbol, syntaxManager); for (auto clause : originRule->clauses) @@ -7512,6 +7746,8 @@ RewriteSyntax { auto newRule = Ptr(new GlrRule); newRule->codeRange = rule->codeRange; + newRule->attPublic = rule->attPublic; + newRule->attParser = rule->attParser; newRule->name = rule->name; newRule->name.value = name; newRule->type = rule->type; @@ -7549,6 +7785,9 @@ RewriteSyntax { auto newRuleSymbol = syntaxManager.CreateRule( rule->name.value, + ruleSymbol->fileIndex, + ruleSymbol->isPublic, + false, rule->name.codeRange ); } @@ -7595,6 +7834,8 @@ RewriteSyntax // rules it references could be renamed auto newRule = Ptr(new GlrRule); newRule->codeRange = rule->codeRange; + newRule->attPublic = rule->attPublic; + newRule->attParser = rule->attParser; newRule->name = rule->name; newRule->type = rule->type; @@ -7991,19 +8232,6 @@ ValidateDeducingPrefixMergeRuleVisitor void ValidateClause(Ptr clause) { clause->Accept(this); - if (result) - { - for (auto [refName, refRuleSymbol] : *result.Obj()) - { - context.syntaxManager.AddError( - ParserErrorType::RuleDeductToPrefixMergeInNonSimpleUseClause, - clause->codeRange, - ruleSymbol->Name(), - refRuleSymbol->Name(), - refName->value - ); - } - } } protected: @@ -9907,7 +10135,7 @@ ValidateTypes } /*********************************************************************** -.\PARSERGEN\PARSERCPPGEN.CPP +.\PARSERGEN_GLOBAL\PARSERCPPGEN.CPP ***********************************************************************/ namespace vl @@ -10075,7 +10303,7 @@ Utility } /*********************************************************************** -.\PARSERGEN\PARSERSYMBOL.CPP +.\PARSERGEN_GLOBAL\PARSERSYMBOL.CPP ***********************************************************************/ namespace vl @@ -12975,13 +13203,13 @@ namespace vl::glr::parsergen { void ParserGenRuleParserData(vl::stream::IStream& outputStream) { - static const vl::vint dataLength = 14861; // 207517 bytes before compressing + static const vl::vint dataLength = 14903; // 207517 bytes before compressing static const vl::vint dataBlock = 256; - static const vl::vint dataRemain = 13; + static const vl::vint dataRemain = 55; static const vl::vint dataSolidRows = 58; static const vl::vint dataRows = 59; static const char* compressed[] = { - "\x9D\x2A\x03\x00\x05\x3A\x00\x00\x27\x00\x01\x82\x80\x08\x0B\x82\x81\x82\x06\x89\x82\x88\x0A\x86\x06\x84\x0A\x0A\x97\x0A\x9C\x0A\x82\x12\x84\x80\x09\xAD\x0A\x92\x1A\x81\x2A\x84\x2B\x0A\xDC\x0A\x9F\x2A\x83\x32\x84\x34\x0A\x8C\x4A\x8F\x4A\x82\x4A\x84\x4B\x0A\xA1\x4A\x87\x5A\x86\x56\x84\x5C\x0A\xC5\x1E\x09\x8F\x7D\x9E\x9F\x9E\x0A\x80\x3F\x9F\x91\xA3\xA2\x9F\xA2\x46\xFF\x48\xA6\xAB\xA3\xA1\xA6\xA2\x0A\xC9\x8A\xB1\xA9\xA7\xA7\xA2\xAA\x4C\xD8\x8E\xA1\xAA\x81\x02\xAC\xA8\x3C\xD5\x9F\xB7\xA1\xB1\xAD\xB3\xAD\x67\xE0\x86\x92\xA6\xA8\xA3\xB0\xB7\x69\xE4\xAB\xA2\xB1\xB8\xBB\xB8\xB3\x77\xE8\x86\x9E\xA9\x84\xBD\xBC\xB5\x03\xEC\xAF\xB3\xA5\xBC\xC3\xBE\xB9\x81\xF4\x87\xD6\xB9\xC0\xBF\x80\x01\x5D\x83\xED\xA6\xCD\xC2\xBD\xCA\xC0\x02\x82\xC5\xD3\xCC\xCA\xCA\xCF\xCD\x9F\x8B\xD4\xD9\xCA\xC7\xC8\xC4\xD2\x8E\xA8\xD6\xCA\xD8\xC9\x82\xCC\xD1\x9D\xA0\xF2\xD0\xD1\xD6\xD0\xC6\xD6\xA7\xAE\xE5\xD8\xD7\xDA\xDD\xD4\xDF\xAB\xC0\xED\xC2\xAB\xDA\xE1\xDC\xE2\xBF\xC8\xC1\xEA\xE3\xE7\xD6\xDB\xD1\xC6\xBD\xCC\xE7\xEE\xE4\xDC\xE9\xE9\xD2\xD5\xD1\xF7", + "\x9D\x2A\x03\x00\x2F\x3A\x00\x00\x27\x00\x01\x82\x80\x08\x0B\x82\x81\x82\x06\x89\x82\x88\x0A\x86\x06\x84\x0A\x0A\x97\x0A\x9C\x0A\x82\x12\x84\x80\x09\xAD\x0A\x92\x1A\x81\x2A\x84\x2B\x0A\xDC\x0A\x9F\x2A\x83\x32\x84\x34\x0A\x8C\x4A\x8F\x4A\x82\x4A\x84\x4B\x0A\xA1\x4A\x87\x5A\x86\x56\x84\x5C\x0A\xC5\x1E\x09\x8F\x7D\x9E\x9F\x9E\x0A\x80\x3F\x9F\x91\xA3\xA2\x9F\xA2\x46\xFF\x48\xA6\xAB\xA3\xA1\xA6\xA2\x0A\xC9\x8A\xB1\xA9\xA7\xA7\xA2\xAA\x4C\xD8\x8E\xA1\xAA\x81\x02\xAC\xA8\x3C\xD5\x9F\xB7\xA1\xB1\xAD\xB3\xAD\x67\xE0\x86\x92\xA6\xA8\xA3\xB0\xB7\x69\xE4\xAB\xA2\xB1\xB8\xBB\xB8\xB3\x77\xE8\x86\x9E\xA9\x84\xBD\xBC\xB5\x03\xEC\xAF\xB3\xA5\xBC\xC3\xBE\xB9\x81\xF4\x87\xD6\xB9\xC0\xBF\x80\x01\x5D\x83\xED\xA6\xCD\xC2\xBD\xCA\xC0\x02\x82\xC5\xD3\xCC\xCA\xCA\xCF\xCD\x9F\x8B\xD4\xD9\xCA\xC7\xC8\xC4\xD2\x8E\xA8\xD6\xCA\xD8\xC9\x82\xCC\xD1\x9D\xA0\xF2\xD0\xD1\xD6\xD0\xC6\xD6\xA7\xAE\xE5\xD8\xD7\xDA\xDD\xD4\xDF\xAB\xC0\xED\xC2\xAB\xDA\xE1\xDC\xE2\xBF\xC8\xC1\xEA\xE3\xE7\xD6\xDB\xD1\xC6\xBD\xCC\xE7\xEE\xE4\xDC\xE9\xE9\xD2\xD5\xD1\xF7", "\xEA\xE8\xEC\xEF\xE2\xDE\xB1\xF4\xD3\xDF\xE2\xF1\xF3\xDA\x02\x83\x11\xC4\xF6\xEE\xF1\xF6\xF4\xDB\xEE\xF1\xF0\xF1\xF4\xF9\xEF\xFB\xE0\x84\x2B\xE3\xFC\xFF\xF0\xF7\xF9\xFF\x75\x71\x81\x01\xFB\x7E\x7D\x7F\x7B\x01\x86\x05\x80\x82\x07\x80\x8D\x82\x80\x0F\xB8\x79\x72\x84\xCB\x54\x8D\x70\x78\x16\x94\x78\x87\x86\x13\x9C\x85\x86\x87\x17\x9D\x82\x8B\x87\x23\xA1\x84\x8B\x89\x26\xA9\x8A\x85\x89\x2B\xA8\x8D\x8A\x8A\xD9\x60\x87\x73\x01\x0B\x8E\x86\x83\x8D\x0C\xB8\x86\x8D\x8E\x3C\xBB\x8E\x8C\x84\x3A\x80\x9D\x8E\x90\x3F\x99\x81\x8C\x8B\x47\xAE\x89\x90\x8C\xDF\x48\x9D\x92\x92\x4F\x8C\x92\x7C\x91\x54\x86\x91\x97\x8B\x58\x8B\x99\x97\x75\x0C\x7D\x56\x7E\x8C\x5A\xA1\x97\x96\x98\x53\x96\x95\x98\x98\x63\xA9\x97\x9A\x93\x6B\x90\x9D\x9A\x94\x5F\xAC\x91\x9E\x9B\x73\xB0\x91\x82\x99\x75\x9B\x9F\x9A\x9E\x79\xA4\x9D\x9E\x9A\x7F\xBB\x9E\x9D\x42\x09\x35\x85\x94\x9A\x82\x80\xA7\x9C\xA2\x81\x8D\xAB\xA2\x9C\x8F\xB4\x91\xA6\x9D\x11\x8C\xA3\xA4\x9F\x97\x83\xA5\xA4\xA4\x9B\x92\xAD\xA7\x70\x0A\x06\xA8\x9D\xA6\x8A\x9F\xA8\xA6\xA9\x9A\x81\x93\xAA\x41", "\x0B\x22\xA6\xA4\xAA\xA5\xAA\xAF\xAB\x40\x0C\x2E\xAC\xA6\xAC\xB7\x83\x9B\xA8\xAE\x9E\xBC\xA4\xA6\xAF\xC7\x4D\x06\xAD\xAF\xBA\xB3\xA5\xB1\xAE\x45\x86\xB9\xB0\xB2\x00\x0E\x4E\x94\xA9\x89\x91\xBE\xA2\x41\x0F\x03\xBF\xAF\xB1\xC4\x8B\xB9\xB7\xA1\xCC\xBB\xA8\xB7\xB5\xDA\xA0\xBC\xB7\xB6\xDE\xA1\xB7\xA8\xB0\xA9\x9F\xB7\xBA\xBA\xE9\xA6\xBD\xBB\xB8\xE2\xA5\xB0\xBF\xBA\xEE\xB1\xAC\xBA\xBD\xF5\x92\xB9\x40\x04\xD6\xB4\xB3\xBF\xBB\xF2\x81\xCA\xB3\xBF\xF8\x80\x01\x05\xBF\x00\xC3\xC2\xC0\xB3\x12\x08\xC5\xC2\xBC\x13\x06\xA0\x47\xB3\xB0\xBA\xB5\xC7\xB4\xE8\x8F\xCA\xC3\xC6\xDD\x9C\xC4\xBA\xC7\xF1\xA0\xCE\xBF\xC2\x1F\xDD\xC6\xC9\xC9\x28\xE1\xC7\xCA\xCA\x29\xE3\xC2\xC9\xC2\x2B\xFE\xB5\x06\xC3\x16\xD9\xC5\xCF\xBD\x37\xF9\xB8\xC4\xCE\x3B\xFF\x86\x06\xA1\x12\x54\xC6\xCD\xCF\x04\xF9\xC5\xD0\xD1\x24\xEC\xCA\xD2\xCB\x31\xF0\xCD\xCA\xD3\x4B\xD0\xDC\xD3\xD3\x1A\xCD\xD5\xD4\xD5\x46\xC9\xDE\xBC\x42\x7B\x48\xDF\xCB\xD5\x51\xE0\xD3\xD6\xB8\x19\x34\xCE\xD6\xD5\x46\xDA\x06\xD8\xB4\x67\xD8\xDD\xD9\xD8\x59\xDF\xD1\xDC\xDA\x6F\xE3\xD6\xDE\xD4\x78", "\xE2\xD9\xDF\xDC\x6E\xEC\xDE\xDF\xC5\x7F\xC3\xD1\xE0\xCF\x09\x5B\x0B\xD8\xE0\x88\xC2\xE9\xE0\xE1\x8B\xFF\x84\x46\xD0\x8C\xCA\xE2\xE5\xE4\x02\x5D\x07\xE3\xE4\x3F\xBB\x40\xE5\x40\x1F\x17\xE4\xE6\xCE\x83\xE0\xED\xE3\xD1\xA1\xE4\xE3\xEA\xD6\x7B\xF5\xD9\xE9\xE9\xA8\xFA\xDE\xE8\xDF\x70\xEA\xEF\xEA\xEC\xB0\xF7\xD3\xED\xE9\x20\x1E\xE2\xE8\xE6\xA6\xFC\xED\xE9\xED\xAB\xE3\xE1\x0A\xA1\x16\x5B\xED\xEF\xE7\xC7\xFB\xE8\xF3\xEF\xB4\xCD\xFC\xEA\xDC\xCE\xE7\xE0\xF7\xF3\x74\xD4\xFD\xDE\xF4\xD5\xD8\xFB\xB7\x08\xBA\xC9\xFE\xF4\xF3\xD6\xF1\xE1\x80\x09\xDD\xE0\xFA\xF6\xB8\x25\x25\xF3\xF7\xF9\xB6\xC0\xF7\xEC\xFB\xC1\xFE\xEB\xFA\xFC\xD9\xF4\xF7\xF6\xFD\xE2\xF0\xFF\xF9\x90\x26\x2A\xF5\xFF\xF2\xF3\x60\x83\xFF\x4A\x74\x81\xEF\x41\x85\x80\xE6\x78\x7D\xFB\x51\x7A\x81\xF8\x42\x87\x7E\x0F\x99\x7D\x03\xFB\x71\x83\x05\xA1\x7E\x82\x0F\x58\x21\xD7\x17\x8E\x80\x04\xA0\x38\x05\xFE\x70\x82\x07\x83\x86\x80\x12\x89\x85\x82\x1D\x85\x86\x08\xAA\x82\x82\x14\x94\x83\x84\x2B\x87\x84\x0C\xAD\x83\x86\x0C\x93\x86\x7D\x38\x8C\x82\x0B\xB9\x8C\x83\x17\xAC\x87", @@ -13005,41 +13233,41 @@ namespace vl::glr::parsergen "\xFC\xF8\xF9\xE7\xD4\xE6\xFB\xE4\xB0\xF0\xF9\xD3\xE9\xF1\x00\x03\xFB\x75\xFD\xFD\x48\xF5\xFB\x93\xFE\xFD\x86\xFC\xE4\xA6\xFC\xF5\xC5\xEB\xED\xA4\xF5\xFC\xDB\xF1\xFF\xE4\x7A\xF8\x5E\x7C\xE2\x70\xFA\x62\x7C\xA0\x6A\x7C\x00\x06\xF7\x4C\x12\xE0\x7F\xFF\x42\x7B\xF7\x68\x79\x95\x7E\x00\xA7\x7A\xFA\x69\xFF\x35\x6A\xD3\x75\x80\x3A\x72\x20\x2B\x7E\xEE\x71\x00\xEF\x7C\xE7\x74\x7F\x01\x7F\xFE\x78\x7C\x0E\x8B\xFF\x18\x7F\x82\x6A\x7B\x74\x7E\x01\xB7\x7E\x05\x8B\x25\x0C\x82\x04\x86\x75\xFC\x7B\xF8\x61\x72\xFF\x7F\x1C\x53\x7F\x50\x16\x81\x3F\x09\xF9\x65\x80\xAE\x0F\x1C\x5E\x66\x99\x62\x6C\x93\x08\x07\xBE\x08\x21\x87\xCC\x4B\x73\x64\x1E\x81\xB8\x68\x08\xA9\x7F\xAD\x7E\xF1\x63\x7E\xFD\x66\x7A\x22\x83\x09\xAE\x7A\xDA\x7A\xFA\x18\x80\x8A\x73\x82\x82\x7F\xF0\x52\x83\x07\x8B\xE7\x4F\x6B\x16\x92\x7F\x91\x7E\xC8\x5F\x82\x28\x8D\x01\xA3\x80\x00\x8F\x82\x68\x83\xFE\x40\x7D\x06\x8A\xFF\x4E\x82\x1A\x8F\x70\xFD\x7D\x00\xB5\x7E\x37\x87\x00\xEE\x7C\x0B\x82\x13\x2E\x83\x0E\xB5\x82\x30\x83\x01\xEA\x76\x0C\x91\x74\x34\x86\x3A\x3C\x67\x9C\x64", "\x04\xFF\x07\xCB\x62\x0D\x82\x6C\xD5\x6E\x72\x98\x7A\x10\x2C\x76\x19\x75\x73\xBF\x7E\xBA\x43\x85\x01\x83\x03\x86\x0A\x82\x11\x7E\x3B\x83\x20\x11\x18\x2B\x8E\xE9\x6D\x7F\xFD\x68\x82\x24\x84\x0E\x9E\x84\x32\x89\x09\x87\x0B\x18\x89\x83\x7B\x85\x03\x9B\x84\x36\x8D\x04\xA9\x85\x29\x97\x7D\xAB\x78\x14\xA7\x82\x51\x87\xF7\x65\x83\xEA\x7C\x1A\x2F\x86\xE4\x5C\x83\xCB\x71\x01\xA1\x75\x42\x0B\x85\xB9\x80\xEC\x7C\x82\x18\x85\x05\xA9\x7E\x41\x12\x85\x2A\x84\x14\xB4\x84\xF0\x75\xFE\x41\x7C\x41\x07\x85\xCB\x80\x02\x83\x08\xC2\x7B\x1D\x66\x60\x30\x9A\x83\xA3\x80\x15\xBD\x82\x81\x0D\xFA\x54\x83\x31\x90\x86\xAE\x87\x0D\xBB\x70\x67\x88\x0B\xD8\x85\x2D\x9A\x86\xC4\x80\xB6\x6B\x7D\x6B\x81\x02\xCA\x85\x38\x81\x83\xAF\x79\x16\xA0\x87\x6C\x82\x0E\x9A\x83\x2D\x93\x87\xE7\x85\x1E\x8B\x7C\x72\x88\x0F\xBA\x87\xFD\x70\x7F\xA7\x7A\x20\x2C\x87\xC4\x7B\x0B\xEC\x7D\x3A\x98\x7A\xF2\x84\x13\x92\x78\x5E\x88\x10\xCE\x87\xC4\x06\x86\x03\x0D\x55\x0E\x87\x81\x86\x10\xFE\x86\x3B\x9B\x86\xB0\x86\x19\x88\x87\x36\x8F\x0E\xF4\x84\x3C\x86\x83\x01\x89\x20", "\x25\x87\x76\x88\x0E\x96\x8B\x2B\x98\x7F\x10\x8A\x20\xBD\x86\x61\x86\x0B\x9A\x8B\x4A\x9D\x7B\x2D\x89\x25\xA2\x89\x97\x8B\xF4\x6E\x7C\x48\x94\x6D\x03\x0E\x59\x32\x88\x00\x04\x11\xA1\x85\x47\x99\x87\xF0\x87\x0E\xA9\x13\x3C\x85\x0D\x8A\x0B\x46\x8D\x85\x1E\x89\x29\x87\x89\xBC\x71\x07\x9C\x78\x3F\x8A\x88\x4C\x81\x03\x82\x81\xB4\x7A\xF9\x6B\x7A\x2F\x86\x08\x3D\x8B\x16\xBF\x88\x93\x8A\x0F\x89\x82\xDE\x7B\x7C\x2E\x88\x2A\x98\x83\x90\x8E\x15\xCD\x8B\xDE\x76\x7D\xCF\x82\x2C\x85\x88\x6F\x8E\x07\x94\x84\x20\x92\x83\x45\x8F\x17\xB4\x89\x8A\x82\x0D\xCC\x8B\x1F\x8C\x77\x68\x8F\x28\x90\x7B\x8B\x80\x14\x98\x89\x59\x97\x8B\xA5\x7B\x27\xA3\x88\x82\x83\x0C\xDC\x89\x50\x9F\x8A\x56\x89\x2E\xB0\x82\xC0\x81\x08\xF9\x70\xC8\x68\x8C\x29\x80\x27\x82\x09\x5A\x1E\x0C\x94\x8F\x4E\x96\x8C\x35\x83\xC9\x42\x16\xB3\x81\x10\x65\x1A\x33\x9B\x8C\x8C\x8E\x20\x1E\x8C\x8D\x6D\xCF\x13\x0F\xC8\x64\x1F\x98\x85\x2B\x90\x85\x05\x82\x09\xAB\x7F\x6A\x8D\x81\xAD\x89\x35\xB0\x6A\xD3\x86\xDD\x37\x66\x63\x94\x75\x01\x0F\x35\xB8\x83\xD8\x8B\x13\xBA\x8F\x50\x9C", - "\x8D\x99\x8D\x9F\x45\x85\x47\x88\x18\x93\x87\x55\x99\x64\x9C\x88\x00\x06\x8F\xDB\x88\x00\xA0\x8E\x5B\x82\x6C\xA3\x89\x38\x88\x80\xA1\x84\x1B\xA8\x83\x60\x07\x84\xCF\x0F\xBD\x72\x8C\x63\x68\x1D\xD6\x0E\x60\x7D\x86\x46\x0B\x11\x88\x85\x0B\x8B\x13\xCE\x8C\x55\x9F\x7C\x03\x09\x3A\x87\x8E\x81\x06\x1E\x99\x7C\x7A\x82\x08\xEA\x8A\x31\x91\x89\xD5\x72\x11\xBB\x88\x75\x98\x7E\x8D\x89\xF6\x4A\x09\xFA\x88\x16\xFC\x8F\x7A\x93\x8A\xEE\x8C\x00\x8E\x8B\xCB\x8B\xFA\x18\x8F\x7F\x80\x00\x06\x93\x3B\x1D\x8F\xED\x02\xD8\x03\x8F\x67\x7D\x67\xE2\x89\x3B\x8A\x08\x07\x93\xF3\x1D\x82\x7F\x92\x8F\x02\x0F\x42\xBA\x8E\x13\x86\xF3\x56\x8E\x33\x97\x8F\xFD\x60\x2F\x87\x91\x04\x9B\x21\x86\x08\x89\x8E\x7D\x27\x95\x42\xBF\x81\x87\x0B\xEA\x4B\x71\x7C\x87\x81\x55\x8C\x91\x0E\x87\x17\x9D\x21\xB1\x93\xEA\x74\x91\x72\x7E\xBA\x62\x25\xE4\x82\x23\xA1\x8F\x40\x1B\x91\x3E\x92\x20\x00\x93\xE7\x8B\x11\x6B\x87\x5C\x9E\x89\x4A\x8C\x19\x81\x08\xBD\x87\x05\xEB\x8A\x56\x89\x92\x75\x8B\x26\xAA\x8B\xC2\x8C\x12\xA7\x89\x56\x89\x86\x25\x8D\x4A\x9D\x8B\x9B\x86\x01", - "\x89\x08\x93\x9D\x84\x7D\x8B\x29\x99\x88\xC1\x87\x24\xCF\x92\x98\x88\x89\x68\x8F\x4A\x9C\x88\x28\x90\x13\xA7\x88\x35\x85\x91\x03\x0F\x4B\x8B\x88\xBA\x8D\x05\x94\x80\x99\x93\x92\x7C\x8A\x49\x80\x01\x37\x9E\xFA\x6A\x90\x52\x81\x93\x86\x8E\x2F\xA0\x8E\xB2\x82\x27\xD1\x89\x93\x97\x7F\x83\x92\x32\x92\x92\x56\x8B\x17\xD9\x91\x9D\x83\x87\x3B\x8E\x4F\x8D\x95\x68\x8D\x26\xDD\x8B\x06\x99\x82\x00\x05\x50\xA3\x8B\x35\x97\x26\x97\x94\x59\x94\x90\x66\x91\x50\x80\x95\x28\x91\x0F\xCF\x88\xA3\x87\x94\x79\x94\x54\x80\x88\x45\x99\x29\xE5\x90\x96\x9D\x8A\xAB\x95\x4B\x98\x8A\x57\x9C\x29\xFA\x91\xAC\x92\x8A\x00\x07\x21\xBD\x8E\x23\x98\x27\x8E\x94\x43\x92\x7C\x18\x93\x49\xB4\x95\x3F\x9A\x27\xDC\x90\xAE\x80\x95\xAF\x93\x2B\x9A\x93\x8F\x8C\x2B\xA7\x94\x98\x85\x96\x09\x8E\x59\xB3\x92\xB6\x80\x2C\xF0\x92\x29\x9D\x95\x94\x97\x57\xA3\x92\xB4\x8A\x13\xE9\x93\xB0\x93\x94\x87\x89\x39\x91\x8C\x59\x91\x27\xDF\x94\xAA\x87\x89\x20\x91\xA7\x62\x91\x60\x99\x16\xD2\x96\xA1\x9D\x7C\xE7\x8A\x40\xA7\x8B\x03\x92\x29\xE7\x95\xB6\x94\x93\xDA\x97\x2F\x84", - "\x93\xFC\x8E\xFA\x1A\x96\x93\x89\x96\x7E\x89\x5D\x82\x6B\x75\x96\x2D\x8B\x95\x30\x95\x94\xCA\x97\x51\xB6\x8B\x7D\x90\x17\x85\x98\x4F\x86\x97\xE7\x7B\x31\x8C\x99\x01\x99\x17\x90\x9B\x63\x82\x97\xF7\x80\x5B\x89\x99\x7C\x92\x30\xFD\x68\xC1\x8F\x90\x08\x86\x72\x33\x90\xC4\x8D\x23\xE8\x8A\xC8\x9B\x89\x38\x93\xF7\x56\x6F\x92\x97\x20\xA7\x9A\xC9\x97\x91\x88\x8B\x48\x87\x91\x94\x91\x09\xEA\x78\xCB\x8C\x97\x34\x9C\x35\xB6\x98\x98\x99\x1C\xB2\x98\x73\x8E\x7F\x39\x98\x36\xBB\x99\x91\x9C\x23\xBC\x99\x90\x81\x08\x3E\x99\x98\x6E\x90\x92\x96\x34\x93\x9A\x40\x17\x99\x0E\x99\x68\xBB\x8C\xB5\x79\x34\xA3\x7A\xCB\x82\x84\xA9\x63\x39\xA6\x72\xAD\x99\x04\x8A\x0B\x27\x62\x6C\xB7\x97\x2D\x83\x09\x73\x2C\x08\x89\x08\xD9\x83\x8F\x5E\x85\x30\x1C\x9A\xB8\x6B\x36\xC6\x66\x60\x69\x27\x65\x9E\x20\x2B\x27\xB8\x93\x10\x7D\x1C\xDD\x82\x08\x76\x98\x6D\x86\x08\x0D\x22\x21\x89\x0B\x3B\x37\x9B\x01\x0F\x6F\xBA\x9B\x81\x0F\x38\x03\x9F\x88\x6A\x9B\xF8\x8E\x20\x3C\x24\xC0\x9B\x89\x6F\x71\x42\x1C\x1E\x8C\x9C\x4F\x96\x6F\x44\x26\x38\x81\x09\xFA\x0C\x9C", - "\xBA\x96\x3B\x8A\x09\x7A\x92\xD8\x56\x7D\xDF\x86\x08\x9E\x9A\x73\x89\x09\xE2\x15\x39\xCF\x46\xE3\x86\x08\xDD\x92\x74\xA8\x9D\xD3\x93\x10\x67\x20\xE3\x8E\x9D\xA5\x9C\x97\x63\x78\xD9\x96\xDD\x42\x8A\x60\x76\x9D\x2C\x94\x71\x9C\x9C\x9E\x4C\x3A\x82\x09\x39\x2C\x9C\xBF\x9D\x74\x81\x9F\xCF\x93\x10\x43\x9E\x75\x02\x03\x3C\x64\x07\x8A\x9F\x80\x04\xDE\x5E\x9A\x42\x1A\x9A\xCD\x99\x21\x3C\x60\xE8\x94\xE7\x4E\x9D\x42\x1A\x9A\xD8\x9F\x79\x8D\x85\xED\x99\x10\x0A\x67\xF4\x96\x9E\x06\x0A\x6B\x9F\x9F\x84\x07\x09\xE1\x9E\x42\x05\x9F\x03\x0A\x6B\xA8\x9E\x81\x0A\x35\xE6\x63\xF8\x87\x64\xE0\x99\x7D\x95\x9E\xE9\x9A\x3D\x89\x0A\x0E\x9A\x81\x3E\x86\x07\x82\x6D\x50\x19\x10\x1A\x90\x89\x9B\x9F\xFB\x8A\x21\x24\x91\xF6\x80\x00\x00\xA1\xFF\x82\xA0\x0A\x0E\x80\xAC\x14\x04\xA4\x28\x0A\x08\xFF\x8B\xA0\x09\x0F\x7F\x8E\xA1\x00\xA1\x41\x89\xA3\x04\xA7\xA0\x15\xA5\x81\x89\x09\x07\xA3\x1F\x99\xA2\x41\x0A\xA0\x1D\xA6\x44\x8D\x08\x0B\xAB\x41\x94\xA2\x08\xA9\x08\xA9\x99\x20\x20\xA1\x0C\x9C\x40\xAB\x9D\x31\x88\x8E\x06\x0F\x7D\x93\x87\xF9\x91\x43\xF5", - "\x9E\x9D\x90\xA1\x11\x66\x86\x83\x08\xDB\x88\x20\xA4\x61\x0B\xA3\x08\x04\xA4\x87\xA4\x90\x21\xAE\x43\x9E\xA3\x0E\xBF\xA1\x02\x0C\x88\xA0\x75\x80\x03\x44\xC8\xA1\x40\x09\xA1\x00\x02\x89\xAE\xA0\x5B\x6E\x44\xCD\x16\x42\x04\xA0\x50\xA1\x8B\xA0\x80\x34\x92\x10\x5C\x67\x40\x1E\xA2\x2A\x8D\x84\x98\xA1\x13\xA3\x2B\xE2\xA0\x04\xA4\xA3\x40\xA3\x73\x97\xA1\x33\xA4\x2B\x6A\xA2\x19\xA1\xA1\x6D\xA2\x2E\xAF\xA2\x16\xA6\x44\xE1\xA2\x41\x1C\xA0\x74\xA0\x8D\xB6\xA3\x81\x08\x47\x81\x0A\xFF\x8E\xA3\x77\xA6\x84\xB1\xA3\x32\xA1\x48\xE3\xA3\x20\xB9\x89\x80\xA4\x8F\x82\xA5\xC9\x83\x42\xF2\xA1\x21\xAC\xA3\x8C\xA0\x85\xB9\x9C\x75\x89\x10\x3C\x67\x9B\x8E\x9F\x3A\xA2\x8A\x7A\x77\x84\x08\x49\xD7\x9F\xA3\x77\xA1\x02\x0D\x93\xA6\x9E\x13\x87\x49\xF1\x9C\xFB\x91\x81\x33\xA4\x93\xA6\xA5\x80\x0A\x35\x8A\x71\x29\xB4\x9F\x9E\xA1\x21\x03\x8D\x3E\xA0\x00\x7F\xA2\x2C\xAB\xA3\x70\xA1\x92\x86\x08\x02\xA3\x4B\x8B\xA4\x13\xB3\x90\xB8\xA1\x8F\x87\xA5\x6B\x9F\x48\xB9\xA7\x2F\xB7\xA5\x73\xA6\x8F\x95\xA3\x5E\xA6\x48\xBA\xA7\x30\x41\xA6\xCA\xA5\x8E\x86\x98", - "\x81\x04\x4B\xB6\xA7\x14\xAF\xA6\xC9\xA5\x96\x95\xA2\x28\xAC\x4C\x90\xA7\x31\xB7\xA6\xF0\x88\x9A\x9A\xA6\x69\xA0\x00\x2F\x91\x35\xB5\xA2\x04\xA6\x9C\xBE\xA5\x1E\xA9\x10\x6A\xA5\x33\xBF\xA6\xE9\x8A\x9C\x96\xA7\x78\xA9\x4D\xF3\xA5\x38\xB5\xA7\x55\xA6\x9D\x9E\xA6\x76\xA2\x1A\xF2\xA7\x36\xAA\x08\xFA\xA6\x98\xBC\xA6\x44\xAD\x4E\xFE\xA4\x39\xB0\xA2\xA1\x99\x20\x27\xA6\x72\xA9\x50\x80\x03\x42\xBA\xA3\x01\x0C\x80\x8D\xA9\x87\xA3\x4C\x81\x0B\x44\xAB\xA7\x24\x97\xA2\xAF\xA7\x81\xA2\x10\x1A\xAB\x3E\xB9\xA8\x06\xA8\xA2\x80\x00\x8F\xA2\x50\xA0\xA8\x3E\xA7\xA8\x0A\x0C\xA4\x82\xA6\x67\xA2\x10\x08\xA9\x48\xB5\xA8\x56\xA4\x9C\x83\xA1\x2A\xA4\x22\xB5\xA8\x4D\xBF\xA7\x28\xA9\xA7\x86\x09\x10\x77\x38\xBB\xA6\x86\x7D\xA9\x20\x77\xA7\x81\x08\x9E\xA3\x54\xC2\xA9\x4C\xBB\xA9\x8D\xA0\xA9\x92\xA5\x8D\xA4\x22\xF6\xA5\x44\xB8\xA8\x50\xAC\xA9\x91\xAB\x8F\xA3\x55\xA5\xA9\x52\xB6\xAA\x4B\xAC\xAA\x99\xAA\xC2\x95\x45\x85\x9C\x4C\xA4\xA0\x5E\xAC\xA5\x81\x09\xB0\xA0\x4F\x82\x08\x59\xBC\xA8\x63\xAD\xAB\xAA\xAA\x72\xA7\x56\xA4\x90\x14\xAD\xAB\x57", - "\xAE\xAC\xB8\xA9\x62\xAB\x52\xE5\xAA\x42\xB5\xAA\xEC\x8F\xA5\xA2\xAA\x87\xA8\x57\xF7\xAA\x54\xA7\xA9\x22\xAC\xA2\xBB\xAA\xC1\xA6\x57\xFC\xAB\x5F\xA0\xA7\x7E\xAA\xAB\x88\xAC\xC3\xAA\x58\x84\xAA\x41\x17\x9A\x01\x08\xB2\x80\x00\x45\x74\x58\xE8\xA9\xA9\x94\xAB\xD1\xA2\xA4\xA3\x66\x45\xA7\x58\x9B\x74\x60\xBF\xAA\xF9\x6A\xAF\x85\xAC\x02\xAB\x59\xD4\xA5\x5F\xA0\x00\x04\xA4\xB2\xA7\xAC\xD8\x75\x59\xA4\x91\x69\xA9\xAC\x58\xAA\xD0\x58\xAD\x71\xA2\x52\xAC\xAF\x69\xAF\xAD\x8C\xA9\xB6\x9E\xAD\xD9\xAE\x54\x97\xAC\x67\xAD\xAC\xE2\x62\xB4\x96\xAC\xDC\xAD\x5A\xA2\x74\x6F\xB5\xA2\xB6\xAD\xB3\x94\x74\xE1\xA4\x22\xC9\xAC\x70\xA1\x08\xC4\xAF\xB4\xAA\xAC\xE5\xAB\x0F\xC7\xAC\x39\xB1\xAE\xD4\xAB\xB2\x8C\xAF\xB8\xA5\x5D\xBF\xAE\x6E\xAD\xA9\xD1\x63\xBB\x9B\xAB\xE5\xAF\x59\xFB\xA8\x14\xAE\xAE\xDF\xAF\x89\xA1\xAF\xF2\xA5\x58\xD0\xA3\x74\xAF\xAE\x47\xA8\xC8\x62\xAF\xC5\xA8\x5D\xF0\xAC\x14\xB9\x7A\xA4\x9B\x20\x10\x9C\x83\x0B\x5F\x83\x08\x6A\x86\x08\x97\x9C\xBF\x8A\x09\xFF\xA3\x10\x01\xB1\xDD\x97\x08\x92\x76\x20\x38\x79\x86\x9C\xDE\x2D\x9E", - "\x42\x14\x9C\x05\xB2\x21\x06\xB1\xA7\x9A\x10\x11\x25\x42\x1D\x24\x17\xB2\x21\x09\x9B\x52\x26\x10\x1C\xB3\x8F\x83\xB0\x12\xB0\xC4\x89\x09\x09\xB1\x10\x5A\x7D\x84\xA9\x08\x26\xB2\x20\x24\xB1\x50\x2A\x10\x0B\x9E\x41\x1E\x70\x02\x08\xC6\x81\x08\x02\xBA\x62\xA5\x71\x42\x14\xB1\x96\x9A\x21\x19\x69\xDD\xAE\x5D\xF5\xAA\x65\xBB\xB1\xF6\x84\xBD\xBF\xB1\xF5\xA6\x5D\xA2\xA8\x90\xB7\x73\xF3\xA9\x8D\x89\x09\x23\xBE\x5B\xA6\xAD\x76\xA4\xA0\x4C\xB5\xBE\xA9\xAE\xD4\xAA\x63\xC6\xAD\x8F\xB9\xAC\x30\xAC\xC9\xA8\xAE\x1F\xB4\x22\xD1\xB1\x92\xA2\x08\x4C\xB7\xBD\x93\xB2\x2D\xBF\x65\x91\x68\x91\xB7\xB2\xB4\xA9\xCB\x96\xB2\x27\xB0\x5F\xE4\xB2\x90\xBD\xB2\x67\xB4\xCD\xA3\xB3\x38\xB0\x5B\xDC\xB1\x95\xA9\x9B\x45\xB2\xCD\x85\x6D\x32\xB0\x00\x4C\xB2\x9F\xAB\xB3\x75\xB0\xCB\xBB\xAA\x37\xB9\x67\x83\xB4\x9D\xB9\xAD\x76\xB3\xC9\x80\xB4\x44\xB2\x68\x85\xAC\xA1\xA8\xB3\xBD\xAE\xCB\xAF\xB3\x3B\xB8\xD1\x0B\xB5\x71\xA3\xAF\x66\xB0\xCF\x90\xB5\xB9\xA3\x10\x12\xB5\xA1\xAD\xAF\x94\xB4\xC7\xB2\xB3\x44\xBB\x58\x8F\xB7\xA8\xAD\xB4\x96\xA8\x8A\x9E\xB5\x4D", - "\xBA\x53\x9D\xB6\xA5\xA7\xAD\xAA\xB1\xB4\x93\xB4\x4C\xBD\x67\x87\xB7\xA5\xAB\xAC\xC6\x99\x20\x39\xB4\x00\x07\x36\xC5\x9E\x42\x10\x9B\x06\x08\xD8\x83\x08\x61\xB2\x10\x73\x9A\xDC\x8A\x08\xC6\xB3\x20\x02\x9C\x65\xBA\x10\x4B\xB6\x40\x12\x27\xCB\x99\x20\x09\x9F\x68\xB1\x10\x54\x07\x72\x89\x46\x3C\x63\x7D\xBC\x80\x1E\x65\x0D\x57\xB4\x0D\xA8\x61\xD4\xB4\x15\x74\x0F\x64\x43\x10\xC1\x08\x0F\x76\x06\xDE\xB4\xDA\x84\xA0\x73\xBA\x10\x57\x05\xBA\xB1\xB6\x1A\x91\xDC\x80\x00\x6C\x0F\x6E\x83\x09\x32\x50\x78\xF2\xB1\x1B\x35\xB7\x53\xAC\xDF\x72\xB6\x42\x1A\x06\xFB\xB4\x95\x97\x6A\x7F\xB9\x10\x5B\x05\xC0\xB6\xAC\x79\x9C\xE0\x81\x08\x6E\x07\x70\x9A\x90\x72\x34\xB6\x9F\x61\x28\x34\xA5\xE0\x20\x71\x8A\x09\x37\x07\xB8\x82\x6E\xB0\x15\xB9\x84\x0E\x0D\x07\xBA\xB6\xA0\x00\x58\x2C\xDA\x96\x69\xE4\x0E\x03\xDA\x2A\xC8\xB4\x0F\x3C\x60\x76\x8A\xB8\x00\x0F\x0D\x07\xB8\x2D\xAB\xB0\x2B\xB8\x1C\x07\xB8\xAD\x9E\x6C\x84\xB9\x38\x13\xB9\xCD\xB3\xE5\x82\x08\x71\x07\x70\xA4\x91\xB2\xAA\xB8\xE3\x06\xE3\x8A\x08\x7A\x27\x72\x89\x12\x42\x19\x27\x45\xBA", - "\x16\x4A\x09\x7E\x2A\x73\x80\x00\x39\x07\xB8\x3A\x85\xA3\x0D\xBB\x72\x0D\x73\x8A\x0A\x4D\x2D\xBA\xE6\x05\xEA\x89\x08\xAA\x2D\x74\xE7\x06\xD6\xA6\x08\x63\x2B\xE3\x86\x08\x74\x08\x71\x8A\x09\x5D\x2D\xBA\xE9\x06\xE5\x8A\x08\xD2\x2D\x74\xEA\x07\xC1\xA4\xA0\xEF\x29\xE9\x81\x12\x12\x96\x6A\x4D\xBB\x3A\x1F\xBA\x03\x0B\xD5\x0D\xBA\x76\x08\x77\x82\x0A\xAB\x2D\xBA\xED\x07\xE0\x90\x79\x0C\x3D\x74\xEE\x06\xE0\xAA\x08\x25\x35\xE9\xAF\x07\x83\xB9\x39\x81\x0B\x89\x2D\xBA\xF0\x07\xE0\x83\x89\x94\x32\x77\xC3\x10\x18\xA1\x08\x05\x3D\xF2\xBF\x10\x1E\xAC\x62\x4D\xB9\x3C\x07\xB8\x3C\xA1\xC6\x0D\xBA\x79\x07\x70\xD0\xA3\x99\x2D\xBA\xF3\x05\xF4\x8A\x09\xD3\xBA\x73\xF4\x06\xEA\xA9\x08\x9E\x35\xE9\xB5\x07\xD7\xB6\x10\x31\xBE\xCE\xB6\x07\xB4\xBB\x20\x0A\x37\xA6\xB7\x0F\x39\xBE\x40\x1B\xBD\x3A\xB8\x1F\x20\xBC\x85\x06\x6F\x4D\xB9\x3E\x03\xBE\x09\x0A\xDF\x0D\xBA\x7D\x07\x70\x88\x7F\xBF\x2D\xBA\xFB\x07\xF0\x89\x08\xB1\x3D\x74\xDD\x0C\xE2\x63\x38\x4D\xBC\x1F\x12\xBC\x85\x0F\x71\x1A\xBC\x95\x10\x78\x49\x3D\xE9\xBD\x06\xC6\xBA\x10\x60\x39\xD3", - "\xBE\x07\x07\xBF\x4D\xB6\x3B\xEA\xB7\x70\xBC\x67\xE0\x2D\xBA\x00\x02\x8F\x49\x46\x45\x61\x78\x5E\xBD\x77\x0E\xBF\xF0\xB9\x00\x32\xBF\x4F\xA3\x10\x06\x3D\xD3\xA2\x00\xFB\xBD\x92\x8A\x08\xFF\xBA\x73\x83\x01\x00\xC6\x08\xC0\x03\x41\xBA\x81\xEE\x02\x6F\xA3\xBB\xB6\x01\x0A\xBE\x8D\x01\xF0\x27\xA0\x0D\x36\xCB\x0C\x04\xC6\x14\x3C\x61\x02\xDF\xB6\x81\x0B\x80\xE0\x0D\x50\x0A\x64\x0E\xC3\x38\x01\x0B\xE8\x90\x3F\x81\x11\x50\x1F\xB8\x21\xC7\x38\x11\x91\x50\xA9\x49\xBF\x11\x50\x1A\x81\xC9\x46\x07\x84\x8E\xE3\x1C\xC3\x29\xC2\x74\x12\xB8\xF0\x24\x7A\xA6\xC1\x75\xA6\x83\x85\x18\x08\xD4\x0F\x41\x0C\x44\xBD\xC1\x29\x1F\x71\xAC\x76\xBC\xAC\x22\xF7\x98\x08\xD7\xA3\x16\xC4\x25\x32\xA0\x07\xDB\xC0\x2E\xC3\x8B\x95\xC1\xE1\x0A\x03\xDA\x99\x15\xCA\xC2\xE8\x79\x96\xBD\xA6\x55\xAB\x51\xDA\x9A\x0F\x9D\xC0\xC9\x09\x28\x04\xAA\x00\x0A\x81\xAF\xA1\x27\x46\x8A\x50\xC4\x4A\x01\x0A\xC9\xA5\x86\xD4\xA2\xF1\x1E\x81\x53\xC7\x38\x01\x0A\xD8\x72\xFB\x69\xC0\xC4\x69\x46\xB4\xA0\x0C\xD6\xC0\x85\x0D\x5F\xE7\xC1\x80\x17\xBC\x8D\x99\x9B\xAD\xC3\xE5\x98", - "\x63\x81\xC7\x83\x03\x88\x78\xC4\x09\xCC\xC1\x10\xB6\x3C\x09\xB8\x0B\xC9\x08\x8D\xBE\x10\xC2\xA8\xC1\x6B\x88\xD6\x61\xDF\x21\x12\xBD\xAD\x12\xCA\xB0\x26\xC0\x61\xFE\xC3\x83\x04\x91\xB4\xA2\x13\xCE\x28\x02\xA4\x89\x9E\xC2\x42\x10\x9A\x43\xC4\x3E\x04\xA1\x14\x91\x86\x95\xB0\x13\xC9\xB1\xCC\x9C\x3E\x10\xA2\x3D\xC2\x82\xAD\xB3\x2A\xB4\x12\x88\x7E\x8C\x50\xA3\x41\xCA\x3C\xBB\xB5\xC4\xA8\xA5\x8F\xC3\xB1\xB1\xC3\x1B\xC8\x6C\xB7\xC4\xD1\xA5\xC1\x5B\xC0\x19\xC7\xA2\xFB\x98\x85\x86\x08\xD2\xAA\xC6\x43\x13\x0C\xC7\x74\x68\xC1\x85\x89\x08\xD3\xB4\xC6\x54\x14\x0D\xC5\xA3\x51\xAF\x20\x41\x0A\xD4\xB8\xC6\x27\x2C\x0B\xD3\x7A\x6C\xC0\xF1\x12\x9D\x2B\xC9\x08\x43\x2F\x12\xC3\x12\x88\x70\x88\xA2\xC7\x54\x2C\xC2\x5C\x2A\x1D\xC1\x08\x40\xCC\x43\xEE\xC5\x5F\x23\x88\xE6\xC3\x0F\xC9\x09\xAF\x22\x8F\xD4\x13\x40\x8D\xC7\xA6\xC1\x21\x21\x2A\x2D\xC3\x10\x6A\x29\x3F\xD1\xC4\xB4\xC2\x0E\xCA\x08\xB6\x24\x90\xC3\x11\xD6\x7C\x61\x91\xC4\x17\xFC\x80\xC5\x2D\x90\xBF\x11\x21\xD0\xC8\x8A\xC1\x20\xC6\x08\x8A\xBC\x8D\x83\x0A\x72\x38\xC6\x7C\x99\x3D", - "\x3C\xBE\x6E\x8D\x8C\x83\x08\x74\x22\xC7\xBC\x1A\xC1\x52\x9B\xEB\x01\x14\x55\x2F\x06\x23\x1D\x0A\x73\x0C\xF6\xC6\x00\x07\x5D\x46\x1D\x76\x28\xC9\x43\x17\x45\x8D\xA9\x99\xCD\x1D\x72\x2C\x4E\xDF\x11\x0D\xA8\x59\xB5\xC5\x84\x07\x60\x30\xA7\xE8\x03\xC3\x42\xCA\x21\xC9\x08\xC2\xB5\x43\xA5\x1F\x59\xB2\x79\xE7\xC3\xA2\x0A\x74\xDC\xAC\x93\xCF\x22\xA2\x6B\xC9\xF2\xB3\xC4\x3D\xC6\xF1\x69\x8C\x0A\x76\x4C\xDA\xC8\x03\x09\xF1\xAF\xC9\x81\x0F\x78\xD8\xC5\x83\xBE\xC4\xF2\xAD\xA0\xBB\xC1\x84\x0D\x79\xE3\xCB\x90\x0A\xB9\x68\xC9\xC8\x8A\xAB\x6E\xCA\x10\x2E\x32\xF1\x02\xBD\xD8\xC5\x13\xF1\xC5\x84\x08\x5B\x92\xAD\x55\xC4\x21\x59\x7E\x53\x83\xCB\x89\x29\xF5\x54\xC8\x58\xC8\x28\xF9\xAA\x20\x05\xC5\xBF\xCB\x42\x05\xC5\x59\x2B\xCB\x06\x0D\xC6\x15\xC8\x2A\x10\x35\xDA\x99\x21\xCB\xCC\x87\xC9\x20\x16\x33\xC9\xCD\x1D\x1E\xB2\x40\x0A\x64\x85\xC1\x1C\xF4\xCB\x84\x0E\x67\x1C\xCC\x78\x1B\xB5\x96\xC9\xD4\x83\x13\xA0\x0A\x69\x26\xCD\x72\x15\xB9\xCA\x8A\xC4\x86\x09\x7D\x20\x99\x83\x0B\xDF\xBD\xC8\x43\x17\x19\xF2\x9F\x1B\xB6\x8B\xB5\xCF\xEF\xB9", - "\xC8\xC9\x0F\x1B\xFB\xCC\x83\x05\x88\xD0\xB7\x68\xC6\x08\xD3\x30\x37\xFF\x11\x74\xCA\x9C\x80\x01\x21\xD5\x70\xC7\xCB\x20\x1E\x36\xD7\xCB\x1C\x26\xB9\x73\xC5\xC4\x18\xB1\x3A\xC2\x08\x76\x33\x99\xCA\xBC\x36\xC1\xBB\x06\x08\x34\xDA\xB1\x92\xC2\x10\x4F\xBD\x73\xC7\x38\xD8\xC7\xEC\xA1\xCE\xD9\xC3\x10\x16\xB2\x76\xC1\x08\x0F\x3B\x32\xEF\x38\x6C\xCC\x76\xEB\xCF\x88\xBC\xC3\xE4\xCD\xAF\x0E\xC5\x1C\xBE\x9B\xFD\x29\x48\xC1\x08\x09\xCC\x18\xC9\x09\x9F\x3D\x3D\xF4\x0F\xC3\xAD\xCE\xFF\xCC\x0C\xF9\xCE\x00\x04\x76\x76\xCF\x83\x12\x2E\x93\xC9\x41\xC3\xC6\x96\xCA\x10\x70\x39\x81\xC9\x08\x7C\x38\x1B\xF1\xBB\xE6\xC0\x73\xAE\x67\x82\xD5\xBF\x6E\xCD\x80\x22\x6E\xCF\x69\x99\x80\x03\xFB\xA1\xD1\xDE\x1F\x2C\xC1\x09\xC7\xCF\x9E\x80\x00\x01\xD8\xA1\x43\x13\xC1\x3F\xC8\x00\x0A\xA2\xCE\xCF\x82\xCA\x3C\x33\xD5\x3B\x0C\xCB\x1C\xA9\x10\x35\xD2\x68\xC1\x12\x41\x0E\xF1\x39\xD0\xF0\x0A\x95\xE6\xCA\x6A\xD5\xC6\x06\x0D\xF3\x03\xD3\xE4\x05\x96\xB0\xD1\x40\x15\xD1\xB4\xCD\x45\xE1\x3D\x25\xDB\x1C\x6D\xCA\x93\xD4\xD1\x81\x88\x48\xF9\x23\x1A\xDE\x62", - "\xDA\xD1\x42\x05\x3D\x54\xD3\x38\x38\xCB\x2B\xD5\xA3\xC6\xCE\x97\xC6\x08\xAA\x39\x4C\xC7\x0E\xC9\xC6\xA4\x89\x08\x74\xC7\xD3\x03\x0E\xF5\x2A\xD2\xE9\x06\x64\x33\xD1\x8D\xD9\xCE\x70\xD2\x20\x32\x3D\x19\xD6\x7B\x33\xD3\x66\xCD\xCA\x06\x0D\x46\xD5\x9B\x12\xD1\x7C\x33\xD3\xF3\x33\xD1\x76\x36\x28\xC3\x09\x1A\xDE\x9E\xF9\xD1\xB5\xA9\xC3\xD8\x3B\x46\xD1\x34\x45\xD2\x10\x70\xCB\x93\xCB\xD0\x4C\x22\x2F\xC0\x00\x3C\xDB\x9A\xF4\x0C\xF7\x33\xD3\xD7\x0A\x53\xC3\xD5\xA8\xC1\x24\x60\x3C\xA8\xC1\x0A\x9A\xD5\x51\xDD\xD5\x00\x1F\x7E\x27\xD6\x2B\xC9\x08\x50\x9B\x26\xF3\x3E\x57\xD1\x20\x1C\xD5\x40\x11\xD5\x25\xD7\xFE\x34\xD5\x07\x19\x34\xB8\xD4\xA9\xDB\xB9\x69\xC2\x5E\x1E\xCD\x15\xDB\xA0\x80\x41\x3F\xDD\xCC\xEC\xCB\x55\xC6\x08\x01\x4D\x8F\xB6\xBE\xBD\xA5\x92\x09\x0F\x47\xCA\xD7\x81\x04\x80\x47\xD4\x78\x03\xD6\xB5\xB5\x3F\xC0\x00\x03\x46\xAD\xC9\x0C\xB6\xD1\xD2\x8E\xD0\x00\x08\x41\x6E\xDB\x1C\x58\xD5\x97\xD3\xD6\x02\x0F\x02\x64\xD7\xE1\x08\xAD\xE6\xD0\xBA\xC1\x08\x1B\x43\x5D\xC7\x0E\x6C\xDF\xA6\xEF\xD4\x00\x1D\x40\xF2\xD2\x3A\x18", - "\xD6\x5B\xDA\x86\x8A\x09\x0A\x46\x1E\x2B\x43\x46\xF5\xBA\x14\xD8\xAD\xA3\xD6\x3E\xC6\x08\x2F\x46\x78\x31\x41\x19\xDA\x77\x84\xDB\xAB\xCD\xD1\x36\x46\x78\x38\x41\x19\xD7\x9B\xCF\xD5\x42\x07\xD7\x01\x0A\xC6\xBD\xD7\x00\x1C\x83\x3B\xD5\x87\x79\x7E\x0B\xD0\x09\x79\xD7\xEB\x0C\x64\xBD\xB6\xBD\xCC\x22\x4C\xB0\x2B\xE1\xB7\x2B\x4D\x8F\xB3\x36\xF1\x0C\xB2\x5F\xCF\x57\xC1\x09\x2C\x46\x3C\x65\x43\x8C\xD7\x35\xC6\x1B\xD7\xAA\xD8\x6A\xBE\x87\x7D\xC4\xAF\x39\xD9\x46\xAB\x26\xCE\x44\xE3\x10\x89\x33\xD0\xF0\xB6\xD8\x06\x0E\x64\xC4\xD6\x6D\xD2\x89\x82\xB9\x80\x0C\x36\xCD\xCA\x69\xF6\xD0\x6D\xDF\x8A\x54\xCF\x70\x17\x36\x17\xD1\x69\xF9\x09\x05\xD8\x00\x2B\x47\x84\xC1\x0A\xE2\x33\x32\xD2\xDA\x26\xB3\x93\x8C\x02\xD7\xD4\x0F\xC5\xB9\x6A\xCA\x08\x70\xD6\xAF\xBD\x46\xD5\xC7\x0E\xE6\xCB\x38\xE3\x9B\xDE\xCD\xA2\x94\x03\xD9\xC1\x10\xE8\xCA\x6E\xC2\x08\xA9\xDE\xAE\xC8\xD3\x30\x57\xDB\x0F\x15\xFB\xAA\xDA\x37\xDB\xA0\xCB\x47\xDB\xD2\x0E\x04\xD3\x70\xC6\x08\x7E\xD3\x93\xA0\x00\xE0\xDE\xAF\xAB\x46\x8C\x54\xBE\x07\xD3\xB7\x89\x0A\xC1\xC3\xCC", - "\x75\x9F\x71\xF8\x6B\xC8\xDA\x10\x6E\x39\xD6\xD5\xDC\x06\x0A\x55\xFE\xDB\x4A\xDA\xB9\x81\x09\x4F\x53\xD1\x7A\x3F\x73\xC2\x08\x62\xB5\x62\x8B\xD1\x53\x43\xD9\x41\x0F\xE7\x81\x08\xD6\xDB\xB1\x93\x28\x6C\xDB\xB5\x8C\xCB\x88\x30\xCC\xA9\xD9\xBB\xF3\x21\xDF\xD3\xDA\x2D\xD2\x5E\x2F\xD1\xB8\xC1\x10\x47\xC6\x54\x4B\xD0\x53\x4C\x52\xC5\x21\x7A\xD3\x63\x98\xD7\xC0\x08\x3C\xC6\x1A\x37\xC2\x08\x58\xC5\xBB\x9D\xB7\xF1\x4F\x17\x6C\xD8\x40\xCB\xD1\xBF\x4A\xBA\xBF\x10\x8E\xD4\xDC\x02\x09\x7B\xCA\xD0\x6D\xD9\x9A\x5D\xDC\x95\x1F\x3C\xE6\xDA\x7C\xDF\xDB\x70\xBA\x9C\x66\xDC\x7C\x53\xD1\x69\xD0\x7C\xC1\x09\x6B\xC3\x10\x23\x2A\xB6\xC1\x4E\x0A\x08\xA2\x37\xDF\x27\x2A\xBF\x86\x09\x80\xD4\xD0\x09\x0A\x3F\x66\xDF\xEE\x04\x7B\x66\xDD\xFF\xD7\xD2\x33\xCD\x43\x43\xE0\xF0\x07\xA8\xF2\xDF\x43\x20\xCE\x07\xDB\x20\x03\x52\xF3\xD6\xA7\x33\xD2\xF6\x26\xDF\xC2\xCA\x20\x36\xDF\xE0\xDF\x44\x19\xE1\x40\x07\xE0\x27\xDF\x89\x1B\xE1\xE3\xDA\xAD\x89\x54\xEC\xDB\xDA\x09\x0C\x45\xE1\xD7\x4B\x57\xB8\xD7\x0D\xAB\xCD\xCE\xD2\xD5\x79\xDA\xD7\x58\x5D\xC2\xC1", - "\x0A\xAE\xCE\xE0\x31\xE0\x00\x39\xE1\x99\xCA\xAC\x35\xE2\x42\x0C\xD6\x30\xE7\x48\xD5\xDE\x81\x0F\xAD\x3E\xE1\x42\x0A\xD7\x41\xE1\x21\x22\xDF\x99\xC4\xAF\x46\xE2\x41\x01\xD8\x49\xE2\x71\x8B\xD0\x89\x5E\xC4\x83\x08\x0D\x53\xCC\x39\xE7\x77\xF3\xC9\x93\x55\xC5\x82\x09\xC7\xD1\xE2\x03\x0C\x79\xC3\xE3\x80\x09\xB4\x5D\xE3\xCC\xCC\xC2\x39\xE4\x71\xE5\xD1\xAE\x53\x99\xF3\x5B\x8C\xC3\xDA\x38\xE3\x3C\xDA\xD6\xC1\x53\x99\x94\x5F\x8C\xC2\x00\xBA\x59\x5A\xCF\xD9\x70\xD3\xBA\x13\xCC\x23\x1C\xDC\xF6\x99\x8F\xC6\x09\xAB\xB6\x10\x56\x2B\xFE\xC4\x21\x84\xE3\x20\x0C\xCF\x70\xDC\x44\x0B\xE6\x40\x0A\xE1\xF6\xD6\x11\x25\xDC\x2A\x16\xB6\x93\xCE\x23\xF2\xE1\x2D\xD2\x12\x13\xE5\xEE\x0E\xB6\x8E\xE3\x25\xFA\xE1\x0B\xD6\x76\x66\xE2\xD6\x73\xC9\x9F\xE4\xD9\xC5\xD1\x9A\x03\x93\xE0\x0F\x0C\x05\xCA\xEB\xDB\x82\xDC\x5D\xA3\xE5\x03\x2D\xE5\x8B\xDB\xA0\xA2\x06\x2A\xE9\x0E\x21\x03\x96\xC6\x08\x2D\xE5\xA2\xA6\x07\x2D\xEB\x0E\xE2\x46\x92\xD4\x71\x05\xDA\x0A\x3F\xE7\x70\x0B\x48\xC2\xE1\xC3\x9A\xD6\xE6\x53\x99\xDC\x5F\x8C\xC3\x49\xE6\xDF\x93\xD7\xDC", - "\xA5\xC6\x10\x64\x5F\x64\xD7\x5F\x33\xD7\x75\xDE\xE5\x3D\xE6\xAF\xFB\x5F\x64\xC7\x60\x33\xD7\x2E\x6E\xDE\x85\x06\xC8\x9C\xE0\x09\x25\xE7\x24\xE5\x45\xC9\xC1\x13\xE1\xC0\xA0\xDA\xB6\xC1\x06\xD7\xDD\x60\x16\xCF\x74\xE1\xAE\xC4\x07\x82\x53\xE7\x02\x09\x1E\xE6\xE7\x15\x2A\xCF\x83\x08\x3F\xDB\xE7\xC3\x0D\x18\x00\xE5\x07\x1F\xCF\xF4\xE6\xBD\xC7\x06\x0B\x53\x20\xC6\x08\xEA\xD3\x93\xC8\x07\x82\x40\xCF\x03\x0A\xA1\xCC\xE5\x27\x20\xC9\xCB\xD9\x8B\xC9\x06\xC6\xE7\x38\x19\x4D\xC9\xC5\xD1\xC0\xDD\xB8\xCD\x06\x19\xEA\x3A\x34\x4C\xF3\xDD\xD1\xBB\xE1\x89\xD1\x06\x21\xEF\x3A\x18\x4E\x8E\xE2\xC4\xB3\xC9\x35\x09\xE9\x41\x0B\x3E\x6C\xE8\x25\xEB\xA0\xD9\x04\x4C\xEA\x08\x0F\x53\xA6\xD2\xE2\x6D\xDD\x0D\x37\xE9\x42\x09\x51\x3A\xEB\x20\x3C\xE4\x99\xD0\x00\x61\x06\x4F\xEC\x52\x93\xE5\xA3\xE2\xE3\x99\xC5\x0E\x47\xEB\x40\x15\xE0\xCD\xCD\xA3\xEA\xE2\xA2\xE9\x0E\x13\xE5\x3B\x03\xE8\x03\x09\x53\x64\xE8\x39\xED\xA2\xEF\x07\x24\xF3\x07\x58\xEA\x20\x00\x57\xAD\xE0\x49\x0B\xD1\x3D\x13\xE4\xF9\x01\xAC\xC1\x09\x6C\x56\xBE\xE8\x2A\x41\x1D\xE8\x33", - "\xCB\x1F\x2A\xEA\x2A\x1D\xC4\xA8\xD2\x5B\xFE\xAF\x0B\xD5\x1F\x33\xEB\xEE\x0D\xAF\x33\xD3\x5D\xE2\x08\x26\xEC\xA8\xC6\x84\x8F\xD2\x10\x04\x5A\xF1\x1F\xEB\x99\xB5\x45\xC1\x00\x30\x62\x91\x80\x00\x15\xF6\xEB\xAE\xE2\x5B\xC3\x00\xC6\xE4\x1F\x14\x5B\x61\xF4\xDB\xE1\xD5\x00\x14\xED\x00\x17\xB1\x17\xED\x42\x03\xEA\x11\xE4\x03\xDB\xED\x07\x11\xB2\x1E\xEE\x41\x0B\xEA\x25\xD1\x01\x23\xED\x20\x1C\xC5\x90\xEE\x32\xED\xD1\x0B\x03\xB5\xEC\x8E\xD9\xE1\x10\x31\x5A\x5F\xFC\xEA\xE1\xD7\x01\x34\xEC\x83\x1B\xDB\xC4\x5B\x6D\xE5\xEB\xDA\xD3\x02\x3B\xED\x0A\x0B\xDB\xCE\x5B\x8C\xCC\xC8\x6F\xEB\x41\xD7\x00\x30\x69\x8A\x89\x0B\xD4\x46\x1E\xC8\xE8\xAF\xDA\xD6\x0C\x0C\xDC\xF4\x0C\x1B\xF8\xC6\xD1\xE8\xB0\xCB\xD1\x0C\x05\xDD\x81\x13\xDA\x50\xEE\x2D\xED\x44\xDA\x01\xEE\xEF\x20\x6D\x58\x78\xF4\xE9\xDA\xD3\x03\x24\xEF\x20\x1E\xC6\xA8\xD1\x76\xE1\x08\x18\xDB\x8C\xC0\x00\x0E\x0B\xDE\xC3\x10\xDF\x47\xEF\xBB\xE3\x41\xDD\x01\xFA\xEF\x23\x74\xE2\x7B\xE3\xE6\xDA\xD6\x03\x3C\xEE\x2A\x1A\xB8\x78\xEF\x40\x13\xEA\xA1\xEC\x73\x03\xF0\x10\x0B\xDB\x90\x5F", - "\x71\xF8\xED\xF6\xD2\x04\x03\xF1\x11\x0B\xDB\xF6\xE0\x76\xFC\xE6\xA3\xDE\x72\x83\xF0\x13\x0B\xDB\xFD\xE1\x7A\xCA\x08\x06\xCD\x45\xE8\x01\x01\xF2\x2F\x6A\xCF\x40\x0F\xEF\xF2\xE9\x05\x20\x62\xAD\x9D\x02\x24\xF0\x78\x1A\xB8\x06\x09\xC4\xE1\xD6\x17\x0E\xE2\xCC\x14\x8C\xE7\xF1\x0B\xD7\x05\x2B\xF1\xEC\x75\xE3\xCB\x0C\x62\x29\xEE\xDA\xD4\x06\x20\x63\x5F\xC9\x10\x2B\x5F\x8C\xDF\xF1\xD2\xED\x45\xF7\x01\x21\xF4\x1F\x7F\xE2\xF2\xC0\x00\x48\xF2\xBB\xDA\xD6\x1D\x0C\xE4\x81\x13\x23\x13\xEB\x51\xF1\xB1\xE1\xD7\x1E\x05\xE5\x8F\x11\x24\x18\xF2\x91\xED\x45\xC0\x03\x2E\xF1\x24\x34\x5F\x91\xF8\xEC\xF6\xD3\x08\x24\xF3\x21\x15\x09\x60\xF3\x67\xEB\xD0\x46\x03\xCD\xFF\x11\x4B\x0E\xE6\xA7\xEF\x82\xC9\x02\x72\xF4\x4A\x39\x5D\x33\xFF\xDA\xE1\xD4\x13\x19\xF3\x4F\x03\xB7\xDB\x04\x67\x49\xE5\xAC\xB2\xB6\xD1\x02\x79\xF4\x0A\x3B\xEC\x58\xE0\xA8\x83\x09\xA1\xE2\xDD\xF2\xEE\x0A\x39\xF3\x2C\x0B\xDB\xBE\x5F\x93\xF7\x2C\x29\xE3\x41\xDB\x03\xDD\xED\x1D\x40\x5F\x8C\xD8\xF4\xC4\xCB\x41\xDD\x02\x4E\xF0\x1E\x3E\xE7\xA5\xE8\xE1\x2D\xD7\x0B\x24\xF5\xE4", - "\x09\x0A\x73\xE8\xA8\xEE\xB5\xDA\xD1\x0C\x2B\xF5\xE5\x06\xBC\x1F\xF5\x98\xE1\xD7\x63\x03\xD6\xC3\x0F\x56\x0E\xEA\xE8\xF1\x86\xE0\x00\x65\x02\xD7\xC7\x0E\xE7\x56\xEB\xEF\xF2\xB6\xC7\x03\xC2\xF2\x3A\x1A\x5F\x62\xF6\xE7\xDA\xD5\x1A\x09\xF6\xD7\x0E\x7B\x4C\xF7\x03\xFB\xA0\xEB\x03\x6E\xED\x03\xBB\xED\x7D\x67\xF4\xCB\xDB\xA0\xEF\x03\x6E\xF1\x03\xBB\xE8\x9B\xCD\xF4\x81\x0F\xEA\x82\x08\xA4\xF3\xC9\x73\x03\xB7\xF5\x03\xDD\xE1\xC0\x4F\xF1\x7D\xC3\x08\x14\xCD\x45\xF7\x03\x1E\xF2\x2E\x6F\xF6\x40\x11\x2D\xDA\xD0\x0F\x3B\xF1\x84\x0C\x07\x74\xF7\x71\x18\xF7\x06\x0D\xDC\xFF\xF4\x26\x2C\x91\xF0\xF7\x82\xDD\x03\xFE\xF7\x5D\x05\xF9\x7B\xFB\xA0\xFE\x03\xBE\xE6\x08\x82\x01\xE1\xD7\x0F\xE1\x20\xE4\xAD\xD3\x20\x0F\xF8\x41\x10\x9C\xE3\xF7\x80\x04\xF1\xC9\xF1\xB8\xC7\x04\x18\xFB\x48\x30\xE7\xC9\xCD\xF1\xD2\xF1\x8B\xCB\x04\x21\xFF\x47\x02\xE9\x27\xF5\xF2\xDA\xF2\xBD\xCF\x04\x29\xFC\x4A\x0E\xE8\x96\xF7\xEB\xF6\xD7\x24\x11\xF9\xDD\x0B\x19\x0E\x47\x96\xF0\x00\x71\xEF\x4C\xD7\x04\x38\xF8\x3C\x0E\x07\x9D\xFA\x10\x20\xEC\xE6\xC2\x08\x9B\x01", - "\xE8\xC9\x0E\x94\xE4\xF3\x84\xDE\xB6\xDF\x04\x4A\xFB\x39\x14\x06\xA2\xFD\xE7\xF6\xD7\x28\x11\xF9\xA7\x03\xB7\xD7\x07\x49\xEC\xF3\xD3\xE6\x80\xC6\x08\xA9\x01\xE6\xED\x05\xDD\xEB\x0D\x5C\xF8\x86\xF2\xEF\xAF\x01\xE6\xF3\x05\xDD\xEF\x0D\x13\xE7\x81\xD9\xEA\x0B\xD5\x16\x10\xF7\x29\x1F\x91\xA6\xCA\xF3\xC4\x21\x75\xFA\xAC\xF7\xFB\x15\x27\x92\x86\x0A\x73\x3A\xD6\xB7\x03\xEE\xF4\x0E\x08\xDE\xF7\x8B\xD1\x2E\x02\xFC\x01\x16\x25\xC3\x09\x9B\xCD\xA2\xBB\x07\x80\xFC\x05\x88\xFE\x20\x0C\xFC\xBB\xF7\xC8\xDB\x17\x38\x1C\x48\x93\xFA\xEF\xD5\xFC\x71\x14\x0E\x1C\x4B\x86\xC3\x08\x3E\xC8\xA0\xC7\x0E\x5F\x01\xF9\xA0\xFE\x42\x15\xC9\xEA\xE2\xE2\xD3\x12\x02\x35\xF1\xE1\xD5\x30\x00\x63\x46\xC7\x87\xD3\xE4\xD6\xF3\x10\x70\xE9\x89\xC6\x06\xB0\xFC\x3E\x15\xEB\xC9\xC4\xFB\x8F\xE7\x82\xCB\x06\xB9\xF9\x40\x17\xEA\xDE\xF9\xAC\xBF\xF4\x34\x01\xFE\x0F\x11\x1E\x02\xE5\x81\x0D\xFB\x98\xE5\xB8\xD5\x06\xC8\xF9\x48\x36\x07\xE5\xF4\xC4\xC5\xFE\x7C\xFA\x06\xD1\xFB\x48\x32\xEA\xF3\xDD\xFC\xA0\xE6\xB6\xDF\x06\xD9\xFE\x05\xF1\xF9\xEE\xF1\xD8\x89\xF2\xD3", - "\xA1\xFF\x54\x14\x00\x23\xFE\x54\xF1\xAE\xE9\x04\xFA\xFD\x0E\x08\x03\xFD\xCA\xB4\x6D\xDE\x0E\x6F\xFC\x78\x0C\x00\xF2\xFD\xD2\x9A\xD7\x79\x06\xFF\xC9\x0C\x04\x19\xFF\xB0\x79\x8B\x68\x0F\x3D\x7F\xCB\x04\x05\x00\x00\xA1\x6F\x79\x74\x01\x83\x1C\x14\x77\xC4\x7C\x7A\x7D\xA2\x42\x00\x37\x31\xEC\x79\x10\x34\x77\x0D\x83\x6C\x6B\xA0\x47\x00\x11\x80\x7D\x0C\xE0\x55\x80\x03\x06\xCF\x75\xA2\x4C\x00\x19\x83\xF8\x07\x00\xB0\x77\x0B\x69\x04\x01\x02\x8F\x08\x23\x78\x07\x82\x10\x1E\x80\x44\x76\x05\x07\x02\x81\x09\x2C\x03\x08\x80\x00\x21\x18\xE9\x77\x0D\x3D\xDC\x4F\x08\xDD\x7D\x91\x61\xAE\x5C\x00\x36\x80\xD1\x0D\xFD\x46\x7D\xD4\x73\x40\x0D\x01\x2F\x80\x43\x08\x0C\x02\x03\x80\x81\x5F\x7F\x40\x02\x02\x04\x81\x3F\x0A\x90\x7A\x02\x98\x26\x0B\x6B\x09\x0C\x04\x94\x09\x38\x02\x0C\x88\xDA\x44\x75\x2C\x03\x14\x8D\x1D\x3C\x00\x56\x83\x82\x61\x03\x1A\x81\xE0\x07\x98\x7F\x04\x80\x00\x57\x82\xF9\x76\x03\x20\x81\xC9\x04\x11\x02\x03\xAC\x69\xE1\x6B\x0E\x0D\x03\xA5\x0E\xDD\x7C\x82\x77\xF4\x58\x26\x53\x81\x10\x07\xC3\x26\x31\x48\x00\xFA\x71\x07", - "\x8B\x68\x43\x03\x14\x88\x04\x37\x81\x38\x76\x1E\x8C\x3B\x5A\x6B\x4A\x03\x14\x8F\x04\x00\x82\x09\x06\x14\x02\x08\x9C\x7B\x87\x7B\x14\x86\x05\x08\x82\x06\x07\x15\x0B\x08\x86\x04\x5E\x7C\x00\x71\xF0\x53\x81\x5D\x00\x24\x83\x10\x1C\x01\x93\x83\x87\x5A\xAD\x5F\x01\x53\x80\x19\x0A\x09\x82\x04\xB2\x78\xF7\x77\xF6\x73\x64\x66\x03\x14\x8B\x06\x23\x82\x01\x06\x19\x0D\x09\xA6\x7B\x0B\x69\x1B\x03\x05\xB2\x01\xAC\x80\x00\x06\xED\x66\x82\xC0\x75\x8B\x64\x07\x13\x81\x79\x01\x2D\x80\x07\x28\x7F\x32\x6A\x41\x09\x6D\x1A\x6B\x7B\x03\x1B\x86\x10\x3C\x01\xB5\x83\xBA\x76\x3C\x15\x18\x44\x65\xC3\x76\x0C\xBC\x0E\x3B\x6A\x40\x0C\x0C\xA2\x7E\x29\x13\x87\x17\xAE\x3B\x7D\x43\x10\x0D\x86\x10\x16\x83\xD4\x82\x0F\x1A\x03\x82\x04\xC3\x81\x8B\x6F\x07\x0F\x83\x02\x04\x20\x05\x0B\xB6\x01\x03\x7A\x58\x63\x10\x31\x67\x2D\x6A\x20\x04\x0E\xBF\x08\xF3\x7A\xF1\x0A\x0E\x82\x04\xE0\x1A\xB6\x63\x08\x2F\x83\x54\x0A\xBE\x7F\xE4\x73\x83\x01\x05\xD8\x6D\xA2\x44\x02\xF8\x81\x77\x0B\x07\x39\x79\x4D\x6A\x40\x05\x94\x6D\x68\x85\x01\x40\x83\x30\x2A\x18\x09\x05", - "\xB4\x1A\xAD\x46\x02\xF8\x83\x21\x05\x0B\x8E\x7C\xC6\x0E\x95\x62\x10\x33\x18\x9B\x7F\x1C\x16\x11\x81\x04\x76\x65\x37\x86\x34\x1D\x84\x03\x06\x43\x8D\xA2\x49\x02\xF8\x82\x22\x05\x0B\xBF\x01\x03\x7B\x98\x67\x11\x98\x83\x73\x12\x4A\x8C\x11\xAC\x84\x29\x10\x46\x86\x10\x07\x84\xE1\x68\x23\x0A\x10\x8C\x0B\x6C\x82\x40\x0C\x10\x9E\x84\x44\x0F\x8D\x19\x10\x35\x69\x3C\x85\x42\x0D\x08\x35\x82\xDD\x04\x50\x83\x10\x34\x84\x2F\x7F\x4D\x8B\x2D\x06\x85\x02\x04\x95\x19\x11\xA9\x10\x4E\x87\x31\x80\x13\xBE\x10\x51\x87\xE2\x7B\xA0\x50\x02\xF8\x81\x24\x05\x0B\x80\x02\x03\x7B\x9F\x66\x15\x9A\x6B\x93\x00\x3E\x84\x09\x35\x82\x81\x03\x80\x7F\x65\x0D\x83\xDA\x6A\x25\x0A\x14\xA2\x0B\xAC\x5F\x40\x07\x16\x81\x85\xA3\x0D\x5B\x82\x10\x1E\x85\x21\x70\x09\x19\xA8\x46\x04\x3E\x84\x5C\x8C\x3B\x25\x66\x06\x04\xA3\x1F\x14\x97\x07\x97\x00\x51\x80\x1E\x3E\x85\x33\x87\x82\x69\x09\x2B\x85\xFE\x08\x61\x83\x10\x13\x6A\x7A\x84\xF2\x0C\x18\x83\x04\xAD\x65\x63\x85\x40\x0F\x86\x02\x05\xE6\x7F\xEB\x5A\x02\xF8\x83\x26\x05\x0B\x91\x7C\xC6\x0C\xA5\x1F\xAC\x0B", - "\x68\x9D\x00\x3E\x8E\x09\x35\x82\x17\x7E\xF1\x01\x19\x87\x85\x0B\x68\x28\x08\x18\xAF\x0B\xCE\x6A\x40\x07\x1A\xB5\x85\x2B\x11\x6B\x81\x10\x1E\x86\x92\x86\xF7\x03\xB0\x43\x04\x77\x87\x44\x74\x42\x0D\x6C\x03\x04\x5F\x8A\x1B\xAB\x10\x15\x6E\x41\x8B\xA0\x61\x02\xAB\x85\xC1\x01\x1C\x81\x04\x2E\x6D\x6D\x82\x2F\x09\x87\x03\x07\xCF\x6A\x1C\x83\x0C\xCC\x85\x65\x85\xCB\x78\x83\xA3\x01\x2D\x84\x08\x03\x78\x38\x6E\xE4\x7B\xA0\x65\x02\xF8\x82\x29\x05\x0B\x85\x02\x03\x7A\x73\x88\x1A\x9A\x6B\xA8\x01\x71\x83\x25\x07\x6D\x02\x06\x78\x80\x1B\x83\x11\xE8\x85\x40\x09\x1D\xBF\x86\x43\x10\xD4\x61\x12\x8B\x68\xA9\x00\x3E\x8A\x0A\x02\x86\xC9\x06\x48\x83\x10\x0F\x1B\xDA\x68\x2B\x06\x1E\xB4\x07\xC9\x67\x40\x01\x0E\xA1\x6B\xAD\x00\x3E\x8E\x0A\x38\x87\xCB\x07\x80\x82\x10\x18\x6D\x2D\x68\x2C\x07\xC3\x04\x79\x0F\x0B\xB6\x16\x10\x35\x83\xCF\x84\xB3\x02\x21\x83\x04\xFE\x80\x7C\x83\x47\x14\x88\xD2\x67\x82\x63\x0B\x08\x88\xE2\x09\x86\x82\x10\x13\x67\x2D\x69\x2D\x00\x22\xBE\x0B\xE8\x1B\x84\x83\x15\x93\x09\x86\x03\x80\x79\x22\x98\x88\x2B\x88\x7D", - "\x00\xF2\x46\x0F\xF4\x19\x43\x8B\xA0\x77\x02\xF8\x80\x2E\x05\x0B\x88\x02\x03\x79\xDA\x63\x10\x3C\x1B\x7F\x86\xD1\x0E\x23\x82\x04\xF8\x19\x90\x84\x34\x05\x89\x06\x06\x7E\x8D\xCD\x78\x83\xBB\x01\x2D\x89\x08\x03\x78\xDE\x67\x8F\x81\x23\xA5\x0E\x51\x88\x91\x83\x25\xA3\x0E\x40\x88\xD8\x7B\xA0\x7D\x02\xFF\x85\x91\x73\xE0\x59\x89\x02\x8B\x8D\x65\x0B\x80\x03\xB5\x80\xCA\x73\xA3\x71\x6D\xDB\x67\x95\x8C\x3B\x28\x89\x01\x05\xC0\x16\x24\xA5\x0E\x6E\x8A\x96\x8A\xAD\x42\x03\x5D\x8A\x41\x0D\x08\x03\x78\x71\x89\x98\x8A\xAD\x43\x03\xB5\x81\x31\x05\x0B\x8E\x02\xBB\x74\xF6\x56\x10\x1C\x67\x15\x8B\xB6\x02\x28\x83\x04\x79\x8B\x7A\x83\x47\x19\x5E\x06\x05\x8D\x85\x28\xA2\x0B\x79\x6E\x40\x0C\x0E\xA1\x6B\xC7\x01\x9D\x81\x24\x11\x8A\x01\x04\x87\x86\xAF\x48\x03\x96\x8B\x82\x85\xE9\x4A\x04\x22\x8B\xAF\x79\x0C\x1D\x8A\x01\x06\x24\x0B\xDB\x53\x8A\xF4\x82\x9A\x83\x24\x14\x02\xA7\x88\xA8\x8A\x2A\xBF\x08\x96\x03\x6E\x75\x71\x09\x04\x09\x1E\xB6\x6A\x0C\x0F\x88\x44\x0E\xE0\x63\x10\x33\x8A\x8F\x8A\xBF\x04\x79\x46\x04\xB5\x89\x8B\x6D\x0C\x38\x8A", - "\xA5\x0F\x7C\x63\x10\x09\x6E\xE1\x68\x34\x04\x2A\x94\x09\xC6\x88\x38\x8B\xA0\x51\x03\xB5\x83\x34\x05\x0B\x98\x02\x03\x78\xB2\x8E\x2C\x9A\x6B\xD5\x00\x3E\x86\x0D\x35\x82\x99\x03\x80\x71\x7E\x46\x04\xA8\x8B\xAF\x78\x0D\x0B\x8B\x9A\x02\xB7\x8A\x10\x1A\x8A\xBF\x79\x36\x0B\x2C\x89\x7D\x4F\x7B\xB7\x80\x23\x9A\x6B\xDA\x03\xB2\x8E\x09\x39\x79\x56\x1D\x42\x0D\x73\x1A\x6B\xDB\x03\xB2\x8D\x1D\x26\x5F\x06\x05\xBD\x8D\x2B\xAF\x0B\x93\x6F\x40\x07\x2F\xAD\x68\xDC\x03\x89\x8F\x2E\x0D\x68\x03\x05\xDA\x1A\xAD\x5E\x03\xF8\x83\x37\x06\x30\x97\x07\x08\x8E\x40\x0C\x76\x1A\x6B\xE1\x00\x3E\x82\x0E\x0F\x8C\x41\x05\xC4\x81\x10\x1E\x6E\x2D\x68\x39\x08\x0F\xA5\x03\x18\x8E\x42\x0A\x30\x86\x04\x13\x8D\x6D\x87\x0E\x21\x8C\x09\x07\xC8\x83\x10\x1C\x8C\x1A\x8A\x74\x09\x0E\x28\x8C\x24\x8D\xE7\x6F\x2A\xB7\x6B\x30\x8F\xCA\x85\xA1\x73\x8C\xF2\x08\xCB\x82\x10\x29\x6E\xFF\x89\xC1\x0A\x33\x81\x04\x74\x1F\x9B\x83\x3A\x16\x68\xD5\x73\xCC\x8D\x0E\x35\x8C\x02\x06\xDC\x19\x10\x3C\x8C\x2D\x8E\x0F\x1A\x34\x86\x04\x41\x8D\xCF\x8C\xBE\x0A\x04\xB6\x7C\x51\x7F", - "\x0E\x28\x81\xCB\x05\x28\x08\xFE\x51\x8D\xB5\x7F\x82\x64\x0F\x18\x8D\xC3\x06\x29\x0B\x35\x94\x8D\x0B\x69\x3E\x00\x36\x87\x07\xAB\x03\xD8\x8C\x9B\x5A\x6B\xFE\x03\xD9\x82\x1D\x30\x02\x60\x33\xC7\x5C\x35\x8A\x66\x0B\x6B\x00\x0B\x1C\x52\x80\x06\x06\x2D\x01\x37\x8A\x04\x73\x8E\xF3\x76\xAF\x48\x00\x77\x8D\xE1\x1B\x37\x89\x04\x7D\x8E\xF7\x7D\xA2\x4D\x00\x81\x8D\x80\x02\x0C\x2A\x8D\x06\x05\xF9\x73\x07\x80\x00\x12\x01\xE2\x87\x7A\x0C\x8E\x03\x06\xE3\x81\x04\xB0\x3D\x92\x8D\x90\x0C\x0C\x14\x8E\x60\x59\xE1\x69\x39\x83\x09\xD1\x00\xE7\x8E\xF2\x7F\x7A\x21\x03\xE7\x87\x7D\x22\x8E\xD9\x69\x8B\x66\x02\x26\x8E\x54\x0B\x36\x08\x3A\x8B\x71\x25\x6B\x0A\x0C\x3A\x9D\x07\xE0\x03\xEB\x8B\xA0\x70\x00\xB3\x8C\x78\x05\x0E\x36\x8E\xDA\x69\x0D\x09\x3B\x89\x07\xEA\x00\xEA\x8C\x02\xA6\x7F\x3A\x03\xEF\x8B\x1C\x2F\x03\xC2\x8F\x82\x6F\x03\x06\x8F\xC3\x04\x3D\x09\x3C\x9A\x6B\x44\x00\xF3\x87\x1C\x39\x03\xA8\x8E\x36\x81\xAE\x49\x01\x07\x5D\x77\x0E\x0F\x03\x78\x85\x8F\x37\x8F\xEB\x4A\x01\xD9\x8C\x86\x0C\x3D\x85\x7D\x0B\x6B\x12\x02\x3D\xB7\x60\x53", - "\x81\xE1\x88\x04\x96\x82\xB5\x7F\xF9\x87\x1D\x05\x00\xE9\x8C\xF9\x8A\xAD\x55\x01\xEE\x8E\xC4\x51\x3F\x8E\x7D\x2D\x6A\x16\x05\x3F\xBF\x34\xF7\x8D\xB3\x79\xEA\x7B\x8F\x90\x61\xFF\x81\xC6\x4B\x68\x64\x00\x00\x92\x1A\x42\x90\x02\x05\x4E\x8F\xEB\x69\x01\xE1\x8D\x72\x0E\x01\x38\x83\x85\x8E\x1C\x87\x39\x81\x04\x6A\x00\xEB\x8F\x06\x0B\x47\xC6\x3B\x0D\x32\x37\x83\x82\x2D\x69\x1C\x0C\x3A\xB6\x01\x18\x92\x84\x5A\x41\xBC\x8D\x1C\x91\xB8\x68\x07\x2C\x8E\x7D\x01\x08\x9D\xA3\x63\x90\x84\x8C\x84\x7F\xEB\x7F\x01\xAC\x8C\x21\x0A\x42\x94\x82\x2C\x90\xD4\x8E\x42\xB2\x77\x86\x00\xEB\x8B\x08\x33\x90\xC5\x4D\x0D\x93\x10\x05\x8E\x95\x82\xBC\x5D\x08\x2C\x8E\x92\x00\x0F\x92\x10\x3D\x00\x3E\x92\x40\x05\x38\xA7\x7B\x25\x68\x25\x0C\x3A\x99\x02\x46\x91\x40\x0D\x07\xA4\x4F\x24\x91\x2E\x81\xAE\x5B\x02\xAC\x8C\x28\x01\x45\x80\x00\x49\x01\x12\x90\x34\xA7\x82\x25\x6A\x28\x0C\x3A\xA7\x02\x5B\x93\x21\x84\x45\x89\x04\xEB\x5E\x41\x0C\x34\x8A\x8A\x29\x11\x1A\x9F\x43\xB8\x8C\x03\x0F\x1A\x91\x10\x27\x1D\xDA\x69\x2A\x0D\x40\x9B\x0B\x19\x69\xC2\x84\xCC", - "\x5B\x91\xAC\x03\x16\x95\x05\x39\x88\x0A\x05\xC9\x81\xAE\x6E\x02\x5B\x90\x2C\x0B\x45\x8F\x82\xC6\x0D\x1E\x94\x5E\x6D\x68\xB2\x03\x1D\x93\x1C\x17\x01\x80\x91\x42\x0F\x33\xB2\x77\xB3\x03\x16\x95\x0B\x1B\x91\x58\x00\x3E\x80\xA2\x7A\x91\x80\x7F\xC1\x58\x0B\x1B\x91\x59\x02\x26\x91\x48\x9F\x68\x07\x5F\x2E\x0B\x45\x9A\x01\xA2\x92\x24\x9B\x25\x87\x5C\xBE\x03\x16\x9B\x05\x0C\x89\x0A\x07\xDF\x1A\xAD\x40\x03\x8E\x92\xBF\x07\xA2\x5C\x92\x2D\x69\x30\x07\x70\x42\x03\x5B\x90\x17\x00\x4B\x89\x04\x82\x92\xBD\x64\x0C\x07\x5C\xC5\x03\x16\x99\x09\x86\x0F\xB7\x92\x40\x03\x49\xB3\x64\xC7\x03\xC1\x58\x0C\x1B\x91\x5E\x00\x3E\x83\xBC\x41\x04\xB2\x91\x8B\x6A\x0C\x35\x92\xEF\x0B\x34\x90\x00\x2A\x8C\xF6\x6B\x32\x07\x70\x4C\x03\x5B\x90\x28\x86\x3C\x1A\x93\xC1\x93\xAF\x7E\x0C\x07\x5C\xCF\x03\x16\x90\x06\x12\x93\x32\x8E\xB6\x61\x0D\x07\x5C\xD2\x03\x16\x91\x06\x38\x83\xD0\x6D\xB4\x5C\x80\x46\x31\x17\x61\xB8\x56\xC6\x30\x5F\xC4\x6C\x0F\x4B\x20\x7B\x65\xE9\x19\x0F\x63\xD8\x46\x0F\x4D\x6C\x40\x98\xA2\x4E\x34\xFF\x93\xF8\x60\x1B\x3E\x46\x8D\x3E", - "\x41\x97\xA5\x4E\x34\x92\x31\x3E\x92\x76\x65\x07\xA1\x33\xB4\x50\xC1\x44\x05\x13\x6B\x3F\x0A\x83\x53\x66\x0E\x36\xD6\x4C\x15\x06\x61\x35\x3E\x22\x3F\x51\xB2\x5B\x22\x97\x07\x62\x6F\x5F\x5C\x6C\x04\x4A\x92\x15\x1F\x5C\x5C\x04\x4B\x97\x82\x72\x5B\xFF\x6C\x00\x0F\xBF\x7F\x03\x3A\x40\x57\x05\x53\xAF\x60\x30\x96\xBC\x5C\x24\x6D\x4A\x3F\x32\x0C\x61\x14\x3E\x40\x5C\x06\x0F\x4E\xD0\x25\x62\x4C\x04\x51\x9A\xF6\x03\x95\x86\x09\x01\x57\x3E\x41\x05\x82\x34\x4B\x9D\x54\x8C\x95\x4B\x94\x09\x56\x09\x50\x95\x67\x92\x06\x5B\xF1\x6A\x50\xB7\x62\x52\x93\x99\x5A\x95\xCD\x64\x57\x93\x10\x35\x94\x82\x34\x58\x9A\x10\x22\x95\xCC\x62\x54\x9F\x55\x94\x95\xD8\x62\x57\x91\x8C\x5F\x50\x69\x62\x5A\x99\x1B\x68\x95\x57\x6A\x5B\x91\x7F\x70\x95\xCB\x4E\x12\x46\x56\xB5\x95\x68\x63\x5D\x92\x2C\x7A\x95\x3C\x95\x36\x5C\x16\x21\x62\x52\x04\x2D\x5E\xD0\x02\x96\x38\x61\xB8\x5A\x21\x6C\x05\x87\x96\x54\x0A\x21\x4E\x34\x8B\x95\x50\x0D\x58\xAB\x53\x5C\x04\x2B\x6E\x14\x12\x96\x43\x04\x89\x4C\x15\x04\x50\x6C\x04\x66\x92\x15\x2B\x5B\x41\x04\x01\x5E\xD0\x10", - "\x51\x6C\x04\x68\x92\x15\x10\x51\x5C\x04\x69\x91\x14\x26\x96\x9B\x50\x6C\x09\x8F\x43\x05\x6F\x4A\x48\x9D\x5A\x81\x05\xAF\x95\x6A\x93\x10\x2E\x96\xDC\x4E\x19\x6E\xB4\x76\x96\xB1\x66\x6C\x9C\x6F\x78\x96\xC9\x4F\x9B\x4D\x5B\x99\x95\xBE\x94\x6C\x90\x5C\x83\x97\x04\x97\x9B\x4E\xD0\x06\x97\xC2\x95\x71\x99\x54\x88\x97\xBA\x96\x43\x9D\x0C\x54\x5B\x6F\x48\x57\x01\x5D\x89\x97\xD0\x96\xBC\x53\x5D\x8D\x97\x05\x95\x40\x07\x5D\xB8\x96\xFB\x93\x2B\x5C\x5D\x94\x97\x71\x96\x77\x9E\x86\x70\x06\xF5\x62\x54\x0C\x43\x5C\x05\xC6\x4A\x52\x09\x5E\xBF\x03\xF8\x59\x50\x00\x90\x4C\x05\xEF\x96\x51\x00\x88\x5C\x05\x80\x62\x43\x35\x2F\x4F\x4C\x3F\x31\xB9\x51\x14\x3A\x97\x89\x53\xF2\x4C\x5F\x8E\x52\xD1\x5B\x7F\x94\x48\x41\x98\xF2\x5A\x80\x93\x10\x11\x62\x6C\x04\x82\x92\x15\x11\x62\x0E\x34\x83\x91\x14\x0E\x98\x93\x51\xB4\x59\x28\x47\x05\x13\x9A\x4F\x08\xF8\x0E\x34\x17\x99\x50\x09\x61\xA4\x47\x48\x6C\x25\x54\x6D\x74\x4E\x4C\x04\x88\x96\x14\x3C\x32\x5C\x04\x89\x91\x14\x26\x98\x23\x66\xF2\x48\x62\x82\x60\xE1\x5B\x8A\x99\xC1\x32\x5B\xD4\x46\x50", - "\x4F\x0F\x0A\x38\x5C\x04\x8D\x91\x14\x36\x98\xE1\x58", + "\x8D\x99\x8D\x9F\x45\x85\x47\x88\x18\x93\x87\x55\x99\x64\x9C\x88\x00\x06\x8F\xDB\x88\x00\xA0\x8E\x5B\x82\x6C\xA3\x89\x38\x88\x80\xA1\x84\x1B\xA8\x83\x60\x07\x84\xCF\x0F\xBD\x72\x8C\x63\x68\x1D\xD6\x0E\x60\x7D\x86\x46\x0B\x11\x88\x85\x0B\x8B\x13\xCE\x8C\x55\x9F\x7C\x03\x09\x3A\x87\x8E\x81\x06\x1E\x99\x7C\x7A\x82\x08\xEA\x8A\x31\x91\x89\xD5\x72\x11\xBB\x88\x75\x98\x7E\x8D\x89\xF6\x4A\x09\xFA\x88\x16\xFC\x8F\x7A\x93\x8A\xEE\x8C\x00\x8E\x8B\xCB\x8B\xFA\x18\x8F\x7F\x80\x00\x06\x93\x3B\x1D\x8F\xED\x02\xD8\x03\x8F\x67\x7D\x67\xE2\x89\x3B\x8A\x08\x07\x93\xF3\x1D\x82\x7F\x92\x8F\x02\x0F\x42\xBA\x8E\x13\x86\xF3\x56\x8E\x33\x97\x8F\xFD\x60\x2F\x87\x91\x04\x9B\x21\x86\x08\x89\x8E\x7D\x27\x95\x42\xBF\x81\x87\x0B\xEA\x4B\x71\x7C\x87\x81\x55\x89\x92\x0E\x87\x17\x9D\x21\xD5\x88\x23\x33\x91\x88\x8A\x94\x09\x8F\x1B\x91\x1A\x83\x0A\x8E\x9D\x91\x02\x0F\x47\x8F\x8F\x8D\x0B\x0E\xF3\x8A\x4F\x8A\x8A\xCC\x81\x20\x3A\x8B\x2B\x8B\x16\xDA\x88\x92\x95\x8B\x33\x8A\x2D\x85\x8C\x96\x87\x12\xD9\x89\x32\x85\x89\x54\x95\x2B\xB7\x88\x0B\x89\x10", + "\x4B\x91\x27\x9D\x8B\x4B\x89\x23\x82\x8C\x23\x9E\x24\xE1\x90\x4A\x88\x8B\x56\x94\x23\x8F\x92\x98\x87\x12\xD4\x85\x89\x83\x08\x5E\x93\x21\xB4\x8B\x2E\x84\x01\xE3\x92\x94\x9C\x8B\x49\x90\x00\x2E\x92\xD7\x79\x26\xC8\x88\x98\x86\x8C\x7E\x88\x3C\xA4\x8B\x38\x91\x15\xCC\x93\xFD\x62\x94\x92\x89\x4A\xAC\x85\xBD\x88\x25\xF4\x93\x38\x9B\x89\x7D\x94\x51\x91\x86\x36\x9D\x15\x9B\x81\x16\x80\x00\x84\x93\x2C\xAA\x92\x33\x96\x29\xE4\x88\x85\x85\x93\x80\x97\x4F\x90\x93\x78\x8F\x14\x8B\x96\xA1\x98\x93\xA3\x90\x20\x89\x94\x4C\x94\x26\xD7\x91\x57\x8A\x95\x5C\x90\x2B\xAD\x95\x4D\x99\x27\xB0\x96\x54\x80\x00\x0F\x8D\x3F\x85\x93\x3B\x9D\x28\x8C\x8A\xE4\x78\x90\x4A\x93\x56\xBE\x93\x3C\x9B\x25\xB7\x97\xA7\x8E\x95\x5B\x89\x4B\x9F\x89\x5D\x96\x2A\xDF\x90\xB1\x89\x88\xCD\x92\x4E\xAC\x8B\x5F\x9F\x26\xA6\x84\xAF\x93\x94\xBE\x92\x4C\xA8\x8A\x9D\x88\x26\xC2\x96\xA4\x87\x8C\xC9\x89\x32\xB1\x94\x38\x9E\x2D\xA7\x97\x49\x80\x91\x39\x6A\x44\x80\x97\xB4\x81\x2D\x85\x95\xE7\x67\x8F\x02\x97\x2C\x87\x91\x48\x96\x2E\xD8\x97\x9C\x99\x96\x7F\x8B\x48\xB9", + "\x8E\xD7\x79\x29\xCD\x90\xB2\x9E\x8B\xE8\x92\xA8\x6A\x97\x6A\x9A\x28\xC1\x84\xA5\x89\x96\x8E\x96\x2E\xBA\x96\xB8\x84\x30\xBC\x89\xB9\x87\x7F\x8B\x8B\x61\x83\x91\xBC\x8F\x30\x8F\x8D\xB8\x97\x87\xD7\x90\x61\xB8\x97\x80\x9D\xD7\x03\x9B\x83\x88\x80\x96\x18\x47\x89\x8E\x19\x9B\x13\xA1\x9B\x4E\x94\x91\x72\x7E\xBA\x7C\x90\xB4\x86\x32\xAC\x9B\xEA\x68\x99\xBB\x7E\xBA\x42\x93\x03\x90\x33\x91\x86\xDA\x64\x99\x68\x8D\x66\xAC\x8C\xB5\x7B\x32\xB4\x99\x8E\x8D\x91\xB8\x88\x00\x3A\x98\xD8\x87\x33\xAF\x98\x62\x9D\x99\xEB\x93\x68\xBB\x8C\xB5\x73\x33\xCC\x8E\xFB\x6A\x9A\xBF\x8D\x68\xA2\x98\x20\x91\x10\x48\x99\xC3\x90\x9A\xD5\x8D\x2A\x8D\x9A\xEF\x02\xD8\x2D\x9A\x20\x89\x65\xCB\x8E\xCC\x61\x9B\x24\x8A\x10\x1F\x66\x60\x76\x95\x6F\x8B\x20\x27\x26\x46\x89\x10\x6B\x9B\x78\x9E\x82\x85\x0B\x6C\xB0\x6A\xB9\x96\xCC\x02\x6D\x3A\x2C\x9B\x06\x0B\x9D\x38\x9B\x81\x0D\x3F\x7B\x9A\x40\x1D\x9B\x6F\x9E\x20\x1A\x20\x09\x99\x10\x6F\x26\xDF\x81\x08\x86\x99\x70\x83\x09\xC7\x1A\x38\xA3\x71\xDC\x98\x8F\x06\x0C\x97\x07\x9D\x4D\x4F\xE6\x09\x08\xF7\x13\x9C", + "\x7B\x96\xBA\x49\x25\xC6\x91\x10\x69\x1F\xE4\x99\x95\xDE\x8A\x21\x34\x96\xC1\x66\xFD\x04\x9E\x41\x05\x9D\xA1\x99\x21\x05\x1E\xCE\x9F\x8C\x15\x9E\x41\x1C\x96\xA9\x9F\x75\xAE\x9D\x81\x07\x46\x13\x9D\xED\x8C\x9D\xBC\x63\xE4\x79\x9C\xEB\x62\x14\x82\x6D\xEF\x8C\x91\x93\x9B\x74\xBC\x49\xD9\x92\x10\x65\x27\xE4\x86\x9E\xAC\x98\x79\xA6\x9D\x81\x0A\x3C\xD6\x0E\x18\x1C\x61\x3C\x81\x7A\x81\x08\xF2\x65\x36\x8A\x09\xD8\x94\x9E\x09\x0C\x87\x57\x9E\x3A\x75\x3D\x89\x09\xD8\x9F\x9E\xD6\x9D\x11\xA2\x9F\x84\x0A\xC8\x5A\x9D\xF7\x86\x08\x61\x9E\x7C\x89\x09\x4B\x88\x3E\x8A\x08\xFB\x83\x08\x61\x9F\x7D\x82\x09\xB0\x96\xC6\x6A\x9F\x21\x67\x9F\xF0\x9C\x7B\x99\x9F\xF0\x99\x10\x3A\x82\x0E\x9E\x81\x3E\x82\xB0\x61\x15\x84\x0A\x21\xA4\x92\x00\xBB\x8F\x0A\x0C\x44\xAD\x8E\x00\x07\x40\x84\xA1\x02\xAA\x08\x0D\xA4\x55\x0F\xA0\x42\x1A\x10\x03\xA2\x04\xA9\x08\x06\xA5\x82\x88\xA0\x0C\xA0\x41\x9A\xA2\x03\xBC\xA0\x14\xA1\x21\x16\xA1\xF9\x80\x42\x86\x09\x04\xA4\xA1\x26\x95\x21\x1D\xA0\x11\xAB\x41\xA9\xA1\x42\x10\x9D\x01\x0F\x84\x99\x91\x09\xA2\x3B\xC5", + "\x84\x72\x86\x08\xF6\x9B\x1A\xBA\x9E\x1C\xAC\x3F\xF5\x93\x0D\xB1\x60\x3D\xA3\x20\x36\x8C\x04\x94\xC2\x34\xA3\x40\x0B\xA0\x43\xA4\x44\x89\xA3\x22\xA5\x42\xC2\xA2\x11\xA2\x08\x4B\xA0\xD4\x41\x08\x25\xAF\x44\x81\x08\x0C\xA0\x00\x51\xA5\x86\xB6\x65\x2A\xAD\x2C\x0A\x0B\x02\xB7\xA2\x60\xA0\x04\xA7\x92\x81\x0C\xCD\x03\x09\x19\xAA\x89\x2C\xA7\x83\xAE\xA0\x59\x99\x46\x97\xA3\x1A\xA7\xA2\xA2\x9E\x83\xAE\xA2\x5A\x11\x47\xED\xA0\x0A\xB4\xA3\x72\x8E\x8E\xB3\xA1\x26\xA8\x46\x86\x0B\x08\xBB\xA3\x6F\xA5\x8F\x83\x09\x3F\xA1\x10\x05\xA1\x1D\xBE\xA3\x2D\xA0\x8F\xAC\xA2\x44\xAA\x46\x8A\xA5\x4E\x87\xA4\x83\xA1\x91\x93\x8C\x15\xA9\x47\x8C\xA7\x1C\xB3\xA4\x2F\xA0\x78\xAA\x87\x84\x0C\xCB\x6E\x91\xFD\x81\xA2\x52\x62\xDF\x49\x09\x4F\xAE\x3D\x8F\x76\x0F\xA2\x08\xA4\xA5\x7D\xA6\x80\x4F\xA8\x3F\xF3\x9D\x0C\x9A\xA1\xA3\xA5\x95\x81\x09\xB0\x9A\xE0\x2C\xA7\xFE\x85\xA5\x09\x0B\x30\x84\xA4\x00\x06\x48\xB9\xA6\x1C\xB7\xA3\x98\xA6\x20\x0B\xA0\x5D\xA2\x49\xD3\xA3\x84\x9F\xA5\x80\xA6\x91\x96\x96\x4B\xA0\x4C\xC6\xA6\x2F\xBA\xA3\x85\xA4\x8B\x84\xA7", + "\x46\xA1\x4C\xC3\x44\x32\xB1\xA6\x7C\xA5\x60\x82\x09\x5D\xAD\x4B\xDA\xA2\x35\xB0\xA6\xBC\xA4\x8B\x97\xA3\x69\xA7\x49\xCE\xA6\x37\xB0\x8F\xD7\xA1\x9C\x99\xA6\xA1\x99\x4E\xDD\xA4\x1C\xA9\x08\x2F\x94\x9B\x9C\xA3\x78\xA5\x4C\xC4\xA0\x3C\xAD\xA7\xF3\xA0\x9F\xAB\xA6\x7A\xA4\x4D\xE6\xA5\x7A\x9A\xA7\x81\xA5\x33\x80\xA8\x65\xA6\x45\x8A\x08\x3F\xA5\xA7\xF6\xA7\x9C\x82\xA8\x70\xAE\x4E\x82\x0B\x15\xA8\x9D\x01\x0A\x9E\xAB\xA6\x88\xA0\x00\x12\xA9\x40\xA0\x00\x0B\xA4\xA2\x96\xA8\x82\xA0\x00\x1A\xA9\x3D\xA4\x91\x1E\xAD\x9F\x89\xA9\xE5\x73\x50\xD5\xA6\x40\x01\xA9\x08\xA8\xA4\xA5\xA8\x7F\xA7\x52\xAB\xAB\x48\xAE\xA8\x0A\x08\xA5\x8D\xA7\x97\xA5\x50\x89\x0A\x4C\xA9\xA6\x26\xAD\xA6\x97\xA8\x05\xAC\x45\xA4\x92\x4F\xBD\xA9\xE2\xA1\xA8\xAB\xA7\x2B\xA1\xE2\x0E\x9E\x30\xBA\x70\x46\xA8\xC4\x48\xAB\x80\x05\x54\xCC\xAB\x52\xBD\xA2\x26\x69\x93\x91\xAA\x85\xAA\x4E\x97\xA9\x43\xA1\x08\x0B\xA7\xAA\x95\xAA\x8E\xAA\x55\xDD\xA8\x17\xBE\xAA\x43\xAF\xA3\x94\xA5\x94\xA3\x56\x8B\x9C\x17\xAC\x9C\x1C\xAB\x81\xA8\xAB\x9C\xA0\x00\x6B\xA8\x4B\xA1\x08\x6E", + "\xAC\xA6\xAD\xAB\xB3\xA4\x57\xEB\xA5\x5C\xA4\x91\x57\xA7\xAE\xA5\xAA\x81\x0A\x57\xD2\xA8\x33\xB8\xA9\x6F\xAD\xA2\xA2\xAA\x5C\x4E\x52\xA4\x93\x46\xAC\xAB\x87\xA9\xB0\x89\xAC\xB9\xAB\x58\x86\xAF\x60\xBF\xAB\xD8\xA7\xA2\x97\xA3\xC6\xAB\x57\x91\xAB\x63\xAF\xA4\x09\x0E\x6B\x81\x08\xCD\xA0\x00\x0A\x74\x65\xB0\x9B\x90\xAB\xAB\xAC\xAB\x71\x61\x49\xA2\xA8\x89\x9E\xAC\x97\xAC\x3D\xB9\x6F\xC2\xAE\x45\xD1\x64\x6B\xA4\xAC\x85\x6F\xB5\x93\x7B\xD0\xAA\x55\xA4\xAF\x36\xA9\xAD\x77\x72\xB6\x80\x72\xDD\xA2\xCE\x3C\xAD\x6E\xAC\xA8\x5C\xA0\xF6\x5F\xAC\x83\x06\x5B\x96\xAE\x69\xAE\xAD\xC0\xAB\x9D\xA8\xAD\xE3\xA0\x5A\xA5\xAC\x59\xB1\xAD\xC9\xAF\xA2\x82\xAE\xDC\xA0\x00\x45\xAE\x60\xAC\xAE\x82\x74\xB6\x81\xAE\xDF\xA5\x5D\xDC\xAF\x72\xAF\xAE\x54\xAB\xBA\x98\xAE\xCC\xA4\x5C\xDC\xAF\x15\xBF\xAE\x33\xA8\xAF\xAB\xAD\xE8\xAC\x51\xD7\xA2\x75\xA3\xAE\xE4\xAB\xD3\x6C\xAE\xB6\xA7\x45\xE2\xAC\x78\xB1\xAF\xBD\xAB\xBE\x81\xAD\x2B\xA9\xF5\x2B\x9F\x40\x17\x9C\x06\x08\xC0\x83\x08\xD4\x86\x10\x1E\x9D\x80\xAA\x08\x04\xB3\x20\x06\xB0\xBE\x97\x11\x12\x76", + "\x41\x18\x79\x0C\x9C\xBD\x74\x9C\x85\x0B\x39\x8A\xB2\x42\x0B\xB0\x02\x0E\x6A\xB8\x98\x81\x0D\x49\x09\x09\x87\xA6\x08\x5B\x9D\x94\x06\x08\x11\xBE\x23\x88\xB3\x85\xA6\xB1\x09\x08\xC3\x81\x08\xED\x76\x61\x89\x08\x8B\xA2\x08\x2A\xB1\x94\x0A\x08\xC9\x96\x10\x1E\x72\x40\x16\xB1\x01\x09\xC1\xB0\xB1\x12\x79\x10\x3A\xB1\xE7\x8A\x08\x19\x6A\xBE\x9A\xAF\x75\xA1\x64\xF6\x86\x7E\xB2\xAB\x45\xB1\x20\x2F\xAE\xEA\xA9\x64\x9D\xAC\x77\xAB\xA0\x4D\xB6\xBE\xA9\xAF\xD6\xA9\x10\x4D\xB3\x92\xA3\xAF\xAA\xAD\xCA\xA2\x75\x21\xB7\x51\xD1\xB0\x77\xB6\xB2\x5F\xB3\xCB\x8E\xAF\x29\xBA\x65\xCD\xAF\x6D\xB8\xB2\x11\x68\xB9\x9C\xB2\x8E\xAD\x64\xE8\xAC\x60\xA8\xB2\xEB\xAB\xCD\xAC\xAA\x30\xB7\x64\xA4\x90\x9D\xB2\xB3\x81\xAE\xCB\xB5\xB2\x20\xB2\x66\xE7\xB3\x7D\xA2\x08\x4D\xB1\xD0\xBD\xB2\xE3\xAF\x67\xE9\xB2\x99\xA4\xB4\x64\xB0\xA3\x6A\xB3\x31\xBF\x66\xF6\xB3\xA0\xB7\xAE\x85\xB0\x00\x3A\xB2\x3C\xB0\x67\x89\x0B\x95\xB1\xB4\x82\xB0\xBA\x94\xB4\xF5\xA5\x66\xB3\xAC\xA3\xB1\xAC\xED\xAC\xCF\x96\xB4\xF3\xA2\x6A\xD9\xAF\xA7\xA2\xAD\xFB\xAD\xD4\xBB\xAD\x3D", + "\xBE\x57\x83\x0B\x9D\xA7\xB5\x5A\xAF\x8A\xAD\xB2\x52\xBD\x69\xAB\xB7\xA6\xB5\xAC\x92\xB3\xD1\xBE\xB3\x44\xB8\x5F\x81\x09\xF3\x9E\xB5\x0A\x0E\x6D\x8C\x9E\x85\x07\x37\x86\x09\xB1\xA3\x08\xC7\xB2\x20\x3A\x9B\xBC\x9A\x10\x4B\xB7\x40\x09\x9C\xCF\xB2\x21\x10\xB6\x81\x02\x4F\x52\x9D\x40\x10\x9E\xD6\xB1\x20\x14\x07\xE5\x89\x8C\x3C\x62\xFC\x9C\x81\x3C\x65\x1A\x1C\xB7\x1D\xA8\xC2\x59\xB4\x2B\x54\x0F\xC9\x43\x20\x81\x0A\x1E\x66\x0D\x63\xB5\xB6\xAB\xA0\xEB\xB2\x21\x17\x06\x77\xB6\x6D\x9A\x92\xB9\xA0\x00\xD8\x04\xDE\x83\x09\x64\x40\xF1\x77\xB5\x36\x1A\xB7\xAE\xA4\xBF\x77\xB6\x85\x0A\x0D\x00\xBB\x2C\xB7\x6A\x03\xB9\x21\x1B\x06\x83\xB2\x57\x80\x9D\xC2\xA1\x08\xDC\x04\xE1\x9A\x90\xE4\x29\x6D\x9F\x65\x50\x1B\xA5\xC1\x2D\xE2\x8A\x09\x6E\x0C\x70\x82\x6E\x61\x3A\xB8\x09\x0E\x1B\x0C\xB9\x6F\xB0\x00\x58\x29\xB6\xB6\x68\xC9\x0E\x07\x9A\x2B\x93\xB4\x1F\x3C\x63\xED\x8F\xB8\x00\x07\x1B\x0C\xB9\x5D\xA0\x61\xB0\xB8\x38\x0C\xB8\x61\x9B\xDA\x89\xB9\x70\x08\x73\xD2\xB4\xCC\xA2\x08\xE2\x04\xE1\xA4\x90\x67\xBF\x70\xE3\x07\xC8\xAA\x08\xF4\x24", + "\xE5\x89\x10\x85\x09\x4F\x4A\xBA\x2C\x4A\x08\xFD\x27\xE7\x80\x00\x72\x0C\x70\xBA\x81\x47\x32\xBA\xE5\x02\xE8\x8A\x08\x9B\x22\x75\xE6\x06\xD6\xA9\x08\x54\x2A\xEA\xA7\x07\xAF\xB6\x10\x63\x28\xC8\xA6\x08\xE8\x05\xE3\x8A\x09\xBA\x22\x75\xE9\x07\xCC\xAA\x08\xA4\x2A\xEA\xAA\x06\x86\xBB\x40\xEF\x2E\xD3\xA1\x12\x24\x96\xD4\x12\xBB\x75\x04\x76\x83\x0B\xAA\x32\xBA\xEC\x05\xEF\x82\x08\x57\x32\x75\xED\x04\xC3\xB0\x78\x19\x32\xEA\xAE\x07\xC3\xBA\x10\x25\x32\xD4\xAF\x07\x0C\xB8\x74\x81\x09\x13\x32\x75\xF0\x04\xC3\xA3\x88\x29\x3F\xEE\x83\x13\x33\xA1\x10\x05\x3A\xE6\xBF\x11\x43\xA4\xC5\x12\xBB\x78\x0C\x70\xC3\xA1\x8C\x32\xBA\xF2\x04\xE1\x97\xA3\x33\x32\x75\xF3\x06\xEA\xAA\x08\xAC\xBF\xE7\xB4\x07\xD7\xB9\x10\x1E\x36\xD4\xB5\x07\xB4\xBE\x20\x36\xBD\x9F\xB6\x0F\x39\xBF\x40\x0A\x36\x52\xBF\x1E\x3E\xBC\x81\x00\x7C\xBF\xB8\x3E\x05\xBD\x0A\x0E\xDE\x12\xBB\x7C\x08\x7C\x89\x0A\xBE\x32\xBA\xFA\x04\xE1\x88\x7D\x7F\x32\x75\xFB\x04\xE3\xA9\x08\x62\x3A\xEA\x9D\x0E\xC4\x73\x70\x52\xB8\x3F\x17\xBC\x0A\x0F\xE3\x1F\xBC\x2A\x10\xF1\x49\x3A\xD4", + "\xBD\x07\x91\xBA\x21\x20\x3A\xA9\xBE\x0F\x0C\xBA\x9B\x96\x3B\xDA\xBC\xE1\xBC\x65\xC1\x32\x75\x80\x02\x1E\x69\x46\x8A\x61\xF0\x23\xBF\xEE\x03\x7F\xF5\xBD\x00\x17\xBF\xA6\xA3\x20\x06\x3C\xA9\xB2\x00\x00\xC0\x27\xAA\x08\x03\xC7\xE7\x83\x00\x03\xC6\x10\x40\x07\x82\x9A\x81\xDD\x0F\xDE\xA8\xB9\x6D\x11\x14\x3E\x8E\x04\xD0\x27\x41\x0C\x6E\x8B\x0F\x0A\xC6\x28\x3C\x62\x05\xC4\xB7\x02\x08\x02\xE0\x0F\xA0\x0A\xC8\x13\xC3\x70\x01\x0A\xD8\x9F\x7E\x81\x11\xA0\x04\x72\xA6\xC3\x71\x11\x90\xA8\xA0\x94\xBF\x11\xA0\x0A\x03\xC9\x46\x0F\x84\x8E\xC6\x1C\x87\x6E\xC0\xE9\x07\x71\xF0\x27\xF6\x8B\xC1\xF5\xA3\x07\xC5\x19\x12\xC4\x1F\x41\x08\x89\x82\xC2\x53\x14\xE4\xAC\x75\x7B\xBC\x44\x7E\x9D\x11\xD4\xB2\xAA\xA7\x41\x39\xA1\x10\xC0\x82\xB3\xC2\x18\xBA\xC0\xC3\x0A\x07\xA1\x9A\x2D\xCF\x84\xE8\x7C\x2E\xA2\x8D\x55\xC0\xD5\x8A\x8E\xA3\x8A\x10\x22\xC1\x72\x01\x0A\x4D\xA8\x00\x1F\xC0\x1B\xAD\x89\x64\xC1\x2C\xA0\xC2\x99\xA9\x0C\xDD\x0F\x21\xA6\x83\xB2\xC0\x95\x01\x0A\xB0\x7A\xF6\x61\xC2\x88\x79\x8C\x3B\xA6\x19\xDB\xC0\x0A\x0A\xC0\xAD\xC3\x00\x1C", + "\x79\x94\x9C\x38\xAB\xC3\xD6\xB6\xC7\x86\xC5\x07\x13\x10\xFD\xC2\x1D\xD1\xC0\x27\xB6\x78\x0E\xB9\x18\xC9\x10\x12\xBF\x22\xD3\xA9\x82\x68\x12\xD6\x63\xBE\x31\x24\x5A\xAA\x26\xCF\xB0\x76\xC5\xC2\x83\xC5\x07\x1E\x58\xF0\xC3\x44\x2B\xA0\x99\xC3\x04\xCA\x08\xAB\x98\x84\xF4\x0F\x02\xA9\x91\x67\xC2\x21\x1B\xB1\x83\xBE\x62\xDD\x1F\x15\xBF\xC3\x27\xC3\xC6\xB2\xA4\x2A\x18\xF8\x66\x63\x15\xA8\xC4\xD2\x9F\xD7\xA7\xB7\x00\x1A\xE0\x3E\xC7\x23\xCA\xC5\x09\x0C\xE8\x97\xB6\xA4\xB1\x86\xAF\x93\xA1\x66\x08\xB8\xC7\x38\x01\x0B\xA6\xBA\x82\x8F\x11\x1A\xCF\xC6\x3F\xA3\x48\x01\x0B\xA8\xB5\x8D\xC1\x10\x67\xB8\xC6\x01\xBF\x41\x01\x0B\xAB\xBD\x8D\x82\x0B\x49\x2F\xC3\x9E\xB4\x12\xFD\x85\x80\x09\x39\xB1\xC5\x42\x03\x2A\x9C\xC3\x48\x10\x79\x42\xCF\x89\x83\x09\xD8\xB1\xC2\x03\x0C\xAB\x31\xC7\x80\x05\x88\xC3\xA1\x3D\xC8\x28\x03\x8D\x1D\xC0\xC5\x84\x0F\x55\x7B\xC4\x95\x03\x88\xF4\xC0\x19\xC6\x09\xB0\x2F\x85\x83\x0A\x5A\x26\xC8\x96\xC1\x1A\xFC\xC0\x85\x0C\x56\x0D\xCB\x90\x19\x7A\x3C\x66\x12\xC0\xC7\xE8\x9A\x58\x16\xCB\x8F\x0A\xC4\x19\xCF\x18", + "\xEE\xC6\x83\x09\x71\xF8\xC6\x40\x0A\x2E\xE5\xC1\x20\x03\x9D\xF4\x01\x80\xDC\x85\x17\xC6\x08\xD0\x28\x1D\xFC\x1C\x05\x78\x35\xE6\xB5\x75\x3B\x20\xA3\x1A\xC1\x69\xC3\x7F\xC1\x10\x57\x2E\xF1\x19\x2E\x32\xCB\x48\x2F\x90\x8A\xAC\x93\xD4\x12\x7C\x21\xCA\x3F\x14\xA2\x87\x97\x5C\xC9\x10\x07\x33\x2D\xA3\x1D\x69\xC3\x29\xD2\xC6\x85\x09\x78\xBC\xA1\xE9\x11\xAB\x32\x7B\x24\xCE\x28\x45\x76\x5D\xC5\xC8\x13\x2A\x74\x35\xC9\xDB\xA3\x30\x83\xC2\xDE\x49\x46\xA2\x7B\xC9\x0A\xCB\x20\x0E\xBC\x9C\xC3\x10\x14\xBD\x4A\xC0\x00\x12\xB3\x14\xF6\xB5\x7F\xA6\x8A\x83\x0A\xE8\xAC\xCB\x43\x17\xE5\xB2\xCA\x23\xB6\x10\x68\xCA\x56\xC2\x08\x2E\x36\x78\x27\xBD\xB7\xC2\x8A\xD3\x9E\xAE\xBB\xAC\x2F\xCE\xA1\x19\x7B\x4E\x9C\x94\x93\x29\xD6\x7D\xCA\x69\xC8\xA1\x3E\xAE\x81\x0A\x88\xDE\xCB\x13\x2A\xC4\x65\x2D\x2E\xC2\x09\x1A\x3E\x91\xD4\x12\xD5\x81\x9B\x8A\xC5\x32\xD1\xCD\x80\x06\x65\x1D\xCD\x77\x04\xB1\x02\x0A\x91\x4A\xC5\x73\xC2\x8E\x8A\x0A\x9F\x26\xCD\xE0\x0A\x18\xE0\xCC\x55\xBA\x8D\x8A\x0A\xA6\x30\xCD\xC9\x0A\xE7\xA3\xC3\x1E\xBA\x10\x7B\x26\x66\xC1", + "\x08\x84\xBE\x24\xFF\x10\x6A\xC9\x3F\xBC\xCD\x42\x14\xB1\x41\x11\x28\x05\xBF\xE2\xCF\x20\x64\xC4\x73\xC3\xB0\x0A\x0D\xDA\xAD\xCD\x84\x03\x6D\x42\xCC\x95\x10\xC7\xD6\xCA\x11\xD5\x71\xE9\xC6\x10\x5E\x34\x6E\xCB\x0E\x2B\xB9\x3B\xC3\x9F\xDF\xC0\x00\x6C\x35\x67\xCF\xBE\x6F\xCE\xEC\x86\x08\xD5\xCA\x10\x5B\x99\x51\xD4\xBE\xD6\xCF\xE0\x2F\xCA\xB6\xBB\x9E\xA8\xB2\x41\x13\xC5\x77\xC2\x21\x0F\x39\xCE\xCF\x72\x6F\xC9\xDC\xB5\xCF\x29\xB1\x10\xC9\xCC\x84\x23\x89\xBF\xB0\x79\xCC\x22\x2B\xC9\x20\x12\xC9\xEB\x01\x14\x3F\x38\xF9\x94\x0F\x14\xBE\x3A\xC9\xD0\x35\xC3\xA0\x81\x08\xD9\x20\xD0\x0F\x12\xBA\x1D\xCD\x09\xD8\x85\xD3\xC9\x42\x10\x3B\x0F\xD1\x21\x3C\x3B\xB7\xC6\x77\xD6\xCD\xCD\xAE\x65\x15\xD0\x00\x3A\xBE\xBC\xC5\x40\x62\x6E\x67\x63\xCD\x00\x04\xFE\xAC\xD0\xEF\x11\x97\x81\x09\x66\xDC\xCE\x02\xC2\x0E\xE0\x0F\x05\x38\x94\xF0\xCA\x7D\xC9\xCE\x0A\x0A\xF1\x3D\xD1\xEE\x05\x95\xC0\xA1\x42\x15\xD1\x00\x04\x35\xC0\xD3\x84\x0E\x78\x43\xD0\x78\x03\xCB\x6F\xC8\x49\xCD\xB3\xA2\xCD\x79\x4E\xD1\x72\x0E\xCB\xD9\xC1\x20\x08\xD2\xDF\xC8\xA3", + "\x82\x09\xE8\x36\xD2\xCB\x0F\x2E\xD9\xD2\x1F\xDB\x2F\xB0\xD0\x13\x28\xD2\xC8\xCD\x36\xC9\x09\xD2\x30\xA6\xC3\x0F\x60\xC3\xD3\x48\xD2\x3A\xCB\xD2\x83\x0A\x7A\x6D\xD3\x71\x1C\xCC\x51\xD4\xC2\x69\xD0\xD7\x36\xA7\xD2\x0E\x91\x3D\xD1\x48\xD7\xC3\xB3\xD3\x81\x02\x7B\x3D\xD2\xED\x3D\xD1\xA5\xCE\x2A\xC6\x08\x24\xDE\x9E\xB0\xD1\xF0\x3D\xD1\xCF\x3D\x47\xF6\x33\xA7\xC3\x10\x48\xD0\x7E\xC5\xCA\xD3\x3D\x47\xD8\x3F\x1E\xD1\x69\x14\xD6\x40\x1A\xCB\x5A\xD1\x45\xCC\x23\xC2\xC0\x00\x02\xD6\x9A\xCF\x10\xDC\x3D\x4F\xD7\x0E\x52\xDD\xA8\xFF\xCB\x8F\x00\x3F\xAA\xD1\x28\x24\xD5\x4B\xD6\xA6\xE0\x0F\xFB\x31\xD5\xB2\xC3\x15\xE9\xD1\xF9\x38\xAB\x81\x12\xA9\xD5\x9A\x29\xD7\xFE\x3D\xD5\x07\x1B\x35\xD6\x99\x51\xDC\x3F\xC3\xD1\x48\x28\xCC\x1B\xD9\xA2\x80\x42\x41\xC7\xCD\x3F\xD7\x54\xC3\x08\x01\x46\x90\xBB\xBF\xBE\xA4\x92\x09\x0A\x49\xD2\xD6\x81\x04\x80\x4F\xD4\x78\x0B\xD6\xB9\xB4\x3C\xC6\x40\x6F\xD9\x1C\x60\xD4\x97\xC3\xD4\x02\x08\x01\x64\xD7\xE5\x00\xAE\xE9\xD2\x15\xC9\x08\x17\x43\x5D\xC3\x0E\x70\xD2\xA7\xDB\xD5\x40\x1B\x40\xF2\xD7\x38\x20", + "\xD7\xED\xC8\xAE\x81\x09\x07\x59\xD7\xD2\x08\x5C\xFF\xD5\xFC\xC9\x10\x29\x42\xF1\x0B\x41\x3D\xD2\xEF\xB3\xD0\x70\xDD\xAA\x83\xCA\x41\x0F\x41\xC6\x19\x06\x7D\xD1\xBF\xBB\xB0\xB9\xD4\x79\xD6\x41\xC6\x18\x07\x7D\xD1\xE0\xC7\xAD\xC7\xCC\x8F\xBD\xD2\x3F\x14\x07\x49\xD7\x1B\xB9\xFD\x29\xD0\x12\x40\xD8\xD7\x0D\xC9\x82\xB6\x7B\xDD\x5A\x4D\xB1\x58\xD6\xB6\x57\x46\x20\xF3\x34\xE3\x1D\x64\xFE\xCA\xC3\xC3\x08\x59\x46\x78\x25\x43\x1E\xD7\x6B\x46\x1E\x30\xCF\xD9\xD2\x9E\x0F\x46\xC8\x5E\x3E\xB3\xCF\xA9\x51\xCE\x44\xC6\x18\x12\x7D\xD1\xE5\xCB\x97\x81\x0B\xCA\xCC\xD6\xE4\xCF\x12\xF4\xC5\x07\x1C\x6C\x56\xCF\xD3\xC0\x00\xA2\xCE\x55\xCA\x8F\x55\x4D\xA1\xD2\x0F\xB5\x21\xD1\x06\x0F\x6A\xDA\xD7\x77\xD7\x0C\xDC\xD8\x7D\x02\x37\x9D\xCF\x6A\xD3\xD2\x18\xDC\x00\x66\xD9\x80\x0A\xBE\x56\xDD\x37\xE9\xD1\x5E\x4F\x9D\xC3\x0C\x7C\xCF\xCE\x02\x0F\x6A\xEE\xD6\x82\xD6\x10\x14\x02\xDB\xCF\x10\xF2\xC8\x6F\xCE\xDB\xE8\xC9\xA2\xC4\x45\xDD\xC7\x0E\xE2\xB9\x6E\xC9\x08\x7E\xDC\xB2\xCB\x47\xE1\xD2\x0E\x0E\xD2\x71\xC6\x09\x81\xD5\x94\xA0\x03\xDF\xC3\xB0", + "\xAB\x46\x8C\x59\xBE\x0C\xDA\x36\xED\xCD\x8A\xC5\x47\x9D\xCD\x22\x7D\xD0\xB7\x30\xB6\x9D\xDC\x24\x29\xD1\x21\x4D\x33\xFD\x49\x1E\xDA\x77\x25\xDE\x40\x09\xB6\x2B\xB1\x45\xCD\x4A\x94\xD1\x14\x4A\xC4\x00\x10\xDD\x7C\xDE\xA1\x3A\xCC\x61\xC6\x99\xA4\x22\x6E\xD7\xDA\xBD\xDB\x85\x35\xD7\x1C\xB2\xAA\x83\x19\x02\xDD\xD8\x06\x09\xE9\x86\x09\x17\xB4\xB6\xD2\x4B\xF1\x4F\x17\x8C\xDC\x78\xC7\xD1\x81\x18\x78\x46\x1C\x71\xC2\x08\xCC\xD9\x77\xC0\xB5\xE7\xD5\x30\x67\xD4\x15\xC4\xCF\x7F\x4E\x75\xFF\x10\x21\xDC\xB9\x82\x0A\xF7\xD9\x8D\x29\xD1\x35\x62\xDE\x2A\x1F\x79\x6B\xDF\xF9\xDB\xCD\x20\xD8\x00\x0A\x4F\xF5\xD0\x9F\x3D\xD1\x9D\xC5\xDF\x01\x0C\x1B\xC3\x09\x91\x23\xBD\xA4\x22\xFE\xC2\x08\x10\x2D\x7F\xEB\x21\x00\xE0\x8D\xA9\xD2\x7E\x4B\xDF\xDD\x0C\xF6\x2B\xDE\x02\xE3\xA6\xC5\xC9\x87\x48\xE0\xE0\x09\x52\xF8\xDF\x87\x22\x92\xB7\xDA\x40\x03\x52\xEB\xDE\x4E\x7D\xD0\xED\x3B\xBE\xCE\xCE\x40\x1C\xDF\xF1\xDC\x89\x1E\xE1\x80\x0C\xC0\xAC\xD8\x13\x20\xE1\x52\x49\x45\xC9\x54\xDA\xD9\x13\x0A\x0B\x8D\xDD\xD7\x00\x07\x52\x4F\xDD\xEB\x07\xAB\xD6", + "\xCF\xD8\xD8\xDA\x29\xD1\x56\x73\xE1\xA0\x02\xAC\x93\xE3\x0D\xF7\xE1\x45\xCA\x59\x7B\xE0\x85\x04\xAD\xB6\xE0\x6D\xCD\xDE\x02\x0F\x5B\x43\xE2\x78\xD6\x87\xB7\xE3\xFB\xC5\xCA\xF4\x53\x89\xC6\x08\x84\xD6\xC4\x9E\xD8\x79\xD2\x58\x52\xE3\x20\x34\x41\xCE\xC7\xC3\xC3\xDE\xF6\xC1\x08\x27\x59\x8B\xC2\x08\x91\xD5\xC5\x86\x09\xF4\xDF\xE2\x00\x01\x69\x62\xE3\x80\x09\xB3\xE5\xE3\x40\x14\xDC\x30\xD5\x6B\x5D\xCD\xB9\x5D\xA3\xC8\xDA\x0F\xFE\xDC\xE4\xCA\x70\x5D\xCC\xCA\x5D\xA3\x82\x02\xEE\x59\xD6\x16\xD9\x7E\xE3\x5D\xCE\xCC\x08\x19\xDD\x19\xDF\xE3\x06\x0C\xEB\x86\x08\xAB\x22\xC0\xC3\x22\x22\xE3\x08\xD8\xC8\x86\xCC\x23\x48\xE2\x10\x2F\xE0\xCB\xCE\x04\x97\xDB\x48\x2D\xDB\xCE\xC4\xC9\xD2\xDD\xFC\xD2\x04\x99\xE0\xF4\x88\xE4\x48\xED\xC2\xE4\xCE\xED\x4B\xE3\xAC\x79\x94\xC0\x01\x4E\xE1\xAE\xF1\xDE\x26\x0A\xE5\xDD\x09\x03\x2A\xE4\x56\xEF\xC4\xB0\xD0\xEF\x48\xE5\x1D\x03\x96\xFA\xC4\xF2\xC2\x0A\x30\xE4\x78\x01\x01\xBA\xE1\x21\x1E\xE3\xA2\xC6\x0A\x3E\xE5\x72\x02\x47\x9C\xE2\x4F\xE4\xCE\x55\x06\xCC\xCB\x0F\x42\x49\xE6\x1E\xB1\x45\xCC\x5F", + "\xCE\xCC\xBD\x3D\xD3\x48\x4B\xDF\xAC\xE5\x61\xCD\xCD\x81\x04\xBE\x1D\xCF\xFD\x5D\xD1\xB3\xDB\x82\xEC\xE4\x5A\xDA\xB5\xFB\x5D\x67\xC7\x60\x3D\xD7\x2E\x74\xDE\x85\x0C\xC8\xA1\xE3\x13\x2D\xE7\x29\xE4\x3C\xCE\xC0\x16\xE9\x10\x26\xBB\xF2\xC9\xD1\xC1\x04\x7B\xD3\x13\xF0\xC1\xCF\xF1\xDC\x31\x0B\x50\xFC\xE2\x20\x3A\xC6\x77\xE4\x42\x03\xEB\x40\x05\xC8\x04\xEB\x39\x05\x06\x43\xE1\x20\x08\xE9\x3F\xF0\xE1\xC7\x03\x41\x4C\xC9\x7B\xE4\x9E\xC8\x07\x82\x4A\xCF\x03\x0B\xA2\xD2\xE5\x27\x26\xC9\xD0\xD9\xFC\xC9\x06\xCD\xE3\x38\x19\x4D\xCE\xCD\xD1\xB8\xE0\x79\xCD\x06\x21\xEB\x36\x63\xE5\x4A\xE5\xCA\xF1\xDD\x34\x09\xE9\xD2\x08\x3B\x64\xE9\x23\xE8\xC6\xD5\x04\x4C\xF7\x0E\xF3\x4B\xA6\xC9\x09\x5A\xEA\xB5\xD9\x07\x4D\xE1\x0A\x0F\x52\xA7\xD1\x9D\x14\xDD\x0D\x3F\xE9\x47\x0A\xE5\x25\xEB\x98\xF0\xD1\x70\x06\xD4\x89\x09\x93\x42\xEA\x03\x0F\x8C\xC5\xCB\x72\x0D\xD4\x86\x0A\x06\xF6\xCE\x25\xE8\x8E\xDA\xDB\x74\x0A\xCA\xED\x04\x43\xE6\x08\x99\x53\x7D\xE5\xE8\x6D\xEE\xA1\x8F\xDA\x2A\xF3\x07\x5F\xEB\x20\x00\x56\xB1\xE1\xC8\xB0\xE1\x3D\x0A\xE5\xF9", + "\x01\xAD\xC2\x09\x6C\x5B\xBE\xE8\x2A\x41\x05\xE9\x45\xCB\x1F\x32\xEB\x1F\x11\xC5\xB3\xD2\x5D\xF0\xCE\xE4\xCD\x1F\x3B\xEA\x2A\x1D\xAF\x3D\xD3\x5F\xE6\xC7\xA2\xD3\xB0\xDD\x0E\x82\x56\x3C\x07\xEE\xA1\xB1\xDF\x01\x00\x8C\x5B\xC9\x80\x08\xC5\xFE\xEA\xDC\xC4\xCF\x03\x02\xB2\xF4\x0E\x8A\x5D\xD8\xBB\xE5\xFC\xC5\x00\x9A\xE9\x40\x17\x59\xCE\xE2\xCC\xA9\xD3\x01\x01\xED\x0F\x11\x64\x64\xEC\x33\xE9\xA2\x89\x00\x6A\xE1\x12\x61\xE6\xB2\xD1\xE6\xF2\xCB\x00\x2F\xEC\x7B\x96\xED\x01\x09\x66\x46\xEC\x3C\xE1\xBF\x8F\x00\x6E\xE6\x18\xBF\xEC\x68\x7B\xED\xD3\xD4\x9E\x93\x03\x6F\xF5\x00\xBF\xEE\x69\x7D\xD1\x8A\xC7\xD7\xA9\xD3\x05\x00\x63\xAD\xC1\x21\x13\x5A\xE3\x1C\xDC\x80\xED\xFC\xD8\x00\xD0\xEC\x3E\x32\xE3\xB7\xC5\xDD\x88\xEC\x79\xD9\x00\xD9\xE9\x40\x2B\x5A\xEA\xE4\xD3\xC5\xCA\x06\x01\xEF\x0F\x15\x6D\x64\xEF\x9D\xE9\xA2\x9B\x00\x7A\xE1\x12\x74\xE3\x46\xDD\xEF\x80\x0B\xB7\xC5\xC8\x07\x0F\xEF\x43\x14\x6F\x6B\xEE\x83\x0A\xD4\xDA\xD9\x07\x18\xEF\x3F\x12\x8F\xF2\xEE\x65\xE1\xBF\x9E\x00\x80\xF4\x12\x8A\x5B\xBF\xEF\xE3\x14\xDF\x01\x07\xF0", + "\x08\x1F\xED\x90\x5B\xB9\xFC\xEC\x18\xE2\x02\x07\xF3\x08\x1F\xED\x7C\xE4\xBB\xED\xEA\x96\xD5\x02\x07\xF2\x09\x1F\xED\x83\xE3\x3E\xCA\x09\x87\xC1\xBF\xA8\x03\x81\xF2\x17\xF4\xCB\x20\x33\xEE\x34\xE9\x02\x60\x61\xD8\x8D\x01\x27\xF0\x3C\x1F\xB8\x83\x04\xE2\xB0\xE2\x0B\x11\xF1\xCC\x13\xC6\xEA\xF1\x14\xDF\x02\x2E\xF1\xF6\x78\xF1\xCB\x08\xB1\x0D\xEE\xF2\xC4\x03\x60\x62\xC5\xAA\x08\xAB\x5D\x47\xC2\xF2\xEB\xE0\xC3\xB7\x02\x91\xF4\x0F\x85\xE6\x53\xC1\x09\x25\xFE\xDD\xF1\xDE\x0E\x0F\xF2\x01\x17\x11\x03\xEC\x2A\xFF\xD8\xB0\xE1\x0F\x18\xF2\x0F\x11\x12\x1B\xF3\xCB\xE1\xBF\xC0\x00\x98\xE1\x12\xB4\x5A\xC9\xDE\xEC\x18\xE3\x04\x67\xF3\x90\x15\x04\x63\xF5\xB4\xE4\xCE\x23\x0E\xE6\xBF\x13\x25\x11\xF3\xAC\xEC\x3C\xC9\x03\x3A\xF4\x25\x39\x5E\x9A\xF3\xED\xF1\xDC\x09\x3C\xF3\x27\x0F\xDB\x9B\x06\x33\x5C\xF2\x32\xB4\x3C\xD1\x02\x3E\xF4\x05\x3F\xEF\x2D\xEA\xD4\x03\x08\xD1\xE4\xE6\x0B\xE3\xE5\xFC\xF1\x16\x1F\xED\xBE\x5A\xCA\xC0\x01\xCB\x29\x10\x78\xE8\x8C\xDB\x02\xBF\xED\x3B\x00\x5F\x1E\xDC\xE9\x86\x09\xD6\xD4\xF4\x00\x05\x0B\x21\xF4\xF0", + "\x05\xCC\x9A\xF5\xA9\xE3\x08\x40\xE0\x46\xDF\x03\x55\xF9\x1C\x29\x07\x60\xEF\xF5\x80\xB1\x45\xE1\x02\x5A\xFB\x1C\x46\x5C\xA9\xE4\xF3\x30\xE3\x0C\x3C\xF5\xE1\x0D\x0A\x37\xF7\x9A\xEC\xD9\x65\x03\xD8\xC7\x0E\xE7\x5F\xEB\xF2\xF1\xFC\xC7\x03\xCA\xF2\x3A\x1A\x5F\x66\xF9\xE7\xF1\xDD\x1A\x11\xF6\xD7\x0E\x7B\x54\xF7\x05\xF4\x9E\xEB\x03\x6F\xED\x03\xBF\xED\x7D\x6E\xF5\x09\xFC\xB2\xEF\x03\x6F\xF1\x03\xBF\xEF\x9B\xD0\xF4\x81\x08\xEB\x81\x0B\xA4\xFB\xE6\x02\x0B\x0E\x3F\xED\x3A\x0F\xDB\x81\x62\xA6\xFF\xCF\x03\x0D\x23\xF1\xDF\x3B\x00\xE4\xE2\x14\xBE\xE2\x08\xB1\x2C\x3C\xF8\x02\x1F\xF9\x10\x7C\x01\xBF\xE7\x0E\x01\xFE\x20\x2D\xF6\x34\xEC\x44\x25\xC9\xBE\xE9\xD1\x7D\x07\xE0\xEF\x16\x87\xF0\xF0\xA9\xD2\x1F\x04\xF8\x06\x0A\x10\x12\xF9\xEB\x03\x5C\x43\xF1\xFC\xC3\x04\x18\xF9\x48\x28\xE7\x75\xF1\x10\x1D\xF8\x93\xEC\xD9\x87\x01\xE4\xC3\x13\x7C\xED\x99\xA6\xF9\x95\xF0\xE1\x8B\x02\xE5\xFF\x11\x85\xEA\xE9\xAE\xF9\x97\xEC\xD9\x8F\x02\xE6\xD4\x12\x8B\xE5\xF3\xC0\xF4\xCB\xD3\x04\x3A\xFD\x3B\x0B\x06\x67\x46\xF3\x80\x01\x7D\xF0\xD1\x97\x01", + "\xE8\xE0\x0E\x67\x04\xF4\x84\xDC\x79\xDB\x04\x4A\xF9\x39\x2F\xE9\x9E\xFB\xB8\xA9\xD3\x27\x11\xFA\xCB\x0C\x1A\x0D\xFA\x40\xF0\xC3\xA3\x06\xCE\xE7\x05\xBF\xEF\x1A\x2A\xE5\xA2\xF4\xD6\x93\xC9\x42\x09\x05\x3A\xFD\x15\x3F\xED\x6D\x03\xF6\x9B\xF0\x12\xE1\x08\xAF\x02\xE7\xF3\x05\xDF\xEF\x0D\x2A\xE5\x84\xC3\x08\xC6\x2C\x3C\xF5\x04\x6C\xF3\x25\x28\xCB\x40\x11\xC9\x09\xEB\x88\x3E\xFA\x81\x0A\xA1\x81\xFF\x1C\x20\xFC\x03\x0E\xB9\x24\xCF\x5B\x0C\xF7\xF4\x0D\xE1\xE9\xFC\x29\xD1\x17\x0D\xFD\x00\x17\x93\x83\x08\x50\xD1\xDF\xBB\x07\xC0\xFC\x05\xC9\xF6\x10\x17\xFF\xDF\xE5\xDE\xCC\x13\x1C\x1C\x48\xCF\xF4\xF8\xA0\xFF\xB6\x04\x07\x1C\x4D\x44\xC3\x09\xA3\xC6\xF8\xD2\x0E\x2F\x1C\xFC\xAB\xFA\x21\x3E\xC9\xF8\xD0\x0C\x1B\xFB\x94\x04\x30\x1E\xF8\x86\xC1\x06\x30\x6B\x84\xC4\xE2\x2A\xF8\xFD\x03\x0E\xD3\xDA\xDA\x63\x0C\xFB\xF4\x0C\x57\xFD\xCC\xC0\xFC\xA5\xE4\xCF\x65\x05\xFC\x81\x12\x57\xE8\xFE\xD1\xD7\xED\xC0\x00\x68\x0D\xFC\x8F\x11\x3C\x0B\xE9\x01\x09\xF9\xDE\xE4\x18\xE5\x0D\x55\xFD\x90\x16\x07\xD8\xF8\x00\x1A\xFE\x93\xE1\xBF\xDA\x06\xF7", + "\xE3\x12\x7A\xEB\x7D\xE3\xFF\x58\xFA\xB5\xDF\x07\xF9\xF3\xC1\x3A\xFB\xFD\xCD\xD7\xF7\xF4\x25\x04\x01\xFC\xED\xE9\x30\xE1\x1D\x34\xFF\xEE\x08\x00\x77\xFD\xAD\xAC\xD9\xEE\x03\xFE\x70\x1E\x0C\x00\xFE\x7E\xA2\x54\x9E\x73\x03\x02\x81\x72\x00\x01\x05\x80\xAE\x59\x8A\x68\x0F\x09\x80\xCB\x04\x05\x0C\x00\xA6\x6F\x29\x69\x3F\x00\x01\x83\x07\xD8\x74\xF4\x7C\xDE\x64\x67\x02\x03\x0D\x3D\xFB\x49\x04\xF7\x76\x06\x86\x10\x3C\x74\xA8\x7B\x01\x0E\x01\xB4\x07\x0F\x7A\x08\x83\x10\x07\x7D\x5A\x6C\x03\x07\x02\xA3\x0F\x13\x80\x7D\x79\xA2\x51\x00\x2F\x83\x83\x06\xE2\x6A\x80\x02\x04\x0B\x88\xEA\x56\x00\x35\x81\x90\x0C\x02\x31\x80\x00\x01\x88\x14\x9E\x5B\x00\x37\x31\x74\x7F\x20\x23\x7F\x50\x68\x0C\x7C\x01\x05\x81\x44\x0F\xF8\x7D\xDF\x68\x7A\x1D\x01\x0F\x83\x24\x30\x00\x40\x83\x13\x80\xEF\x41\x04\x22\x02\x14\x8F\x23\x05\x79\x38\x80\x66\x29\xA2\x67\x00\x5A\x80\x95\x08\x03\x00\x81\x52\x74\x8C\x6C\x02\x21\x81\xDD\x04\x0F\x04\x06\xA9\x68\x31\x00\x1A\x80\x1E\x26\x79\x5D\x80\x00\x05\x06\x9A\x6D\x36\x02\x1B\x89\x1C\x04\x01\x40\x80\x9E\x60\xC3", + "\x7B\x00\x4C\x81\xE9\x03\xFE\x5A\x75\xA8\x78\x0F\x01\x06\x81\x01\x37\x32\x19\x38\x04\x34\x7F\x7F\x81\x8A\x63\x04\x21\x81\x48\x01\x21\x8A\x10\x0D\x01\x88\x83\x78\x61\xBF\x4A\x01\x61\x83\x13\x0E\x08\x89\x04\x52\x01\x24\x89\x10\x25\x7D\x0C\x69\x47\x01\x06\x96\x01\x97\x82\x41\x07\x05\x1A\x82\x20\x59\x8A\x68\x05\x21\x81\x5D\x01\x28\x83\x10\x1C\x01\xA4\x81\x89\x54\x9E\x5F\x01\x61\x80\x19\x0A\x0A\x82\x04\xBB\x7A\xFA\x7E\xF6\x68\x71\x66\x01\x18\x8B\x06\x33\x82\x01\x06\x19\x0D\x0A\x82\x04\xEF\x79\x59\x7C\xAF\x21\x81\x72\x00\x2F\x80\x00\x1E\x7B\xB6\x80\x71\x71\xBF\x74\x01\x61\x81\x1E\x06\x0C\xB0\x01\xF4\x7C\x8F\x66\x10\x19\x1B\xE4\x67\x1E\x0D\x07\x86\x04\x7C\x02\x31\x84\xEF\x46\x0F\x15\x19\x53\x66\xF1\x57\x83\xBC\x0D\x91\x62\x10\x1D\x83\xAD\x7E\x0F\x1F\x61\x27\x2B\xA6\x7F\x10\x12\x04\x86\x04\xE7\x81\x39\x86\x34\x09\x81\x02\x04\x35\x81\xBF\x7F\x01\xE0\x82\x40\x00\x08\x06\x83\x76\x03\x81\x7B\x96\x43\x04\xFB\x65\xFC\x62\x08\x35\x83\x3F\x08\xBF\x76\x3C\x3B\x83\x02\x04\xB8\x14\x9E\x43\x02\x00\x84\x95\x03\xF0\x5A\x7A\x04\x85", + "\x40\x08\xB6\x71\x6F\x84\x01\x42\x8D\x1D\x3B\x01\x7C\x78\x96\x62\x10\x0E\x65\xF1\x6D\x21\x02\x11\x83\x0C\x2A\x19\x42\x01\x6D\x24\x67\x86\x01\x42\x87\x08\x06\x83\x17\x7E\xF1\x02\xA6\x42\x04\x33\x19\x23\x73\x47\x27\x84\x60\x71\x3A\x83\x47\x01\x66\x06\x07\x47\x81\xBF\x49\x02\x09\x86\x22\x06\x0C\xBF\x01\x07\x7B\x9B\x68\x12\xAE\x84\x29\x12\x4E\x8D\x12\xAA\x84\x29\x11\x4A\x86\x10\x18\x84\x30\x70\x23\x0B\x11\x8C\x0B\x7A\x82\x40\x0D\x11\xAE\x83\x44\x0F\x8D\x19\x10\x3F\x69\x4C\x85\x42\x0D\x08\x06\x83\xDD\x04\x54\x83\x10\x04\x85\x38\x7F\x51\x8B\x2D\x16\x85\x02\x04\x95\x10\x14\xBE\x10\x5E\x84\x36\x8C\x13\xA0\x85\x0A\x04\xE9\x72\xFD\x50\x02\x09\x85\x24\x06\x0C\x80\x02\x07\x79\xA2\x66\xF9\x69\x68\x93\x01\x42\x84\x09\x06\x83\x81\x03\x81\x7F\x65\x1E\x83\xA6\x72\x56\x82\x2E\x31\x5E\x03\x07\x5D\x81\x15\xA3\x0E\x7C\x86\x40\x0E\x16\xA6\x70\x4F\x13\xA4\x66\x10\x0E\x85\x7F\x84\xEF\x0F\x9A\x46\x04\x8C\x1B\x57\x81\x14\x17\x02\x54\x84\x78\x0D\x18\x83\x85\x29\x69\x26\x0A\x17\xBE\x0B\x93\x87\x40\x0D\xA9\x49\x86\xC8\x0F\x66\x83\x10\x37", + "\x66\x9C\x85\x01\x1E\x19\x82\x04\x66\x84\x1A\x7A\x09\x09\x84\x9B\x02\x31\x8A\xF1\x46\x0F\x94\x1B\xB3\x29\xA2\x5D\x02\x09\x86\x27\x06\x0C\xA0\x7C\xC6\x0C\x68\x87\x15\xA9\x68\xA0\x03\x65\x8F\x2E\x16\x6B\x02\x06\x6D\x84\x18\xA4\x10\xBC\x85\x40\x0D\x1A\xA1\x86\xDE\x0E\xC2\x63\x10\x06\x86\x1B\x74\x09\x14\xB1\x43\x04\x8B\x85\x72\x8B\x42\x1C\x6C\x17\x85\x8A\x61\x0A\x3A\x86\x05\x0C\x74\x81\x10\x33\x6C\xC4\x86\xBC\x08\x1D\x83\x04\x44\x6D\x76\x83\x30\x1B\x87\xA4\x85\x8A\x62\x0A\x09\x84\xA3\x02\x31\x84\x08\x07\x78\x3D\x6D\xE7\x79\xA2\x65\x02\x09\x86\x29\x06\x0C\x85\x02\x07\x79\x77\x87\x1B\xA4\x67\xA8\x00\x75\x83\x25\x0C\x6D\x01\x06\x7C\x8F\x1B\xAB\x10\xF8\x84\x00\x09\x1E\x8E\x87\x43\x11\xD5\x63\x10\x32\x84\x30\x71\x2A\x09\x10\xAA\x02\x91\x85\x72\x04\x20\x82\x04\xCF\x18\x79\x6C\x0A\x36\x87\xF4\x05\x75\x63\x10\x32\x83\x30\x71\x2B\x09\x10\xAE\x02\x09\x8B\x72\x04\x21\x82\x04\x5F\x6D\xFC\x60\x0B\x37\x30\x47\x79\x80\x0B\x6D\x06\x04\x06\x86\x77\x8C\x2C\x23\x88\x03\x07\x43\x80\x20\xB3\x11\x25\x8B\x40\x0E\x9D\x71\x6F\xB3\x01\x86", + "\x82\x2E\x2A\x88\x02\x07\x8B\x80\xC3\x75\x02\x32\x8A\xBF\x08\x6E\x24\x88\x63\x87\x94\x06\x08\x07\x78\x3B\x89\x8A\x8D\x23\xB4\x07\x29\x7E\xF1\x04\x6F\x1E\x84\x29\x6B\x2D\x09\x10\xB8\x02\xC6\x80\x22\x07\xE0\x70\x6D\x03\x04\xBF\x1E\x18\x84\x0D\x50\x8A\x40\x08\x6F\x13\x89\xA5\x0F\x95\x81\x13\xA9\x68\xBA\x01\x42\x8B\x0B\x06\x83\x89\x03\x81\x78\x9E\x51\x89\x43\x89\xE9\x03\x26\x96\x89\x65\x8B\xE8\x02\x25\x86\x04\x91\x6C\x0C\x7D\x0B\x10\x88\x09\x06\x22\x07\xE0\x6B\x89\x13\x89\x8A\x6E\x0B\x06\x83\xC0\x02\x31\x81\xF3\x7D\x68\x77\x6E\x40\x06\x9E\x66\x88\xDB\x09\x9F\x81\x10\x01\x1C\x58\x8B\xE8\x04\x28\xAC\x89\x29\x6A\x30\x00\x27\x86\x04\x8D\x03\x81\x77\x28\xB5\x89\xE4\x67\x30\x06\x0C\x85\x03\xC6\x82\x23\x0F\xDB\x5D\x5F\x06\x07\x9F\x8B\x22\xA9\x10\x98\x8B\x40\x0F\x28\xBB\x87\x43\x12\xE7\x56\x10\x07\x89\x80\x8A\xB8\x01\xB8\x42\x04\xFD\x80\x44\x7B\x28\x81\x09\xA7\x89\x40\x0D\x22\xAC\x6C\xC8\x03\xAA\x8C\x21\x98\x7A\x0A\x04\x8D\x82\xFD\x49\x03\xB2\x89\x40\x02\x09\x3F\x76\xA9\x89\x41\x89\x26\x81\x09\x94\x00\xAF\x85\x2B\xBF\x8A", + "\x43\x0A\x25\x0F\xDB\x55\x1C\x09\x05\xC2\x14\x9E\x4A\x03\x20\x88\xD1\x09\xB8\x43\x04\xC8\x89\xA9\x8E\x2F\x19\x5E\x06\x06\xB2\x81\xBF\x4D\x03\xCD\x89\xE9\x0D\x9F\x43\x04\x6D\x88\xCB\x60\x0D\x39\x8A\x54\x0B\xB6\x81\x0F\xA9\x68\xD1\x02\x31\x83\x0D\x06\x83\x98\x03\x81\x7D\x2D\x81\x04\x1B\x8A\xF4\x75\x0D\x09\x84\xD6\x02\x31\x89\x09\x07\x78\xE6\x5E\x41\x0D\x2B\x92\x7F\xD8\x00\xB8\x8A\x09\x34\x8B\x0A\x07\xAB\x82\xFD\x59\x03\xE0\x88\xD4\x7A\xE9\x75\x8B\x42\x88\x79\x6A\x0D\x20\x8B\x9E\x00\x9F\x76\x75\x09\x04\x3D\x1C\x79\x6B\x0D\x20\x8B\xDD\x07\xFA\x56\x10\x0B\x8C\xD2\x8B\xBB\x0B\xB9\x43\x04\x0D\x8D\xFC\x6C\x0D\x39\x88\xEF\x0B\x85\x63\x10\x29\x1D\xE4\x66\x37\x09\x10\x9F\x03\x1C\x8F\x75\x0E\x31\x82\x04\x6C\x1C\x79\x61\x0E\x09\x84\xE2\x01\xC9\x81\x14\x27\x8C\x01\x04\xE9\x61\xBF\x64\x03\x09\x85\x39\x0E\x32\x8A\x04\x20\x8E\x41\x09\x32\x84\x87\xE7\x03\xCD\x89\x10\x39\x8C\x03\x06\xCC\x8B\x29\x97\x07\xE9\x02\xCF\x8A\x33\x8A\x04\x42\x8C\xA8\x87\x1C\x2B\x03\x46\x8D\xD0\x8A\x10\x20\x68\x15\x8D\xC1\x09\x34\x81\x04\xAD\x6D\xD4\x83", + "\x25\x13\x8D\x00\x00\xDD\x15\x28\xBC\x0E\x50\x8C\x37\x74\x2C\x81\x04\xED\x01\xD3\x82\x10\x32\x1D\x09\x05\xD5\x83\x34\x86\x0D\x64\x8E\x41\x0A\x35\x96\x8D\xF4\x07\xDA\x81\xFC\x69\x68\xEF\x02\x1D\x8B\x1C\x21\x02\xF4\x7E\xDB\x8A\xFC\x71\x6F\xF4\x02\xDC\x83\x1C\x26\x02\x75\x8E\x0B\x79\xA2\x79\x03\x7A\x8F\x71\x0B\x0A\x3D\x8D\xC6\x65\xFC\x6E\x0F\x01\x8E\xD2\x04\x2C\x00\xC6\x24\x5C\x76\x8F\xF6\x7C\xB2\x43\x00\xCB\x47\x07\x86\x10\x36\x02\x8B\x8E\x42\x0D\x38\xA4\x7F\x30\x70\x02\x01\x39\x85\x1E\x95\x8D\x42\x07\x39\xAC\x7F\xA8\x79\x03\x0B\x39\x81\x08\xC2\x00\xE1\x86\x10\x20\x8E\x57\x80\x00\x02\x01\x23\x8E\xA7\x1E\xE9\x80\xEB\x4E\x77\xAC\x8D\x90\x0C\x0C\x2E\x8E\xB9\x78\x79\x6C\x01\x31\x8E\x43\x09\x34\x04\x3B\xB7\x7C\xD2\x7D\x08\x08\x3B\x97\x1F\xBB\x8D\x2B\x70\xC3\x66\x00\xBF\x8C\x95\x0B\x0D\x01\x8F\x24\x81\xEA\x8B\x02\x05\x8F\xDD\x04\x38\x08\x3C\xA9\x68\x30\x00\xF3\x80\x1E\x25\x03\xCF\x8C\x79\x65\x03\x12\x8F\xC9\x06\x3A\x01\x3C\xBA\x80\xA9\x8E\x0E\x08\x3D\x8B\x07\xEF\x03\xF6\x89\xA2\x7F\x00\xDF\x8F\x70\x04\x0F\x22\x8F\xE4", + "\x64\x11\x05\x3E\x87\x07\xF9\x01\xF0\x8B\x0E\xB0\x70\x49\x00\xC3\x5D\x1D\x3E\x03\x07\x7B\xE5\x80\x0F\x92\x7F\x4A\x02\xFC\x88\x21\x35\x8F\x4E\x7D\xFC\x6B\x04\x2B\x8F\x3C\x61\x18\x87\x39\x96\x81\xC2\x81\x25\x70\x40\x97\x07\x05\x02\x00\x9D\x3F\xB0\x70\x55\x03\x01\x97\x71\x4A\x90\x55\x7C\x79\x6A\x05\x0E\x90\x3F\x34\x04\x95\xED\x70\x70\x5F\x00\x05\x95\x89\x56\x90\x51\x75\x8A\x64\x06\x1A\x90\xA2\x44\x07\x9B\x99\x69\x68\x69\x02\xFE\x89\x1C\x1E\x00\x09\x87\xE5\x80\x08\xA9\x8E\x6A\x01\xF1\x8F\x06\x0B\x47\xC6\x3B\x0D\x3C\x38\x92\x82\x30\x71\x1C\x05\x3C\xB6\x01\x30\x93\x85\x52\x43\x96\x8E\x34\x90\xCB\x68\x07\x05\x8F\x7D\x01\x0E\x97\xA4\x7B\x90\x9E\x8C\xB9\x72\xFD\x7F\x01\xC5\x8C\x21\x02\x44\xA0\x58\x44\x92\xDA\x86\x44\xA8\x71\x86\x01\xF1\x8B\x08\x0B\x91\xCC\x4D\x13\x93\x10\x17\x8E\x9C\x83\xBD\x5D\x08\x05\x8F\x92\x00\x15\x92\x10\x3D\x00\x56\x92\x40\x07\x39\x81\x83\x66\x7C\x89\x85\x3C\x99\x02\x5E\x91\x40\x0B\x08\xAB\x4F\x3C\x92\x32\x80\xC3\x5B\x02\xC5\x8C\x28\x09\x46\x80\x00\x49\x01\x18\x91\x10\x23\x91\xE2\x85\xF1\x87\x0A", + "\x33\x91\x96\x80\x1B\x99\x10\x30\x5F\x06\x06\xD9\x8A\x34\xA9\x10\x80\x93\x15\x9F\x35\x9E\x0F\x82\x90\xDC\x79\xA2\x69\x02\x26\x93\xB6\x03\xA2\x5F\x8C\x29\x6A\x2A\x03\x47\xAC\x02\x73\x91\x15\x0B\x24\x8A\x04\x3B\x8C\x0C\x7E\x0A\x33\x91\xB0\x03\x1C\x90\x0A\x86\x0F\x8F\x90\xA5\x39\xA2\x72\x02\x8D\x93\x70\x07\x05\x17\x92\x09\x04\xD6\x85\x94\x73\x02\x73\x91\x2D\x03\x47\xA7\x82\xC6\x0F\x8A\x60\x49\x8B\x7E\x0C\x5C\x2E\x03\x47\x99\x01\x09\x86\x2C\x98\x32\x9C\x89\x0C\x5F\x2E\x03\x47\x9A\x01\xB9\x90\xD2\x89\xA2\x7D\x02\x0C\x5E\x2F\x03\x47\x9B\x01\x5E\x8A\x42\x0F\x77\x32\x73\xA5\x92\xBF\x02\xA3\x73\x92\xF1\x6D\x30\x0C\x70\x42\x03\x73\x90\x17\x09\x4C\x89\x04\x99\x90\xCB\x64\x0C\x0C\x5C\xC5\x03\x1C\x99\x0A\x86\x0F\xCF\x92\x40\x0A\x4A\xB0\x68\xC7\x00\xC3\x58\x0C\x33\x91\x5E\x01\x42\x87\xBC\x42\x04\xCB\x91\xFC\x6A\x0C\x0D\x93\xEF\x0B\x3A\x91\x10\x00\x8D\x2C\x6F\x32\x0C\x70\x4C\x03\x73\x90\x2C\x86\x3C\x32\x93\x00\x01\x36\x92\xFD\x4E\x03\x0C\x5F\x33\x03\x47\xA0\x01\xEA\x92\x30\x94\x9E\x51\x03\x0C\x5E\x34\x03\x47\xA1\x01\x09\x85", + "\xF5\x66\x6D\x51\x60\x46\x30\x07\x66\x6E\x66\x31\xF5\x5D\xD3\x6C\x03\x4B\x48\x86\x64\xCD\x02\x84\x46\x42\x86\x0A\xD4\x69\x51\x86\x0F\x0E\x34\x46\x94\xA1\x5B\x06\xBE\x45\xE3\x3F\x51\xAF\x65\x0E\x36\x24\x32\x51\xA7\x5D\xE5\x05\x28\x38\x6D\x55\x70\x44\x05\xD7\x6D\x13\x3F\x60\x9D\x66\x43\x31\x36\x5C\x05\x4B\x61\xCD\x3A\xC8\x38\x94\xF7\x5B\x4E\x94\x82\x77\x5B\x24\x5C\x5B\x01\x54\x92\x05\x24\x5C\x57\x05\x54\xAC\x60\xF7\x5B\x82\x60\x00\x0B\x68\xFF\x02\x0E\x4C\x15\x0E\x95\x34\x61\x52\x97\x6F\x4B\x49\xAC\x4B\x0F\x37\x83\x41\x05\x3E\x40\x57\x0E\x03\x4E\x34\xA9\x60\x53\x0D\x55\xAA\x3D\x5C\x95\x47\x92\xD8\x05\x95\x63\x95\x50\x05\x56\xAB\x50\x96\x42\x59\x9E\x3E\x6A\x95\x7E\x91\x08\x54\xF2\x71\x50\xBB\x60\x03\x56\x87\x72\x95\x9D\x64\x5D\x95\xC0\x68\x95\x03\x06\x53\x92\xD8\x3A\x95\x65\x60\x5B\x97\x57\xAE\x95\x63\x6A\x5D\x91\x58\x82\x36\x14\x94\x61\x9E\x57\x83\x96\xE3\x4C\x60\x92\x3D\x4A\x41\x78\x97\x62\x9E\x86\x4A\x96\xC1\x49\x63\x91\x59\xA0\x53\x6C\x07\x2E\x56\xC4\x3B\x52\x0E\x34\x66\x9D\x83\x66\x5B\x1A\x48\x5B\x0D\x59\x92", + "\x05\x1A\x4A\x43\x31\x5A\x81\x05\xA3\x95\x3D\x5C\x15\x30\x62\x4E\x04\x6A\x93\x14\x24\x48\x5C\x07\x02\x5C\x16\x2E\x96\x52\x04\xBC\x51\x14\x0B\x50\x0E\x37\x15\x5C\x16\x36\x96\x52\x07\x15\x5C\x15\x3A\x96\x41\x04\x6F\x92\x4A\x70\x06\x02\x67\x50\x0E\x26\x7B\x94\xC3\x95\x50\x05\x5C\xBF\x96\x03\x04\x71\x99\x58\xA7\x52\x53\x6C\x73\x90\xBF\x4E\x97\x37\x96\x9B\x40\x3D\x52\x97\xC6\x95\x5C\x94\x5D\x88\x97\x2C\x64\x76\x9B\x8C\x5A\x97\x1E\x94\x3B\x6D\x51\xAE\x49\x0E\x34\x78\x95\x5D\x86\x0F\x7A\x4B\x77\x96\x5E\xA6\x5B\x6E\x48\x57\x09\x5E\xA3\x97\xD9\x5B\x7A\x9C\x5D\xAA\x97\xE7\x95\x7B\x91\x86\x65\x97\x3D\x68\x7D\x9F\x96\x76\x97\x81\x96\x2D\x52\x45\x61\x07\xFE\x62\x54\x03\x44\x5C\x05\xC5\x4A\x52\x01\x60\xBF\x03\xFD\x59\x50\x09\x90\x4C\x05\x07\x9A\x51\x05\x88\x5C\x05\x85\x62\x43\x34\x2F\x4E\x4C\x3F\x32\xBA\x51\x14\x12\x98\x90\x52\xF4\x44\x61\x95\x52\xD6\x5B\x85\x9B\x48\x59\x98\xF7\x5A\x86\x93\x10\x16\x62\x6C\x04\x88\x92\x15\x16\x62\x0E\x34\x89\x91\x14\x26\x98\x9A\x52\xB5\x58\x28\x47\x05\x2B\x9A\x4F\x08\xF8\x0E\x34\x2F\x99\x50", + "\x01\x63\xA4\x47\xC8\x6F\x26\x59\x6D\x7B\x4E\x4C\x04\x8E\x96\x14\x3C\x32\x5C\x04\x8F\x91\x14\x3E\x98\x2D\x65\xF4\x40\x64\x87\x60\xE6\x5B\x90\x99\xC1\x37\x5B\xD4\x46\x50\x4F\x0F\x0A\x38\x5C\x04\x93\x91\x14\x0E\x99\xE6\x58", }; vl::glr::DecompressSerializedData(compressed, true, dataSolidRows, dataRows, dataBlock, dataRemain, outputStream); } @@ -14829,6 +15057,617 @@ namespace vl::glr::parsergen } +/*********************************************************************** +.\PARSERGEN_PRINTER\SYNTAXASTTOCODE.CPP +***********************************************************************/ + +namespace vl::glr::parsergen +{ + using namespace collections; + using namespace stream; + + namespace ast_printer + { + class SyntaxAstToStringVisitor + : public Object + , protected virtual GlrCondition::IVisitor + , protected virtual GlrSyntax::IVisitor + , protected virtual GlrClause::IVisitor + { + protected: + TextWriter& writer; + vint priority = -1; + + public: + SyntaxAstToStringVisitor( + TextWriter& _writer + ) + : writer(_writer) + { + } + + void VisitClause(Ptr clause) + { + clause->Accept(this); + } + protected: + + void VisitString(const WString& str) + { + writer.WriteString(str); + } + + void VisitConditionalLiteral(const WString& str) + { + writer.WriteString(str); + } + + void VisitSyntax(GlrSyntax* node, vint _priority = 2) + { + vint oldPriority = priority; + priority = _priority; + node->Accept(this); + priority = oldPriority; + } + + void VisitCondition(GlrCondition* node, vint _priority = 2) + { + vint oldPriority = priority; + priority = _priority; + node->Accept(this); + priority = oldPriority; + } + + void VisitSwitchItems(List>& switches) + { + for (auto [switchItem, index] : indexed(switches)) + { + if (index != 0) writer.WriteString(L", "); + if (switchItem->value == GlrSwitchValue::False) writer.WriteChar(L'!'); + writer.WriteString(switchItem->name.value); + } + } + + //////////////////////////////////////////////////////////////////////// + // GlrCondition::IVisitor + //////////////////////////////////////////////////////////////////////// + + void Visit(GlrRefCondition* node) override + { + writer.WriteString(node->name.value); + } + + void Visit(GlrNotCondition* node) override + { + writer.WriteChar(L'!'); + VisitCondition(node->condition.Obj(), 0); + } + + void Visit(GlrAndCondition* node) override + { + if (priority < 1) writer.WriteChar(L'('); + VisitCondition(node->first.Obj(), 1); + writer.WriteString(L"&&"); + VisitCondition(node->second.Obj(), 1); + if (priority < 1) writer.WriteChar(L')'); + } + + void Visit(GlrOrCondition* node) override + { + if (priority < 2) writer.WriteChar(L'('); + VisitCondition(node->first.Obj(), 2); + writer.WriteString(L"||"); + VisitCondition(node->second.Obj(), 2); + if (priority < 2) writer.WriteChar(L')'); + } + + //////////////////////////////////////////////////////////////////////// + // GlrSyntax::IVisitor + //////////////////////////////////////////////////////////////////////// + + void Visit(GlrRefSyntax* node) override + { + switch (node->refType) + { + case GlrRefType::Id: + writer.WriteString(node->literal.value); + break; + case GlrRefType::Literal: + VisitString(node->literal.value); + break; + case GlrRefType::ConditionalLiteral: + VisitConditionalLiteral(node->literal.value); + break; + default:; + } + if (node->field) + { + writer.WriteChar(L':'); + writer.WriteString(node->field.value); + } + } + + void Visit(GlrUseSyntax* node) override + { + writer.WriteChar(L'!'); + writer.WriteString(node->name.value); + } + + void Visit(GlrLoopSyntax* node) override + { + writer.WriteChar(L'{'); + VisitSyntax(node->syntax.Obj()); + if (node->delimiter) + { + writer.WriteString(L" ; "); + VisitSyntax(node->delimiter.Obj()); + } + writer.WriteChar(L'}'); + } + + void Visit(GlrOptionalSyntax* node) override + { + switch (node->priority) + { + case GlrOptionalPriority::PreferTake: + writer.WriteChar(L'+'); + break; + case GlrOptionalPriority::PreferSkip: + writer.WriteChar(L'-'); + break; + case GlrOptionalPriority::Equal: + break; + default:; + } + writer.WriteChar(L'['); + VisitSyntax(node->syntax.Obj()); + writer.WriteChar(L']'); + } + + void Visit(GlrSequenceSyntax* node) override + { + if (priority < 1) writer.WriteChar(L'('); + VisitSyntax(node->first.Obj(), 1); + writer.WriteChar(L' '); + VisitSyntax(node->second.Obj(), 1); + if (priority < 1) writer.WriteChar(L')'); + } + + void Visit(GlrAlternativeSyntax* node) override + { + if (priority < 2) writer.WriteChar(L'('); + VisitSyntax(node->first.Obj(), 2); + writer.WriteString(L" | "); + VisitSyntax(node->second.Obj(), 2); + if (priority < 2) writer.WriteChar(L')'); + } + + void Visit(GlrPushConditionSyntax* node) override + { + writer.WriteString(L"!("); + VisitSwitchItems(node->switches); + writer.WriteString(L"; "); + VisitSyntax(node->syntax.Obj()); + writer.WriteChar(L')'); + } + + void Visit(GlrTestConditionSyntax* node) override + { + writer.WriteString(L"?("); + for (auto [branch, index] : indexed(node->branches)) + { + if (index != 0) writer.WriteString(L" | "); + VisitCondition(branch->condition.Obj()); + writer.WriteString(L": "); + if (branch->syntax) + { + VisitSyntax(branch->syntax.Obj()); + } + else + { + writer.WriteChar(L';'); + } + } + writer.WriteChar(L')'); + } + + //////////////////////////////////////////////////////////////////////// + // GlrClause::IVisitor + //////////////////////////////////////////////////////////////////////// + + void Visit(List>& assignments) + { + if (assignments.Count() > 0) + { + writer.WriteString(L" {"); + for (auto [assignment, index] : indexed(assignments)) + { + if (index != 0) writer.WriteString(L", "); + writer.WriteString(assignment->field.value); + if (assignment->type == GlrAssignmentType::Weak) + { + writer.WriteString(L" ?= "); + } + else + { + writer.WriteString(L" = "); + } + VisitString(assignment->value.value); + } + writer.WriteChar(L'}'); + } + } + + void Visit(GlrCreateClause* node) override + { + VisitSyntax(node->syntax.Obj()); + writer.WriteString(L" as "); + writer.WriteString(node->type.value); + Visit(node->assignments); + } + + void Visit(GlrPartialClause* node) override + { + VisitSyntax(node->syntax.Obj()); + writer.WriteString(L" as partial "); + writer.WriteString(node->type.value); + Visit(node->assignments); + } + + void Visit(GlrReuseClause* node) override + { + VisitSyntax(node->syntax.Obj()); + Visit(node->assignments); + } + + void Visit(GlrLeftRecursionPlaceholderClause* node) override + { + writer.WriteString(L"left_recursion_placeholder("); + for (auto [flag, index] : indexed(node->flags)) + { + if (index != 0) writer.WriteString(L", "); + writer.WriteString(flag->flag.value); + } + writer.WriteChar(L')'); + } + + void VisitLriCont(GlrLeftRecursionInjectContinuation* node) + { + if (node->type == GlrLeftRecursionInjectContinuationType::Optional) + { + writer.WriteChar(L'['); + } + + writer.WriteString(L"left_recursion_inject"); + if (node->configuration == GlrLeftRecursionConfiguration::Multiple) + { + writer.WriteString(L"_multiple"); + } + + writer.WriteChar(L'('); + for (auto [lriFlag, index] : indexed(node->flags)) + { + if (index != 0) writer.WriteString(L", "); + writer.WriteString(lriFlag->flag.value); + } + writer.WriteString(L") "); + + for (auto [target, index] : indexed(node->injectionTargets)) + { + if (index != 0) writer.WriteString(L" | "); + VisitLriTarget(target.Obj()); + } + + if (node->type == GlrLeftRecursionInjectContinuationType::Optional) + { + writer.WriteChar(L']'); + } + } + + void VisitLriTarget(GlrLeftRecursionInjectClause* node) + { + if (node->continuation) + { + writer.WriteChar(L'('); + writer.WriteString(node->rule->literal.value); + writer.WriteChar(L' '); + VisitLriCont(node->continuation.Obj()); + writer.WriteChar(L')'); + } + else + { + writer.WriteString(node->rule->literal.value); + } + } + + void Visit(GlrLeftRecursionInjectClause* node) override + { + writer.WriteChar(L'!'); + writer.WriteString(node->rule->literal.value); + writer.WriteChar(L' '); + VisitLriCont(node->continuation.Obj()); + } + + void Visit(GlrPrefixMergeClause* node) override + { + writer.WriteString(L"!prefix_merge("); + writer.WriteString(node->rule->literal.value); + writer.WriteString(L")"); + } + }; + } + + /*********************************************************************** + SyntaxAstToCode + ***********************************************************************/ + + void SyntaxAstToCode( + Ptr file, + TextWriter& writer + ) + { + if (file->switches.Count() > 0) + { + writer.WriteString(L"switch "); + for (auto [switchItem, index] : indexed(file->switches)) + { + if (index != 0) writer.WriteString(L", "); + if (switchItem->value == GlrSwitchValue::False) writer.WriteChar(L'!'); + writer.WriteString(switchItem->name.value); + } + writer.WriteLine(L";"); + writer.WriteLine(L""); + } + + ast_printer::SyntaxAstToStringVisitor visitor(writer); + for (auto rule : file->rules) + { + if (rule->attPublic) + { + writer.WriteString(L"@public "); + } + if (rule->attParser) + { + writer.WriteString(L"@parser "); + } + writer.WriteString(rule->name.value); + if (rule->type) + { + writer.WriteString(L" : "); + writer.WriteString(rule->type.value); + } + writer.WriteLine(L""); + + for (auto clause : rule->clauses) + { + writer.WriteString(L" ::= "); + visitor.VisitClause(clause); + writer.WriteLine(L""); + } + writer.WriteLine(L" ;"); + writer.WriteLine(L""); + } + } +} + +/*********************************************************************** +.\PARSERGEN_PRINTER\TYPEASTTOCODE.CPP +***********************************************************************/ + +namespace vl::glr::parsergen +{ + using namespace collections; + using namespace stream; + + namespace ast_printer + { + class TypeAstToStringVisitor + : public Object + , protected virtual GlrType::IVisitor + { + protected: + TextWriter& writer; + + public: + TypeAstToStringVisitor( + TextWriter& _writer + ) + : writer(_writer) + { + } + + void VisitType(Ptr clause) + { + clause->Accept(this); + } + protected: + + //////////////////////////////////////////////////////////////////////// + // GlrType::IVisitor + //////////////////////////////////////////////////////////////////////// + + void Visit(GlrEnum* node) override + { + if (node->attPublic) + { + writer.WriteString(L"@public "); + } + writer.WriteString(L"enum "); + writer.WriteString(node->name.value); + writer.WriteLine(L""); + writer.WriteLine(L"{"); + for (auto item : node->items) + { + writer.WriteString(L" "); + writer.WriteString(item->name.value); + writer.WriteLine(L","); + } + writer.WriteLine(L"}"); + } + + void Visit(GlrClass* node) override + { + if (node->attPublic) + { + writer.WriteString(L"@public "); + } + if (node->attAmbiguous) + { + writer.WriteString(L"@ambiguous "); + } + writer.WriteString(L"class "); + writer.WriteString(node->name.value); + if (node->baseClass) + { + writer.WriteString(L" : "); + writer.WriteString(node->baseClass.value); + } + writer.WriteLine(L""); + writer.WriteLine(L"{"); + for (auto prop : node->props) + { + writer.WriteString(L" var "); + writer.WriteString(prop->name.value); + writer.WriteString(L" : "); + switch (prop->propType) + { + case GlrPropType::Token: + writer.WriteString(L"token"); + break; + case GlrPropType::Type: + writer.WriteString(prop->propTypeName.value); + break; + case GlrPropType::Array: + writer.WriteString(prop->propTypeName.value); + writer.WriteString(L"[]"); + break; + } + writer.WriteLine(L";"); + } + writer.WriteLine(L"}"); + } + }; + } + + /*********************************************************************** + TypeAstToCode + ***********************************************************************/ + + void TypeAstToCode( + Ptr file, + TextWriter& writer + ) + { + ast_printer::TypeAstToStringVisitor visitor(writer); + for (auto type : file->types) + { + visitor.VisitType(type); + writer.WriteLine(L""); + } + } +} + +/*********************************************************************** +.\PARSERGEN_PRINTER\TYPESYMBOLTOAST.CPP +***********************************************************************/ + +namespace vl::glr::parsergen +{ + /*********************************************************************** + TypeAstToCode + ***********************************************************************/ + + Ptr TypeSymbolToAst( + const AstSymbolManager& manager, + bool createGeneratedTypes + ) + { + auto generated = Ptr(new GlrAstFile); + for (auto groupName : manager.FileGroupOrder()) + { + auto group = manager.FileGroups()[groupName]; + for (auto typeName : group->SymbolOrder()) + { + auto symbol = group->Symbols()[typeName]; + + if (auto enumSymbol = dynamic_cast(symbol)) + { + auto enumType = Ptr(new GlrEnum); + generated->types.Add(enumType); + + if (enumSymbol->isPublic) enumType->attPublic.value = L"@public"; + enumType->name.value = enumSymbol->Name(); + + for (auto itemName : enumSymbol->ItemOrder()) + { + auto itemSymbol = enumSymbol->Items()[itemName]; + + auto enumItem = Ptr(new GlrEnumItem); + enumType->items.Add(enumItem); + + enumItem->name.value = itemSymbol->Name(); + } + } + + if (auto classSymbol = dynamic_cast(symbol)) + { + if (!createGeneratedTypes && classSymbol->classType != AstClassType::Defined) + { + continue; + } + + auto classType = Ptr(new GlrClass); + generated->types.Add(classType); + + if (classSymbol->isPublic) classType->attPublic.value = L"@public"; + if (classSymbol->derivedClass_ToResolve) classType->attAmbiguous.value = L"@ambiguous"; + classType->name.value = classSymbol->Name(); + + if (classSymbol->baseClass) + { + if (!createGeneratedTypes && classSymbol->baseClass->classType == AstClassType::Generated_Common) + { + classType->baseClass.value = classSymbol->baseClass->baseClass->Name(); + } + else + { + classType->baseClass.value = classSymbol->baseClass->Name(); + } + } + + if (!createGeneratedTypes && classSymbol->derivedClass_Common) + { + classSymbol = classSymbol->derivedClass_Common; + } + for (auto propName : classSymbol->PropOrder()) + { + auto propSymbol = classSymbol->Props()[propName]; + + auto classProp = Ptr(new GlrClassProp); + classType->props.Add(classProp); + + classProp->name.value = propSymbol->Name(); + switch (propSymbol->propType) + { + case AstPropType::Token: + classProp->propType = GlrPropType::Token; + break; + case AstPropType::Type: + classProp->propType = GlrPropType::Type; + break; + case AstPropType::Array: + classProp->propType = GlrPropType::Array; + break; + } + if (propSymbol->propSymbol) classProp->propTypeName.value = propSymbol->propSymbol->Name(); + } + } + } + } + return generated; + } +} + /*********************************************************************** .\SYNTAX\SYNTAXCPPGEN.CPP ***********************************************************************/ @@ -14860,9 +15699,9 @@ GenerateSyntaxFileNames { return GenerateToStream([&](StreamWriter& writer) { - WriteNssName(astType->Owner()->cppNss, writer); + WriteNssName(astType->Owner()->Owner()->cppNss, writer); writer.WriteString(L"::"); - writer.WriteString(astType->Owner()->classPrefix); + writer.WriteString(astType->Owner()->Owner()->classPrefix); writer.WriteString(astType->Name()); }); } @@ -15016,7 +15855,7 @@ WriteSyntaxCppFile if ( output->classIds.Count() == 0 || From(output->classIds.Keys()) - .Where([](auto c) { return c->ambiguousDerivedClass != nullptr; }) + .Where([](auto c) { return c->derivedClass_ToResolve != nullptr; }) .IsEmpty() ) { @@ -15177,9 +16016,10 @@ EdgeSymbol RuleSymbol ***********************************************************************/ - RuleSymbol::RuleSymbol(SyntaxSymbolManager* _ownerManager, const WString& _name) + RuleSymbol::RuleSymbol(SyntaxSymbolManager* _ownerManager, const WString& _name, vint _fileIndex) : ownerManager(_ownerManager) , name(_name) + , fileIndex(_fileIndex) { } @@ -15192,10 +16032,10 @@ SyntaxSymbolManager { } - RuleSymbol* SyntaxSymbolManager::CreateRule(const WString& name, ParsingTextRange codeRange) + RuleSymbol* SyntaxSymbolManager::CreateRule(const WString& name, vint fileIndex, bool isPublic, bool isParser, ParsingTextRange codeRange) { CHECK_ERROR(states.Count() + edges.Count() == 0, L"vl::gre::parsergen::SyntaxSymbolManager::CreateRule(const WString&)#Cannot create new rules after building the automaton."); - auto rule = new RuleSymbol(this, name); + auto rule = new RuleSymbol(this, name, fileIndex); if (!rules.Add(name, rule)) { AddError( @@ -15204,6 +16044,8 @@ SyntaxSymbolManager name ); } + rule->isPublic = isPublic; + rule->isParser = isParser; return rule; } @@ -15979,32 +16821,37 @@ CreateParserGenRuleSyntax void CreateParserGenRuleSyntax(AstSymbolManager& ast, SyntaxSymbolManager& manager) { + auto createRule = [&](const wchar_t* ruleName) + { + return manager.CreateRule(WString::Unmanaged(ruleName), -1, false, false); + }; + manager.name = L"RuleParser"; - auto _cond0 = manager.CreateRule(L"Cond0"); - auto _cond1 = manager.CreateRule(L"Cond1"); - auto _cond2 = manager.CreateRule(L"Cond2"); - auto _cond = manager.CreateRule(L"Cond"); - auto _switchItem = manager.CreateRule(L"SwitchItem"); - auto _switches = manager.CreateRule(L"Switches"); - auto _optionalBody = manager.CreateRule(L"OptionalBody"); - auto _testBranch = manager.CreateRule(L"TestBranch"); - auto _token = manager.CreateRule(L"Token"); - auto _syntax0 = manager.CreateRule(L"Syntax0"); - auto _syntax1 = manager.CreateRule(L"Syntax1"); - auto _syntax2 = manager.CreateRule(L"Syntax2"); - auto _syntax = manager.CreateRule(L"Syntax"); - auto _assignmentOp = manager.CreateRule(L"AssignmentOp"); - auto _assignment = manager.CreateRule(L"Assignment"); - auto _clause = manager.CreateRule(L"Clause"); - auto _placeholder = manager.CreateRule(L"Placeholder"); - auto _ruleName = manager.CreateRule(L"RuleName"); - auto _lriConfig = manager.CreateRule(L"LriConfig"); - auto _lriContinuationBody = manager.CreateRule(L"LriContinuationBody"); - auto _lriContinuation = manager.CreateRule(L"LriContinuation"); - auto _lriTarget = manager.CreateRule(L"LriTarget"); - auto _rule = manager.CreateRule(L"Rule"); - auto _file = manager.CreateRule(L"File"); + auto _cond0 = createRule(L"Cond0"); + auto _cond1 = createRule(L"Cond1"); + auto _cond2 = createRule(L"Cond2"); + auto _cond = createRule(L"Cond"); + auto _switchItem = createRule(L"SwitchItem"); + auto _switches = createRule(L"Switches"); + auto _optionalBody = createRule(L"OptionalBody"); + auto _testBranch = createRule(L"TestBranch"); + auto _token = createRule(L"Token"); + auto _syntax0 = createRule(L"Syntax0"); + auto _syntax1 = createRule(L"Syntax1"); + auto _syntax2 = createRule(L"Syntax2"); + auto _syntax = createRule(L"Syntax"); + auto _assignmentOp = createRule(L"AssignmentOp"); + auto _assignment = createRule(L"Assignment"); + auto _clause = createRule(L"Clause"); + auto _placeholder = createRule(L"Placeholder"); + auto _ruleName = createRule(L"RuleName"); + auto _lriConfig = createRule(L"LriConfig"); + auto _lriContinuationBody = createRule(L"LriContinuationBody"); + auto _lriContinuation = createRule(L"LriContinuation"); + auto _lriTarget = createRule(L"LriTarget"); + auto _rule = createRule(L"Rule"); + auto _file = createRule(L"File"); _switches->isPartial = true; _optionalBody->isPartial = true; @@ -16014,7 +16861,7 @@ CreateParserGenRuleSyntax _lriContinuationBody->isPartial = true; _file->isParser = true; - _file->ruleType = dynamic_cast(ast.Symbols()[L"SyntaxFile"]); + _file->ruleType = dynamic_cast(ast.Symbols()[L"SyntaxFile"][0]); using T = ParserGenTokens; using C = ParserGenClasses; @@ -16209,7 +17056,7 @@ CreateParserGenRuleSyntax /////////////////////////////////////////////////////////////////////////////////// // ["@public"] ["@parser"] ID:name {"::=" Clause:clauses} ";" as Rule - Clause{ _rule } = create(opt(tok(T::ATT_PUBLIC, F::Rule_attParser)) + opt(tok(T::ATT_PARSER, F::Rule_attParser)) + tok(T::ID, F::Rule_name) + opt(tok(T::COLON) + tok(T::ID, F::Rule_type)) + loop(tok(T::INFER) + rule(_clause, F::Rule_clauses)) + tok(T::SEMICOLON), C::Rule); + Clause{ _rule } = create(opt(tok(T::ATT_PUBLIC, F::Rule_attPublic)) + opt(tok(T::ATT_PARSER, F::Rule_attParser)) + tok(T::ID, F::Rule_name) + opt(tok(T::COLON) + tok(T::ID, F::Rule_type)) + loop(tok(T::INFER) + rule(_clause, F::Rule_clauses)) + tok(T::SEMICOLON), C::Rule); // [Switches] Rule:rules {Rule:rules} as SyntaxFile Clause{ _file } = create(opt(prule(_switches)) + rule(_rule, F::SyntaxFile_rules) + loop(rule(_rule, F::SyntaxFile_rules)), C::SyntaxFile); @@ -16240,22 +17087,27 @@ CreateParserGenTypeSyntax void CreateParserGenTypeSyntax(AstSymbolManager& ast, SyntaxSymbolManager& manager) { + auto createRule = [&](const wchar_t* ruleName) + { + return manager.CreateRule(WString::Unmanaged(ruleName), -1, false, false); + }; + manager.name = L"TypeParser"; - auto _enumItem = manager.CreateRule(L"EnumItem"); - auto _enum = manager.CreateRule(L"Enum"); - auto _classPropType = manager.CreateRule(L"ClassPropType"); - auto _classProp = manager.CreateRule(L"classProp"); - auto _classBody = manager.CreateRule(L"ClassBody"); - auto _class = manager.CreateRule(L"Class"); - auto _type = manager.CreateRule(L"Type"); - auto _file = manager.CreateRule(L"File"); + auto _enumItem = createRule(L"EnumItem"); + auto _enum = createRule(L"Enum"); + auto _classPropType = createRule(L"ClassPropType"); + auto _classProp = createRule(L"classProp"); + auto _classBody = createRule(L"ClassBody"); + auto _class = createRule(L"Class"); + auto _type = createRule(L"Type"); + auto _file = createRule(L"File"); _classPropType->isPartial = true; _classBody->isPartial = true; _file->isParser = true; - _file->ruleType = dynamic_cast(ast.Symbols()[L"AstFile"]); + _file->ruleType = dynamic_cast(ast.Symbols()[L"AstFile"][0]); using T = ParserGenTokens; using C = ParserGenClasses; @@ -17089,7 +17941,7 @@ SyntaxSymbolManager::FixLeftRecursionInjectEdge return; } - // calculate all acceptable input from inject edge + // calculate all acceptable Token input from inject edge // key: // token // the number of return edges carried into this edge, at least 1 @@ -17101,6 +17953,13 @@ SyntaxSymbolManager::FixLeftRecursionInjectEdge using InputValue = Tuple; Group acceptableInputs; + // calculate all acceptable Ending input from inject edge + // value: + // index of placeholder edge + // the additional Ending edge + using EndingInputValue = Pair; + List acceptableEndingInputs; + for(auto [placeholderEdge, index] : indexed(placeholderEdges)) { auto& endingStates = endingStatesArray[index]; @@ -17119,6 +17978,92 @@ SyntaxSymbolManager::FixLeftRecursionInjectEdge { case EdgeInputType::Ending: endingEdge = outEdge; + if (returnEdge == injectEdge) + { + // all possible Ending input are comsumed + // an ending edge should be created if + // the injection edge cannot be skipped + // the injection edge to state has Ending input + // an optional injection can be skipped + // a non-optional injection can be skipped by surrounding syntax + + auto endingEdgeAfterInject = From(injectEdge->To()->OutEdges()) + .Where([](auto edge) { return edge->input.type == EdgeInputType::Ending; }) + .First(nullptr); + if (endingEdgeAfterInject) + { + // find if there is a state in the same rule that looks like: + // +-------------------(ending)---------------------+ + // | | + // S -+ +->E + // | | + // +-{-(leftrec)-> X} -(lri:ThisEdge)-> T -(ending)-+ + // or + // +-(same rule)-> Y -----------------(ending)------------------+ + // | | + // S -+ +->E + // | | + // +-(same rule)-{-(leftrec)-> X} -(lri:ThisEdge)-> T -(ending)-+ + + List visiting; + SortedList visited; + visiting.Add(injectEdge->From()); + + // TODO: (enumerable) visiting/visited + for (vint i = 0; i < visiting.Count(); i++) + { + auto visitingState = visiting[i]; + if (visited.Contains(visitingState)) continue; + visited.Add(visitingState); + + for (auto siblingEdge : visitingState->OutEdges()) + { + if (siblingEdge->input.type == EdgeInputType::Ending) + { + goto SKIP_SEARCHING; + } + } + + for (auto commingEdge : visitingState->InEdges()) + { + if (commingEdge->From()->Rule() != injectEdge->From()->Rule()) continue; + + switch (commingEdge->input.type) + { + case EdgeInputType::LeftRec: + visiting.Add(commingEdge->From()); + break; + case EdgeInputType::Rule: + { + auto expectedReturnRule = commingEdge->input.rule; + for (auto siblingCommingEdge : commingEdge->From()->OutEdges()) + { + if (siblingCommingEdge == commingEdge) continue; + if (siblingCommingEdge->input.type != EdgeInputType::Rule) continue; + if (siblingCommingEdge->input.rule != expectedReturnRule) continue; + + if (!From(siblingCommingEdge->To()->OutEdges()) + .Where([](auto edge) { return edge->input.type == EdgeInputType::Ending; }) + .IsEmpty()) + { + goto SKIP_SEARCHING; + } + } + } + break; + default:; + } + } + } + + { + // if there is no such state + // an Ending edge is needed + acceptableEndingInputs.Add({ index,endingEdgeAfterInject }); + } + SKIP_SEARCHING:; + } + } break; // find if there is any LeftRec from this state case EdgeInputType::LeftRec: @@ -17143,12 +18088,67 @@ SyntaxSymbolManager::FixLeftRecursionInjectEdge if (!endingEdge) { - // stop searching if any Token edge are found + // stop searching if there is no Ending input + // since there will be no more {Ending} Token edge to compact break; } } } + auto prepareLriEdgeInstructions = [&](vint placeholderIndex, vint returnEdgeCount, List& instructionPrefix) + { + auto placeholderEdge = placeholderEdges[placeholderIndex]; + auto& endingStates = endingStatesArray[placeholderIndex]; + auto& returnEdges = returnEdgesArray[placeholderIndex]; + + // search for all possible "LrPlaceholder {Ending} LeftRec Token" transitions + // for each transition, compact edges and put injectEdge properly in returnEdges + // here insBeforeInput has been ensured to be: + // EndObject + // LriStore + // DelayFieldAssignment + // placeholderEdge->insBeforeInput + // LriFetch + // loop {endingEdge->insBeforeInput returnEdge->insAfterInput} + // --LeftRec--> ... + + // EndObject is for the ReopenObject in the use rule transition before + // DelayFieldAssignment is for the ReopenObject in injectEdge->insAfterInput + // injectEdge is the last returnEdge + + // there is no instruction in injectEdge->insBeforeInput + instructionPrefix.Add({ AstInsType::EndObject }); + instructionPrefix.Add({ AstInsType::LriStore }); + instructionPrefix.Add({ AstInsType::DelayFieldAssignment }); + CopyFrom(instructionPrefix, placeholderEdge->insBeforeInput, true); + instructionPrefix.Add({ AstInsType::LriFetch }); + + // TODO: (enumerable) foreach:reversed + for (vint i = returnEdges.Count() - 1; i >= returnEdgeCount; i--) + { + auto endingState = endingStates[i]; + auto returnEdge = returnEdges[i]; + auto endingEdge = From(endingState->OutEdges()) + .Where([](auto edge) { return edge->input.type == EdgeInputType::Ending; }) + .First(); + + CopyFrom(instructionPrefix, endingEdge->insBeforeInput, true); + CopyFrom(instructionPrefix, returnEdge->insAfterInput, true); + } + }; + + for (auto [placeholderIndex, endingEdgeAfterInject] : acceptableEndingInputs) + { + auto newEdge = Ptr(new EdgeSymbol(injectEdge->From(), endingEdgeAfterInject->To())); + edges.Add(newEdge); + newEdge->input = endingEdgeAfterInject->input; + newEdge->importancy = endingEdgeAfterInject->importancy; + + prepareLriEdgeInstructions(placeholderIndex, 0, newEdge->insBeforeInput); + CopyFrom(newEdge->insBeforeInput, endingEdgeAfterInject->insBeforeInput, true); + CopyFrom(newEdge->insBeforeInput, endingEdgeAfterInject->insAfterInput, true); + } + // TODO: (enumerable) foreach on group for (auto [input, inputIndex] : indexed(acceptableInputs.Keys())) { @@ -17226,88 +18226,29 @@ SyntaxSymbolManager::FixLeftRecursionInjectEdge // convert reminaings for (auto [placeholderIndex, lrEdge, tokenEdge] : placeholderRecords) { - auto placeholderEdge = placeholderEdges[placeholderIndex]; - auto& endingStates = endingStatesArray[placeholderIndex]; - auto& returnEdges = returnEdgesArray[placeholderIndex]; - - // search for all possible "LrPlaceholder {Ending} LeftRec Token" transitions - // for each transition, compact edges and put injectEdge properly in returnEdges - // here insBeforeInput has been ensured to be: - // EndObject - // LriStore - // DelayFieldAssignment - // placeholderEdge->insBeforeInput - // LriFetch - // loop {endingEdge->insBeforeInput returnEdge->insAfterInput} - // --LeftRec--> ... - - // EndObject is for the ReopenObject in the use rule transition before - // DelayFieldAssignment is for the ReopenObject in injectEdge->insAfterInput - // injectEdge is the last returnEdge - - List instructionPrefix; - // there is no instruction in injectEdge->insBeforeInput - instructionPrefix.Add({ AstInsType::EndObject }); - instructionPrefix.Add({ AstInsType::LriStore }); - instructionPrefix.Add({ AstInsType::DelayFieldAssignment }); - CopyFrom(instructionPrefix, placeholderEdge->insBeforeInput, true); - instructionPrefix.Add({ AstInsType::LriFetch }); - - // TODO: (enumerable) foreach:reversed - for (vint i = returnEdges.Count() - 1; i >= returnEdgeCount; i--) - { - auto endingState = endingStates[i]; - auto returnEdge = returnEdges[i]; - auto endingEdge = From(endingState->OutEdges()) - .Where([](auto edge) { return edge->input.type == EdgeInputType::Ending; }) - .First(); - - CopyFrom(instructionPrefix, endingEdge->insBeforeInput, true); - CopyFrom(instructionPrefix, returnEdge->insAfterInput, true); - } + auto newEdge = Ptr(new EdgeSymbol(injectEdge->From(), tokenEdge->To())); + edges.Add(newEdge); + newEdge->input = tokenEdge->input; + newEdge->importancy = tokenEdge->importancy; + CopyFrom(newEdge->returnEdges, From(returnEdgesArray[placeholderIndex]).Take(returnEdgeCount), true); + CopyFrom(newEdge->returnEdges, tokenEdge->returnEdges, true); + prepareLriEdgeInstructions(placeholderIndex, returnEdgeCount, newEdge->insBeforeInput); if (lrEdge) { - auto newEdge = Ptr(new EdgeSymbol(injectEdge->From(), tokenEdge->To())); - edges.Add(newEdge); - - newEdge->input = tokenEdge->input; - newEdge->importancy = tokenEdge->importancy; - CopyFrom(newEdge->returnEdges, From(returnEdges).Take(returnEdgeCount), true); - CopyFrom(newEdge->returnEdges, tokenEdge->returnEdges, true); - // newEdge consumes a token // lrEdge->insAfterInput happens before consuming this token // so it should be copied to newEdge->insBeforeInput - CopyFrom(newEdge->insBeforeInput, instructionPrefix, true); CopyFrom(newEdge->insBeforeInput, lrEdge->insBeforeInput, true); CopyFrom(newEdge->insBeforeInput, lrEdge->insAfterInput, true); - CopyFrom(newEdge->insBeforeInput, tokenEdge->insBeforeInput, true); - - CopyFrom(newEdge->insAfterInput, tokenEdge->insAfterInput, true); - } - else - { - auto newEdge = Ptr(new EdgeSymbol(injectEdge->From(), tokenEdge->To())); - edges.Add(newEdge); - - newEdge->input = tokenEdge->input; - newEdge->importancy = tokenEdge->importancy; - CopyFrom(newEdge->returnEdges, From(returnEdges).Take(returnEdgeCount), true); - CopyFrom(newEdge->returnEdges, tokenEdge->returnEdges, true); - - // newEdge consumes a token - // lrEdge->insAfterInput happens before consuming this token - // so it should be copied to newEdge->insBeforeInput - CopyFrom(newEdge->insBeforeInput, instructionPrefix, true); - CopyFrom(newEdge->insBeforeInput, tokenEdge->insBeforeInput, true); - CopyFrom(newEdge->insAfterInput, tokenEdge->insAfterInput, true); } + CopyFrom(newEdge->insBeforeInput, tokenEdge->insBeforeInput, true); + CopyFrom(newEdge->insAfterInput, tokenEdge->insAfterInput, true); } } // report an error if nothing is created - if (acceptableInputs.Count() == 0) + if (acceptableInputs.Count() == 0 && acceptableEndingInputs.Count() == 0) { AddError( ParserErrorType::LeftRecursionInjectHasNoContinuation, diff --git a/Import/VlppGlrParserCompiler.h b/Import/VlppGlrParserCompiler.h index e5e03c48..0321ed5b 100644 --- a/Import/VlppGlrParserCompiler.h +++ b/Import/VlppGlrParserCompiler.h @@ -9,7 +9,7 @@ DEVELOPER: Zihan Chen(vczh) #include "VlppRegex.h" /*********************************************************************** -.\PARSERGEN\PARSERSYMBOL.H +.\PARSERGEN_GLOBAL\PARSERSYMBOL.H ***********************************************************************/ /*********************************************************************** Author: Zihan Chen (vczh) @@ -78,18 +78,21 @@ ParserSymbolManager #define GLR_PARSER_ERROR_LIST(ERROR_ITEM)\ /* AstSymbolManager */\ + ERROR_ITEM(DuplicatedFileGroup, fileGroupName)\ ERROR_ITEM(DuplicatedFile, fileName)\ - ERROR_ITEM(FileDependencyNotExists, fileName, dependency)\ - ERROR_ITEM(FileCyclicDependency, fileName, dependency)\ - ERROR_ITEM(DuplicatedSymbol, fileName, symbolName)\ - ERROR_ITEM(DuplicatedSymbolGlobally, fileName, symbolName, anotherFileName)\ + ERROR_ITEM(FileGroupDependencyNotExists, fileGroupName, dependency)\ + ERROR_ITEM(FileGroupCyclicDependency, fileGroupName, dependency)\ + ERROR_ITEM(DuplicatedSymbolInFile, fileName, symbolName)\ + ERROR_ITEM(DuplicatedSymbolInFileGroup, fileName, symbolName, anotherFileName)\ ERROR_ITEM(DuplicatedClassProp, fileName, className, propName)\ ERROR_ITEM(DuplicatedEnumItem, fileName, enumName, propName)\ ERROR_ITEM(BaseClassNotExists, fileName, className, typeName)\ ERROR_ITEM(BaseClassNotClass, fileName, className, typeName)\ + ERROR_ITEM(BaseClassNotPublic, fileName, className, typeName)\ ERROR_ITEM(BaseClassCyclicDependency, fileName, className)\ ERROR_ITEM(FieldTypeNotExists, fileName, className, propName)\ ERROR_ITEM(FieldTypeNotClass, fileName, className, propName)\ + ERROR_ITEM(FieldTypeNotPublic, fileName, className, propName)\ /* LexerSymbolManager */\ ERROR_ITEM(InvalidTokenDefinition, code)\ ERROR_ITEM(DuplicatedToken, tokenName)\ @@ -105,9 +108,11 @@ ParserSymbolManager ERROR_ITEM(LeftRecursionInjectHasNoContinuation, ruleName, placeholder, targetRuleName)\ /* SyntaxAst(ResolveName) */\ ERROR_ITEM(RuleNameConflictedWithToken, ruleName)\ + ERROR_ITEM(TypeNotUniqueInRule, ruleName, name)\ ERROR_ITEM(TypeNotExistsInRule, ruleName, name)\ ERROR_ITEM(TypeNotClassInRule, ruleName, name)\ ERROR_ITEM(TokenOrRuleNotExistsInRule, ruleName, name)\ + ERROR_ITEM(ReferencedRuleNotPublicInRuleOfDifferentFile, ruleName, name)\ ERROR_ITEM(LiteralNotValidToken, ruleName, name)\ ERROR_ITEM(LiteralIsDiscardedToken, ruleName, name)\ ERROR_ITEM(ConditionalLiteralNotValidToken, ruleName, name)\ @@ -171,7 +176,6 @@ ParserSymbolManager ERROR_ITEM(PartialRuleIndirectlyBeginsWithPrefixMerge, ruleName, prefixMergeRule)\ ERROR_ITEM(ClausePartiallyIndirectlyBeginsWithPrefixMergeAndLiteral, ruleName, prefixMergeRule, literal)\ ERROR_ITEM(ClausePartiallyIndirectlyBeginsWithPrefixMergeAndRule, ruleName, prefixMergeRule, literal)\ - ERROR_ITEM(RuleDeductToPrefixMergeInNonSimpleUseClause, ruleName, prefixMergeRule, byRule)\ /* SyntaxAst(RewriteSyntax_PrefixMerge, prefix_merge) */\ ERROR_ITEM(PrefixExtractionAffectedRuleReferencedAnother, ruleName, conflictedRule, prefixRule) /* During left_recursion_inject clause generation, if prefix extracted affected the process, all !prefixRule clauses where prefixRule is the prefix of conflictedRule in any !conflictedRule clauses, prefixRule should not be affected */\ @@ -184,6 +188,7 @@ ParserSymbolManager enum class ParserDefFileType { + AstGroup, Ast, Lexer, Syntax, @@ -275,6 +280,7 @@ namespace vl class AstEnumSymbol; class AstClassSymbol; class AstDefFile; + class AstDefFileGroup; class AstSymbolManager; /*********************************************************************** @@ -290,8 +296,8 @@ AstSymbol AstSymbol(AstDefFile* _file, const WString& _name); public: bool isPublic = false; - AstDefFile* Owner() { return ownerFile; } - const WString& Name() { return name; } + AstDefFile* Owner() const { return ownerFile; } + const WString& Name() const { return name; } }; /*********************************************************************** @@ -308,7 +314,7 @@ AstEnumSymbol public: vint value = 0; - AstEnumSymbol* Parent() { return parent; } + AstEnumSymbol* Parent() const { return parent; } }; class AstEnumSymbol : public AstSymbol @@ -320,8 +326,9 @@ AstEnumSymbol AstEnumSymbol(AstDefFile* _file, const WString& _name); public: AstEnumItemSymbol* CreateItem(const WString& itemName, ParsingTextRange codeRange = {}); - const auto& Items() { return items.map; } - const auto& ItemOrder() { return items.order; } + + const auto& Items() const { return items.map; } + const auto& ItemOrder() const { return items.order; } }; /*********************************************************************** @@ -346,10 +353,17 @@ AstClassSymbol AstPropType propType = AstPropType::Token; AstSymbol* propSymbol = nullptr; - AstClassSymbol* Parent() { return parent; } + AstClassSymbol* Parent() const { return parent; } bool SetPropType(AstPropType _type, const WString& typeName = WString::Empty, ParsingTextRange codeRange = {}); }; + enum class AstClassType + { + Defined, + Generated_ToResolve, + Generated_Common, + }; + class AstClassSymbol : public AstSymbol { friend class AstDefFile; @@ -358,15 +372,20 @@ AstClassSymbol AstClassSymbol(AstDefFile* _file, const WString& _name); public: + AstClassType classType = AstClassType::Defined; AstClassSymbol* baseClass = nullptr; - AstClassSymbol* ambiguousDerivedClass = nullptr; collections::List derivedClasses; + + AstClassSymbol* derivedClass_ToResolve = nullptr; + AstClassSymbol* derivedClass_Common = nullptr; bool SetBaseClass(const WString& typeName, ParsingTextRange codeRange = {}); - AstClassSymbol* CreateAmbiguousDerivedClass(ParsingTextRange codeRange); + AstClassSymbol* CreateDerivedClass_ToResolve(ParsingTextRange codeRange); + AstClassSymbol* CreateDerivedClass_Common(ParsingTextRange codeRange); AstClassPropSymbol* CreateProp(const WString& propName, ParsingTextRange codeRange = {}); - const auto& Props() { return props.map; } - const auto& PropOrder() { return props.order; } + + const auto& Props() const { return props.map; } + const auto& PropOrder() const { return props.order; } }; extern AstClassSymbol* FindCommonBaseClass(AstClassSymbol* c1, AstClassSymbol* c2); @@ -378,39 +397,73 @@ AstDefFile class AstDefFile : public Object { - friend class AstSymbolManager; - + friend class AstDefFileGroup; using DependenciesList = collections::List; using StringItems = collections::List; protected: - ParserSymbolManager* global = nullptr; - AstSymbolManager* ownerManager = nullptr; + AstDefFileGroup* ownerGroup = nullptr; WString name; MappedOwning symbols; template T* CreateSymbol(const WString& symbolName, ParsingTextRange codeRange); - AstDefFile(ParserSymbolManager* _global, AstSymbolManager* _ownerManager, const WString& _name); + AstDefFile(AstDefFileGroup* _ownerGroup, const WString& _name); public: - DependenciesList dependencies; - StringItems cppNss; - StringItems refNss; - WString classPrefix; + AstDefFileGroup* Owner() const { return ownerGroup; } + const WString& Name() const { return name; } + AstEnumSymbol* CreateEnum(const WString& symbolName, bool isPublic = false, ParsingTextRange codeRange = {}); + AstClassSymbol* CreateClass(const WString& symbolName, bool isPublic = false, ParsingTextRange codeRange = {}); - AstSymbolManager* Owner() { return ownerManager; } - const WString& Name() { return name; } - bool AddDependency(const WString& dependency, ParsingTextRange codeRange = {}); - AstEnumSymbol* CreateEnum(const WString& symbolName, ParsingTextRange codeRange = {}); - AstClassSymbol* CreateClass(const WString& symbolName, ParsingTextRange codeRange = {}); - const auto& Symbols() { return symbols.map; } - const auto& SymbolOrder() { return symbols.order; } + const auto& Symbols() const { return symbols.map; } + const auto& SymbolOrder() const { return symbols.order; } template - void AddError(ParserErrorType type, ParsingTextRange codeRange, TArgs&&... args) + void AddError(ParserErrorType type, ParsingTextRange codeRange, TArgs&&... args); + }; + +/*********************************************************************** +AstDefFileGroup +***********************************************************************/ + + class AstDefFileGroup : public Object + { + friend class AstDefFile; + friend class AstSymbolManager; + using DependenciesList = collections::List; + using StringItems = collections::List; + using SymbolMap = collections::Dictionary; + protected: + AstSymbolManager* ownerManager = nullptr; + WString name; + MappedOwning files; + SymbolMap symbolMap; + + AstDefFileGroup(AstSymbolManager* _ownerManager, const WString& _name); + public: + DependenciesList dependencies; + StringItems cppNss; + StringItems refNss; + WString classPrefix; + + AstSymbolManager* Owner() const { return ownerManager; } + const WString& Name() const { return name; } + bool AddDependency(const WString& dependency, ParsingTextRange codeRange = {}); + AstDefFile* CreateFile(const WString& name); + + const auto& Files() const { return files.map; } + const auto& FileOrder() const { return files.order; } + const auto& Symbols() const { return symbolMap; } + collections::LazyList SymbolOrder() { - global->AddError(type, { ParserDefFileType::Ast,name,codeRange }, std::forward(args)...); + return From(files.order) + .Select([this](const WString& fileName) { return files.map[fileName]; }) + .SelectMany([](AstDefFile* file) { return From(file->SymbolOrder()); }) + ; } + + template + void AddError(ParserErrorType type, ParsingTextRange codeRange, TArgs&&... args); }; /*********************************************************************** @@ -419,27 +472,47 @@ AstSymbolManager class AstSymbolManager : public Object { - using SymbolMap = collections::Dictionary; - friend class AstDefFile; + using SymbolGroup = collections::Group; + using FileMap = collections::Dictionary; protected: - MappedOwning files; - SymbolMap symbolMap; - ParserSymbolManager& global; + ParserSymbolManager& global; + MappedOwning fileGroups; + SymbolGroup symbolGroup; + FileMap fileMap; public: AstSymbolManager(ParserSymbolManager& _global); - AstDefFile* CreateFile(const WString& name); + AstDefFileGroup* CreateFileGroup(const WString& name); - const ParserSymbolManager& Global() const { return global; } - const auto& Files() const { return files.map; } - const auto& FileOrder() const { return files.order; } - const auto& Symbols() const { return symbolMap; } + const ParserSymbolManager& Global() const { return global; } + const auto& FileGroups() const { return fileGroups.map; } + const auto& FileGroupOrder() const { return fileGroups.order; } + const auto& Symbols() const { return symbolGroup; } + const auto& Files() const { return fileMap; } }; - extern AstDefFile* CreateParserGenTypeAst(AstSymbolManager& manager); - extern AstDefFile* CreateParserGenRuleAst(AstSymbolManager& manager); + extern AstDefFile* CreateParserGenTypeAst(AstSymbolManager& manager); + extern AstDefFile* CreateParserGenRuleAst(AstSymbolManager& manager); + +/*********************************************************************** +AddError +***********************************************************************/ + + template + void AstDefFile::AddError(ParserErrorType type, ParsingTextRange codeRange, TArgs&&... args) + { + auto&& global = const_cast(ownerGroup->Owner()->Global()); + global.AddError(type, { ParserDefFileType::Ast,name,codeRange }, std::forward(args)...); + } + + template + void AstDefFileGroup::AddError(ParserErrorType type, ParsingTextRange codeRange, TArgs&&... args) + { + auto&& global = const_cast(ownerManager->Global()); + global.AddError(type, { ParserDefFileType::AstGroup,name,codeRange }, std::forward(args)...); + } } } } @@ -521,7 +594,7 @@ LexerSymbolManager #endif /*********************************************************************** -.\PARSERGEN\PARSERCPPGEN.H +.\PARSERGEN_GLOBAL\PARSERCPPGEN.H ***********************************************************************/ /*********************************************************************** Author: Zihan Chen (vczh) @@ -538,7 +611,7 @@ namespace vl { namespace parsergen { - class AstDefFile; + class AstDefFileGroup; class AstClassPropSymbol; class AstClassSymbol; class TokenSymbol; @@ -576,7 +649,7 @@ Output WString assemblyCpp; WString lexerH; WString lexerCpp; - collections::Dictionary> astOutputs; + collections::Dictionary> astOutputs; collections::Dictionary> syntaxOutputs; collections::Dictionary classIds; @@ -623,29 +696,29 @@ namespace vl { extern void GenerateAstFileNames(AstSymbolManager& manager, Ptr parserOutput); - extern void WriteAstHeaderFile (AstDefFile* file, stream::StreamWriter& writer); - extern void WriteAstCppFile (AstDefFile* file, const WString& astHeaderName, stream::StreamWriter& writer); + extern void WriteAstHeaderFile (AstDefFileGroup* group, stream::StreamWriter& writer); + extern void WriteAstCppFile (AstDefFileGroup* group, const WString& astHeaderName, stream::StreamWriter& writer); - extern void WriteAstUtilityHeaderFile (AstDefFile* file, Ptr output, const WString& extraNss, stream::StreamWriter& writer, Func callback); - extern void WriteAstUtilityCppFile (AstDefFile* file, const WString& utilityHeaderFile, const WString& extraNss, stream::StreamWriter& writer, Func callback); + extern void WriteAstUtilityHeaderFile (AstDefFileGroup* group, Ptr output, const WString& extraNss, stream::StreamWriter& writer, Func callback); + extern void WriteAstUtilityCppFile (AstDefFileGroup* group, const WString& utilityHeaderFile, const WString& extraNss, stream::StreamWriter& writer, Func callback); extern void WriteParserUtilityHeaderFile (AstSymbolManager& manager, Ptr output, const WString& guardPostfix, stream::StreamWriter& writer, Func callback); extern void WriteParserUtilityCppFile (AstSymbolManager& manager, const WString& utilityHeaderFile, stream::StreamWriter& writer, Func callback); - extern void WriteAstBuilderHeaderFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteAstBuilderCppFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteEmptyVisitorHeaderFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteEmptyVisitorCppFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteCopyVisitorHeaderFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteCopyVisitorCppFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteTraverseVisitorHeaderFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteTraverseVisitorCppFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteJsonVisitorHeaderFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); - extern void WriteJsonVisitorCppFile (AstDefFile* file, Ptr output, stream::StreamWriter& writer); + extern void WriteAstBuilderHeaderFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteAstBuilderCppFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteEmptyVisitorHeaderFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteEmptyVisitorCppFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteCopyVisitorHeaderFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteCopyVisitorCppFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteTraverseVisitorHeaderFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteTraverseVisitorCppFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteJsonVisitorHeaderFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); + extern void WriteJsonVisitorCppFile (AstDefFileGroup* group, Ptr output, stream::StreamWriter& writer); extern void WriteAstAssemblerHeaderFile (AstSymbolManager& manager, Ptr output, stream::StreamWriter& writer); extern void WriteAstAssemblerCppFile (AstSymbolManager& manager, Ptr output, stream::StreamWriter& writer); - extern void WriteAstFiles (AstDefFile* file, Ptr output, collections::Dictionary& files); + extern void WriteAstFiles (AstDefFileGroup* group, Ptr output, collections::Dictionary& files); extern void WriteAstFiles (AstSymbolManager& manager, Ptr output, collections::Dictionary& files); } } @@ -2444,6 +2517,33 @@ namespace vl::glr::parsergen } #endif +/*********************************************************************** +.\PARSERGEN_PRINTER\ASTTOCODE.H +***********************************************************************/ +#ifndef VCZH_PARSER2_PARSERGEN_ASTTOCODE +#define VCZH_PARSER2_PARSERGEN_ASTTOCODE + + +namespace vl::glr::parsergen +{ + extern Ptr TypeSymbolToAst( + const AstSymbolManager& manager, + bool createGeneratedTypes + ); + + extern void TypeAstToCode( + Ptr file, + stream::TextWriter& writer + ); + + extern void SyntaxAstToCode( + Ptr file, + stream::TextWriter& writer + ); +} + +#endif + /*********************************************************************** .\SYNTAX\SYNTAXSYMBOL.H ***********************************************************************/ @@ -2592,9 +2692,10 @@ RuleSymbol WString name; vint32_t currentClauseId = -1; - RuleSymbol(SyntaxSymbolManager* _ownerManager, const WString& _name); + RuleSymbol(SyntaxSymbolManager* _ownerManager, const WString& _name, vint _fileIndex); public: StateList startStates; + vint fileIndex = -1; bool isPublic = false; bool isParser = false; bool isPartial = false; @@ -2656,7 +2757,7 @@ SyntaxSymbolManager WString name; LrpFlagList lrpFlags; - RuleSymbol* CreateRule(const WString& name, ParsingTextRange codeRange = {}); + RuleSymbol* CreateRule(const WString& name, vint fileIndex, bool isPublic, bool isParser, ParsingTextRange codeRange = {}); void RemoveRule(const WString& name); StateSymbol* CreateState(RuleSymbol* rule, vint32_t clauseId); @@ -2830,9 +2931,11 @@ Compiler ***********************************************************************/ extern WString UnescapeLiteral(const WString& literal, wchar_t quot); + extern void CompileAst(AstSymbolManager& astManager, collections::List>>& files); extern void CompileAst(AstSymbolManager& astManager, AstDefFile* astDefFile, Ptr file); extern void CompileLexer(LexerSymbolManager& lexerManager, const WString& input); extern Ptr CompileSyntax(AstSymbolManager& astManager, LexerSymbolManager& lexerManager, SyntaxSymbolManager& syntaxManager, Ptr output, collections::List>& files); + extern Ptr CompileSyntax(AstSymbolManager& astManager, LexerSymbolManager& lexerManager, SyntaxSymbolManager& syntaxManager, Ptr output, Ptr file); } } } diff --git a/Tools/Executables/GlrParserGen/Main.cpp b/Tools/Executables/GlrParserGen/Main.cpp index de925144..5cf7fc35 100644 --- a/Tools/Executables/GlrParserGen/Main.cpp +++ b/Tools/Executables/GlrParserGen/Main.cpp @@ -113,6 +113,9 @@ void PrintCompileErrors(ParserSymbolManager& global) { switch (error.location.type) { + case ParserDefFileType::AstGroup: + Console::Write(L"[AstGroup:" + error.location.name + L"]"); + break; case ParserDefFileType::Ast: Console::Write(L"[Ast:" + error.location.name + L"]"); break; @@ -251,22 +254,33 @@ int main(int argc, char* argv[]) for (auto elementAst : asts) { - WString name, file; + WString name; READ_ATTRIBUTE(name, elementAst, L"name", L"/Parser/Asts/Ast@name"); - READ_ATTRIBUTE(file, elementAst, L"file", L"/Parser/Asts/Ast@file[@name=\"" + name + L"\"]"); - Console::WriteLine(L"Processing " + file + L" ..."); - File astFile = workingDir / file; - if (!astFile.Exists()) EXIT_ERROR(L"Missing ast definition file: " + astFile.GetFilePath().GetFullPath()); - auto astInput = astFile.ReadAllTextByBom(); - auto ast = typeParser.ParseFile(astInput); - EXIT_IF_PARSER_FAIL(errors, L"Syntax errors found in file: " + astFile.GetFilePath().GetFullPath()); + auto astDefFileGroup = astManager.CreateFileGroup(name); + READ_ELEMENT_ITEMS(astDefFileGroup->cppNss, regexNamespace, elementAst, L"CppNamespace", L"/Parser/Asts/Ast@file[@name=\"" + name + L"\"]/CppNamespace"); + READ_ELEMENT_ITEMS(astDefFileGroup->refNss, regexNamespace, elementAst, L"ReflectionNamespace", L"/Parser/Asts/Ast@file[@name=\"" + name + L"\"]/ReflectionNamespace"); + READ_ELEMENT(astDefFileGroup->classPrefix, elementAst, L"ClassPrefix", L"/Parser/Asts/Ast@file[@name=\"" + name + L"\"]/ClassPrefix"); - auto astDefFile = astManager.CreateFile(name); - READ_ELEMENT_ITEMS(astDefFile->cppNss, regexNamespace, elementAst, L"CppNamespace", L"/Parser/Asts/Ast@file[@name=\"" + name + L"\"]/CppNamespace"); - READ_ELEMENT_ITEMS(astDefFile->refNss, regexNamespace, elementAst, L"ReflectionNamespace", L"/Parser/Asts/Ast@file[@name=\"" + name + L"\"]/ReflectionNamespace"); - READ_ELEMENT(astDefFile->classPrefix, elementAst, L"ClassPrefix", L"/Parser/Asts/Ast@file[@name=\"" + name + L"\"]/ClassPrefix"); - CompileAst(astManager, astDefFile, ast); + List>> astFiles; + for (auto elementFile : XmlGetElements(elementAst, L"File")) + { + WString file; + READ_ATTRIBUTE(file, elementFile, L"file", L"/Parser/Asts/Ast/File@file"); + Console::WriteLine(L"Processing " + file + L" ..."); + + File astFile = workingDir / file; + if (!astFile.Exists()) EXIT_ERROR(L"Missing ast definition file: " + astFile.GetFilePath().GetFullPath()); + auto astInput = astFile.ReadAllTextByBom(); + auto ast = typeParser.ParseFile(astInput); + EXIT_IF_PARSER_FAIL(errors, L"Syntax errors found in file: " + astFile.GetFilePath().GetFullPath()); + + auto astDefFile = astDefFileGroup->CreateFile(file); + astFiles.Add({ astDefFile,ast }); + } + + if (astFiles.Count() == 0) EXIT_ERROR(L"Missing /Parser/Asts/Ast/File"); + CompileAst(astManager, astFiles); } EXIT_IF_COMPILE_FAIL(global); @@ -293,24 +307,30 @@ int main(int argc, char* argv[]) } else { - EXIT_ERROR(L"Missing /Parser/Asts"); + EXIT_ERROR(L"Missing /Parser/Lexer"); } if (auto elementSyntax = XmlGetElement(config->rootElement, L"Syntax")) { - WString name, file; + WString name; READ_ATTRIBUTE(name, elementSyntax, L"name", L"/Parser/Syntax@name"); - READ_ATTRIBUTE(file, elementSyntax, L"file", L"/Parser/Syntax@file[@name=\"" + name + L"\"]"); - Console::WriteLine(L"Processing " + file + L" ..."); - - File syntaxFile = workingDir / file; - auto syntaxInput = syntaxFile.ReadAllTextByBom(); - auto syntax = ruleParser.ParseFile(syntaxInput); - EXIT_IF_PARSER_FAIL(errors, L"Syntax errors found in file: " + syntaxFile.GetFilePath().GetFullPath()); + syntaxManager.name = name; List> syntaxFiles; - syntaxFiles.Add(syntax); - syntaxManager.name = name; + for (auto elementFile : XmlGetElements(elementSyntax, L"File")) + { + WString file; + READ_ATTRIBUTE(file, elementFile, L"file", L"/Parser/Syntax/File@file"); + Console::WriteLine(L"Processing " + file + L" ..."); + + File syntaxFile = workingDir / file; + auto syntaxInput = syntaxFile.ReadAllTextByBom(); + auto syntax = ruleParser.ParseFile(syntaxInput); + EXIT_IF_PARSER_FAIL(errors, L"Syntax errors found in file: " + syntaxFile.GetFilePath().GetFullPath()); + syntaxFiles.Add(syntax); + } + + if (syntaxFiles.Count() == 0) EXIT_ERROR(L"Missing /Parser/Syntax/File"); CompileSyntax(astManager, lexerManager, syntaxManager, output, syntaxFiles); EXIT_IF_COMPILE_FAIL(global); @@ -326,7 +346,7 @@ int main(int argc, char* argv[]) } else { - EXIT_ERROR(L"Missing /Parser/Asts"); + EXIT_ERROR(L"Missing /Parser/Syntax"); } { @@ -334,7 +354,7 @@ int main(int argc, char* argv[]) for (auto elementAst : XmlGetElements(elementAsts, L"Ast")) { auto name = XmlGetAttribute(elementAst, L"name")->value.value; - auto astOutput = output->astOutputs[astManager.Files()[name]]; + auto astOutput = output->astOutputs[astManager.FileGroups()[name]]; if (auto elementBlocked = XmlGetElement(elementAst, L"BlockedUtilities")) { diff --git a/Tools/Reflection32.bin b/Tools/Reflection32.bin index 8b29d267..0b681965 100644 Binary files a/Tools/Reflection32.bin and b/Tools/Reflection32.bin differ diff --git a/Tools/Reflection64.bin b/Tools/Reflection64.bin index 7799ca77..aa34da92 100644 Binary files a/Tools/Reflection64.bin and b/Tools/Reflection64.bin differ diff --git a/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x64 b/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x64 index 84671534..6002dddd 100644 Binary files a/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x64 and b/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x64 differ diff --git a/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x86 b/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x86 index f3666050..8683bd41 100644 Binary files a/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x86 and b/Tutorial/GacUI_HelloWorlds/UIRes/Xml.bin.x86 differ