| OLD | NEW |
| 1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 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 #include "src/profiler/heap-snapshot-generator.h" | 5 #include "src/profiler/heap-snapshot-generator.h" |
| 6 | 6 |
| 7 #include "src/code-stubs.h" | 7 #include "src/code-stubs.h" |
| 8 #include "src/conversions.h" | 8 #include "src/conversions.h" |
| 9 #include "src/debug/debug.h" | 9 #include "src/debug/debug.h" |
| 10 #include "src/objects-body-descriptors.h" | 10 #include "src/objects-body-descriptors.h" |
| (...skipping 2594 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2605 } | 2605 } |
| 2606 | 2606 |
| 2607 | 2607 |
| 2608 bool HeapSnapshotGenerator::FillReferences() { | 2608 bool HeapSnapshotGenerator::FillReferences() { |
| 2609 SnapshotFiller filler(snapshot_, &entries_); | 2609 SnapshotFiller filler(snapshot_, &entries_); |
| 2610 return v8_heap_explorer_.IterateAndExtractReferences(&filler) | 2610 return v8_heap_explorer_.IterateAndExtractReferences(&filler) |
| 2611 && dom_explorer_.IterateAndExtractReferences(&filler); | 2611 && dom_explorer_.IterateAndExtractReferences(&filler); |
| 2612 } | 2612 } |
| 2613 | 2613 |
| 2614 | 2614 |
| 2615 template<int bytes> struct MaxDecimalDigitsIn; | |
| 2616 template<> struct MaxDecimalDigitsIn<4> { | |
| 2617 static const int kSigned = 11; | |
| 2618 static const int kUnsigned = 10; | |
| 2619 }; | |
| 2620 template<> struct MaxDecimalDigitsIn<8> { | |
| 2621 static const int kSigned = 20; | |
| 2622 static const int kUnsigned = 20; | |
| 2623 }; | |
| 2624 | |
| 2625 | |
| 2626 class OutputStreamWriter { | |
| 2627 public: | |
| 2628 explicit OutputStreamWriter(v8::OutputStream* stream) | |
| 2629 : stream_(stream), | |
| 2630 chunk_size_(stream->GetChunkSize()), | |
| 2631 chunk_(chunk_size_), | |
| 2632 chunk_pos_(0), | |
| 2633 aborted_(false) { | |
| 2634 DCHECK(chunk_size_ > 0); | |
| 2635 } | |
| 2636 bool aborted() { return aborted_; } | |
| 2637 void AddCharacter(char c) { | |
| 2638 DCHECK(c != '\0'); | |
| 2639 DCHECK(chunk_pos_ < chunk_size_); | |
| 2640 chunk_[chunk_pos_++] = c; | |
| 2641 MaybeWriteChunk(); | |
| 2642 } | |
| 2643 void AddString(const char* s) { | |
| 2644 AddSubstring(s, StrLength(s)); | |
| 2645 } | |
| 2646 void AddSubstring(const char* s, int n) { | |
| 2647 if (n <= 0) return; | |
| 2648 DCHECK(static_cast<size_t>(n) <= strlen(s)); | |
| 2649 const char* s_end = s + n; | |
| 2650 while (s < s_end) { | |
| 2651 int s_chunk_size = | |
| 2652 Min(chunk_size_ - chunk_pos_, static_cast<int>(s_end - s)); | |
| 2653 DCHECK(s_chunk_size > 0); | |
| 2654 MemCopy(chunk_.start() + chunk_pos_, s, s_chunk_size); | |
| 2655 s += s_chunk_size; | |
| 2656 chunk_pos_ += s_chunk_size; | |
| 2657 MaybeWriteChunk(); | |
| 2658 } | |
| 2659 } | |
| 2660 void AddNumber(unsigned n) { AddNumberImpl<unsigned>(n, "%u"); } | |
| 2661 void Finalize() { | |
| 2662 if (aborted_) return; | |
| 2663 DCHECK(chunk_pos_ < chunk_size_); | |
| 2664 if (chunk_pos_ != 0) { | |
| 2665 WriteChunk(); | |
| 2666 } | |
| 2667 stream_->EndOfStream(); | |
| 2668 } | |
| 2669 | |
| 2670 private: | |
| 2671 template<typename T> | |
| 2672 void AddNumberImpl(T n, const char* format) { | |
| 2673 // Buffer for the longest value plus trailing \0 | |
| 2674 static const int kMaxNumberSize = | |
| 2675 MaxDecimalDigitsIn<sizeof(T)>::kUnsigned + 1; | |
| 2676 if (chunk_size_ - chunk_pos_ >= kMaxNumberSize) { | |
| 2677 int result = SNPrintF( | |
| 2678 chunk_.SubVector(chunk_pos_, chunk_size_), format, n); | |
| 2679 DCHECK(result != -1); | |
| 2680 chunk_pos_ += result; | |
| 2681 MaybeWriteChunk(); | |
| 2682 } else { | |
| 2683 EmbeddedVector<char, kMaxNumberSize> buffer; | |
| 2684 int result = SNPrintF(buffer, format, n); | |
| 2685 USE(result); | |
| 2686 DCHECK(result != -1); | |
| 2687 AddString(buffer.start()); | |
| 2688 } | |
| 2689 } | |
| 2690 void MaybeWriteChunk() { | |
| 2691 DCHECK(chunk_pos_ <= chunk_size_); | |
| 2692 if (chunk_pos_ == chunk_size_) { | |
| 2693 WriteChunk(); | |
| 2694 } | |
| 2695 } | |
| 2696 void WriteChunk() { | |
| 2697 if (aborted_) return; | |
| 2698 if (stream_->WriteAsciiChunk(chunk_.start(), chunk_pos_) == | |
| 2699 v8::OutputStream::kAbort) aborted_ = true; | |
| 2700 chunk_pos_ = 0; | |
| 2701 } | |
| 2702 | |
| 2703 v8::OutputStream* stream_; | |
| 2704 int chunk_size_; | |
| 2705 ScopedVector<char> chunk_; | |
| 2706 int chunk_pos_; | |
| 2707 bool aborted_; | |
| 2708 }; | |
| 2709 | |
| 2710 | |
| 2711 // type, name|index, to_node. | 2615 // type, name|index, to_node. |
| 2712 const int HeapSnapshotJSONSerializer::kEdgeFieldsCount = 3; | 2616 const int HeapSnapshotJSONSerializer::kEdgeFieldsCount = 3; |
| 2713 // type, name, id, self_size, edge_count, trace_node_id. | 2617 // type, name, id, self_size, edge_count, trace_node_id. |
| 2714 const int HeapSnapshotJSONSerializer::kNodeFieldsCount = 6; | 2618 const int HeapSnapshotJSONSerializer::kNodeFieldsCount = 6; |
| 2715 | 2619 |
| 2716 void HeapSnapshotJSONSerializer::Serialize(v8::OutputStream* stream) { | 2620 void HeapSnapshotJSONSerializer::Serialize(v8::OutputStream* stream) { |
| 2717 if (AllocationTracker* allocation_tracker = | 2621 if (AllocationTracker* allocation_tracker = |
| 2718 snapshot_->profiler()->allocation_tracker()) { | 2622 snapshot_->profiler()->allocation_tracker()) { |
| 2719 allocation_tracker->PrepareForSerialization(); | 2623 allocation_tracker->PrepareForSerialization(); |
| 2720 } | 2624 } |
| (...skipping 440 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3161 for (int i = 1; i < sorted_strings.length(); ++i) { | 3065 for (int i = 1; i < sorted_strings.length(); ++i) { |
| 3162 writer_->AddCharacter(','); | 3066 writer_->AddCharacter(','); |
| 3163 SerializeString(sorted_strings[i]); | 3067 SerializeString(sorted_strings[i]); |
| 3164 if (writer_->aborted()) return; | 3068 if (writer_->aborted()) return; |
| 3165 } | 3069 } |
| 3166 } | 3070 } |
| 3167 | 3071 |
| 3168 | 3072 |
| 3169 } // namespace internal | 3073 } // namespace internal |
| 3170 } // namespace v8 | 3074 } // namespace v8 |
| OLD | NEW |