OLD | NEW |
1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 149 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
160 Handle<Object> JsonParser::ParseJsonObject() { | 160 Handle<Object> JsonParser::ParseJsonObject() { |
161 Handle<JSFunction> object_constructor( | 161 Handle<JSFunction> object_constructor( |
162 isolate()->global_context()->object_function()); | 162 isolate()->global_context()->object_function()); |
163 Handle<JSObject> json_object = | 163 Handle<JSObject> json_object = |
164 isolate()->factory()->NewJSObject(object_constructor); | 164 isolate()->factory()->NewJSObject(object_constructor); |
165 ASSERT_EQ(c0_, '{'); | 165 ASSERT_EQ(c0_, '{'); |
166 | 166 |
167 AdvanceSkipWhitespace(); | 167 AdvanceSkipWhitespace(); |
168 if (c0_ != '}') { | 168 if (c0_ != '}') { |
169 do { | 169 do { |
| 170 if (c0_ != '"') return ReportUnexpectedCharacter(); |
170 Handle<String> key = ParseJsonSymbol(); | 171 Handle<String> key = ParseJsonSymbol(); |
171 if (key.is_null() || c0_ != ':') return ReportUnexpectedCharacter(); | 172 if (key.is_null() || c0_ != ':') return ReportUnexpectedCharacter(); |
172 AdvanceSkipWhitespace(); | 173 AdvanceSkipWhitespace(); |
173 Handle<Object> value = ParseJsonValue(); | 174 Handle<Object> value = ParseJsonValue(); |
174 if (value.is_null()) return ReportUnexpectedCharacter(); | 175 if (value.is_null()) return ReportUnexpectedCharacter(); |
175 | 176 |
176 uint32_t index; | 177 uint32_t index; |
177 if (key->AsArrayIndex(&index)) { | 178 if (key->AsArrayIndex(&index)) { |
178 SetOwnElement(json_object, index, value, kNonStrictMode); | 179 SetOwnElement(json_object, index, value, kNonStrictMode); |
179 } else if (key->Equals(isolate()->heap()->Proto_symbol())) { | 180 } else if (key->Equals(isolate()->heap()->Proto_symbol())) { |
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
276 number_ = StringToDouble(isolate()->unicode_cache(), | 277 number_ = StringToDouble(isolate()->unicode_cache(), |
277 result, | 278 result, |
278 NO_FLAGS, // Hex, octal or trailing junk. | 279 NO_FLAGS, // Hex, octal or trailing junk. |
279 0.0); | 280 0.0); |
280 buffer.Dispose(); | 281 buffer.Dispose(); |
281 } | 282 } |
282 SkipWhitespace(); | 283 SkipWhitespace(); |
283 return isolate()->factory()->NewNumber(number_); | 284 return isolate()->factory()->NewNumber(number_); |
284 } | 285 } |
285 | 286 |
286 Handle<Object> JsonParser::SlowScanJsonString() { | 287 Handle<String> JsonParser::SlowScanJsonString() { |
287 // The currently scanned ascii characters. | 288 // The currently scanned ascii characters. |
288 Handle<String> ascii(isolate()->factory()->NewSubString(source_, | 289 Handle<String> ascii(isolate()->factory()->NewSubString(source_, |
289 beg_pos_, | 290 beg_pos_, |
290 position_)); | 291 position_)); |
291 Handle<String> two_byte = | 292 Handle<String> two_byte = |
292 isolate()->factory()->NewRawTwoByteString(kInitialSpecialStringSize, | 293 isolate()->factory()->NewRawTwoByteString(kInitialSpecialStringSize, |
293 NOT_TENURED); | 294 NOT_TENURED); |
294 Handle<SeqTwoByteString> seq_two_byte = | 295 Handle<SeqTwoByteString> seq_two_byte = |
295 Handle<SeqTwoByteString>::cast(two_byte); | 296 Handle<SeqTwoByteString>::cast(two_byte); |
296 | 297 |
297 int allocation_count = 1; | 298 int allocation_count = 1; |
298 int count = 0; | 299 int count = 0; |
299 | 300 |
300 while (c0_ != '"') { | 301 while (c0_ != '"') { |
301 // Create new seq string | 302 // Create new seq string |
302 if (count >= kInitialSpecialStringSize * allocation_count) { | 303 if (count >= kInitialSpecialStringSize * allocation_count) { |
303 allocation_count = allocation_count * 2; | 304 allocation_count = allocation_count * 2; |
304 int new_size = allocation_count * kInitialSpecialStringSize; | 305 int new_size = allocation_count * kInitialSpecialStringSize; |
305 Handle<String> new_two_byte = | 306 Handle<String> new_two_byte = |
306 isolate()->factory()->NewRawTwoByteString(new_size, | 307 isolate()->factory()->NewRawTwoByteString(new_size, |
307 NOT_TENURED); | 308 NOT_TENURED); |
308 uc16* char_start = | 309 uc16* char_start = |
309 Handle<SeqTwoByteString>::cast(new_two_byte)->GetChars(); | 310 Handle<SeqTwoByteString>::cast(new_two_byte)->GetChars(); |
310 String::WriteToFlat(*seq_two_byte, char_start, 0, count); | 311 String::WriteToFlat(*seq_two_byte, char_start, 0, count); |
311 seq_two_byte = Handle<SeqTwoByteString>::cast(new_two_byte); | 312 seq_two_byte = Handle<SeqTwoByteString>::cast(new_two_byte); |
312 } | 313 } |
313 | 314 |
314 // Check for control character (0x00-0x1f) or unterminated string (<0). | 315 // Check for control character (0x00-0x1f) or unterminated string (<0). |
315 if (c0_ < 0x20) return ReportUnexpectedCharacter(); | 316 if (c0_ < 0x20) return Handle<String>::null(); |
316 if (c0_ != '\\') { | 317 if (c0_ != '\\') { |
317 seq_two_byte->SeqTwoByteStringSet(count++, c0_); | 318 seq_two_byte->SeqTwoByteStringSet(count++, c0_); |
318 Advance(); | 319 Advance(); |
319 } else { | 320 } else { |
320 Advance(); | 321 Advance(); |
321 switch (c0_) { | 322 switch (c0_) { |
322 case '"': | 323 case '"': |
323 case '\\': | 324 case '\\': |
324 case '/': | 325 case '/': |
325 seq_two_byte->SeqTwoByteStringSet(count++, c0_); | 326 seq_two_byte->SeqTwoByteStringSet(count++, c0_); |
(...skipping 12 matching lines...) Expand all Loading... |
338 break; | 339 break; |
339 case 't': | 340 case 't': |
340 seq_two_byte->SeqTwoByteStringSet(count++, '\x09'); | 341 seq_two_byte->SeqTwoByteStringSet(count++, '\x09'); |
341 break; | 342 break; |
342 case 'u': { | 343 case 'u': { |
343 uc32 value = 0; | 344 uc32 value = 0; |
344 for (int i = 0; i < 4; i++) { | 345 for (int i = 0; i < 4; i++) { |
345 Advance(); | 346 Advance(); |
346 int digit = HexValue(c0_); | 347 int digit = HexValue(c0_); |
347 if (digit < 0) { | 348 if (digit < 0) { |
348 return ReportUnexpectedCharacter(); | 349 return Handle<String>::null(); |
349 } | 350 } |
350 value = value * 16 + digit; | 351 value = value * 16 + digit; |
351 } | 352 } |
352 seq_two_byte->SeqTwoByteStringSet(count++, value); | 353 seq_two_byte->SeqTwoByteStringSet(count++, value); |
353 break; | 354 break; |
354 } | 355 } |
355 default: | 356 default: |
356 return ReportUnexpectedCharacter(); | 357 return Handle<String>::null(); |
357 } | 358 } |
358 Advance(); | 359 Advance(); |
359 } | 360 } |
360 } | 361 } |
361 // Advance past the last '"'. | 362 // Advance past the last '"'. |
362 ASSERT_EQ('"', c0_); | 363 ASSERT_EQ('"', c0_); |
363 AdvanceSkipWhitespace(); | 364 AdvanceSkipWhitespace(); |
364 | 365 |
365 // Shrink the the string to our length. | 366 // Shrink the the string to our length. |
366 if (isolate()->heap()->InNewSpace(*seq_two_byte)) { | 367 if (isolate()->heap()->InNewSpace(*seq_two_byte)) { |
367 isolate()->heap()->new_space()-> | 368 isolate()->heap()->new_space()-> |
368 ShrinkStringAtAllocationBoundary<SeqTwoByteString>(*seq_two_byte, | 369 ShrinkStringAtAllocationBoundary<SeqTwoByteString>(*seq_two_byte, |
369 count); | 370 count); |
370 } else { | 371 } else { |
371 int string_size = SeqTwoByteString::SizeFor(count); | 372 int string_size = SeqTwoByteString::SizeFor(count); |
372 int allocated_string_size = | 373 int allocated_string_size = |
373 SeqTwoByteString::SizeFor(kInitialSpecialStringSize * allocation_count); | 374 SeqTwoByteString::SizeFor(kInitialSpecialStringSize * allocation_count); |
374 int delta = allocated_string_size - string_size; | 375 int delta = allocated_string_size - string_size; |
375 Address start_filler_object = seq_two_byte->address() + string_size; | 376 Address start_filler_object = seq_two_byte->address() + string_size; |
376 seq_two_byte->set_length(count); | 377 seq_two_byte->set_length(count); |
377 isolate()->heap()->CreateFillerObjectAt(start_filler_object, delta); | 378 isolate()->heap()->CreateFillerObjectAt(start_filler_object, delta); |
378 } | 379 } |
379 return isolate()->factory()->NewConsString(ascii, seq_two_byte); | 380 return isolate()->factory()->NewConsString(ascii, seq_two_byte); |
380 } | 381 } |
381 | 382 |
382 | 383 |
383 template <bool is_symbol> | 384 template <bool is_symbol> |
384 Handle<Object> JsonParser::ScanJsonString() { | 385 Handle<String> JsonParser::ScanJsonString() { |
385 ASSERT_EQ('"', c0_); | 386 ASSERT_EQ('"', c0_); |
386 Advance(); | 387 Advance(); |
387 beg_pos_ = position_; | 388 beg_pos_ = position_; |
388 // Fast case for ascii only without escape characters. | 389 // Fast case for ascii only without escape characters. |
389 while (c0_ != '"') { | 390 while (c0_ != '"') { |
390 // Check for control character (0x00-0x1f) or unterminated string (<0). | 391 // Check for control character (0x00-0x1f) or unterminated string (<0). |
391 if (c0_ < 0x20) return ReportUnexpectedCharacter(); | 392 if (c0_ < 0x20) return Handle<String>::null(); |
392 if (c0_ != '\\' && c0_ < kMaxAsciiCharCode) { | 393 if (c0_ != '\\' && c0_ < kMaxAsciiCharCode) { |
393 Advance(); | 394 Advance(); |
394 } else { | 395 } else { |
395 return SlowScanJsonString(); | 396 return SlowScanJsonString(); |
396 } | 397 } |
397 } | 398 } |
398 ASSERT_EQ('"', c0_); | 399 ASSERT_EQ('"', c0_); |
399 end_pos_ = position_; | 400 end_pos_ = position_; |
400 // Advance past the last '"'. | 401 // Advance past the last '"'. |
401 AdvanceSkipWhitespace(); | 402 AdvanceSkipWhitespace(); |
402 if (is_sequential_ascii_ && is_symbol) { | 403 if (is_sequential_ascii_ && is_symbol) { |
403 return isolate()->factory()->LookupAsciiSymbol(seq_source_, | 404 return isolate()->factory()->LookupAsciiSymbol(seq_source_, |
404 beg_pos_, | 405 beg_pos_, |
405 end_pos_ - beg_pos_); | 406 end_pos_ - beg_pos_); |
406 } else { | 407 } else { |
407 return isolate()->factory()->NewSubString(source_, beg_pos_, end_pos_); | 408 return isolate()->factory()->NewSubString(source_, beg_pos_, end_pos_); |
408 } | 409 } |
409 } | 410 } |
410 | 411 |
411 } } // namespace v8::internal | 412 } } // namespace v8::internal |
OLD | NEW |