Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(707)

Side by Side Diff: runtime/observatory/lib/src/heap_snapshot/heap_snapshot.dart

Issue 2266343002: Converted Observatory heap-snapshot element (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Added missing explanation text Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file
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.
4
5 part of heap_snapshot;
6
7 class HeapSnapshot implements M.HeapSnapshot {
8 ObjectGraph graph;
9 DateTime timestamp;
10 int get objects => graph.vertexCount;
11 int get references => graph.edgeCount;
12 int get size => graph.size;
13 HeapSnapshotDominatorNode dominatorTree;
14 List<MergedVertex> classReferences;
15
16 static Future sleep([Duration duration = const Duration(microseconds: 0)]) {
17 final Completer completer = new Completer();
18 new Timer(duration, () => completer.complete() );
19 return completer.future;
20 }
21
22 Stream<double> loadProgress(S.Isolate isolate, S.RawHeapSnapshot raw) {
23 final progress = new StreamController<double>.broadcast();
24 progress.add(0.0);
25 graph = new ObjectGraph(raw.chunks, raw.count);
26 var signal = (double p) {
27 progress.add(p);
28 return sleep();
29 };
30 (() async {
31 timestamp = new DateTime.now();
32 await graph.process(new StreamController.broadcast());
33 dominatorTree = new HeapSnapshotDominatorNode(isolate, graph.root);
34 progress.add(0.5);
35 classReferences = await buildMergedVertices(isolate, graph, signal);
36 progress.close();
37 }());
38 return progress.stream;
39 }
40
41 Future<List<MergedVertex>> buildMergedVertices(S.Isolate isolate,
42 ObjectGraph graph,
43 signal) async {
44 final cidToMergedVertex = {};
45
46 int count = 0;
47 final Stopwatch watch = new Stopwatch();
48 watch.start();
49 var needToUpdate = () {
50 count++;
51 if (((count % 256) == 0) && (watch.elapsedMilliseconds > 16)) {
52 watch.reset();
53 return true;
54 }
55 return false;
56 };
57 final length = graph.vertices.length;
58 for (final vertex in graph.vertices) {
59 count++;
60 if (vertex.vmCid == 0) {
61 continue;
62 }
63 if (needToUpdate()) {
64 await signal(count * 100.0 / length);
65 }
66 final cid = vertex.vmCid;
67 MergedVertex source = cidToMergedVertex[cid];
68 if (source == null) {
69 cidToMergedVertex[cid] = source = new MergedVertex(isolate, cid);
70 }
71
72 source.instances++;
73 source.shallowSize += vertex.shallowSize ?? 0;
74
75 for (final vertex2 in vertex.successors) {
76 if (vertex2.vmCid == 0) {
77 continue;
78 }
79 final cid2 = vertex2.vmCid;
80 MergedEdge edge = source.outgoingEdges[cid2];
81 if (edge == null) {
82 MergedVertex target = cidToMergedVertex[cid2];
83 if (target == null) {
84 cidToMergedVertex[cid2] = target = new MergedVertex(isolate, cid2);
85 }
86 edge = new MergedEdge(source, target);
87 source.outgoingEdges[cid2] = edge;
88 target.incomingEdges.add(edge);
89 }
90 edge.count++;
91 // An over-estimate if there are multiple references to the same object.
92 edge.shallowSize += vertex2.shallowSize ?? 0;
93 }
94 }
95 return cidToMergedVertex.values.toList();
96 }
97
98 List<Future<S.ServiceObject>> getMostRetained(S.Isolate isolate,
99 {int classId, int limit}) {
100 var result = [];
101 for (ObjectVertex v in graph.getMostRetained(classId: classId,
102 limit: limit)) {
103 result.add(isolate.getObjectByAddress(v.address)
104 .then((S.ServiceObject obj) {
105 if (obj is S.HeapObject) {
106 obj.retainedSize = v.retainedSize;
107 } else {
108 print("${obj.runtimeType} should be a HeapObject");
109 }
110 return obj;
111 }));
112 }
113 return result;
114 }
115 }
116
117 class HeapSnapshotDominatorNode implements M.HeapSnapshotDominatorNode {
118 final ObjectVertex v;
119 final S.Isolate isolate;
120 S.HeapObject _preloaded;
121
122 Future<S.HeapObject> get object {
123 if (_preloaded != null) {
124 return new Future.value(_preloaded);
125 } else {
126 return isolate.getObjectByAddress(v.address).then((S.HeapObject obj) {
127 return _preloaded = obj;
128 });
129 }
130 }
131 Iterable<HeapSnapshotDominatorNode> _children;
132 Iterable<HeapSnapshotDominatorNode> get children {
133 if (_children != null) {
134 return _children;
135 } else {
136 return _children = new List.unmodifiable(
137 v.dominatorTreeChildren().map((v) {
138 return new HeapSnapshotDominatorNode(isolate, v);
139 })
140 );
141 }
142 }
143 int get retainedSize => v.retainedSize;
144 int get shallowSize => v.shallowSize;
145
146 HeapSnapshotDominatorNode(S.Isolate isolate, ObjectVertex vertex)
147 : isolate = isolate,
148 v = vertex;
149 }
150
151 class MergedEdge {
152 final MergedVertex sourceVertex;
153 final MergedVertex targetVertex;
154 int count = 0;
155 int shallowSize = 0;
156 int retainedSize = 0;
157
158 MergedEdge(this.sourceVertex, this.targetVertex);
159 }
160
161 class MergedVertex implements M.HeapSnapshotClassReferences {
162 final int cid;
163 final S.Isolate isolate;
164 S.Class get clazz => isolate.getClassByCid(cid);
165 int instances = 0;
166 int shallowSize = 0;
167 int retainedSize = 0;
168
169 List<MergedEdge> incomingEdges = new List<MergedEdge>();
170 Map<int, MergedEdge> outgoingEdges = new Map<int, MergedEdge>();
171
172 Iterable<HeapSnapshotClassInbound> _inbounds;
173 Iterable<HeapSnapshotClassInbound> get inbounds {
174 if (_inbounds != null) {
175 return _inbounds;
176 } else {
177 return _inbounds = new List.unmodifiable(
178 incomingEdges.map((edge) {
179 return new HeapSnapshotClassInbound(this, edge);
180 })
181 );
182 }
183 }
184
185 Iterable<HeapSnapshotClassOutbound> _outbounds;
186 Iterable<HeapSnapshotClassOutbound> get outbounds {
187 if (_outbounds != null) {
188 return _outbounds;
189 } else {
190 return _outbounds = new List.unmodifiable(
191 outgoingEdges.values.map((edge) {
192 return new HeapSnapshotClassInbound(this, edge);
193 })
194 );
195 }
196 }
197
198 MergedVertex(this.isolate, this.cid);
199 }
200
201 class HeapSnapshotClassInbound implements M.HeapSnapshotClassInbound {
202 final MergedVertex vertex;
203 final MergedEdge edge;
204 S.Class get source => edge.sourceVertex != vertex ? edge.sourceVertex.clazz
205 : edge.targetVertex.clazz;
206 int get count => edge.count;
207 int get shallowSize => edge.shallowSize;
208 int get retainedSize => edge.retainedSize;
209
210 HeapSnapshotClassInbound(this.vertex, this.edge);
211 }
212
213 class HeapSnapshotClassOutbound implements M.HeapSnapshotClassOutbound {
214 final MergedVertex vertex;
215 final MergedEdge edge;
216 S.Class get target => edge.sourceVertex != vertex ? edge.sourceVertex.clazz
217 : edge.targetVertex.clazz;
218 int get count => edge.count;
219 int get shallowSize => edge.shallowSize;
220 int get retainedSize => edge.retainedSize;
221
222 HeapSnapshotClassOutbound(this.vertex, this.edge);
223 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698