summaryrefslogtreecommitdiffstats
path: root/WebCore/bindings/js/SerializedScriptValue.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'WebCore/bindings/js/SerializedScriptValue.cpp')
-rw-r--r--WebCore/bindings/js/SerializedScriptValue.cpp87
1 files changed, 74 insertions, 13 deletions
diff --git a/WebCore/bindings/js/SerializedScriptValue.cpp b/WebCore/bindings/js/SerializedScriptValue.cpp
index 7c4ad62..fd9cb59 100644
--- a/WebCore/bindings/js/SerializedScriptValue.cpp
+++ b/WebCore/bindings/js/SerializedScriptValue.cpp
@@ -28,12 +28,14 @@
#include "SerializedScriptValue.h"
#include "File.h"
+#include "FileList.h"
#include "JSDOMGlobalObject.h"
#include "JSFile.h"
#include "JSFileList.h"
#include <JavaScriptCore/APICast.h>
#include <runtime/DateInstance.h>
#include <runtime/ExceptionHelpers.h>
+#include <runtime/JSLock.h>
#include <runtime/PropertyNameArray.h>
#include <wtf/HashTraits.h>
#include <wtf/Vector.h>
@@ -141,6 +143,28 @@ private:
unsigned m_length;
};
+class SerializedFileList : public SharedSerializedData {
+public:
+ static PassRefPtr<SerializedFileList> create(const FileList* list)
+ {
+ return adoptRef(new SerializedFileList(list));
+ }
+
+ unsigned length() const { return m_files.size(); }
+ const String& item(unsigned idx) { return m_files[idx]; }
+
+private:
+ SerializedFileList(const FileList* list)
+ {
+ unsigned length = list->length();
+ m_files.reserveCapacity(length);
+ for (unsigned i = 0; i < length; i++)
+ m_files.append(list->item(i)->path().crossThreadString());
+ }
+
+ Vector<String> m_files;
+};
+
SerializedScriptValueData::SerializedScriptValueData(RefPtr<SerializedObject> data)
: m_type(ObjectType)
, m_sharedData(data)
@@ -153,6 +177,12 @@ SerializedScriptValueData::SerializedScriptValueData(RefPtr<SerializedArray> dat
{
}
+SerializedScriptValueData::SerializedScriptValueData(const FileList* fileList)
+ : m_type(FileListType)
+ , m_sharedData(SerializedFileList::create(fileList))
+{
+}
+
SerializedScriptValueData::SerializedScriptValueData(const File* file)
: m_type(FileType)
, m_string(file->path().crossThreadString())
@@ -169,6 +199,11 @@ SerializedObject* SharedSerializedData::asObject()
return static_cast<SerializedObject*>(this);
}
+SerializedFileList* SharedSerializedData::asFileList()
+{
+ return static_cast<SerializedFileList*>(this);
+}
+
static const unsigned maximumFilterRecursion = 40000;
enum WalkerState { StateUnknown, ArrayStartState, ArrayStartVisitMember, ArrayEndVisitMember,
ObjectStartState, ObjectStartVisitMember, ObjectEndVisitMember };
@@ -496,6 +531,8 @@ struct SerializingTreeWalker : public BaseWalker {
JSObject* obj = asObject(value);
if (obj->inherits(&JSFile::s_info))
return SerializedScriptValueData(toFile(obj));
+ if (obj->inherits(&JSFileList::s_info))
+ return SerializedScriptValueData(toFileList(obj));
CallData unusedData;
if (value.getCallData(unusedData) == CallTypeNone)
@@ -575,8 +612,10 @@ struct DeserializingTreeWalker : public BaseWalker {
typedef JSObject* OutputObject;
typedef SerializedObject::PropertyNameList PropertyList;
- DeserializingTreeWalker(ExecState* exec, bool mustCopy)
+ DeserializingTreeWalker(ExecState* exec, JSGlobalObject* globalObject, bool mustCopy)
: BaseWalker(exec)
+ , m_globalObject(globalObject)
+ , m_isDOMGlobalObject(globalObject->inherits(&JSDOMGlobalObject::s_info))
, m_mustCopy(mustCopy)
{
}
@@ -605,14 +644,14 @@ struct DeserializingTreeWalker : public BaseWalker {
JSArray* createOutputArray(unsigned length)
{
- JSArray* array = constructEmptyArray(m_exec);
+ JSArray* array = constructEmptyArray(m_exec, m_globalObject);
array->setLength(length);
return array;
}
JSObject* createOutputObject()
{
- return constructEmptyObject(m_exec);
+ return constructEmptyObject(m_exec, m_globalObject);
}
uint32_t length(RefPtr<SerializedArray> array)
@@ -655,13 +694,27 @@ struct DeserializingTreeWalker : public BaseWalker {
case SerializedScriptValueData::NumberType:
return jsNumber(m_exec, value.asDouble());
case SerializedScriptValueData::DateType:
- return new (m_exec) DateInstance(m_exec, value.asDouble());
+ return new (m_exec) DateInstance(m_exec, m_globalObject->dateStructure(), value.asDouble());
case SerializedScriptValueData::FileType:
- return toJS(m_exec, static_cast<JSDOMGlobalObject*>(m_exec->lexicalGlobalObject()), File::create(value.asString().crossThreadString()));
- default:
+ if (!m_isDOMGlobalObject)
+ return jsNull();
+ return toJS(m_exec, static_cast<JSDOMGlobalObject*>(m_globalObject), File::create(value.asString().crossThreadString()));
+ case SerializedScriptValueData::FileListType: {
+ if (!m_isDOMGlobalObject)
+ return jsNull();
+ RefPtr<FileList> result = FileList::create();
+ SerializedFileList* serializedFileList = value.asFileList();
+ unsigned length = serializedFileList->length();
+ for (unsigned i = 0; i < length; i++)
+ result->append(File::create(serializedFileList->item(i)));
+ return toJS(m_exec, static_cast<JSDOMGlobalObject*>(m_globalObject), result.get());
+ }
+ case SerializedScriptValueData::EmptyType:
ASSERT_NOT_REACHED();
- return JSValue();
+ return jsNull();
}
+ ASSERT_NOT_REACHED();
+ return jsNull();
}
void getPropertyNames(RefPtr<SerializedObject> object, Vector<SerializedObject::PropertyNameList, 16>& properties)
@@ -699,12 +752,15 @@ struct DeserializingTreeWalker : public BaseWalker {
}
private:
+ void* operator new(size_t);
+ JSGlobalObject* m_globalObject;
+ bool m_isDOMGlobalObject;
bool m_mustCopy;
};
-JSValue SerializedScriptValueData::deserialize(ExecState* exec, bool mustCopy) const
+JSValue SerializedScriptValueData::deserialize(ExecState* exec, JSGlobalObject* global, bool mustCopy) const
{
- DeserializingTreeWalker context(exec, mustCopy);
+ DeserializingTreeWalker context(exec, global, mustCopy);
return walk<DeserializingTreeWalker>(context, *this);
}
@@ -808,11 +864,14 @@ struct TeardownTreeWalker {
case SerializedScriptValueData::StringType:
case SerializedScriptValueData::ImmediateType:
case SerializedScriptValueData::NumberType:
+ case SerializedScriptValueData::DateType:
+ case SerializedScriptValueData::EmptyType:
+ case SerializedScriptValueData::FileType:
+ case SerializedScriptValueData::FileListType:
return true;
- default:
- ASSERT_NOT_REACHED();
- return JSValue();
}
+ ASSERT_NOT_REACHED();
+ return true;
}
void getPropertyNames(RefPtr<SerializedObject> object, Vector<SerializedObject::PropertyNameList, 16>& properties)
@@ -860,6 +919,7 @@ SerializedScriptValue::~SerializedScriptValue()
PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(JSContextRef originContext, JSValueRef apiValue, JSValueRef* exception)
{
+ JSLock lock(SilenceAssertionsOnly);
ExecState* exec = toJS(originContext);
JSValue value = toJS(exec, apiValue);
PassRefPtr<SerializedScriptValue> serializedValue = SerializedScriptValue::create(exec, value);
@@ -875,8 +935,9 @@ PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(JSContextRef ori
JSValueRef SerializedScriptValue::deserialize(JSContextRef destinationContext, JSValueRef* exception)
{
+ JSLock lock(SilenceAssertionsOnly);
ExecState* exec = toJS(destinationContext);
- JSValue value = deserialize(exec);
+ JSValue value = deserialize(exec, exec->lexicalGlobalObject());
if (exec->hadException()) {
if (exception)
*exception = toRef(exec, exec->exception());