Chromium Code Reviews| Index: base/trace_event/trace_event_etw_export_win.cc |
| diff --git a/base/trace_event/trace_event_etw_export_win.cc b/base/trace_event/trace_event_etw_export_win.cc |
| new file mode 100644 |
| index 0000000000000000000000000000000000000000..dac12d21434eae574380c14820568f743eb661a3 |
| --- /dev/null |
| +++ b/base/trace_event/trace_event_etw_export_win.cc |
| @@ -0,0 +1,164 @@ |
| +// Copyright (c) 2015 The Chromium Authors. All rights reserved. |
| +// Use of this source code is governed by a BSD-style license that can be |
| +// found in the LICENSE file. |
| + |
| +#include "base/trace_event/trace_event_etw_export_win.h" |
| + |
| +#include "base/command_line.h" |
| +#include "base/logging.h" |
| +#include "base/memory/singleton.h" |
| +#include "base/strings/utf_string_conversions.h" |
| +#include "base/trace_event/etw_manifest/chrome_events_win.h" // In SHARED_INTERMEDIATE_DIR. |
| +#include "base/trace_event/trace_event.h" |
| +#include "base/trace_event/trace_event_impl.h" |
| + |
| +#include <evntprov.h> // NOLINT |
| +#include <initguid.h> // NOLINT |
| + |
| +namespace base { |
| +namespace trace_event { |
| + |
| +TraceEventETWExport::TraceEventETWExport() : ETWExportEnabled_(false) { |
| + EventRegisterChrome(); |
| +} |
| + |
| +TraceEventETWExport::~TraceEventETWExport() { |
| + EventUnregisterChrome(); |
| +} |
| + |
| +// static |
| +TraceEventETWExport* TraceEventETWExport::GetInstance() { |
| + return Singleton<TraceEventETWExport, |
| + StaticMemorySingletonTraits<TraceEventETWExport>>::get(); |
| +} |
| + |
| +// static |
| +void TraceEventETWExport::EnableETWExport() { |
| + GetInstance()->ETWExportEnabled_ = true; |
| +} |
| + |
| +// static |
| +void TraceEventETWExport::DisableETWExport() { |
| + GetInstance()->ETWExportEnabled_ = false; |
| +} |
| + |
| +// static |
| +void TraceEventETWExport::AddEvent( |
| + char phase, |
| + const unsigned char* category_group_enabled, |
| + const char* name, |
| + unsigned long long id, |
| + int num_args, |
| + const char** arg_names, |
| + const unsigned char* arg_types, |
| + const unsigned long long* arg_values, |
| + const scoped_refptr<ConvertableToTraceFormat>* convertable_values) { |
| + // We bail early in case exporting is disabled or no consumer is listening. |
| + if (!GetInstance()->ETWExportEnabled_ || !EventEnabledChromeEvent()) |
| + return; |
| + |
| + std::string phase_string = "Unknown"; |
| + switch (phase) { |
| + case TRACE_EVENT_PHASE_BEGIN: |
|
dsinclair
2015/03/26 18:18:17
This seems fragile to me. This list is going to ge
Georges Khalil
2015/03/26 23:09:19
I added a default statement that outputs the code.
|
| + phase_string = "Begin"; |
| + break; |
| + case TRACE_EVENT_PHASE_END: |
| + phase_string = "End"; |
| + break; |
| + case TRACE_EVENT_PHASE_COMPLETE: |
| + phase_string = "Complete"; |
| + break; |
| + case TRACE_EVENT_PHASE_INSTANT: |
| + phase_string = "Instant"; |
| + break; |
| + case TRACE_EVENT_PHASE_ASYNC_BEGIN: |
| + phase_string = "Async Begin"; |
| + break; |
| + case TRACE_EVENT_PHASE_ASYNC_STEP_INTO: |
| + phase_string = "Async Step Into"; |
| + break; |
| + case TRACE_EVENT_PHASE_ASYNC_STEP_PAST: |
| + phase_string = "Async Step Past"; |
| + break; |
| + case TRACE_EVENT_PHASE_ASYNC_END: |
| + phase_string = "Async End"; |
| + break; |
| + case TRACE_EVENT_PHASE_NESTABLE_ASYNC_BEGIN: |
| + phase_string = "NEStable Async Begin"; |
| + break; |
| + case TRACE_EVENT_PHASE_NESTABLE_ASYNC_END: |
| + phase_string = "NEStable Async End"; |
| + break; |
| + case TRACE_EVENT_PHASE_NESTABLE_ASYNC_INSTANT: |
| + phase_string = "NEStable Async Instant"; |
| + break; |
| + case TRACE_EVENT_PHASE_FLOW_BEGIN: |
| + phase_string = "Phase Flow Begin"; |
| + break; |
| + case TRACE_EVENT_PHASE_FLOW_STEP: |
| + phase_string = "Phase Flow Step"; |
| + break; |
| + case TRACE_EVENT_PHASE_FLOW_END: |
| + phase_string = "Phase Flow End"; |
| + break; |
| + case TRACE_EVENT_PHASE_METADATA: |
| + phase_string = "Phase Metadata"; |
| + break; |
| + case TRACE_EVENT_PHASE_COUNTER: |
| + phase_string = "Phase Counter"; |
| + break; |
| + case TRACE_EVENT_PHASE_SAMPLE: |
| + phase_string = "Phase Sample"; |
| + break; |
| + case TRACE_EVENT_PHASE_CREATE_OBJECT: |
| + phase_string = "Phase Create Object"; |
| + break; |
| + case TRACE_EVENT_PHASE_SNAPSHOT_OBJECT: |
| + phase_string = "Phase Snapshot Object"; |
| + break; |
| + case TRACE_EVENT_PHASE_DELETE_OBJECT: |
| + phase_string = "Phase Delete Object"; |
| + break; |
| + } |
| + |
| + std::string arg_values_string[3]; |
| + for (int i = 0; i < num_args; i++) { |
| + if (arg_types[i] == TRACE_VALUE_TYPE_CONVERTABLE) { |
| + convertable_values[i]->AppendAsTraceFormat(arg_values_string + i); |
| + } else { |
| + TraceEvent::TraceValue trace_event; |
| + trace_event.as_uint = arg_values[i]; |
| + TraceEvent::AppendValueAsJSON(arg_types[i], trace_event, |
| + arg_values_string + i); |
| + } |
| + } |
| + |
| + EventWriteChromeEvent( |
| + name, phase_string.c_str(), num_args > 0 ? arg_names[0] : "", |
| + arg_values_string[0].c_str(), num_args > 1 ? arg_names[1] : "", |
| + arg_values_string[1].c_str(), num_args > 2 ? arg_names[2] : "", |
| + arg_values_string[2].c_str()); |
| +} |
| + |
| +// static |
| +void TraceEventETWExport::AddCustomEvent(const char* name, |
| + char const* phase, |
| + const char* arg_name_1, |
| + const char* arg_value_1, |
| + const char* arg_name_2, |
| + const char* arg_value_2, |
| + const char* arg_name_3, |
| + const char* arg_value_3) { |
| + if (!GetInstance()->ETWExportEnabled_ || !EventEnabledChromeEvent()) |
| + return; |
| + |
| + EventWriteChromeEvent(name, phase, arg_name_1, arg_value_1, arg_name_2, |
| + arg_value_2, arg_name_3, arg_value_3); |
| +} |
| + |
| +void TraceEventETWExport::Resurrect() { |
| + StaticMemorySingletonTraits<TraceEventETWExport>::Resurrect(); |
| +} |
| + |
| +} // namespace trace_event |
| +} // namespace base |