Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/nodejs/node.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'deps/v8/src/json-stringifier.cc')
-rw-r--r--deps/v8/src/json-stringifier.cc122
1 files changed, 120 insertions, 2 deletions
diff --git a/deps/v8/src/json-stringifier.cc b/deps/v8/src/json-stringifier.cc
index b1d95422b0c..91a1b7201bf 100644
--- a/deps/v8/src/json-stringifier.cc
+++ b/deps/v8/src/json-stringifier.cc
@@ -5,14 +5,128 @@
#include "src/json-stringifier.h"
#include "src/conversions.h"
+#include "src/heap/heap-inl.h"
#include "src/lookup.h"
#include "src/messages.h"
#include "src/objects-inl.h"
+#include "src/objects/js-array-inl.h"
+#include "src/string-builder-inl.h"
#include "src/utils.h"
namespace v8 {
namespace internal {
+class JsonStringifier BASE_EMBEDDED {
+ public:
+ explicit JsonStringifier(Isolate* isolate);
+
+ ~JsonStringifier() { DeleteArray(gap_); }
+
+ V8_WARN_UNUSED_RESULT MaybeHandle<Object> Stringify(Handle<Object> object,
+ Handle<Object> replacer,
+ Handle<Object> gap);
+
+ private:
+ enum Result { UNCHANGED, SUCCESS, EXCEPTION };
+
+ bool InitializeReplacer(Handle<Object> replacer);
+ bool InitializeGap(Handle<Object> gap);
+
+ V8_WARN_UNUSED_RESULT MaybeHandle<Object> ApplyToJsonFunction(
+ Handle<Object> object, Handle<Object> key);
+ V8_WARN_UNUSED_RESULT MaybeHandle<Object> ApplyReplacerFunction(
+ Handle<Object> value, Handle<Object> key, Handle<Object> initial_holder);
+
+ // Entry point to serialize the object.
+ V8_INLINE Result SerializeObject(Handle<Object> obj) {
+ return Serialize_<false>(obj, false, factory()->empty_string());
+ }
+
+ // Serialize an array element.
+ // The index may serve as argument for the toJSON function.
+ V8_INLINE Result SerializeElement(Isolate* isolate, Handle<Object> object,
+ int i) {
+ return Serialize_<false>(object, false,
+ Handle<Object>(Smi::FromInt(i), isolate));
+ }
+
+ // Serialize a object property.
+ // The key may or may not be serialized depending on the property.
+ // The key may also serve as argument for the toJSON function.
+ V8_INLINE Result SerializeProperty(Handle<Object> object, bool deferred_comma,
+ Handle<String> deferred_key) {
+ DCHECK(!deferred_key.is_null());
+ return Serialize_<true>(object, deferred_comma, deferred_key);
+ }
+
+ template <bool deferred_string_key>
+ Result Serialize_(Handle<Object> object, bool comma, Handle<Object> key);
+
+ V8_INLINE void SerializeDeferredKey(bool deferred_comma,
+ Handle<Object> deferred_key);
+
+ Result SerializeSmi(Smi* object);
+
+ Result SerializeDouble(double number);
+ V8_INLINE Result SerializeHeapNumber(Handle<HeapNumber> object) {
+ return SerializeDouble(object->value());
+ }
+
+ Result SerializeJSValue(Handle<JSValue> object);
+
+ V8_INLINE Result SerializeJSArray(Handle<JSArray> object);
+ V8_INLINE Result SerializeJSObject(Handle<JSObject> object);
+
+ Result SerializeJSProxy(Handle<JSProxy> object);
+ Result SerializeJSReceiverSlow(Handle<JSReceiver> object);
+ Result SerializeArrayLikeSlow(Handle<JSReceiver> object, uint32_t start,
+ uint32_t length);
+
+ void SerializeString(Handle<String> object);
+
+ template <typename SrcChar, typename DestChar>
+ V8_INLINE static void SerializeStringUnchecked_(
+ Vector<const SrcChar> src,
+ IncrementalStringBuilder::NoExtend<DestChar>* dest);
+
+ template <typename SrcChar, typename DestChar>
+ V8_INLINE void SerializeString_(Handle<String> string);
+
+ template <typename Char>
+ V8_INLINE static bool DoNotEscape(Char c);
+
+ V8_INLINE void NewLine();
+ V8_INLINE void Indent() { indent_++; }
+ V8_INLINE void Unindent() { indent_--; }
+ V8_INLINE void Separator(bool first);
+
+ Handle<JSReceiver> CurrentHolder(Handle<Object> value,
+ Handle<Object> inital_holder);
+
+ Result StackPush(Handle<Object> object);
+ void StackPop();
+
+ Factory* factory() { return isolate_->factory(); }
+
+ Isolate* isolate_;
+ IncrementalStringBuilder builder_;
+ Handle<String> tojson_string_;
+ Handle<JSArray> stack_;
+ Handle<FixedArray> property_list_;
+ Handle<JSReceiver> replacer_function_;
+ uc16* gap_;
+ int indent_;
+
+ static const int kJsonEscapeTableEntrySize = 8;
+ static const char* const JsonEscapeTable;
+};
+
+MaybeHandle<Object> JsonStringify(Isolate* isolate, Handle<Object> object,
+ Handle<Object> replacer, Handle<Object> gap) {
+ JsonStringifier stringifier(isolate);
+ return stringifier.Stringify(object, replacer, gap);
+}
+
// Translation table to escape Latin1 characters.
// Table entries start at a multiple of 8 and are null-terminated.
const char* const JsonStringifier::JsonEscapeTable =
@@ -112,7 +226,9 @@ bool JsonStringifier::InitializeReplacer(Handle<Object> replacer) {
Handle<Object> length_obj;
ASSIGN_RETURN_ON_EXCEPTION_VALUE(
isolate_, length_obj,
- Object::GetLengthFromArrayLike(isolate_, replacer), false);
+ Object::GetLengthFromArrayLike(isolate_,
+ Handle<JSReceiver>::cast(replacer)),
+ false);
uint32_t length;
if (!length_obj->ToUint32(&length)) length = kMaxUInt32;
for (uint32_t i = 0; i < length; i++) {
@@ -606,7 +722,9 @@ JsonStringifier::Result JsonStringifier::SerializeJSProxy(
Handle<Object> length_object;
ASSIGN_RETURN_ON_EXCEPTION_VALUE(
isolate_, length_object,
- Object::GetLengthFromArrayLike(isolate_, object), EXCEPTION);
+ Object::GetLengthFromArrayLike(isolate_,
+ Handle<JSReceiver>::cast(object)),
+ EXCEPTION);
uint32_t length;
if (!length_object->ToUint32(&length)) {
// Technically, we need to be able to handle lengths outside the