summaryrefslogtreecommitdiffstats
path: root/chromium/v8/src/heap-profiler.cc
diff options
context:
space:
mode:
Diffstat (limited to 'chromium/v8/src/heap-profiler.cc')
-rw-r--r--chromium/v8/src/heap-profiler.cc134
1 files changed, 81 insertions, 53 deletions
diff --git a/chromium/v8/src/heap-profiler.cc b/chromium/v8/src/heap-profiler.cc
index 3d8e3364c90..e576d3b23e9 100644
--- a/chromium/v8/src/heap-profiler.cc
+++ b/chromium/v8/src/heap-profiler.cc
@@ -1,55 +1,45 @@
// Copyright 2009-2010 the V8 project authors. All rights reserved.
-// Redistribution and use in source and binary forms, with or without
-// modification, are permitted provided that the following conditions are
-// met:
-//
-// * Redistributions of source code must retain the above copyright
-// notice, this list of conditions and the following disclaimer.
-// * Redistributions in binary form must reproduce the above
-// copyright notice, this list of conditions and the following
-// disclaimer in the documentation and/or other materials provided
-// with the distribution.
-// * Neither the name of Google Inc. nor the names of its
-// contributors may be used to endorse or promote products derived
-// from this software without specific prior written permission.
-//
-// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-
-#include "v8.h"
-
-#include "heap-profiler.h"
-#include "heap-snapshot-generator-inl.h"
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "src/v8.h"
+
+#include "src/heap-profiler.h"
+
+#include "src/allocation-tracker.h"
+#include "src/heap-snapshot-generator-inl.h"
namespace v8 {
namespace internal {
HeapProfiler::HeapProfiler(Heap* heap)
- : snapshots_(new HeapSnapshotsCollection(heap)),
+ : ids_(new HeapObjectsMap(heap)),
+ names_(new StringsStorage(heap)),
next_snapshot_uid_(1),
- is_tracking_allocations_(false),
is_tracking_object_moves_(false) {
}
+static void DeleteHeapSnapshot(HeapSnapshot** snapshot_ptr) {
+ delete *snapshot_ptr;
+}
+
+
HeapProfiler::~HeapProfiler() {
- delete snapshots_;
+ snapshots_.Iterate(DeleteHeapSnapshot);
+ snapshots_.Clear();
}
void HeapProfiler::DeleteAllSnapshots() {
- Heap* the_heap = heap();
- delete snapshots_;
- snapshots_ = new HeapSnapshotsCollection(the_heap);
+ snapshots_.Iterate(DeleteHeapSnapshot);
+ snapshots_.Clear();
+ names_.Reset(new StringsStorage(heap()));
+}
+
+
+void HeapProfiler::RemoveSnapshot(HeapSnapshot* snapshot) {
+ snapshots_.RemoveElement(snapshot);
}
@@ -76,15 +66,17 @@ HeapSnapshot* HeapProfiler::TakeSnapshot(
const char* name,
v8::ActivityControl* control,
v8::HeapProfiler::ObjectNameResolver* resolver) {
- HeapSnapshot* result = snapshots_->NewSnapshot(name, next_snapshot_uid_++);
+ HeapSnapshot* result = new HeapSnapshot(this, name, next_snapshot_uid_++);
{
HeapSnapshotGenerator generator(result, control, resolver, heap());
if (!generator.GenerateSnapshot()) {
delete result;
result = NULL;
+ } else {
+ snapshots_.Add(result);
}
}
- snapshots_->SnapshotGenerationFinished(result);
+ ids_->RemoveDeadEntries();
is_tracking_object_moves_ = true;
return result;
}
@@ -94,69 +86,82 @@ HeapSnapshot* HeapProfiler::TakeSnapshot(
String* name,
v8::ActivityControl* control,
v8::HeapProfiler::ObjectNameResolver* resolver) {
- return TakeSnapshot(snapshots_->names()->GetName(name), control, resolver);
+ return TakeSnapshot(names_->GetName(name), control, resolver);
}
void HeapProfiler::StartHeapObjectsTracking(bool track_allocations) {
- snapshots_->StartHeapObjectsTracking(track_allocations);
+ ids_->UpdateHeapObjectsMap();
is_tracking_object_moves_ = true;
- ASSERT(!is_tracking_allocations_);
+ ASSERT(!is_tracking_allocations());
if (track_allocations) {
+ allocation_tracker_.Reset(new AllocationTracker(ids_.get(), names_.get()));
heap()->DisableInlineAllocation();
- is_tracking_allocations_ = true;
}
}
SnapshotObjectId HeapProfiler::PushHeapObjectsStats(OutputStream* stream) {
- return snapshots_->PushHeapObjectsStats(stream);
+ return ids_->PushHeapObjectsStats(stream);
}
void HeapProfiler::StopHeapObjectsTracking() {
- snapshots_->StopHeapObjectsTracking();
- if (is_tracking_allocations_) {
+ ids_->StopHeapObjectsTracking();
+ if (is_tracking_allocations()) {
+ allocation_tracker_.Reset(NULL);
heap()->EnableInlineAllocation();
- is_tracking_allocations_ = false;
}
}
size_t HeapProfiler::GetMemorySizeUsedByProfiler() {
- return snapshots_->GetUsedMemorySize();
+ size_t size = sizeof(*this);
+ size += names_->GetUsedMemorySize();
+ size += ids_->GetUsedMemorySize();
+ size += GetMemoryUsedByList(snapshots_);
+ for (int i = 0; i < snapshots_.length(); ++i) {
+ size += snapshots_[i]->RawSnapshotSize();
+ }
+ return size;
}
int HeapProfiler::GetSnapshotsCount() {
- return snapshots_->snapshots()->length();
+ return snapshots_.length();
}
HeapSnapshot* HeapProfiler::GetSnapshot(int index) {
- return snapshots_->snapshots()->at(index);
+ return snapshots_.at(index);
}
SnapshotObjectId HeapProfiler::GetSnapshotObjectId(Handle<Object> obj) {
if (!obj->IsHeapObject())
return v8::HeapProfiler::kUnknownObjectId;
- return snapshots_->FindObjectId(HeapObject::cast(*obj)->address());
+ return ids_->FindEntry(HeapObject::cast(*obj)->address());
}
void HeapProfiler::ObjectMoveEvent(Address from, Address to, int size) {
- snapshots_->ObjectMoveEvent(from, to, size);
+ bool known_object = ids_->MoveObject(from, to, size);
+ if (!known_object && !allocation_tracker_.is_empty()) {
+ allocation_tracker_->address_to_trace()->MoveObject(from, to, size);
+ }
}
void HeapProfiler::AllocationEvent(Address addr, int size) {
- snapshots_->AllocationEvent(addr, size);
+ DisallowHeapAllocation no_allocation;
+ if (!allocation_tracker_.is_empty()) {
+ allocation_tracker_->AllocationEvent(addr, size);
+ }
}
void HeapProfiler::UpdateObjectSizeEvent(Address addr, int size) {
- snapshots_->UpdateObjectSizeEvent(addr, size);
+ ids_->UpdateObjectSize(addr, size);
}
@@ -167,4 +172,27 @@ void HeapProfiler::SetRetainedObjectInfo(UniqueId id,
}
+Handle<HeapObject> HeapProfiler::FindHeapObjectById(SnapshotObjectId id) {
+ HeapObject* object = NULL;
+ HeapIterator iterator(heap(), HeapIterator::kFilterUnreachable);
+ // Make sure that object with the given id is still reachable.
+ for (HeapObject* obj = iterator.next();
+ obj != NULL;
+ obj = iterator.next()) {
+ if (ids_->FindEntry(obj->address()) == id) {
+ ASSERT(object == NULL);
+ object = obj;
+ // Can't break -- kFilterUnreachable requires full heap traversal.
+ }
+ }
+ return object != NULL ? Handle<HeapObject>(object) : Handle<HeapObject>();
+}
+
+
+void HeapProfiler::ClearHeapObjectMap() {
+ ids_.Reset(new HeapObjectsMap(heap()));
+ if (!is_tracking_allocations()) is_tracking_object_moves_ = false;
+}
+
+
} } // namespace v8::internal