| Index: base/debug/trace_event.cc
|
| diff --git a/base/debug/trace_event.cc b/base/debug/trace_event.cc
|
| index 879f3a978f9361900a8658b61c4ead4ef5f75f0b..3f321018417d5a9027d003c046418adf77547678 100644
|
| --- a/base/debug/trace_event.cc
|
| +++ b/base/debug/trace_event.cc
|
| @@ -5,18 +5,22 @@
|
| #include "base/debug/trace_event.h"
|
|
|
| #include <algorithm>
|
| +#include <math.h>
|
|
|
| #if defined(OS_WIN)
|
| #include "base/debug/trace_event_win.h"
|
| #endif
|
| #include "base/format_macros.h"
|
| +#include "base/json/json_reader.h"
|
| #include "base/memory/ref_counted_memory.h"
|
| +#include "base/memory/scoped_ptr.h"
|
| #include "base/process_util.h"
|
| #include "base/stringprintf.h"
|
| #include "base/threading/thread_local.h"
|
| #include "base/utf_string_conversions.h"
|
| #include "base/stl_util.h"
|
| #include "base/time.h"
|
| +#include "base/values.h"
|
|
|
| #define USE_UNRELIABLE_NOW
|
|
|
| @@ -126,6 +130,21 @@ const char* GetPhaseStr(TraceEventPhase phase) {
|
| }
|
| }
|
|
|
| +TraceEventPhase GetPhaseFromStr(const char* phase) {
|
| + switch(*phase) {
|
| + case 'B':
|
| + return TRACE_EVENT_PHASE_BEGIN;
|
| + case 'I':
|
| + return TRACE_EVENT_PHASE_INSTANT;
|
| + case 'E':
|
| + return TRACE_EVENT_PHASE_END;
|
| + case 'M':
|
| + return TRACE_EVENT_PHASE_METADATA;
|
| + default:
|
| + return TRACE_EVENT_PHASE_BEGIN;
|
| + }
|
| +}
|
| +
|
| size_t GetAllocLength(const char* str) { return str ? strlen(str) + 1 : 0; }
|
|
|
| // Copies |*member| into |*buffer|, sets |*member| to point to this new
|
| @@ -143,6 +162,112 @@ void CopyTraceEventParameter(char** buffer,
|
|
|
| } // namespace
|
|
|
| +TestTraceEvent::TestTraceEvent()
|
| + : pid_tid(0, 0),
|
| + timestamp(0),
|
| + phase(TRACE_EVENT_PHASE_BEGIN),
|
| + other_event(NULL) {
|
| +}
|
| +
|
| +TestTraceEvent::TestTraceEvent(const base::Value* event_value)
|
| + : pid_tid(0, 0),
|
| + timestamp(0),
|
| + phase(TRACE_EVENT_PHASE_BEGIN),
|
| + other_event(NULL) {
|
| + if (event_value->GetType() != base::Value::TYPE_DICTIONARY)
|
| + return;
|
| + const base::DictionaryValue* dictionary =
|
| + static_cast<const base::DictionaryValue*>(event_value);
|
| +
|
| + std::string phase_str;
|
| + base::DictionaryValue* args = NULL;
|
| +
|
| + if (dictionary->GetInteger("pid", &pid_tid.pid) &&
|
| + dictionary->GetInteger("tid", &pid_tid.tid) &&
|
| + dictionary->GetDouble("ts", ×tamp) &&
|
| + dictionary->GetString("cat", &category) &&
|
| + dictionary->GetString("name", &name) &&
|
| + dictionary->GetString("ph", &phase_str) &&
|
| + dictionary->GetDictionary("args", &args)) {
|
| +
|
| + phase = GetPhaseFromStr(phase_str.c_str());
|
| +
|
| + // For each argument, copy the type and create a TraceValue.
|
| + base::DictionaryValue::key_iterator keyi = args->begin_keys();
|
| + for (; keyi != args->end_keys(); ++keyi) {
|
| + std::string str;
|
| + bool boolean = false;
|
| + int int_num = 0;
|
| + double double_num = 0.0;
|
| + Value* value = NULL;
|
| + if (args->GetWithoutPathExpansion(*keyi, &value)) {
|
| + if (value->GetAsString(&str))
|
| + arg_strings[*keyi] = str;
|
| + else if (value->GetAsInteger(&int_num))
|
| + arg_numbers[*keyi] = static_cast<double>(int_num);
|
| + else if (value->GetAsBoolean(&boolean))
|
| + arg_numbers[*keyi] = static_cast<double>(boolean ? 1 : 0);
|
| + else if (value->GetAsDouble(&double_num))
|
| + arg_numbers[*keyi] = double_num;
|
| + }
|
| + }
|
| + }
|
| +}
|
| +
|
| +TestTraceEvent::~TestTraceEvent() {
|
| +}
|
| +
|
| +bool TestTraceEvent::ParseEventsFromJson(const std::string& json,
|
| + std::vector<TestTraceEvent>* output) {
|
| + scoped_ptr<base::Value> root;
|
| + root.reset(base::JSONReader::Read(json, false));
|
| +
|
| + ListValue* root_list = NULL;
|
| + if (!root.get() || !root->GetAsList(&root_list))
|
| + return false;
|
| +
|
| + for (size_t i = 0; i < root_list->GetSize(); ++i) {
|
| + Value* item = NULL;
|
| + if (root_list->Get(i, &item))
|
| + output->push_back(TestTraceEvent(item));
|
| + }
|
| +
|
| + return true;
|
| +}
|
| +
|
| +bool TestTraceEvent::GetDuration(double* duration) const {
|
| + if (!other_event)
|
| + return false;
|
| +
|
| + *duration = fabs(other_event->timestamp - timestamp);
|
| + return true;
|
| +}
|
| +
|
| +bool TestTraceEvent::IsArg(const std::string& name) const {
|
| + return arg_numbers.find(name) != arg_numbers.end() ||
|
| + arg_strings.find(name) != arg_strings.end();
|
| +}
|
| +
|
| +bool TestTraceEvent::GetArgAsString(const std::string& name,
|
| + std::string* arg) const {
|
| + std::map<std::string, std::string>::const_iterator i = arg_strings.find(name);
|
| + if (i != arg_strings.end()) {
|
| + *arg = i->second;
|
| + return true;
|
| + }
|
| + return false;
|
| +}
|
| +
|
| +bool TestTraceEvent::GetArgAsNumber(const std::string& name,
|
| + double* arg) const {
|
| + std::map<std::string, double>::const_iterator i = arg_numbers.find(name);
|
| + if (i != arg_numbers.end()) {
|
| + *arg = i->second;
|
| + return true;
|
| + }
|
| + return false;
|
| +}
|
| +
|
| TraceEvent::TraceEvent()
|
| : process_id_(0),
|
| thread_id_(0),
|
|
|