Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(173)

Side by Side Diff: src/json-stringifier.cc

Issue 2002933002: [json] move json parser and stringifier into own compilation units. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: rebase Created 4 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/json-stringifier.h ('k') | src/runtime/runtime.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2016 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #ifndef V8_JSON_STRINGIFIER_H_ 5 #include "src/json-stringifier.h"
6 #define V8_JSON_STRINGIFIER_H_
7 6
8 #include "src/conversions.h" 7 #include "src/conversions.h"
9 #include "src/lookup.h" 8 #include "src/lookup.h"
10 #include "src/messages.h" 9 #include "src/messages.h"
11 #include "src/string-builder.h" 10 #include "src/objects-inl.h"
12 #include "src/utils.h" 11 #include "src/utils.h"
13 12
14 namespace v8 { 13 namespace v8 {
15 namespace internal { 14 namespace internal {
16 15
17 class BasicJsonStringifier BASE_EMBEDDED {
18 public:
19 BasicJsonStringifier(Isolate* isolate, Handle<String> gap);
20
21 ~BasicJsonStringifier() { DeleteArray(gap_); }
22
23 MUST_USE_RESULT MaybeHandle<Object> Stringify(Handle<Object> object);
24
25 MUST_USE_RESULT INLINE(static MaybeHandle<Object> StringifyString(
26 Isolate* isolate,
27 Handle<String> object));
28
29 private:
30 enum Result { UNCHANGED, SUCCESS, EXCEPTION };
31
32 MUST_USE_RESULT MaybeHandle<Object> ApplyToJsonFunction(
33 Handle<Object> object,
34 Handle<Object> key);
35
36 // Entry point to serialize the object.
37 INLINE(Result SerializeObject(Handle<Object> obj)) {
38 return Serialize_<false>(obj, false, factory()->empty_string());
39 }
40
41 // Serialize an array element.
42 // The index may serve as argument for the toJSON function.
43 INLINE(Result SerializeElement(Isolate* isolate,
44 Handle<Object> object,
45 int i)) {
46 return Serialize_<false>(object,
47 false,
48 Handle<Object>(Smi::FromInt(i), isolate));
49 }
50
51 // Serialize a object property.
52 // The key may or may not be serialized depending on the property.
53 // The key may also serve as argument for the toJSON function.
54 INLINE(Result SerializeProperty(Handle<Object> object,
55 bool deferred_comma,
56 Handle<String> deferred_key)) {
57 DCHECK(!deferred_key.is_null());
58 return Serialize_<true>(object, deferred_comma, deferred_key);
59 }
60
61 template <bool deferred_string_key>
62 Result Serialize_(Handle<Object> object, bool comma, Handle<Object> key);
63
64 void SerializeDeferredKey(bool deferred_comma, Handle<Object> deferred_key) {
65 Separator(!deferred_comma);
66 SerializeString(Handle<String>::cast(deferred_key));
67 builder_.AppendCharacter(':');
68 if (gap_ != nullptr) builder_.AppendCharacter(' ');
69 }
70
71 Result SerializeSmi(Smi* object);
72
73 Result SerializeDouble(double number);
74 INLINE(Result SerializeHeapNumber(Handle<HeapNumber> object)) {
75 return SerializeDouble(object->value());
76 }
77
78 Result SerializeJSValue(Handle<JSValue> object);
79
80 INLINE(Result SerializeJSArray(Handle<JSArray> object));
81 INLINE(Result SerializeJSObject(Handle<JSObject> object));
82
83 Result SerializeJSProxy(Handle<JSProxy> object);
84 Result SerializeJSReceiverSlow(Handle<JSReceiver> object);
85 Result SerializeArrayLikeSlow(Handle<JSReceiver> object, uint32_t start,
86 uint32_t length);
87
88 void SerializeString(Handle<String> object);
89
90 template <typename SrcChar, typename DestChar>
91 INLINE(static void SerializeStringUnchecked_(
92 Vector<const SrcChar> src,
93 IncrementalStringBuilder::NoExtend<DestChar>* dest));
94
95 template <typename SrcChar, typename DestChar>
96 INLINE(void SerializeString_(Handle<String> string));
97
98 template <typename Char>
99 INLINE(static bool DoNotEscape(Char c));
100
101 INLINE(void NewLine());
102 INLINE(void Indent() { indent_++; });
103 INLINE(void Unindent() { indent_--; });
104 INLINE(void Separator(bool first) {
105 if (!first) builder_.AppendCharacter(',');
106 NewLine();
107 })
108
109 Result StackPush(Handle<Object> object);
110 void StackPop();
111
112 Factory* factory() { return isolate_->factory(); }
113
114 Isolate* isolate_;
115 IncrementalStringBuilder builder_;
116 Handle<String> tojson_string_;
117 Handle<JSArray> stack_;
118 Handle<String> gap_string_;
119 uc16* gap_;
120 int indent_;
121
122 static const int kJsonEscapeTableEntrySize = 8;
123 static const char* const JsonEscapeTable;
124 };
125
126
127 // Translation table to escape Latin1 characters. 16 // Translation table to escape Latin1 characters.
128 // Table entries start at a multiple of 8 and are null-terminated. 17 // Table entries start at a multiple of 8 and are null-terminated.
129 const char* const BasicJsonStringifier::JsonEscapeTable = 18 const char* const BasicJsonStringifier::JsonEscapeTable =
130 "\\u0000\0 \\u0001\0 \\u0002\0 \\u0003\0 " 19 "\\u0000\0 \\u0001\0 \\u0002\0 \\u0003\0 "
131 "\\u0004\0 \\u0005\0 \\u0006\0 \\u0007\0 " 20 "\\u0004\0 \\u0005\0 \\u0006\0 \\u0007\0 "
132 "\\b\0 \\t\0 \\n\0 \\u000b\0 " 21 "\\b\0 \\t\0 \\n\0 \\u000b\0 "
133 "\\f\0 \\r\0 \\u000e\0 \\u000f\0 " 22 "\\f\0 \\r\0 \\u000e\0 \\u000f\0 "
134 "\\u0010\0 \\u0011\0 \\u0012\0 \\u0013\0 " 23 "\\u0010\0 \\u0011\0 \\u0012\0 \\u0013\0 "
135 "\\u0014\0 \\u0015\0 \\u0016\0 \\u0017\0 " 24 "\\u0014\0 \\u0015\0 \\u0016\0 \\u0017\0 "
136 "\\u0018\0 \\u0019\0 \\u001a\0 \\u001b\0 " 25 "\\u0018\0 \\u0019\0 \\u001a\0 \\u001b\0 "
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
207 CopyChars(gap_, flat.ToOneByteVector().start(), gap_length); 96 CopyChars(gap_, flat.ToOneByteVector().start(), gap_length);
208 } else { 97 } else {
209 CopyChars(gap_, flat.ToUC16Vector().start(), gap_length); 98 CopyChars(gap_, flat.ToUC16Vector().start(), gap_length);
210 } 99 }
211 gap_[gap_length] = '\0'; 100 gap_[gap_length] = '\0';
212 } else { 101 } else {
213 gap_ = nullptr; 102 gap_ = nullptr;
214 } 103 }
215 } 104 }
216 105
217
218 MaybeHandle<Object> BasicJsonStringifier::Stringify(Handle<Object> object) { 106 MaybeHandle<Object> BasicJsonStringifier::Stringify(Handle<Object> object) {
219 Result result = SerializeObject(object); 107 Result result = SerializeObject(object);
220 if (result == UNCHANGED) return factory()->undefined_value(); 108 if (result == UNCHANGED) return factory()->undefined_value();
221 if (result == SUCCESS) return builder_.Finish(); 109 if (result == SUCCESS) return builder_.Finish();
222 DCHECK(result == EXCEPTION); 110 DCHECK(result == EXCEPTION);
223 return MaybeHandle<Object>(); 111 return MaybeHandle<Object>();
224 } 112 }
225 113
226
227 MaybeHandle<Object> BasicJsonStringifier::StringifyString( 114 MaybeHandle<Object> BasicJsonStringifier::StringifyString(
228 Isolate* isolate, Handle<String> object) { 115 Isolate* isolate, Handle<String> object) {
229 static const int kJsonQuoteWorstCaseBlowup = 6; 116 static const int kJsonQuoteWorstCaseBlowup = 6;
230 static const int kSpaceForQuotes = 2; 117 static const int kSpaceForQuotes = 2;
231 int worst_case_length = 118 int worst_case_length =
232 object->length() * kJsonQuoteWorstCaseBlowup + kSpaceForQuotes; 119 object->length() * kJsonQuoteWorstCaseBlowup + kSpaceForQuotes;
233 120
234 if (worst_case_length > 32 * KB) { // Slow path if too large. 121 if (worst_case_length > 32 * KB) { // Slow path if too large.
235 BasicJsonStringifier stringifier(isolate, 122 BasicJsonStringifier stringifier(isolate,
236 isolate->factory()->empty_string()); 123 isolate->factory()->empty_string());
237 return stringifier.Stringify(object); 124 return stringifier.Stringify(object);
238 } 125 }
(...skipping 19 matching lines...) Expand all
258 IncrementalStringBuilder::NoExtendString<uc16> no_extend(result, 145 IncrementalStringBuilder::NoExtendString<uc16> no_extend(result,
259 worst_case_length); 146 worst_case_length);
260 no_extend.Append('\"'); 147 no_extend.Append('\"');
261 SerializeStringUnchecked_(object->GetFlatContent().ToUC16Vector(), 148 SerializeStringUnchecked_(object->GetFlatContent().ToUC16Vector(),
262 &no_extend); 149 &no_extend);
263 no_extend.Append('\"'); 150 no_extend.Append('\"');
264 return no_extend.Finalize(); 151 return no_extend.Finalize();
265 } 152 }
266 } 153 }
267 154
268
269 MaybeHandle<Object> BasicJsonStringifier::ApplyToJsonFunction( 155 MaybeHandle<Object> BasicJsonStringifier::ApplyToJsonFunction(
270 Handle<Object> object, Handle<Object> key) { 156 Handle<Object> object, Handle<Object> key) {
271 LookupIterator it(object, tojson_string_, 157 LookupIterator it(object, tojson_string_,
272 LookupIterator::PROTOTYPE_CHAIN_SKIP_INTERCEPTOR); 158 LookupIterator::PROTOTYPE_CHAIN_SKIP_INTERCEPTOR);
273 Handle<Object> fun; 159 Handle<Object> fun;
274 ASSIGN_RETURN_ON_EXCEPTION(isolate_, fun, Object::GetProperty(&it), Object); 160 ASSIGN_RETURN_ON_EXCEPTION(isolate_, fun, Object::GetProperty(&it), Object);
275 if (!fun->IsCallable()) return object; 161 if (!fun->IsCallable()) return object;
276 162
277 // Call toJSON function. 163 // Call toJSON function.
278 if (key->IsSmi()) key = factory()->NumberToString(key); 164 if (key->IsSmi()) key = factory()->NumberToString(key);
279 Handle<Object> argv[] = { key }; 165 Handle<Object> argv[] = {key};
280 HandleScope scope(isolate_); 166 HandleScope scope(isolate_);
281 ASSIGN_RETURN_ON_EXCEPTION( 167 ASSIGN_RETURN_ON_EXCEPTION(isolate_, object,
282 isolate_, object, 168 Execution::Call(isolate_, fun, object, 1, argv),
283 Execution::Call(isolate_, fun, object, 1, argv), 169 Object);
284 Object);
285 return scope.CloseAndEscape(object); 170 return scope.CloseAndEscape(object);
286 } 171 }
287 172
288
289 BasicJsonStringifier::Result BasicJsonStringifier::StackPush( 173 BasicJsonStringifier::Result BasicJsonStringifier::StackPush(
290 Handle<Object> object) { 174 Handle<Object> object) {
291 StackLimitCheck check(isolate_); 175 StackLimitCheck check(isolate_);
292 if (check.HasOverflowed()) { 176 if (check.HasOverflowed()) {
293 isolate_->StackOverflow(); 177 isolate_->StackOverflow();
294 return EXCEPTION; 178 return EXCEPTION;
295 } 179 }
296 180
297 int length = Smi::cast(stack_->length())->value(); 181 int length = Smi::cast(stack_->length())->value();
298 { 182 {
299 DisallowHeapAllocation no_allocation; 183 DisallowHeapAllocation no_allocation;
300 FixedArray* elements = FixedArray::cast(stack_->elements()); 184 FixedArray* elements = FixedArray::cast(stack_->elements());
301 for (int i = 0; i < length; i++) { 185 for (int i = 0; i < length; i++) {
302 if (elements->get(i) == *object) { 186 if (elements->get(i) == *object) {
303 AllowHeapAllocation allow_to_return_error; 187 AllowHeapAllocation allow_to_return_error;
304 Handle<Object> error = 188 Handle<Object> error =
305 factory()->NewTypeError(MessageTemplate::kCircularStructure); 189 factory()->NewTypeError(MessageTemplate::kCircularStructure);
306 isolate_->Throw(*error); 190 isolate_->Throw(*error);
307 return EXCEPTION; 191 return EXCEPTION;
308 } 192 }
309 } 193 }
310 } 194 }
311 JSArray::SetLength(stack_, length + 1); 195 JSArray::SetLength(stack_, length + 1);
312 FixedArray::cast(stack_->elements())->set(length, *object); 196 FixedArray::cast(stack_->elements())->set(length, *object);
313 return SUCCESS; 197 return SUCCESS;
314 } 198 }
315 199
316
317 void BasicJsonStringifier::StackPop() { 200 void BasicJsonStringifier::StackPop() {
318 int length = Smi::cast(stack_->length())->value(); 201 int length = Smi::cast(stack_->length())->value();
319 stack_->set_length(Smi::FromInt(length - 1)); 202 stack_->set_length(Smi::FromInt(length - 1));
320 } 203 }
321 204
322
323 template <bool deferred_string_key> 205 template <bool deferred_string_key>
324 BasicJsonStringifier::Result BasicJsonStringifier::Serialize_( 206 BasicJsonStringifier::Result BasicJsonStringifier::Serialize_(
325 Handle<Object> object, bool comma, Handle<Object> key) { 207 Handle<Object> object, bool comma, Handle<Object> key) {
326 if (object->IsJSReceiver()) { 208 if (object->IsJSReceiver()) {
327 ASSIGN_RETURN_ON_EXCEPTION_VALUE( 209 ASSIGN_RETURN_ON_EXCEPTION_VALUE(
328 isolate_, object, 210 isolate_, object, ApplyToJsonFunction(object, key), EXCEPTION);
329 ApplyToJsonFunction(object, key),
330 EXCEPTION);
331 } 211 }
332 212
333 if (object->IsSmi()) { 213 if (object->IsSmi()) {
334 if (deferred_string_key) SerializeDeferredKey(comma, key); 214 if (deferred_string_key) SerializeDeferredKey(comma, key);
335 return SerializeSmi(Smi::cast(*object)); 215 return SerializeSmi(Smi::cast(*object));
336 } 216 }
337 217
338 switch (HeapObject::cast(*object)->map()->instance_type()) { 218 switch (HeapObject::cast(*object)->map()->instance_type()) {
339 case HEAP_NUMBER_TYPE: 219 case HEAP_NUMBER_TYPE:
340 case MUTABLE_HEAP_NUMBER_TYPE: 220 case MUTABLE_HEAP_NUMBER_TYPE:
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
380 return SerializeJSProxy(Handle<JSProxy>::cast(object)); 260 return SerializeJSProxy(Handle<JSProxy>::cast(object));
381 } 261 }
382 return SerializeJSObject(Handle<JSObject>::cast(object)); 262 return SerializeJSObject(Handle<JSObject>::cast(object));
383 } 263 }
384 } 264 }
385 265
386 UNREACHABLE(); 266 UNREACHABLE();
387 return UNCHANGED; 267 return UNCHANGED;
388 } 268 }
389 269
390
391 BasicJsonStringifier::Result BasicJsonStringifier::SerializeJSValue( 270 BasicJsonStringifier::Result BasicJsonStringifier::SerializeJSValue(
392 Handle<JSValue> object) { 271 Handle<JSValue> object) {
393 String* class_name = object->class_name(); 272 String* class_name = object->class_name();
394 if (class_name == isolate_->heap()->String_string()) { 273 if (class_name == isolate_->heap()->String_string()) {
395 Handle<Object> value; 274 Handle<Object> value;
396 ASSIGN_RETURN_ON_EXCEPTION_VALUE( 275 ASSIGN_RETURN_ON_EXCEPTION_VALUE(
397 isolate_, value, Object::ToString(isolate_, object), EXCEPTION); 276 isolate_, value, Object::ToString(isolate_, object), EXCEPTION);
398 SerializeString(Handle<String>::cast(value)); 277 SerializeString(Handle<String>::cast(value));
399 } else if (class_name == isolate_->heap()->Number_string()) { 278 } else if (class_name == isolate_->heap()->Number_string()) {
400 Handle<Object> value; 279 Handle<Object> value;
401 ASSIGN_RETURN_ON_EXCEPTION_VALUE(isolate_, value, Object::ToNumber(object), 280 ASSIGN_RETURN_ON_EXCEPTION_VALUE(isolate_, value, Object::ToNumber(object),
402 EXCEPTION); 281 EXCEPTION);
403 if (value->IsSmi()) return SerializeSmi(Smi::cast(*value)); 282 if (value->IsSmi()) return SerializeSmi(Smi::cast(*value));
404 SerializeHeapNumber(Handle<HeapNumber>::cast(value)); 283 SerializeHeapNumber(Handle<HeapNumber>::cast(value));
405 } else if (class_name == isolate_->heap()->Boolean_string()) { 284 } else if (class_name == isolate_->heap()->Boolean_string()) {
406 Object* value = JSValue::cast(*object)->value(); 285 Object* value = JSValue::cast(*object)->value();
407 DCHECK(value->IsBoolean()); 286 DCHECK(value->IsBoolean());
408 builder_.AppendCString(value->IsTrue() ? "true" : "false"); 287 builder_.AppendCString(value->IsTrue() ? "true" : "false");
409 } else { 288 } else {
410 // ES6 24.3.2.1 step 10.c, serialize as an ordinary JSObject. 289 // ES6 24.3.2.1 step 10.c, serialize as an ordinary JSObject.
411 return SerializeJSObject(object); 290 return SerializeJSObject(object);
412 } 291 }
413 return SUCCESS; 292 return SUCCESS;
414 } 293 }
415 294
416
417 BasicJsonStringifier::Result BasicJsonStringifier::SerializeSmi(Smi* object) { 295 BasicJsonStringifier::Result BasicJsonStringifier::SerializeSmi(Smi* object) {
418 static const int kBufferSize = 100; 296 static const int kBufferSize = 100;
419 char chars[kBufferSize]; 297 char chars[kBufferSize];
420 Vector<char> buffer(chars, kBufferSize); 298 Vector<char> buffer(chars, kBufferSize);
421 builder_.AppendCString(IntToCString(object->value(), buffer)); 299 builder_.AppendCString(IntToCString(object->value(), buffer));
422 return SUCCESS; 300 return SUCCESS;
423 } 301 }
424 302
425
426 BasicJsonStringifier::Result BasicJsonStringifier::SerializeDouble( 303 BasicJsonStringifier::Result BasicJsonStringifier::SerializeDouble(
427 double number) { 304 double number) {
428 if (std::isinf(number) || std::isnan(number)) { 305 if (std::isinf(number) || std::isnan(number)) {
429 builder_.AppendCString("null"); 306 builder_.AppendCString("null");
430 return SUCCESS; 307 return SUCCESS;
431 } 308 }
432 static const int kBufferSize = 100; 309 static const int kBufferSize = 100;
433 char chars[kBufferSize]; 310 char chars[kBufferSize];
434 Vector<char> buffer(chars, kBufferSize); 311 Vector<char> buffer(chars, kBufferSize);
435 builder_.AppendCString(DoubleToCString(number, buffer)); 312 builder_.AppendCString(DoubleToCString(number, buffer));
436 return SUCCESS; 313 return SUCCESS;
437 } 314 }
438 315
439
440 BasicJsonStringifier::Result BasicJsonStringifier::SerializeJSArray( 316 BasicJsonStringifier::Result BasicJsonStringifier::SerializeJSArray(
441 Handle<JSArray> object) { 317 Handle<JSArray> object) {
442 HandleScope handle_scope(isolate_); 318 HandleScope handle_scope(isolate_);
443 Result stack_push = StackPush(object); 319 Result stack_push = StackPush(object);
444 if (stack_push != SUCCESS) return stack_push; 320 if (stack_push != SUCCESS) return stack_push;
445 uint32_t length = 0; 321 uint32_t length = 0;
446 CHECK(object->length()->ToArrayLength(&length)); 322 CHECK(object->length()->ToArrayLength(&length));
447 DCHECK(!object->IsAccessCheckNeeded()); 323 DCHECK(!object->IsAccessCheckNeeded());
448 builder_.AppendCharacter('['); 324 builder_.AppendCharacter('[');
449 Indent(); 325 Indent();
(...skipping 201 matching lines...) Expand 10 before | Expand all | Expand 10 after
651 if (length > 0) NewLine(); 527 if (length > 0) NewLine();
652 builder_.AppendCharacter(']'); 528 builder_.AppendCharacter(']');
653 } else { 529 } else {
654 Result result = SerializeJSReceiverSlow(object); 530 Result result = SerializeJSReceiverSlow(object);
655 if (result != SUCCESS) return result; 531 if (result != SUCCESS) return result;
656 } 532 }
657 StackPop(); 533 StackPop();
658 return SUCCESS; 534 return SUCCESS;
659 } 535 }
660 536
661
662 template <typename SrcChar, typename DestChar> 537 template <typename SrcChar, typename DestChar>
663 void BasicJsonStringifier::SerializeStringUnchecked_( 538 void BasicJsonStringifier::SerializeStringUnchecked_(
664 Vector<const SrcChar> src, 539 Vector<const SrcChar> src,
665 IncrementalStringBuilder::NoExtend<DestChar>* dest) { 540 IncrementalStringBuilder::NoExtend<DestChar>* dest) {
666 // Assert that uc16 character is not truncated down to 8 bit. 541 // Assert that uc16 character is not truncated down to 8 bit.
667 // The <uc16, char> version of this method must not be called. 542 // The <uc16, char> version of this method must not be called.
668 DCHECK(sizeof(DestChar) >= sizeof(SrcChar)); 543 DCHECK(sizeof(DestChar) >= sizeof(SrcChar));
669 544
670 for (int i = 0; i < src.length(); i++) { 545 for (int i = 0; i < src.length(); i++) {
671 SrcChar c = src[i]; 546 SrcChar c = src[i];
672 if (DoNotEscape(c)) { 547 if (DoNotEscape(c)) {
673 dest->Append(c); 548 dest->Append(c);
674 } else { 549 } else {
675 dest->AppendCString(&JsonEscapeTable[c * kJsonEscapeTableEntrySize]); 550 dest->AppendCString(&JsonEscapeTable[c * kJsonEscapeTableEntrySize]);
676 } 551 }
677 } 552 }
678 } 553 }
679 554
680
681 template <typename SrcChar, typename DestChar> 555 template <typename SrcChar, typename DestChar>
682 void BasicJsonStringifier::SerializeString_(Handle<String> string) { 556 void BasicJsonStringifier::SerializeString_(Handle<String> string) {
683 int length = string->length(); 557 int length = string->length();
684 builder_.Append<uint8_t, DestChar>('"'); 558 builder_.Append<uint8_t, DestChar>('"');
685 // We make a rough estimate to find out if the current string can be 559 // We make a rough estimate to find out if the current string can be
686 // serialized without allocating a new string part. The worst case length of 560 // serialized without allocating a new string part. The worst case length of
687 // an escaped character is 6. Shifting the remainin string length right by 3 561 // an escaped character is 6. Shifting the remainin string length right by 3
688 // is a more pessimistic estimate, but faster to calculate. 562 // is a more pessimistic estimate, but faster to calculate.
689 int worst_case_length = length << 3; 563 int worst_case_length = length << 3;
690 if (builder_.CurrentPartCanFit(worst_case_length)) { 564 if (builder_.CurrentPartCanFit(worst_case_length)) {
(...skipping 10 matching lines...) Expand all
701 builder_.Append<SrcChar, DestChar>(c); 575 builder_.Append<SrcChar, DestChar>(c);
702 } else { 576 } else {
703 builder_.AppendCString(&JsonEscapeTable[c * kJsonEscapeTableEntrySize]); 577 builder_.AppendCString(&JsonEscapeTable[c * kJsonEscapeTableEntrySize]);
704 } 578 }
705 } 579 }
706 } 580 }
707 581
708 builder_.Append<uint8_t, DestChar>('"'); 582 builder_.Append<uint8_t, DestChar>('"');
709 } 583 }
710 584
711
712 template <> 585 template <>
713 bool BasicJsonStringifier::DoNotEscape(uint8_t c) { 586 bool BasicJsonStringifier::DoNotEscape(uint8_t c) {
714 return c >= '#' && c <= '~' && c != '\\'; 587 return c >= '#' && c <= '~' && c != '\\';
715 } 588 }
716 589
717
718 template <> 590 template <>
719 bool BasicJsonStringifier::DoNotEscape(uint16_t c) { 591 bool BasicJsonStringifier::DoNotEscape(uint16_t c) {
720 return c >= '#' && c != '\\' && c != 0x7f; 592 return c >= '#' && c != '\\' && c != 0x7f;
721 } 593 }
722 594
723 void BasicJsonStringifier::NewLine() { 595 void BasicJsonStringifier::NewLine() {
724 if (gap_ == nullptr) return; 596 if (gap_ == nullptr) return;
725 builder_.AppendCharacter('\n'); 597 builder_.AppendCharacter('\n');
726 for (int i = 0; i < indent_; i++) builder_.AppendCString(gap_); 598 for (int i = 0; i < indent_; i++) builder_.AppendCString(gap_);
727 } 599 }
728 600
601 void BasicJsonStringifier::Separator(bool first) {
602 if (!first) builder_.AppendCharacter(',');
603 NewLine();
604 }
605
606 void BasicJsonStringifier::SerializeDeferredKey(bool deferred_comma,
607 Handle<Object> deferred_key) {
608 Separator(!deferred_comma);
609 SerializeString(Handle<String>::cast(deferred_key));
610 builder_.AppendCharacter(':');
611 if (gap_ != nullptr) builder_.AppendCharacter(' ');
612 }
613
729 void BasicJsonStringifier::SerializeString(Handle<String> object) { 614 void BasicJsonStringifier::SerializeString(Handle<String> object) {
730 object = String::Flatten(object); 615 object = String::Flatten(object);
731 if (builder_.CurrentEncoding() == String::ONE_BYTE_ENCODING) { 616 if (builder_.CurrentEncoding() == String::ONE_BYTE_ENCODING) {
732 if (object->IsOneByteRepresentationUnderneath()) { 617 if (object->IsOneByteRepresentationUnderneath()) {
733 SerializeString_<uint8_t, uint8_t>(object); 618 SerializeString_<uint8_t, uint8_t>(object);
734 } else { 619 } else {
735 builder_.ChangeEncoding(); 620 builder_.ChangeEncoding();
736 SerializeString(object); 621 SerializeString(object);
737 } 622 }
738 } else { 623 } else {
739 if (object->IsOneByteRepresentationUnderneath()) { 624 if (object->IsOneByteRepresentationUnderneath()) {
740 SerializeString_<uint8_t, uc16>(object); 625 SerializeString_<uint8_t, uc16>(object);
741 } else { 626 } else {
742 SerializeString_<uc16, uc16>(object); 627 SerializeString_<uc16, uc16>(object);
743 } 628 }
744 } 629 }
745 } 630 }
746 631
747 } // namespace internal 632 } // namespace internal
748 } // namespace v8 633 } // namespace v8
749
750 #endif // V8_JSON_STRINGIFIER_H_
OLDNEW
« no previous file with comments | « src/json-stringifier.h ('k') | src/runtime/runtime.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698