Title: [214498] trunk/Source/_javascript_Core
Revision
214498
Author
[email protected]
Date
2017-03-28 15:16:01 -0700 (Tue, 28 Mar 2017)

Log Message

WebAssembly: add fallback to use pinned register to load/store state
https://bugs.webkit.org/show_bug.cgi?id=169773

Reviewed by Saam Barati.

This patch adds a new pinned register to hold JSWebAssemblyInstance,
which is used to represent the context of running Wasm code.
While we use fast TLS to hold the context in macOS, we do not have
any system reserved fast TLS slot in the other systems. This pinned
register approach is used in these systems. These changes decouple
VM from Wasm module to make Wasm module position independent code.

While using fast TLS could be beneficial in x64 systems which number of
registers is relatively small, pinned register approach could be
beneficial in ARM64 which has plenty of registers. In macOS, we can
switch the implementation with the runtime flag. Thus macOS port can
compare the performance and decide which implementation is used after
landing this patch.

* heap/MarkedBlock.h:
(JSC::MarkedBlock::offsetOfVM):
* jit/AssemblyHelpers.cpp:
(JSC::AssemblyHelpers::loadWasmContext):
(JSC::AssemblyHelpers::storeWasmContext):
(JSC::AssemblyHelpers::loadWasmContextNeedsMacroScratchRegister):
(JSC::AssemblyHelpers::storeWasmContextNeedsMacroScratchRegister):
* jit/AssemblyHelpers.h:
(JSC::AssemblyHelpers::loadWasmContext): Deleted.
(JSC::AssemblyHelpers::storeWasmContext): Deleted.
(JSC::AssemblyHelpers::loadWasmContextNeedsMacroScratchRegister): Deleted.
(JSC::AssemblyHelpers::storeWasmContextNeedsMacroScratchRegister): Deleted.
* jit/Repatch.cpp:
(JSC::webAssemblyOwner):
(JSC::linkFor):
(JSC::linkPolymorphicCall):
(JSC::isWebAssemblyToJSCallee): Deleted.
* jit/ThunkGenerators.cpp:
(JSC::throwExceptionFromWasmThunkGenerator):
* llint/LLIntData.cpp:
(JSC::LLInt::Data::performAssertions):
* llint/LowLevelInterpreter.asm:
* runtime/JSCell.cpp:
(JSC::JSCell::isAnyWasmCallee):
* runtime/JSCellInlines.h:
(JSC::isWebAssemblyToJSCallee):
* runtime/JSType.h:
* runtime/StackFrame.cpp:
(JSC::StackFrame::functionName):
* runtime/VM.cpp:
(JSC::VM::VM):
* runtime/VM.h:
(JSC::VM::wasmContextOffset):
* wasm/WasmB3IRGenerator.cpp:
(JSC::Wasm::B3IRGenerator::materializeWasmContext):
(JSC::Wasm::B3IRGenerator::restoreWasmContext):
(JSC::Wasm::B3IRGenerator::B3IRGenerator):
(JSC::Wasm::getMemoryBaseAndSize):
(JSC::Wasm::B3IRGenerator::restoreWebAssemblyGlobalState):
(JSC::Wasm::createJSToWasmWrapper):
(JSC::Wasm::loadWasmContext): Deleted.
(JSC::Wasm::storeWasmContext): Deleted.
(JSC::Wasm::restoreWebAssemblyGlobalState): Deleted.
* wasm/WasmBinding.cpp:
(JSC::Wasm::wasmToJs):
* wasm/WasmContext.cpp:
(JSC::loadWasmContext):
(JSC::storeWasmContext):
* wasm/WasmContext.h:
* wasm/WasmMemoryInformation.cpp:
(JSC::Wasm::getPinnedRegisters):
(JSC::Wasm::PinnedRegisterInfo::get):
(JSC::Wasm::PinnedRegisterInfo::PinnedRegisterInfo):
* wasm/WasmMemoryInformation.h:
(JSC::Wasm::PinnedRegisterInfo::toSave):
(JSC::Wasm::useFastTLS):
(JSC::Wasm::useFastTLSForWasmContext):
* wasm/js/JSWebAssemblyInstance.cpp:
(JSC::JSWebAssemblyInstance::finishCreation):
(JSC::JSWebAssemblyInstance::visitChildren):
* wasm/js/JSWebAssemblyInstance.h:
(JSC::JSWebAssemblyInstance::offsetOfCallee):
* wasm/js/JSWebAssemblyModule.cpp:
(JSC::JSWebAssemblyModule::finishCreation):
(JSC::JSWebAssemblyModule::visitChildren):
* wasm/js/JSWebAssemblyModule.h:
(JSC::JSWebAssemblyModule::callee):
* wasm/js/WebAssemblyFunction.cpp:
(JSC::callWebAssemblyFunction):
(JSC::WebAssemblyFunction::create):
* wasm/js/WebAssemblyToJSCallee.cpp:
(JSC::WebAssemblyToJSCallee::create):
(JSC::WebAssemblyToJSCallee::createStructure):
(JSC::WebAssemblyToJSCallee::finishCreation):
(JSC::WebAssemblyToJSCallee::visitChildren):
(JSC::WebAssemblyToJSCallee::destroy): Deleted.
* wasm/js/WebAssemblyToJSCallee.h:

Modified Paths

Diff

Modified: trunk/Source/_javascript_Core/ChangeLog (214497 => 214498)


--- trunk/Source/_javascript_Core/ChangeLog	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/ChangeLog	2017-03-28 22:16:01 UTC (rev 214498)
@@ -1,3 +1,102 @@
+2017-03-28  Yusuke Suzuki  <[email protected]>
+
+        WebAssembly: add fallback to use pinned register to load/store state
+        https://bugs.webkit.org/show_bug.cgi?id=169773
+
+        Reviewed by Saam Barati.
+
+        This patch adds a new pinned register to hold JSWebAssemblyInstance,
+        which is used to represent the context of running Wasm code.
+        While we use fast TLS to hold the context in macOS, we do not have
+        any system reserved fast TLS slot in the other systems. This pinned
+        register approach is used in these systems. These changes decouple
+        VM from Wasm module to make Wasm module position independent code.
+
+        While using fast TLS could be beneficial in x64 systems which number of
+        registers is relatively small, pinned register approach could be
+        beneficial in ARM64 which has plenty of registers. In macOS, we can
+        switch the implementation with the runtime flag. Thus macOS port can
+        compare the performance and decide which implementation is used after
+        landing this patch.
+
+        * heap/MarkedBlock.h:
+        (JSC::MarkedBlock::offsetOfVM):
+        * jit/AssemblyHelpers.cpp:
+        (JSC::AssemblyHelpers::loadWasmContext):
+        (JSC::AssemblyHelpers::storeWasmContext):
+        (JSC::AssemblyHelpers::loadWasmContextNeedsMacroScratchRegister):
+        (JSC::AssemblyHelpers::storeWasmContextNeedsMacroScratchRegister):
+        * jit/AssemblyHelpers.h:
+        (JSC::AssemblyHelpers::loadWasmContext): Deleted.
+        (JSC::AssemblyHelpers::storeWasmContext): Deleted.
+        (JSC::AssemblyHelpers::loadWasmContextNeedsMacroScratchRegister): Deleted.
+        (JSC::AssemblyHelpers::storeWasmContextNeedsMacroScratchRegister): Deleted.
+        * jit/Repatch.cpp:
+        (JSC::webAssemblyOwner):
+        (JSC::linkFor):
+        (JSC::linkPolymorphicCall):
+        (JSC::isWebAssemblyToJSCallee): Deleted.
+        * jit/ThunkGenerators.cpp:
+        (JSC::throwExceptionFromWasmThunkGenerator):
+        * llint/LLIntData.cpp:
+        (JSC::LLInt::Data::performAssertions):
+        * llint/LowLevelInterpreter.asm:
+        * runtime/JSCell.cpp:
+        (JSC::JSCell::isAnyWasmCallee):
+        * runtime/JSCellInlines.h:
+        (JSC::isWebAssemblyToJSCallee):
+        * runtime/JSType.h:
+        * runtime/StackFrame.cpp:
+        (JSC::StackFrame::functionName):
+        * runtime/VM.cpp:
+        (JSC::VM::VM):
+        * runtime/VM.h:
+        (JSC::VM::wasmContextOffset):
+        * wasm/WasmB3IRGenerator.cpp:
+        (JSC::Wasm::B3IRGenerator::materializeWasmContext):
+        (JSC::Wasm::B3IRGenerator::restoreWasmContext):
+        (JSC::Wasm::B3IRGenerator::B3IRGenerator):
+        (JSC::Wasm::getMemoryBaseAndSize):
+        (JSC::Wasm::B3IRGenerator::restoreWebAssemblyGlobalState):
+        (JSC::Wasm::createJSToWasmWrapper):
+        (JSC::Wasm::loadWasmContext): Deleted.
+        (JSC::Wasm::storeWasmContext): Deleted.
+        (JSC::Wasm::restoreWebAssemblyGlobalState): Deleted.
+        * wasm/WasmBinding.cpp:
+        (JSC::Wasm::wasmToJs):
+        * wasm/WasmContext.cpp:
+        (JSC::loadWasmContext):
+        (JSC::storeWasmContext):
+        * wasm/WasmContext.h:
+        * wasm/WasmMemoryInformation.cpp:
+        (JSC::Wasm::getPinnedRegisters):
+        (JSC::Wasm::PinnedRegisterInfo::get):
+        (JSC::Wasm::PinnedRegisterInfo::PinnedRegisterInfo):
+        * wasm/WasmMemoryInformation.h:
+        (JSC::Wasm::PinnedRegisterInfo::toSave):
+        (JSC::Wasm::useFastTLS):
+        (JSC::Wasm::useFastTLSForWasmContext):
+        * wasm/js/JSWebAssemblyInstance.cpp:
+        (JSC::JSWebAssemblyInstance::finishCreation):
+        (JSC::JSWebAssemblyInstance::visitChildren):
+        * wasm/js/JSWebAssemblyInstance.h:
+        (JSC::JSWebAssemblyInstance::offsetOfCallee):
+        * wasm/js/JSWebAssemblyModule.cpp:
+        (JSC::JSWebAssemblyModule::finishCreation):
+        (JSC::JSWebAssemblyModule::visitChildren):
+        * wasm/js/JSWebAssemblyModule.h:
+        (JSC::JSWebAssemblyModule::callee):
+        * wasm/js/WebAssemblyFunction.cpp:
+        (JSC::callWebAssemblyFunction):
+        (JSC::WebAssemblyFunction::create):
+        * wasm/js/WebAssemblyToJSCallee.cpp:
+        (JSC::WebAssemblyToJSCallee::create):
+        (JSC::WebAssemblyToJSCallee::createStructure):
+        (JSC::WebAssemblyToJSCallee::finishCreation):
+        (JSC::WebAssemblyToJSCallee::visitChildren):
+        (JSC::WebAssemblyToJSCallee::destroy): Deleted.
+        * wasm/js/WebAssemblyToJSCallee.h:
+
 2017-03-28  Brian Burg  <[email protected]>
 
         Web Inspector: Add "Disable Caches" option that only applies to the inspected page while Web Inspector is open

Modified: trunk/Source/_javascript_Core/heap/MarkedBlock.h (214497 => 214498)


--- trunk/Source/_javascript_Core/heap/MarkedBlock.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/heap/MarkedBlock.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -298,6 +298,11 @@
     
     bool isMarkedRaw(const void* p);
     HeapVersion markingVersion() const { return m_markingVersion; }
+
+    static ptrdiff_t offsetOfVM()
+    {
+        return OBJECT_OFFSETOF(MarkedBlock, m_vm);
+    }
     
 private:
     static const size_t atomAlignmentMask = atomSize - 1;

Modified: trunk/Source/_javascript_Core/jit/AssemblyHelpers.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/jit/AssemblyHelpers.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/jit/AssemblyHelpers.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -32,6 +32,10 @@
 #include "JSCInlines.h"
 #include "LinkBuffer.h"
 
+#if ENABLE(WEBASSEMBLY)
+#include "WasmMemoryInformation.h"
+#endif
+
 namespace JSC {
 
 ExecutableBase* AssemblyHelpers::executableFor(const CodeOrigin& codeOrigin)
@@ -766,6 +770,49 @@
     done.link(this);
 }
 
+#if ENABLE(WEBASSEMBLY)
+void AssemblyHelpers::loadWasmContext(GPRReg dst)
+{
+#if ENABLE(FAST_TLS_JIT)
+    if (Wasm::useFastTLSForWasmContext()) {
+        loadFromTLSPtr(fastTLSOffsetForKey(WTF_WASM_CONTEXT_KEY), dst);
+        return;
+    }
+#endif
+    move(Wasm::PinnedRegisterInfo::get().wasmContextPointer, dst);
+}
+
+void AssemblyHelpers::storeWasmContext(GPRReg src)
+{
+#if ENABLE(FAST_TLS_JIT)
+    if (Wasm::useFastTLSForWasmContext()) {
+        storeToTLSPtr(src, fastTLSOffsetForKey(WTF_WASM_CONTEXT_KEY));
+        return;
+    }
+#endif
+    move(src, Wasm::PinnedRegisterInfo::get().wasmContextPointer);
+}
+
+bool AssemblyHelpers::loadWasmContextNeedsMacroScratchRegister()
+{
+#if ENABLE(FAST_TLS_JIT)
+    if (Wasm::useFastTLSForWasmContext())
+        return loadFromTLSPtrNeedsMacroScratchRegister();
+#endif
+    return false;
+}
+
+bool AssemblyHelpers::storeWasmContextNeedsMacroScratchRegister()
+{
+#if ENABLE(FAST_TLS_JIT)
+    if (Wasm::useFastTLSForWasmContext())
+        return storeToTLSPtrNeedsMacroScratchRegister();
+#endif
+    return false;
+}
+
+#endif
+
 } // namespace JSC
 
 #endif // ENABLE(JIT)

Modified: trunk/Source/_javascript_Core/jit/AssemblyHelpers.h (214497 => 214498)


--- trunk/Source/_javascript_Core/jit/AssemblyHelpers.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/jit/AssemblyHelpers.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -1636,46 +1636,13 @@
     void wangsInt64Hash(GPRReg inputAndResult, GPRReg scratch);
 #endif
 
-    void loadWasmContext(GPRReg dst)
-    {
-#if ENABLE(FAST_TLS_JIT)
-        if (Options::useWebAssemblyFastTLS()) {
-            loadFromTLSPtr(fastTLSOffsetForKey(WTF_WASM_CONTEXT_KEY), dst);
-            return;
-        }
+#if ENABLE(WEBASSEMBLY)
+    void loadWasmContext(GPRReg dst);
+    void storeWasmContext(GPRReg src);
+    static bool loadWasmContextNeedsMacroScratchRegister();
+    static bool storeWasmContextNeedsMacroScratchRegister();
 #endif
-        // FIXME: Save this state elsewhere to allow PIC. https://bugs.webkit.org/show_bug.cgi?id=169773
-        loadPtr(&m_vm->wasmContext, dst);
-    }
 
-    void storeWasmContext(GPRReg src)
-    {
-#if ENABLE(FAST_TLS_JIT)
-        if (Options::useWebAssemblyFastTLS())
-            return storeToTLSPtr(src, fastTLSOffsetForKey(WTF_WASM_CONTEXT_KEY));
-#endif
-        // FIXME: Save this state elsewhere to allow PIC. https://bugs.webkit.org/show_bug.cgi?id=169773
-        storePtr(src, &m_vm->wasmContext);
-    }
-
-    static bool loadWasmContextNeedsMacroScratchRegister()
-    {
-#if ENABLE(FAST_TLS_JIT)
-        if (Options::useWebAssemblyFastTLS())
-            return loadFromTLSPtrNeedsMacroScratchRegister();
-#endif
-        return true;
-    }
-
-    static bool storeWasmContextNeedsMacroScratchRegister()
-    {
-#if ENABLE(FAST_TLS_JIT)
-        if (Options::useWebAssemblyFastTLS())
-            return storeToTLSPtrNeedsMacroScratchRegister();
-#endif
-        return true;
-    }
-
 protected:
     VM* m_vm;
     CodeBlock* m_codeBlock;

Modified: trunk/Source/_javascript_Core/jit/Repatch.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/jit/Repatch.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/jit/Repatch.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -59,7 +59,6 @@
 #include "StructureStubClearingWatchpoint.h"
 #include "StructureStubInfo.h"
 #include "ThunkGenerators.h"
-#include "WasmContext.h"
 #include <wtf/CommaPrinter.h>
 #include <wtf/ListDump.h>
 #include <wtf/StringPrintStream.h>
@@ -577,25 +576,13 @@
     callLinkInfo.setSlowStub(createJITStubRoutine(virtualThunk, *vm, nullptr, true));
 }
 
-static bool isWebAssemblyToJSCallee(VM& vm, JSCell* callee)
+static JSCell* webAssemblyOwner(JSCell* callee)
 {
 #if ENABLE(WEBASSEMBLY)
-    // The WebAssembly -> JS stub sets it caller frame's callee to a singleton which lives on the VM.
-    return callee == vm.webAssemblyToJSCallee.get();
+    // Each WebAssembly.Instance shares the stubs from their WebAssembly.Module, which are therefore the appropriate owner.
+    return jsCast<WebAssemblyToJSCallee*>(callee)->module();
 #else
-    UNUSED_PARAM(vm);
     UNUSED_PARAM(callee);
-    return false;
-#endif // ENABLE(WEBASSEMBLY)
-}
-
-static JSCell* webAssemblyOwner(VM& vm)
-{
-#if ENABLE(WEBASSEMBLY)
-    // Each WebAssembly.Instance shares the stubs from their WebAssembly.Module, which are therefore the appropriate owner.
-    return loadWasmContext(vm)->module();
-#else
-    UNUSED_PARAM(vm);
     RELEASE_ASSERT_NOT_REACHED();
     return nullptr;
 #endif // ENABLE(WEBASSEMBLY)
@@ -612,7 +599,7 @@
     CodeBlock* callerCodeBlock = callerFrame->codeBlock();
 
     // WebAssembly -> JS stubs don't have a valid CodeBlock.
-    JSCell* owner = isWebAssemblyToJSCallee(vm, callerFrame->callee()) ? webAssemblyOwner(vm) : callerCodeBlock;
+    JSCell* owner = isWebAssemblyToJSCallee(callerFrame->callee()) ? webAssemblyOwner(callerFrame->callee()) : callerCodeBlock;
     ASSERT(owner);
 
     ASSERT(!callLinkInfo.isLinked());
@@ -732,10 +719,10 @@
     CallFrame* callerFrame = exec->callerFrame();
     VM& vm = callerFrame->vm();
     CodeBlock* callerCodeBlock = callerFrame->codeBlock();
-    bool isWebAssembly = isWebAssemblyToJSCallee(vm, callerFrame->callee());
+    bool isWebAssembly = isWebAssemblyToJSCallee(callerFrame->callee());
 
     // WebAssembly -> JS stubs don't have a valid CodeBlock.
-    JSCell* owner = isWebAssembly ? webAssemblyOwner(vm) : callerCodeBlock;
+    JSCell* owner = isWebAssembly ? webAssemblyOwner(callerFrame->callee()) : callerCodeBlock;
     ASSERT(owner);
 
     CallVariantList list;

Modified: trunk/Source/_javascript_Core/jit/ThunkGenerators.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/jit/ThunkGenerators.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/jit/ThunkGenerators.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -38,7 +38,6 @@
 #include "MathCommon.h"
 #include "MaxFrameExtentForSlowPathCall.h"
 #include "SpecializedThunkJIT.h"
-#include "WasmContext.h"
 #include "WasmExceptionType.h"
 #include <wtf/InlineASM.h>
 #include <wtf/StringPrintStream.h>
@@ -1148,16 +1147,17 @@
     }
 
     jit.move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR0);
+    jit.loadWasmContext(GPRInfo::argumentGPR2);
     CCallHelpers::Call call = jit.call();
     jit.jumpToExceptionHandler();
 
-    void (*throwWasmException)(ExecState*, Wasm::ExceptionType) = [] (ExecState* exec, Wasm::ExceptionType type) {
+    void (*throwWasmException)(ExecState*, Wasm::ExceptionType, JSWebAssemblyInstance*) = [] (ExecState* exec, Wasm::ExceptionType type, JSWebAssemblyInstance* wasmContext) {
         VM* vm = &exec->vm();
         NativeCallFrameTracer tracer(vm, exec);
 
         {
             auto throwScope = DECLARE_THROW_SCOPE(*vm);
-            JSGlobalObject* globalObject = loadWasmContext(*vm)->globalObject();
+            JSGlobalObject* globalObject = wasmContext->globalObject();
 
             JSWebAssemblyRuntimeError* error = JSWebAssemblyRuntimeError::create(exec, *vm, globalObject->WebAssemblyRuntimeErrorStructure(), Wasm::errorMessageForExceptionType(type));
             throwException(exec, throwScope, error);

Modified: trunk/Source/_javascript_Core/llint/LLIntData.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/llint/LLIntData.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/llint/LLIntData.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -156,21 +156,21 @@
     
     STATIC_ASSERT(StringType == 6);
     STATIC_ASSERT(SymbolType == 7);
-    STATIC_ASSERT(ObjectType == 23);
-    STATIC_ASSERT(FinalObjectType == 24);
-    STATIC_ASSERT(JSFunctionType == 26);
-    STATIC_ASSERT(ArrayType == 34);
-    STATIC_ASSERT(DerivedArrayType == 35);
-    STATIC_ASSERT(ProxyObjectType == 53);
-    STATIC_ASSERT(Int8ArrayType == 36);
-    STATIC_ASSERT(Int16ArrayType == 37);
-    STATIC_ASSERT(Int32ArrayType == 38);
-    STATIC_ASSERT(Uint8ArrayType == 39);
-    STATIC_ASSERT(Uint8ClampedArrayType == 40);
-    STATIC_ASSERT(Uint16ArrayType == 41);
-    STATIC_ASSERT(Uint32ArrayType == 42);
-    STATIC_ASSERT(Float32ArrayType == 43);
-    STATIC_ASSERT(Float64ArrayType == 44);
+    STATIC_ASSERT(ObjectType == 24);
+    STATIC_ASSERT(FinalObjectType == 25);
+    STATIC_ASSERT(JSFunctionType == 27);
+    STATIC_ASSERT(ArrayType == 35);
+    STATIC_ASSERT(DerivedArrayType == 36);
+    STATIC_ASSERT(ProxyObjectType == 54);
+    STATIC_ASSERT(Int8ArrayType == 37);
+    STATIC_ASSERT(Int16ArrayType == 38);
+    STATIC_ASSERT(Int32ArrayType == 39);
+    STATIC_ASSERT(Uint8ArrayType == 40);
+    STATIC_ASSERT(Uint8ClampedArrayType == 41);
+    STATIC_ASSERT(Uint16ArrayType == 42);
+    STATIC_ASSERT(Uint32ArrayType == 43);
+    STATIC_ASSERT(Float32ArrayType == 44);
+    STATIC_ASSERT(Float64ArrayType == 45);
     STATIC_ASSERT(MasqueradesAsUndefined == 1);
     STATIC_ASSERT(ImplementsDefaultHasInstance == 2);
     STATIC_ASSERT(FirstConstantRegisterIndex == 0x40000000);

Modified: trunk/Source/_javascript_Core/llint/LowLevelInterpreter.asm (214497 => 214498)


--- trunk/Source/_javascript_Core/llint/LowLevelInterpreter.asm	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/llint/LowLevelInterpreter.asm	2017-03-28 22:16:01 UTC (rev 214498)
@@ -345,24 +345,24 @@
 # Type constants.
 const StringType = 6
 const SymbolType = 7
-const ObjectType = 23
-const FinalObjectType = 24
-const JSFunctionType = 26
-const ArrayType = 34
-const DerivedArrayType = 35
-const ProxyObjectType = 53
+const ObjectType = 24
+const FinalObjectType = 25
+const JSFunctionType = 27
+const ArrayType = 35
+const DerivedArrayType = 36
+const ProxyObjectType = 54
 
 # The typed array types need to be numbered in a particular order because of the manually written
 # switch statement in get_by_val and put_by_val.
-const Int8ArrayType = 36
-const Int16ArrayType = 37
-const Int32ArrayType = 38
-const Uint8ArrayType = 39
-const Uint8ClampedArrayType = 40
-const Uint16ArrayType = 41
-const Uint32ArrayType = 42
-const Float32ArrayType = 43
-const Float64ArrayType = 44
+const Int8ArrayType = 37
+const Int16ArrayType = 38
+const Int32ArrayType = 39
+const Uint8ArrayType = 40
+const Uint8ClampedArrayType = 41
+const Uint16ArrayType = 42
+const Uint32ArrayType = 43
+const Float32ArrayType = 44
+const Float64ArrayType = 45
 
 const FirstArrayType = Int8ArrayType
 const LastArrayType = Float64ArrayType

Modified: trunk/Source/_javascript_Core/runtime/JSCell.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/runtime/JSCell.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/runtime/JSCell.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -298,7 +298,7 @@
 bool JSCell::isAnyWasmCallee(VM& vm) const
 {
 #if ENABLE(WEBASSEMBLY)
-    return inherits(vm, JSWebAssemblyCallee::info()) || inherits(vm, WebAssemblyToJSCallee::info());
+    return inherits(vm, JSWebAssemblyCallee::info()) || isWebAssemblyToJSCallee(this);
 #else
     UNUSED_PARAM(vm);
     return false;

Modified: trunk/Source/_javascript_Core/runtime/JSCellInlines.h (214497 => 214498)


--- trunk/Source/_javascript_Core/runtime/JSCellInlines.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/runtime/JSCellInlines.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -346,4 +346,9 @@
     return toObjectSlow(exec, globalObject);
 }
 
+inline bool isWebAssemblyToJSCallee(const JSCell* cell)
+{
+    return cell->type() == WebAssemblyToJSCalleeType;
+}
+
 } // namespace JSC

Modified: trunk/Source/_javascript_Core/runtime/JSType.h (214497 => 214498)


--- trunk/Source/_javascript_Core/runtime/JSType.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/runtime/JSType.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -53,6 +53,8 @@
     JSSourceCodeType,
     JSScriptFetcherType,
 
+    WebAssemblyToJSCalleeType,
+
     // The ObjectType value must come before any JSType that is a subclass of JSObject.
     ObjectType,
     FinalObjectType,

Modified: trunk/Source/_javascript_Core/runtime/StackFrame.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/runtime/StackFrame.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/runtime/StackFrame.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -72,10 +72,10 @@
     }
     String name;
     if (m_callee) {
+        if (m_callee->isAnyWasmCallee(*m_callee->vm()))
+            return ASCIILiteral("<wasm>");
         if (m_callee->isObject())
             name = getCalculatedDisplayName(vm, jsCast<JSObject*>(m_callee.get())).impl();
-        else if (m_callee->isAnyWasmCallee(*m_callee->vm()))
-            return ASCIILiteral("<wasm>");
     }
     return name.isNull() ? emptyString() : name;
 }

Modified: trunk/Source/_javascript_Core/runtime/VM.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/runtime/VM.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/runtime/VM.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -240,7 +240,6 @@
     webAssemblyCalleeStructure.set(*this, JSWebAssemblyCallee::createStructure(*this, 0, jsNull()));
     webAssemblyToJSCalleeStructure.set(*this, WebAssemblyToJSCallee::createStructure(*this, 0, jsNull()));
     webAssemblyCodeBlockStructure.set(*this, JSWebAssemblyCodeBlock::createStructure(*this, 0, jsNull()));
-    webAssemblyToJSCallee.set(*this, WebAssemblyToJSCallee::create(*this, webAssemblyToJSCalleeStructure.get()));
 #endif
     moduleProgramExecutableStructure.set(*this, ModuleProgramExecutable::createStructure(*this, 0, jsNull()));
     regExpStructure.set(*this, RegExp::createStructure(*this, 0, jsNull()));

Modified: trunk/Source/_javascript_Core/runtime/VM.h (214497 => 214498)


--- trunk/Source/_javascript_Core/runtime/VM.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/runtime/VM.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -336,7 +336,6 @@
     Strong<Structure> webAssemblyCalleeStructure;
     Strong<Structure> webAssemblyToJSCalleeStructure;
     Strong<Structure> webAssemblyCodeBlockStructure;
-    Strong<JSCell> webAssemblyToJSCallee;
 #endif
     Strong<Structure> moduleProgramExecutableStructure;
     Strong<Structure> regExpStructure;
@@ -490,6 +489,11 @@
         return OBJECT_OFFSETOF(VM, targetMachinePCForThrow);
     }
 
+    static ptrdiff_t wasmContextOffset()
+    {
+        return OBJECT_OFFSETOF(VM, wasmContext);
+    }
+
     void restorePreviousException(Exception* exception) { setException(exception); }
 
     void clearLastException() { m_lastException = nullptr; }

Modified: trunk/Source/_javascript_Core/wasm/WasmB3IRGenerator.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/WasmB3IRGenerator.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/WasmB3IRGenerator.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -35,6 +35,7 @@
 #include "B3ConstPtrValue.h"
 #include "B3FixSSA.h"
 #include "B3Generate.h"
+#include "B3SlotBaseValue.h"
 #include "B3StackmapGenerationParams.h"
 #include "B3SwitchValue.h"
 #include "B3Validate.h"
@@ -49,7 +50,6 @@
 #include "JSWebAssemblyRuntimeError.h"
 #include "VirtualRegister.h"
 #include "WasmCallingConvention.h"
-#include "WasmContext.h"
 #include "WasmExceptionType.h"
 #include "WasmFunctionParser.h"
 #include "WasmMemory.h"
@@ -219,6 +219,10 @@
 
     void emitChecksForModOrDiv(B3::Opcode, ExpressionType left, ExpressionType right);
 
+    Value* materializeWasmContext(Procedure&, BasicBlock*);
+    void restoreWasmContext(Procedure&, BasicBlock*, Value*);
+    void restoreWebAssemblyGlobalState(const MemoryInformation&, Value* instance, Procedure&, BasicBlock*);
+
     VM& m_vm;
     const ModuleInformation& m_info;
     Procedure& m_proc;
@@ -227,35 +231,63 @@
     Vector<UnlinkedWasmToWasmCall>& m_unlinkedWasmToWasmCalls; // List each call site and the function index whose address it should be patched with.
     GPRReg m_memoryBaseGPR;
     GPRReg m_memorySizeGPR;
+    GPRReg m_wasmContextGPR;
     Value* m_zeroValues[numTypes];
     Value* m_instanceValue; // FIXME: make this lazy https://bugs.webkit.org/show_bug.cgi?id=169792
 };
 
-static Value* loadWasmContext(Procedure& proc, BasicBlock* block)
+Value* B3IRGenerator::materializeWasmContext(Procedure& proc, BasicBlock* block)
 {
+    if (useFastTLSForWasmContext()) {
+        PatchpointValue* patchpoint = block->appendNew<PatchpointValue>(proc, pointerType(), Origin());
+        if (CCallHelpers::loadWasmContextNeedsMacroScratchRegister())
+            patchpoint->clobber(RegisterSet::macroScratchRegisters());
+        patchpoint->setGenerator(
+            [=] (CCallHelpers& jit, const StackmapGenerationParams& params) {
+                AllowMacroScratchRegisterUsageIf allowScratch(jit, CCallHelpers::loadWasmContextNeedsMacroScratchRegister());
+                jit.loadWasmContext(params[0].gpr());
+            });
+        return patchpoint;
+    }
+
+    // FIXME: Because WasmToWasm call clobbers wasmContext register and does not restore it, we need to restore it in the caller side.
+    // This prevents us from using ArgumentReg to this (logically) immutable pinned register.
     PatchpointValue* patchpoint = block->appendNew<PatchpointValue>(proc, pointerType(), Origin());
-    if (CCallHelpers::loadWasmContextNeedsMacroScratchRegister())
-        patchpoint->clobber(RegisterSet::macroScratchRegisters());
-    patchpoint->setGenerator(
-        [&] (CCallHelpers& jit, const StackmapGenerationParams& params) {
-            AllowMacroScratchRegisterUsageIf allowScratch(jit, CCallHelpers::loadWasmContextNeedsMacroScratchRegister());
-            jit.loadWasmContext(params[0].gpr());
-        });
-
-    return block->appendNew<Value>(proc, Identity, Origin(), patchpoint);
+    patchpoint->effects.writesPinned = false;
+    patchpoint->effects.readsPinned = true;
+    patchpoint->resultConstraint = ValueRep::reg(m_wasmContextGPR);
+    patchpoint->setGenerator([] (CCallHelpers&, const StackmapGenerationParams&) { });
+    return patchpoint;
 }
 
-static void storeWasmContext(Procedure& proc, BasicBlock* block, Value* arg)
+void B3IRGenerator::restoreWasmContext(Procedure& proc, BasicBlock* block, Value* arg)
 {
+    if (useFastTLSForWasmContext()) {
+        PatchpointValue* patchpoint = block->appendNew<PatchpointValue>(proc, B3::Void, Origin());
+        if (CCallHelpers::storeWasmContextNeedsMacroScratchRegister())
+            patchpoint->clobber(RegisterSet::macroScratchRegisters());
+        patchpoint->append(ConstrainedValue(arg, ValueRep::SomeRegister));
+        patchpoint->setGenerator(
+            [=] (CCallHelpers& jit, const StackmapGenerationParams& params) {
+                AllowMacroScratchRegisterUsageIf allowScratch(jit, CCallHelpers::storeWasmContextNeedsMacroScratchRegister());
+                jit.storeWasmContext(params[0].gpr());
+            });
+        return;
+    }
+
+    // FIXME: Because WasmToWasm call clobbers wasmContext register and does not restore it, we need to restore it in the caller side.
+    // This prevents us from using ArgumentReg to this (logically) immutable pinned register.
     PatchpointValue* patchpoint = block->appendNew<PatchpointValue>(proc, B3::Void, Origin());
-    if (CCallHelpers::storeWasmContextNeedsMacroScratchRegister())
-        patchpoint->clobber(RegisterSet::macroScratchRegisters());
-    patchpoint->append(ConstrainedValue(arg, ValueRep::SomeRegister));
-    patchpoint->setGenerator(
-        [&] (CCallHelpers& jit, const StackmapGenerationParams& params) {
-            AllowMacroScratchRegisterUsageIf allowScratch(jit, CCallHelpers::storeWasmContextNeedsMacroScratchRegister());
-            jit.storeWasmContext(params[0].gpr());
-        });
+    Effects effects = Effects::none();
+    effects.writesPinned = true;
+    effects.reads = B3::HeapRange::top();
+    patchpoint->effects = effects;
+    patchpoint->clobberLate(RegisterSet(m_wasmContextGPR));
+    patchpoint->append(m_instanceValue, ValueRep::SomeRegister);
+    GPRReg wasmContextGPR = m_wasmContextGPR;
+    patchpoint->setGenerator([=] (CCallHelpers& jit, const StackmapGenerationParams& param) {
+        jit.move(param[0].gpr(), wasmContextGPR);
+    });
 }
 
 B3IRGenerator::B3IRGenerator(VM& vm, const ModuleInformation& info, Procedure& procedure, WasmInternalFunction* compilation, Vector<UnlinkedWasmToWasmCall>& unlinkedWasmToWasmCalls)
@@ -283,7 +315,10 @@
     // FIXME we don't really need to pin registers here if there's no memory. It makes wasm -> wasm thunks simpler for now. https://bugs.webkit.org/show_bug.cgi?id=166623
     const PinnedRegisterInfo& pinnedRegs = PinnedRegisterInfo::get();
     m_memoryBaseGPR = pinnedRegs.baseMemoryPointer;
+    m_wasmContextGPR = pinnedRegs.wasmContextPointer;
     m_proc.pinRegister(m_memoryBaseGPR);
+    if (!useFastTLSForWasmContext())
+        m_proc.pinRegister(m_wasmContextGPR);
     ASSERT(!pinnedRegs.sizeRegisters[0].sizeOffset);
     m_memorySizeGPR = pinnedRegs.sizeRegisters[0].sizeRegister;
     for (const PinnedSizeRegisterInfo& regInfo : pinnedRegs.sizeRegisters)
@@ -299,7 +334,7 @@
 
     wasmCallingConvention().setupFrameInPrologue(&compilation->wasmCalleeMoveLocation, m_proc, Origin(), m_currentBlock);
 
-    m_instanceValue = loadWasmContext(m_proc, m_currentBlock);
+    m_instanceValue = materializeWasmContext(m_proc, m_currentBlock);
 }
 
 struct MemoryBaseAndSize {
@@ -307,12 +342,12 @@
     Value* size;
 };
 
-static MemoryBaseAndSize getMemoryBaseAndSize(VM& vm, Value* instance, Procedure& proc, BasicBlock* block)
+static MemoryBaseAndSize getMemoryBaseAndSize(Value* instance, Procedure& proc, BasicBlock* block)
 {
     Value* memoryObject = block->appendNew<MemoryValue>(proc, Load, pointerType(), Origin(), instance, JSWebAssemblyInstance::offsetOfMemory());
 
-    static_assert(sizeof(decltype(loadWasmContext(vm)->memory()->memory().memory())) == sizeof(void*), "codegen relies on this size");
-    static_assert(sizeof(decltype(loadWasmContext(vm)->memory()->memory().size())) == sizeof(uint64_t), "codegen relies on this size");
+    static_assert(sizeof(decltype(static_cast<JSWebAssemblyInstance*>(nullptr)->memory()->memory().memory())) == sizeof(void*), "codegen relies on this size");
+    static_assert(sizeof(decltype(static_cast<JSWebAssemblyInstance*>(nullptr)->memory()->memory().size())) == sizeof(uint64_t), "codegen relies on this size");
     MemoryBaseAndSize result;
     result.base = block->appendNew<MemoryValue>(proc, Load, pointerType(), Origin(), memoryObject, JSWebAssemblyMemory::offsetOfMemory());
     result.size = block->appendNew<MemoryValue>(proc, Load, Int64, Origin(), memoryObject, JSWebAssemblyMemory::offsetOfSize());
@@ -320,9 +355,9 @@
     return result;
 }
 
-static void restoreWebAssemblyGlobalState(const MemoryInformation& memory, Value* instance, Procedure& proc, BasicBlock* block)
+void B3IRGenerator::restoreWebAssemblyGlobalState(const MemoryInformation& memory, Value* instance, Procedure& proc, BasicBlock* block)
 {
-    storeWasmContext(proc, block, instance);
+    restoreWasmContext(proc, block, instance);
 
     if (!!memory) {
         const PinnedRegisterInfo* pinnedRegs = &PinnedRegisterInfo::get();
@@ -392,7 +427,7 @@
 
     m_locals.grow(signature->argumentCount());
     wasmCallingConvention().loadArguments(signature, m_proc, m_currentBlock, Origin(),
-        [&] (ExpressionType argument, unsigned i) {
+        [=] (ExpressionType argument, unsigned i) {
             Variable* argumentVariable = m_proc.addVariable(argument->type());
             m_locals[i] = argumentVariable;
             m_currentBlock->appendNew<VariableValue>(m_proc, Set, Origin(), argumentVariable, argument);
@@ -419,12 +454,11 @@
 
 auto B3IRGenerator::addGrowMemory(ExpressionType delta, ExpressionType& result) -> PartialResult
 {
-    int32_t (*growMemory) (ExecState*, int32_t) = [] (ExecState* exec, int32_t delta) -> int32_t {
+    int32_t (*growMemory) (ExecState*, JSWebAssemblyInstance*, int32_t) = [] (ExecState* exec, JSWebAssemblyInstance* wasmContext, int32_t delta) -> int32_t {
         VM& vm = exec->vm();
         auto scope = DECLARE_THROW_SCOPE(vm);
 
-        JSWebAssemblyInstance* instance = loadWasmContext(vm);
-        JSWebAssemblyMemory* wasmMemory = instance->memory();
+        JSWebAssemblyMemory* wasmMemory = wasmContext->memory();
 
         if (delta < 0)
             return -1;
@@ -440,7 +474,7 @@
 
     result = m_currentBlock->appendNew<CCallValue>(m_proc, Int32, Origin(),
         m_currentBlock->appendNew<ConstPtrValue>(m_proc, Origin(), bitwise_cast<void*>(growMemory)),
-        m_currentBlock->appendNew<B3::Value>(m_proc, B3::FramePointer, Origin()), delta);
+        m_currentBlock->appendNew<B3::Value>(m_proc, B3::FramePointer, Origin()), m_instanceValue, delta);
 
     restoreWebAssemblyGlobalState(m_info.memory, m_instanceValue, m_proc, m_currentBlock);
 
@@ -449,7 +483,7 @@
 
 auto B3IRGenerator::addCurrentMemory(ExpressionType& result) -> PartialResult
 {
-    auto memoryValue = getMemoryBaseAndSize(m_vm, m_instanceValue, m_proc, m_currentBlock);
+    auto memoryValue = getMemoryBaseAndSize(m_instanceValue, m_proc, m_currentBlock);
 
     constexpr uint32_t shiftValue = 16;
     static_assert(PageCount::pageSize == 1 << shiftValue, "This must hold for the code below to be correct.");
@@ -889,9 +923,10 @@
         m_currentBlock->appendNewControlValue(m_proc, B3::Branch, Origin(), isWasmCall, FrequentedBlock(isWasmBlock), FrequentedBlock(isJSBlock));
 
         Value* wasmCallResult = wasmCallingConvention().setupCall(m_proc, isWasmBlock, Origin(), args, toB3Type(returnType),
-            [&] (PatchpointValue* patchpoint) {
+            [=] (PatchpointValue* patchpoint) {
                 patchpoint->effects.writesPinned = true;
                 patchpoint->effects.readsPinned = true;
+                patchpoint->clobberLate(PinnedRegisterInfo::get().toSave());
                 patchpoint->setGenerator([unlinkedWasmToWasmCalls, functionIndex] (CCallHelpers& jit, const B3::StackmapGenerationParams&) {
                     AllowMacroScratchRegisterUsage allowScratch(jit);
                     CCallHelpers::Call call = jit.call();
@@ -904,9 +939,10 @@
         isWasmBlock->appendNewControlValue(m_proc, Jump, Origin(), continuation);
 
         Value* jsCallResult = wasmCallingConvention().setupCall(m_proc, isJSBlock, Origin(), args, toB3Type(returnType),
-            [&] (PatchpointValue* patchpoint) {
+            [=] (PatchpointValue* patchpoint) {
                 patchpoint->effects.writesPinned = true;
                 patchpoint->effects.readsPinned = true;
+                patchpoint->clobberLate(PinnedRegisterInfo::get().toSave());
                 patchpoint->setGenerator([unlinkedWasmToWasmCalls, functionIndex] (CCallHelpers& jit, const B3::StackmapGenerationParams&) {
                     AllowMacroScratchRegisterUsage allowScratch(jit);
                     CCallHelpers::Call call = jit.call();
@@ -932,9 +968,10 @@
         restoreWebAssemblyGlobalState(m_info.memory, m_instanceValue, m_proc, continuation);
     } else {
         result = wasmCallingConvention().setupCall(m_proc, m_currentBlock, Origin(), args, toB3Type(returnType),
-            [&] (PatchpointValue* patchpoint) {
+            [=] (PatchpointValue* patchpoint) {
                 patchpoint->effects.writesPinned = true;
                 patchpoint->effects.readsPinned = true;
+
                 patchpoint->setGenerator([unlinkedWasmToWasmCalls, functionIndex] (CCallHelpers& jit, const B3::StackmapGenerationParams&) {
                     AllowMacroScratchRegisterUsage allowScratch(jit);
                     CCallHelpers::Call call = jit.call();
@@ -1010,12 +1047,12 @@
 
     Type returnType = signature->returnType();
     result = wasmCallingConvention().setupCall(m_proc, m_currentBlock, Origin(), args, toB3Type(returnType),
-        [&] (PatchpointValue* patchpoint) {
+        [=] (PatchpointValue* patchpoint) {
             patchpoint->effects.writesPinned = true;
             patchpoint->effects.readsPinned = true;
+            patchpoint->clobberLate(PinnedRegisterInfo::get().toSave());
 
             patchpoint->append(calleeCode, ValueRep::SomeRegister);
-
             patchpoint->setGenerator([=] (CCallHelpers& jit, const B3::StackmapGenerationParams& params) {
                 AllowMacroScratchRegisterUsage allowScratch(jit);
                 jit.call(params[returnType == Void ? 0 : 1].gpr());
@@ -1080,11 +1117,8 @@
         *linkedCalleeMove = linkBuffer.locationOf(calleeMoveLocation);
     });
 
-    RegisterSet toSave;
     const PinnedRegisterInfo& pinnedRegs = PinnedRegisterInfo::get();
-    toSave.set(pinnedRegs.baseMemoryPointer);
-    for (const PinnedSizeRegisterInfo& regInfo : pinnedRegs.sizeRegisters)
-        toSave.set(regInfo.sizeRegister);
+    RegisterSet toSave = pinnedRegs.toSave();
 
 #if !ASSERT_DISABLED
     unsigned toSaveSize = toSave.numberOfSetGPRs();
@@ -1191,10 +1225,25 @@
         }
     }
 
+    // FIXME: JStoWasm wrapper should take JSWebAssemblyInstance pointer as an argument directly.
+    // https://bugs.webkit.org/show_bug.cgi?id=170182
+    GPRReg wasmContext = pinnedRegs.wasmContextPointer;
+    if (!useFastTLSForWasmContext()) {
+        jit.loadPtr(CCallHelpers::Address(GPRInfo::callFrameRegister, CallFrameSlot::callee * static_cast<int>(sizeof(Register))), wasmContext);
+        jit.andPtr(CCallHelpers::TrustedImmPtr(MarkedBlock::blockMask), wasmContext);
+        jit.loadPtr(CCallHelpers::Address(wasmContext, MarkedBlock::offsetOfVM()), wasmContext);
+        jit.loadPtr(CCallHelpers::Address(wasmContext, VM::wasmContextOffset()), wasmContext);
+    }
+
     if (!!info.memory) {
         GPRReg baseMemory = pinnedRegs.baseMemoryPointer;
-        jit.loadWasmContext(baseMemory);
-        jit.loadPtr(CCallHelpers::Address(baseMemory, JSWebAssemblyInstance::offsetOfMemory()), baseMemory);
+
+        if (!useFastTLSForWasmContext())
+            jit.loadPtr(CCallHelpers::Address(wasmContext, JSWebAssemblyInstance::offsetOfMemory()), baseMemory);
+        else {
+            jit.loadWasmContext(baseMemory);
+            jit.loadPtr(CCallHelpers::Address(baseMemory, JSWebAssemblyInstance::offsetOfMemory()), baseMemory);
+        }
         const auto& sizeRegs = pinnedRegs.sizeRegisters;
         ASSERT(sizeRegs.size() >= 1);
         ASSERT(!sizeRegs[0].sizeOffset); // The following code assumes we start at 0, and calculates subsequent size registers relative to 0.

Modified: trunk/Source/_javascript_Core/wasm/WasmBinding.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/WasmBinding.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/WasmBinding.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -36,7 +36,6 @@
 #include "LinkBuffer.h"
 #include "NativeErrorConstructor.h"
 #include "WasmCallingConvention.h"
-#include "WasmContext.h"
 #include "WasmExceptionType.h"
 
 namespace JSC { namespace Wasm {
@@ -66,9 +65,7 @@
 
     jit.emitFunctionPrologue();
     jit.store64(JIT::TrustedImm32(0), JIT::Address(GPRInfo::callFrameRegister, CallFrameSlot::codeBlock * static_cast<int>(sizeof(Register)))); // FIXME Stop using 0 as codeBlocks. https://bugs.webkit.org/show_bug.cgi?id=165321
-    jit.storePtr(JIT::TrustedImmPtr(vm->webAssemblyToJSCallee.get()), JIT::Address(GPRInfo::callFrameRegister, CallFrameSlot::callee * static_cast<int>(sizeof(Register))));
 
-
     {
         bool hasBadI64Use = false;
         hasBadI64Use |= signature->returnType() == I64;
@@ -93,16 +90,22 @@
         if (hasBadI64Use) {
             jit.copyCalleeSavesToVMEntryFrameCalleeSavesBuffer();
             jit.move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR0);
+            jit.loadWasmContext(GPRInfo::argumentGPR1);
+
+            // Store Callee.
+            jit.loadPtr(CCallHelpers::Address(GPRInfo::argumentGPR1, JSWebAssemblyInstance::offsetOfCallee()), GPRInfo::argumentGPR2);
+            jit.storePtr(GPRInfo::argumentGPR2, JIT::Address(GPRInfo::callFrameRegister, CallFrameSlot::callee * static_cast<int>(sizeof(Register))));
+
             auto call = jit.call();
             jit.jumpToExceptionHandler();
 
-            void (*throwBadI64)(ExecState*) = [] (ExecState* exec) -> void {
+            void (*throwBadI64)(ExecState*, JSWebAssemblyInstance*) = [] (ExecState* exec, JSWebAssemblyInstance* wasmContext) -> void {
                 VM* vm = &exec->vm();
                 NativeCallFrameTracer tracer(vm, exec);
 
                 {
                     auto throwScope = DECLARE_THROW_SCOPE(*vm);
-                    JSGlobalObject* globalObject = loadWasmContext(*vm)->globalObject();
+                    JSGlobalObject* globalObject = wasmContext->globalObject();
                     auto* error = ErrorInstance::create(exec, *vm, globalObject->typeErrorConstructor()->errorStructure(), ASCIILiteral("i64 not allowed as return type or argument to an imported function"));
                     throwException(exec, throwScope, error);
                 }
@@ -252,6 +255,10 @@
         }
     }
 
+    jit.loadWasmContext(GPRInfo::argumentGPR0);
+    jit.loadPtr(CCallHelpers::Address(GPRInfo::argumentGPR0, JSWebAssemblyInstance::offsetOfCallee()), GPRInfo::argumentGPR0);
+    jit.storePtr(GPRInfo::argumentGPR0, JIT::Address(GPRInfo::callFrameRegister, CallFrameSlot::callee * static_cast<int>(sizeof(Register))));
+
     GPRReg importJSCellGPRReg = GPRInfo::regT0; // Callee needs to be in regT0 for slow path below.
     ASSERT(!wasmCC.m_calleeSaveRegisters.get(importJSCellGPRReg));
 

Modified: trunk/Source/_javascript_Core/wasm/WasmContext.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/WasmContext.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/WasmContext.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -34,17 +34,17 @@
 
 namespace JSC {
 
-JSWebAssemblyInstance* loadWasmContext(VM& vm)
+WasmContext* loadWasmContext(VM& vm)
 {
 #if ENABLE(FAST_TLS_JIT)
     if (Options::useWebAssemblyFastTLS())
-        return bitwise_cast<JSWebAssemblyInstance*>(_pthread_getspecific_direct(WTF_WASM_CONTEXT_KEY));
+        return bitwise_cast<WasmContext*>(_pthread_getspecific_direct(WTF_WASM_CONTEXT_KEY));
 #endif
     // FIXME: Save this state elsewhere to allow PIC. https://bugs.webkit.org/show_bug.cgi?id=169773
     return vm.wasmContext;
 }
 
-void storeWasmContext(VM& vm, JSWebAssemblyInstance* instance)
+void storeWasmContext(VM& vm, WasmContext* instance)
 {
 #if ENABLE(FAST_TLS_JIT)
     if (Options::useWebAssemblyFastTLS())

Modified: trunk/Source/_javascript_Core/wasm/WasmContext.h (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/WasmContext.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/WasmContext.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -32,9 +32,11 @@
 class JSWebAssemblyInstance;
 class VM;
 
-JSWebAssemblyInstance* loadWasmContext(VM&);
-void storeWasmContext(VM&, JSWebAssemblyInstance*);
+using WasmContext = JSWebAssemblyInstance;
 
+WasmContext* loadWasmContext(VM&);
+void storeWasmContext(VM&, WasmContext*);
+
 } // namespace JSC
 
 #endif // ENABLE(WEBASSEMBLY)

Modified: trunk/Source/_javascript_Core/wasm/WasmMemoryInformation.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/WasmMemoryInformation.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/WasmMemoryInformation.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -34,6 +34,21 @@
 
 namespace JSC { namespace Wasm {
 
+static Vector<GPRReg> getPinnedRegisters(unsigned remainingPinnedRegisters)
+{
+    Vector<GPRReg> registers;
+    jscCallingConvention().m_calleeSaveRegisters.forEach([&] (Reg reg) {
+        if (!reg.isGPR())
+            return;
+        GPRReg gpr = reg.gpr();
+        if (!remainingPinnedRegisters || RegisterSet::stackRegisters().get(reg))
+            return;
+        --remainingPinnedRegisters;
+        registers.append(gpr);
+    });
+    return registers;
+}
+
 const PinnedRegisterInfo& PinnedRegisterInfo::get()
 {
     static LazyNeverDestroyed<PinnedRegisterInfo> staticPinnedRegisterInfo;
@@ -40,7 +55,8 @@
     static std::once_flag staticPinnedRegisterInfoFlag;
     std::call_once(staticPinnedRegisterInfoFlag, [] () {
         Vector<PinnedSizeRegisterInfo> sizeRegisters;
-        GPRReg baseMemoryPointer;
+        GPRReg baseMemoryPointer = InvalidGPRReg;
+        GPRReg wasmContextPointer = InvalidGPRReg;
 
         // FIXME: We should support more than one memory size register, and we should allow different
         //        WebAssembly.Instance to have different pins. Right now we take a vector with only one entry.
@@ -47,30 +63,28 @@
         //        If we have more than one size register, we can have one for each load size class.
         //        see: https://bugs.webkit.org/show_bug.cgi?id=162952
         Vector<unsigned> pinnedSizes = { 0 };
-        unsigned remainingPinnedRegisters = pinnedSizes.size() + 1;
-        jscCallingConvention().m_calleeSaveRegisters.forEach([&] (Reg reg) {
-            if (!reg.isGPR())
-                return;
-            GPRReg gpr = reg.gpr();
-            if (!remainingPinnedRegisters || RegisterSet::stackRegisters().get(reg))
-                return;
-            if (remainingPinnedRegisters == 1) {
-                baseMemoryPointer = gpr;
-                remainingPinnedRegisters--;
-            } else
-                sizeRegisters.append({ gpr, pinnedSizes[--remainingPinnedRegisters - 1] });
-        });
+        unsigned numberOfPinnedRegisters = pinnedSizes.size() + 1;
+        if (!useFastTLSForWasmContext())
+            ++numberOfPinnedRegisters;
+        Vector<GPRReg> pinnedRegs = getPinnedRegisters(numberOfPinnedRegisters);
 
-        ASSERT(!remainingPinnedRegisters);
-        staticPinnedRegisterInfo.construct(WTFMove(sizeRegisters), baseMemoryPointer);
+        baseMemoryPointer = pinnedRegs.takeLast();
+        if (!useFastTLSForWasmContext())
+            wasmContextPointer = pinnedRegs.takeLast();
+
+        ASSERT(pinnedSizes.size() == pinnedRegs.size());
+        for (unsigned i = 0; i < pinnedSizes.size(); ++i)
+            sizeRegisters.append({ pinnedRegs[i], pinnedSizes[i] });
+        staticPinnedRegisterInfo.construct(WTFMove(sizeRegisters), baseMemoryPointer, wasmContextPointer);
     });
 
     return staticPinnedRegisterInfo.get();
 }
 
-PinnedRegisterInfo::PinnedRegisterInfo(Vector<PinnedSizeRegisterInfo>&& sizeRegisters, GPRReg baseMemoryPointer)
+PinnedRegisterInfo::PinnedRegisterInfo(Vector<PinnedSizeRegisterInfo>&& sizeRegisters, GPRReg baseMemoryPointer, GPRReg wasmContextPointer)
     : sizeRegisters(WTFMove(sizeRegisters))
     , baseMemoryPointer(baseMemoryPointer)
+    , wasmContextPointer(wasmContextPointer)
 {
 }
 

Modified: trunk/Source/_javascript_Core/wasm/WasmMemoryInformation.h (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/WasmMemoryInformation.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/WasmMemoryInformation.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -28,6 +28,7 @@
 #if ENABLE(WEBASSEMBLY)
 
 #include "GPRInfo.h"
+#include "RegisterSet.h"
 #include "WasmMemory.h"
 #include "WasmPageCount.h"
 #include <wtf/Ref.h>
@@ -43,8 +44,20 @@
 struct PinnedRegisterInfo {
     Vector<PinnedSizeRegisterInfo> sizeRegisters;
     GPRReg baseMemoryPointer;
+    GPRReg wasmContextPointer;
     static const PinnedRegisterInfo& get();
-    PinnedRegisterInfo(Vector<PinnedSizeRegisterInfo>&&, GPRReg);
+    PinnedRegisterInfo(Vector<PinnedSizeRegisterInfo>&&, GPRReg, GPRReg);
+
+    RegisterSet toSave() const
+    {
+        RegisterSet result;
+        result.set(baseMemoryPointer);
+        if (wasmContextPointer != InvalidGPRReg)
+            result.set(wasmContextPointer);
+        for (const auto& info : sizeRegisters)
+            result.set(info.sizeRegister);
+        return result;
+    }
 };
 
 class MemoryInformation {
@@ -73,6 +86,20 @@
     bool m_isImport { false };
 };
 
+inline bool useFastTLS()
+{
+#if ENABLE(FAST_TLS_JIT)
+    return Options::useWebAssemblyFastTLS();
+#else
+    return false;
+#endif
+}
+
+inline bool useFastTLSForWasmContext()
+{
+    return useFastTLS();
+}
+
 } } // namespace JSC::Wasm
 
 #endif // ENABLE(WASM)

Modified: trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyInstance.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyInstance.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyInstance.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -34,6 +34,7 @@
 #include "JSModuleNamespaceObject.h"
 #include "JSWebAssemblyMemory.h"
 #include "JSWebAssemblyModule.h"
+#include "WebAssemblyToJSCallee.h"
 #include <wtf/StdLibExtras.h>
 
 namespace JSC {
@@ -81,6 +82,7 @@
 
     m_codeBlock.set(vm, this, module->codeBlock());
     m_moduleNamespaceObject.set(vm, this, moduleNamespaceObject);
+    m_callee.set(vm, this, module->callee());
     putDirect(vm, Identifier::fromString(&vm, "exports"), moduleNamespaceObject, None);
 }
 
@@ -99,6 +101,7 @@
     visitor.append(thisObject->m_moduleNamespaceObject);
     visitor.append(thisObject->m_memory);
     visitor.append(thisObject->m_table);
+    visitor.append(thisObject->m_callee);
     visitor.reportExtraMemoryVisited(thisObject->module()->moduleInformation().globals.size());
     for (unsigned i = 0; i < thisObject->m_numImportFunctions; ++i)
         visitor.append(*thisObject->importFunction(i));

Modified: trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyInstance.h (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyInstance.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyInstance.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -37,6 +37,7 @@
 
 class JSModuleNamespaceObject;
 class JSWebAssemblyModule;
+class WebAssemblyToJSCallee;
 
 class JSWebAssemblyInstance : public JSDestructibleObject {
 public:
@@ -97,6 +98,7 @@
 
     static ptrdiff_t offsetOfMemory() { return OBJECT_OFFSETOF(JSWebAssemblyInstance, m_memory); }
     static ptrdiff_t offsetOfTable() { return OBJECT_OFFSETOF(JSWebAssemblyInstance, m_table); }
+    static ptrdiff_t offsetOfCallee() { return OBJECT_OFFSETOF(JSWebAssemblyInstance, m_callee); }
     static ptrdiff_t offsetOfGlobals() { return OBJECT_OFFSETOF(JSWebAssemblyInstance, m_globals); }
     static size_t offsetOfImportFunctions() { return WTF::roundUpToMultipleOf<sizeof(WriteBarrier<JSCell>)>(sizeof(JSWebAssemblyInstance)); }
     static size_t offsetOfImportFunction(size_t importFunctionNum) { return offsetOfImportFunctions() + importFunctionNum * sizeof(sizeof(WriteBarrier<JSCell>)); }
@@ -117,6 +119,7 @@
     WriteBarrier<JSModuleNamespaceObject> m_moduleNamespaceObject;
     WriteBarrier<JSWebAssemblyMemory> m_memory;
     WriteBarrier<JSWebAssemblyTable> m_table;
+    WriteBarrier<WebAssemblyToJSCallee> m_callee;
     MallocPtr<uint64_t> m_globals;
     unsigned m_numImportFunctions;
 };

Modified: trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyModule.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyModule.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyModule.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -36,6 +36,7 @@
 #include "WasmFormat.h"
 #include "WasmMemory.h"
 #include "WasmPlan.h"
+#include "WebAssemblyToJSCallee.h"
 #include <wtf/StdLibExtras.h>
 
 namespace JSC {
@@ -132,6 +133,7 @@
     m_sourceBuffer = ArrayBuffer::create(source, byteSize);
     m_moduleInformation = plan.takeModuleInformation();
     m_exportSymbolTable.set(vm, this, exportSymbolTable);
+    m_callee.set(vm, this, WebAssemblyToJSCallee::create(vm, vm.webAssemblyToJSCalleeStructure.get(), this));
     codeBlockFor(codeBlock->mode()).set(vm, this, codeBlock);
 }
 
@@ -147,6 +149,7 @@
 
     Base::visitChildren(thisObject, visitor);
     visitor.append(thisObject->m_exportSymbolTable);
+    visitor.append(thisObject->m_callee);
     for (unsigned i = 0; i < Wasm::NumberOfMemoryModes; ++i)
         visitor.append(thisObject->m_codeBlocks[i]);
 }

Modified: trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyModule.h (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyModule.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/js/JSWebAssemblyModule.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -43,6 +43,7 @@
 
 class SymbolTable;
 class JSWebAssemblyMemory;
+class WebAssemblyToJSCallee;
 
 class JSWebAssemblyModule : public JSDestructibleObject {
 public:
@@ -60,6 +61,7 @@
     {
         return m_moduleInformation->signatureIndexFromFunctionIndexSpace(functionIndexSpace);
     }
+    WebAssemblyToJSCallee* callee() const { return m_callee.get(); }
 
     // Returns the code block that this module was originally compiled expecting to use. This won't need to recompile.
     JSWebAssemblyCodeBlock* codeBlock() { return codeBlockFor(m_moduleInformation->memory.mode()).get(); }
@@ -79,6 +81,7 @@
     std::unique_ptr<Wasm::ModuleInformation> m_moduleInformation;
     WriteBarrier<SymbolTable> m_exportSymbolTable;
     WriteBarrier<JSWebAssemblyCodeBlock> m_codeBlocks[Wasm::NumberOfMemoryModes];
+    WriteBarrier<WebAssemblyToJSCallee> m_callee;
 };
 
 } // namespace JSC

Modified: trunk/Source/_javascript_Core/wasm/js/WebAssemblyFunction.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/js/WebAssemblyFunction.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/js/WebAssemblyFunction.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -42,6 +42,7 @@
 #include "WasmContext.h"
 #include "WasmFormat.h"
 #include "WasmMemory.h"
+#include <wtf/FastTLS.h>
 #include <wtf/SystemTracing.h>
 
 namespace JSC {
@@ -121,6 +122,10 @@
     protoCallFrame.init(nullptr, wasmFunction, firstArgument, argCount, remainingArgs);
 
     // FIXME Do away with this entire function, and only use the entrypoint generated by B3. https://bugs.webkit.org/show_bug.cgi?id=166486
+    // FIXME: We would like to make loadWasmContext and storeWasmContext no-op if we use pinned registers.
+    // However, we use VM.wasmContext field to pass instance to wasm function's JS glue code.
+    // We should pass JSWebAssemblyInstance directly to vmEntryToWasm.
+    // https://bugs.webkit.org/show_bug.cgi?id=170182
     JSWebAssemblyInstance* prevJSWebAssemblyInstance = loadWasmContext(vm);
     storeWasmContext(vm, wasmFunction->instance());
     ASSERT(wasmFunction->instance());
@@ -153,6 +158,7 @@
     Structure* structure = globalObject->webAssemblyFunctionStructure();
     WebAssemblyFunction* function = new (NotNull, allocateCell<WebAssemblyFunction>(vm.heap)) WebAssemblyFunction(vm, globalObject, structure, wasmEntrypoint, signatureIndex);
     function->finishCreation(vm, executable, length, name, instance, jsEntrypoint, wasmEntrypoint);
+    ASSERT_WITH_MESSAGE(!function->isLargeAllocation(), "WebAssemblyFunction should be allocated not in large allocation since it is JSCallee.");
     return function;
 }
 

Modified: trunk/Source/_javascript_Core/wasm/js/WebAssemblyToJSCallee.cpp (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/js/WebAssemblyToJSCallee.cpp	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/js/WebAssemblyToJSCallee.cpp	2017-03-28 22:16:01 UTC (rev 214498)
@@ -29,21 +29,22 @@
 #if ENABLE(WEBASSEMBLY)
 
 #include "JSCInlines.h"
+#include "JSWebAssemblyModule.h"
 
 namespace JSC {
 
 const ClassInfo WebAssemblyToJSCallee::s_info = { "WebAssemblyToJSCallee", nullptr, 0, CREATE_METHOD_TABLE(WebAssemblyToJSCallee) };
 
-WebAssemblyToJSCallee* WebAssemblyToJSCallee::create(VM& vm, Structure* structure)
+WebAssemblyToJSCallee* WebAssemblyToJSCallee::create(VM& vm, Structure* structure, JSWebAssemblyModule* module)
 {
     WebAssemblyToJSCallee* callee = new (NotNull, allocateCell<WebAssemblyToJSCallee>(vm.heap)) WebAssemblyToJSCallee(vm, structure);
-    callee->finishCreation(vm);
+    callee->finishCreation(vm, module);
     return callee;
 }
 
 Structure* WebAssemblyToJSCallee::createStructure(VM& vm, JSGlobalObject* globalObject, JSValue prototype)
 {
-    return Structure::create(vm, globalObject, prototype, TypeInfo(CellType, StructureFlags), info());
+    return Structure::create(vm, globalObject, prototype, TypeInfo(WebAssemblyToJSCalleeType, StructureFlags), info());
 }
 
 WebAssemblyToJSCallee::WebAssemblyToJSCallee(VM& vm, Structure* structure)
@@ -51,15 +52,19 @@
 {
 }
 
-void WebAssemblyToJSCallee::finishCreation(VM& vm)
+void WebAssemblyToJSCallee::finishCreation(VM& vm, JSWebAssemblyModule* module)
 {
     Base::finishCreation(vm);
+    m_module.set(vm, this, module);
 }
 
-void WebAssemblyToJSCallee::destroy(JSCell* cell)
+void WebAssemblyToJSCallee::visitChildren(JSCell* cell, SlotVisitor& visitor)
 {
-    WebAssemblyToJSCallee* thisObject = static_cast<WebAssemblyToJSCallee*>(cell);
-    thisObject->WebAssemblyToJSCallee::~WebAssemblyToJSCallee();
+    auto* thisObject = jsCast<WebAssemblyToJSCallee*>(cell);
+    ASSERT_GC_OBJECT_INHERITS(thisObject, info());
+
+    Base::visitChildren(thisObject, visitor);
+    visitor.append(thisObject->m_module);
 }
 
 } // namespace JSC

Modified: trunk/Source/_javascript_Core/wasm/js/WebAssemblyToJSCallee.h (214497 => 214498)


--- trunk/Source/_javascript_Core/wasm/js/WebAssemblyToJSCallee.h	2017-03-28 22:14:49 UTC (rev 214497)
+++ trunk/Source/_javascript_Core/wasm/js/WebAssemblyToJSCallee.h	2017-03-28 22:16:01 UTC (rev 214498)
@@ -31,21 +31,27 @@
 
 namespace JSC {
 
-class WebAssemblyToJSCallee : public JSCell {
+class JSWebAssemblyModule;
+
+class WebAssemblyToJSCallee final : public JSCell {
 public:
     typedef JSCell Base;
     static const unsigned StructureFlags = Base::StructureFlags | StructureIsImmortal;
 
-    static WebAssemblyToJSCallee* create(VM&, Structure*);
+    static WebAssemblyToJSCallee* create(VM&, Structure*, JSWebAssemblyModule*);
     static Structure* createStructure(VM&, JSGlobalObject*, JSValue);
 
     DECLARE_EXPORT_INFO;
-    static const bool needsDestruction = true;
-    static void destroy(JSCell*);
 
+    static void visitChildren(JSCell*, SlotVisitor&);
+
+    JSWebAssemblyModule* module() { return m_module.get(); }
+
 private:
-    void finishCreation(VM&);
+    void finishCreation(VM&, JSWebAssemblyModule*);
     WebAssemblyToJSCallee(VM&, Structure*);
+
+    WriteBarrier<JSWebAssemblyModule> m_module;
 };
 
 } // namespace JSC
_______________________________________________
webkit-changes mailing list
[email protected]
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to