diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/emscripten-helpers.cc | 2 | ||||
-rw-r--r-- | src/tools/wasm-interp.cc | 2 | ||||
-rw-r--r-- | src/tools/wast-desugar.cc | 4 | ||||
-rw-r--r-- | src/tools/wast2json.cc | 4 | ||||
-rw-r--r-- | src/tools/wat2wasm.cc | 17 | ||||
-rw-r--r-- | src/wast-parser.cc | 90 | ||||
-rw-r--r-- | src/wast-parser.h | 24 |
7 files changed, 93 insertions, 50 deletions
diff --git a/src/emscripten-helpers.cc b/src/emscripten-helpers.cc index 48513fdd..9b0f1117 100644 --- a/src/emscripten-helpers.cc +++ b/src/emscripten-helpers.cc @@ -66,7 +66,7 @@ WabtParseWastResult* wabt_parse_wast(wabt::WastLexer* lexer, wabt::ErrorHandlerBuffer* error_handler) { WabtParseWastResult* result = new WabtParseWastResult(); std::unique_ptr<wabt::Script> script; - result->result = wabt::ParseWast(lexer, &script, error_handler); + result->result = wabt::ParseWastScript(lexer, &script, error_handler); result->script = std::move(script); return result; } diff --git a/src/tools/wasm-interp.cc b/src/tools/wasm-interp.cc index 5c108405..12fdae04 100644 --- a/src/tools/wasm-interp.cc +++ b/src/tools/wasm-interp.cc @@ -1014,7 +1014,7 @@ wabt::Result SpecJSONParser::ReadInvalidTextModule( std::unique_ptr<WastLexer> lexer = WastLexer::CreateFileLexer(module_filename); std::unique_ptr<Script> script; - wabt::Result result = ParseWast(lexer.get(), &script, error_handler); + wabt::Result result = ParseWastScript(lexer.get(), &script, error_handler); if (Succeeded(result)) { wabt::Module* module = script->GetFirstModule(); result = ResolveNamesModule(lexer.get(), module, error_handler); diff --git a/src/tools/wast-desugar.cc b/src/tools/wast-desugar.cc index 03bdc4b8..8aa76af8 100644 --- a/src/tools/wast-desugar.cc +++ b/src/tools/wast-desugar.cc @@ -88,8 +88,8 @@ int ProgramMain(int argc, char** argv) { ErrorHandlerFile error_handler(Location::Type::Text); std::unique_ptr<Script> script; WastParseOptions parse_wast_options(s_features); - Result result = - ParseWast(lexer.get(), &script, &error_handler, &parse_wast_options); + Result result = ParseWastScript(lexer.get(), &script, &error_handler, + &parse_wast_options); if (Succeeded(result)) { Module* module = script->GetFirstModule(); diff --git a/src/tools/wast2json.cc b/src/tools/wast2json.cc index 7fb75c72..c13221dd 100644 --- a/src/tools/wast2json.cc +++ b/src/tools/wast2json.cc @@ -101,8 +101,8 @@ int ProgramMain(int argc, char** argv) { ErrorHandlerFile error_handler(Location::Type::Text); std::unique_ptr<Script> script; WastParseOptions parse_wast_options(s_features); - Result result = - ParseWast(lexer.get(), &script, &error_handler, &parse_wast_options); + Result result = ParseWastScript(lexer.get(), &script, &error_handler, + &parse_wast_options); if (Succeeded(result)) { result = ResolveNamesScript(lexer.get(), script.get(), &error_handler); diff --git a/src/tools/wat2wasm.cc b/src/tools/wat2wasm.cc index 20e27908..2eb63a42 100644 --- a/src/tools/wat2wasm.cc +++ b/src/tools/wat2wasm.cc @@ -123,26 +123,21 @@ int ProgramMain(int argc, char** argv) { WABT_FATAL("unable to read file: %s\n", s_infile); ErrorHandlerFile error_handler(Location::Type::Text); - // TODO(binji): Parse Module instead of Script. - std::unique_ptr<Script> script; + std::unique_ptr<Module> module; WastParseOptions parse_wast_options(s_features); Result result = - ParseWast(lexer.get(), &script, &error_handler, &parse_wast_options); + ParseWatModule(lexer.get(), &module, &error_handler, &parse_wast_options); if (Succeeded(result)) { - result = ResolveNamesScript(lexer.get(), script.get(), &error_handler); + result = ResolveNamesModule(lexer.get(), module.get(), &error_handler); if (Succeeded(result) && s_validate) - result = ValidateScript(lexer.get(), script.get(), &error_handler); + result = ValidateModule(lexer.get(), module.get(), &error_handler); if (Succeeded(result)) { MemoryStream stream(s_log_stream.get()); - const Module* module = script->GetFirstModule(); - if (module) { - result = WriteBinaryModule(&stream, module, &s_write_binary_options); - } else { - WABT_FATAL("no module found\n"); - } + result = + WriteBinaryModule(&stream, module.get(), &s_write_binary_options); if (Succeeded(result)) WriteBufferToFile(s_outfile, stream.output_buffer()); diff --git a/src/wast-parser.cc b/src/wast-parser.cc index 3048cee2..a9a53973 100644 --- a/src/wast-parser.cc +++ b/src/wast-parser.cc @@ -630,9 +630,37 @@ Result WastParser::ParseNat(uint64_t* out_nat) { return Result::Ok; } -Result WastParser::ParseScript() { +Result WastParser::ParseModule(std::unique_ptr<Module>* out_module) { + WABT_TRACE(ParseModule); + auto module = MakeUnique<Module>(); + + if (PeekMatchLpar(TokenType::Module)) { + // Starts with "(module". Allow text and binary modules, but no quoted + // modules. + CommandPtr command; + CHECK_RESULT(ParseModuleCommand(nullptr, &command)); + auto module_command = cast<ModuleCommand>(std::move(command)); + *module = std::move(module_command->module); + } else if (IsModuleField(PeekPair())) { + // Parse an inline module (i.e. one with no surrounding (module)). + CHECK_RESULT(ParseModuleFieldList(module.get())); + } else { + ConsumeIfLpar(); + ErrorExpected({"a module field", "a module"}); + } + + EXPECT(Eof); + if (errors_ == 0) { + *out_module = std::move(module); + return Result::Ok; + } else { + return Result::Error; + } +} + +Result WastParser::ParseScript(std::unique_ptr<Script>* out_script) { WABT_TRACE(ParseScript); - script_ = MakeUnique<Script>(); + auto script = MakeUnique<Script>(); // Don't consume the Lpar yet, even though it is required. This way the // sub-parser functions (e.g. ParseFuncModuleField) can consume it and keep @@ -642,16 +670,21 @@ Result WastParser::ParseScript() { auto command = MakeUnique<ModuleCommand>(); command->module.loc = GetLocation(); CHECK_RESULT(ParseModuleFieldList(&command->module)); - script_->commands.emplace_back(std::move(command)); + script->commands.emplace_back(std::move(command)); } else if (IsCommand(PeekPair())) { - CHECK_RESULT(ParseCommandList(&script_->commands)); + CHECK_RESULT(ParseCommandList(script.get(), &script->commands)); } else { ConsumeIfLpar(); ErrorExpected({"a module field", "a command"}); } EXPECT(Eof); - return errors_ == 0 ? Result::Ok : Result::Error; + if (errors_ == 0) { + *out_script = std::move(script); + return Result::Ok; + } else { + return Result::Error; + } } Result WastParser::ParseModuleFieldList(Module* module) { @@ -1660,11 +1693,12 @@ Result WastParser::ParseGlobalType(Global* global) { return Result::Ok; } -Result WastParser::ParseCommandList(CommandPtrVector* commands) { +Result WastParser::ParseCommandList(Script* script, + CommandPtrVector* commands) { WABT_TRACE(ParseCommandList); while (IsCommand(PeekPair())) { CommandPtr command; - if (Succeeded(ParseCommand(&command))) { + if (Succeeded(ParseCommand(script, &command))) { commands->push_back(std::move(command)); } else { CHECK_RESULT(Synchronize(IsCommand)); @@ -1673,7 +1707,7 @@ Result WastParser::ParseCommandList(CommandPtrVector* commands) { return Result::Ok; } -Result WastParser::ParseCommand(CommandPtr* out_command) { +Result WastParser::ParseCommand(Script* script, CommandPtr* out_command) { WABT_TRACE(ParseCommand); switch (Peek(1)) { case TokenType::AssertExhaustion: @@ -1705,7 +1739,7 @@ Result WastParser::ParseCommand(CommandPtr* out_command) { return ParseActionCommand(out_command); case TokenType::Module: - return ParseModuleCommand(out_command); + return ParseModuleCommand(script, out_command); case TokenType::Register: return ParseRegisterCommand(out_command); @@ -1793,7 +1827,7 @@ Result WastParser::ParseActionCommand(CommandPtr* out_command) { return Result::Ok; } -Result WastParser::ParseModuleCommand(CommandPtr* out_command) { +Result WastParser::ParseModuleCommand(Script* script, CommandPtr* out_command) { WABT_TRACE(ParseModuleCommand); std::unique_ptr<ScriptModule> script_module; CHECK_RESULT(ParseScriptModule(&script_module)); @@ -1822,14 +1856,18 @@ Result WastParser::ParseModuleCommand(CommandPtr* out_command) { return ErrorExpected({"a binary module", "a text module"}); } - Index command_index = script_->commands.size(); + // script is nullptr when ParseModuleCommand is called from ParseModule. + if (script) { + Index command_index = script->commands.size(); - if (!module.name.empty()) { - script_->module_bindings.emplace(module.name, - Binding(module.loc, command_index)); + if (!module.name.empty()) { + script->module_bindings.emplace(module.name, + Binding(module.loc, command_index)); + } + + last_module_index_ = command_index; } - last_module_index_ = command_index; *out_command = std::move(command); return Result::Ok; } @@ -1982,19 +2020,23 @@ void WastParser::CheckImportOrdering(Module* module) { } } -std::unique_ptr<Script> WastParser::ReleaseScript() { - return std::move(script_); +Result ParseWatModule(WastLexer* lexer, + std::unique_ptr<Module>* out_module, + ErrorHandler* error_handler, + WastParseOptions* options) { + assert(out_module != nullptr); + WastParser parser(lexer, error_handler, options); + return parser.ParseModule(out_module); } -Result ParseWast(WastLexer* lexer, - std::unique_ptr<Script>* out_script, - ErrorHandler* error_handler, - WastParseOptions* options) { + +Result ParseWastScript(WastLexer* lexer, + std::unique_ptr<Script>* out_script, + ErrorHandler* error_handler, + WastParseOptions* options) { assert(out_script != nullptr); WastParser parser(lexer, error_handler, options); - Result result = parser.ParseScript(); - *out_script = parser.ReleaseScript(); - return result; + return parser.ParseScript(out_script); } } // namespace wabt diff --git a/src/wast-parser.h b/src/wast-parser.h index 95f5bc96..c537c7f1 100644 --- a/src/wast-parser.h +++ b/src/wast-parser.h @@ -43,7 +43,9 @@ class WastParser { WastParser(WastLexer*, ErrorHandler*, WastParseOptions*); void WABT_PRINTF_FORMAT(3, 4) Error(Location, const char* format, ...); - Result ParseScript(); + Result ParseModule(std::unique_ptr<Module>* out_module); + Result ParseScript(std::unique_ptr<Script>* out_script); + std::unique_ptr<Script> ReleaseScript(); private: @@ -168,8 +170,8 @@ class WastParser { template <typename T> Result ParsePlainInstrVar(Location, std::unique_ptr<Expr>*); - Result ParseCommandList(CommandPtrVector*); - Result ParseCommand(CommandPtr*); + Result ParseCommandList(Script*, CommandPtrVector*); + Result ParseCommand(Script*, CommandPtr*); Result ParseAssertExhaustionCommand(CommandPtr*); Result ParseAssertInvalidCommand(CommandPtr*); Result ParseAssertMalformedCommand(CommandPtr*); @@ -179,7 +181,7 @@ class WastParser { Result ParseAssertTrapCommand(CommandPtr*); Result ParseAssertUnlinkableCommand(CommandPtr*); Result ParseActionCommand(CommandPtr*); - Result ParseModuleCommand(CommandPtr*); + Result ParseModuleCommand(Script*, CommandPtr*); Result ParseRegisterCommand(CommandPtr*); Result ParseAction(ActionPtr*); @@ -197,7 +199,6 @@ class WastParser { void CheckImportOrdering(Module*); WastLexer* lexer_; - std::unique_ptr<Script> script_; Index last_module_index_ = kInvalidIndex; ErrorHandler* error_handler_; int errors_ = 0; @@ -206,10 +207,15 @@ class WastParser { CircularArray<Token, 2> tokens_; }; -Result ParseWast(WastLexer* lexer, - std::unique_ptr<Script>* out_script, - ErrorHandler*, - WastParseOptions* options = nullptr); +Result ParseWatModule(WastLexer* lexer, + std::unique_ptr<Module>* out_module, + ErrorHandler*, + WastParseOptions* options = nullptr); + +Result ParseWastScript(WastLexer* lexer, + std::unique_ptr<Script>* out_script, + ErrorHandler*, + WastParseOptions* options = nullptr); } // namespace wabt |