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

Side by Side Diff: runtime/vm/timeline.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.h ('k') | runtime/vm/timeline_analysis.h » ('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 "platform/globals.h" 5 #include "platform/globals.h"
6 #ifndef PRODUCT 6 #ifndef PRODUCT
7 7
8 #include <errno.h> 8 #include <errno.h>
9 #include <fcntl.h> 9 #include <fcntl.h>
10 #include <cstdlib> 10 #include <cstdlib>
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after
93 // cached block is being operated on. 93 // cached block is being operated on.
94 // - |Thread::thread_list_lock_| This lock is held when iterating over 94 // - |Thread::thread_list_lock_| This lock is held when iterating over
95 // |Thread|s. 95 // |Thread|s.
96 // 96 //
97 // Locks must always be taken in the following order: 97 // Locks must always be taken in the following order:
98 // |Thread::thread_list_lock_| 98 // |Thread::thread_list_lock_|
99 // |Thread::timeline_block_lock_| 99 // |Thread::timeline_block_lock_|
100 // |TimelineEventRecorder::lock_| 100 // |TimelineEventRecorder::lock_|
101 // 101 //
102 102
103
104 static TimelineEventRecorder* CreateTimelineRecorder() { 103 static TimelineEventRecorder* CreateTimelineRecorder() {
105 // Some flags require that we use the endless recorder. 104 // Some flags require that we use the endless recorder.
106 const bool use_endless_recorder = 105 const bool use_endless_recorder =
107 (FLAG_timeline_dir != NULL) || FLAG_timing || FLAG_complete_timeline; 106 (FLAG_timeline_dir != NULL) || FLAG_timing || FLAG_complete_timeline;
108 107
109 const bool use_startup_recorder = FLAG_startup_timeline; 108 const bool use_startup_recorder = FLAG_startup_timeline;
110 const bool use_systrace_recorder = FLAG_systrace_timeline; 109 const bool use_systrace_recorder = FLAG_systrace_timeline;
111 110
112 const char* flag = FLAG_timeline_recorder; 111 const char* flag = FLAG_timeline_recorder;
113 112
(...skipping 29 matching lines...) Expand all
143 } 142 }
144 143
145 if (FLAG_trace_timeline) { 144 if (FLAG_trace_timeline) {
146 THR_Print("Using the ring timeline recorder.\n"); 145 THR_Print("Using the ring timeline recorder.\n");
147 } 146 }
148 147
149 // Always fall back to the ring recorder. 148 // Always fall back to the ring recorder.
150 return new TimelineEventRingRecorder(); 149 return new TimelineEventRingRecorder();
151 } 150 }
152 151
153
154 // Returns a caller freed array of stream names in FLAG_timeline_streams. 152 // Returns a caller freed array of stream names in FLAG_timeline_streams.
155 static MallocGrowableArray<char*>* GetEnabledByDefaultTimelineStreams() { 153 static MallocGrowableArray<char*>* GetEnabledByDefaultTimelineStreams() {
156 MallocGrowableArray<char*>* result = new MallocGrowableArray<char*>(); 154 MallocGrowableArray<char*>* result = new MallocGrowableArray<char*>();
157 if (FLAG_timeline_streams == NULL) { 155 if (FLAG_timeline_streams == NULL) {
158 // Nothing set. 156 // Nothing set.
159 return result; 157 return result;
160 } 158 }
161 char* save_ptr; // Needed for strtok_r. 159 char* save_ptr; // Needed for strtok_r.
162 // strtok modifies arg 1 so we make a copy of it. 160 // strtok modifies arg 1 so we make a copy of it.
163 char* streams = strdup(FLAG_timeline_streams); 161 char* streams = strdup(FLAG_timeline_streams);
164 char* token = strtok_r(streams, ",", &save_ptr); 162 char* token = strtok_r(streams, ",", &save_ptr);
165 while (token != NULL) { 163 while (token != NULL) {
166 result->Add(strdup(token)); 164 result->Add(strdup(token));
167 token = strtok_r(NULL, ",", &save_ptr); 165 token = strtok_r(NULL, ",", &save_ptr);
168 } 166 }
169 free(streams); 167 free(streams);
170 return result; 168 return result;
171 } 169 }
172 170
173
174 // Frees the result of |GetEnabledByDefaultTimelineStreams|. 171 // Frees the result of |GetEnabledByDefaultTimelineStreams|.
175 static void FreeEnabledByDefaultTimelineStreams( 172 static void FreeEnabledByDefaultTimelineStreams(
176 MallocGrowableArray<char*>* streams) { 173 MallocGrowableArray<char*>* streams) {
177 if (streams == NULL) { 174 if (streams == NULL) {
178 return; 175 return;
179 } 176 }
180 for (intptr_t i = 0; i < streams->length(); i++) { 177 for (intptr_t i = 0; i < streams->length(); i++) {
181 free((*streams)[i]); 178 free((*streams)[i]);
182 } 179 }
183 delete streams; 180 delete streams;
184 } 181 }
185 182
186
187 // Returns true if |streams| contains |stream| or "all". Not case sensitive. 183 // Returns true if |streams| contains |stream| or "all". Not case sensitive.
188 static bool HasStream(MallocGrowableArray<char*>* streams, const char* stream) { 184 static bool HasStream(MallocGrowableArray<char*>* streams, const char* stream) {
189 if ((FLAG_timeline_dir != NULL) || FLAG_timing || FLAG_complete_timeline || 185 if ((FLAG_timeline_dir != NULL) || FLAG_timing || FLAG_complete_timeline ||
190 FLAG_startup_timeline) { 186 FLAG_startup_timeline) {
191 return true; 187 return true;
192 } 188 }
193 for (intptr_t i = 0; i < streams->length(); i++) { 189 for (intptr_t i = 0; i < streams->length(); i++) {
194 const char* checked_stream = (*streams)[i]; 190 const char* checked_stream = (*streams)[i];
195 if ((strstr(checked_stream, "all") != NULL) || 191 if ((strstr(checked_stream, "all") != NULL) ||
196 (strstr(checked_stream, stream) != NULL)) { 192 (strstr(checked_stream, stream) != NULL)) {
197 return true; 193 return true;
198 } 194 }
199 } 195 }
200 return false; 196 return false;
201 } 197 }
202 198
203
204 void Timeline::InitOnce() { 199 void Timeline::InitOnce() {
205 ASSERT(recorder_ == NULL); 200 ASSERT(recorder_ == NULL);
206 recorder_ = CreateTimelineRecorder(); 201 recorder_ = CreateTimelineRecorder();
207 ASSERT(recorder_ != NULL); 202 ASSERT(recorder_ != NULL);
208 enabled_streams_ = GetEnabledByDefaultTimelineStreams(); 203 enabled_streams_ = GetEnabledByDefaultTimelineStreams();
209 // Global overrides. 204 // Global overrides.
210 #define TIMELINE_STREAM_FLAG_DEFAULT(name, not_used) \ 205 #define TIMELINE_STREAM_FLAG_DEFAULT(name, not_used) \
211 stream_##name##_.Init(#name, HasStream(enabled_streams_, #name)); 206 stream_##name##_.Init(#name, HasStream(enabled_streams_, #name));
212 TIMELINE_STREAM_LIST(TIMELINE_STREAM_FLAG_DEFAULT) 207 TIMELINE_STREAM_LIST(TIMELINE_STREAM_FLAG_DEFAULT)
213 #undef TIMELINE_STREAM_FLAG_DEFAULT 208 #undef TIMELINE_STREAM_FLAG_DEFAULT
214 209
215 if (Timeline::stream_Embedder_.enabled() && 210 if (Timeline::stream_Embedder_.enabled() &&
216 (Timeline::get_start_recording_cb() != NULL)) { 211 (Timeline::get_start_recording_cb() != NULL)) {
217 Timeline::get_start_recording_cb()(); 212 Timeline::get_start_recording_cb()();
218 } 213 }
219 } 214 }
220 215
221
222 void Timeline::StreamStateChange(const char* stream_name, 216 void Timeline::StreamStateChange(const char* stream_name,
223 bool prev, 217 bool prev,
224 bool curr) { 218 bool curr) {
225 if (prev == curr) { 219 if (prev == curr) {
226 return; 220 return;
227 } 221 }
228 if (strcmp(stream_name, "Embedder") == 0) { 222 if (strcmp(stream_name, "Embedder") == 0) {
229 if (curr && (Timeline::get_start_recording_cb() != NULL)) { 223 if (curr && (Timeline::get_start_recording_cb() != NULL)) {
230 Timeline::get_start_recording_cb()(); 224 Timeline::get_start_recording_cb()();
231 } else if (!curr && (Timeline::get_stop_recording_cb() != NULL)) { 225 } else if (!curr && (Timeline::get_stop_recording_cb() != NULL)) {
232 Timeline::get_stop_recording_cb()(); 226 Timeline::get_stop_recording_cb()();
233 } 227 }
234 } 228 }
235 } 229 }
236 230
237
238 void Timeline::Shutdown() { 231 void Timeline::Shutdown() {
239 ASSERT(recorder_ != NULL); 232 ASSERT(recorder_ != NULL);
240 233
241 if (Timeline::stream_Embedder_.enabled() && 234 if (Timeline::stream_Embedder_.enabled() &&
242 (Timeline::get_stop_recording_cb() != NULL)) { 235 (Timeline::get_stop_recording_cb() != NULL)) {
243 Timeline::get_stop_recording_cb()(); 236 Timeline::get_stop_recording_cb()();
244 } 237 }
245 238
246 if (FLAG_timeline_dir != NULL) { 239 if (FLAG_timeline_dir != NULL) {
247 recorder_->WriteTo(FLAG_timeline_dir); 240 recorder_->WriteTo(FLAG_timeline_dir);
248 } 241 }
249 242
250 // Disable global streams. 243 // Disable global streams.
251 #define TIMELINE_STREAM_DISABLE(name, not_used) \ 244 #define TIMELINE_STREAM_DISABLE(name, not_used) \
252 Timeline::stream_##name##_.set_enabled(false); 245 Timeline::stream_##name##_.set_enabled(false);
253 TIMELINE_STREAM_LIST(TIMELINE_STREAM_DISABLE) 246 TIMELINE_STREAM_LIST(TIMELINE_STREAM_DISABLE)
254 #undef TIMELINE_STREAM_DISABLE 247 #undef TIMELINE_STREAM_DISABLE
255 delete recorder_; 248 delete recorder_;
256 recorder_ = NULL; 249 recorder_ = NULL;
257 if (enabled_streams_ != NULL) { 250 if (enabled_streams_ != NULL) {
258 FreeEnabledByDefaultTimelineStreams(enabled_streams_); 251 FreeEnabledByDefaultTimelineStreams(enabled_streams_);
259 enabled_streams_ = NULL; 252 enabled_streams_ = NULL;
260 } 253 }
261 } 254 }
262 255
263
264 TimelineEventRecorder* Timeline::recorder() { 256 TimelineEventRecorder* Timeline::recorder() {
265 return recorder_; 257 return recorder_;
266 } 258 }
267 259
268
269 void Timeline::ReclaimCachedBlocksFromThreads() { 260 void Timeline::ReclaimCachedBlocksFromThreads() {
270 TimelineEventRecorder* recorder = Timeline::recorder(); 261 TimelineEventRecorder* recorder = Timeline::recorder();
271 if (recorder == NULL) { 262 if (recorder == NULL) {
272 return; 263 return;
273 } 264 }
274 265
275 // Iterate over threads. 266 // Iterate over threads.
276 OSThreadIterator it; 267 OSThreadIterator it;
277 while (it.HasNext()) { 268 while (it.HasNext()) {
278 OSThread* thread = it.Next(); 269 OSThread* thread = it.Next();
279 MutexLocker ml(thread->timeline_block_lock()); 270 MutexLocker ml(thread->timeline_block_lock());
280 // Grab block and clear it. 271 // Grab block and clear it.
281 TimelineEventBlock* block = thread->timeline_block(); 272 TimelineEventBlock* block = thread->timeline_block();
282 thread->set_timeline_block(NULL); 273 thread->set_timeline_block(NULL);
283 // TODO(johnmccutchan): Consider dropping the timeline_block_lock here 274 // TODO(johnmccutchan): Consider dropping the timeline_block_lock here
284 // if we can do it everywhere. This would simplify the lock ordering 275 // if we can do it everywhere. This would simplify the lock ordering
285 // requirements. 276 // requirements.
286 recorder->FinishBlock(block); 277 recorder->FinishBlock(block);
287 } 278 }
288 } 279 }
289 280
290
291 void Timeline::PrintFlagsToJSON(JSONStream* js) { 281 void Timeline::PrintFlagsToJSON(JSONStream* js) {
292 JSONObject obj(js); 282 JSONObject obj(js);
293 obj.AddProperty("type", "TimelineFlags"); 283 obj.AddProperty("type", "TimelineFlags");
294 TimelineEventRecorder* recorder = Timeline::recorder(); 284 TimelineEventRecorder* recorder = Timeline::recorder();
295 if (recorder == NULL) { 285 if (recorder == NULL) {
296 obj.AddProperty("recorderName", "null"); 286 obj.AddProperty("recorderName", "null");
297 } else { 287 } else {
298 obj.AddProperty("recorderName", recorder->name()); 288 obj.AddProperty("recorderName", recorder->name());
299 } 289 }
300 { 290 {
301 JSONArray availableStreams(&obj, "availableStreams"); 291 JSONArray availableStreams(&obj, "availableStreams");
302 #define ADD_STREAM_NAME(name, not_used) availableStreams.AddValue(#name); 292 #define ADD_STREAM_NAME(name, not_used) availableStreams.AddValue(#name);
303 TIMELINE_STREAM_LIST(ADD_STREAM_NAME); 293 TIMELINE_STREAM_LIST(ADD_STREAM_NAME);
304 #undef ADD_STREAM_NAME 294 #undef ADD_STREAM_NAME
305 } 295 }
306 { 296 {
307 JSONArray recordedStreams(&obj, "recordedStreams"); 297 JSONArray recordedStreams(&obj, "recordedStreams");
308 #define ADD_RECORDED_STREAM_NAME(name, not_used) \ 298 #define ADD_RECORDED_STREAM_NAME(name, not_used) \
309 if (stream_##name##_.enabled()) { \ 299 if (stream_##name##_.enabled()) { \
310 recordedStreams.AddValue(#name); \ 300 recordedStreams.AddValue(#name); \
311 } 301 }
312 TIMELINE_STREAM_LIST(ADD_RECORDED_STREAM_NAME); 302 TIMELINE_STREAM_LIST(ADD_RECORDED_STREAM_NAME);
313 #undef ADD_RECORDED_STREAM_NAME 303 #undef ADD_RECORDED_STREAM_NAME
314 } 304 }
315 } 305 }
316 306
317
318 void Timeline::Clear() { 307 void Timeline::Clear() {
319 TimelineEventRecorder* recorder = Timeline::recorder(); 308 TimelineEventRecorder* recorder = Timeline::recorder();
320 if (recorder == NULL) { 309 if (recorder == NULL) {
321 return; 310 return;
322 } 311 }
323 ReclaimCachedBlocksFromThreads(); 312 ReclaimCachedBlocksFromThreads();
324 recorder->Clear(); 313 recorder->Clear();
325 } 314 }
326 315
327
328 TimelineEventRecorder* Timeline::recorder_ = NULL; 316 TimelineEventRecorder* Timeline::recorder_ = NULL;
329 MallocGrowableArray<char*>* Timeline::enabled_streams_ = NULL; 317 MallocGrowableArray<char*>* Timeline::enabled_streams_ = NULL;
330 Dart_EmbedderTimelineStartRecording Timeline::start_recording_cb_ = NULL; 318 Dart_EmbedderTimelineStartRecording Timeline::start_recording_cb_ = NULL;
331 Dart_EmbedderTimelineStopRecording Timeline::stop_recording_cb_ = NULL; 319 Dart_EmbedderTimelineStopRecording Timeline::stop_recording_cb_ = NULL;
332 320
333 #define TIMELINE_STREAM_DEFINE(name, enabled_by_default) \ 321 #define TIMELINE_STREAM_DEFINE(name, enabled_by_default) \
334 TimelineStream Timeline::stream_##name##_; 322 TimelineStream Timeline::stream_##name##_;
335 TIMELINE_STREAM_LIST(TIMELINE_STREAM_DEFINE) 323 TIMELINE_STREAM_LIST(TIMELINE_STREAM_DEFINE)
336 #undef TIMELINE_STREAM_DEFINE 324 #undef TIMELINE_STREAM_DEFINE
337 325
338 TimelineEvent::TimelineEvent() 326 TimelineEvent::TimelineEvent()
339 : timestamp0_(0), 327 : timestamp0_(0),
340 timestamp1_(0), 328 timestamp1_(0),
341 thread_timestamp0_(-1), 329 thread_timestamp0_(-1),
342 thread_timestamp1_(-1), 330 thread_timestamp1_(-1),
343 arguments_(NULL), 331 arguments_(NULL),
344 arguments_length_(0), 332 arguments_length_(0),
345 state_(0), 333 state_(0),
346 label_(NULL), 334 label_(NULL),
347 category_(""), 335 category_(""),
348 thread_(OSThread::kInvalidThreadId), 336 thread_(OSThread::kInvalidThreadId),
349 isolate_id_(ILLEGAL_PORT) {} 337 isolate_id_(ILLEGAL_PORT) {}
350 338
351
352 TimelineEvent::~TimelineEvent() { 339 TimelineEvent::~TimelineEvent() {
353 Reset(); 340 Reset();
354 } 341 }
355 342
356
357 void TimelineEvent::Reset() { 343 void TimelineEvent::Reset() {
358 if (owns_label() && label_ != NULL) { 344 if (owns_label() && label_ != NULL) {
359 free(const_cast<char*>(label_)); 345 free(const_cast<char*>(label_));
360 } 346 }
361 state_ = 0; 347 state_ = 0;
362 thread_ = OSThread::kInvalidThreadId; 348 thread_ = OSThread::kInvalidThreadId;
363 isolate_id_ = ILLEGAL_PORT; 349 isolate_id_ = ILLEGAL_PORT;
364 category_ = ""; 350 category_ = "";
365 label_ = NULL; 351 label_ = NULL;
366 FreeArguments(); 352 FreeArguments();
367 set_pre_serialized_json(false); 353 set_pre_serialized_json(false);
368 set_event_type(kNone); 354 set_event_type(kNone);
369 set_owns_label(false); 355 set_owns_label(false);
370 } 356 }
371 357
372
373 void TimelineEvent::AsyncBegin(const char* label, 358 void TimelineEvent::AsyncBegin(const char* label,
374 int64_t async_id, 359 int64_t async_id,
375 int64_t micros) { 360 int64_t micros) {
376 Init(kAsyncBegin, label); 361 Init(kAsyncBegin, label);
377 set_timestamp0(micros); 362 set_timestamp0(micros);
378 // Overload timestamp1_ with the async_id. 363 // Overload timestamp1_ with the async_id.
379 set_timestamp1(async_id); 364 set_timestamp1(async_id);
380 } 365 }
381 366
382
383 void TimelineEvent::AsyncInstant(const char* label, 367 void TimelineEvent::AsyncInstant(const char* label,
384 int64_t async_id, 368 int64_t async_id,
385 int64_t micros) { 369 int64_t micros) {
386 Init(kAsyncInstant, label); 370 Init(kAsyncInstant, label);
387 set_timestamp0(micros); 371 set_timestamp0(micros);
388 // Overload timestamp1_ with the async_id. 372 // Overload timestamp1_ with the async_id.
389 set_timestamp1(async_id); 373 set_timestamp1(async_id);
390 } 374 }
391 375
392
393 void TimelineEvent::AsyncEnd(const char* label, 376 void TimelineEvent::AsyncEnd(const char* label,
394 int64_t async_id, 377 int64_t async_id,
395 int64_t micros) { 378 int64_t micros) {
396 Init(kAsyncEnd, label); 379 Init(kAsyncEnd, label);
397 set_timestamp0(micros); 380 set_timestamp0(micros);
398 // Overload timestamp1_ with the async_id. 381 // Overload timestamp1_ with the async_id.
399 set_timestamp1(async_id); 382 set_timestamp1(async_id);
400 } 383 }
401 384
402
403 void TimelineEvent::DurationBegin(const char* label, 385 void TimelineEvent::DurationBegin(const char* label,
404 int64_t micros, 386 int64_t micros,
405 int64_t thread_micros) { 387 int64_t thread_micros) {
406 Init(kDuration, label); 388 Init(kDuration, label);
407 set_timestamp0(micros); 389 set_timestamp0(micros);
408 set_thread_timestamp0(thread_micros); 390 set_thread_timestamp0(thread_micros);
409 } 391 }
410 392
411
412 void TimelineEvent::DurationEnd(int64_t micros, int64_t thread_micros) { 393 void TimelineEvent::DurationEnd(int64_t micros, int64_t thread_micros) {
413 ASSERT(timestamp1_ == 0); 394 ASSERT(timestamp1_ == 0);
414 set_timestamp1(micros); 395 set_timestamp1(micros);
415 set_thread_timestamp1(thread_micros); 396 set_thread_timestamp1(thread_micros);
416 } 397 }
417 398
418
419 void TimelineEvent::Instant(const char* label, int64_t micros) { 399 void TimelineEvent::Instant(const char* label, int64_t micros) {
420 Init(kInstant, label); 400 Init(kInstant, label);
421 set_timestamp0(micros); 401 set_timestamp0(micros);
422 } 402 }
423 403
424
425 void TimelineEvent::Duration(const char* label, 404 void TimelineEvent::Duration(const char* label,
426 int64_t start_micros, 405 int64_t start_micros,
427 int64_t end_micros, 406 int64_t end_micros,
428 int64_t thread_start_micros, 407 int64_t thread_start_micros,
429 int64_t thread_end_micros) { 408 int64_t thread_end_micros) {
430 Init(kDuration, label); 409 Init(kDuration, label);
431 set_timestamp0(start_micros); 410 set_timestamp0(start_micros);
432 set_timestamp1(end_micros); 411 set_timestamp1(end_micros);
433 set_thread_timestamp0(thread_start_micros); 412 set_thread_timestamp0(thread_start_micros);
434 set_thread_timestamp1(thread_end_micros); 413 set_thread_timestamp1(thread_end_micros);
435 } 414 }
436 415
437
438 void TimelineEvent::Begin(const char* label, 416 void TimelineEvent::Begin(const char* label,
439 int64_t micros, 417 int64_t micros,
440 int64_t thread_micros) { 418 int64_t thread_micros) {
441 Init(kBegin, label); 419 Init(kBegin, label);
442 set_timestamp0(micros); 420 set_timestamp0(micros);
443 set_thread_timestamp0(thread_micros); 421 set_thread_timestamp0(thread_micros);
444 } 422 }
445 423
446
447 void TimelineEvent::End(const char* label, 424 void TimelineEvent::End(const char* label,
448 int64_t micros, 425 int64_t micros,
449 int64_t thread_micros) { 426 int64_t thread_micros) {
450 Init(kEnd, label); 427 Init(kEnd, label);
451 set_timestamp0(micros); 428 set_timestamp0(micros);
452 set_thread_timestamp0(thread_micros); 429 set_thread_timestamp0(thread_micros);
453 } 430 }
454 431
455
456 void TimelineEvent::Counter(const char* label, int64_t micros) { 432 void TimelineEvent::Counter(const char* label, int64_t micros) {
457 Init(kCounter, label); 433 Init(kCounter, label);
458 set_timestamp0(micros); 434 set_timestamp0(micros);
459 } 435 }
460 436
461
462 void TimelineEvent::Metadata(const char* label, int64_t micros) { 437 void TimelineEvent::Metadata(const char* label, int64_t micros) {
463 Init(kMetadata, label); 438 Init(kMetadata, label);
464 set_timestamp0(micros); 439 set_timestamp0(micros);
465 } 440 }
466 441
467
468 void TimelineEvent::CompleteWithPreSerializedJSON(const char* json) { 442 void TimelineEvent::CompleteWithPreSerializedJSON(const char* json) {
469 set_pre_serialized_json(true); 443 set_pre_serialized_json(true);
470 SetNumArguments(1); 444 SetNumArguments(1);
471 CopyArgument(0, "Dart", json); 445 CopyArgument(0, "Dart", json);
472 Complete(); 446 Complete();
473 } 447 }
474 448
475
476 void TimelineEvent::SetNumArguments(intptr_t length) { 449 void TimelineEvent::SetNumArguments(intptr_t length) {
477 // Cannot call this twice. 450 // Cannot call this twice.
478 ASSERT(arguments_ == NULL); 451 ASSERT(arguments_ == NULL);
479 ASSERT(arguments_length_ == 0); 452 ASSERT(arguments_length_ == 0);
480 if (length == 0) { 453 if (length == 0) {
481 return; 454 return;
482 } 455 }
483 arguments_length_ = length; 456 arguments_length_ = length;
484 arguments_ = reinterpret_cast<TimelineEventArgument*>( 457 arguments_ = reinterpret_cast<TimelineEventArgument*>(
485 calloc(sizeof(TimelineEventArgument), length)); 458 calloc(sizeof(TimelineEventArgument), length));
486 } 459 }
487 460
488
489 void TimelineEvent::SetArgument(intptr_t i, const char* name, char* argument) { 461 void TimelineEvent::SetArgument(intptr_t i, const char* name, char* argument) {
490 ASSERT(i >= 0); 462 ASSERT(i >= 0);
491 ASSERT(i < arguments_length_); 463 ASSERT(i < arguments_length_);
492 arguments_[i].name = name; 464 arguments_[i].name = name;
493 arguments_[i].value = argument; 465 arguments_[i].value = argument;
494 } 466 }
495 467
496
497 void TimelineEvent::FormatArgument(intptr_t i, 468 void TimelineEvent::FormatArgument(intptr_t i,
498 const char* name, 469 const char* name,
499 const char* fmt, 470 const char* fmt,
500 ...) { 471 ...) {
501 ASSERT(i >= 0); 472 ASSERT(i >= 0);
502 ASSERT(i < arguments_length_); 473 ASSERT(i < arguments_length_);
503 va_list args; 474 va_list args;
504 va_start(args, fmt); 475 va_start(args, fmt);
505 intptr_t len = OS::VSNPrint(NULL, 0, fmt, args); 476 intptr_t len = OS::VSNPrint(NULL, 0, fmt, args);
506 va_end(args); 477 va_end(args);
507 478
508 char* buffer = reinterpret_cast<char*>(malloc(len + 1)); 479 char* buffer = reinterpret_cast<char*>(malloc(len + 1));
509 va_list args2; 480 va_list args2;
510 va_start(args2, fmt); 481 va_start(args2, fmt);
511 OS::VSNPrint(buffer, (len + 1), fmt, args2); 482 OS::VSNPrint(buffer, (len + 1), fmt, args2);
512 va_end(args2); 483 va_end(args2);
513 484
514 SetArgument(i, name, buffer); 485 SetArgument(i, name, buffer);
515 } 486 }
516 487
517
518 void TimelineEvent::CopyArgument(intptr_t i, 488 void TimelineEvent::CopyArgument(intptr_t i,
519 const char* name, 489 const char* name,
520 const char* argument) { 490 const char* argument) {
521 SetArgument(i, name, strdup(argument)); 491 SetArgument(i, name, strdup(argument));
522 } 492 }
523 493
524
525 void TimelineEvent::StealArguments(intptr_t arguments_length, 494 void TimelineEvent::StealArguments(intptr_t arguments_length,
526 TimelineEventArgument* arguments) { 495 TimelineEventArgument* arguments) {
527 arguments_length_ = arguments_length; 496 arguments_length_ = arguments_length;
528 arguments_ = arguments; 497 arguments_ = arguments;
529 } 498 }
530 499
531
532 #if defined(HOST_OS_FUCHSIA) 500 #if defined(HOST_OS_FUCHSIA)
533
534 // TODO(zra): The functions below emit Dart's timeline events all as category 501 // TODO(zra): The functions below emit Dart's timeline events all as category
535 // "dart". Instead, we could have finer-grained categories that make use of 502 // "dart". Instead, we could have finer-grained categories that make use of
536 // the name of the timeline stream, e.g. "VM", "GC", etc. 503 // the name of the timeline stream, e.g. "VM", "GC", etc.
537 504
538 #define FUCHSIA_EVENT_ARGS_LIST(V) \ 505 #define FUCHSIA_EVENT_ARGS_LIST(V) \
539 V(Begin, TRACE_DURATION_BEGIN) \ 506 V(Begin, TRACE_DURATION_BEGIN) \
540 V(End, TRACE_DURATION_END) 507 V(End, TRACE_DURATION_END)
541 508
542 #define EMIT_FUCHSIA_EVENT(__name, __macro) \ 509 #define EMIT_FUCHSIA_EVENT(__name, __macro) \
543 static void EmitFuchsia##__name##Event(const char* label, \ 510 static void EmitFuchsia##__name##Event(const char* label, \
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
576 } else { \ 543 } else { \
577 __macro("dart", label, id, arguments[0].name, \ 544 __macro("dart", label, id, arguments[0].name, \
578 const_cast<const char*>(arguments[0].value), arguments[1].name, \ 545 const_cast<const char*>(arguments[0].value), arguments[1].name, \
579 const_cast<const char*>(arguments[1].value)); \ 546 const_cast<const char*>(arguments[1].value)); \
580 } \ 547 } \
581 } 548 }
582 549
583 FUCHSIA_EVENT_ID_ARGS_LIST(EMIT_FUCHSIA_EVENT) 550 FUCHSIA_EVENT_ID_ARGS_LIST(EMIT_FUCHSIA_EVENT)
584 #undef EMIT_FUCHSIA_EVENT 551 #undef EMIT_FUCHSIA_EVENT
585 552
586
587 void TimelineEvent::EmitFuchsiaEvent() { 553 void TimelineEvent::EmitFuchsiaEvent() {
588 switch (event_type()) { 554 switch (event_type()) {
589 case kBegin: 555 case kBegin:
590 EmitFuchsiaBeginEvent(label_, arguments_, arguments_length_); 556 EmitFuchsiaBeginEvent(label_, arguments_, arguments_length_);
591 break; 557 break;
592 case kEnd: 558 case kEnd:
593 EmitFuchsiaEndEvent(label_, arguments_, arguments_length_); 559 EmitFuchsiaEndEvent(label_, arguments_, arguments_length_);
594 break; 560 break;
595 case kInstant: 561 case kInstant:
596 EmitFuchsiaInstantEvent(label_, TRACE_SCOPE_THREAD, arguments_, 562 EmitFuchsiaInstantEvent(label_, TRACE_SCOPE_THREAD, arguments_,
(...skipping 12 matching lines...) Expand all
609 arguments_length_); 575 arguments_length_);
610 break; 576 break;
611 default: 577 default:
612 // TODO(zra): Figure out what to do with kDuration, kCounter, and 578 // TODO(zra): Figure out what to do with kDuration, kCounter, and
613 // kMetadata. 579 // kMetadata.
614 break; 580 break;
615 } 581 }
616 } 582 }
617 #endif 583 #endif
618 584
619
620 intptr_t TimelineEvent::PrintSystrace(char* buffer, intptr_t buffer_size) { 585 intptr_t TimelineEvent::PrintSystrace(char* buffer, intptr_t buffer_size) {
621 ASSERT(buffer != NULL); 586 ASSERT(buffer != NULL);
622 ASSERT(buffer_size > 0); 587 ASSERT(buffer_size > 0);
623 buffer[0] = '\0'; 588 buffer[0] = '\0';
624 intptr_t length = 0; 589 intptr_t length = 0;
625 int64_t pid = OS::ProcessId(); 590 int64_t pid = OS::ProcessId();
626 switch (event_type()) { 591 switch (event_type()) {
627 case kBegin: { 592 case kBegin: {
628 length = OS::SNPrint(buffer, buffer_size, "B|%" Pd64 "|%s", pid, label()); 593 length = OS::SNPrint(buffer, buffer_size, "B|%" Pd64 "|%s", pid, label());
629 } break; 594 } break;
630 case kEnd: { 595 case kEnd: {
631 length = OS::SNPrint(buffer, buffer_size, "E"); 596 length = OS::SNPrint(buffer, buffer_size, "E");
632 } break; 597 } break;
633 case kCounter: { 598 case kCounter: {
634 if (arguments_length_ > 0) { 599 if (arguments_length_ > 0) {
635 // We only report the first counter value. 600 // We only report the first counter value.
636 length = OS::SNPrint(buffer, buffer_size, "C|%" Pd64 "|%s|%s", pid, 601 length = OS::SNPrint(buffer, buffer_size, "C|%" Pd64 "|%s|%s", pid,
637 label(), arguments_[0].value); 602 label(), arguments_[0].value);
638 } 603 }
639 } 604 }
640 default: 605 default:
641 // Ignore event types that we cannot serialize to the Systrace format. 606 // Ignore event types that we cannot serialize to the Systrace format.
642 break; 607 break;
643 } 608 }
644 return length; 609 return length;
645 } 610 }
646 611
647
648 void TimelineEvent::Complete() { 612 void TimelineEvent::Complete() {
649 TimelineEventRecorder* recorder = Timeline::recorder(); 613 TimelineEventRecorder* recorder = Timeline::recorder();
650 if (recorder != NULL) { 614 if (recorder != NULL) {
651 recorder->CompleteEvent(this); 615 recorder->CompleteEvent(this);
652 } 616 }
653 } 617 }
654 618
655
656 void TimelineEvent::FreeArguments() { 619 void TimelineEvent::FreeArguments() {
657 if (arguments_ == NULL) { 620 if (arguments_ == NULL) {
658 return; 621 return;
659 } 622 }
660 for (intptr_t i = 0; i < arguments_length_; i++) { 623 for (intptr_t i = 0; i < arguments_length_; i++) {
661 free(arguments_[i].value); 624 free(arguments_[i].value);
662 } 625 }
663 free(arguments_); 626 free(arguments_);
664 arguments_ = NULL; 627 arguments_ = NULL;
665 arguments_length_ = 0; 628 arguments_length_ = 0;
666 } 629 }
667 630
668
669 void TimelineEvent::StreamInit(TimelineStream* stream) { 631 void TimelineEvent::StreamInit(TimelineStream* stream) {
670 if (stream != NULL) { 632 if (stream != NULL) {
671 category_ = stream->name(); 633 category_ = stream->name();
672 } else { 634 } else {
673 category_ = ""; 635 category_ = "";
674 } 636 }
675 } 637 }
676 638
677
678 void TimelineEvent::Init(EventType event_type, const char* label) { 639 void TimelineEvent::Init(EventType event_type, const char* label) {
679 ASSERT(label != NULL); 640 ASSERT(label != NULL);
680 state_ = 0; 641 state_ = 0;
681 timestamp0_ = 0; 642 timestamp0_ = 0;
682 timestamp1_ = 0; 643 timestamp1_ = 0;
683 thread_timestamp0_ = -1; 644 thread_timestamp0_ = -1;
684 thread_timestamp1_ = -1; 645 thread_timestamp1_ = -1;
685 OSThread* os_thread = OSThread::Current(); 646 OSThread* os_thread = OSThread::Current();
686 ASSERT(os_thread != NULL); 647 ASSERT(os_thread != NULL);
687 thread_ = os_thread->trace_id(); 648 thread_ = os_thread->trace_id();
688 Isolate* isolate = Isolate::Current(); 649 Isolate* isolate = Isolate::Current();
689 if (isolate != NULL) { 650 if (isolate != NULL) {
690 isolate_id_ = isolate->main_port(); 651 isolate_id_ = isolate->main_port();
691 } else { 652 } else {
692 isolate_id_ = ILLEGAL_PORT; 653 isolate_id_ = ILLEGAL_PORT;
693 } 654 }
694 label_ = label; 655 label_ = label;
695 FreeArguments(); 656 FreeArguments();
696 set_pre_serialized_json(false); 657 set_pre_serialized_json(false);
697 set_event_type(event_type); 658 set_event_type(event_type);
698 set_owns_label(false); 659 set_owns_label(false);
699 } 660 }
700 661
701
702 bool TimelineEvent::Within(int64_t time_origin_micros, 662 bool TimelineEvent::Within(int64_t time_origin_micros,
703 int64_t time_extent_micros) { 663 int64_t time_extent_micros) {
704 if ((time_origin_micros == -1) || (time_extent_micros == -1)) { 664 if ((time_origin_micros == -1) || (time_extent_micros == -1)) {
705 // No time range specified. 665 // No time range specified.
706 return true; 666 return true;
707 } 667 }
708 if (IsFinishedDuration()) { 668 if (IsFinishedDuration()) {
709 // Event is from e_t0 to e_t1. 669 // Event is from e_t0 to e_t1.
710 int64_t e_t0 = TimeOrigin(); 670 int64_t e_t0 = TimeOrigin();
711 int64_t e_t1 = TimeEnd(); 671 int64_t e_t1 = TimeEnd();
712 ASSERT(e_t0 <= e_t1); 672 ASSERT(e_t0 <= e_t1);
713 // Range is from r_t0 to r_t1. 673 // Range is from r_t0 to r_t1.
714 int64_t r_t0 = time_origin_micros; 674 int64_t r_t0 = time_origin_micros;
715 int64_t r_t1 = time_origin_micros + time_extent_micros; 675 int64_t r_t1 = time_origin_micros + time_extent_micros;
716 ASSERT(r_t0 <= r_t1); 676 ASSERT(r_t0 <= r_t1);
717 return !((r_t1 < e_t0) || (e_t1 < r_t0)); 677 return !((r_t1 < e_t0) || (e_t1 < r_t0));
718 } 678 }
719 int64_t delta = TimeOrigin() - time_origin_micros; 679 int64_t delta = TimeOrigin() - time_origin_micros;
720 return (delta >= 0) && (delta <= time_extent_micros); 680 return (delta >= 0) && (delta <= time_extent_micros);
721 } 681 }
722 682
723
724 const char* TimelineEvent::GetSerializedJSON() const { 683 const char* TimelineEvent::GetSerializedJSON() const {
725 ASSERT(pre_serialized_json()); 684 ASSERT(pre_serialized_json());
726 ASSERT(arguments_length_ == 1); 685 ASSERT(arguments_length_ == 1);
727 ASSERT(arguments_ != NULL); 686 ASSERT(arguments_ != NULL);
728 return arguments_[0].value; 687 return arguments_[0].value;
729 } 688 }
730 689
731
732 void TimelineEvent::PrintJSON(JSONStream* stream) const { 690 void TimelineEvent::PrintJSON(JSONStream* stream) const {
733 if (!FLAG_support_service) { 691 if (!FLAG_support_service) {
734 return; 692 return;
735 } 693 }
736 if (pre_serialized_json()) { 694 if (pre_serialized_json()) {
737 // Event has already been serialized into JSON- just append the 695 // Event has already been serialized into JSON- just append the
738 // raw data. 696 // raw data.
739 stream->AppendSerializedObject(GetSerializedJSON()); 697 stream->AppendSerializedObject(GetSerializedJSON());
740 return; 698 return;
741 } 699 }
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
796 args.AddProperty(arg.name, arg.value); 754 args.AddProperty(arg.name, arg.value);
797 } 755 }
798 if (isolate_id_ != ILLEGAL_PORT) { 756 if (isolate_id_ != ILLEGAL_PORT) {
799 // If we have one, append the isolate id. 757 // If we have one, append the isolate id.
800 args.AddPropertyF("isolateNumber", "%" Pd64 "", 758 args.AddPropertyF("isolateNumber", "%" Pd64 "",
801 static_cast<int64_t>(isolate_id_)); 759 static_cast<int64_t>(isolate_id_));
802 } 760 }
803 } 761 }
804 } 762 }
805 763
806
807 int64_t TimelineEvent::TimeOrigin() const { 764 int64_t TimelineEvent::TimeOrigin() const {
808 return timestamp0_; 765 return timestamp0_;
809 } 766 }
810 767
811
812 int64_t TimelineEvent::AsyncId() const { 768 int64_t TimelineEvent::AsyncId() const {
813 return timestamp1_; 769 return timestamp1_;
814 } 770 }
815 771
816
817 int64_t TimelineEvent::LowTime() const { 772 int64_t TimelineEvent::LowTime() const {
818 return timestamp0_; 773 return timestamp0_;
819 } 774 }
820 775
821
822 int64_t TimelineEvent::HighTime() const { 776 int64_t TimelineEvent::HighTime() const {
823 if (event_type() == kDuration) { 777 if (event_type() == kDuration) {
824 return timestamp1_; 778 return timestamp1_;
825 } else { 779 } else {
826 return timestamp0_; 780 return timestamp0_;
827 } 781 }
828 } 782 }
829 783
830
831 int64_t TimelineEvent::TimeDuration() const { 784 int64_t TimelineEvent::TimeDuration() const {
832 if (timestamp1_ == 0) { 785 if (timestamp1_ == 0) {
833 // This duration is still open, use current time as end. 786 // This duration is still open, use current time as end.
834 return OS::GetCurrentMonotonicMicros() - timestamp0_; 787 return OS::GetCurrentMonotonicMicros() - timestamp0_;
835 } 788 }
836 return timestamp1_ - timestamp0_; 789 return timestamp1_ - timestamp0_;
837 } 790 }
838 791
839
840 bool TimelineEvent::HasThreadCPUTime() const { 792 bool TimelineEvent::HasThreadCPUTime() const {
841 return (thread_timestamp0_ != -1); 793 return (thread_timestamp0_ != -1);
842 } 794 }
843 795
844
845 int64_t TimelineEvent::ThreadCPUTimeOrigin() const { 796 int64_t TimelineEvent::ThreadCPUTimeOrigin() const {
846 ASSERT(HasThreadCPUTime()); 797 ASSERT(HasThreadCPUTime());
847 return thread_timestamp0_; 798 return thread_timestamp0_;
848 } 799 }
849 800
850
851 int64_t TimelineEvent::ThreadCPUTimeDuration() const { 801 int64_t TimelineEvent::ThreadCPUTimeDuration() const {
852 ASSERT(HasThreadCPUTime()); 802 ASSERT(HasThreadCPUTime());
853 if (thread_timestamp1_ == -1) { 803 if (thread_timestamp1_ == -1) {
854 // This duration is still open, use current time as end. 804 // This duration is still open, use current time as end.
855 return OS::GetCurrentThreadCPUMicros() - thread_timestamp0_; 805 return OS::GetCurrentThreadCPUMicros() - thread_timestamp0_;
856 } 806 }
857 return thread_timestamp1_ - thread_timestamp0_; 807 return thread_timestamp1_ - thread_timestamp0_;
858 } 808 }
859 809
860
861 TimelineStream::TimelineStream() : name_(NULL), enabled_(false) {} 810 TimelineStream::TimelineStream() : name_(NULL), enabled_(false) {}
862 811
863
864 void TimelineStream::Init(const char* name, bool enabled) { 812 void TimelineStream::Init(const char* name, bool enabled) {
865 name_ = name; 813 name_ = name;
866 enabled_ = enabled; 814 enabled_ = enabled;
867 } 815 }
868 816
869
870 TimelineEvent* TimelineStream::StartEvent() { 817 TimelineEvent* TimelineStream::StartEvent() {
871 TimelineEventRecorder* recorder = Timeline::recorder(); 818 TimelineEventRecorder* recorder = Timeline::recorder();
872 if (!enabled() || (recorder == NULL)) { 819 if (!enabled() || (recorder == NULL)) {
873 return NULL; 820 return NULL;
874 } 821 }
875 ASSERT(name_ != NULL); 822 ASSERT(name_ != NULL);
876 TimelineEvent* event = recorder->StartEvent(); 823 TimelineEvent* event = recorder->StartEvent();
877 if (event != NULL) { 824 if (event != NULL) {
878 event->StreamInit(this); 825 event->StreamInit(this);
879 } 826 }
880 return event; 827 return event;
881 } 828 }
882 829
883
884 TimelineEventScope::TimelineEventScope(TimelineStream* stream, 830 TimelineEventScope::TimelineEventScope(TimelineStream* stream,
885 const char* label) 831 const char* label)
886 : StackResource(reinterpret_cast<Thread*>(NULL)), 832 : StackResource(reinterpret_cast<Thread*>(NULL)),
887 stream_(stream), 833 stream_(stream),
888 label_(label), 834 label_(label),
889 arguments_(NULL), 835 arguments_(NULL),
890 arguments_length_(0), 836 arguments_length_(0),
891 enabled_(false) { 837 enabled_(false) {
892 Init(); 838 Init();
893 } 839 }
894 840
895
896 TimelineEventScope::TimelineEventScope(Thread* thread, 841 TimelineEventScope::TimelineEventScope(Thread* thread,
897 TimelineStream* stream, 842 TimelineStream* stream,
898 const char* label) 843 const char* label)
899 : StackResource(thread), 844 : StackResource(thread),
900 stream_(stream), 845 stream_(stream),
901 label_(label), 846 label_(label),
902 arguments_(NULL), 847 arguments_(NULL),
903 arguments_length_(0), 848 arguments_length_(0),
904 enabled_(false) { 849 enabled_(false) {
905 Init(); 850 Init();
906 } 851 }
907 852
908
909 TimelineEventScope::~TimelineEventScope() { 853 TimelineEventScope::~TimelineEventScope() {
910 FreeArguments(); 854 FreeArguments();
911 } 855 }
912 856
913
914 void TimelineEventScope::Init() { 857 void TimelineEventScope::Init() {
915 ASSERT(enabled_ == false); 858 ASSERT(enabled_ == false);
916 ASSERT(label_ != NULL); 859 ASSERT(label_ != NULL);
917 ASSERT(stream_ != NULL); 860 ASSERT(stream_ != NULL);
918 if (!stream_->enabled()) { 861 if (!stream_->enabled()) {
919 // Stream is not enabled, do nothing. 862 // Stream is not enabled, do nothing.
920 return; 863 return;
921 } 864 }
922 enabled_ = true; 865 enabled_ = true;
923 } 866 }
924 867
925
926 void TimelineEventScope::SetNumArguments(intptr_t length) { 868 void TimelineEventScope::SetNumArguments(intptr_t length) {
927 if (!enabled()) { 869 if (!enabled()) {
928 return; 870 return;
929 } 871 }
930 ASSERT(arguments_ == NULL); 872 ASSERT(arguments_ == NULL);
931 ASSERT(arguments_length_ == 0); 873 ASSERT(arguments_length_ == 0);
932 arguments_length_ = length; 874 arguments_length_ = length;
933 if (arguments_length_ == 0) { 875 if (arguments_length_ == 0) {
934 return; 876 return;
935 } 877 }
936 arguments_ = reinterpret_cast<TimelineEventArgument*>( 878 arguments_ = reinterpret_cast<TimelineEventArgument*>(
937 calloc(sizeof(TimelineEventArgument), length)); 879 calloc(sizeof(TimelineEventArgument), length));
938 } 880 }
939 881
940
941 // |name| must be a compile time constant. Takes ownership of |argumentp|. 882 // |name| must be a compile time constant. Takes ownership of |argumentp|.
942 void TimelineEventScope::SetArgument(intptr_t i, 883 void TimelineEventScope::SetArgument(intptr_t i,
943 const char* name, 884 const char* name,
944 char* argument) { 885 char* argument) {
945 if (!enabled()) { 886 if (!enabled()) {
946 return; 887 return;
947 } 888 }
948 ASSERT(i >= 0); 889 ASSERT(i >= 0);
949 ASSERT(i < arguments_length_); 890 ASSERT(i < arguments_length_);
950 arguments_[i].name = name; 891 arguments_[i].name = name;
951 arguments_[i].value = argument; 892 arguments_[i].value = argument;
952 } 893 }
953 894
954
955 // |name| must be a compile time constant. Copies |argument|. 895 // |name| must be a compile time constant. Copies |argument|.
956 void TimelineEventScope::CopyArgument(intptr_t i, 896 void TimelineEventScope::CopyArgument(intptr_t i,
957 const char* name, 897 const char* name,
958 const char* argument) { 898 const char* argument) {
959 if (!enabled()) { 899 if (!enabled()) {
960 return; 900 return;
961 } 901 }
962 SetArgument(i, name, strdup(argument)); 902 SetArgument(i, name, strdup(argument));
963 } 903 }
964 904
965
966 void TimelineEventScope::FormatArgument(intptr_t i, 905 void TimelineEventScope::FormatArgument(intptr_t i,
967 const char* name, 906 const char* name,
968 const char* fmt, 907 const char* fmt,
969 ...) { 908 ...) {
970 if (!enabled()) { 909 if (!enabled()) {
971 return; 910 return;
972 } 911 }
973 va_list args; 912 va_list args;
974 va_start(args, fmt); 913 va_start(args, fmt);
975 intptr_t len = OS::VSNPrint(NULL, 0, fmt, args); 914 intptr_t len = OS::VSNPrint(NULL, 0, fmt, args);
976 va_end(args); 915 va_end(args);
977 916
978 char* buffer = reinterpret_cast<char*>(malloc(len + 1)); 917 char* buffer = reinterpret_cast<char*>(malloc(len + 1));
979 va_list args2; 918 va_list args2;
980 va_start(args2, fmt); 919 va_start(args2, fmt);
981 OS::VSNPrint(buffer, (len + 1), fmt, args2); 920 OS::VSNPrint(buffer, (len + 1), fmt, args2);
982 va_end(args2); 921 va_end(args2);
983 922
984 SetArgument(i, name, buffer); 923 SetArgument(i, name, buffer);
985 } 924 }
986 925
987
988 void TimelineEventScope::FreeArguments() { 926 void TimelineEventScope::FreeArguments() {
989 if (arguments_ == NULL) { 927 if (arguments_ == NULL) {
990 return; 928 return;
991 } 929 }
992 for (intptr_t i = 0; i < arguments_length_; i++) { 930 for (intptr_t i = 0; i < arguments_length_; i++) {
993 free(arguments_[i].value); 931 free(arguments_[i].value);
994 } 932 }
995 free(arguments_); 933 free(arguments_);
996 arguments_ = NULL; 934 arguments_ = NULL;
997 arguments_length_ = 0; 935 arguments_length_ = 0;
998 } 936 }
999 937
1000
1001 void TimelineEventScope::StealArguments(TimelineEvent* event) { 938 void TimelineEventScope::StealArguments(TimelineEvent* event) {
1002 if (event == NULL) { 939 if (event == NULL) {
1003 return; 940 return;
1004 } 941 }
1005 event->StealArguments(arguments_length_, arguments_); 942 event->StealArguments(arguments_length_, arguments_);
1006 arguments_length_ = 0; 943 arguments_length_ = 0;
1007 arguments_ = NULL; 944 arguments_ = NULL;
1008 } 945 }
1009 946
1010
1011 TimelineDurationScope::TimelineDurationScope(TimelineStream* stream, 947 TimelineDurationScope::TimelineDurationScope(TimelineStream* stream,
1012 const char* label) 948 const char* label)
1013 : TimelineEventScope(stream, label) { 949 : TimelineEventScope(stream, label) {
1014 if (!FLAG_support_timeline || !enabled()) { 950 if (!FLAG_support_timeline || !enabled()) {
1015 return; 951 return;
1016 } 952 }
1017 #if defined(HOST_OS_FUCHSIA) 953 #if defined(HOST_OS_FUCHSIA)
1018 TRACE_DURATION_BEGIN("dart", label); 954 TRACE_DURATION_BEGIN("dart", label);
1019 #else 955 #else
1020 timestamp_ = OS::GetCurrentMonotonicMicros(); 956 timestamp_ = OS::GetCurrentMonotonicMicros();
1021 thread_timestamp_ = OS::GetCurrentThreadCPUMicros(); 957 thread_timestamp_ = OS::GetCurrentThreadCPUMicros();
1022 #endif 958 #endif
1023 } 959 }
1024 960
1025
1026 TimelineDurationScope::TimelineDurationScope(Thread* thread, 961 TimelineDurationScope::TimelineDurationScope(Thread* thread,
1027 TimelineStream* stream, 962 TimelineStream* stream,
1028 const char* label) 963 const char* label)
1029 : TimelineEventScope(thread, stream, label) { 964 : TimelineEventScope(thread, stream, label) {
1030 if (!FLAG_support_timeline || !enabled()) { 965 if (!FLAG_support_timeline || !enabled()) {
1031 return; 966 return;
1032 } 967 }
1033 #if defined(HOST_OS_FUCHSIA) 968 #if defined(HOST_OS_FUCHSIA)
1034 TRACE_DURATION_BEGIN("dart", label); 969 TRACE_DURATION_BEGIN("dart", label);
1035 #else 970 #else
1036 timestamp_ = OS::GetCurrentMonotonicMicros(); 971 timestamp_ = OS::GetCurrentMonotonicMicros();
1037 thread_timestamp_ = OS::GetCurrentThreadCPUMicros(); 972 thread_timestamp_ = OS::GetCurrentThreadCPUMicros();
1038 #endif 973 #endif
1039 } 974 }
1040 975
1041
1042 TimelineDurationScope::~TimelineDurationScope() { 976 TimelineDurationScope::~TimelineDurationScope() {
1043 if (!FLAG_support_timeline) { 977 if (!FLAG_support_timeline) {
1044 return; 978 return;
1045 } 979 }
1046 if (!ShouldEmitEvent()) { 980 if (!ShouldEmitEvent()) {
1047 return; 981 return;
1048 } 982 }
1049 #if defined(HOST_OS_FUCHSIA) 983 #if defined(HOST_OS_FUCHSIA)
1050 EmitFuchsiaEndEvent(label(), arguments(), arguments_length()); 984 EmitFuchsiaEndEvent(label(), arguments(), arguments_length());
1051 #else 985 #else
1052 TimelineEvent* event = stream()->StartEvent(); 986 TimelineEvent* event = stream()->StartEvent();
1053 if (event == NULL) { 987 if (event == NULL) {
1054 // Stream is now disabled. 988 // Stream is now disabled.
1055 return; 989 return;
1056 } 990 }
1057 ASSERT(event != NULL); 991 ASSERT(event != NULL);
1058 // Emit a duration event. 992 // Emit a duration event.
1059 event->Duration(label(), timestamp_, OS::GetCurrentMonotonicMicros(), 993 event->Duration(label(), timestamp_, OS::GetCurrentMonotonicMicros(),
1060 thread_timestamp_, OS::GetCurrentThreadCPUMicros()); 994 thread_timestamp_, OS::GetCurrentThreadCPUMicros());
1061 StealArguments(event); 995 StealArguments(event);
1062 event->Complete(); 996 event->Complete();
1063 #endif 997 #endif
1064 } 998 }
1065 999
1066
1067 TimelineBeginEndScope::TimelineBeginEndScope(TimelineStream* stream, 1000 TimelineBeginEndScope::TimelineBeginEndScope(TimelineStream* stream,
1068 const char* label) 1001 const char* label)
1069 : TimelineEventScope(stream, label) { 1002 : TimelineEventScope(stream, label) {
1070 if (!FLAG_support_timeline) { 1003 if (!FLAG_support_timeline) {
1071 return; 1004 return;
1072 } 1005 }
1073 EmitBegin(); 1006 EmitBegin();
1074 } 1007 }
1075 1008
1076
1077 TimelineBeginEndScope::TimelineBeginEndScope(Thread* thread, 1009 TimelineBeginEndScope::TimelineBeginEndScope(Thread* thread,
1078 TimelineStream* stream, 1010 TimelineStream* stream,
1079 const char* label) 1011 const char* label)
1080 : TimelineEventScope(thread, stream, label) { 1012 : TimelineEventScope(thread, stream, label) {
1081 if (!FLAG_support_timeline) { 1013 if (!FLAG_support_timeline) {
1082 return; 1014 return;
1083 } 1015 }
1084 EmitBegin(); 1016 EmitBegin();
1085 } 1017 }
1086 1018
1087
1088 TimelineBeginEndScope::~TimelineBeginEndScope() { 1019 TimelineBeginEndScope::~TimelineBeginEndScope() {
1089 if (!FLAG_support_timeline) { 1020 if (!FLAG_support_timeline) {
1090 return; 1021 return;
1091 } 1022 }
1092 EmitEnd(); 1023 EmitEnd();
1093 } 1024 }
1094 1025
1095
1096 void TimelineBeginEndScope::EmitBegin() { 1026 void TimelineBeginEndScope::EmitBegin() {
1097 if (!FLAG_support_timeline) { 1027 if (!FLAG_support_timeline) {
1098 return; 1028 return;
1099 } 1029 }
1100 if (!ShouldEmitEvent()) { 1030 if (!ShouldEmitEvent()) {
1101 return; 1031 return;
1102 } 1032 }
1103 TimelineEvent* event = stream()->StartEvent(); 1033 TimelineEvent* event = stream()->StartEvent();
1104 if (event == NULL) { 1034 if (event == NULL) {
1105 // Stream is now disabled. 1035 // Stream is now disabled.
1106 set_enabled(false); 1036 set_enabled(false);
1107 return; 1037 return;
1108 } 1038 }
1109 ASSERT(event != NULL); 1039 ASSERT(event != NULL);
1110 // Emit a begin event. 1040 // Emit a begin event.
1111 event->Begin(label()); 1041 event->Begin(label());
1112 event->Complete(); 1042 event->Complete();
1113 } 1043 }
1114 1044
1115
1116 void TimelineBeginEndScope::EmitEnd() { 1045 void TimelineBeginEndScope::EmitEnd() {
1117 if (!FLAG_support_timeline) { 1046 if (!FLAG_support_timeline) {
1118 return; 1047 return;
1119 } 1048 }
1120 if (!ShouldEmitEvent()) { 1049 if (!ShouldEmitEvent()) {
1121 return; 1050 return;
1122 } 1051 }
1123 TimelineEvent* event = stream()->StartEvent(); 1052 TimelineEvent* event = stream()->StartEvent();
1124 if (event == NULL) { 1053 if (event == NULL) {
1125 // Stream is now disabled. 1054 // Stream is now disabled.
1126 set_enabled(false); 1055 set_enabled(false);
1127 return; 1056 return;
1128 } 1057 }
1129 ASSERT(event != NULL); 1058 ASSERT(event != NULL);
1130 // Emit an end event. 1059 // Emit an end event.
1131 event->End(label()); 1060 event->End(label());
1132 StealArguments(event); 1061 StealArguments(event);
1133 event->Complete(); 1062 event->Complete();
1134 } 1063 }
1135 1064
1136
1137 TimelineEventFilter::TimelineEventFilter(int64_t time_origin_micros, 1065 TimelineEventFilter::TimelineEventFilter(int64_t time_origin_micros,
1138 int64_t time_extent_micros) 1066 int64_t time_extent_micros)
1139 : time_origin_micros_(time_origin_micros), 1067 : time_origin_micros_(time_origin_micros),
1140 time_extent_micros_(time_extent_micros) { 1068 time_extent_micros_(time_extent_micros) {
1141 ASSERT(time_origin_micros_ >= -1); 1069 ASSERT(time_origin_micros_ >= -1);
1142 ASSERT(time_extent_micros_ >= -1); 1070 ASSERT(time_extent_micros_ >= -1);
1143 } 1071 }
1144 1072
1145
1146 TimelineEventFilter::~TimelineEventFilter() {} 1073 TimelineEventFilter::~TimelineEventFilter() {}
1147 1074
1148
1149 IsolateTimelineEventFilter::IsolateTimelineEventFilter( 1075 IsolateTimelineEventFilter::IsolateTimelineEventFilter(
1150 Dart_Port isolate_id, 1076 Dart_Port isolate_id,
1151 int64_t time_origin_micros, 1077 int64_t time_origin_micros,
1152 int64_t time_extent_micros) 1078 int64_t time_extent_micros)
1153 : TimelineEventFilter(time_origin_micros, time_extent_micros), 1079 : TimelineEventFilter(time_origin_micros, time_extent_micros),
1154 isolate_id_(isolate_id) {} 1080 isolate_id_(isolate_id) {}
1155 1081
1156
1157 TimelineEventRecorder::TimelineEventRecorder() 1082 TimelineEventRecorder::TimelineEventRecorder()
1158 : async_id_(0), time_low_micros_(0), time_high_micros_(0) {} 1083 : async_id_(0), time_low_micros_(0), time_high_micros_(0) {}
1159 1084
1160
1161 void TimelineEventRecorder::PrintJSONMeta(JSONArray* events) const { 1085 void TimelineEventRecorder::PrintJSONMeta(JSONArray* events) const {
1162 if (!FLAG_support_service) { 1086 if (!FLAG_support_service) {
1163 return; 1087 return;
1164 } 1088 }
1165 OSThreadIterator it; 1089 OSThreadIterator it;
1166 while (it.HasNext()) { 1090 while (it.HasNext()) {
1167 OSThread* thread = it.Next(); 1091 OSThread* thread = it.Next();
1168 const char* thread_name = thread->name(); 1092 const char* thread_name = thread->name();
1169 if (thread_name == NULL) { 1093 if (thread_name == NULL) {
1170 // Only emit a thread name if one was set. 1094 // Only emit a thread name if one was set.
1171 continue; 1095 continue;
1172 } 1096 }
1173 JSONObject obj(events); 1097 JSONObject obj(events);
1174 int64_t pid = OS::ProcessId(); 1098 int64_t pid = OS::ProcessId();
1175 int64_t tid = OSThread::ThreadIdToIntPtr(thread->trace_id()); 1099 int64_t tid = OSThread::ThreadIdToIntPtr(thread->trace_id());
1176 obj.AddProperty("name", "thread_name"); 1100 obj.AddProperty("name", "thread_name");
1177 obj.AddProperty("ph", "M"); 1101 obj.AddProperty("ph", "M");
1178 obj.AddProperty64("pid", pid); 1102 obj.AddProperty64("pid", pid);
1179 obj.AddProperty64("tid", tid); 1103 obj.AddProperty64("tid", tid);
1180 { 1104 {
1181 JSONObject args(&obj, "args"); 1105 JSONObject args(&obj, "args");
1182 args.AddPropertyF("name", "%s (%" Pd64 ")", thread_name, tid); 1106 args.AddPropertyF("name", "%s (%" Pd64 ")", thread_name, tid);
1183 } 1107 }
1184 } 1108 }
1185 } 1109 }
1186 1110
1187
1188 TimelineEvent* TimelineEventRecorder::ThreadBlockStartEvent() { 1111 TimelineEvent* TimelineEventRecorder::ThreadBlockStartEvent() {
1189 // Grab the current thread. 1112 // Grab the current thread.
1190 OSThread* thread = OSThread::Current(); 1113 OSThread* thread = OSThread::Current();
1191 ASSERT(thread != NULL); 1114 ASSERT(thread != NULL);
1192 Mutex* thread_block_lock = thread->timeline_block_lock(); 1115 Mutex* thread_block_lock = thread->timeline_block_lock();
1193 ASSERT(thread_block_lock != NULL); 1116 ASSERT(thread_block_lock != NULL);
1194 // We are accessing the thread's timeline block- so take the lock here. 1117 // We are accessing the thread's timeline block- so take the lock here.
1195 // This lock will be held until the call to |CompleteEvent| is made. 1118 // This lock will be held until the call to |CompleteEvent| is made.
1196 thread_block_lock->Lock(); 1119 thread_block_lock->Lock();
1197 #if defined(DEBUG) 1120 #if defined(DEBUG)
(...skipping 28 matching lines...) Expand all
1226 // Drop lock here as no event is being handed out. 1149 // Drop lock here as no event is being handed out.
1227 #if defined(DEBUG) 1150 #if defined(DEBUG)
1228 if (T != NULL) { 1151 if (T != NULL) {
1229 T->DecrementNoSafepointScopeDepth(); 1152 T->DecrementNoSafepointScopeDepth();
1230 } 1153 }
1231 #endif // defined(DEBUG) 1154 #endif // defined(DEBUG)
1232 thread_block_lock->Unlock(); 1155 thread_block_lock->Unlock();
1233 return NULL; 1156 return NULL;
1234 } 1157 }
1235 1158
1236
1237 void TimelineEventRecorder::ResetTimeTracking() { 1159 void TimelineEventRecorder::ResetTimeTracking() {
1238 time_high_micros_ = 0; 1160 time_high_micros_ = 0;
1239 time_low_micros_ = kMaxInt64; 1161 time_low_micros_ = kMaxInt64;
1240 } 1162 }
1241 1163
1242
1243 void TimelineEventRecorder::ReportTime(int64_t micros) { 1164 void TimelineEventRecorder::ReportTime(int64_t micros) {
1244 if (time_high_micros_ < micros) { 1165 if (time_high_micros_ < micros) {
1245 time_high_micros_ = micros; 1166 time_high_micros_ = micros;
1246 } 1167 }
1247 if (time_low_micros_ > micros) { 1168 if (time_low_micros_ > micros) {
1248 time_low_micros_ = micros; 1169 time_low_micros_ = micros;
1249 } 1170 }
1250 } 1171 }
1251 1172
1252
1253 int64_t TimelineEventRecorder::TimeOriginMicros() const { 1173 int64_t TimelineEventRecorder::TimeOriginMicros() const {
1254 if (time_high_micros_ == 0) { 1174 if (time_high_micros_ == 0) {
1255 return 0; 1175 return 0;
1256 } 1176 }
1257 return time_low_micros_; 1177 return time_low_micros_;
1258 } 1178 }
1259 1179
1260
1261 int64_t TimelineEventRecorder::TimeExtentMicros() const { 1180 int64_t TimelineEventRecorder::TimeExtentMicros() const {
1262 if (time_high_micros_ == 0) { 1181 if (time_high_micros_ == 0) {
1263 return 0; 1182 return 0;
1264 } 1183 }
1265 return time_high_micros_ - time_low_micros_; 1184 return time_high_micros_ - time_low_micros_;
1266 } 1185 }
1267 1186
1268
1269 void TimelineEventRecorder::ThreadBlockCompleteEvent(TimelineEvent* event) { 1187 void TimelineEventRecorder::ThreadBlockCompleteEvent(TimelineEvent* event) {
1270 if (event == NULL) { 1188 if (event == NULL) {
1271 return; 1189 return;
1272 } 1190 }
1273 // Grab the current thread. 1191 // Grab the current thread.
1274 OSThread* thread = OSThread::Current(); 1192 OSThread* thread = OSThread::Current();
1275 ASSERT(thread != NULL); 1193 ASSERT(thread != NULL);
1276 // Unlock the thread's block lock. 1194 // Unlock the thread's block lock.
1277 Mutex* thread_block_lock = thread->timeline_block_lock(); 1195 Mutex* thread_block_lock = thread->timeline_block_lock();
1278 ASSERT(thread_block_lock != NULL); 1196 ASSERT(thread_block_lock != NULL);
1279 #if defined(DEBUG) 1197 #if defined(DEBUG)
1280 Thread* T = Thread::Current(); 1198 Thread* T = Thread::Current();
1281 if (T != NULL) { 1199 if (T != NULL) {
1282 T->DecrementNoSafepointScopeDepth(); 1200 T->DecrementNoSafepointScopeDepth();
1283 } 1201 }
1284 #endif // defined(DEBUG) 1202 #endif // defined(DEBUG)
1285 thread_block_lock->Unlock(); 1203 thread_block_lock->Unlock();
1286 } 1204 }
1287 1205
1288
1289 void TimelineEventRecorder::WriteTo(const char* directory) { 1206 void TimelineEventRecorder::WriteTo(const char* directory) {
1290 if (!FLAG_support_service) { 1207 if (!FLAG_support_service) {
1291 return; 1208 return;
1292 } 1209 }
1293 Dart_FileOpenCallback file_open = Dart::file_open_callback(); 1210 Dart_FileOpenCallback file_open = Dart::file_open_callback();
1294 Dart_FileWriteCallback file_write = Dart::file_write_callback(); 1211 Dart_FileWriteCallback file_write = Dart::file_write_callback();
1295 Dart_FileCloseCallback file_close = Dart::file_close_callback(); 1212 Dart_FileCloseCallback file_close = Dart::file_close_callback();
1296 if ((file_open == NULL) || (file_write == NULL) || (file_close == NULL)) { 1213 if ((file_open == NULL) || (file_write == NULL) || (file_close == NULL)) {
1297 return; 1214 return;
1298 } 1215 }
(...skipping 19 matching lines...) Expand all
1318 intptr_t output_length = 0; 1235 intptr_t output_length = 0;
1319 js.Steal(&output, &output_length); 1236 js.Steal(&output, &output_length);
1320 (*file_write)(output, output_length, file); 1237 (*file_write)(output, output_length, file);
1321 // Free the stolen output. 1238 // Free the stolen output.
1322 free(output); 1239 free(output);
1323 (*file_close)(file); 1240 (*file_close)(file);
1324 1241
1325 return; 1242 return;
1326 } 1243 }
1327 1244
1328
1329 int64_t TimelineEventRecorder::GetNextAsyncId() { 1245 int64_t TimelineEventRecorder::GetNextAsyncId() {
1330 // TODO(johnmccutchan): Gracefully handle wrap around. 1246 // TODO(johnmccutchan): Gracefully handle wrap around.
1331 uint32_t next = 1247 uint32_t next =
1332 static_cast<uint32_t>(AtomicOperations::FetchAndIncrement(&async_id_)); 1248 static_cast<uint32_t>(AtomicOperations::FetchAndIncrement(&async_id_));
1333 return static_cast<int64_t>(next); 1249 return static_cast<int64_t>(next);
1334 } 1250 }
1335 1251
1336
1337 void TimelineEventRecorder::FinishBlock(TimelineEventBlock* block) { 1252 void TimelineEventRecorder::FinishBlock(TimelineEventBlock* block) {
1338 if (block == NULL) { 1253 if (block == NULL) {
1339 return; 1254 return;
1340 } 1255 }
1341 MutexLocker ml(&lock_); 1256 MutexLocker ml(&lock_);
1342 block->Finish(); 1257 block->Finish();
1343 } 1258 }
1344 1259
1345
1346 TimelineEventBlock* TimelineEventRecorder::GetNewBlock() { 1260 TimelineEventBlock* TimelineEventRecorder::GetNewBlock() {
1347 MutexLocker ml(&lock_); 1261 MutexLocker ml(&lock_);
1348 return GetNewBlockLocked(); 1262 return GetNewBlockLocked();
1349 } 1263 }
1350 1264
1351
1352 TimelineEventFixedBufferRecorder::TimelineEventFixedBufferRecorder( 1265 TimelineEventFixedBufferRecorder::TimelineEventFixedBufferRecorder(
1353 intptr_t capacity) 1266 intptr_t capacity)
1354 : blocks_(NULL), capacity_(capacity), num_blocks_(0), block_cursor_(0) { 1267 : blocks_(NULL), capacity_(capacity), num_blocks_(0), block_cursor_(0) {
1355 // Capacity must be a multiple of TimelineEventBlock::kBlockSize 1268 // Capacity must be a multiple of TimelineEventBlock::kBlockSize
1356 ASSERT((capacity % TimelineEventBlock::kBlockSize) == 0); 1269 ASSERT((capacity % TimelineEventBlock::kBlockSize) == 0);
1357 // Allocate blocks array. 1270 // Allocate blocks array.
1358 num_blocks_ = capacity / TimelineEventBlock::kBlockSize; 1271 num_blocks_ = capacity / TimelineEventBlock::kBlockSize;
1359 blocks_ = reinterpret_cast<TimelineEventBlock**>( 1272 blocks_ = reinterpret_cast<TimelineEventBlock**>(
1360 calloc(num_blocks_, sizeof(TimelineEventBlock*))); 1273 calloc(num_blocks_, sizeof(TimelineEventBlock*)));
1361 // Allocate each block. 1274 // Allocate each block.
1362 for (intptr_t i = 0; i < num_blocks_; i++) { 1275 for (intptr_t i = 0; i < num_blocks_; i++) {
1363 blocks_[i] = new TimelineEventBlock(i); 1276 blocks_[i] = new TimelineEventBlock(i);
1364 } 1277 }
1365 // Chain blocks together. 1278 // Chain blocks together.
1366 for (intptr_t i = 0; i < num_blocks_ - 1; i++) { 1279 for (intptr_t i = 0; i < num_blocks_ - 1; i++) {
1367 blocks_[i]->set_next(blocks_[i + 1]); 1280 blocks_[i]->set_next(blocks_[i + 1]);
1368 } 1281 }
1369 } 1282 }
1370 1283
1371
1372 TimelineEventFixedBufferRecorder::~TimelineEventFixedBufferRecorder() { 1284 TimelineEventFixedBufferRecorder::~TimelineEventFixedBufferRecorder() {
1373 // Delete all blocks. 1285 // Delete all blocks.
1374 for (intptr_t i = 0; i < num_blocks_; i++) { 1286 for (intptr_t i = 0; i < num_blocks_; i++) {
1375 TimelineEventBlock* block = blocks_[i]; 1287 TimelineEventBlock* block = blocks_[i];
1376 delete block; 1288 delete block;
1377 } 1289 }
1378 free(blocks_); 1290 free(blocks_);
1379 } 1291 }
1380 1292
1381
1382 void TimelineEventFixedBufferRecorder::PrintJSONEvents( 1293 void TimelineEventFixedBufferRecorder::PrintJSONEvents(
1383 JSONArray* events, 1294 JSONArray* events,
1384 TimelineEventFilter* filter) { 1295 TimelineEventFilter* filter) {
1385 if (!FLAG_support_service) { 1296 if (!FLAG_support_service) {
1386 return; 1297 return;
1387 } 1298 }
1388 MutexLocker ml(&lock_); 1299 MutexLocker ml(&lock_);
1389 ResetTimeTracking(); 1300 ResetTimeTracking();
1390 intptr_t block_offset = FindOldestBlockIndex(); 1301 intptr_t block_offset = FindOldestBlockIndex();
1391 if (block_offset == -1) { 1302 if (block_offset == -1) {
(...skipping 12 matching lines...) Expand all
1404 event->Within(filter->time_origin_micros(), 1315 event->Within(filter->time_origin_micros(),
1405 filter->time_extent_micros())) { 1316 filter->time_extent_micros())) {
1406 ReportTime(event->LowTime()); 1317 ReportTime(event->LowTime());
1407 ReportTime(event->HighTime()); 1318 ReportTime(event->HighTime());
1408 events->AddValue(event); 1319 events->AddValue(event);
1409 } 1320 }
1410 } 1321 }
1411 } 1322 }
1412 } 1323 }
1413 1324
1414
1415 void TimelineEventFixedBufferRecorder::PrintJSON(JSONStream* js, 1325 void TimelineEventFixedBufferRecorder::PrintJSON(JSONStream* js,
1416 TimelineEventFilter* filter) { 1326 TimelineEventFilter* filter) {
1417 if (!FLAG_support_service) { 1327 if (!FLAG_support_service) {
1418 return; 1328 return;
1419 } 1329 }
1420 JSONObject topLevel(js); 1330 JSONObject topLevel(js);
1421 topLevel.AddProperty("type", "_Timeline"); 1331 topLevel.AddProperty("type", "_Timeline");
1422 { 1332 {
1423 JSONArray events(&topLevel, "traceEvents"); 1333 JSONArray events(&topLevel, "traceEvents");
1424 PrintJSONMeta(&events); 1334 PrintJSONMeta(&events);
1425 PrintJSONEvents(&events, filter); 1335 PrintJSONEvents(&events, filter);
1426 } 1336 }
1427 topLevel.AddPropertyTimeMicros("timeOriginMicros", TimeOriginMicros()); 1337 topLevel.AddPropertyTimeMicros("timeOriginMicros", TimeOriginMicros());
1428 topLevel.AddPropertyTimeMicros("timeExtentMicros", TimeExtentMicros()); 1338 topLevel.AddPropertyTimeMicros("timeExtentMicros", TimeExtentMicros());
1429 } 1339 }
1430 1340
1431
1432 void TimelineEventFixedBufferRecorder::PrintTraceEvent( 1341 void TimelineEventFixedBufferRecorder::PrintTraceEvent(
1433 JSONStream* js, 1342 JSONStream* js,
1434 TimelineEventFilter* filter) { 1343 TimelineEventFilter* filter) {
1435 if (!FLAG_support_service) { 1344 if (!FLAG_support_service) {
1436 return; 1345 return;
1437 } 1346 }
1438 JSONArray events(js); 1347 JSONArray events(js);
1439 PrintJSONMeta(&events); 1348 PrintJSONMeta(&events);
1440 PrintJSONEvents(&events, filter); 1349 PrintJSONEvents(&events, filter);
1441 } 1350 }
1442 1351
1443
1444 TimelineEventBlock* TimelineEventFixedBufferRecorder::GetHeadBlockLocked() { 1352 TimelineEventBlock* TimelineEventFixedBufferRecorder::GetHeadBlockLocked() {
1445 return blocks_[0]; 1353 return blocks_[0];
1446 } 1354 }
1447 1355
1448
1449 void TimelineEventFixedBufferRecorder::Clear() { 1356 void TimelineEventFixedBufferRecorder::Clear() {
1450 MutexLocker ml(&lock_); 1357 MutexLocker ml(&lock_);
1451 for (intptr_t i = 0; i < num_blocks_; i++) { 1358 for (intptr_t i = 0; i < num_blocks_; i++) {
1452 TimelineEventBlock* block = blocks_[i]; 1359 TimelineEventBlock* block = blocks_[i];
1453 block->Reset(); 1360 block->Reset();
1454 } 1361 }
1455 } 1362 }
1456 1363
1457
1458 intptr_t TimelineEventFixedBufferRecorder::FindOldestBlockIndex() const { 1364 intptr_t TimelineEventFixedBufferRecorder::FindOldestBlockIndex() const {
1459 int64_t earliest_time = kMaxInt64; 1365 int64_t earliest_time = kMaxInt64;
1460 intptr_t earliest_index = -1; 1366 intptr_t earliest_index = -1;
1461 for (intptr_t block_idx = 0; block_idx < num_blocks_; block_idx++) { 1367 for (intptr_t block_idx = 0; block_idx < num_blocks_; block_idx++) {
1462 TimelineEventBlock* block = blocks_[block_idx]; 1368 TimelineEventBlock* block = blocks_[block_idx];
1463 if (block->IsEmpty()) { 1369 if (block->IsEmpty()) {
1464 // Skip empty blocks. 1370 // Skip empty blocks.
1465 continue; 1371 continue;
1466 } 1372 }
1467 if (block->LowerTimeBound() < earliest_time) { 1373 if (block->LowerTimeBound() < earliest_time) {
1468 earliest_time = block->LowerTimeBound(); 1374 earliest_time = block->LowerTimeBound();
1469 earliest_index = block_idx; 1375 earliest_index = block_idx;
1470 } 1376 }
1471 } 1377 }
1472 return earliest_index; 1378 return earliest_index;
1473 } 1379 }
1474 1380
1475
1476 TimelineEvent* TimelineEventFixedBufferRecorder::StartEvent() { 1381 TimelineEvent* TimelineEventFixedBufferRecorder::StartEvent() {
1477 return ThreadBlockStartEvent(); 1382 return ThreadBlockStartEvent();
1478 } 1383 }
1479 1384
1480
1481 void TimelineEventFixedBufferRecorder::CompleteEvent(TimelineEvent* event) { 1385 void TimelineEventFixedBufferRecorder::CompleteEvent(TimelineEvent* event) {
1482 if (event == NULL) { 1386 if (event == NULL) {
1483 return; 1387 return;
1484 } 1388 }
1485 ThreadBlockCompleteEvent(event); 1389 ThreadBlockCompleteEvent(event);
1486 } 1390 }
1487 1391
1488
1489 TimelineEventSystraceRecorder::TimelineEventSystraceRecorder(intptr_t capacity) 1392 TimelineEventSystraceRecorder::TimelineEventSystraceRecorder(intptr_t capacity)
1490 : TimelineEventFixedBufferRecorder(capacity), systrace_fd_(-1) { 1393 : TimelineEventFixedBufferRecorder(capacity), systrace_fd_(-1) {
1491 #if defined(HOST_OS_ANDROID) || defined(HOST_OS_LINUX) 1394 #if defined(HOST_OS_ANDROID) || defined(HOST_OS_LINUX)
1492 const char* kSystracePath = "/sys/kernel/debug/tracing/trace_marker"; 1395 const char* kSystracePath = "/sys/kernel/debug/tracing/trace_marker";
1493 systrace_fd_ = open(kSystracePath, O_WRONLY); 1396 systrace_fd_ = open(kSystracePath, O_WRONLY);
1494 if ((systrace_fd_ < 0) && FLAG_trace_timeline) { 1397 if ((systrace_fd_ < 0) && FLAG_trace_timeline) {
1495 OS::PrintErr("TimelineEventSystraceRecorder: Could not open `%s`\n", 1398 OS::PrintErr("TimelineEventSystraceRecorder: Could not open `%s`\n",
1496 kSystracePath); 1399 kSystracePath);
1497 } 1400 }
1498 #else 1401 #else
1499 OS::PrintErr( 1402 OS::PrintErr(
1500 "Warning: The systrace timeline recorder is equivalent to the" 1403 "Warning: The systrace timeline recorder is equivalent to the"
1501 "ring recorder on this platform."); 1404 "ring recorder on this platform.");
1502 #endif 1405 #endif
1503 } 1406 }
1504 1407
1505
1506 TimelineEventSystraceRecorder::~TimelineEventSystraceRecorder() { 1408 TimelineEventSystraceRecorder::~TimelineEventSystraceRecorder() {
1507 #if defined(HOST_OS_ANDROID) || defined(HOST_OS_LINUX) 1409 #if defined(HOST_OS_ANDROID) || defined(HOST_OS_LINUX)
1508 if (systrace_fd_ >= 0) { 1410 if (systrace_fd_ >= 0) {
1509 close(systrace_fd_); 1411 close(systrace_fd_);
1510 } 1412 }
1511 #endif 1413 #endif
1512 } 1414 }
1513 1415
1514
1515 TimelineEventBlock* TimelineEventSystraceRecorder::GetNewBlockLocked() { 1416 TimelineEventBlock* TimelineEventSystraceRecorder::GetNewBlockLocked() {
1516 // TODO(johnmccutchan): This function should only hand out blocks 1417 // TODO(johnmccutchan): This function should only hand out blocks
1517 // which have been marked as finished. 1418 // which have been marked as finished.
1518 if (block_cursor_ == num_blocks_) { 1419 if (block_cursor_ == num_blocks_) {
1519 block_cursor_ = 0; 1420 block_cursor_ = 0;
1520 } 1421 }
1521 TimelineEventBlock* block = blocks_[block_cursor_++]; 1422 TimelineEventBlock* block = blocks_[block_cursor_++];
1522 block->Reset(); 1423 block->Reset();
1523 block->Open(); 1424 block->Open();
1524 return block; 1425 return block;
1525 } 1426 }
1526 1427
1527
1528 void TimelineEventSystraceRecorder::CompleteEvent(TimelineEvent* event) { 1428 void TimelineEventSystraceRecorder::CompleteEvent(TimelineEvent* event) {
1529 if (event == NULL) { 1429 if (event == NULL) {
1530 return; 1430 return;
1531 } 1431 }
1532 #if defined(HOST_OS_ANDROID) || defined(HOST_OS_LINUX) 1432 #if defined(HOST_OS_ANDROID) || defined(HOST_OS_LINUX)
1533 if (systrace_fd_ >= 0) { 1433 if (systrace_fd_ >= 0) {
1534 // Serialize to the systrace format. 1434 // Serialize to the systrace format.
1535 const intptr_t kBufferLength = 1024; 1435 const intptr_t kBufferLength = 1024;
1536 char buffer[kBufferLength]; 1436 char buffer[kBufferLength];
1537 const intptr_t event_length = 1437 const intptr_t event_length =
1538 event->PrintSystrace(&buffer[0], kBufferLength); 1438 event->PrintSystrace(&buffer[0], kBufferLength);
1539 if (event_length > 0) { 1439 if (event_length > 0) {
1540 ssize_t __result; 1440 ssize_t __result;
1541 // Repeatedly attempt the write while we are being interrupted. 1441 // Repeatedly attempt the write while we are being interrupted.
1542 do { 1442 do {
1543 __result = write(systrace_fd_, buffer, event_length); 1443 __result = write(systrace_fd_, buffer, event_length);
1544 } while ((__result == -1L) && (errno == EINTR)); 1444 } while ((__result == -1L) && (errno == EINTR));
1545 } 1445 }
1546 } 1446 }
1547 #endif 1447 #endif
1548 ThreadBlockCompleteEvent(event); 1448 ThreadBlockCompleteEvent(event);
1549 } 1449 }
1550 1450
1551
1552 #if defined(HOST_OS_FUCHSIA) 1451 #if defined(HOST_OS_FUCHSIA)
1553 TimelineEventFuchsiaRecorder::TimelineEventFuchsiaRecorder(intptr_t capacity) 1452 TimelineEventFuchsiaRecorder::TimelineEventFuchsiaRecorder(intptr_t capacity)
1554 : TimelineEventFixedBufferRecorder(capacity) {} 1453 : TimelineEventFixedBufferRecorder(capacity) {}
1555 1454
1556 1455
1557 TimelineEventBlock* TimelineEventFuchsiaRecorder::GetNewBlockLocked() { 1456 TimelineEventBlock* TimelineEventFuchsiaRecorder::GetNewBlockLocked() {
1558 // TODO(johnmccutchan): This function should only hand out blocks 1457 // TODO(johnmccutchan): This function should only hand out blocks
1559 // which have been marked as finished. 1458 // which have been marked as finished.
1560 if (block_cursor_ == num_blocks_) { 1459 if (block_cursor_ == num_blocks_) {
1561 block_cursor_ = 0; 1460 block_cursor_ = 0;
1562 } 1461 }
1563 TimelineEventBlock* block = blocks_[block_cursor_++]; 1462 TimelineEventBlock* block = blocks_[block_cursor_++];
1564 block->Reset(); 1463 block->Reset();
1565 block->Open(); 1464 block->Open();
1566 return block; 1465 return block;
1567 } 1466 }
1568 1467
1569
1570 void TimelineEventFuchsiaRecorder::CompleteEvent(TimelineEvent* event) { 1468 void TimelineEventFuchsiaRecorder::CompleteEvent(TimelineEvent* event) {
1571 if (event == NULL) { 1469 if (event == NULL) {
1572 return; 1470 return;
1573 } 1471 }
1574 event->EmitFuchsiaEvent(); 1472 event->EmitFuchsiaEvent();
1575 ThreadBlockCompleteEvent(event); 1473 ThreadBlockCompleteEvent(event);
1576 } 1474 }
1577 #endif // defined(HOST_OS_FUCHSIA) 1475 #endif // defined(HOST_OS_FUCHSIA)
1578 1476
1579
1580 TimelineEventBlock* TimelineEventRingRecorder::GetNewBlockLocked() { 1477 TimelineEventBlock* TimelineEventRingRecorder::GetNewBlockLocked() {
1581 // TODO(johnmccutchan): This function should only hand out blocks 1478 // TODO(johnmccutchan): This function should only hand out blocks
1582 // which have been marked as finished. 1479 // which have been marked as finished.
1583 if (block_cursor_ == num_blocks_) { 1480 if (block_cursor_ == num_blocks_) {
1584 block_cursor_ = 0; 1481 block_cursor_ = 0;
1585 } 1482 }
1586 TimelineEventBlock* block = blocks_[block_cursor_++]; 1483 TimelineEventBlock* block = blocks_[block_cursor_++];
1587 block->Reset(); 1484 block->Reset();
1588 block->Open(); 1485 block->Open();
1589 return block; 1486 return block;
1590 } 1487 }
1591 1488
1592
1593 TimelineEventBlock* TimelineEventStartupRecorder::GetNewBlockLocked() { 1489 TimelineEventBlock* TimelineEventStartupRecorder::GetNewBlockLocked() {
1594 if (block_cursor_ == num_blocks_) { 1490 if (block_cursor_ == num_blocks_) {
1595 return NULL; 1491 return NULL;
1596 } 1492 }
1597 TimelineEventBlock* block = blocks_[block_cursor_++]; 1493 TimelineEventBlock* block = blocks_[block_cursor_++];
1598 block->Reset(); 1494 block->Reset();
1599 block->Open(); 1495 block->Open();
1600 return block; 1496 return block;
1601 } 1497 }
1602 1498
1603
1604 TimelineEventCallbackRecorder::TimelineEventCallbackRecorder() {} 1499 TimelineEventCallbackRecorder::TimelineEventCallbackRecorder() {}
1605 1500
1606
1607 TimelineEventCallbackRecorder::~TimelineEventCallbackRecorder() {} 1501 TimelineEventCallbackRecorder::~TimelineEventCallbackRecorder() {}
1608 1502
1609
1610 void TimelineEventCallbackRecorder::PrintJSON(JSONStream* js, 1503 void TimelineEventCallbackRecorder::PrintJSON(JSONStream* js,
1611 TimelineEventFilter* filter) { 1504 TimelineEventFilter* filter) {
1612 if (!FLAG_support_service) { 1505 if (!FLAG_support_service) {
1613 return; 1506 return;
1614 } 1507 }
1615 JSONObject topLevel(js); 1508 JSONObject topLevel(js);
1616 topLevel.AddProperty("type", "_Timeline"); 1509 topLevel.AddProperty("type", "_Timeline");
1617 { 1510 {
1618 JSONArray events(&topLevel, "traceEvents"); 1511 JSONArray events(&topLevel, "traceEvents");
1619 PrintJSONMeta(&events); 1512 PrintJSONMeta(&events);
1620 } 1513 }
1621 } 1514 }
1622 1515
1623
1624 void TimelineEventCallbackRecorder::PrintTraceEvent( 1516 void TimelineEventCallbackRecorder::PrintTraceEvent(
1625 JSONStream* js, 1517 JSONStream* js,
1626 TimelineEventFilter* filter) { 1518 TimelineEventFilter* filter) {
1627 if (!FLAG_support_service) { 1519 if (!FLAG_support_service) {
1628 return; 1520 return;
1629 } 1521 }
1630 JSONArray events(js); 1522 JSONArray events(js);
1631 } 1523 }
1632 1524
1633
1634 TimelineEvent* TimelineEventCallbackRecorder::StartEvent() { 1525 TimelineEvent* TimelineEventCallbackRecorder::StartEvent() {
1635 TimelineEvent* event = new TimelineEvent(); 1526 TimelineEvent* event = new TimelineEvent();
1636 return event; 1527 return event;
1637 } 1528 }
1638 1529
1639
1640 void TimelineEventCallbackRecorder::CompleteEvent(TimelineEvent* event) { 1530 void TimelineEventCallbackRecorder::CompleteEvent(TimelineEvent* event) {
1641 OnEvent(event); 1531 OnEvent(event);
1642 delete event; 1532 delete event;
1643 } 1533 }
1644 1534
1645
1646 TimelineEventEndlessRecorder::TimelineEventEndlessRecorder() 1535 TimelineEventEndlessRecorder::TimelineEventEndlessRecorder()
1647 : head_(NULL), block_index_(0) {} 1536 : head_(NULL), block_index_(0) {}
1648 1537
1649 TimelineEventEndlessRecorder::~TimelineEventEndlessRecorder() { 1538 TimelineEventEndlessRecorder::~TimelineEventEndlessRecorder() {
1650 TimelineEventBlock* current = head_; 1539 TimelineEventBlock* current = head_;
1651 head_ = NULL; 1540 head_ = NULL;
1652 1541
1653 while (current != NULL) { 1542 while (current != NULL) {
1654 TimelineEventBlock* next = current->next(); 1543 TimelineEventBlock* next = current->next();
1655 delete current; 1544 delete current;
(...skipping 10 matching lines...) Expand all
1666 topLevel.AddProperty("type", "_Timeline"); 1555 topLevel.AddProperty("type", "_Timeline");
1667 { 1556 {
1668 JSONArray events(&topLevel, "traceEvents"); 1557 JSONArray events(&topLevel, "traceEvents");
1669 PrintJSONMeta(&events); 1558 PrintJSONMeta(&events);
1670 PrintJSONEvents(&events, filter); 1559 PrintJSONEvents(&events, filter);
1671 } 1560 }
1672 topLevel.AddPropertyTimeMicros("timeOriginMicros", TimeOriginMicros()); 1561 topLevel.AddPropertyTimeMicros("timeOriginMicros", TimeOriginMicros());
1673 topLevel.AddPropertyTimeMicros("timeExtentMicros", TimeExtentMicros()); 1562 topLevel.AddPropertyTimeMicros("timeExtentMicros", TimeExtentMicros());
1674 } 1563 }
1675 1564
1676
1677 void TimelineEventEndlessRecorder::PrintTraceEvent( 1565 void TimelineEventEndlessRecorder::PrintTraceEvent(
1678 JSONStream* js, 1566 JSONStream* js,
1679 TimelineEventFilter* filter) { 1567 TimelineEventFilter* filter) {
1680 if (!FLAG_support_service) { 1568 if (!FLAG_support_service) {
1681 return; 1569 return;
1682 } 1570 }
1683 JSONArray events(js); 1571 JSONArray events(js);
1684 PrintJSONMeta(&events); 1572 PrintJSONMeta(&events);
1685 PrintJSONEvents(&events, filter); 1573 PrintJSONEvents(&events, filter);
1686 } 1574 }
1687 1575
1688
1689 TimelineEventBlock* TimelineEventEndlessRecorder::GetHeadBlockLocked() { 1576 TimelineEventBlock* TimelineEventEndlessRecorder::GetHeadBlockLocked() {
1690 return head_; 1577 return head_;
1691 } 1578 }
1692 1579
1693
1694 TimelineEvent* TimelineEventEndlessRecorder::StartEvent() { 1580 TimelineEvent* TimelineEventEndlessRecorder::StartEvent() {
1695 return ThreadBlockStartEvent(); 1581 return ThreadBlockStartEvent();
1696 } 1582 }
1697 1583
1698
1699 void TimelineEventEndlessRecorder::CompleteEvent(TimelineEvent* event) { 1584 void TimelineEventEndlessRecorder::CompleteEvent(TimelineEvent* event) {
1700 if (event == NULL) { 1585 if (event == NULL) {
1701 return; 1586 return;
1702 } 1587 }
1703 ThreadBlockCompleteEvent(event); 1588 ThreadBlockCompleteEvent(event);
1704 } 1589 }
1705 1590
1706
1707 TimelineEventBlock* TimelineEventEndlessRecorder::GetNewBlockLocked() { 1591 TimelineEventBlock* TimelineEventEndlessRecorder::GetNewBlockLocked() {
1708 TimelineEventBlock* block = new TimelineEventBlock(block_index_++); 1592 TimelineEventBlock* block = new TimelineEventBlock(block_index_++);
1709 block->set_next(head_); 1593 block->set_next(head_);
1710 block->Open(); 1594 block->Open();
1711 head_ = block; 1595 head_ = block;
1712 if (FLAG_trace_timeline) { 1596 if (FLAG_trace_timeline) {
1713 OS::Print("Created new block %p\n", block); 1597 OS::Print("Created new block %p\n", block);
1714 } 1598 }
1715 return head_; 1599 return head_;
1716 } 1600 }
1717 1601
1718 static int TimelineEventBlockCompare(TimelineEventBlock* const* a, 1602 static int TimelineEventBlockCompare(TimelineEventBlock* const* a,
1719 TimelineEventBlock* const* b) { 1603 TimelineEventBlock* const* b) {
1720 return (*a)->LowerTimeBound() - (*b)->LowerTimeBound(); 1604 return (*a)->LowerTimeBound() - (*b)->LowerTimeBound();
1721 } 1605 }
1722 1606
1723
1724 void TimelineEventEndlessRecorder::PrintJSONEvents( 1607 void TimelineEventEndlessRecorder::PrintJSONEvents(
1725 JSONArray* events, 1608 JSONArray* events,
1726 TimelineEventFilter* filter) { 1609 TimelineEventFilter* filter) {
1727 if (!FLAG_support_service) { 1610 if (!FLAG_support_service) {
1728 return; 1611 return;
1729 } 1612 }
1730 MutexLocker ml(&lock_); 1613 MutexLocker ml(&lock_);
1731 ResetTimeTracking(); 1614 ResetTimeTracking();
1732 // Collect all interesting blocks. 1615 // Collect all interesting blocks.
1733 MallocGrowableArray<TimelineEventBlock*> blocks(8); 1616 MallocGrowableArray<TimelineEventBlock*> blocks(8);
(...skipping 21 matching lines...) Expand all
1755 event->Within(filter->time_origin_micros(), 1638 event->Within(filter->time_origin_micros(),
1756 filter->time_extent_micros())) { 1639 filter->time_extent_micros())) {
1757 ReportTime(event->LowTime()); 1640 ReportTime(event->LowTime());
1758 ReportTime(event->HighTime()); 1641 ReportTime(event->HighTime());
1759 events->AddValue(event); 1642 events->AddValue(event);
1760 } 1643 }
1761 } 1644 }
1762 } 1645 }
1763 } 1646 }
1764 1647
1765
1766 void TimelineEventEndlessRecorder::Clear() { 1648 void TimelineEventEndlessRecorder::Clear() {
1767 TimelineEventBlock* current = head_; 1649 TimelineEventBlock* current = head_;
1768 while (current != NULL) { 1650 while (current != NULL) {
1769 TimelineEventBlock* next = current->next(); 1651 TimelineEventBlock* next = current->next();
1770 delete current; 1652 delete current;
1771 current = next; 1653 current = next;
1772 } 1654 }
1773 head_ = NULL; 1655 head_ = NULL;
1774 block_index_ = 0; 1656 block_index_ = 0;
1775 OSThread* thread = OSThread::Current(); 1657 OSThread* thread = OSThread::Current();
1776 thread->set_timeline_block(NULL); 1658 thread->set_timeline_block(NULL);
1777 } 1659 }
1778 1660
1779
1780 TimelineEventBlock::TimelineEventBlock(intptr_t block_index) 1661 TimelineEventBlock::TimelineEventBlock(intptr_t block_index)
1781 : next_(NULL), 1662 : next_(NULL),
1782 length_(0), 1663 length_(0),
1783 block_index_(block_index), 1664 block_index_(block_index),
1784 thread_id_(OSThread::kInvalidThreadId), 1665 thread_id_(OSThread::kInvalidThreadId),
1785 in_use_(false) {} 1666 in_use_(false) {}
1786 1667
1787
1788 TimelineEventBlock::~TimelineEventBlock() { 1668 TimelineEventBlock::~TimelineEventBlock() {
1789 Reset(); 1669 Reset();
1790 } 1670 }
1791 1671
1792
1793 void TimelineEventBlock::PrintJSON(JSONStream* js) const { 1672 void TimelineEventBlock::PrintJSON(JSONStream* js) const {
1794 ASSERT(!in_use()); 1673 ASSERT(!in_use());
1795 JSONArray events(js); 1674 JSONArray events(js);
1796 for (intptr_t i = 0; i < length(); i++) { 1675 for (intptr_t i = 0; i < length(); i++) {
1797 const TimelineEvent* event = At(i); 1676 const TimelineEvent* event = At(i);
1798 events.AddValue(event); 1677 events.AddValue(event);
1799 } 1678 }
1800 } 1679 }
1801 1680
1802
1803 TimelineEvent* TimelineEventBlock::StartEvent() { 1681 TimelineEvent* TimelineEventBlock::StartEvent() {
1804 ASSERT(!IsFull()); 1682 ASSERT(!IsFull());
1805 if (FLAG_trace_timeline) { 1683 if (FLAG_trace_timeline) {
1806 OSThread* os_thread = OSThread::Current(); 1684 OSThread* os_thread = OSThread::Current();
1807 ASSERT(os_thread != NULL); 1685 ASSERT(os_thread != NULL);
1808 intptr_t tid = OSThread::ThreadIdToIntPtr(os_thread->id()); 1686 intptr_t tid = OSThread::ThreadIdToIntPtr(os_thread->id());
1809 OS::Print("StartEvent in block %p for thread %" Px "\n", this, tid); 1687 OS::Print("StartEvent in block %p for thread %" Px "\n", this, tid);
1810 } 1688 }
1811 return &events_[length_++]; 1689 return &events_[length_++];
1812 } 1690 }
1813 1691
1814
1815 int64_t TimelineEventBlock::LowerTimeBound() const { 1692 int64_t TimelineEventBlock::LowerTimeBound() const {
1816 if (length_ == 0) { 1693 if (length_ == 0) {
1817 return kMaxInt64; 1694 return kMaxInt64;
1818 } 1695 }
1819 ASSERT(length_ > 0); 1696 ASSERT(length_ > 0);
1820 return events_[0].TimeOrigin(); 1697 return events_[0].TimeOrigin();
1821 } 1698 }
1822 1699
1823
1824 bool TimelineEventBlock::CheckBlock() { 1700 bool TimelineEventBlock::CheckBlock() {
1825 if (length() == 0) { 1701 if (length() == 0) {
1826 return true; 1702 return true;
1827 } 1703 }
1828 1704
1829 for (intptr_t i = 0; i < length(); i++) { 1705 for (intptr_t i = 0; i < length(); i++) {
1830 if (At(i)->thread() != thread_id()) { 1706 if (At(i)->thread() != thread_id()) {
1831 return false; 1707 return false;
1832 } 1708 }
1833 } 1709 }
1834 1710
1835 // - events have monotonically increasing timestamps. 1711 // - events have monotonically increasing timestamps.
1836 int64_t last_time = LowerTimeBound(); 1712 int64_t last_time = LowerTimeBound();
1837 for (intptr_t i = 0; i < length(); i++) { 1713 for (intptr_t i = 0; i < length(); i++) {
1838 if (last_time > At(i)->TimeOrigin()) { 1714 if (last_time > At(i)->TimeOrigin()) {
1839 return false; 1715 return false;
1840 } 1716 }
1841 last_time = At(i)->TimeOrigin(); 1717 last_time = At(i)->TimeOrigin();
1842 } 1718 }
1843 1719
1844 return true; 1720 return true;
1845 } 1721 }
1846 1722
1847
1848 void TimelineEventBlock::Reset() { 1723 void TimelineEventBlock::Reset() {
1849 for (intptr_t i = 0; i < kBlockSize; i++) { 1724 for (intptr_t i = 0; i < kBlockSize; i++) {
1850 // Clear any extra data. 1725 // Clear any extra data.
1851 events_[i].Reset(); 1726 events_[i].Reset();
1852 } 1727 }
1853 length_ = 0; 1728 length_ = 0;
1854 thread_id_ = OSThread::kInvalidThreadId; 1729 thread_id_ = OSThread::kInvalidThreadId;
1855 in_use_ = false; 1730 in_use_ = false;
1856 } 1731 }
1857 1732
1858
1859 void TimelineEventBlock::Open() { 1733 void TimelineEventBlock::Open() {
1860 OSThread* os_thread = OSThread::Current(); 1734 OSThread* os_thread = OSThread::Current();
1861 ASSERT(os_thread != NULL); 1735 ASSERT(os_thread != NULL);
1862 thread_id_ = os_thread->trace_id(); 1736 thread_id_ = os_thread->trace_id();
1863 in_use_ = true; 1737 in_use_ = true;
1864 } 1738 }
1865 1739
1866
1867 void TimelineEventBlock::Finish() { 1740 void TimelineEventBlock::Finish() {
1868 if (FLAG_trace_timeline) { 1741 if (FLAG_trace_timeline) {
1869 OS::Print("Finish block %p\n", this); 1742 OS::Print("Finish block %p\n", this);
1870 } 1743 }
1871 in_use_ = false; 1744 in_use_ = false;
1872 if (Service::timeline_stream.enabled()) { 1745 if (Service::timeline_stream.enabled()) {
1873 ServiceEvent service_event(NULL, ServiceEvent::kTimelineEvents); 1746 ServiceEvent service_event(NULL, ServiceEvent::kTimelineEvents);
1874 service_event.set_timeline_event_block(this); 1747 service_event.set_timeline_event_block(this);
1875 Service::HandleEvent(&service_event); 1748 Service::HandleEvent(&service_event);
1876 } 1749 }
1877 } 1750 }
1878 1751
1879
1880 TimelineEventBlockIterator::TimelineEventBlockIterator( 1752 TimelineEventBlockIterator::TimelineEventBlockIterator(
1881 TimelineEventRecorder* recorder) 1753 TimelineEventRecorder* recorder)
1882 : current_(NULL), recorder_(NULL) { 1754 : current_(NULL), recorder_(NULL) {
1883 Reset(recorder); 1755 Reset(recorder);
1884 } 1756 }
1885 1757
1886
1887 TimelineEventBlockIterator::~TimelineEventBlockIterator() { 1758 TimelineEventBlockIterator::~TimelineEventBlockIterator() {
1888 Reset(NULL); 1759 Reset(NULL);
1889 } 1760 }
1890 1761
1891
1892 void TimelineEventBlockIterator::Reset(TimelineEventRecorder* recorder) { 1762 void TimelineEventBlockIterator::Reset(TimelineEventRecorder* recorder) {
1893 // Clear current. 1763 // Clear current.
1894 current_ = NULL; 1764 current_ = NULL;
1895 if (recorder_ != NULL) { 1765 if (recorder_ != NULL) {
1896 // Unlock old recorder. 1766 // Unlock old recorder.
1897 recorder_->lock_.Unlock(); 1767 recorder_->lock_.Unlock();
1898 } 1768 }
1899 recorder_ = recorder; 1769 recorder_ = recorder;
1900 if (recorder_ == NULL) { 1770 if (recorder_ == NULL) {
1901 return; 1771 return;
1902 } 1772 }
1903 // Lock new recorder. 1773 // Lock new recorder.
1904 recorder_->lock_.Lock(); 1774 recorder_->lock_.Lock();
1905 // Queue up first block. 1775 // Queue up first block.
1906 current_ = recorder_->GetHeadBlockLocked(); 1776 current_ = recorder_->GetHeadBlockLocked();
1907 } 1777 }
1908 1778
1909
1910 bool TimelineEventBlockIterator::HasNext() const { 1779 bool TimelineEventBlockIterator::HasNext() const {
1911 return current_ != NULL; 1780 return current_ != NULL;
1912 } 1781 }
1913 1782
1914
1915 TimelineEventBlock* TimelineEventBlockIterator::Next() { 1783 TimelineEventBlock* TimelineEventBlockIterator::Next() {
1916 ASSERT(current_ != NULL); 1784 ASSERT(current_ != NULL);
1917 TimelineEventBlock* r = current_; 1785 TimelineEventBlock* r = current_;
1918 current_ = current_->next(); 1786 current_ = current_->next();
1919 return r; 1787 return r;
1920 } 1788 }
1921 1789
1922 } // namespace dart 1790 } // namespace dart
1923 1791
1924 #endif // !PRODUCT 1792 #endif // !PRODUCT
OLDNEW
« no previous file with comments | « runtime/vm/timeline.h ('k') | runtime/vm/timeline_analysis.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698