| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/snapshot.h" | 5 #include "vm/snapshot.h" |
| 6 | 6 |
| 7 #include "platform/assert.h" | 7 #include "platform/assert.h" |
| 8 #include "vm/bootstrap.h" | 8 #include "vm/bootstrap.h" |
| 9 #include "vm/exceptions.h" | 9 #include "vm/exceptions.h" |
| 10 #include "vm/heap.h" | 10 #include "vm/heap.h" |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 48 ASSERT(kLengthIndex == length_offset()); | 48 ASSERT(kLengthIndex == length_offset()); |
| 49 ASSERT((kSnapshotFlagIndex * sizeof(int32_t)) == kind_offset()); | 49 ASSERT((kSnapshotFlagIndex * sizeof(int32_t)) == kind_offset()); |
| 50 ASSERT((kHeapObjectTag & kInlined)); | 50 ASSERT((kHeapObjectTag & kInlined)); |
| 51 ASSERT((kHeapObjectTag & kObjectId)); | 51 ASSERT((kHeapObjectTag & kObjectId)); |
| 52 ASSERT((kObjectAlignmentMask & kObjectId) == kObjectId); | 52 ASSERT((kObjectAlignmentMask & kObjectId) == kObjectId); |
| 53 const Snapshot* snapshot = reinterpret_cast<const Snapshot*>(raw_memory); | 53 const Snapshot* snapshot = reinterpret_cast<const Snapshot*>(raw_memory); |
| 54 return snapshot; | 54 return snapshot; |
| 55 } | 55 } |
| 56 | 56 |
| 57 | 57 |
| 58 RawSmi* BaseReader::ReadAsSmi() { |
| 59 intptr_t value = ReadIntptrValue(); |
| 60 ASSERT((value & kSmiTagMask) == 0); |
| 61 return reinterpret_cast<RawSmi*>(value); |
| 62 } |
| 63 |
| 64 |
| 65 intptr_t BaseReader::ReadSmiValue() { |
| 66 return Smi::Value(ReadAsSmi()); |
| 67 } |
| 68 |
| 69 |
| 58 SnapshotReader::SnapshotReader(const Snapshot* snapshot, Isolate* isolate) | 70 SnapshotReader::SnapshotReader(const Snapshot* snapshot, Isolate* isolate) |
| 59 : stream_(snapshot->content(), snapshot->length()), | 71 : BaseReader(snapshot->content(), snapshot->length()), |
| 60 kind_(snapshot->kind()), | 72 kind_(snapshot->kind()), |
| 61 isolate_(isolate), | 73 isolate_(isolate), |
| 62 cls_(Class::Handle()), | 74 cls_(Class::Handle()), |
| 63 obj_(Object::Handle()), | 75 obj_(Object::Handle()), |
| 64 str_(String::Handle()), | 76 str_(String::Handle()), |
| 65 library_(Library::Handle()), | 77 library_(Library::Handle()), |
| 66 type_(AbstractType::Handle()), | 78 type_(AbstractType::Handle()), |
| 67 type_arguments_(AbstractTypeArguments::Handle()), | 79 type_arguments_(AbstractTypeArguments::Handle()), |
| 68 backward_references_((snapshot->kind() == Snapshot::kFull) ? | 80 backward_references_((snapshot->kind() == Snapshot::kFull) ? |
| 69 kNumInitialReferencesInFullSnapshot : | 81 kNumInitialReferencesInFullSnapshot : |
| (...skipping 348 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 418 #undef SNAPSHOT_READ | 430 #undef SNAPSHOT_READ |
| 419 default: UNREACHABLE(); break; | 431 default: UNREACHABLE(); break; |
| 420 } | 432 } |
| 421 if (kind_ == Snapshot::kFull) { | 433 if (kind_ == Snapshot::kFull) { |
| 422 obj_.SetCreatedFromSnapshot(); | 434 obj_.SetCreatedFromSnapshot(); |
| 423 } | 435 } |
| 424 return obj_.raw(); | 436 return obj_.raw(); |
| 425 } | 437 } |
| 426 | 438 |
| 427 | 439 |
| 440 CMessageReader::CMessageReader(const uint8_t* buffer, |
| 441 intptr_t length, |
| 442 ReAlloc alloc) |
| 443 : BaseReader(buffer, length), alloc_(alloc) { |
| 444 } |
| 445 |
| 446 |
| 447 intptr_t CMessageReader::LookupInternalClass(intptr_t class_header) { |
| 448 SerializedHeaderType header_type = SerializedHeaderTag::decode(class_header); |
| 449 ASSERT(header_type == kObjectId); |
| 450 intptr_t header_value = SerializedHeaderData::decode(class_header); |
| 451 return header_value; |
| 452 } |
| 453 |
| 454 |
| 455 Dart_CObject* CMessageReader::AllocateDartValue(Dart_CObject::Type type) { |
| 456 Dart_CObject* value = |
| 457 reinterpret_cast<Dart_CObject*>( |
| 458 alloc_(NULL, 0, sizeof(Dart_CObject))); |
| 459 value->type = type; |
| 460 return value; |
| 461 } |
| 462 |
| 463 |
| 464 Dart_CObject* CMessageReader::AllocateDartValueNull() { |
| 465 return AllocateDartValue(Dart_CObject::kNull); |
| 466 } |
| 467 |
| 468 |
| 469 Dart_CObject* CMessageReader::AllocateDartValueBool(bool val) { |
| 470 Dart_CObject* value = AllocateDartValue(Dart_CObject::kBool); |
| 471 value->value.as_bool = val; |
| 472 return value; |
| 473 } |
| 474 |
| 475 |
| 476 Dart_CObject* CMessageReader::AllocateDartValueInt32(int32_t val) { |
| 477 Dart_CObject* value = AllocateDartValue(Dart_CObject::kInt32); |
| 478 value->value.as_int32 = val; |
| 479 return value; |
| 480 } |
| 481 |
| 482 |
| 483 Dart_CObject* CMessageReader::AllocateDartValueDouble(double val) { |
| 484 Dart_CObject* value = AllocateDartValue(Dart_CObject::kDouble); |
| 485 value->value.as_double = val; |
| 486 return value; |
| 487 } |
| 488 |
| 489 |
| 490 Dart_CObject* CMessageReader::AllocateDartValueString(intptr_t length) { |
| 491 // Allocate a Dart_CObject structure followed by an array of chars |
| 492 // for the string content. The pointer to the string content is set |
| 493 // up to this area. |
| 494 Dart_CObject* value = |
| 495 reinterpret_cast<Dart_CObject*>( |
| 496 alloc_(NULL, 0, sizeof(Dart_CObject) + length + 1)); |
| 497 value->value.as_string = reinterpret_cast<char*>(value) + sizeof(*value); |
| 498 value->type = Dart_CObject::kString; |
| 499 return value; |
| 500 } |
| 501 |
| 502 |
| 503 Dart_CObject* CMessageReader::AllocateDartValueArray(intptr_t length) { |
| 504 // Allocate a Dart_CObject structure followed by an array of |
| 505 // pointers to Dart_CObject structures. The pointer to the array |
| 506 // content is set up to this area. |
| 507 Dart_CObject* value = |
| 508 reinterpret_cast<Dart_CObject*>( |
| 509 alloc_(NULL, 0, sizeof(Dart_CObject) + length * sizeof(value))); |
| 510 value->type = Dart_CObject::kArray; |
| 511 value->value.as_array.length = length; |
| 512 if (length > 0) { |
| 513 value->value.as_array.values = reinterpret_cast<Dart_CObject**>(value + 1); |
| 514 } else { |
| 515 value->value.as_array.values = NULL; |
| 516 } |
| 517 return value; |
| 518 } |
| 519 |
| 520 |
| 521 Dart_CObject* CMessageReader::ReadInlinedObject(intptr_t object_id) { |
| 522 // Read the class header information and lookup the class. |
| 523 intptr_t class_header = ReadIntptrValue(); |
| 524 intptr_t tags = ReadIntptrValue(); |
| 525 USE(tags); |
| 526 intptr_t class_id; |
| 527 |
| 528 // Reading of regular dart instances is not supported. |
| 529 if (SerializedHeaderData::decode(class_header) == kInstanceId) { |
| 530 return NULL; |
| 531 } |
| 532 |
| 533 ASSERT((class_header & kSmiTagMask) != 0); |
| 534 class_id = LookupInternalClass(class_header); |
| 535 switch (class_id) { |
| 536 case Object::kClassClass: { |
| 537 return NULL; |
| 538 } |
| 539 case ObjectStore::kArrayClass: { |
| 540 intptr_t len = ReadSmiValue(); |
| 541 // Skip type arguments. |
| 542 Dart_CObject* type_arguments = ReadObject(); |
| 543 if (type_arguments == NULL || |
| 544 type_arguments->type != Dart_CObject::kNull) { |
| 545 return NULL; |
| 546 } |
| 547 Dart_CObject* value = AllocateDartValueArray(len); |
| 548 for (int i = 0; i < len; i++) { |
| 549 value->value.as_array.values[i] = ReadObject(); |
| 550 } |
| 551 return value; |
| 552 break; |
| 553 } |
| 554 case ObjectStore::kDoubleClass: { |
| 555 // Read the double value for the object. |
| 556 return AllocateDartValueDouble(Read<double>()); |
| 557 break; |
| 558 } |
| 559 case ObjectStore::kOneByteStringClass: { |
| 560 intptr_t len = ReadSmiValue(); |
| 561 intptr_t hash = ReadSmiValue(); |
| 562 USE(hash); |
| 563 Dart_CObject* value = AllocateDartValueString(len); |
| 564 char* p = value->value.as_string; |
| 565 for (intptr_t i = 0; i < len; i++) { |
| 566 *p = Read<uint8_t>(); |
| 567 p++; |
| 568 } |
| 569 *p = '\0'; |
| 570 return value; |
| 571 break; |
| 572 } |
| 573 case ObjectStore::kTwoByteStringClass: |
| 574 // Two byte strings not supported. |
| 575 return NULL; |
| 576 break; |
| 577 case ObjectStore::kFourByteStringClass: |
| 578 // Four byte strings not supported. |
| 579 return NULL; |
| 580 break; |
| 581 default: |
| 582 // Everything else not supported. |
| 583 return NULL; |
| 584 } |
| 585 } |
| 586 |
| 587 |
| 588 Dart_CObject* CMessageReader::ReadIndexedObject(intptr_t object_id) { |
| 589 if (object_id == Object::kNullObject) { |
| 590 return AllocateDartValueNull(); |
| 591 } else if (object_id == ObjectStore::kTrueValue) { |
| 592 return AllocateDartValueBool(true); |
| 593 } else if (object_id == ObjectStore::kFalseValue) { |
| 594 return AllocateDartValueBool(false); |
| 595 } else { |
| 596 // TODO(sgjesse): Handle back-references. |
| 597 UNREACHABLE(); |
| 598 } |
| 599 return NULL; |
| 600 } |
| 601 |
| 602 |
| 603 Dart_CObject* CMessageReader::ReadObjectImpl(intptr_t header) { |
| 604 SerializedHeaderType header_type = SerializedHeaderTag::decode(header); |
| 605 intptr_t header_value = SerializedHeaderData::decode(header); |
| 606 |
| 607 if (header_type == kObjectId) { |
| 608 return ReadIndexedObject(header_value); |
| 609 } |
| 610 ASSERT(header_type == kInlined); |
| 611 return ReadInlinedObject(header_value); |
| 612 } |
| 613 |
| 614 |
| 615 Dart_CObject* CMessageReader::ReadObject() { |
| 616 int64_t value = Read<int64_t>(); |
| 617 if ((value & kSmiTagMask) == 0) { |
| 618 Dart_CObject* dart_value = AllocateDartValueInt32(value >> kSmiTagShift); |
| 619 return dart_value; |
| 620 } |
| 621 ASSERT((value <= kIntptrMax) && (value >= kIntptrMin)); |
| 622 return ReadObjectImpl(value); |
| 623 } |
| 624 |
| 625 |
| 428 void MessageWriter::WriteMessage(intptr_t field_count, intptr_t *data) { | 626 void MessageWriter::WriteMessage(intptr_t field_count, intptr_t *data) { |
| 429 // Write out the serialization header value for this object. | 627 // Write out the serialization header value for this object. |
| 430 WriteSerializationMarker(kInlined, kMaxPredefinedObjectIds); | 628 WriteSerializationMarker(kInlined, kMaxPredefinedObjectIds); |
| 431 | 629 |
| 432 // Write out the class and tags information. | 630 // Write out the class and tags information. |
| 433 WriteObjectHeader(ObjectStore::kArrayClass, 0); | 631 WriteObjectHeader(ObjectStore::kArrayClass, 0); |
| 434 | 632 |
| 435 // Write out the length field. | 633 // Write out the length field. |
| 436 Write<RawObject*>(Smi::New(field_count)); | 634 Write<RawObject*>(Smi::New(field_count)); |
| 437 | 635 |
| (...skipping 212 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 650 | 848 |
| 651 | 849 |
| 652 void SnapshotWriterVisitor::VisitPointers(RawObject** first, RawObject** last) { | 850 void SnapshotWriterVisitor::VisitPointers(RawObject** first, RawObject** last) { |
| 653 for (RawObject** current = first; current <= last; current++) { | 851 for (RawObject** current = first; current <= last; current++) { |
| 654 RawObject* raw_obj = *current; | 852 RawObject* raw_obj = *current; |
| 655 writer_->WriteObject(raw_obj); | 853 writer_->WriteObject(raw_obj); |
| 656 } | 854 } |
| 657 } | 855 } |
| 658 | 856 |
| 659 } // namespace dart | 857 } // namespace dart |
| OLD | NEW |