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

Side by Side Diff: runtime/vm/timeline_analysis.cc

Issue 2974233002: VM: Re-format to use at most one newline between functions (Closed)
Patch Set: Rebase and merge Created 3 years, 5 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
« no previous file with comments | « runtime/vm/timeline_analysis.h ('k') | runtime/vm/timeline_test.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2015, 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/timeline_analysis.h" 5 #include "vm/timeline_analysis.h"
6 6
7 #include "vm/flags.h" 7 #include "vm/flags.h"
8 #include "vm/isolate.h" 8 #include "vm/isolate.h"
9 #include "vm/log.h" 9 #include "vm/log.h"
10 #include "vm/os_thread.h" 10 #include "vm/os_thread.h"
11 11
12 namespace dart { 12 namespace dart {
13 13
14 #ifndef PRODUCT 14 #ifndef PRODUCT
15 15
16 DECLARE_FLAG(bool, trace_timeline_analysis); 16 DECLARE_FLAG(bool, trace_timeline_analysis);
17 DECLARE_FLAG(bool, timing); 17 DECLARE_FLAG(bool, timing);
18 18
19 TimelineAnalysisThread::TimelineAnalysisThread(ThreadId id) : id_(id) {} 19 TimelineAnalysisThread::TimelineAnalysisThread(ThreadId id) : id_(id) {}
20 20
21
22 TimelineAnalysisThread::~TimelineAnalysisThread() {} 21 TimelineAnalysisThread::~TimelineAnalysisThread() {}
23 22
24
25 void TimelineAnalysisThread::AddBlock(TimelineEventBlock* block) { 23 void TimelineAnalysisThread::AddBlock(TimelineEventBlock* block) {
26 blocks_.Add(block); 24 blocks_.Add(block);
27 } 25 }
28 26
29
30 static int CompareBlocksLowerTimeBound(TimelineEventBlock* const* a, 27 static int CompareBlocksLowerTimeBound(TimelineEventBlock* const* a,
31 TimelineEventBlock* const* b) { 28 TimelineEventBlock* const* b) {
32 ASSERT(a != NULL); 29 ASSERT(a != NULL);
33 ASSERT(*a != NULL); 30 ASSERT(*a != NULL);
34 ASSERT(b != NULL); 31 ASSERT(b != NULL);
35 ASSERT(*b != NULL); 32 ASSERT(*b != NULL);
36 return (*a)->LowerTimeBound() - (*b)->LowerTimeBound(); 33 return (*a)->LowerTimeBound() - (*b)->LowerTimeBound();
37 } 34 }
38 35
39
40 void TimelineAnalysisThread::Finalize() { 36 void TimelineAnalysisThread::Finalize() {
41 blocks_.Sort(CompareBlocksLowerTimeBound); 37 blocks_.Sort(CompareBlocksLowerTimeBound);
42 if (FLAG_trace_timeline_analysis) { 38 if (FLAG_trace_timeline_analysis) {
43 THR_Print("Thread %" Px " has %" Pd " blocks\n", 39 THR_Print("Thread %" Px " has %" Pd " blocks\n",
44 OSThread::ThreadIdToIntPtr(id_), blocks_.length()); 40 OSThread::ThreadIdToIntPtr(id_), blocks_.length());
45 } 41 }
46 } 42 }
47 43
48
49 TimelineAnalysisThreadEventIterator::TimelineAnalysisThreadEventIterator( 44 TimelineAnalysisThreadEventIterator::TimelineAnalysisThreadEventIterator(
50 TimelineAnalysisThread* thread) { 45 TimelineAnalysisThread* thread) {
51 Reset(thread); 46 Reset(thread);
52 } 47 }
53 48
54
55 TimelineAnalysisThreadEventIterator::~TimelineAnalysisThreadEventIterator() { 49 TimelineAnalysisThreadEventIterator::~TimelineAnalysisThreadEventIterator() {
56 Reset(NULL); 50 Reset(NULL);
57 } 51 }
58 52
59
60 void TimelineAnalysisThreadEventIterator::Reset( 53 void TimelineAnalysisThreadEventIterator::Reset(
61 TimelineAnalysisThread* thread) { 54 TimelineAnalysisThread* thread) {
62 current_ = NULL; 55 current_ = NULL;
63 thread_ = thread; 56 thread_ = thread;
64 block_cursor_ = 0; 57 block_cursor_ = 0;
65 event_cursor_ = 0; 58 event_cursor_ = 0;
66 if (thread_ == NULL) { 59 if (thread_ == NULL) {
67 return; 60 return;
68 } 61 }
69 if (thread_->NumBlocks() == 0) { 62 if (thread_->NumBlocks() == 0) {
70 return; 63 return;
71 } 64 }
72 TimelineEventBlock* block = thread_->At(block_cursor_); 65 TimelineEventBlock* block = thread_->At(block_cursor_);
73 ASSERT(!block->IsEmpty()); 66 ASSERT(!block->IsEmpty());
74 current_ = block->At(event_cursor_++); 67 current_ = block->At(event_cursor_++);
75 } 68 }
76 69
77
78 bool TimelineAnalysisThreadEventIterator::HasNext() const { 70 bool TimelineAnalysisThreadEventIterator::HasNext() const {
79 return current_ != NULL; 71 return current_ != NULL;
80 } 72 }
81 73
82
83 TimelineEvent* TimelineAnalysisThreadEventIterator::Next() { 74 TimelineEvent* TimelineAnalysisThreadEventIterator::Next() {
84 ASSERT(current_ != NULL); 75 ASSERT(current_ != NULL);
85 TimelineEvent* r = current_; 76 TimelineEvent* r = current_;
86 current_ = NULL; 77 current_ = NULL;
87 78
88 TimelineEventBlock* block = thread_->At(block_cursor_); 79 TimelineEventBlock* block = thread_->At(block_cursor_);
89 if (event_cursor_ == block->length()) { 80 if (event_cursor_ == block->length()) {
90 // Reached the end of this block, move to the next. 81 // Reached the end of this block, move to the next.
91 block_cursor_++; 82 block_cursor_++;
92 if (block_cursor_ == thread_->NumBlocks()) { 83 if (block_cursor_ == thread_->NumBlocks()) {
93 // Exhausted our supply of blocks. 84 // Exhausted our supply of blocks.
94 return r; 85 return r;
95 } 86 }
96 // Grab next block. 87 // Grab next block.
97 block = thread_->At(block_cursor_); 88 block = thread_->At(block_cursor_);
98 event_cursor_ = 0; 89 event_cursor_ = 0;
99 ASSERT(!block->IsEmpty()); 90 ASSERT(!block->IsEmpty());
100 } 91 }
101 current_ = block->At(event_cursor_++); 92 current_ = block->At(event_cursor_++);
102 return r; 93 return r;
103 } 94 }
104 95
105
106 TimelineAnalysis::TimelineAnalysis(Zone* zone, 96 TimelineAnalysis::TimelineAnalysis(Zone* zone,
107 Isolate* isolate, 97 Isolate* isolate,
108 TimelineEventRecorder* recorder) 98 TimelineEventRecorder* recorder)
109 : zone_(zone), 99 : zone_(zone),
110 isolate_(isolate), 100 isolate_(isolate),
111 recorder_(recorder), 101 recorder_(recorder),
112 has_error_(false), 102 has_error_(false),
113 error_msg_(NULL) { 103 error_msg_(NULL) {
114 ASSERT(zone_ != NULL); 104 ASSERT(zone_ != NULL);
115 ASSERT(isolate_ != NULL); 105 ASSERT(isolate_ != NULL);
116 ASSERT(recorder_ != NULL); 106 ASSERT(recorder_ != NULL);
117 } 107 }
118 108
119
120 TimelineAnalysis::~TimelineAnalysis() {} 109 TimelineAnalysis::~TimelineAnalysis() {}
121 110
122
123 void TimelineAnalysis::BuildThreads() { 111 void TimelineAnalysis::BuildThreads() {
124 DiscoverThreads(); 112 DiscoverThreads();
125 FinalizeThreads(); 113 FinalizeThreads();
126 } 114 }
127 115
128
129 TimelineAnalysisThread* TimelineAnalysis::GetThread(ThreadId tid) { 116 TimelineAnalysisThread* TimelineAnalysis::GetThread(ThreadId tid) {
130 // Linear lookup because we expect N (# of threads in an isolate) to be small. 117 // Linear lookup because we expect N (# of threads in an isolate) to be small.
131 for (intptr_t i = 0; i < threads_.length(); i++) { 118 for (intptr_t i = 0; i < threads_.length(); i++) {
132 TimelineAnalysisThread* thread = threads_.At(i); 119 TimelineAnalysisThread* thread = threads_.At(i);
133 ASSERT(thread != NULL); 120 ASSERT(thread != NULL);
134 if (thread->id() == tid) { 121 if (thread->id() == tid) {
135 return thread; 122 return thread;
136 } 123 }
137 } 124 }
138 return NULL; 125 return NULL;
139 } 126 }
140 127
141
142 TimelineAnalysisThread* TimelineAnalysis::GetOrAddThread(ThreadId tid) { 128 TimelineAnalysisThread* TimelineAnalysis::GetOrAddThread(ThreadId tid) {
143 TimelineAnalysisThread* thread = GetThread(tid); 129 TimelineAnalysisThread* thread = GetThread(tid);
144 if (thread != NULL) { 130 if (thread != NULL) {
145 return thread; 131 return thread;
146 } 132 }
147 // New thread. 133 // New thread.
148 thread = new TimelineAnalysisThread(tid); 134 thread = new TimelineAnalysisThread(tid);
149 threads_.Add(thread); 135 threads_.Add(thread);
150 return thread; 136 return thread;
151 } 137 }
152 138
153
154 void TimelineAnalysis::DiscoverThreads() { 139 void TimelineAnalysis::DiscoverThreads() {
155 TimelineEventBlockIterator it(recorder_); 140 TimelineEventBlockIterator it(recorder_);
156 while (it.HasNext()) { 141 while (it.HasNext()) {
157 TimelineEventBlock* block = it.Next(); 142 TimelineEventBlock* block = it.Next();
158 ASSERT(block != NULL); 143 ASSERT(block != NULL);
159 if (block->IsEmpty()) { 144 if (block->IsEmpty()) {
160 // Skip empty blocks. 145 // Skip empty blocks.
161 continue; 146 continue;
162 } 147 }
163 if (!block->CheckBlock()) { 148 if (!block->CheckBlock()) {
164 if (FLAG_trace_timeline_analysis) { 149 if (FLAG_trace_timeline_analysis) {
165 THR_Print("DiscoverThreads block %" Pd 150 THR_Print("DiscoverThreads block %" Pd
166 " " 151 " "
167 "violates invariants.\n", 152 "violates invariants.\n",
168 block->block_index()); 153 block->block_index());
169 } 154 }
170 SetError("Block %" Pd 155 SetError("Block %" Pd
171 " violates invariants. See " 156 " violates invariants. See "
172 "TimelineEventBlock::CheckBlock", 157 "TimelineEventBlock::CheckBlock",
173 block->block_index()); 158 block->block_index());
174 return; 159 return;
175 } 160 }
176 TimelineAnalysisThread* thread = GetOrAddThread(block->thread_id()); 161 TimelineAnalysisThread* thread = GetOrAddThread(block->thread_id());
177 ASSERT(thread != NULL); 162 ASSERT(thread != NULL);
178 thread->AddBlock(block); 163 thread->AddBlock(block);
179 } 164 }
180 } 165 }
181 166
182
183 void TimelineAnalysis::FinalizeThreads() { 167 void TimelineAnalysis::FinalizeThreads() {
184 for (intptr_t i = 0; i < threads_.length(); i++) { 168 for (intptr_t i = 0; i < threads_.length(); i++) {
185 TimelineAnalysisThread* thread = threads_.At(i); 169 TimelineAnalysisThread* thread = threads_.At(i);
186 ASSERT(thread != NULL); 170 ASSERT(thread != NULL);
187 thread->Finalize(); 171 thread->Finalize();
188 } 172 }
189 } 173 }
190 174
191
192 void TimelineAnalysis::SetError(const char* format, ...) { 175 void TimelineAnalysis::SetError(const char* format, ...) {
193 ASSERT(!has_error_); 176 ASSERT(!has_error_);
194 ASSERT(error_msg_ == NULL); 177 ASSERT(error_msg_ == NULL);
195 has_error_ = true; 178 has_error_ = true;
196 va_list args; 179 va_list args;
197 va_start(args, format); 180 va_start(args, format);
198 error_msg_ = zone_->VPrint(format, args); 181 error_msg_ = zone_->VPrint(format, args);
199 ASSERT(error_msg_ != NULL); 182 ASSERT(error_msg_ != NULL);
200 if (FLAG_trace_timeline_analysis) { 183 if (FLAG_trace_timeline_analysis) {
201 OS::Print("TimelineAnalysis error = %s\n", error_msg_); 184 OS::Print("TimelineAnalysis error = %s\n", error_msg_);
202 } 185 }
203 } 186 }
204 187
205
206 TimelineLabelPauseInfo::TimelineLabelPauseInfo(const char* name) 188 TimelineLabelPauseInfo::TimelineLabelPauseInfo(const char* name)
207 : name_(name), 189 : name_(name),
208 inclusive_micros_(0), 190 inclusive_micros_(0),
209 exclusive_micros_(0), 191 exclusive_micros_(0),
210 max_inclusive_micros_(0), 192 max_inclusive_micros_(0),
211 max_exclusive_micros_(0) { 193 max_exclusive_micros_(0) {
212 ASSERT(name_ != NULL); 194 ASSERT(name_ != NULL);
213 } 195 }
214 196
215
216 void TimelineLabelPauseInfo::OnPush(int64_t micros, bool already_on_stack) { 197 void TimelineLabelPauseInfo::OnPush(int64_t micros, bool already_on_stack) {
217 UpdateInclusiveMicros(micros, already_on_stack); 198 UpdateInclusiveMicros(micros, already_on_stack);
218 } 199 }
219 200
220
221 void TimelineLabelPauseInfo::OnPop(int64_t exclusive_micros) { 201 void TimelineLabelPauseInfo::OnPop(int64_t exclusive_micros) {
222 UpdateExclusiveMicros(exclusive_micros); 202 UpdateExclusiveMicros(exclusive_micros);
223 } 203 }
224 204
225
226 void TimelineLabelPauseInfo::OnBeginPop(int64_t inclusive_micros, 205 void TimelineLabelPauseInfo::OnBeginPop(int64_t inclusive_micros,
227 int64_t exclusive_micros, 206 int64_t exclusive_micros,
228 bool already_on_stack) { 207 bool already_on_stack) {
229 UpdateInclusiveMicros(inclusive_micros, already_on_stack); 208 UpdateInclusiveMicros(inclusive_micros, already_on_stack);
230 UpdateExclusiveMicros(exclusive_micros); 209 UpdateExclusiveMicros(exclusive_micros);
231 } 210 }
232 211
233
234 void TimelineLabelPauseInfo::UpdateInclusiveMicros(int64_t inclusive_micros, 212 void TimelineLabelPauseInfo::UpdateInclusiveMicros(int64_t inclusive_micros,
235 bool already_on_stack) { 213 bool already_on_stack) {
236 if (!already_on_stack) { 214 if (!already_on_stack) {
237 // Only adjust inclusive counts if we aren't already on the stack. 215 // Only adjust inclusive counts if we aren't already on the stack.
238 add_inclusive_micros(inclusive_micros); 216 add_inclusive_micros(inclusive_micros);
239 if (inclusive_micros > max_inclusive_micros_) { 217 if (inclusive_micros > max_inclusive_micros_) {
240 max_inclusive_micros_ = inclusive_micros; 218 max_inclusive_micros_ = inclusive_micros;
241 } 219 }
242 } 220 }
243 } 221 }
244 222
245
246 void TimelineLabelPauseInfo::UpdateExclusiveMicros(int64_t exclusive_micros) { 223 void TimelineLabelPauseInfo::UpdateExclusiveMicros(int64_t exclusive_micros) {
247 add_exclusive_micros(exclusive_micros); 224 add_exclusive_micros(exclusive_micros);
248 if (exclusive_micros > max_exclusive_micros_) { 225 if (exclusive_micros > max_exclusive_micros_) {
249 max_exclusive_micros_ = exclusive_micros; 226 max_exclusive_micros_ = exclusive_micros;
250 } 227 }
251 } 228 }
252 229
253
254 void TimelineLabelPauseInfo::Aggregate( 230 void TimelineLabelPauseInfo::Aggregate(
255 const TimelineLabelPauseInfo* thread_pause_info) { 231 const TimelineLabelPauseInfo* thread_pause_info) {
256 ASSERT(thread_pause_info != NULL); 232 ASSERT(thread_pause_info != NULL);
257 inclusive_micros_ += thread_pause_info->inclusive_micros_; 233 inclusive_micros_ += thread_pause_info->inclusive_micros_;
258 exclusive_micros_ += thread_pause_info->exclusive_micros_; 234 exclusive_micros_ += thread_pause_info->exclusive_micros_;
259 if (max_inclusive_micros_ < thread_pause_info->max_inclusive_micros_) { 235 if (max_inclusive_micros_ < thread_pause_info->max_inclusive_micros_) {
260 max_inclusive_micros_ = thread_pause_info->max_inclusive_micros_; 236 max_inclusive_micros_ = thread_pause_info->max_inclusive_micros_;
261 } 237 }
262 if (max_exclusive_micros_ < thread_pause_info->max_exclusive_micros_) { 238 if (max_exclusive_micros_ < thread_pause_info->max_exclusive_micros_) {
263 max_exclusive_micros_ = thread_pause_info->max_exclusive_micros_; 239 max_exclusive_micros_ = thread_pause_info->max_exclusive_micros_;
264 } 240 }
265 } 241 }
266 242
267
268 TimelinePauses::TimelinePauses(Zone* zone, 243 TimelinePauses::TimelinePauses(Zone* zone,
269 Isolate* isolate, 244 Isolate* isolate,
270 TimelineEventRecorder* recorder) 245 TimelineEventRecorder* recorder)
271 : TimelineAnalysis(zone, isolate, recorder) {} 246 : TimelineAnalysis(zone, isolate, recorder) {}
272 247
273
274 void TimelinePauses::Setup() { 248 void TimelinePauses::Setup() {
275 BuildThreads(); 249 BuildThreads();
276 } 250 }
277 251
278
279 void TimelinePauses::CalculatePauseTimesForThread(ThreadId tid) { 252 void TimelinePauses::CalculatePauseTimesForThread(ThreadId tid) {
280 if (has_error()) { 253 if (has_error()) {
281 return; 254 return;
282 } 255 }
283 TimelineAnalysisThread* thread = GetThread(tid); 256 TimelineAnalysisThread* thread = GetThread(tid);
284 if (thread == NULL) { 257 if (thread == NULL) {
285 SetError("Thread %" Px " does not exist.", OSThread::ThreadIdToIntPtr(tid)); 258 SetError("Thread %" Px " does not exist.", OSThread::ThreadIdToIntPtr(tid));
286 return; 259 return;
287 } 260 }
288 ProcessThread(thread); 261 ProcessThread(thread);
289 } 262 }
290 263
291
292 TimelineLabelPauseInfo* TimelinePauses::GetLabelPauseInfo( 264 TimelineLabelPauseInfo* TimelinePauses::GetLabelPauseInfo(
293 const char* name) const { 265 const char* name) const {
294 ASSERT(name != NULL); 266 ASSERT(name != NULL);
295 // Linear lookup because we expect N (# of labels in an isolate) to be small. 267 // Linear lookup because we expect N (# of labels in an isolate) to be small.
296 for (intptr_t i = 0; i < labels_.length(); i++) { 268 for (intptr_t i = 0; i < labels_.length(); i++) {
297 TimelineLabelPauseInfo* label = labels_.At(i); 269 TimelineLabelPauseInfo* label = labels_.At(i);
298 if (strcmp(label->name(), name) == 0) { 270 if (strcmp(label->name(), name) == 0) {
299 return label; 271 return label;
300 } 272 }
301 } 273 }
302 return NULL; 274 return NULL;
303 } 275 }
304 276
305
306 int64_t TimelinePauses::InclusiveTime(const char* name) const { 277 int64_t TimelinePauses::InclusiveTime(const char* name) const {
307 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name); 278 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name);
308 ASSERT(pause_info != NULL); 279 ASSERT(pause_info != NULL);
309 return pause_info->inclusive_micros(); 280 return pause_info->inclusive_micros();
310 } 281 }
311 282
312
313 int64_t TimelinePauses::ExclusiveTime(const char* name) const { 283 int64_t TimelinePauses::ExclusiveTime(const char* name) const {
314 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name); 284 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name);
315 ASSERT(pause_info != NULL); 285 ASSERT(pause_info != NULL);
316 return pause_info->exclusive_micros(); 286 return pause_info->exclusive_micros();
317 } 287 }
318 288
319
320 int64_t TimelinePauses::MaxInclusiveTime(const char* name) const { 289 int64_t TimelinePauses::MaxInclusiveTime(const char* name) const {
321 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name); 290 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name);
322 ASSERT(pause_info != NULL); 291 ASSERT(pause_info != NULL);
323 return pause_info->max_inclusive_micros(); 292 return pause_info->max_inclusive_micros();
324 } 293 }
325 294
326
327 int64_t TimelinePauses::MaxExclusiveTime(const char* name) const { 295 int64_t TimelinePauses::MaxExclusiveTime(const char* name) const {
328 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name); 296 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name);
329 ASSERT(pause_info != NULL); 297 ASSERT(pause_info != NULL);
330 return pause_info->max_exclusive_micros(); 298 return pause_info->max_exclusive_micros();
331 } 299 }
332 300
333
334 void TimelinePauses::ProcessThread(TimelineAnalysisThread* thread) { 301 void TimelinePauses::ProcessThread(TimelineAnalysisThread* thread) {
335 ASSERT(thread != NULL); 302 ASSERT(thread != NULL);
336 stack_.Clear(); 303 stack_.Clear();
337 labels_.Clear(); 304 labels_.Clear();
338 305
339 TimelineAnalysisThreadEventIterator it(thread); 306 TimelineAnalysisThreadEventIterator it(thread);
340 if (FLAG_trace_timeline_analysis) { 307 if (FLAG_trace_timeline_analysis) {
341 THR_Print(">>> TimelinePauses::ProcessThread %" Px "\n", 308 THR_Print(">>> TimelinePauses::ProcessThread %" Px "\n",
342 OSThread::ThreadIdToIntPtr(thread->id())); 309 OSThread::ThreadIdToIntPtr(thread->id()));
343 } 310 }
(...skipping 28 matching lines...) Expand all
372 } 339 }
373 } 340 }
374 // Pop remaining duration stack. 341 // Pop remaining duration stack.
375 PopFinishedDurations(kMaxInt64); 342 PopFinishedDurations(kMaxInt64);
376 if (FLAG_trace_timeline_analysis) { 343 if (FLAG_trace_timeline_analysis) {
377 THR_Print("<<< TimelinePauses::ProcessThread %" Px " had %" Pd " events\n", 344 THR_Print("<<< TimelinePauses::ProcessThread %" Px " had %" Pd " events\n",
378 OSThread::ThreadIdToIntPtr(thread->id()), event_count); 345 OSThread::ThreadIdToIntPtr(thread->id()), event_count);
379 } 346 }
380 } 347 }
381 348
382
383 // Verify that |event| is contained within all parent events on the stack. 349 // Verify that |event| is contained within all parent events on the stack.
384 bool TimelinePauses::CheckStack(TimelineEvent* event) { 350 bool TimelinePauses::CheckStack(TimelineEvent* event) {
385 ASSERT(event != NULL); 351 ASSERT(event != NULL);
386 for (intptr_t i = 0; i < stack_.length(); i++) { 352 for (intptr_t i = 0; i < stack_.length(); i++) {
387 const StackItem& slot = stack_.At(i); 353 const StackItem& slot = stack_.At(i);
388 if (slot.event->IsDuration()) { 354 if (slot.event->IsDuration()) {
389 if (!slot.event->DurationContains(event)) { 355 if (!slot.event->DurationContains(event)) {
390 return false; 356 return false;
391 } 357 }
392 } else { 358 } else {
393 ASSERT(slot.event->IsBegin()); 359 ASSERT(slot.event->IsBegin());
394 if (slot.event->TimeOrigin() > event->TimeOrigin()) { 360 if (slot.event->TimeOrigin() > event->TimeOrigin()) {
395 return false; 361 return false;
396 } 362 }
397 } 363 }
398 } 364 }
399 return true; 365 return true;
400 } 366 }
401 367
402
403 void TimelinePauses::PopFinishedDurations(int64_t start) { 368 void TimelinePauses::PopFinishedDurations(int64_t start) {
404 while (stack_.length() > 0) { 369 while (stack_.length() > 0) {
405 const StackItem& top = stack_.Last(); 370 const StackItem& top = stack_.Last();
406 if (top.event->IsDuration() && top.event->DurationFinishedBefore(start)) { 371 if (top.event->IsDuration() && top.event->DurationFinishedBefore(start)) {
407 top.pause_info->OnPop(top.exclusive_micros); 372 top.pause_info->OnPop(top.exclusive_micros);
408 // Top of stack completes before |start|. 373 // Top of stack completes before |start|.
409 stack_.RemoveLast(); 374 stack_.RemoveLast();
410 if (FLAG_trace_timeline_analysis) { 375 if (FLAG_trace_timeline_analysis) {
411 THR_Print("Popping %s (%" Pd64 " <= %" Pd64 ")\n", top.event->label(), 376 THR_Print("Popping %s (%" Pd64 " <= %" Pd64 ")\n", top.event->label(),
412 top.event->TimeEnd(), start); 377 top.event->TimeEnd(), start);
413 } 378 }
414 } else { 379 } else {
415 return; 380 return;
416 } 381 }
417 } 382 }
418 } 383 }
419 384
420
421 void TimelinePauses::PopBegin(const char* label, int64_t end) { 385 void TimelinePauses::PopBegin(const char* label, int64_t end) {
422 if (stack_.length() == 0) { 386 if (stack_.length() == 0) {
423 SetError("PopBegin(%s, ...) called with empty stack.", label); 387 SetError("PopBegin(%s, ...) called with empty stack.", label);
424 return; 388 return;
425 } 389 }
426 ASSERT(stack_.length() > 0); 390 ASSERT(stack_.length() > 0);
427 const StackItem& top = stack_.Last(); 391 const StackItem& top = stack_.Last();
428 const char* top_label = top.event->label(); 392 const char* top_label = top.event->label();
429 const bool top_is_begin = top.event->IsBegin(); 393 const bool top_is_begin = top.event->IsBegin();
430 const int64_t start = top.event->TimeOrigin(); 394 const int64_t start = top.event->TimeOrigin();
(...skipping 22 matching lines...) Expand all
453 stack_.RemoveLast(); 417 stack_.RemoveLast();
454 top.pause_info->OnBeginPop(duration, exclusive_micros, 418 top.pause_info->OnBeginPop(duration, exclusive_micros,
455 IsLabelOnStack(top_label)); 419 IsLabelOnStack(top_label));
456 if (StackDepth() > 0) { 420 if (StackDepth() > 0) {
457 StackItem& top = GetStackTop(); 421 StackItem& top = GetStackTop();
458 // |top| is under the popped |event|'s shadow, adjust the exclusive micros. 422 // |top| is under the popped |event|'s shadow, adjust the exclusive micros.
459 top.exclusive_micros -= duration; 423 top.exclusive_micros -= duration;
460 } 424 }
461 } 425 }
462 426
463
464 void TimelinePauses::Push(TimelineEvent* event) { 427 void TimelinePauses::Push(TimelineEvent* event) {
465 TimelineLabelPauseInfo* pause_info = GetOrAddLabelPauseInfo(event->label()); 428 TimelineLabelPauseInfo* pause_info = GetOrAddLabelPauseInfo(event->label());
466 ASSERT(pause_info != NULL); 429 ASSERT(pause_info != NULL);
467 // |pause_info| will be running for |event->TimeDuration()|. 430 // |pause_info| will be running for |event->TimeDuration()|.
468 if (FLAG_trace_timeline_analysis) { 431 if (FLAG_trace_timeline_analysis) {
469 THR_Print("Pushing %s %" Pd64 " us\n", pause_info->name(), 432 THR_Print("Pushing %s %" Pd64 " us\n", pause_info->name(),
470 event->TimeDuration()); 433 event->TimeDuration());
471 } 434 }
472 if (event->IsDuration()) { 435 if (event->IsDuration()) {
473 pause_info->OnPush(event->TimeDuration(), IsLabelOnStack(event->label())); 436 pause_info->OnPush(event->TimeDuration(), IsLabelOnStack(event->label()));
(...skipping 13 matching lines...) Expand all
487 pause_info->OnPush(0, IsLabelOnStack(event->label())); 450 pause_info->OnPush(0, IsLabelOnStack(event->label()));
488 // Push onto the stack. 451 // Push onto the stack.
489 StackItem item; 452 StackItem item;
490 item.event = event; 453 item.event = event;
491 item.pause_info = pause_info; 454 item.pause_info = pause_info;
492 item.exclusive_micros = 0; 455 item.exclusive_micros = 0;
493 stack_.Add(item); 456 stack_.Add(item);
494 } 457 }
495 } 458 }
496 459
497
498 bool TimelinePauses::IsLabelOnStack(const char* label) const { 460 bool TimelinePauses::IsLabelOnStack(const char* label) const {
499 ASSERT(label != NULL); 461 ASSERT(label != NULL);
500 for (intptr_t i = 0; i < stack_.length(); i++) { 462 for (intptr_t i = 0; i < stack_.length(); i++) {
501 const StackItem& slot = stack_.At(i); 463 const StackItem& slot = stack_.At(i);
502 if (strcmp(slot.event->label(), label) == 0) { 464 if (strcmp(slot.event->label(), label) == 0) {
503 return true; 465 return true;
504 } 466 }
505 } 467 }
506 return false; 468 return false;
507 } 469 }
508 470
509
510 intptr_t TimelinePauses::StackDepth() const { 471 intptr_t TimelinePauses::StackDepth() const {
511 return stack_.length(); 472 return stack_.length();
512 } 473 }
513 474
514
515 TimelinePauses::StackItem& TimelinePauses::GetStackTop() { 475 TimelinePauses::StackItem& TimelinePauses::GetStackTop() {
516 ASSERT(stack_.length() > 0); 476 ASSERT(stack_.length() > 0);
517 return stack_.Last(); 477 return stack_.Last();
518 } 478 }
519 479
520
521 TimelineLabelPauseInfo* TimelinePauses::GetOrAddLabelPauseInfo( 480 TimelineLabelPauseInfo* TimelinePauses::GetOrAddLabelPauseInfo(
522 const char* name) { 481 const char* name) {
523 ASSERT(name != NULL); 482 ASSERT(name != NULL);
524 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name); 483 TimelineLabelPauseInfo* pause_info = GetLabelPauseInfo(name);
525 if (pause_info != NULL) { 484 if (pause_info != NULL) {
526 return pause_info; 485 return pause_info;
527 } 486 }
528 // New label. 487 // New label.
529 pause_info = new TimelineLabelPauseInfo(name); 488 pause_info = new TimelineLabelPauseInfo(name);
530 labels_.Add(pause_info); 489 labels_.Add(pause_info);
531 return pause_info; 490 return pause_info;
532 } 491 }
533 492
534
535 TimelinePauseTrace::TimelinePauseTrace() {} 493 TimelinePauseTrace::TimelinePauseTrace() {}
536 494
537
538 TimelinePauseTrace::~TimelinePauseTrace() {} 495 TimelinePauseTrace::~TimelinePauseTrace() {}
539 496
540
541 void TimelinePauseTrace::Print() { 497 void TimelinePauseTrace::Print() {
542 Thread* thread = Thread::Current(); 498 Thread* thread = Thread::Current();
543 ASSERT(thread != NULL); 499 ASSERT(thread != NULL);
544 Isolate* isolate = thread->isolate(); 500 Isolate* isolate = thread->isolate();
545 ASSERT(isolate != NULL); 501 ASSERT(isolate != NULL);
546 Zone* zone = thread->zone(); 502 Zone* zone = thread->zone();
547 ASSERT(zone != NULL); 503 ASSERT(zone != NULL);
548 TimelineEventRecorder* recorder = Timeline::recorder(); 504 TimelineEventRecorder* recorder = Timeline::recorder();
549 ASSERT(recorder != NULL); 505 ASSERT(recorder != NULL);
550 TimelinePauses pauses(zone, isolate, recorder); 506 TimelinePauses pauses(zone, isolate, recorder);
(...skipping 18 matching lines...) Expand all
569 } 525 }
570 THR_Print("Totals:\n"); 526 THR_Print("Totals:\n");
571 for (intptr_t i = 0; i < isolate_labels_.length(); i++) { 527 for (intptr_t i = 0; i < isolate_labels_.length(); i++) {
572 TimelineLabelPauseInfo* pause_info = isolate_labels_.At(i); 528 TimelineLabelPauseInfo* pause_info = isolate_labels_.At(i);
573 ASSERT(pause_info != NULL); 529 ASSERT(pause_info != NULL);
574 PrintPauseInfo(pause_info); 530 PrintPauseInfo(pause_info);
575 } 531 }
576 THR_Print("\n"); 532 THR_Print("\n");
577 } 533 }
578 534
579
580 TimelineLabelPauseInfo* TimelinePauseTrace::GetOrAddLabelPauseInfo( 535 TimelineLabelPauseInfo* TimelinePauseTrace::GetOrAddLabelPauseInfo(
581 const char* name) { 536 const char* name) {
582 ASSERT(name != NULL); 537 ASSERT(name != NULL);
583 // Linear lookup because we expect N (# of labels in an isolate) to be small. 538 // Linear lookup because we expect N (# of labels in an isolate) to be small.
584 for (intptr_t i = 0; i < isolate_labels_.length(); i++) { 539 for (intptr_t i = 0; i < isolate_labels_.length(); i++) {
585 TimelineLabelPauseInfo* label = isolate_labels_.At(i); 540 TimelineLabelPauseInfo* label = isolate_labels_.At(i);
586 if (strcmp(label->name(), name) == 0) { 541 if (strcmp(label->name(), name) == 0) {
587 return label; 542 return label;
588 } 543 }
589 } 544 }
590 // New label. 545 // New label.
591 TimelineLabelPauseInfo* pause_info = new TimelineLabelPauseInfo(name); 546 TimelineLabelPauseInfo* pause_info = new TimelineLabelPauseInfo(name);
592 isolate_labels_.Add(pause_info); 547 isolate_labels_.Add(pause_info);
593 return pause_info; 548 return pause_info;
594 } 549 }
595 550
596
597 void TimelinePauseTrace::Aggregate( 551 void TimelinePauseTrace::Aggregate(
598 const TimelineLabelPauseInfo* thread_pause_info) { 552 const TimelineLabelPauseInfo* thread_pause_info) {
599 ASSERT(thread_pause_info != NULL); 553 ASSERT(thread_pause_info != NULL);
600 TimelineLabelPauseInfo* isolate_pause_info = 554 TimelineLabelPauseInfo* isolate_pause_info =
601 GetOrAddLabelPauseInfo(thread_pause_info->name()); 555 GetOrAddLabelPauseInfo(thread_pause_info->name());
602 ASSERT(isolate_pause_info != NULL); 556 ASSERT(isolate_pause_info != NULL);
603 isolate_pause_info->Aggregate(thread_pause_info); 557 isolate_pause_info->Aggregate(thread_pause_info);
604 } 558 }
605 559
606
607 void TimelinePauseTrace::PrintPauseInfo( 560 void TimelinePauseTrace::PrintPauseInfo(
608 const TimelineLabelPauseInfo* pause_info) { 561 const TimelineLabelPauseInfo* pause_info) {
609 ASSERT(pause_info != NULL); 562 ASSERT(pause_info != NULL);
610 THR_Print("%s : ", pause_info->name()); 563 THR_Print("%s : ", pause_info->name());
611 THR_Print("%.3f ms total on stack; ", 564 THR_Print("%.3f ms total on stack; ",
612 MicrosecondsToMilliseconds(pause_info->inclusive_micros())); 565 MicrosecondsToMilliseconds(pause_info->inclusive_micros()));
613 THR_Print("%.3f ms total executing; ", 566 THR_Print("%.3f ms total executing; ",
614 MicrosecondsToMilliseconds(pause_info->exclusive_micros())); 567 MicrosecondsToMilliseconds(pause_info->exclusive_micros()));
615 THR_Print("%.3f ms max on stack; ", 568 THR_Print("%.3f ms max on stack; ",
616 MicrosecondsToMilliseconds(pause_info->max_inclusive_micros())); 569 MicrosecondsToMilliseconds(pause_info->max_inclusive_micros()));
617 THR_Print("%.3f ms max executing.\n", 570 THR_Print("%.3f ms max executing.\n",
618 MicrosecondsToMilliseconds(pause_info->max_exclusive_micros())); 571 MicrosecondsToMilliseconds(pause_info->max_exclusive_micros()));
619 } 572 }
620 573
621 #endif // !PRODUCT 574 #endif // !PRODUCT
622 575
623 } // namespace dart 576 } // namespace dart
OLDNEW
« no previous file with comments | « runtime/vm/timeline_analysis.h ('k') | runtime/vm/timeline_test.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698