Sfoglia il codice sorgente

change serialization to use C API

Michael Holman 7 anni fa
parent
commit
9b3774a38b

+ 17 - 2
bin/ch/ChakraRtInterface.h

@@ -127,7 +127,12 @@ struct JsAPIHooks
     typedef JsErrorCode(WINAPI *JsrtConnectJITProcess)(HANDLE processHandle, void* serverSecurityDescriptor, UUID connectionId);
 #endif
 
-    typedef JsErrorCode(WINAPI *JsrtVarSerializerPtr)(SerializerCallbackBase *delegate, SerializerHandleBase **serializerHandle);
+    typedef JsErrorCode(WINAPI *JsrtVarSerializerPtr)(ReallocateBufferMemoryFunc reallocateBufferMemory, WriteHostObjectFunc writeHostObject, JsVarSerializerHandle *serializerHandle);
+    typedef JsErrorCode(WINAPI *JsrtVarSerializerSetTransferableVarsPtr)(JsVarSerializerHandle serializerHandle, JsValueRef *transferableVars, size_t transferableVarsCount);
+    typedef JsErrorCode(WINAPI *JsrtVarSerializerWriteValuePtr)(JsVarSerializerHandle serializerHandle, JsValueRef rootObject);
+    typedef JsErrorCode(WINAPI *JsrtVarSerializerReleaseDataPtr)(JsVarSerializerHandle serializerHandle, byte** data, size_t *dataLength);
+    typedef JsErrorCode(WINAPI *JsrtVarSerializerFreePtr)(JsVarSerializerHandle serializerHandle);
+
     typedef JsErrorCode(WINAPI *JsrtVarDeserializerPtr)(void *data, size_t dataLength, DeserializerCallbackBase *delegate, DeserializerHandleBase **deserializerHandle);
     typedef JsErrorCode(WINAPI *JsrtDetachArrayBufferPtr)(JsValueRef buffer);
 
@@ -250,6 +255,11 @@ struct JsAPIHooks
     JsrtTTDReplayExecutionPtr pfJsrtTTDReplayExecution;
 
     JsrtVarSerializerPtr pfJsrtVarSerializer;
+    JsrtVarSerializerSetTransferableVarsPtr pfJsrtVarSerializerSetTransferableVars;
+    JsrtVarSerializerWriteValuePtr pfJsrtVarSerializerWriteValue;
+    JsrtVarSerializerReleaseDataPtr pfJsrtVarSerializerReleaseData;
+    JsrtVarSerializerFreePtr pfJsrtVarSerializerFree;
+
     JsrtVarDeserializerPtr pfJsrtVarDeserializer;
     JsrtDetachArrayBufferPtr pfJsrtDetachArrayBuffer;
 #ifdef _WIN32
@@ -476,7 +486,12 @@ public:
     static JsErrorCode WINAPI JsSerializeParserState(JsValueRef script, JsValueRef *buffer, JsParseScriptAttributes parseAttributes) { return HOOK_JS_API(SerializeParserState(script, buffer, parseAttributes)); }
     static JsErrorCode WINAPI JsRunScriptWithParserState(JsValueRef script, JsSourceContext sourceContext, JsValueRef sourceUrl, JsParseScriptAttributes parseAttributes, JsValueRef parserState, JsValueRef * result) { return HOOK_JS_API(RunScriptWithParserState(script, sourceContext, sourceUrl, parseAttributes, parserState, result)); }
 
-    static JsErrorCode WINAPI JsVarSerializer(SerializerCallbackBase *delegate, SerializerHandleBase **serializerHandle) { return HOOK_JS_API(VarSerializer(delegate, serializerHandle)); }
+    static JsErrorCode WINAPI JsVarSerializer(ReallocateBufferMemoryFunc reallocateBufferMemory, WriteHostObjectFunc writeHostObject, JsVarSerializerHandle *serializerHandle) { return HOOK_JS_API(VarSerializer(reallocateBufferMemory, writeHostObject, serializerHandle)); }
+    static JsErrorCode WINAPI JsVarSerializerSetTransferableVars(JsVarSerializerHandle serializerHandle, JsValueRef *transferableVars, size_t transferableVarsCount) { return HOOK_JS_API(VarSerializerSetTransferableVars(serializerHandle, transferableVars, transferableVarsCount)); }
+    static JsErrorCode WINAPI JsVarSerializerWriteValue(JsVarSerializerHandle serializerHandle, JsValueRef rootObject) { return HOOK_JS_API(VarSerializerWriteValue(serializerHandle, rootObject)); }
+    static JsErrorCode WINAPI JsVarSerializerReleaseData(JsVarSerializerHandle serializerHandle, byte** data, size_t *dataLength) { return HOOK_JS_API(VarSerializerReleaseData(serializerHandle, data, dataLength)); }
+    static JsErrorCode WINAPI JsVarSerializerFree(JsVarSerializerHandle serializerHandle) { return HOOK_JS_API(VarSerializerFree(serializerHandle)); }
+
     static JsErrorCode WINAPI JsVarDeserializer(void *data, size_t dataLength, DeserializerCallbackBase *delegate, DeserializerHandleBase **deserializerHandle) { return HOOK_JS_API(VarDeserializer(data, dataLength, delegate, deserializerHandle)); }
     static JsErrorCode WINAPI JsDetachArrayBuffer(JsValueRef buffer) { return HOOK_JS_API(DetachArrayBuffer(buffer)); }
     static JsErrorCode WINAPI JsQueueBackgroundParse_Experimental(JsScriptContents* contents, DWORD* dwBgParseCookie) { return HOOK_JS_API(QueueBackgroundParse_Experimental)(contents, dwBgParseCookie);  }

+ 22 - 45
bin/ch/WScriptJsrt.cpp

@@ -278,44 +278,6 @@ void WScriptJsrt::SetExceptionIf(JsErrorCode errorCode, LPCWSTR errorMessage)
     }
 }
 
-class SerializerDelegateData : public SerializerCallbackBase
-{
-public:
-    virtual byte *ReallocateBufferMemory(byte *oldBuffer, size_t newSize, size_t *allocatedSize) override
-    {
-        void* data = realloc((void*)oldBuffer, newSize);
-        if (allocatedSize)
-        {
-            *allocatedSize = newSize;
-        }
-        return (byte*)data;
-    }
-
-
-    virtual void FreeBufferMemory(byte *buffer) override
-    {
-        free(buffer);
-    }
-
-    virtual void ThrowDataCloneError(void *message)
-    {
-        // TBD
-    }
-
-    virtual bool WriteHostObject(JsValueRef data)
-    {
-        // Not implemented
-        return true;
-    }
-
-    virtual uint GetSharedArrayBufferId(JsValueRef sharedArrayBuffer)
-    {
-        // Not implemented
-        return 0;
-    }
-
-};
-
 class DeserializerDelegateData : public DeserializerCallbackBase
 {
 public:
@@ -337,6 +299,22 @@ public:
     }
 };
 
+byte * CHAKRA_CALLBACK ReallocateBufferMemory(byte *oldBuffer, size_t newSize, size_t *allocatedSize)
+{
+    void* data = realloc((void*)oldBuffer, newSize);
+    if (allocatedSize)
+    {
+        *allocatedSize = newSize;
+    }
+    return (byte*)data;
+}
+
+bool CHAKRA_CALLBACK WriteHostObject(JsValueRef data)
+{
+    // Not implemented
+    return true;
+}
+
 JsValueRef __stdcall WScriptJsrt::SerializeObject(JsValueRef callee, bool isConstructCall, JsValueRef *arguments, unsigned short argumentCount, void *callbackState)
 {
     JsErrorCode errorCode = JsNoError;
@@ -402,15 +380,14 @@ JsValueRef __stdcall WScriptJsrt::SerializeObject(JsValueRef callee, bool isCons
             }
         }
 
-        SerializerDelegateData *delegateData = new SerializerDelegateData();
-        SerializerHandleBase *serializerHandle = nullptr;
+        JsVarSerializerHandle serializerHandle = nullptr;
 
         // This memory will be claimed at WScriptJsrt::Deserialize.
         SerializerBlob *blob = new SerializerBlob();
-        IfJsrtErrorSetGo(ChakraRTInterface::JsVarSerializer(delegateData, &serializerHandle));
-        IfJsrtErrorSetGo(serializerHandle->SetTransferableVars(transferVarsArray, transferVarsCount));
-        serializerHandle->WriteValue(rootObject);
-        serializerHandle->ReleaseData((byte**)&blob->data, &blob->dataLength);
+        IfJsrtErrorSetGo(ChakraRTInterface::JsVarSerializer(ReallocateBufferMemory, WriteHostObject, &serializerHandle));
+        IfJsrtErrorSetGo(ChakraRTInterface::JsVarSerializerSetTransferableVars(serializerHandle, transferVarsArray, transferVarsCount));
+        IfJsrtErrorSetGo(ChakraRTInterface::JsVarSerializerWriteValue(serializerHandle, rootObject));
+        IfJsrtErrorSetGo(ChakraRTInterface::JsVarSerializerReleaseData(serializerHandle, (byte**)&blob->data, &blob->dataLength));
 
         for (int i = 0; i < transferVarsCount; i++)
         {
@@ -423,7 +400,7 @@ JsValueRef __stdcall WScriptJsrt::SerializeObject(JsValueRef callee, bool isCons
         }
 
         errorCode = ChakraRTInterface::JsCreateExternalArrayBuffer((void*)blob, sizeof(SerializerBlob), nullptr, nullptr, &returnValue);
-        serializerHandle->FreeSelf();
+        IfJsrtErrorSetGo(ChakraRTInterface::JsVarSerializerFree(serializerHandle));
     }
 Error:
     SetExceptionIf(errorCode, errorMessage);

+ 105 - 111
lib/Jsrt/ChakraCore.h

@@ -48,6 +48,14 @@ typedef void* JsModuleRecord;
 /// </remarks>
 typedef void *JsSharedArrayBufferContentHandle;
 
+/// <summary>
+///     A reference to a SCA Serializer.
+/// </summary>
+/// <remarks>
+///     This represents the internal state of a Serializer
+/// </remarks>
+typedef void *JsVarSerializerHandle;
+
 /// <summary>
 ///     Flags for parsing a module.
 /// </summary>
@@ -1644,113 +1652,6 @@ CHAKRA_API
         _Out_ JsRef * buffer
     );
 
-/// <summary>
-///     A callback structure to facilitate during variable serialization work. The callback handles many stuff like
-///     allocating buffer, de-allocate that buffer. This memory buffer is used to hold the serialization data.
-/// </summary>
-typedef struct SerializerCallbackBase
-{
-public:
-    /// <summary>
-    ///     A callback function to ask host to re-allocated buffer to the new size when the current buffer is full
-    /// </summary>
-    /// <param name="oldBuffer">An old memory buffer, which may be null, to be reallocated</param>
-    /// <param name="allocatedSize">Request host to allocate buffer of this size</param>
-    /// <param name="arrayBuffer">Actual size of the new buffer</param>
-    /// <returns>
-    ///     New buffer will be returned upon success, null otherwise.
-    /// </returns>
-    virtual byte *ReallocateBufferMemory(byte *oldBuffer, size_t newSize, size_t *allocatedSize) = 0;
-
-    /// <summary>
-    ///     A callback to ask host to free the buffer which was allocated using ReallocateBufferMemory 
-    /// </summary>
-    /// <param name="buffer">Buffer to be freed</param>
-    virtual void FreeBufferMemory(byte *buffer) = 0;
-
-    /// <summary>
-    ///     A callback to ask host to throw an exception upon Structured Cloning Algorithm error.
-    /// </summary>
-    /// <param name="message">Error message to be populated with</param>
-    virtual void ThrowDataCloneError(void *message) = 0;
-
-    /// <summary>
-    ///     A callback to ask host write current Host object to the serialization buffer.
-    /// </summary>
-    /// <param name="hostObject">Host object to be serialized</param>
-    /// <returns>
-    ///     A Boolean true is returned upon success, false otherwise.
-    /// </returns>
-    virtual bool WriteHostObject(void* hostObject) = 0;
-
-    /// <summary>
-    ///     A callback to ask host to record current SharedArrayBuffer and pass an unique ID
-    /// </summary>
-    /// <param name="sharedArrayBuffer">SharedArrayBuffer object</param>
-    /// <returns>
-    ///     An unique ID representing the SharedArrayBuffer is returned. Upon failures the exception is thrown
-    /// </returns>
-    virtual unsigned int GetSharedArrayBufferId(void * sharedArrayBuffer) = 0;
-
-} SerializerCallbackBase;
-
-/// <summary>
-///     The object of SerializerHandleBase will be passed to the caller when JsVarSerializer is called.
-///     This object will provide functionality to write data to serialization buffer.
-/// </summary>
-typedef struct SerializerHandleBase
-{
-public:
-    /// <summary>
-    ///     Write raw bytes to the buffer.
-    /// </summary>
-    /// <param name="source">Source byte buffer</param>
-    /// <param name="length">Length of bytes to write from source raw byte buffer</param>
-    virtual void WriteRawBytes(const void* source, size_t length) = 0;
-
-    /// <summary>
-    ///     A method to serialize given Javascript object to the serialization buffer
-    /// </summary>
-    /// <param name="rootObject">A Javascript object to be serialized</param>
-    /// <returns>
-    ///     A Boolean value true is returned upon success, false otherwise.
-    /// </returns>
-    virtual bool WriteValue(JsValueRef rootObject) = 0;
-
-    /// <summary>
-    ///     A method to pass on the current serialized buffer (this buffer was allocated using ReallocateBufferMemory) to host.
-    /// </summary>
-    /// <param name="data">A buffer which holds current serialized data</param>
-    /// <param name="dataLength">Length of the buffer</param>
-    /// <returns>
-    ///     A Boolean value true is returned upon success, false otherwise.
-    /// </returns>
-    virtual bool ReleaseData(byte** data, size_t *dataLength) = 0;
-
-    /// <summary>
-    ///     Detach all array buffers which were passed using SetTransferableVars.
-    /// </summary>
-    /// <returns>
-    ///     A Boolean value true is returned upon success, false otherwise.
-    /// </returns>
-    virtual bool DetachArrayBuffer() = 0;
-
-    /// <summary>
-    ///     Host provides all the objects which has transferable semantics (Such as ArrayBuffers).
-    /// </summary>
-    /// <param name="transferableVars">An array of transferable objects</param>
-    /// <param name="transferableVarsCount">Length of transferableVars array </param>
-    /// <returns>
-    ///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
-    /// </returns>
-    virtual JsErrorCode SetTransferableVars(JsValueRef *transferableVars, size_t transferableVarsCount) = 0;
-
-    /// <summary>
-    ///     Free current object (which was created upon JsVarSerializer) when the serialization is done. SerializerHandleBase object should not be used further after FreeSelf call.
-    /// </summary>
-    virtual void FreeSelf() = 0;
-} SerializerHandleBase;
-
 /// <summary>
 ///     A callback structure to facilitate de-serialization work.
 /// </summary>
@@ -1828,18 +1729,111 @@ public:
     virtual void FreeSelf() = 0;
 } DeserializerHandleBase;
 
+/// <summary>
+///     A callback function to ask host to re-allocated buffer to the new size when the current buffer is full
+/// </summary>
+/// <param name="oldBuffer">An old memory buffer, which may be null, to be reallocated</param>
+/// <param name="allocatedSize">Request host to allocate buffer of this size</param>
+/// <param name="arrayBuffer">Actual size of the new buffer</param>
+/// <returns>
+///     New buffer will be returned upon success, null otherwise.
+/// </returns>
+typedef byte * (CHAKRA_CALLBACK *ReallocateBufferMemoryFunc)(byte *oldBuffer, size_t newSize, size_t *allocatedSize);
+
+/// <summary>
+///     A callback to ask host write current Host object to the serialization buffer.
+/// </summary>
+/// <returns>
+///     A Boolean true is returned upon success, false otherwise.
+/// </returns>
+typedef bool (CHAKRA_CALLBACK *WriteHostObjectFunc)(void* hostObject);
+
 /// <summary>
 ///     Initialize Serialization of the object.
 /// </summary>
-/// <param name="serializerCallback">A callback object to interact with host during serialization.</param>
-/// <param name="serializerHandle">A handle which provides various functionalities to serailize objects</param>
+/// <param name="reallocateBufferMemory">A callback function to ask host to re-allocated buffer to the new size when the current buffer is full</param>
+/// <param name="writeHostObject">A callback object to interact with host during serialization.</param>
+/// <param name="serializerHandle">A handle which provides various functionalities to serialize objects</param>
 /// <returns>
 ///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
 /// </returns>
 CHAKRA_API
 JsVarSerializer(
-    _In_ SerializerCallbackBase *serializerCallback,
-    _Out_ SerializerHandleBase **serializerHandle);
+    _In_ ReallocateBufferMemoryFunc reallocateBufferMemory,
+    _In_ WriteHostObjectFunc writeHostObject,
+    _Out_ JsVarSerializerHandle *serializerHandle);
+
+/// <summary>
+///     Write raw bytes to the buffer.
+/// </summary>
+/// <param name="source">Source byte buffer</param>
+/// <param name="length">Length of bytes to write from source raw byte buffer</param>
+/// <returns>
+///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
+/// </returns>
+CHAKRA_API
+JsVarSerializerWriteRawBytes(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _In_ const void* source,
+    _In_ size_t length);
+
+/// <summary>
+///     A method to serialize given Javascript object to the serialization buffer
+/// </summary>
+/// <param name="rootObject">A Javascript object to be serialized</param>
+/// <returns>
+///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
+/// </returns>
+CHAKRA_API
+JsVarSerializerWriteValue(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _In_ JsValueRef rootObject);
+
+/// <summary>
+///     A method to pass on the current serialized buffer (this buffer was allocated using ReallocateBufferMemory) to host.
+/// </summary>
+/// <param name="data">A buffer which holds current serialized data</param>
+/// <param name="dataLength">Length of the buffer</param>
+/// <returns>
+///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
+/// </returns>
+CHAKRA_API
+JsVarSerializerReleaseData(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _Out_ byte** data,
+    _Out_ size_t *dataLength);
+
+/// <summary>
+///     Detach all array buffers which were passed using SetTransferableVars.
+/// </summary>
+/// <returns>
+///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
+/// </returns>
+CHAKRA_API
+JsVarSerializerDetachArrayBuffer(_In_ JsVarSerializerHandle serializerHandle);
+
+/// <summary>
+///     Host provides all the objects which has transferable semantics (Such as ArrayBuffers).
+/// </summary>
+/// <param name="transferableVars">An array of transferable objects</param>
+/// <param name="transferableVarsCount">Length of transferableVars array </param>
+/// <returns>
+///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
+/// </returns>
+CHAKRA_API
+JsVarSerializerSetTransferableVars(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _In_opt_ JsValueRef *transferableVars,
+    _In_ size_t transferableVarsCount);
+
+/// <summary>
+///     Free current object (which was created upon JsVarSerializer) when the serialization is done. SerializerHandleBase object should not be used further after FreeSelf call.
+/// </summary>
+/// <returns>
+///     The code <c>JsNoError</c> if the operation succeeded, a failure code otherwise.
+/// </returns>
+CHAKRA_API
+JsVarSerializerFree(_In_ JsVarSerializerHandle serializerHandle);
 
 /// <summary>
 ///     Initiate Deserialization of the memory buffer to a Javascript object.

+ 7 - 21
lib/Jsrt/Core/JsrtContextCore.cpp

@@ -164,29 +164,10 @@ ChakraCoreStreamWriter::~ChakraCoreStreamWriter()
     HeapDelete(m_serializerCore);
 }
 
-bool ChakraCoreStreamWriter::WriteHostObject(void* data)
-{
-    Assert(m_delegate);
-    return WriteHostObject(data);
-}
-
 byte * ChakraCoreStreamWriter::ExtendBuffer(byte *oldBuffer, size_t newSize, size_t *allocatedSize)
 {
-    if (m_delegate)
-    {
-        m_data = m_delegate->ReallocateBufferMemory(oldBuffer, newSize, allocatedSize);
-        m_length = newSize;
-    }
-    else
-    {
-        void* data = realloc((void*)oldBuffer, newSize);
-        if (allocatedSize)
-        {
-            *allocatedSize = newSize;
-        }
-        m_data = (byte*)data;
-        m_length = newSize;
-    }
+    m_data = this->reallocateBufferMemory(oldBuffer, newSize, allocatedSize);
+    m_length = newSize;
 
     if (m_data == nullptr)
     {
@@ -196,6 +177,11 @@ byte * ChakraCoreStreamWriter::ExtendBuffer(byte *oldBuffer, size_t newSize, siz
     return m_data;
 }
 
+bool ChakraCoreStreamWriter::WriteHostObject(void* data)
+{
+    return this->writeHostObject(data);
+}
+
 void ChakraCoreStreamWriter::SetSerializer(Js::SCACore::Serializer *s)
 {
     m_serializerCore = s;

+ 14 - 12
lib/Jsrt/Core/JsrtContextCore.h

@@ -33,16 +33,18 @@ private:
     FieldNoBarrier(ChakraCoreHostScriptContext*) hostContext;
 };
 
-class ChakraCoreStreamWriter : public HostStream, public SerializerHandleBase
+class ChakraCoreStreamWriter : public HostStream
 {
-    SerializerCallbackBase *m_delegate;
     Js::SCACore::Serializer *m_serializerCore;
     byte* m_data;
     size_t m_length;
 
+    ReallocateBufferMemoryFunc reallocateBufferMemory;
+    WriteHostObjectFunc writeHostObject;
 public:
-    ChakraCoreStreamWriter(SerializerCallbackBase *delegate)
-        : m_delegate(delegate),
+    ChakraCoreStreamWriter(ReallocateBufferMemoryFunc reallocateBufferMemory, WriteHostObjectFunc writeHostObject) :
+        reallocateBufferMemory(reallocateBufferMemory),
+        writeHostObject(writeHostObject),
         m_data(nullptr),
         m_length(0),
         m_serializerCore(nullptr)
@@ -53,15 +55,15 @@ public:
 
     void SetSerializer(Js::SCACore::Serializer *s);
 
-    void WriteRawBytes(const void* source, size_t length) override;
-    bool WriteValue(JsValueRef root) override;
-    bool ReleaseData(byte** data, size_t *dataLength) override;
-    bool DetachArrayBuffer() override;
-    JsErrorCode SetTransferableVars(JsValueRef *transferableVars, size_t transferableVarsCount) override;
-    void FreeSelf() override;
+    void WriteRawBytes(const void* source, size_t length);
+    bool WriteValue(JsValueRef root);
+    bool ReleaseData(byte** data, size_t *dataLength);
+    bool DetachArrayBuffer();
+    JsErrorCode SetTransferableVars(JsValueRef *transferableVars, size_t transferableVarsCount);
+    void FreeSelf();
 
-    bool WriteHostObject(void* data) override;
-    byte * ExtendBuffer(byte *oldBuffer, size_t newSize, size_t *allocatedSize) override;
+    virtual bool WriteHostObject(void* data) override;
+    virtual byte * ExtendBuffer(byte *oldBuffer, size_t newSize, size_t *allocatedSize) override;
 };
 
 class ChakraHostDeserializerHandle : public HostReadStream, public DeserializerHandleBase

+ 94 - 5
lib/Jsrt/Core/JsrtCore.cpp

@@ -259,16 +259,18 @@ CHAKRA_API JsGetModuleNamespace(_In_ JsModuleRecord requestModule, _Outptr_resul
 
 CHAKRA_API
 JsVarSerializer(
-    _In_ SerializerCallbackBase *delegate,
-    _Out_ SerializerHandleBase **serializerHandle)
+    _In_ ReallocateBufferMemoryFunc reallocateBufferMemory,
+    _In_ WriteHostObjectFunc writeHostObject,
+    _Out_ JsVarSerializerHandle *serializerHandle)
 {
-    PARAM_NOT_NULL(delegate);
+    PARAM_NOT_NULL(reallocateBufferMemory);
+    PARAM_NOT_NULL(writeHostObject);
     PARAM_NOT_NULL(serializerHandle);
     JsErrorCode errorCode = ContextAPINoScriptWrapper_NoRecord([&](Js::ScriptContext *scriptContext) -> JsErrorCode {
 
-        ChakraCoreStreamWriter *writer = HeapNew(ChakraCoreStreamWriter, delegate);
+        ChakraCoreStreamWriter *writer = HeapNew(ChakraCoreStreamWriter, reallocateBufferMemory, writeHostObject);
         writer->SetSerializer(HeapNew(Js::SCACore::Serializer, scriptContext, writer));
-        *serializerHandle = (SerializerHandleBase *)writer;
+        *serializerHandle = writer;
         return JsNoError;
     });
 
@@ -276,6 +278,93 @@ JsVarSerializer(
 
 }
 
+CHAKRA_API
+JsVarSerializerWriteRawBytes(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _In_ const void* source,
+    _In_ size_t length)
+{
+    PARAM_NOT_NULL(serializerHandle);
+    PARAM_NOT_NULL(source);
+    return ContextAPINoScriptWrapper_NoRecord([&](Js::ScriptContext *scriptContext) -> JsErrorCode {
+        ChakraCoreStreamWriter* streamWriter = reinterpret_cast<ChakraCoreStreamWriter*>(serializerHandle);
+        streamWriter->WriteRawBytes(source, length);
+        return JsNoError;
+    });
+}
+
+CHAKRA_API
+JsVarSerializerWriteValue(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _In_ JsValueRef rootObject)
+{
+    PARAM_NOT_NULL(serializerHandle);
+    PARAM_NOT_NULL(rootObject);
+    return ContextAPINoScriptWrapper_NoRecord([&](Js::ScriptContext *scriptContext) -> JsErrorCode {
+        ChakraCoreStreamWriter* streamWriter = reinterpret_cast<ChakraCoreStreamWriter*>(serializerHandle);
+        streamWriter->WriteValue(rootObject);
+        return JsNoError;
+    });
+}
+
+CHAKRA_API
+JsVarSerializerReleaseData(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _Out_ byte** data,
+    _Out_ size_t *dataLength)
+{
+    PARAM_NOT_NULL(serializerHandle);
+    PARAM_NOT_NULL(data);
+    PARAM_NOT_NULL(dataLength);
+    return ContextAPINoScriptWrapper_NoRecord([&](Js::ScriptContext *scriptContext) -> JsErrorCode {
+        ChakraCoreStreamWriter* streamWriter = reinterpret_cast<ChakraCoreStreamWriter*>(serializerHandle);
+        if (!streamWriter->ReleaseData(data, dataLength))
+        {
+            return JsErrorInvalidArgument;
+        }
+        return JsNoError;
+    });
+}
+
+CHAKRA_API
+JsVarSerializerDetachArrayBuffer(_In_ JsVarSerializerHandle serializerHandle)
+{
+    PARAM_NOT_NULL(serializerHandle);
+    return ContextAPINoScriptWrapper_NoRecord([&](Js::ScriptContext *scriptContext) -> JsErrorCode {
+        ChakraCoreStreamWriter* streamWriter = reinterpret_cast<ChakraCoreStreamWriter*>(serializerHandle);
+        if (!streamWriter->DetachArrayBuffer())
+        {
+            return JsErrorInvalidArgument;
+        }
+        return JsNoError;
+    });
+}
+
+CHAKRA_API
+JsVarSerializerSetTransferableVars(
+    _In_ JsVarSerializerHandle serializerHandle,
+    _In_opt_ JsValueRef *transferableVars,
+    _In_ size_t transferableVarsCount)
+{
+    PARAM_NOT_NULL(serializerHandle);
+    return ContextAPINoScriptWrapper_NoRecord([&](Js::ScriptContext *scriptContext) -> JsErrorCode {
+        ChakraCoreStreamWriter* streamWriter = reinterpret_cast<ChakraCoreStreamWriter*>(serializerHandle);
+        return streamWriter->SetTransferableVars(transferableVars, transferableVarsCount);
+    });
+
+}
+
+CHAKRA_API
+JsVarSerializerFree(_In_ JsVarSerializerHandle serializerHandle)
+{
+    PARAM_NOT_NULL(serializerHandle);
+    return ContextAPINoScriptWrapper_NoRecord([&](Js::ScriptContext *scriptContext) -> JsErrorCode {
+        ChakraCoreStreamWriter* streamWriter = reinterpret_cast<ChakraCoreStreamWriter*>(serializerHandle);
+        streamWriter->FreeSelf();
+        return JsNoError;
+    });
+}
+
 CHAKRA_API
 JsVarDeserializer(
     _In_ void *data,

+ 0 - 16
lib/SCACore/StreamWriter.h

@@ -37,22 +37,6 @@ namespace Js
         void Write(const void* pv, size_t cb);
         void WriteHostObject(void* data);
 
-        //template <typename T>
-        //void Write(const T& value)
-        //{
-        //    C_ASSERT(BUF_SIZE >= sizeof(T));
-
-        //    if (m_cur <= BUF_SIZE - sizeof(T))
-        //    {
-        //        *(T*)(m_buf + m_cur) = value;
-        //        m_cur += sizeof(T);
-        //    }
-        //    else
-        //    {
-        //        Write(&value, sizeof(T));
-        //    }
-        //}
-
         template <typename T>
         void Write(const T& value)
         {