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/class_finalizer.h" | 9 #include "vm/class_finalizer.h" |
10 #include "vm/dart.h" | 10 #include "vm/dart.h" |
(...skipping 607 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
618 for (intptr_t i = 0; i <= num_flds; i++) { | 618 for (intptr_t i = 0; i <= num_flds; i++) { |
619 *(object_store->from() + i) = ReadObjectImpl(kAsInlinedObject); | 619 *(object_store->from() + i) = ReadObjectImpl(kAsInlinedObject); |
620 } | 620 } |
621 for (intptr_t i = 0; i < backward_references_->length(); i++) { | 621 for (intptr_t i = 0; i < backward_references_->length(); i++) { |
622 if (!(*backward_references_)[i].is_deserialized()) { | 622 if (!(*backward_references_)[i].is_deserialized()) { |
623 ReadObjectImpl(kAsInlinedObject); | 623 ReadObjectImpl(kAsInlinedObject); |
624 (*backward_references_)[i].set_state(kIsDeserialized); | 624 (*backward_references_)[i].set_state(kIsDeserialized); |
625 } | 625 } |
626 } | 626 } |
627 | 627 |
628 if (Snapshot::IncludesCode(kind_)) { | 628 if (kind_ == Snapshot::kAppNoJIT) { |
629 ICData& ic = ICData::Handle(thread->zone()); | 629 ICData& ic = ICData::Handle(thread->zone()); |
630 Object& funcOrCode = Object::Handle(thread->zone()); | 630 Object& funcOrCode = Object::Handle(thread->zone()); |
631 Code& code = Code::Handle(thread->zone()); | 631 Code& code = Code::Handle(thread->zone()); |
632 Smi& entry_point = Smi::Handle(thread->zone()); | 632 Smi& entry_point = Smi::Handle(thread->zone()); |
633 for (intptr_t i = 0; i < backward_references_->length(); i++) { | 633 for (intptr_t i = 0; i < backward_references_->length(); i++) { |
634 if ((*backward_references_)[i].reference()->IsICData()) { | 634 if ((*backward_references_)[i].reference()->IsICData()) { |
635 ic ^= (*backward_references_)[i].reference()->raw(); | 635 ic ^= (*backward_references_)[i].reference()->raw(); |
636 for (intptr_t j = 0; j < ic.NumberOfChecks(); j++) { | 636 for (intptr_t j = 0; j < ic.NumberOfChecks(); j++) { |
637 funcOrCode = ic.GetTargetOrCodeAt(j); | 637 funcOrCode = ic.GetTargetOrCodeAt(j); |
638 if (funcOrCode.IsCode()) { | 638 if (funcOrCode.IsCode()) { |
(...skipping 514 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1153 #if defined(PRODUCT) | 1153 #if defined(PRODUCT) |
1154 // Instructions are only dedup in product mode because it obfuscates profiler | 1154 // Instructions are only dedup in product mode because it obfuscates profiler |
1155 // results. | 1155 // results. |
1156 for (intptr_t i = 0; i < instructions_.length(); i++) { | 1156 for (intptr_t i = 0; i < instructions_.length(); i++) { |
1157 if (instructions_[i].raw_insns_ == instructions) { | 1157 if (instructions_[i].raw_insns_ == instructions) { |
1158 return instructions_[i].offset_; | 1158 return instructions_[i].offset_; |
1159 } | 1159 } |
1160 } | 1160 } |
1161 #endif | 1161 #endif |
1162 | 1162 |
1163 intptr_t payload_size = instructions->ptr()->size_; | 1163 intptr_t heap_size = instructions->Size(); |
1164 payload_size = Utils::RoundUp(payload_size, OS::PreferredCodeAlignment()); | |
1165 | |
1166 intptr_t offset = next_offset_; | 1164 intptr_t offset = next_offset_; |
1167 ASSERT(Utils::IsAligned(next_offset_, OS::PreferredCodeAlignment())); | 1165 next_offset_ += heap_size; |
1168 next_offset_ += payload_size; | |
1169 ASSERT(Utils::IsAligned(next_offset_, OS::PreferredCodeAlignment())); | |
1170 instructions_.Add(InstructionsData(instructions, code, offset)); | 1166 instructions_.Add(InstructionsData(instructions, code, offset)); |
1171 | 1167 |
1172 return offset; | 1168 return offset; |
1173 } | 1169 } |
1174 | 1170 |
1175 | 1171 |
1176 int32_t InstructionsWriter::GetObjectOffsetFor(RawObject* raw_object) { | 1172 int32_t InstructionsWriter::GetObjectOffsetFor(RawObject* raw_object) { |
1177 intptr_t heap_size = raw_object->Size(); | 1173 intptr_t heap_size = raw_object->Size(); |
1178 intptr_t offset = next_object_offset_; | 1174 intptr_t offset = next_object_offset_; |
1179 next_object_offset_ += heap_size; | 1175 next_object_offset_ += heap_size; |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1228 | 1224 |
1229 Object& owner = Object::Handle(zone); | 1225 Object& owner = Object::Handle(zone); |
1230 String& str = String::Handle(zone); | 1226 String& str = String::Handle(zone); |
1231 | 1227 |
1232 for (intptr_t i = 0; i < instructions_.length(); i++) { | 1228 for (intptr_t i = 0; i < instructions_.length(); i++) { |
1233 const Instructions& insns = *instructions_[i].insns_; | 1229 const Instructions& insns = *instructions_[i].insns_; |
1234 const Code& code = *instructions_[i].code_; | 1230 const Code& code = *instructions_[i].code_; |
1235 | 1231 |
1236 ASSERT(insns.raw()->Size() % sizeof(uint64_t) == 0); | 1232 ASSERT(insns.raw()->Size() % sizeof(uint64_t) == 0); |
1237 | 1233 |
1238 // 1. Write a label at the entry point. | 1234 // 1. Write from the header to the entry point. |
| 1235 { |
| 1236 NoSafepointScope no_safepoint; |
| 1237 |
| 1238 uword beginning = reinterpret_cast<uword>(insns.raw_ptr()); |
| 1239 uword entry = beginning + Instructions::HeaderSize(); |
| 1240 |
| 1241 ASSERT(Utils::IsAligned(beginning, sizeof(uint64_t))); |
| 1242 ASSERT(Utils::IsAligned(entry, sizeof(uint64_t))); |
| 1243 |
| 1244 // Write Instructions with the mark and VM heap bits set. |
| 1245 uword marked_tags = insns.raw_ptr()->tags_; |
| 1246 marked_tags = RawObject::VMHeapObjectTag::update(true, marked_tags); |
| 1247 marked_tags = RawObject::MarkBit::update(true, marked_tags); |
| 1248 |
| 1249 WriteWordLiteral(marked_tags); |
| 1250 beginning += sizeof(uword); |
| 1251 |
| 1252 for (uword* cursor = reinterpret_cast<uword*>(beginning); |
| 1253 cursor < reinterpret_cast<uword*>(entry); |
| 1254 cursor++) { |
| 1255 WriteWordLiteral(*cursor); |
| 1256 } |
| 1257 } |
| 1258 |
| 1259 // 2. Write a label at the entry point. |
1239 owner = code.owner(); | 1260 owner = code.owner(); |
1240 if (owner.IsNull()) { | 1261 if (owner.IsNull()) { |
1241 const char* name = StubCode::NameOfStub(insns.EntryPoint()); | 1262 const char* name = StubCode::NameOfStub(insns.EntryPoint()); |
1242 assembly_stream_.Print("Precompiled_Stub_%s:\n", name); | 1263 assembly_stream_.Print("Precompiled_Stub_%s:\n", name); |
1243 } else if (owner.IsClass()) { | 1264 } else if (owner.IsClass()) { |
1244 str = Class::Cast(owner).Name(); | 1265 str = Class::Cast(owner).Name(); |
1245 const char* name = str.ToCString(); | 1266 const char* name = str.ToCString(); |
1246 EnsureIdentifier(const_cast<char*>(name)); | 1267 EnsureIdentifier(const_cast<char*>(name)); |
1247 assembly_stream_.Print("Precompiled_AllocationStub_%s_%" Pd ":\n", | 1268 assembly_stream_.Print("Precompiled_AllocationStub_%s_%" Pd ":\n", |
1248 name, i); | 1269 name, i); |
1249 } else if (owner.IsFunction()) { | 1270 } else if (owner.IsFunction()) { |
1250 const char* name = Function::Cast(owner).ToQualifiedCString(); | 1271 const char* name = Function::Cast(owner).ToQualifiedCString(); |
1251 EnsureIdentifier(const_cast<char*>(name)); | 1272 EnsureIdentifier(const_cast<char*>(name)); |
1252 assembly_stream_.Print("Precompiled_%s_%" Pd ":\n", name, i); | 1273 assembly_stream_.Print("Precompiled_%s_%" Pd ":\n", name, i); |
1253 } else { | 1274 } else { |
1254 UNREACHABLE(); | 1275 UNREACHABLE(); |
1255 } | 1276 } |
1256 | 1277 |
1257 { | 1278 { |
1258 // 2. Write from the entry point to the end. | 1279 // 3. Write from the entry point to the end. |
1259 NoSafepointScope no_safepoint; | 1280 NoSafepointScope no_safepoint; |
1260 uword beginning = reinterpret_cast<uword>(insns.raw()) - kHeapObjectTag; | 1281 uword beginning = reinterpret_cast<uword>(insns.raw()) - kHeapObjectTag; |
1261 uword entry = beginning + Instructions::HeaderSize(); | 1282 uword entry = beginning + Instructions::HeaderSize(); |
1262 uword payload_size = insns.size(); | 1283 uword payload_size = insns.size(); |
1263 payload_size = Utils::RoundUp(payload_size, OS::PreferredCodeAlignment()); | 1284 payload_size = Utils::RoundUp(payload_size, OS::PreferredCodeAlignment()); |
1264 uword end = entry + payload_size; | 1285 uword end = entry + payload_size; |
1265 | 1286 |
1266 ASSERT(Utils::IsAligned(beginning, sizeof(uint64_t))); | 1287 ASSERT(Utils::IsAligned(beginning, sizeof(uint64_t))); |
1267 ASSERT(Utils::IsAligned(entry, sizeof(uint64_t))); | 1288 ASSERT(Utils::IsAligned(entry, sizeof(uint64_t))); |
1268 ASSERT(Utils::IsAligned(end, sizeof(uint64_t))); | 1289 ASSERT(Utils::IsAligned(end, sizeof(uint64_t))); |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1335 intptr_t instructions_length = next_offset_; | 1356 intptr_t instructions_length = next_offset_; |
1336 instructions_blob_stream_.WriteWord(instructions_length); | 1357 instructions_blob_stream_.WriteWord(instructions_length); |
1337 intptr_t header_words = InstructionsSnapshot::kHeaderSize / sizeof(uword); | 1358 intptr_t header_words = InstructionsSnapshot::kHeaderSize / sizeof(uword); |
1338 for (intptr_t i = 1; i < header_words; i++) { | 1359 for (intptr_t i = 1; i < header_words; i++) { |
1339 instructions_blob_stream_.WriteWord(0); | 1360 instructions_blob_stream_.WriteWord(0); |
1340 } | 1361 } |
1341 | 1362 |
1342 for (intptr_t i = 0; i < instructions_.length(); i++) { | 1363 for (intptr_t i = 0; i < instructions_.length(); i++) { |
1343 const Instructions& insns = *instructions_[i].insns_; | 1364 const Instructions& insns = *instructions_[i].insns_; |
1344 | 1365 |
| 1366 // 1. Write from the header to the entry point. |
1345 { | 1367 { |
1346 // 2. Write from the entry point to the end. | 1368 NoSafepointScope no_safepoint; |
| 1369 |
| 1370 uword beginning = reinterpret_cast<uword>(insns.raw_ptr()); |
| 1371 uword entry = beginning + Instructions::HeaderSize(); |
| 1372 |
| 1373 ASSERT(Utils::IsAligned(beginning, sizeof(uint64_t))); |
| 1374 ASSERT(Utils::IsAligned(entry, sizeof(uint64_t))); |
| 1375 |
| 1376 // Write Instructions with the mark and VM heap bits set. |
| 1377 uword marked_tags = insns.raw_ptr()->tags_; |
| 1378 marked_tags = RawObject::VMHeapObjectTag::update(true, marked_tags); |
| 1379 marked_tags = RawObject::MarkBit::update(true, marked_tags); |
| 1380 |
| 1381 instructions_blob_stream_.WriteWord(marked_tags); |
| 1382 beginning += sizeof(uword); |
| 1383 |
| 1384 for (uword* cursor = reinterpret_cast<uword*>(beginning); |
| 1385 cursor < reinterpret_cast<uword*>(entry); |
| 1386 cursor++) { |
| 1387 instructions_blob_stream_.WriteWord(*cursor); |
| 1388 } |
| 1389 } |
| 1390 |
| 1391 // 2. Write from the entry point to the end. |
| 1392 { |
1347 NoSafepointScope no_safepoint; | 1393 NoSafepointScope no_safepoint; |
1348 uword beginning = reinterpret_cast<uword>(insns.raw()) - kHeapObjectTag; | 1394 uword beginning = reinterpret_cast<uword>(insns.raw()) - kHeapObjectTag; |
1349 uword entry = beginning + Instructions::HeaderSize(); | 1395 uword entry = beginning + Instructions::HeaderSize(); |
1350 uword payload_size = insns.size(); | 1396 uword payload_size = insns.size(); |
1351 payload_size = Utils::RoundUp(payload_size, OS::PreferredCodeAlignment()); | 1397 payload_size = Utils::RoundUp(payload_size, OS::PreferredCodeAlignment()); |
1352 uword end = entry + payload_size; | 1398 uword end = entry + payload_size; |
1353 | 1399 |
1354 ASSERT(Utils::IsAligned(beginning, sizeof(uint64_t))); | 1400 ASSERT(Utils::IsAligned(beginning, sizeof(uint64_t))); |
1355 ASSERT(Utils::IsAligned(entry, sizeof(uint64_t))); | 1401 ASSERT(Utils::IsAligned(entry, sizeof(uint64_t))); |
1356 ASSERT(Utils::IsAligned(end, sizeof(uint64_t))); | 1402 ASSERT(Utils::IsAligned(end, sizeof(uint64_t))); |
(...skipping 354 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1711 const uint8_t* data_buffer, | 1757 const uint8_t* data_buffer, |
1712 Thread* thread) | 1758 Thread* thread) |
1713 : SnapshotReader(buffer, | 1759 : SnapshotReader(buffer, |
1714 size, | 1760 size, |
1715 instructions_buffer, | 1761 instructions_buffer, |
1716 data_buffer, | 1762 data_buffer, |
1717 kind, | 1763 kind, |
1718 new ZoneGrowableArray<BackRefNode>( | 1764 new ZoneGrowableArray<BackRefNode>( |
1719 kNumInitialReferencesInFullSnapshot), | 1765 kNumInitialReferencesInFullSnapshot), |
1720 thread) { | 1766 thread) { |
1721 isolate()->set_compilation_allowed(instructions_buffer_ == NULL); | 1767 isolate()->set_compilation_allowed(kind != Snapshot::kAppNoJIT); |
1722 ASSERT(Snapshot::IsFull(kind)); | 1768 ASSERT(Snapshot::IsFull(kind)); |
1723 } | 1769 } |
1724 | 1770 |
1725 | 1771 |
1726 IsolateSnapshotReader::~IsolateSnapshotReader() { | 1772 IsolateSnapshotReader::~IsolateSnapshotReader() { |
1727 ResetBackwardReferenceTable(); | 1773 ResetBackwardReferenceTable(); |
1728 } | 1774 } |
1729 | 1775 |
1730 | 1776 |
1731 ScriptSnapshotReader::ScriptSnapshotReader(const uint8_t* buffer, | 1777 ScriptSnapshotReader::ScriptSnapshotReader(const uint8_t* buffer, |
(...skipping 403 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2135 OS::Print("Instructions(CodeSize): %" Pd "\n", | 2181 OS::Print("Instructions(CodeSize): %" Pd "\n", |
2136 instructions_writer_->binary_size()); | 2182 instructions_writer_->binary_size()); |
2137 intptr_t total = VmIsolateSnapshotSize() + | 2183 intptr_t total = VmIsolateSnapshotSize() + |
2138 IsolateSnapshotSize() + | 2184 IsolateSnapshotSize() + |
2139 instructions_writer_->binary_size(); | 2185 instructions_writer_->binary_size(); |
2140 OS::Print("Total(CodeSize): %" Pd "\n", total); | 2186 OS::Print("Total(CodeSize): %" Pd "\n", total); |
2141 } | 2187 } |
2142 } | 2188 } |
2143 | 2189 |
2144 | 2190 |
2145 PrecompiledSnapshotWriter::PrecompiledSnapshotWriter( | |
2146 uint8_t** vm_isolate_snapshot_buffer, | |
2147 uint8_t** isolate_snapshot_buffer, | |
2148 ReAlloc alloc, | |
2149 InstructionsWriter* instructions_writer) | |
2150 : FullSnapshotWriter(Snapshot::kAppNoJIT, | |
2151 vm_isolate_snapshot_buffer, | |
2152 isolate_snapshot_buffer, | |
2153 alloc, | |
2154 instructions_writer, | |
2155 false /* vm_isolate_is_symbolic */) { | |
2156 } | |
2157 | |
2158 | |
2159 PrecompiledSnapshotWriter::~PrecompiledSnapshotWriter() {} | |
2160 | |
2161 | |
2162 ForwardList::ForwardList(Thread* thread, intptr_t first_object_id) | 2191 ForwardList::ForwardList(Thread* thread, intptr_t first_object_id) |
2163 : thread_(thread), | 2192 : thread_(thread), |
2164 first_object_id_(first_object_id), | 2193 first_object_id_(first_object_id), |
2165 nodes_(), | 2194 nodes_(), |
2166 first_unprocessed_object_id_(first_object_id) { | 2195 first_unprocessed_object_id_(first_object_id) { |
2167 } | 2196 } |
2168 | 2197 |
2169 | 2198 |
2170 ForwardList::~ForwardList() { | 2199 ForwardList::~ForwardList() { |
2171 heap()->ResetObjectIdTable(); | 2200 heap()->ResetObjectIdTable(); |
(...skipping 568 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2740 if (setjmp(*jump.Set()) == 0) { | 2769 if (setjmp(*jump.Set()) == 0) { |
2741 NoSafepointScope no_safepoint; | 2770 NoSafepointScope no_safepoint; |
2742 WriteObject(obj.raw()); | 2771 WriteObject(obj.raw()); |
2743 } else { | 2772 } else { |
2744 ThrowException(exception_type(), exception_msg()); | 2773 ThrowException(exception_type(), exception_msg()); |
2745 } | 2774 } |
2746 } | 2775 } |
2747 | 2776 |
2748 | 2777 |
2749 } // namespace dart | 2778 } // namespace dart |
OLD | NEW |