| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "base/trace_event/trace_event_impl.h" | 5 #include "base/trace_event/trace_event_impl.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 | 8 |
| 9 #include "base/format_macros.h" | 9 #include "base/format_macros.h" |
| 10 #include "base/json/string_escape.h" | 10 #include "base/json/string_escape.h" |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 49 flags_(0), | 49 flags_(0), |
| 50 phase_(TRACE_EVENT_PHASE_BEGIN) { | 50 phase_(TRACE_EVENT_PHASE_BEGIN) { |
| 51 for (int i = 0; i < kTraceMaxNumArgs; ++i) | 51 for (int i = 0; i < kTraceMaxNumArgs; ++i) |
| 52 arg_names_[i] = NULL; | 52 arg_names_[i] = NULL; |
| 53 memset(arg_values_, 0, sizeof(arg_values_)); | 53 memset(arg_values_, 0, sizeof(arg_values_)); |
| 54 } | 54 } |
| 55 | 55 |
| 56 TraceEvent::~TraceEvent() { | 56 TraceEvent::~TraceEvent() { |
| 57 } | 57 } |
| 58 | 58 |
| 59 void TraceEvent::CopyFrom(const TraceEvent& other) { | 59 void TraceEvent::MoveFrom(scoped_ptr<TraceEvent> other) { |
| 60 timestamp_ = other.timestamp_; | 60 timestamp_ = other->timestamp_; |
| 61 thread_timestamp_ = other.thread_timestamp_; | 61 thread_timestamp_ = other->thread_timestamp_; |
| 62 duration_ = other.duration_; | 62 duration_ = other->duration_; |
| 63 scope_ = other.scope_; | 63 scope_ = other->scope_; |
| 64 id_ = other.id_; | 64 id_ = other->id_; |
| 65 category_group_enabled_ = other.category_group_enabled_; | 65 category_group_enabled_ = other->category_group_enabled_; |
| 66 name_ = other.name_; | 66 name_ = other->name_; |
| 67 if (other.flags_ & TRACE_EVENT_FLAG_HAS_PROCESS_ID) | 67 if (other->flags_ & TRACE_EVENT_FLAG_HAS_PROCESS_ID) |
| 68 process_id_ = other.process_id_; | 68 process_id_ = other->process_id_; |
| 69 else | 69 else |
| 70 thread_id_ = other.thread_id_; | 70 thread_id_ = other->thread_id_; |
| 71 phase_ = other.phase_; | 71 phase_ = other->phase_; |
| 72 flags_ = other.flags_; | 72 flags_ = other->flags_; |
| 73 parameter_copy_storage_ = other.parameter_copy_storage_; | 73 parameter_copy_storage_ = std::move(other->parameter_copy_storage_); |
| 74 | 74 |
| 75 for (int i = 0; i < kTraceMaxNumArgs; ++i) { | 75 for (int i = 0; i < kTraceMaxNumArgs; ++i) { |
| 76 arg_names_[i] = other.arg_names_[i]; | 76 arg_names_[i] = other->arg_names_[i]; |
| 77 arg_types_[i] = other.arg_types_[i]; | 77 arg_types_[i] = other->arg_types_[i]; |
| 78 arg_values_[i] = other.arg_values_[i]; | 78 arg_values_[i] = other->arg_values_[i]; |
| 79 convertable_values_[i] = other.convertable_values_[i]; | 79 convertable_values_[i] = std::move(other->convertable_values_[i]); |
| 80 } | 80 } |
| 81 } | 81 } |
| 82 | 82 |
| 83 void TraceEvent::Initialize( | 83 void TraceEvent::Initialize( |
| 84 int thread_id, | 84 int thread_id, |
| 85 TimeTicks timestamp, | 85 TimeTicks timestamp, |
| 86 ThreadTicks thread_timestamp, | 86 ThreadTicks thread_timestamp, |
| 87 char phase, | 87 char phase, |
| 88 const unsigned char* category_group_enabled, | 88 const unsigned char* category_group_enabled, |
| 89 const char* name, | 89 const char* name, |
| 90 const char* scope, | 90 const char* scope, |
| 91 unsigned long long id, | 91 unsigned long long id, |
| 92 unsigned long long bind_id, | 92 unsigned long long bind_id, |
| 93 int num_args, | 93 int num_args, |
| 94 const char** arg_names, | 94 const char** arg_names, |
| 95 const unsigned char* arg_types, | 95 const unsigned char* arg_types, |
| 96 const unsigned long long* arg_values, | 96 const unsigned long long* arg_values, |
| 97 const scoped_refptr<ConvertableToTraceFormat>* convertable_values, | 97 scoped_ptr<ConvertableToTraceFormat>* convertable_values, |
| 98 unsigned int flags) { | 98 unsigned int flags) { |
| 99 timestamp_ = timestamp; | 99 timestamp_ = timestamp; |
| 100 thread_timestamp_ = thread_timestamp; | 100 thread_timestamp_ = thread_timestamp; |
| 101 duration_ = TimeDelta::FromInternalValue(-1); | 101 duration_ = TimeDelta::FromInternalValue(-1); |
| 102 scope_ = scope; | 102 scope_ = scope; |
| 103 id_ = id; | 103 id_ = id; |
| 104 category_group_enabled_ = category_group_enabled; | 104 category_group_enabled_ = category_group_enabled; |
| 105 name_ = name; | 105 name_ = name; |
| 106 thread_id_ = thread_id; | 106 thread_id_ = thread_id; |
| 107 phase_ = phase; | 107 phase_ = phase; |
| 108 flags_ = flags; | 108 flags_ = flags; |
| 109 bind_id_ = bind_id; | 109 bind_id_ = bind_id; |
| 110 | 110 |
| 111 // Clamp num_args since it may have been set by a third_party library. | 111 // Clamp num_args since it may have been set by a third_party library. |
| 112 num_args = (num_args > kTraceMaxNumArgs) ? kTraceMaxNumArgs : num_args; | 112 num_args = (num_args > kTraceMaxNumArgs) ? kTraceMaxNumArgs : num_args; |
| 113 int i = 0; | 113 int i = 0; |
| 114 for (; i < num_args; ++i) { | 114 for (; i < num_args; ++i) { |
| 115 arg_names_[i] = arg_names[i]; | 115 arg_names_[i] = arg_names[i]; |
| 116 arg_types_[i] = arg_types[i]; | 116 arg_types_[i] = arg_types[i]; |
| 117 | 117 |
| 118 if (arg_types[i] == TRACE_VALUE_TYPE_CONVERTABLE) | 118 if (arg_types[i] == TRACE_VALUE_TYPE_CONVERTABLE) { |
| 119 convertable_values_[i] = convertable_values[i]; | 119 convertable_values_[i] = std::move(convertable_values[i]); |
| 120 else | 120 } else { |
| 121 arg_values_[i].as_uint = arg_values[i]; | 121 arg_values_[i].as_uint = arg_values[i]; |
| 122 convertable_values_[i].reset(); |
| 123 } |
| 122 } | 124 } |
| 123 for (; i < kTraceMaxNumArgs; ++i) { | 125 for (; i < kTraceMaxNumArgs; ++i) { |
| 124 arg_names_[i] = NULL; | 126 arg_names_[i] = NULL; |
| 125 arg_values_[i].as_uint = 0u; | 127 arg_values_[i].as_uint = 0u; |
| 126 convertable_values_[i] = NULL; | 128 convertable_values_[i].reset(); |
| 127 arg_types_[i] = TRACE_VALUE_TYPE_UINT; | 129 arg_types_[i] = TRACE_VALUE_TYPE_UINT; |
| 128 } | 130 } |
| 129 | 131 |
| 130 bool copy = !!(flags & TRACE_EVENT_FLAG_COPY); | 132 bool copy = !!(flags & TRACE_EVENT_FLAG_COPY); |
| 131 size_t alloc_size = 0; | 133 size_t alloc_size = 0; |
| 132 if (copy) { | 134 if (copy) { |
| 133 alloc_size += GetAllocLength(name) + GetAllocLength(scope); | 135 alloc_size += GetAllocLength(name) + GetAllocLength(scope); |
| 134 for (i = 0; i < num_args; ++i) { | 136 for (i = 0; i < num_args; ++i) { |
| 135 alloc_size += GetAllocLength(arg_names_[i]); | 137 alloc_size += GetAllocLength(arg_names_[i]); |
| 136 if (arg_types_[i] == TRACE_VALUE_TYPE_STRING) | 138 if (arg_types_[i] == TRACE_VALUE_TYPE_STRING) |
| 137 arg_types_[i] = TRACE_VALUE_TYPE_COPY_STRING; | 139 arg_types_[i] = TRACE_VALUE_TYPE_COPY_STRING; |
| 138 } | 140 } |
| 139 } | 141 } |
| 140 | 142 |
| 141 bool arg_is_copy[kTraceMaxNumArgs]; | 143 bool arg_is_copy[kTraceMaxNumArgs]; |
| 142 for (i = 0; i < num_args; ++i) { | 144 for (i = 0; i < num_args; ++i) { |
| 143 // No copying of convertable types, we retain ownership. | 145 // No copying of convertable types, we retain ownership. |
| 144 if (arg_types_[i] == TRACE_VALUE_TYPE_CONVERTABLE) | 146 if (arg_types_[i] == TRACE_VALUE_TYPE_CONVERTABLE) |
| 145 continue; | 147 continue; |
| 146 | 148 |
| 147 // We only take a copy of arg_vals if they are of type COPY_STRING. | 149 // We only take a copy of arg_vals if they are of type COPY_STRING. |
| 148 arg_is_copy[i] = (arg_types_[i] == TRACE_VALUE_TYPE_COPY_STRING); | 150 arg_is_copy[i] = (arg_types_[i] == TRACE_VALUE_TYPE_COPY_STRING); |
| 149 if (arg_is_copy[i]) | 151 if (arg_is_copy[i]) |
| 150 alloc_size += GetAllocLength(arg_values_[i].as_string); | 152 alloc_size += GetAllocLength(arg_values_[i].as_string); |
| 151 } | 153 } |
| 152 | 154 |
| 153 if (alloc_size) { | 155 if (alloc_size) { |
| 154 parameter_copy_storage_ = new RefCountedString; | 156 parameter_copy_storage_.reset(new std::string); |
| 155 parameter_copy_storage_->data().resize(alloc_size); | 157 parameter_copy_storage_->resize(alloc_size); |
| 156 char* ptr = string_as_array(¶meter_copy_storage_->data()); | 158 char* ptr = string_as_array(parameter_copy_storage_.get()); |
| 157 const char* end = ptr + alloc_size; | 159 const char* end = ptr + alloc_size; |
| 158 if (copy) { | 160 if (copy) { |
| 159 CopyTraceEventParameter(&ptr, &name_, end); | 161 CopyTraceEventParameter(&ptr, &name_, end); |
| 160 CopyTraceEventParameter(&ptr, &scope_, end); | 162 CopyTraceEventParameter(&ptr, &scope_, end); |
| 161 for (i = 0; i < num_args; ++i) { | 163 for (i = 0; i < num_args; ++i) { |
| 162 CopyTraceEventParameter(&ptr, &arg_names_[i], end); | 164 CopyTraceEventParameter(&ptr, &arg_names_[i], end); |
| 163 } | 165 } |
| 164 } | 166 } |
| 165 for (i = 0; i < num_args; ++i) { | 167 for (i = 0; i < num_args; ++i) { |
| 166 if (arg_types_[i] == TRACE_VALUE_TYPE_CONVERTABLE) | 168 if (arg_types_[i] == TRACE_VALUE_TYPE_CONVERTABLE) |
| 167 continue; | 169 continue; |
| 168 if (arg_is_copy[i]) | 170 if (arg_is_copy[i]) |
| 169 CopyTraceEventParameter(&ptr, &arg_values_[i].as_string, end); | 171 CopyTraceEventParameter(&ptr, &arg_values_[i].as_string, end); |
| 170 } | 172 } |
| 171 DCHECK_EQ(end, ptr) << "Overrun by " << ptr - end; | 173 DCHECK_EQ(end, ptr) << "Overrun by " << ptr - end; |
| 172 } | 174 } |
| 173 } | 175 } |
| 174 | 176 |
| 175 void TraceEvent::Reset() { | 177 void TraceEvent::Reset() { |
| 176 // Only reset fields that won't be initialized in Initialize(), or that may | 178 // Only reset fields that won't be initialized in Initialize(), or that may |
| 177 // hold references to other objects. | 179 // hold references to other objects. |
| 178 duration_ = TimeDelta::FromInternalValue(-1); | 180 duration_ = TimeDelta::FromInternalValue(-1); |
| 179 parameter_copy_storage_ = NULL; | 181 parameter_copy_storage_.reset(); |
| 180 for (int i = 0; i < kTraceMaxNumArgs; ++i) | 182 for (int i = 0; i < kTraceMaxNumArgs; ++i) |
| 181 convertable_values_[i] = NULL; | 183 convertable_values_[i].reset(); |
| 182 } | 184 } |
| 183 | 185 |
| 184 void TraceEvent::UpdateDuration(const TimeTicks& now, | 186 void TraceEvent::UpdateDuration(const TimeTicks& now, |
| 185 const ThreadTicks& thread_now) { | 187 const ThreadTicks& thread_now) { |
| 186 DCHECK_EQ(duration_.ToInternalValue(), -1); | 188 DCHECK_EQ(duration_.ToInternalValue(), -1); |
| 187 duration_ = now - timestamp_; | 189 duration_ = now - timestamp_; |
| 188 | 190 |
| 189 // |thread_timestamp_| can be empty if the thread ticks clock wasn't | 191 // |thread_timestamp_| can be empty if the thread ticks clock wasn't |
| 190 // initialized when it was recorded. | 192 // initialized when it was recorded. |
| 191 if (thread_timestamp_ != ThreadTicks()) | 193 if (thread_timestamp_ != ThreadTicks()) |
| 192 thread_duration_ = thread_now - thread_timestamp_; | 194 thread_duration_ = thread_now - thread_timestamp_; |
| 193 } | 195 } |
| 194 | 196 |
| 195 void TraceEvent::EstimateTraceMemoryOverhead( | 197 void TraceEvent::EstimateTraceMemoryOverhead( |
| 196 TraceEventMemoryOverhead* overhead) { | 198 TraceEventMemoryOverhead* overhead) { |
| 197 overhead->Add("TraceEvent", sizeof(*this)); | 199 overhead->Add("TraceEvent", sizeof(*this)); |
| 198 | 200 |
| 199 // TODO(primiano): parameter_copy_storage_ is refcounted and, in theory, | |
| 200 // could be shared by several events and we might overcount. In practice | |
| 201 // this is unlikely but it's worth checking. | |
| 202 if (parameter_copy_storage_) | 201 if (parameter_copy_storage_) |
| 203 overhead->AddRefCountedString(*parameter_copy_storage_.get()); | 202 overhead->AddString(*parameter_copy_storage_); |
| 204 | 203 |
| 205 for (size_t i = 0; i < kTraceMaxNumArgs; ++i) { | 204 for (size_t i = 0; i < kTraceMaxNumArgs; ++i) { |
| 206 if (arg_types_[i] == TRACE_VALUE_TYPE_CONVERTABLE) | 205 if (arg_types_[i] == TRACE_VALUE_TYPE_CONVERTABLE) |
| 207 convertable_values_[i]->EstimateTraceMemoryOverhead(overhead); | 206 convertable_values_[i]->EstimateTraceMemoryOverhead(overhead); |
| 208 } | 207 } |
| 209 } | 208 } |
| 210 | 209 |
| 211 // static | 210 // static |
| 212 void TraceEvent::AppendValueAsJSON(unsigned char type, | 211 void TraceEvent::AppendValueAsJSON(unsigned char type, |
| 213 TraceEvent::TraceValue value, | 212 TraceEvent::TraceValue value, |
| (...skipping 204 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 418 AppendValueAsJSON(arg_types_[i], arg_values_[i], &value_as_text); | 417 AppendValueAsJSON(arg_types_[i], arg_values_[i], &value_as_text); |
| 419 | 418 |
| 420 *out << value_as_text; | 419 *out << value_as_text; |
| 421 } | 420 } |
| 422 *out << "}"; | 421 *out << "}"; |
| 423 } | 422 } |
| 424 } | 423 } |
| 425 | 424 |
| 426 } // namespace trace_event | 425 } // namespace trace_event |
| 427 } // namespace base | 426 } // namespace base |
| OLD | NEW |