summaryrefslogtreecommitdiff
path: root/Source/JavaScriptCore/runtime/JSONObject.cpp
diff options
context:
space:
mode:
authorAllan Sandfeld Jensen <allan.jensen@digia.com>2013-09-13 12:51:20 +0200
committerThe Qt Project <gerrit-noreply@qt-project.org>2013-09-19 20:50:05 +0200
commitd441d6f39bb846989d95bcf5caf387b42414718d (patch)
treee367e64a75991c554930278175d403c072de6bb8 /Source/JavaScriptCore/runtime/JSONObject.cpp
parent0060b2994c07842f4c59de64b5e3e430525c4b90 (diff)
downloadqtwebkit-d441d6f39bb846989d95bcf5caf387b42414718d.tar.gz
Import Qt5x2 branch of QtWebkit for Qt 5.2
Importing a new snapshot of webkit. Change-Id: I2d01ad12cdc8af8cb015387641120a9d7ea5f10c Reviewed-by: Allan Sandfeld Jensen <allan.jensen@digia.com>
Diffstat (limited to 'Source/JavaScriptCore/runtime/JSONObject.cpp')
-rw-r--r--Source/JavaScriptCore/runtime/JSONObject.cpp103
1 files changed, 36 insertions, 67 deletions
diff --git a/Source/JavaScriptCore/runtime/JSONObject.cpp b/Source/JavaScriptCore/runtime/JSONObject.cpp
index e051ec7d9..91b412ec3 100644
--- a/Source/JavaScriptCore/runtime/JSONObject.cpp
+++ b/Source/JavaScriptCore/runtime/JSONObject.cpp
@@ -35,6 +35,8 @@
#include "Local.h"
#include "LocalScope.h"
#include "Lookup.h"
+#include "ObjectConstructor.h"
+#include "Operations.h"
#include "PropertyNameArray.h"
#include <wtf/MathExtras.h>
#include <wtf/text/StringBuilder.h>
@@ -53,13 +55,13 @@ static EncodedJSValue JSC_HOST_CALL JSONProtoFuncStringify(ExecState*);
namespace JSC {
JSONObject::JSONObject(JSGlobalObject* globalObject, Structure* structure)
- : JSNonFinalObject(globalObject->globalData(), structure)
+ : JSNonFinalObject(globalObject->vm(), structure)
{
}
void JSONObject::finishCreation(JSGlobalObject* globalObject)
{
- Base::finishCreation(globalObject->globalData());
+ Base::finishCreation(globalObject->vm());
ASSERT(inherits(&s_info));
}
@@ -88,7 +90,7 @@ public:
private:
class Holder {
public:
- Holder(JSGlobalData&, JSObject*);
+ Holder(VM&, JSObject*);
JSObject* object() const { return m_object.get(); }
@@ -125,7 +127,7 @@ private:
CallData m_replacerCallData;
const String m_gap;
- Vector<Holder, 16> m_holderStack;
+ Vector<Holder, 16, UnsafeVectorOverflow> m_holderStack;
String m_repeatedGap;
String m_indent;
};
@@ -215,7 +217,7 @@ Stringifier::Stringifier(ExecState* exec, const Local<Unknown>& replacer, const
if (m_replacer.asObject()->inherits(&JSArray::s_info)) {
m_usingArrayReplacer = true;
Handle<JSObject> array = m_replacer.asObject();
- unsigned length = array->get(exec, exec->globalData().propertyNames->length).toUInt32(exec);
+ unsigned length = array->get(exec, exec->vm().propertyNames->length).toUInt32(exec);
for (unsigned i = 0; i < length; ++i) {
JSValue name = array->get(exec, i);
if (exec->hadException())
@@ -238,18 +240,18 @@ Local<Unknown> Stringifier::stringify(Handle<Unknown> value)
{
JSObject* object = constructEmptyObject(m_exec);
if (m_exec->hadException())
- return Local<Unknown>(m_exec->globalData(), jsNull());
+ return Local<Unknown>(m_exec->vm(), jsNull());
- PropertyNameForFunctionCall emptyPropertyName(m_exec->globalData().propertyNames->emptyIdentifier);
- object->putDirect(m_exec->globalData(), m_exec->globalData().propertyNames->emptyIdentifier, value.get());
+ PropertyNameForFunctionCall emptyPropertyName(m_exec->vm().propertyNames->emptyIdentifier);
+ object->putDirect(m_exec->vm(), m_exec->vm().propertyNames->emptyIdentifier, value.get());
StringBuilder result;
if (appendStringifiedValue(result, value.get(), object, emptyPropertyName) != StringifySucceeded)
- return Local<Unknown>(m_exec->globalData(), jsUndefined());
+ return Local<Unknown>(m_exec->vm(), jsUndefined());
if (m_exec->hadException())
- return Local<Unknown>(m_exec->globalData(), jsNull());
+ return Local<Unknown>(m_exec->vm(), jsNull());
- return Local<Unknown>(m_exec->globalData(), jsString(m_exec, result.toString()));
+ return Local<Unknown>(m_exec->vm(), jsString(m_exec, result.toString()));
}
template <typename CharType>
@@ -318,10 +320,10 @@ void Stringifier::appendQuotedString(StringBuilder& builder, const String& value
inline JSValue Stringifier::toJSON(JSValue value, const PropertyNameForFunctionCall& propertyName)
{
ASSERT(!m_exec->hadException());
- if (!value.isObject() || !asObject(value)->hasProperty(m_exec, m_exec->globalData().propertyNames->toJSON))
+ if (!value.isObject() || !asObject(value)->hasProperty(m_exec, m_exec->vm().propertyNames->toJSON))
return value;
- JSValue toJSONFunction = asObject(value)->get(m_exec, m_exec->globalData().propertyNames->toJSON);
+ JSValue toJSONFunction = asObject(value)->get(m_exec, m_exec->vm().propertyNames->toJSON);
if (m_exec->hadException())
return jsNull();
@@ -385,7 +387,7 @@ Stringifier::StringifyResult Stringifier::appendStringifiedValue(StringBuilder&
if (value.isNumber()) {
double number = value.asNumber();
- if (!isfinite(number))
+ if (!std::isfinite(number))
builder.appendLiteral("null");
else
builder.append(String::numberToStringECMAScript(number));
@@ -414,25 +416,14 @@ Stringifier::StringifyResult Stringifier::appendStringifiedValue(StringBuilder&
}
}
bool holderStackWasEmpty = m_holderStack.isEmpty();
- m_holderStack.append(Holder(m_exec->globalData(), object));
+ m_holderStack.append(Holder(m_exec->vm(), object));
if (!holderStackWasEmpty)
return StringifySucceeded;
- // If this is the outermost call, then loop to handle everything on the holder stack.
- TimeoutChecker localTimeoutChecker(m_exec->globalData().timeoutChecker);
- localTimeoutChecker.reset();
- unsigned tickCount = localTimeoutChecker.ticksUntilNextCheck();
do {
while (m_holderStack.last().appendNextProperty(*this, builder)) {
if (m_exec->hadException())
return StringifyFailed;
- if (!--tickCount) {
- if (localTimeoutChecker.didTimeOut(m_exec)) {
- throwError(m_exec, createInterruptedExecutionException(&m_exec->globalData()));
- return StringifyFailed;
- }
- tickCount = localTimeoutChecker.ticksUntilNextCheck();
- }
}
m_holderStack.removeLast();
} while (!m_holderStack.isEmpty());
@@ -468,8 +459,8 @@ inline void Stringifier::startNewLine(StringBuilder& builder) const
builder.append(m_indent);
}
-inline Stringifier::Holder::Holder(JSGlobalData& globalData, JSObject* object)
- : m_object(globalData, object)
+inline Stringifier::Holder::Holder(VM& vm, JSObject* object)
+ : m_object(vm, object)
, m_isArray(object->inherits(&JSArray::s_info))
, m_index(0)
#ifndef NDEBUG
@@ -488,7 +479,7 @@ bool Stringifier::Holder::appendNextProperty(Stringifier& stringifier, StringBui
if (!m_index) {
if (m_isArray) {
m_isJSArray = isJSArray(m_object.get());
- m_size = m_object->get(exec, exec->globalData().propertyNames->length).toUInt32(exec);
+ m_size = m_object->get(exec, exec->vm().propertyNames->length).toUInt32(exec);
builder.append('[');
} else {
if (stringifier.m_usingArrayReplacer)
@@ -613,7 +604,7 @@ class Walker {
public:
Walker(ExecState* exec, Handle<JSObject> function, CallType callType, CallData callData)
: m_exec(exec)
- , m_function(exec->globalData(), function)
+ , m_function(exec->vm(), function)
, m_callType(callType)
, m_callData(callData)
{
@@ -636,26 +627,22 @@ private:
CallData m_callData;
};
-// We clamp recursion well beyond anything reasonable, but we also have a timeout check
-// to guard against "infinite" execution by inserting arbitrarily large objects.
+// We clamp recursion well beyond anything reasonable.
static const unsigned maximumFilterRecursion = 40000;
enum WalkerState { StateUnknown, ArrayStartState, ArrayStartVisitMember, ArrayEndVisitMember,
ObjectStartState, ObjectStartVisitMember, ObjectEndVisitMember };
NEVER_INLINE JSValue Walker::walk(JSValue unfiltered)
{
- Vector<PropertyNameArray, 16> propertyStack;
- Vector<uint32_t, 16> indexStack;
- LocalStack<JSObject, 16> objectStack(m_exec->globalData());
- LocalStack<JSArray, 16> arrayStack(m_exec->globalData());
+ Vector<PropertyNameArray, 16, UnsafeVectorOverflow> propertyStack;
+ Vector<uint32_t, 16, UnsafeVectorOverflow> indexStack;
+ LocalStack<JSObject, 16> objectStack(m_exec->vm());
+ LocalStack<JSArray, 16> arrayStack(m_exec->vm());
- Vector<WalkerState, 16> stateStack;
+ Vector<WalkerState, 16, UnsafeVectorOverflow> stateStack;
WalkerState state = StateUnknown;
JSValue inValue = unfiltered;
JSValue outValue = jsNull();
- TimeoutChecker localTimeoutChecker(m_exec->globalData().timeoutChecker);
- localTimeoutChecker.reset();
- unsigned tickCount = localTimeoutChecker.ticksUntilNextCheck();
while (1) {
switch (state) {
arrayStartState:
@@ -672,12 +659,6 @@ NEVER_INLINE JSValue Walker::walk(JSValue unfiltered)
}
arrayStartVisitMember:
case ArrayStartVisitMember: {
- if (!--tickCount) {
- if (localTimeoutChecker.didTimeOut(m_exec))
- return throwError(m_exec, createInterruptedExecutionException(&m_exec->globalData()));
- tickCount = localTimeoutChecker.ticksUntilNextCheck();
- }
-
JSArray* array = arrayStack.peek();
uint32_t index = indexStack.last();
if (index == array->length()) {
@@ -731,12 +712,6 @@ NEVER_INLINE JSValue Walker::walk(JSValue unfiltered)
}
objectStartVisitMember:
case ObjectStartVisitMember: {
- if (!--tickCount) {
- if (localTimeoutChecker.didTimeOut(m_exec))
- return throwError(m_exec, createInterruptedExecutionException(&m_exec->globalData()));
- tickCount = localTimeoutChecker.ticksUntilNextCheck();
- }
-
JSObject* object = objectStack.peek();
uint32_t index = indexStack.last();
PropertyNameArray& properties = propertyStack.last();
@@ -794,16 +769,10 @@ NEVER_INLINE JSValue Walker::walk(JSValue unfiltered)
state = stateStack.last();
stateStack.removeLast();
-
- if (!--tickCount) {
- if (localTimeoutChecker.didTimeOut(m_exec))
- return throwError(m_exec, createInterruptedExecutionException(&m_exec->globalData()));
- tickCount = localTimeoutChecker.ticksUntilNextCheck();
- }
}
JSObject* finalHolder = constructEmptyObject(m_exec);
PutPropertySlot slot;
- finalHolder->methodTable()->put(finalHolder, m_exec, m_exec->globalData().propertyNames->emptyIdentifier, outValue, slot);
+ finalHolder->methodTable()->put(finalHolder, m_exec, m_exec->vm().propertyNames->emptyIdentifier, outValue, slot);
return callReviver(finalHolder, jsEmptyString(m_exec), outValue);
}
@@ -817,7 +786,7 @@ EncodedJSValue JSC_HOST_CALL JSONProtoFuncParse(ExecState* exec)
return JSValue::encode(jsNull());
JSValue unfiltered;
- LocalScope scope(exec->globalData());
+ LocalScope scope(exec->vm());
if (source.is8Bit()) {
LiteralParser<LChar> jsonParser(exec, source.characters8(), source.length(), StrictJSON);
unfiltered = jsonParser.tryLiteralParse();
@@ -838,7 +807,7 @@ EncodedJSValue JSC_HOST_CALL JSONProtoFuncParse(ExecState* exec)
CallType callType = getCallData(function, callData);
if (callType == CallTypeNone)
return JSValue::encode(unfiltered);
- return JSValue::encode(Walker(exec, Local<JSObject>(exec->globalData(), asObject(function)), callType, callData).walk(unfiltered));
+ return JSValue::encode(Walker(exec, Local<JSObject>(exec->vm(), asObject(function)), callType, callData).walk(unfiltered));
}
// ECMA-262 v5 15.12.3
@@ -846,17 +815,17 @@ EncodedJSValue JSC_HOST_CALL JSONProtoFuncStringify(ExecState* exec)
{
if (!exec->argumentCount())
return throwVMError(exec, createError(exec, ASCIILiteral("No input to stringify")));
- LocalScope scope(exec->globalData());
- Local<Unknown> value(exec->globalData(), exec->argument(0));
- Local<Unknown> replacer(exec->globalData(), exec->argument(1));
- Local<Unknown> space(exec->globalData(), exec->argument(2));
+ LocalScope scope(exec->vm());
+ Local<Unknown> value(exec->vm(), exec->argument(0));
+ Local<Unknown> replacer(exec->vm(), exec->argument(1));
+ Local<Unknown> space(exec->vm(), exec->argument(2));
return JSValue::encode(Stringifier(exec, replacer, space).stringify(value).get());
}
String JSONStringify(ExecState* exec, JSValue value, unsigned indent)
{
- LocalScope scope(exec->globalData());
- Local<Unknown> result = Stringifier(exec, Local<Unknown>(exec->globalData(), jsNull()), Local<Unknown>(exec->globalData(), jsNumber(indent))).stringify(Local<Unknown>(exec->globalData(), value));
+ LocalScope scope(exec->vm());
+ Local<Unknown> result = Stringifier(exec, Local<Unknown>(exec->vm(), jsNull()), Local<Unknown>(exec->vm(), jsNumber(indent))).stringify(Local<Unknown>(exec->vm(), value));
if (result.isUndefinedOrNull())
return String();
return result.getString(exec);