1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 6 #ifndef BASE_DEBUG_TRACE_EVENT_IMPL_H_ 7 #define BASE_DEBUG_TRACE_EVENT_IMPL_H_ 8 9 #include <stack> 10 #include <string> 11 #include <vector> 12 13 #include "base/atomicops.h" 14 #include "base/base_export.h" 15 #include "base/callback.h" 16 #include "base/containers/hash_tables.h" 17 #include "base/gtest_prod_util.h" 18 #include "base/memory/ref_counted_memory.h" 19 #include "base/memory/scoped_vector.h" 20 #include "base/observer_list.h" 21 #include "base/strings/string_util.h" 22 #include "base/synchronization/condition_variable.h" 23 #include "base/synchronization/lock.h" 24 #include "base/threading/thread.h" 25 #include "base/threading/thread_local.h" 26 #include "base/timer/timer.h" 27 28 // Older style trace macros with explicit id and extra data 29 // Only these macros result in publishing data to ETW as currently implemented. 30 #define TRACE_EVENT_BEGIN_ETW(name, id, extra) \ 31 base::debug::TraceLog::AddTraceEventEtw( \ 32 TRACE_EVENT_PHASE_BEGIN, \ 33 name, reinterpret_cast<const void*>(id), extra) 34 35 #define TRACE_EVENT_END_ETW(name, id, extra) \ 36 base::debug::TraceLog::AddTraceEventEtw( \ 37 TRACE_EVENT_PHASE_END, \ 38 name, reinterpret_cast<const void*>(id), extra) 39 40 #define TRACE_EVENT_INSTANT_ETW(name, id, extra) \ 41 base::debug::TraceLog::AddTraceEventEtw( \ 42 TRACE_EVENT_PHASE_INSTANT, \ 43 name, reinterpret_cast<const void*>(id), extra) 44 45 template <typename Type> 46 struct DefaultSingletonTraits; 47 48 #if defined(COMPILER_GCC) 49 namespace BASE_HASH_NAMESPACE { 50 template <> 51 struct hash<base::MessageLoop*> { 52 std::size_t operator()(base::MessageLoop* value) const { 53 return reinterpret_cast<std::size_t>(value); 54 } 55 }; 56 } // BASE_HASH_NAMESPACE 57 #endif 58 59 namespace base { 60 61 class WaitableEvent; 62 class MessageLoop; 63 64 namespace debug { 65 66 // For any argument of type TRACE_VALUE_TYPE_CONVERTABLE the provided 67 // class must implement this interface. 68 class BASE_EXPORT ConvertableToTraceFormat 69 : public RefCounted<ConvertableToTraceFormat> { 70 public: 71 // Append the class info to the provided |out| string. The appended 72 // data must be a valid JSON object. Strings must be properly quoted, and 73 // escaped. There is no processing applied to the content after it is 74 // appended. 75 virtual void AppendAsTraceFormat(std::string* out) const = 0; 76 77 std::string ToString() const { 78 std::string result; 79 AppendAsTraceFormat(&result); 80 return result; 81 } 82 83 protected: 84 virtual ~ConvertableToTraceFormat() {} 85 86 private: 87 friend class RefCounted<ConvertableToTraceFormat>; 88 }; 89 90 struct TraceEventHandle { 91 uint32 chunk_seq; 92 uint16 chunk_index; 93 uint16 event_index; 94 }; 95 96 const int kTraceMaxNumArgs = 2; 97 98 class BASE_EXPORT TraceEvent { 99 public: 100 union TraceValue { 101 bool as_bool; 102 unsigned long long as_uint; 103 long long as_int; 104 double as_double; 105 const void* as_pointer; 106 const char* as_string; 107 }; 108 109 TraceEvent(); 110 ~TraceEvent(); 111 112 // We don't need to copy TraceEvent except when TraceEventBuffer is cloned. 113 // Use explicit copy method to avoid accidentally misuse of copy. 114 void CopyFrom(const TraceEvent& other); 115 116 void Initialize( 117 int thread_id, 118 TimeTicks timestamp, 119 TimeTicks thread_timestamp, 120 char phase, 121 const unsigned char* category_group_enabled, 122 const char* name, 123 unsigned long long id, 124 int num_args, 125 const char** arg_names, 126 const unsigned char* arg_types, 127 const unsigned long long* arg_values, 128 const scoped_refptr<ConvertableToTraceFormat>* convertable_values, 129 unsigned char flags); 130 131 void Reset(); 132 133 void UpdateDuration(const TimeTicks& now, const TimeTicks& thread_now); 134 135 // Serialize event data to JSON 136 void AppendAsJSON(std::string* out) const; 137 void AppendPrettyPrinted(std::ostringstream* out) const; 138 139 static void AppendValueAsJSON(unsigned char type, 140 TraceValue value, 141 std::string* out); 142 143 TimeTicks timestamp() const { return timestamp_; } 144 TimeTicks thread_timestamp() const { return thread_timestamp_; } 145 char phase() const { return phase_; } 146 int thread_id() const { return thread_id_; } 147 TimeDelta duration() const { return duration_; } 148 TimeDelta thread_duration() const { return thread_duration_; } 149 unsigned long long id() const { return id_; } 150 unsigned char flags() const { return flags_; } 151 152 // Exposed for unittesting: 153 154 const base::RefCountedString* parameter_copy_storage() const { 155 return parameter_copy_storage_.get(); 156 } 157 158 const unsigned char* category_group_enabled() const { 159 return category_group_enabled_; 160 } 161 162 const char* name() const { return name_; } 163 164 #if defined(OS_ANDROID) 165 void SendToATrace(); 166 #endif 167 168 private: 169 // Note: these are ordered by size (largest first) for optimal packing. 170 TimeTicks timestamp_; 171 TimeTicks thread_timestamp_; 172 TimeDelta duration_; 173 TimeDelta thread_duration_; 174 // id_ can be used to store phase-specific data. 175 unsigned long long id_; 176 TraceValue arg_values_[kTraceMaxNumArgs]; 177 const char* arg_names_[kTraceMaxNumArgs]; 178 scoped_refptr<ConvertableToTraceFormat> convertable_values_[kTraceMaxNumArgs]; 179 const unsigned char* category_group_enabled_; 180 const char* name_; 181 scoped_refptr<base::RefCountedString> parameter_copy_storage_; 182 int thread_id_; 183 char phase_; 184 unsigned char flags_; 185 unsigned char arg_types_[kTraceMaxNumArgs]; 186 187 DISALLOW_COPY_AND_ASSIGN(TraceEvent); 188 }; 189 190 // TraceBufferChunk is the basic unit of TraceBuffer. 191 class BASE_EXPORT TraceBufferChunk { 192 public: 193 TraceBufferChunk(uint32 seq) 194 : next_free_(0), 195 seq_(seq) { 196 } 197 198 void Reset(uint32 new_seq); 199 TraceEvent* AddTraceEvent(size_t* event_index); 200 bool IsFull() const { return next_free_ == kTraceBufferChunkSize; } 201 202 uint32 seq() const { return seq_; } 203 size_t capacity() const { return kTraceBufferChunkSize; } 204 size_t size() const { return next_free_; } 205 206 TraceEvent* GetEventAt(size_t index) { 207 DCHECK(index < size()); 208 return &chunk_[index]; 209 } 210 const TraceEvent* GetEventAt(size_t index) const { 211 DCHECK(index < size()); 212 return &chunk_[index]; 213 } 214 215 scoped_ptr<TraceBufferChunk> Clone() const; 216 217 static const size_t kTraceBufferChunkSize = 64; 218 219 private: 220 size_t next_free_; 221 TraceEvent chunk_[kTraceBufferChunkSize]; 222 uint32 seq_; 223 }; 224 225 // TraceBuffer holds the events as they are collected. 226 class BASE_EXPORT TraceBuffer { 227 public: 228 virtual ~TraceBuffer() {} 229 230 virtual scoped_ptr<TraceBufferChunk> GetChunk(size_t *index) = 0; 231 virtual void ReturnChunk(size_t index, 232 scoped_ptr<TraceBufferChunk> chunk) = 0; 233 234 virtual bool IsFull() const = 0; 235 virtual size_t Size() const = 0; 236 virtual size_t Capacity() const = 0; 237 virtual TraceEvent* GetEventByHandle(TraceEventHandle handle) = 0; 238 239 // For iteration. Each TraceBuffer can only be iterated once. 240 virtual const TraceBufferChunk* NextChunk() = 0; 241 242 virtual scoped_ptr<TraceBuffer> CloneForIteration() const = 0; 243 }; 244 245 // TraceResultBuffer collects and converts trace fragments returned by TraceLog 246 // to JSON output. 247 class BASE_EXPORT TraceResultBuffer { 248 public: 249 typedef base::Callback<void(const std::string&)> OutputCallback; 250 251 // If you don't need to stream JSON chunks out efficiently, and just want to 252 // get a complete JSON string after calling Finish, use this struct to collect 253 // JSON trace output. 254 struct BASE_EXPORT SimpleOutput { 255 OutputCallback GetCallback(); 256 void Append(const std::string& json_string); 257 258 // Do what you want with the json_output_ string after calling 259 // TraceResultBuffer::Finish. 260 std::string json_output; 261 }; 262 263 TraceResultBuffer(); 264 ~TraceResultBuffer(); 265 266 // Set callback. The callback will be called during Start with the initial 267 // JSON output and during AddFragment and Finish with following JSON output 268 // chunks. The callback target must live past the last calls to 269 // TraceResultBuffer::Start/AddFragment/Finish. 270 void SetOutputCallback(const OutputCallback& json_chunk_callback); 271 272 // Start JSON output. This resets all internal state, so you can reuse 273 // the TraceResultBuffer by calling Start. 274 void Start(); 275 276 // Call AddFragment 0 or more times to add trace fragments from TraceLog. 277 void AddFragment(const std::string& trace_fragment); 278 279 // When all fragments have been added, call Finish to complete the JSON 280 // formatted output. 281 void Finish(); 282 283 private: 284 OutputCallback output_callback_; 285 bool append_comma_; 286 }; 287 288 class BASE_EXPORT CategoryFilter { 289 public: 290 typedef std::vector<std::string> StringList; 291 292 // The default category filter, used when none is provided. 293 // Allows all categories through, except if they end in the suffix 'Debug' or 294 // 'Test'. 295 static const char* kDefaultCategoryFilterString; 296 297 // |filter_string| is a comma-delimited list of category wildcards. 298 // A category can have an optional '-' prefix to make it an excluded category. 299 // All the same rules apply above, so for example, having both included and 300 // excluded categories in the same list would not be supported. 301 // 302 // Example: CategoryFilter"test_MyTest*"); 303 // Example: CategoryFilter("test_MyTest*,test_OtherStuff"); 304 // Example: CategoryFilter("-excluded_category1,-excluded_category2"); 305 // Example: CategoryFilter("-*,webkit"); would disable everything but webkit. 306 // Example: CategoryFilter("-webkit"); would enable everything but webkit. 307 // 308 // Category filters can also be used to configure synthetic delays. 309 // 310 // Example: CategoryFilter("DELAY(gpu.PresentingFrame;16)"); would make swap 311 // buffers always take at least 16 ms. 312 // Example: CategoryFilter("DELAY(gpu.PresentingFrame;16;oneshot)"); would 313 // make swap buffers take at least 16 ms the first time it is 314 // called. 315 // Example: CategoryFilter("DELAY(gpu.PresentingFrame;16;alternating)"); 316 // would make swap buffers take at least 16 ms every other time it 317 // is called. 318 explicit CategoryFilter(const std::string& filter_string); 319 320 CategoryFilter(); 321 322 CategoryFilter(const CategoryFilter& cf); 323 324 ~CategoryFilter(); 325 326 CategoryFilter& operator=(const CategoryFilter& rhs); 327 328 // Writes the string representation of the CategoryFilter. This is a comma 329 // separated string, similar in nature to the one used to determine 330 // enabled/disabled category patterns, except here there is an arbitrary 331 // order, included categories go first, then excluded categories. Excluded 332 // categories are distinguished from included categories by the prefix '-'. 333 std::string ToString() const; 334 335 // Determines whether category group would be enabled or 336 // disabled by this category filter. 337 bool IsCategoryGroupEnabled(const char* category_group) const; 338 339 // Return a list of the synthetic delays specified in this category filter. 340 const StringList& GetSyntheticDelayValues() const; 341 342 // Merges nested_filter with the current CategoryFilter 343 void Merge(const CategoryFilter& nested_filter); 344 345 // Clears both included/excluded pattern lists. This would be equivalent to 346 // creating a CategoryFilter with an empty string, through the constructor. 347 // i.e: CategoryFilter(). 348 // 349 // When using an empty filter, all categories are considered included as we 350 // are not excluding anything. 351 void Clear(); 352 353 private: 354 FRIEND_TEST_ALL_PREFIXES(TraceEventTestFixture, CategoryFilter); 355 356 static bool IsEmptyOrContainsLeadingOrTrailingWhitespace( 357 const std::string& str); 358 359 void Initialize(const std::string& filter_string); 360 void WriteString(const StringList& values, 361 std::string* out, 362 bool included) const; 363 void WriteString(const StringList& delays, std::string* out) const; 364 bool HasIncludedPatterns() const; 365 366 bool DoesCategoryGroupContainCategory(const char* category_group, 367 const char* category) const; 368 369 StringList included_; 370 StringList disabled_; 371 StringList excluded_; 372 StringList delays_; 373 }; 374 375 class TraceSamplingThread; 376 377 // Options determines how the trace buffer stores data. 378 enum TraceRecordMode { 379 // Record until the trace buffer is full. 380 RECORD_UNTIL_FULL, 381 382 // Record until the user ends the trace. The trace buffer is a fixed size 383 // and we use it as a ring buffer during recording. 384 RECORD_CONTINUOUSLY, 385 386 // Echo to console. Events are discarded. 387 ECHO_TO_CONSOLE, 388 389 // Record until the trace buffer is full, but with a huge buffer size. 390 RECORD_AS_MUCH_AS_POSSIBLE 391 }; 392 393 struct BASE_EXPORT TraceOptions { 394 395 TraceOptions() 396 : record_mode(RECORD_UNTIL_FULL), 397 enable_sampling(false), 398 enable_systrace(false) {} 399 400 TraceOptions(TraceRecordMode record_mode) 401 : record_mode(record_mode), 402 enable_sampling(false), 403 enable_systrace(false) {} 404 405 // |options_string| is a comma-delimited list of trace options. 406 // Possible options are: "record-until-full", "record-continuously", 407 // "trace-to-console", "enable-sampling" and "enable-systrace". 408 // The first 3 options are trace recoding modes and hence 409 // mutually exclusive. If more than one trace recording modes appear in the 410 // options_string, the last one takes precedence. If none of the trace 411 // recording mode is specified, recording mode is RECORD_UNTIL_FULL. 412 // 413 // The trace option will first be reset to the default option 414 // (record_mode set to RECORD_UNTIL_FULL, enable_sampling and enable_systrace 415 // set to false) before options parsed from |options_string| are applied on 416 // it. 417 // If |options_string| is invalid, the final state of trace_options is 418 // undefined. 419 // 420 // Example: trace_options.SetFromString("record-until-full") 421 // Example: trace_options.SetFromString( 422 // "record-continuously, enable-sampling") 423 // Example: trace_options.SetFromString("record-until-full, trace-to-console") 424 // will set ECHO_TO_CONSOLE as the recording mode. 425 // 426 // Returns true on success. 427 bool SetFromString(const std::string& options_string); 428 429 std::string ToString() const; 430 431 TraceRecordMode record_mode; 432 bool enable_sampling; 433 bool enable_systrace; 434 }; 435 436 class BASE_EXPORT TraceLog { 437 public: 438 enum Mode { 439 DISABLED = 0, 440 RECORDING_MODE, 441 MONITORING_MODE, 442 }; 443 444 // The pointer returned from GetCategoryGroupEnabledInternal() points to a 445 // value with zero or more of the following bits. Used in this class only. 446 // The TRACE_EVENT macros should only use the value as a bool. 447 // These values must be in sync with macro values in TraceEvent.h in Blink. 448 enum CategoryGroupEnabledFlags { 449 // Category group enabled for the recording mode. 450 ENABLED_FOR_RECORDING = 1 << 0, 451 // Category group enabled for the monitoring mode. 452 ENABLED_FOR_MONITORING = 1 << 1, 453 // Category group enabled by SetEventCallbackEnabled(). 454 ENABLED_FOR_EVENT_CALLBACK = 1 << 2, 455 }; 456 457 static TraceLog* GetInstance(); 458 459 // Get set of known category groups. This can change as new code paths are 460 // reached. The known category groups are inserted into |category_groups|. 461 void GetKnownCategoryGroups(std::vector<std::string>* category_groups); 462 463 // Retrieves a copy (for thread-safety) of the current CategoryFilter. 464 CategoryFilter GetCurrentCategoryFilter(); 465 466 // Retrieves a copy (for thread-safety) of the current TraceOptions. 467 TraceOptions GetCurrentTraceOptions() const; 468 469 // Enables normal tracing (recording trace events in the trace buffer). 470 // See CategoryFilter comments for details on how to control what categories 471 // will be traced. If tracing has already been enabled, |category_filter| will 472 // be merged into the current category filter. 473 void SetEnabled(const CategoryFilter& category_filter, 474 Mode mode, const TraceOptions& options); 475 476 // Disables normal tracing for all categories. 477 void SetDisabled(); 478 479 bool IsEnabled() { return mode_ != DISABLED; } 480 481 // The number of times we have begun recording traces. If tracing is off, 482 // returns -1. If tracing is on, then it returns the number of times we have 483 // recorded a trace. By watching for this number to increment, you can 484 // passively discover when a new trace has begun. This is then used to 485 // implement the TRACE_EVENT_IS_NEW_TRACE() primitive. 486 int GetNumTracesRecorded(); 487 488 #if defined(OS_ANDROID) 489 void StartATrace(); 490 void StopATrace(); 491 void AddClockSyncMetadataEvent(); 492 #endif 493 494 // Enabled state listeners give a callback when tracing is enabled or 495 // disabled. This can be used to tie into other library's tracing systems 496 // on-demand. 497 class BASE_EXPORT EnabledStateObserver { 498 public: 499 // Called just after the tracing system becomes enabled, outside of the 500 // |lock_|. TraceLog::IsEnabled() is true at this point. 501 virtual void OnTraceLogEnabled() = 0; 502 503 // Called just after the tracing system disables, outside of the |lock_|. 504 // TraceLog::IsEnabled() is false at this point. 505 virtual void OnTraceLogDisabled() = 0; 506 }; 507 void AddEnabledStateObserver(EnabledStateObserver* listener); 508 void RemoveEnabledStateObserver(EnabledStateObserver* listener); 509 bool HasEnabledStateObserver(EnabledStateObserver* listener) const; 510 511 float GetBufferPercentFull() const; 512 bool BufferIsFull() const; 513 514 // Not using base::Callback because of its limited by 7 parameters. 515 // Also, using primitive type allows directly passing callback from WebCore. 516 // WARNING: It is possible for the previously set callback to be called 517 // after a call to SetEventCallbackEnabled() that replaces or a call to 518 // SetEventCallbackDisabled() that disables the callback. 519 // This callback may be invoked on any thread. 520 // For TRACE_EVENT_PHASE_COMPLETE events, the client will still receive pairs 521 // of TRACE_EVENT_PHASE_BEGIN and TRACE_EVENT_PHASE_END events to keep the 522 // interface simple. 523 typedef void (*EventCallback)(TimeTicks timestamp, 524 char phase, 525 const unsigned char* category_group_enabled, 526 const char* name, 527 unsigned long long id, 528 int num_args, 529 const char* const arg_names[], 530 const unsigned char arg_types[], 531 const unsigned long long arg_values[], 532 unsigned char flags); 533 534 // Enable tracing for EventCallback. 535 void SetEventCallbackEnabled(const CategoryFilter& category_filter, 536 EventCallback cb); 537 void SetEventCallbackDisabled(); 538 539 // Flush all collected events to the given output callback. The callback will 540 // be called one or more times either synchronously or asynchronously from 541 // the current thread with IPC-bite-size chunks. The string format is 542 // undefined. Use TraceResultBuffer to convert one or more trace strings to 543 // JSON. The callback can be null if the caller doesn't want any data. 544 // Due to the implementation of thread-local buffers, flush can't be 545 // done when tracing is enabled. If called when tracing is enabled, the 546 // callback will be called directly with (empty_string, false) to indicate 547 // the end of this unsuccessful flush. 548 typedef base::Callback<void(const scoped_refptr<base::RefCountedString>&, 549 bool has_more_events)> OutputCallback; 550 void Flush(const OutputCallback& cb); 551 void FlushButLeaveBufferIntact(const OutputCallback& flush_output_callback); 552 553 // Called by TRACE_EVENT* macros, don't call this directly. 554 // The name parameter is a category group for example: 555 // TRACE_EVENT0("renderer,webkit", "WebViewImpl::HandleInputEvent") 556 static const unsigned char* GetCategoryGroupEnabled(const char* name); 557 static const char* GetCategoryGroupName( 558 const unsigned char* category_group_enabled); 559 560 // Called by TRACE_EVENT* macros, don't call this directly. 561 // If |copy| is set, |name|, |arg_name1| and |arg_name2| will be deep copied 562 // into the event; see "Memory scoping note" and TRACE_EVENT_COPY_XXX above. 563 TraceEventHandle AddTraceEvent( 564 char phase, 565 const unsigned char* category_group_enabled, 566 const char* name, 567 unsigned long long id, 568 int num_args, 569 const char** arg_names, 570 const unsigned char* arg_types, 571 const unsigned long long* arg_values, 572 const scoped_refptr<ConvertableToTraceFormat>* convertable_values, 573 unsigned char flags); 574 TraceEventHandle AddTraceEventWithThreadIdAndTimestamp( 575 char phase, 576 const unsigned char* category_group_enabled, 577 const char* name, 578 unsigned long long id, 579 int thread_id, 580 const TimeTicks& timestamp, 581 int num_args, 582 const char** arg_names, 583 const unsigned char* arg_types, 584 const unsigned long long* arg_values, 585 const scoped_refptr<ConvertableToTraceFormat>* convertable_values, 586 unsigned char flags); 587 static void AddTraceEventEtw(char phase, 588 const char* category_group, 589 const void* id, 590 const char* extra); 591 static void AddTraceEventEtw(char phase, 592 const char* category_group, 593 const void* id, 594 const std::string& extra); 595 596 void UpdateTraceEventDuration(const unsigned char* category_group_enabled, 597 const char* name, 598 TraceEventHandle handle); 599 600 // For every matching event, the callback will be called. 601 typedef base::Callback<void()> WatchEventCallback; 602 void SetWatchEvent(const std::string& category_name, 603 const std::string& event_name, 604 const WatchEventCallback& callback); 605 // Cancel the watch event. If tracing is enabled, this may race with the 606 // watch event notification firing. 607 void CancelWatchEvent(); 608 609 int process_id() const { return process_id_; } 610 611 // Exposed for unittesting: 612 613 void WaitSamplingEventForTesting(); 614 615 // Allows deleting our singleton instance. 616 static void DeleteForTesting(); 617 618 // Allow tests to inspect TraceEvents. 619 size_t GetEventsSize() const { return logged_events_->Size(); } 620 TraceEvent* GetEventByHandle(TraceEventHandle handle); 621 622 void SetProcessID(int process_id); 623 624 // Process sort indices, if set, override the order of a process will appear 625 // relative to other processes in the trace viewer. Processes are sorted first 626 // on their sort index, ascending, then by their name, and then tid. 627 void SetProcessSortIndex(int sort_index); 628 629 // Sets the name of the process. 630 void SetProcessName(const std::string& process_name); 631 632 // Processes can have labels in addition to their names. Use labels, for 633 // instance, to list out the web page titles that a process is handling. 634 void UpdateProcessLabel(int label_id, const std::string& current_label); 635 void RemoveProcessLabel(int label_id); 636 637 // Thread sort indices, if set, override the order of a thread will appear 638 // within its process in the trace viewer. Threads are sorted first on their 639 // sort index, ascending, then by their name, and then tid. 640 void SetThreadSortIndex(PlatformThreadId , int sort_index); 641 642 // Allow setting an offset between the current TimeTicks time and the time 643 // that should be reported. 644 void SetTimeOffset(TimeDelta offset); 645 646 size_t GetObserverCountForTest() const; 647 648 // Call this method if the current thread may block the message loop to 649 // prevent the thread from using the thread-local buffer because the thread 650 // may not handle the flush request in time causing lost of unflushed events. 651 void SetCurrentThreadBlocksMessageLoop(); 652 653 private: 654 typedef unsigned int InternalTraceOptions; 655 656 FRIEND_TEST_ALL_PREFIXES(TraceEventTestFixture, 657 TraceBufferRingBufferGetReturnChunk); 658 FRIEND_TEST_ALL_PREFIXES(TraceEventTestFixture, 659 TraceBufferRingBufferHalfIteration); 660 FRIEND_TEST_ALL_PREFIXES(TraceEventTestFixture, 661 TraceBufferRingBufferFullIteration); 662 FRIEND_TEST_ALL_PREFIXES(TraceEventTestFixture, 663 TraceBufferVectorReportFull); 664 FRIEND_TEST_ALL_PREFIXES(TraceEventTestFixture, 665 ConvertTraceOptionsToInternalOptions); 666 FRIEND_TEST_ALL_PREFIXES(TraceEventTestFixture, 667 TraceRecordAsMuchAsPossibleMode); 668 669 // This allows constructor and destructor to be private and usable only 670 // by the Singleton class. 671 friend struct DefaultSingletonTraits<TraceLog>; 672 673 // Enable/disable each category group based on the current mode_, 674 // category_filter_, event_callback_ and event_callback_category_filter_. 675 // Enable the category group in the enabled mode if category_filter_ matches 676 // the category group, or event_callback_ is not null and 677 // event_callback_category_filter_ matches the category group. 678 void UpdateCategoryGroupEnabledFlags(); 679 void UpdateCategoryGroupEnabledFlag(size_t category_index); 680 681 // Configure synthetic delays based on the values set in the current 682 // category filter. 683 void UpdateSyntheticDelaysFromCategoryFilter(); 684 685 InternalTraceOptions GetInternalOptionsFromTraceOptions( 686 const TraceOptions& options); 687 688 class ThreadLocalEventBuffer; 689 class OptionalAutoLock; 690 691 TraceLog(); 692 ~TraceLog(); 693 const unsigned char* GetCategoryGroupEnabledInternal(const char* name); 694 void AddMetadataEventsWhileLocked(); 695 696 InternalTraceOptions trace_options() const { 697 return static_cast<InternalTraceOptions>( 698 subtle::NoBarrier_Load(&trace_options_)); 699 } 700 701 TraceBuffer* trace_buffer() const { return logged_events_.get(); } 702 TraceBuffer* CreateTraceBuffer(); 703 TraceBuffer* CreateTraceBufferVectorOfSize(size_t max_chunks); 704 705 std::string EventToConsoleMessage(unsigned char phase, 706 const TimeTicks& timestamp, 707 TraceEvent* trace_event); 708 709 TraceEvent* AddEventToThreadSharedChunkWhileLocked(TraceEventHandle* handle, 710 bool check_buffer_is_full); 711 void CheckIfBufferIsFullWhileLocked(); 712 void SetDisabledWhileLocked(); 713 714 TraceEvent* GetEventByHandleInternal(TraceEventHandle handle, 715 OptionalAutoLock* lock); 716 717 // |generation| is used in the following callbacks to check if the callback 718 // is called for the flush of the current |logged_events_|. 719 void FlushCurrentThread(int generation); 720 void ConvertTraceEventsToTraceFormat(scoped_ptr<TraceBuffer> logged_events, 721 const TraceLog::OutputCallback& flush_output_callback); 722 void FinishFlush(int generation); 723 void OnFlushTimeout(int generation); 724 725 int generation() const { 726 return static_cast<int>(subtle::NoBarrier_Load(&generation_)); 727 } 728 bool CheckGeneration(int generation) const { 729 return generation == this->generation(); 730 } 731 void UseNextTraceBuffer(); 732 733 TimeTicks OffsetNow() const { 734 return OffsetTimestamp(TimeTicks::NowFromSystemTraceTime()); 735 } 736 TimeTicks OffsetTimestamp(const TimeTicks& timestamp) const { 737 return timestamp - time_offset_; 738 } 739 740 // Internal representation of trace options since we store the currently used 741 // trace option as an AtomicWord. 742 static const InternalTraceOptions kInternalNone; 743 static const InternalTraceOptions kInternalRecordUntilFull; 744 static const InternalTraceOptions kInternalRecordContinuously; 745 static const InternalTraceOptions kInternalEchoToConsole; 746 static const InternalTraceOptions kInternalEnableSampling; 747 static const InternalTraceOptions kInternalRecordAsMuchAsPossible; 748 749 // This lock protects TraceLog member accesses (except for members protected 750 // by thread_info_lock_) from arbitrary threads. 751 mutable Lock lock_; 752 // This lock protects accesses to thread_names_, thread_event_start_times_ 753 // and thread_colors_. 754 Lock thread_info_lock_; 755 int locked_line_; 756 Mode mode_; 757 int num_traces_recorded_; 758 scoped_ptr<TraceBuffer> logged_events_; 759 subtle::AtomicWord /* EventCallback */ event_callback_; 760 bool dispatching_to_observer_list_; 761 std::vector<EnabledStateObserver*> enabled_state_observer_list_; 762 763 std::string process_name_; 764 base::hash_map<int, std::string> process_labels_; 765 int process_sort_index_; 766 base::hash_map<int, int> thread_sort_indices_; 767 base::hash_map<int, std::string> thread_names_; 768 769 // The following two maps are used only when ECHO_TO_CONSOLE. 770 base::hash_map<int, std::stack<TimeTicks> > thread_event_start_times_; 771 base::hash_map<std::string, int> thread_colors_; 772 773 TimeTicks buffer_limit_reached_timestamp_; 774 775 // XORed with TraceID to make it unlikely to collide with other processes. 776 unsigned long long process_id_hash_; 777 778 int process_id_; 779 780 TimeDelta time_offset_; 781 782 // Allow tests to wake up when certain events occur. 783 WatchEventCallback watch_event_callback_; 784 subtle::AtomicWord /* const unsigned char* */ watch_category_; 785 std::string watch_event_name_; 786 787 subtle::AtomicWord /* Options */ trace_options_; 788 789 // Sampling thread handles. 790 scoped_ptr<TraceSamplingThread> sampling_thread_; 791 PlatformThreadHandle sampling_thread_handle_; 792 793 CategoryFilter category_filter_; 794 CategoryFilter event_callback_category_filter_; 795 796 ThreadLocalPointer<ThreadLocalEventBuffer> thread_local_event_buffer_; 797 ThreadLocalBoolean thread_blocks_message_loop_; 798 ThreadLocalBoolean thread_is_in_trace_event_; 799 800 // Contains the message loops of threads that have had at least one event 801 // added into the local event buffer. Not using MessageLoopProxy because we 802 // need to know the life time of the message loops. 803 hash_set<MessageLoop*> thread_message_loops_; 804 805 // For events which can't be added into the thread local buffer, e.g. events 806 // from threads without a message loop. 807 scoped_ptr<TraceBufferChunk> thread_shared_chunk_; 808 size_t thread_shared_chunk_index_; 809 810 // Set when asynchronous Flush is in progress. 811 OutputCallback flush_output_callback_; 812 scoped_refptr<MessageLoopProxy> flush_message_loop_proxy_; 813 subtle::AtomicWord generation_; 814 815 DISALLOW_COPY_AND_ASSIGN(TraceLog); 816 }; 817 818 } // namespace debug 819 } // namespace base 820 821 #endif // BASE_DEBUG_TRACE_EVENT_IMPL_H_ 822