Changeset 249708 in webkit


Ignore:
Timestamp:
Sep 10, 2019 2:42:15 AM (5 years ago)
Author:
ysuzuki@apple.com
Message:

[WebAssembly] Use StreamingParser in existing Wasm::BBQPlan
https://bugs.webkit.org/show_bug.cgi?id=189043

Reviewed by Keith Miller.

JSTests:

The offset performing the validation becomes a bit different.
The offset 0 is nice since it is the starting offset of the Module header signature compared to the offset 8.

  • wasm/js-api/version.js:

Source/JavaScriptCore:

This patch integrates Wasm::StreamingParser into the existing Wasm::BBQPlan.
And remove Wasm::ModuleParser. This patch paves the way to implementing Wasm streaming features by
using Wasm::StreamingParser.

Currently, we are not using streaming feature of StreamingParser. In a subsequent patch, we will
create a mechanism to pipe a chunk of data to streaming parser to enable WebAssembly.compileStreaming
and instantiateStreaming.

  • JavaScriptCore.xcodeproj/project.pbxproj:
  • Sources.txt:
  • tools/JSDollarVM.cpp:

(JSC::WasmStreamingParser::WasmStreamingParser):

  • wasm/WasmAirIRGenerator.cpp:

(JSC::Wasm::parseAndCompileAir):

  • wasm/WasmAirIRGenerator.h:
  • wasm/WasmB3IRGenerator.cpp:

(JSC::Wasm::parseAndCompile): Use FunctionData, it is good since it is more strongly typed.

  • wasm/WasmB3IRGenerator.h:
  • wasm/WasmBBQPlan.cpp:

(JSC::Wasm::BBQPlan::BBQPlan):
(JSC::Wasm::BBQPlan::didReceiveFunctionData): Add a callback, which invokes validation.
(JSC::Wasm::BBQPlan::parseAndValidateModule): Use StreamingParser instead of old ModuleParser.
(JSC::Wasm::BBQPlan::compileFunctions):
(JSC::Wasm::BBQPlan::complete):

  • wasm/WasmBBQPlan.h:
  • wasm/WasmModuleParser.cpp: Removed.
  • wasm/WasmModuleParser.h: Removed.
  • wasm/WasmOMGForOSREntryPlan.cpp:

(JSC::Wasm::OMGForOSREntryPlan::work):

  • wasm/WasmOMGPlan.cpp:

(JSC::Wasm::OMGPlan::work):

  • wasm/WasmPlan.cpp:

(JSC::Wasm::Plan::fail): Make fail function callable multiple times. The first error will be used.

  • wasm/WasmSectionParser.cpp:

(JSC::Wasm::SectionParser::parseCode): Since the Code section is specially handled in StreamingParser, this code is never used.

  • wasm/WasmStreamingParser.cpp:

(JSC::Wasm::StreamingParser::StreamingParser):
(JSC::Wasm::StreamingParser::parseCodeSectionSize):
(JSC::Wasm::StreamingParser::parseFunctionPayload):
(JSC::Wasm::StreamingParser::parseSectionPayload):
(JSC::Wasm::StreamingParser::finalize): Call client's callbacks at appropriate timings.

  • wasm/WasmStreamingParser.h:

(JSC::Wasm::StreamingParserClient::didReceiveSectionData):
(JSC::Wasm::StreamingParserClient::didReceiveFunctionData):
(JSC::Wasm::StreamingParserClient::didFinishParsing): Add StreamingParserClient,
which has 3 callbacks right now. StreamingParser gets this client and call these callbacks
at appropriate timings.

  • wasm/WasmValidate.cpp:

(JSC::Wasm::validateFunction):

  • wasm/WasmValidate.h: Use FunctionData, it is good since it is more strongly typed.
Location:
trunk
Files:
2 deleted
20 edited

Legend:

Unmodified
Added
Removed
  • trunk/JSTests/ChangeLog

    r249661 r249708  
     12019-09-10  Yusuke Suzuki  <ysuzuki@apple.com>
     2
     3        [WebAssembly] Use StreamingParser in existing Wasm::BBQPlan
     4        https://bugs.webkit.org/show_bug.cgi?id=189043
     5
     6        Reviewed by Keith Miller.
     7
     8        The offset performing the validation becomes a bit different.
     9        The offset 0 is nice since it is the starting offset of the Module header signature compared to the offset 8.
     10
     11        * wasm/js-api/version.js:
     12
    1132019-09-07  Keith Miller  <keith_miller@apple.com>
    214
  • trunk/JSTests/wasm/js-api/version.js

    r235420 r249708  
    66        continue;
    77    const emptyModuleArray = Uint8Array.of(0x0, 0x61, 0x73, 0x6d, version, 0x00, 0x00, 0x00);
    8     assert.throws(() => new WebAssembly.Module(emptyModuleArray), WebAssembly.CompileError, `WebAssembly.Module doesn't parse at byte 8: unexpected version number ${version} expected 1`);
     8    assert.throws(() => new WebAssembly.Module(emptyModuleArray), WebAssembly.CompileError, `WebAssembly.Module doesn't parse at byte 0: unexpected version number ${version} expected 1`);
    99}
  • trunk/Source/JavaScriptCore/ChangeLog

    r249706 r249708  
     12019-09-10  Yusuke Suzuki  <ysuzuki@apple.com>
     2
     3        [WebAssembly] Use StreamingParser in existing Wasm::BBQPlan
     4        https://bugs.webkit.org/show_bug.cgi?id=189043
     5
     6        Reviewed by Keith Miller.
     7
     8        This patch integrates Wasm::StreamingParser into the existing Wasm::BBQPlan.
     9        And remove Wasm::ModuleParser. This patch paves the way to implementing Wasm streaming features by
     10        using Wasm::StreamingParser.
     11
     12        Currently, we are not using streaming feature of StreamingParser. In a subsequent patch, we will
     13        create a mechanism to pipe a chunk of data to streaming parser to enable WebAssembly.compileStreaming
     14        and instantiateStreaming.
     15
     16        * JavaScriptCore.xcodeproj/project.pbxproj:
     17        * Sources.txt:
     18        * tools/JSDollarVM.cpp:
     19        (JSC::WasmStreamingParser::WasmStreamingParser):
     20        * wasm/WasmAirIRGenerator.cpp:
     21        (JSC::Wasm::parseAndCompileAir):
     22        * wasm/WasmAirIRGenerator.h:
     23        * wasm/WasmB3IRGenerator.cpp:
     24        (JSC::Wasm::parseAndCompile): Use FunctionData, it is good since it is more strongly typed.
     25        * wasm/WasmB3IRGenerator.h:
     26        * wasm/WasmBBQPlan.cpp:
     27        (JSC::Wasm::BBQPlan::BBQPlan):
     28        (JSC::Wasm::BBQPlan::didReceiveFunctionData): Add a callback, which invokes validation.
     29        (JSC::Wasm::BBQPlan::parseAndValidateModule): Use StreamingParser instead of old ModuleParser.
     30        (JSC::Wasm::BBQPlan::compileFunctions):
     31        (JSC::Wasm::BBQPlan::complete):
     32        * wasm/WasmBBQPlan.h:
     33        * wasm/WasmModuleParser.cpp: Removed.
     34        * wasm/WasmModuleParser.h: Removed.
     35        * wasm/WasmOMGForOSREntryPlan.cpp:
     36        (JSC::Wasm::OMGForOSREntryPlan::work):
     37        * wasm/WasmOMGPlan.cpp:
     38        (JSC::Wasm::OMGPlan::work):
     39        * wasm/WasmPlan.cpp:
     40        (JSC::Wasm::Plan::fail): Make fail function callable multiple times. The first error will be used.
     41        * wasm/WasmSectionParser.cpp:
     42        (JSC::Wasm::SectionParser::parseCode): Since the Code section is specially handled in StreamingParser, this code is never used.
     43        * wasm/WasmStreamingParser.cpp:
     44        (JSC::Wasm::StreamingParser::StreamingParser):
     45        (JSC::Wasm::StreamingParser::parseCodeSectionSize):
     46        (JSC::Wasm::StreamingParser::parseFunctionPayload):
     47        (JSC::Wasm::StreamingParser::parseSectionPayload):
     48        (JSC::Wasm::StreamingParser::finalize): Call client's callbacks at appropriate timings.
     49        * wasm/WasmStreamingParser.h:
     50        (JSC::Wasm::StreamingParserClient::didReceiveSectionData):
     51        (JSC::Wasm::StreamingParserClient::didReceiveFunctionData):
     52        (JSC::Wasm::StreamingParserClient::didFinishParsing): Add StreamingParserClient,
     53        which has 3 callbacks right now. StreamingParser gets this client and call these callbacks
     54        at appropriate timings.
     55        * wasm/WasmValidate.cpp:
     56        (JSC::Wasm::validateFunction):
     57        * wasm/WasmValidate.h: Use FunctionData, it is good since it is more strongly typed.
     58
    1592019-09-09  Yusuke Suzuki  <ysuzuki@apple.com>
    260
  • trunk/Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj

    r249547 r249708  
    11101110                53F40E8D1D5901F20099A1B6 /* WasmParser.h in Headers */ = {isa = PBXBuildFile; fileRef = 53F40E8C1D5901F20099A1B6 /* WasmParser.h */; };
    11111111                53F40E931D5A4AB30099A1B6 /* WasmB3IRGenerator.h in Headers */ = {isa = PBXBuildFile; fileRef = 53F40E921D5A4AB30099A1B6 /* WasmB3IRGenerator.h */; };
    1112                 53F40E951D5A7AEF0099A1B6 /* WasmModuleParser.h in Headers */ = {isa = PBXBuildFile; fileRef = 53F40E941D5A7AEF0099A1B6 /* WasmModuleParser.h */; };
    11131112                53F6BF6D1C3F060A00F41E5D /* InternalFunctionAllocationProfile.h in Headers */ = {isa = PBXBuildFile; fileRef = 53F6BF6C1C3F060A00F41E5D /* InternalFunctionAllocationProfile.h */; settings = {ATTRIBUTES = (Private, ); }; };
    11141113                53F8D2001E8387D400D21116 /* WasmBBQPlanInlines.h in Headers */ = {isa = PBXBuildFile; fileRef = 53F8D1FF1E8387D400D21116 /* WasmBBQPlanInlines.h */; };
     
    37813780                53F40E8E1D5902820099A1B6 /* WasmB3IRGenerator.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WasmB3IRGenerator.cpp; sourceTree = "<group>"; };
    37823781                53F40E921D5A4AB30099A1B6 /* WasmB3IRGenerator.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WasmB3IRGenerator.h; sourceTree = "<group>"; };
    3783                 53F40E941D5A7AEF0099A1B6 /* WasmModuleParser.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WasmModuleParser.h; sourceTree = "<group>"; };
    3784                 53F40E961D5A7BEC0099A1B6 /* WasmModuleParser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WasmModuleParser.cpp; sourceTree = "<group>"; };
    37853782                53F6BF6C1C3F060A00F41E5D /* InternalFunctionAllocationProfile.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = InternalFunctionAllocationProfile.h; sourceTree = "<group>"; };
    37863783                53F8D1FF1E8387D400D21116 /* WasmBBQPlanInlines.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WasmBBQPlanInlines.h; sourceTree = "<group>"; };
     
    67596756                                53E777E11E92E265007CBEC4 /* WasmModuleInformation.cpp */,
    67606757                                53E777E21E92E265007CBEC4 /* WasmModuleInformation.h */,
    6761                                 53F40E961D5A7BEC0099A1B6 /* WasmModuleParser.cpp */,
    6762                                 53F40E941D5A7AEF0099A1B6 /* WasmModuleParser.h */,
    67636758                                AD5B416E1EBAFB65008EFA43 /* WasmName.h */,
    67646759                                AD7B4B2D1FA3E28600C9DF79 /* WasmNameSection.h */,
     
    1016410159                                790081391E95A8EC0052D7CD /* WasmModule.h in Headers */,
    1016510160                                53E777E41E92E265007CBEC4 /* WasmModuleInformation.h in Headers */,
    10166                                 53F40E951D5A7AEF0099A1B6 /* WasmModuleParser.h in Headers */,
    1016710161                                AD5B416F1EBAFB77008EFA43 /* WasmName.h in Headers */,
    1016810162                                AD7B4B2E1FA3E29800C9DF79 /* WasmNameSection.h in Headers */,
  • trunk/Source/JavaScriptCore/Sources.txt

    r249075 r249708  
    10141014wasm/WasmModule.cpp
    10151015wasm/WasmModuleInformation.cpp
    1016 wasm/WasmModuleParser.cpp
    10171016wasm/WasmNameSectionParser.cpp
    10181017wasm/WasmOMGForOSREntryPlan.cpp
  • trunk/Source/JavaScriptCore/tools/JSDollarVM.cpp

    r249495 r249708  
    11111111class WasmStreamingParser : public JSDestructibleObject {
    11121112public:
     1113    class Client final : public Wasm::StreamingParserClient {
     1114    public:
     1115        explicit Client(WasmStreamingParser* parser)
     1116            : m_parser(parser)
     1117        {
     1118        }
     1119
     1120        void didReceiveSectionData(Wasm::Section) override { }
     1121        void didReceiveFunctionData(unsigned, const Wasm::FunctionData&) override { }
     1122        void didFinishParsing() override { }
     1123
     1124        WasmStreamingParser* m_parser;
     1125    };
     1126
    11131127    WasmStreamingParser(VM& vm, Structure* structure)
    11141128        : Base(vm, structure)
    11151129        , m_info(Wasm::ModuleInformation::create())
    1116         , m_streamingParser(m_info.get())
     1130        , m_client(this)
     1131        , m_streamingParser(m_info.get(), m_client)
    11171132    {
    11181133    }
     
    11471162
    11481163    Ref<Wasm::ModuleInformation> m_info;
     1164    Client m_client;
    11491165    Wasm::StreamingParser m_streamingParser;
    11501166};
  • trunk/Source/JavaScriptCore/wasm/WasmAirIRGenerator.cpp

    r249661 r249708  
    22302230}
    22312231
    2232 Expected<std::unique_ptr<InternalFunction>, String> parseAndCompileAir(CompilationContext& compilationContext, const uint8_t* functionStart, size_t functionLength, const Signature& signature, Vector<UnlinkedWasmToWasmCall>& unlinkedWasmToWasmCalls, const ModuleInformation& info, MemoryMode mode, uint32_t functionIndex, TierUpCount* tierUp, ThrowWasmException throwWasmException)
     2232Expected<std::unique_ptr<InternalFunction>, String> parseAndCompileAir(CompilationContext& compilationContext, const FunctionData& function, const Signature& signature, Vector<UnlinkedWasmToWasmCall>& unlinkedWasmToWasmCalls, const ModuleInformation& info, MemoryMode mode, uint32_t functionIndex, TierUpCount* tierUp, ThrowWasmException throwWasmException)
    22332233{
    22342234    auto result = makeUnique<InternalFunction>();
     
    22542254
    22552255    AirIRGenerator irGenerator(info, procedure, result.get(), unlinkedWasmToWasmCalls, mode, functionIndex, tierUp, throwWasmException, signature);
    2256     FunctionParser<AirIRGenerator> parser(irGenerator, functionStart, functionLength, signature, info);
     2256    FunctionParser<AirIRGenerator> parser(irGenerator, function.data.data(), function.data.size(), signature, info);
    22572257    WASM_FAIL_IF_HELPER_FAILS(parser.parse());
    22582258
  • trunk/Source/JavaScriptCore/wasm/WasmAirIRGenerator.h

    r241579 r249708  
    3232namespace JSC { namespace Wasm {
    3333
    34 Expected<std::unique_ptr<InternalFunction>, String> parseAndCompileAir(CompilationContext&, const uint8_t*, size_t, const Signature&, Vector<UnlinkedWasmToWasmCall>&, const ModuleInformation&, MemoryMode, uint32_t functionIndex, TierUpCount* = nullptr, ThrowWasmException = nullptr);
     34Expected<std::unique_ptr<InternalFunction>, String> parseAndCompileAir(CompilationContext&, const FunctionData&, const Signature&, Vector<UnlinkedWasmToWasmCall>&, const ModuleInformation&, MemoryMode, uint32_t functionIndex, TierUpCount* = nullptr, ThrowWasmException = nullptr);
    3535
    3636} } // namespace JSC::Wasm
  • trunk/Source/JavaScriptCore/wasm/WasmB3IRGenerator.cpp

    r249661 r249708  
    16981698}
    16991699
    1700 Expected<std::unique_ptr<InternalFunction>, String> parseAndCompile(CompilationContext& compilationContext, const uint8_t* functionStart, size_t functionLength, const Signature& signature, Vector<UnlinkedWasmToWasmCall>& unlinkedWasmToWasmCalls, unsigned& osrEntryScratchBufferSize, const ModuleInformation& info, MemoryMode mode, CompilationMode compilationMode, uint32_t functionIndex, uint32_t loopIndexForOSREntry, TierUpCount* tierUp, ThrowWasmException throwWasmException)
     1700Expected<std::unique_ptr<InternalFunction>, String> parseAndCompile(CompilationContext& compilationContext, const FunctionData& function, const Signature& signature, Vector<UnlinkedWasmToWasmCall>& unlinkedWasmToWasmCalls, unsigned& osrEntryScratchBufferSize, const ModuleInformation& info, MemoryMode mode, CompilationMode compilationMode, uint32_t functionIndex, uint32_t loopIndexForOSREntry, TierUpCount* tierUp, ThrowWasmException throwWasmException)
    17011701{
    17021702    auto result = makeUnique<InternalFunction>();
     
    17231723
    17241724    B3IRGenerator irGenerator(info, procedure, result.get(), unlinkedWasmToWasmCalls, osrEntryScratchBufferSize, mode, compilationMode, functionIndex, loopIndexForOSREntry, tierUp, throwWasmException);
    1725     FunctionParser<B3IRGenerator> parser(irGenerator, functionStart, functionLength, signature, info);
     1725    FunctionParser<B3IRGenerator> parser(irGenerator, function.data.data(), function.data.size(), signature, info);
    17261726    WASM_FAIL_IF_HELPER_FAILS(parser.parse());
    17271727
  • trunk/Source/JavaScriptCore/wasm/WasmB3IRGenerator.h

    r248878 r249708  
    5252};
    5353
    54 Expected<std::unique_ptr<InternalFunction>, String> parseAndCompile(CompilationContext&, const uint8_t*, size_t, const Signature&, Vector<UnlinkedWasmToWasmCall>&, unsigned& osrEntryScratchBufferSize, const ModuleInformation&, MemoryMode, CompilationMode, uint32_t functionIndex, uint32_t loopIndexForOSREntry, TierUpCount* = nullptr, ThrowWasmException = nullptr);
     54Expected<std::unique_ptr<InternalFunction>, String> parseAndCompile(CompilationContext&, const FunctionData&, const Signature&, Vector<UnlinkedWasmToWasmCall>&, unsigned& osrEntryScratchBufferSize, const ModuleInformation&, MemoryMode, CompilationMode, uint32_t functionIndex, uint32_t loopIndexForOSREntry, TierUpCount* = nullptr, ThrowWasmException = nullptr);
    5555
    5656} } // namespace JSC::Wasm
  • trunk/Source/JavaScriptCore/wasm/WasmBBQPlan.cpp

    r248878 r249708  
    3737#include "WasmFaultSignalHandler.h"
    3838#include "WasmMemory.h"
    39 #include "WasmModuleParser.h"
    4039#include "WasmSignatureInlines.h"
    4140#include "WasmTierUpCount.h"
     
    5655BBQPlan::BBQPlan(Context* context, Ref<ModuleInformation> info, AsyncWork work, CompletionTask&& task, CreateEmbedderWrapper&& createEmbedderWrapper, ThrowWasmException throwWasmException)
    5756    : Base(context, WTFMove(info), WTFMove(task), WTFMove(createEmbedderWrapper), throwWasmException)
     57    , m_streamingParser(m_moduleInformation.get(), *this)
    5858    , m_state(State::Validated)
    5959    , m_asyncWork(work)
     
    6464    : Base(context, ModuleInformation::create(), WTFMove(task), WTFMove(createEmbedderWrapper), throwWasmException)
    6565    , m_source(WTFMove(source))
     66    , m_streamingParser(m_moduleInformation.get(), *this)
    6667    , m_state(State::Initial)
    6768    , m_asyncWork(work)
     
    7172BBQPlan::BBQPlan(Context* context, AsyncWork work, CompletionTask&& task)
    7273    : Base(context, WTFMove(task))
     74    , m_streamingParser(m_moduleInformation.get(), *this)
    7375    , m_state(State::Initial)
    7476    , m_asyncWork(work)
     
    9597}
    9698
     99void BBQPlan::didReceiveFunctionData(unsigned functionIndex, const FunctionData& function)
     100{
     101    dataLogLnIf(WasmBBQPlanInternal::verbose, "Processing function starting at: ", function.start, " and ending at: ", function.end);
     102    size_t functionLength = function.end - function.start;
     103    ASSERT(functionLength == function.data.size());
     104    SignatureIndex signatureIndex = m_moduleInformation->internalFunctionSignatureIndices[functionIndex];
     105    const Signature& signature = SignatureInformation::get(signatureIndex);
     106
     107    auto validationResult = validateFunction(function, signature, m_moduleInformation.get());
     108    if (!validationResult) {
     109        if (WasmBBQPlanInternal::verbose) {
     110            for (unsigned i = 0; i < functionLength; ++i)
     111                dataLog(RawPointer(reinterpret_cast<void*>(function.data[i])), ", ");
     112            dataLogLn();
     113        }
     114        fail(holdLock(m_lock), makeString(validationResult.error(), ", in function at index ", String::number(functionIndex))); // FIXME make this an Expected.
     115    }
     116}
     117
    97118bool BBQPlan::parseAndValidateModule(const uint8_t* source, size_t sourceLength)
    98119{
     
    105126        startTime = MonotonicTime::now();
    106127
     128    m_streamingParser.addBytes(source, sourceLength);
     129    if (m_streamingParser.finalize() != StreamingParser::State::Finished) {
     130        fail(holdLock(m_lock), String(m_streamingParser.errorMessage()));
     131        return false;
     132    }
    107133    {
    108         ModuleParser moduleParser(source, sourceLength, m_moduleInformation);
    109         auto parseResult = moduleParser.parse();
    110         if (!parseResult) {
    111             Base::fail(holdLock(m_lock), WTFMove(parseResult.error()));
     134        auto locker = holdLock(m_lock);
     135        if (failed())
    112136            return false;
    113         }
    114     }
    115 
    116     const auto& functions = m_moduleInformation->functions;
    117     for (unsigned functionIndex = 0; functionIndex < functions.size(); ++functionIndex) {
    118         const auto& function = functions[functionIndex];
    119         dataLogLnIf(WasmBBQPlanInternal::verbose, "Processing function starting at: ", function.start, " and ending at: ", function.end);
    120         size_t functionLength = function.end - function.start;
    121         ASSERT(functionLength <= sourceLength);
    122         ASSERT(functionLength == function.data.size());
    123         SignatureIndex signatureIndex = m_moduleInformation->internalFunctionSignatureIndices[functionIndex];
    124         const Signature& signature = SignatureInformation::get(signatureIndex);
    125 
    126         auto validationResult = validateFunction(function.data.data(), function.data.size(), signature, m_moduleInformation.get());
    127         if (!validationResult) {
    128             if (WasmBBQPlanInternal::verbose) {
    129                 for (unsigned i = 0; i < functionLength; ++i)
    130                     dataLog(RawPointer(reinterpret_cast<void*>(function.data[i])), ", ");
    131                 dataLogLn();
    132             }
    133             Base::fail(holdLock(m_lock), makeString(validationResult.error(), ", in function at index ", String::number(functionIndex))); // FIXME make this an Expected.
    134             return false;
    135         }
    136     }
    137 
     137    }
    138138    if (WasmBBQPlanInternal::verbose || Options::reportCompileTimes())
    139139        dataLogLn("Took ", (MonotonicTime::now() - startTime).microseconds(), " us to validate module");
     
    265265        unsigned functionIndexSpace = m_wasmToWasmExitStubs.size() + functionIndex;
    266266        ASSERT_UNUSED(functionIndexSpace, m_moduleInformation->signatureIndexFromFunctionIndexSpace(functionIndexSpace) == signatureIndex);
    267         ASSERT(validateFunction(function.data.data(), function.data.size(), signature, m_moduleInformation.get()));
     267        ASSERT(validateFunction(function, signature, m_moduleInformation.get()));
    268268
    269269        m_unlinkedWasmToWasmCalls[functionIndex] = Vector<UnlinkedWasmToWasmCall>();
     
    284284
    285285        if (!forceUsingB3 && Options::wasmBBQUsesAir())
    286             parseAndCompileResult = parseAndCompileAir(m_compilationContexts[functionIndex], function.data.data(), function.data.size(), signature, m_unlinkedWasmToWasmCalls[functionIndex], m_moduleInformation.get(), m_mode, functionIndex, tierUp, m_throwWasmException);
     286            parseAndCompileResult = parseAndCompileAir(m_compilationContexts[functionIndex], function, signature, m_unlinkedWasmToWasmCalls[functionIndex], m_moduleInformation.get(), m_mode, functionIndex, tierUp, m_throwWasmException);
    287287        else
    288             parseAndCompileResult = parseAndCompile(m_compilationContexts[functionIndex], function.data.data(), function.data.size(), signature, m_unlinkedWasmToWasmCalls[functionIndex], osrEntryScratchBufferSize, m_moduleInformation.get(), m_mode, CompilationMode::BBQMode, functionIndex, UINT32_MAX, tierUp, m_throwWasmException);
     288            parseAndCompileResult = parseAndCompile(m_compilationContexts[functionIndex], function, signature, m_unlinkedWasmToWasmCalls[functionIndex], osrEntryScratchBufferSize, m_moduleInformation.get(), m_mode, CompilationMode::BBQMode, functionIndex, UINT32_MAX, tierUp, m_throwWasmException);
    289289
    290290        if (UNLIKELY(!parseAndCompileResult)) {
    291291            auto locker = holdLock(m_lock);
    292             if (!m_errorMessage) {
    293                 // Multiple compiles could fail simultaneously. We arbitrarily choose the first.
    294                 fail(locker, makeString(parseAndCompileResult.error(), ", in function at index ", String::number(functionIndex))); // FIXME make this an Expected.
    295             }
     292            fail(locker, makeString(parseAndCompileResult.error(), ", in function at index ", String::number(functionIndex))); // FIXME make this an Expected.
    296293            m_currentIndex = functions.size();
    297294            return;
     
    325322                LinkBuffer linkBuffer(*context.wasmEntrypointJIT, nullptr, JITCompilationCanFail);
    326323                if (UNLIKELY(linkBuffer.didFailToAllocate())) {
    327                     Base::fail(locker, makeString("Out of executable memory in function at index ", String::number(functionIndex)));
     324                    fail(locker, makeString("Out of executable memory in function at index ", String::number(functionIndex)));
    328325                    return;
    329326                }
     
    337334                LinkBuffer linkBuffer(*context.embedderEntrypointJIT, nullptr, JITCompilationCanFail);
    338335                if (UNLIKELY(linkBuffer.didFailToAllocate())) {
    339                     Base::fail(locker, makeString("Out of executable memory in function entrypoint at index ", String::number(functionIndex)));
     336                    fail(locker, makeString("Out of executable memory in function entrypoint at index ", String::number(functionIndex)));
    340337                    return;
    341338                }
  • trunk/Source/JavaScriptCore/wasm/WasmBBQPlan.h

    r248878 r249708  
    3232#include "WasmModuleInformation.h"
    3333#include "WasmPlan.h"
     34#include "WasmStreamingParser.h"
    3435#include "WasmTierUpCount.h"
    3536#include <wtf/Bag.h>
     
    4546namespace Wasm {
    4647
    47 class BBQPlan final : public Plan {
     48class BBQPlan final : public Plan, public StreamingParserClient {
    4849public:
    4950    using Base = Plan;
     
    122123    bool multiThreaded() const override { return hasBeenPrepared(); }
    123124
     125    void didReceiveFunctionData(unsigned, const FunctionData&) override;
     126
    124127private:
    125128    class ThreadCountHolder;
     
    144147
    145148    Vector<Vector<UnlinkedWasmToWasmCall>> m_unlinkedWasmToWasmCalls;
     149    StreamingParser m_streamingParser;
    146150    State m_state;
    147151
  • trunk/Source/JavaScriptCore/wasm/WasmOMGForOSREntryPlan.cpp

    r248878 r249708  
    8080    SignatureIndex signatureIndex = m_moduleInformation->internalFunctionSignatureIndices[m_functionIndex];
    8181    const Signature& signature = SignatureInformation::get(signatureIndex);
    82     ASSERT(validateFunction(function.data.data(), function.data.size(), signature, m_moduleInformation.get()));
     82    ASSERT(validateFunction(function, signature, m_moduleInformation.get()));
    8383
    8484    Vector<UnlinkedWasmToWasmCall> unlinkedCalls;
    8585    CompilationContext context;
    8686    unsigned osrEntryScratchBufferSize = 0;
    87     auto parseAndCompileResult = parseAndCompile(context, function.data.data(), function.data.size(), signature, unlinkedCalls, osrEntryScratchBufferSize, m_moduleInformation.get(), m_mode, CompilationMode::OMGForOSREntryMode, m_functionIndex, m_loopIndex);
     87    auto parseAndCompileResult = parseAndCompile(context, function, signature, unlinkedCalls, osrEntryScratchBufferSize, m_moduleInformation.get(), m_mode, CompilationMode::OMGForOSREntryMode, m_functionIndex, m_loopIndex);
    8888
    8989    if (UNLIKELY(!parseAndCompileResult)) {
  • trunk/Source/JavaScriptCore/wasm/WasmOMGPlan.cpp

    r248878 r249708  
    7878    SignatureIndex signatureIndex = m_moduleInformation->internalFunctionSignatureIndices[m_functionIndex];
    7979    const Signature& signature = SignatureInformation::get(signatureIndex);
    80     ASSERT(validateFunction(function.data.data(), function.data.size(), signature, m_moduleInformation.get()));
     80    ASSERT(validateFunction(function, signature, m_moduleInformation.get()));
    8181
    8282    Vector<UnlinkedWasmToWasmCall> unlinkedCalls;
    8383    unsigned osrEntryScratchBufferSize;
    8484    CompilationContext context;
    85     auto parseAndCompileResult = parseAndCompile(context, function.data.data(), function.data.size(), signature, unlinkedCalls, osrEntryScratchBufferSize, m_moduleInformation.get(), m_mode, CompilationMode::OMGMode, m_functionIndex, UINT32_MAX);
     85    auto parseAndCompileResult = parseAndCompile(context, function, signature, unlinkedCalls, osrEntryScratchBufferSize, m_moduleInformation.get(), m_mode, CompilationMode::OMGMode, m_functionIndex, UINT32_MAX);
    8686
    8787    if (UNLIKELY(!parseAndCompileResult)) {
  • trunk/Source/JavaScriptCore/wasm/WasmPlan.cpp

    r235420 r249708  
    3636#include "WasmFaultSignalHandler.h"
    3737#include "WasmMemory.h"
    38 #include "WasmModuleParser.h"
    3938#include "WasmValidate.h"
    4039#include <wtf/DataLog.h>
     
    132131void Plan::fail(const AbstractLocker& locker, String&& errorMessage)
    133132{
     133    ASSERT(errorMessage);
     134    if (failed())
     135        return;
    134136    dataLogLnIf(WasmPlanInternal::verbose, "failing with message: ", errorMessage);
    135137    m_errorMessage = WTFMove(errorMessage);
  • trunk/Source/JavaScriptCore/wasm/WasmSectionParser.cpp

    r248833 r249708  
    412412}
    413413
    414 // This function will be changed to be RELEASE_ASSERT_NOT_REACHED once we switch our parsing infrastructure to the streaming parser.
    415414auto SectionParser::parseCode() -> PartialResult
    416415{
    417     m_info->codeSectionSize = length();
    418     uint32_t count;
    419     WASM_PARSER_FAIL_IF(!parseVarUInt32(count), "can't get Code section's count");
    420     WASM_PARSER_FAIL_IF(count == std::numeric_limits<uint32_t>::max(), "Code section's count is too big ", count);
    421     WASM_PARSER_FAIL_IF(count != m_info->functions.size(), "Code section count ", count, " exceeds the declared number of functions ", m_info->functions.size());
    422 
    423     for (uint32_t i = 0; i < count; ++i) {
    424         uint32_t functionSize;
    425         WASM_PARSER_FAIL_IF(!parseVarUInt32(functionSize), "can't get ", i, "th Code function's size");
    426         WASM_PARSER_FAIL_IF(functionSize > length(), "Code function's size ", functionSize, " exceeds the module's size ", length());
    427         WASM_PARSER_FAIL_IF(functionSize > length() - m_offset, "Code function's size ", functionSize, " exceeds the module's remaining size", length() - m_offset);
    428         WASM_PARSER_FAIL_IF(functionSize > maxFunctionSize, "Code function's size ", functionSize, " is too big");
    429 
    430         Vector<uint8_t> data(functionSize);
    431         std::memcpy(data.data(), source() + m_offset, functionSize);
    432         m_info->functions[i].start = m_offsetInSource + m_offset;
    433         m_info->functions[i].end = m_offsetInSource + m_offset + functionSize;
    434         m_info->functions[i].data = WTFMove(data);
    435         m_offset += functionSize;
    436     }
    437 
     416    // The Code section is handled specially in StreamingParser.
     417    RELEASE_ASSERT_NOT_REACHED();
    438418    return { };
    439419}
  • trunk/Source/JavaScriptCore/wasm/WasmStreamingParser.cpp

    r248824 r249708  
    2929#if ENABLE(WEBASSEMBLY)
    3030
    31 #include "WasmModuleParser.h"
    3231#include "WasmSectionParser.h"
    3332#include <wtf/Optional.h>
     
    6867}
    6968
    70 StreamingParser::StreamingParser(ModuleInformation& info)
     69StreamingParser::StreamingParser(ModuleInformation& info, StreamingParserClient& client)
    7170    : m_info(info)
     71    , m_client(client)
    7272{
    7373    dataLogLnIf(WasmStreamingParserInternal::verbose, "starting validation");
     
    121121    if (m_functionIndex == m_functionCount) {
    122122        WASM_PARSER_FAIL_IF((m_codeOffset + m_sectionLength) != m_nextOffset, "parsing ended before the end of ", m_section, " section");
     123        m_client.didReceiveSectionData(m_section);
    123124        return State::SectionID;
    124125    }
     
    140141    function.data = WTFMove(data);
    141142    dataLogLnIf(WasmStreamingParserInternal::verbose, "Processing function starting at: ", function.start, " and ending at: ", function.end);
     143    m_client.didReceiveFunctionData(m_functionIndex, function);
    142144    ++m_functionIndex;
     145
    143146    if (m_functionIndex == m_functionCount) {
    144147        WASM_PARSER_FAIL_IF((m_codeOffset + m_sectionLength) != (m_offset + m_functionSize), "parsing ended before the end of ", m_section, " section");
     148        m_client.didReceiveSectionData(m_section);
    145149        return State::SectionID;
    146150    }
     
    173177    WASM_PARSER_FAIL_IF(parser.length() != parser.offset(), "parsing ended before the end of ", m_section, " section");
    174178
     179    m_client.didReceiveSectionData(m_section);
    175180    return State::SectionID;
    176181}
     
    383388                m_info->nameSection->setHash(m_hasher.computeHexDigest());
    384389            m_state = State::Finished;
     390            m_client.didFinishParsing();
    385391        } else
    386392            m_state = failOnState(State::SectionID);
  • trunk/Source/JavaScriptCore/wasm/WasmStreamingParser.h

    r242776 r249708  
    3838
    3939class StreamingParserClient {
     40public:
     41    virtual ~StreamingParserClient() = default;
     42    virtual void didReceiveSectionData(Section) { }
     43    virtual void didReceiveFunctionData(unsigned, const FunctionData&) { }
     44    virtual void didFinishParsing() { }
    4045};
    4146
     
    6873    enum class IsEndOfStream { Yes, No };
    6974
    70     StreamingParser(ModuleInformation&);
     75    StreamingParser(ModuleInformation&, StreamingParserClient&);
    7176
    7277    State addBytes(const uint8_t* bytes, size_t length) { return addBytes(bytes, length, IsEndOfStream::No); }
     
    98103
    99104    Ref<ModuleInformation> m_info;
     105    StreamingParserClient& m_client;
    100106    Vector<uint8_t> m_remaining;
    101107    String m_errorMessage;
  • trunk/Source/JavaScriptCore/wasm/WasmValidate.cpp

    r249221 r249708  
    462462}
    463463
    464 Expected<void, String> validateFunction(const uint8_t* source, size_t length, const Signature& signature, const ModuleInformation& module)
     464Expected<void, String> validateFunction(const FunctionData& function, const Signature& signature, const ModuleInformation& module)
    465465{
    466466    Validate context(module);
    467     FunctionParser<Validate> validator(context, source, length, signature, module);
     467    FunctionParser<Validate> validator(context, function.data.data(), function.data.size(), signature, module);
    468468    WASM_FAIL_IF_HELPER_FAILS(validator.parse());
    469469    return { };
  • trunk/Source/JavaScriptCore/wasm/WasmValidate.h

    r214919 r249708  
    3535namespace Wasm {
    3636
    37 Expected<void, String> validateFunction(const uint8_t*, size_t, const Signature&, const ModuleInformation&);
     37Expected<void, String> validateFunction(const FunctionData&, const Signature&, const ModuleInformation&);
    3838
    3939} } // namespace JSC::Wasm
Note: See TracChangeset for help on using the changeset viewer.