summaryrefslogtreecommitdiffstats
path: root/content/browser
diff options
context:
space:
mode:
authorwangxianzhu@chromium.org <wangxianzhu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-12-03 19:48:19 +0000
committerwangxianzhu@chromium.org <wangxianzhu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-12-03 19:48:19 +0000
commit6174a36970df96acaa6a4bc00bb46727ddb6e7a7 (patch)
treefd540c556137ed279c13ddabe8ac3f0ed0fb3697 /content/browser
parent6a3ad06b4dc301ff395a13605e7ab7439d9680d4 (diff)
downloadchromium_src-6174a36970df96acaa6a4bc00bb46727ddb6e7a7.zip
chromium_src-6174a36970df96acaa6a4bc00bb46727ddb6e7a7.tar.gz
chromium_src-6174a36970df96acaa6a4bc00bb46727ddb6e7a7.tar.bz2
Reapply "Remove TraceController"
This reverts https://codereview.chromium.org/101543004/ which was created when suspected the reason of failure of telemetry tests, but turned out not the real reason. Reapply. Reapply the following change: > Revert "Revert 237280 "Remove TraceController"" > > This reverts commit 6aa58b8599840160df945afa89e7482d14d1c4d4. > > Fixed double-close issue when ending recording. > > > Revert 237280 "Remove TraceController" > > > > Seems to have broken trace-based telemetry benchmarks on android. > > > > BUG=323749 > > > > > Remove TraceController > > > > > > TraceController is obsoleted by TracingController. > > > Changed all remaining clients to use TracingController. > > > > > > BUG=none > > > > > > Review URL: https://codereview.chromium.org/67683003 > > > > TBR=wangxianzhu@chromium.org > > > > Review URL: https://codereview.chromium.org/89753004 > > > > git-svn-id: svn://svn.chromium.org/chrome/trunk/src@237452 0039d316-1c4b-4281-b951-d872f2087c98 > > TBR=wangxianzhu@chromium.org > > Committed: https://src.chromium.org/viewvc/chrome?view=rev&revision=238234 TBR= Review URL: https://codereview.chromium.org/102003003 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@238442 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'content/browser')
-rw-r--r--content/browser/android/tracing_controller_android.cc67
-rw-r--r--content/browser/android/tracing_controller_android.h10
-rw-r--r--content/browser/devtools/devtools_tracing_handler.cc112
-rw-r--r--content/browser/devtools/devtools_tracing_handler.h26
-rw-r--r--content/browser/renderer_host/render_process_host_impl.cc1
-rw-r--r--content/browser/tracing/trace_controller_impl.cc371
-rw-r--r--content/browser/tracing/trace_controller_impl.h105
-rw-r--r--content/browser/tracing/trace_message_filter.cc23
-rw-r--r--content/browser/tracing/trace_message_filter.h2
-rw-r--r--content/browser/tracing/trace_subscriber_stdio.cc201
-rw-r--r--content/browser/tracing/trace_subscriber_stdio.h57
-rw-r--r--content/browser/tracing/trace_subscriber_stdio_unittest.cc132
-rw-r--r--content/browser/tracing/tracing_controller_browsertest.cc15
-rw-r--r--content/browser/tracing/tracing_controller_impl.cc172
-rw-r--r--content/browser/tracing/tracing_controller_impl.h39
-rw-r--r--content/browser/tracing/tracing_ui.cc5
16 files changed, 287 insertions, 1051 deletions
diff --git a/content/browser/android/tracing_controller_android.cc b/content/browser/android/tracing_controller_android.cc
index 42d147e..75ac6d7 100644
--- a/content/browser/android/tracing_controller_android.cc
+++ b/content/browser/android/tracing_controller_android.cc
@@ -6,12 +6,9 @@
#include "base/android/jni_android.h"
#include "base/android/jni_string.h"
-#include "base/command_line.h"
#include "base/debug/trace_event.h"
-#include "base/files/file_path.h"
#include "base/logging.h"
-#include "content/browser/tracing/trace_subscriber_stdio.h"
-#include "content/public/browser/trace_controller.h"
+#include "content/public/browser/tracing_controller.h"
#include "jni/TracingControllerAndroid_jni.h"
namespace content {
@@ -21,29 +18,9 @@ static jlong Init(JNIEnv* env, jobject obj) {
return reinterpret_cast<intptr_t>(profiler);
}
-class TracingControllerAndroid::Subscriber
- : public content::TraceSubscriberStdio {
- public:
- Subscriber(TracingControllerAndroid* profiler, const base::FilePath& path)
- : TraceSubscriberStdio(path, FILE_TYPE_ARRAY, false),
- profiler_(profiler) {}
-
- void set_profiler(TracingControllerAndroid* profiler) {
- CHECK(!profiler_);
- profiler_ = profiler;
- }
-
- virtual void OnEndTracingComplete() OVERRIDE {
- TraceSubscriberStdio::OnEndTracingComplete();
- profiler_->OnTracingStopped();
- }
-
- private:
- TracingControllerAndroid* profiler_;
-};
-
TracingControllerAndroid::TracingControllerAndroid(JNIEnv* env, jobject obj)
- : weak_java_object_(env, obj) {}
+ : weak_java_object_(env, obj),
+ weak_factory_(this) {}
TracingControllerAndroid::~TracingControllerAndroid() {}
@@ -56,39 +33,37 @@ bool TracingControllerAndroid::StartTracing(JNIEnv* env,
jstring jfilename,
jstring jcategories,
jboolean record_continuously) {
- if (subscriber_.get()) {
- return false;
- }
- std::string filename = base::android::ConvertJavaStringToUTF8(env, jfilename);
+ file_path_ = base::FilePath(
+ base::android::ConvertJavaStringToUTF8(env, jfilename));
std::string categories =
base::android::ConvertJavaStringToUTF8(env, jcategories);
- subscriber_.reset(new Subscriber(this, base::FilePath(filename)));
- return TraceController::GetInstance()->BeginTracing(
- subscriber_.get(),
+
+ // This log is required by adb_profile_chrome.py.
+ LOG(WARNING) << "Logging performance trace to file: " << file_path_.value();
+
+ return TracingController::GetInstance()->EnableRecording(
categories,
- record_continuously ? base::debug::TraceLog::RECORD_CONTINUOUSLY
- : base::debug::TraceLog::RECORD_UNTIL_FULL);
+ record_continuously ? TracingController::RECORD_CONTINUOUSLY
+ : TracingController::DEFAULT_OPTIONS,
+ TracingController::EnableRecordingDoneCallback());
}
void TracingControllerAndroid::StopTracing(JNIEnv* env, jobject obj) {
- if (!subscriber_.get()) {
- return;
- }
- TraceController* controller = TraceController::GetInstance();
- if (!controller->EndTracingAsync(subscriber_.get())) {
+ if (!TracingController::GetInstance()->DisableRecording(
+ file_path_,
+ base::Bind(&TracingControllerAndroid::OnTracingStopped,
+ weak_factory_.GetWeakPtr()))) {
LOG(ERROR) << "EndTracingAsync failed, forcing an immediate stop";
- controller->CancelSubscriber(subscriber_.get());
- OnTracingStopped();
+ OnTracingStopped(file_path_);
}
}
-void TracingControllerAndroid::OnTracingStopped() {
+void TracingControllerAndroid::OnTracingStopped(
+ const base::FilePath& file_path) {
JNIEnv* env = base::android::AttachCurrentThread();
base::android::ScopedJavaLocalRef<jobject> obj = weak_java_object_.get(env);
- if (obj.obj()) {
+ if (obj.obj())
Java_TracingControllerAndroid_onTracingStopped(env, obj.obj());
- }
- subscriber_.reset();
}
static jstring GetDefaultCategories(JNIEnv* env, jobject obj) {
diff --git a/content/browser/android/tracing_controller_android.h b/content/browser/android/tracing_controller_android.h
index 0cd310e..4d70e7b 100644
--- a/content/browser/android/tracing_controller_android.h
+++ b/content/browser/android/tracing_controller_android.h
@@ -6,7 +6,8 @@
#define CONTENT_BROWSER_ANDROID_TRACING_CONTROLLER_ANDROID_H_
#include "base/android/jni_helper.h"
-#include "base/memory/scoped_ptr.h"
+#include "base/files/file_path.h"
+#include "base/memory/weak_ptr.h"
namespace content {
@@ -25,12 +26,11 @@ class TracingControllerAndroid {
private:
~TracingControllerAndroid();
- void OnTracingStopped();
+ void OnTracingStopped(const base::FilePath& file_path);
JavaObjectWeakGlobalRef weak_java_object_;
-
- class Subscriber;
- scoped_ptr<Subscriber> subscriber_;
+ base::FilePath file_path_;
+ base::WeakPtrFactory<TracingControllerAndroid> weak_factory_;
DISALLOW_COPY_AND_ASSIGN(TracingControllerAndroid);
};
diff --git a/content/browser/devtools/devtools_tracing_handler.cc b/content/browser/devtools/devtools_tracing_handler.cc
index 0657b8e..0e1869a 100644
--- a/content/browser/devtools/devtools_tracing_handler.cc
+++ b/content/browser/devtools/devtools_tracing_handler.cc
@@ -6,14 +6,18 @@
#include "base/bind.h"
#include "base/callback.h"
+#include "base/file_util.h"
+#include "base/json/json_reader.h"
+#include "base/json/json_writer.h"
#include "base/location.h"
+#include "base/memory/ref_counted_memory.h"
#include "base/strings/string_split.h"
#include "base/strings/stringprintf.h"
#include "base/values.h"
#include "content/browser/devtools/devtools_http_handler_impl.h"
#include "content/browser/devtools/devtools_protocol_constants.h"
-#include "content/public/browser/trace_controller.h"
-#include "content/public/browser/trace_subscriber.h"
+#include "content/public/browser/browser_thread.h"
+#include "content/public/browser/tracing_controller.h"
namespace content {
@@ -23,10 +27,23 @@ const char kRecordUntilFull[] = "record-until-full";
const char kRecordContinuously[] = "record-continuously";
const char kEnableSampling[] = "enable-sampling";
+void ReadFile(
+ const base::FilePath& path,
+ const base::Callback<void(const scoped_refptr<base::RefCountedString>&)>
+ callback) {
+ std::string trace_data;
+ if (!base::ReadFileToString(path, &trace_data))
+ LOG(ERROR) << "Failed to read file: " << path.value();
+ base::DeleteFile(path, false);
+ BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
+ base::Bind(callback, make_scoped_refptr(
+ base::RefCountedString::TakeString(&trace_data))));
+}
+
} // namespace
DevToolsTracingHandler::DevToolsTracingHandler()
- : is_running_(false) {
+ : weak_factory_(this) {
RegisterCommandHandler(devtools::Tracing::start::kName,
base::Bind(&DevToolsTracingHandler::OnStart,
base::Unretained(this)));
@@ -38,28 +55,60 @@ DevToolsTracingHandler::DevToolsTracingHandler()
DevToolsTracingHandler::~DevToolsTracingHandler() {
}
-void DevToolsTracingHandler::OnEndTracingComplete() {
- is_running_ = false;
+void DevToolsTracingHandler::BeginReadingRecordingResult(
+ const base::FilePath& path) {
+ BrowserThread::PostTask(
+ BrowserThread::FILE, FROM_HERE,
+ base::Bind(&ReadFile, path,
+ base::Bind(&DevToolsTracingHandler::ReadRecordingResult,
+ weak_factory_.GetWeakPtr())));
+}
+
+void DevToolsTracingHandler::ReadRecordingResult(
+ const scoped_refptr<base::RefCountedString>& trace_data) {
+ if (trace_data->data().size()) {
+ scoped_ptr<base::Value> trace_value(base::JSONReader::Read(
+ trace_data->data()));
+ DictionaryValue* dictionary = NULL;
+ bool ok = trace_value->GetAsDictionary(&dictionary);
+ DCHECK(ok);
+ ListValue* list = NULL;
+ ok = dictionary->GetList("traceEvents", &list);
+ DCHECK(ok);
+ std::string buffer;
+ for (size_t i = 0; i < list->GetSize(); ++i) {
+ std::string item;
+ base::Value* item_value;
+ list->Get(i, &item_value);
+ base::JSONWriter::Write(item_value, &item);
+ if (buffer.size())
+ buffer.append(",");
+ buffer.append(item);
+ if (i % 1000 == 0) {
+ OnTraceDataCollected(buffer);
+ buffer.clear();
+ }
+ }
+ if (buffer.size())
+ OnTraceDataCollected(buffer);
+ }
+
SendNotification(devtools::Tracing::tracingComplete::kName, NULL);
}
void DevToolsTracingHandler::OnTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& trace_fragment) {
- if (is_running_) {
- // Hand-craft protocol notification message so we can substitute JSON
- // that we already got as string as a bare object, not a quoted string.
- std::string message = base::StringPrintf(
- "{ \"method\": \"%s\", \"params\": { \"%s\": [ %s ] } }",
- devtools::Tracing::dataCollected::kName,
- devtools::Tracing::dataCollected::kValue,
- trace_fragment->data().c_str());
- SendRawMessage(message);
- }
+ const std::string& trace_fragment) {
+ // Hand-craft protocol notification message so we can substitute JSON
+ // that we already got as string as a bare object, not a quoted string.
+ std::string message = base::StringPrintf(
+ "{ \"method\": \"%s\", \"params\": { \"%s\": [ %s ] } }",
+ devtools::Tracing::dataCollected::kName,
+ devtools::Tracing::dataCollected::kValue,
+ trace_fragment.c_str());
+ SendRawMessage(message);
}
-// Note, if you add more options here you also need to update:
-// base/debug/trace_event_impl:TraceOptionsFromString
-base::debug::TraceLog::Options DevToolsTracingHandler::TraceOptionsFromString(
+TracingController::Options DevToolsTracingHandler::TraceOptionsFromString(
const std::string& options) {
std::vector<std::string> split;
std::vector<std::string>::iterator iter;
@@ -68,18 +117,14 @@ base::debug::TraceLog::Options DevToolsTracingHandler::TraceOptionsFromString(
base::SplitString(options, ',', &split);
for (iter = split.begin(); iter != split.end(); ++iter) {
if (*iter == kRecordUntilFull) {
- ret |= base::debug::TraceLog::RECORD_UNTIL_FULL;
+ ret &= ~TracingController::RECORD_CONTINUOUSLY;
} else if (*iter == kRecordContinuously) {
- ret |= base::debug::TraceLog::RECORD_CONTINUOUSLY;
+ ret |= TracingController::RECORD_CONTINUOUSLY;
} else if (*iter == kEnableSampling) {
- ret |= base::debug::TraceLog::ENABLE_SAMPLING;
+ ret |= TracingController::ENABLE_SAMPLING;
}
}
- if (!(ret & base::debug::TraceLog::RECORD_UNTIL_FULL) &&
- !(ret & base::debug::TraceLog::RECORD_CONTINUOUSLY))
- ret |= base::debug::TraceLog::RECORD_UNTIL_FULL;
-
- return static_cast<base::debug::TraceLog::Options>(ret);
+ return static_cast<TracingController::Options>(ret);
}
scoped_refptr<DevToolsProtocol::Response>
@@ -90,23 +135,26 @@ DevToolsTracingHandler::OnStart(
if (params)
params->GetString(devtools::Tracing::start::kCategories, &categories);
- base::debug::TraceLog::Options options =
- base::debug::TraceLog::RECORD_UNTIL_FULL;
+ TracingController::Options options = TracingController::DEFAULT_OPTIONS;
if (params && params->HasKey(devtools::Tracing::start::kTraceOptions)) {
std::string options_param;
params->GetString(devtools::Tracing::start::kTraceOptions, &options_param);
options = TraceOptionsFromString(options_param);
}
- TraceController::GetInstance()->BeginTracing(this, categories, options);
- is_running_ = true;
+ TracingController::GetInstance()->EnableRecording(
+ categories, options,
+ TracingController::EnableRecordingDoneCallback());
return command->SuccessResponse(NULL);
}
scoped_refptr<DevToolsProtocol::Response>
DevToolsTracingHandler::OnEnd(
scoped_refptr<DevToolsProtocol::Command> command) {
- TraceController::GetInstance()->EndTracingAsync(this);
+ TracingController::GetInstance()->DisableRecording(
+ base::FilePath(),
+ base::Bind(&DevToolsTracingHandler::BeginReadingRecordingResult,
+ weak_factory_.GetWeakPtr()));
return command->SuccessResponse(NULL);
}
diff --git a/content/browser/devtools/devtools_tracing_handler.h b/content/browser/devtools/devtools_tracing_handler.h
index 43cd615..b551e75 100644
--- a/content/browser/devtools/devtools_tracing_handler.h
+++ b/content/browser/devtools/devtools_tracing_handler.h
@@ -5,36 +5,36 @@
#ifndef CONTENT_BROWSER_DEVTOOLS_DEVTOOLS_TRACING_HANDLER_H_
#define CONTENT_BROWSER_DEVTOOLS_DEVTOOLS_TRACING_HANDLER_H_
-#include "base/debug/trace_event.h"
+#include "base/memory/weak_ptr.h"
#include "content/browser/devtools/devtools_protocol.h"
-#include "content/public/browser/trace_subscriber.h"
+#include "content/public/browser/tracing_controller.h"
+
+namespace base {
+class RefCountedString;
+}
namespace content {
// This class bridges DevTools remote debugging server with the trace
// infrastructure.
-class DevToolsTracingHandler
- : public TraceSubscriber,
- public DevToolsProtocol::Handler {
+class DevToolsTracingHandler : public DevToolsProtocol::Handler {
public:
DevToolsTracingHandler();
virtual ~DevToolsTracingHandler();
- // TraceSubscriber:
- virtual void OnEndTracingComplete() OVERRIDE;;
- virtual void OnTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& trace_fragment) OVERRIDE;
-
private:
+ void BeginReadingRecordingResult(const base::FilePath& path);
+ void ReadRecordingResult(const scoped_refptr<base::RefCountedString>& result);
+ void OnTraceDataCollected(const std::string& trace_fragment);
+
scoped_refptr<DevToolsProtocol::Response> OnStart(
scoped_refptr<DevToolsProtocol::Command> command);
scoped_refptr<DevToolsProtocol::Response> OnEnd(
scoped_refptr<DevToolsProtocol::Command> command);
- base::debug::TraceLog::Options TraceOptionsFromString(
- const std::string& options);
+ TracingController::Options TraceOptionsFromString(const std::string& options);
- bool is_running_;
+ base::WeakPtrFactory<DevToolsTracingHandler> weak_factory_;
DISALLOW_COPY_AND_ASSIGN(DevToolsTracingHandler);
};
diff --git a/content/browser/renderer_host/render_process_host_impl.cc b/content/browser/renderer_host/render_process_host_impl.cc
index da44fd8..90b14e6 100644
--- a/content/browser/renderer_host/render_process_host_impl.cc
+++ b/content/browser/renderer_host/render_process_host_impl.cc
@@ -101,7 +101,6 @@
#include "content/browser/speech/speech_recognition_dispatcher_host.h"
#include "content/browser/storage_partition_impl.h"
#include "content/browser/streams/stream_context.h"
-#include "content/browser/tracing/trace_controller_impl.h"
#include "content/browser/tracing/trace_message_filter.h"
#include "content/browser/vibration/vibration_message_filter.h"
#include "content/browser/webui/web_ui_controller_factory_registry.h"
diff --git a/content/browser/tracing/trace_controller_impl.cc b/content/browser/tracing/trace_controller_impl.cc
deleted file mode 100644
index 061e508..0000000
--- a/content/browser/tracing/trace_controller_impl.cc
+++ /dev/null
@@ -1,371 +0,0 @@
-// Copyright 2013 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 "content/browser/tracing/trace_controller_impl.h"
-
-#include "base/bind.h"
-#include "base/command_line.h"
-#include "base/debug/trace_event.h"
-#include "base/strings/string_number_conversions.h"
-#include "components/tracing/tracing_messages.h"
-#include "content/browser/tracing/trace_message_filter.h"
-#include "content/browser/tracing/trace_subscriber_stdio.h"
-#include "content/common/child_process_messages.h"
-#include "content/public/browser/browser_message_filter.h"
-#include "content/public/common/content_switches.h"
-
-using base::debug::TraceLog;
-
-namespace content {
-
-namespace {
-
-base::LazyInstance<TraceControllerImpl>::Leaky g_controller =
- LAZY_INSTANCE_INITIALIZER;
-
-} // namespace
-
-TraceController* TraceController::GetInstance() {
- return TraceControllerImpl::GetInstance();
-}
-
-TraceControllerImpl::TraceControllerImpl() :
- subscriber_(NULL),
- pending_end_ack_count_(0),
- pending_bpf_ack_count_(0),
- maximum_bpf_(0.0f),
- is_tracing_(false),
- is_get_category_groups_(false),
- category_filter_(
- base::debug::CategoryFilter::kDefaultCategoryFilterString) {
- TraceLog::GetInstance()->SetNotificationCallback(
- base::Bind(&TraceControllerImpl::OnTraceNotification,
- base::Unretained(this)));
-}
-
-TraceControllerImpl::~TraceControllerImpl() {
- // No need to SetNotificationCallback(nil) on the TraceLog since this is a
- // Leaky instance.
- NOTREACHED();
-}
-
-TraceControllerImpl* TraceControllerImpl::GetInstance() {
- return g_controller.Pointer();
-}
-
-bool TraceControllerImpl::GetKnownCategoryGroupsAsync(
- TraceSubscriber* subscriber) {
- DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
-
- // Known categories come back from child processes with the EndTracingAck
- // message. So to get known categories, just begin and end tracing immediately
- // afterwards. This will ping all the child processes for categories.
- is_get_category_groups_ = true;
- bool success = BeginTracing(subscriber, "*",
- TraceLog::GetInstance()->trace_options()) &&
- EndTracingAsync(subscriber);
- is_get_category_groups_ = success;
- return success;
-}
-
-bool TraceControllerImpl::BeginTracing(TraceSubscriber* subscriber,
- const std::string& category_patterns,
- base::debug::TraceLog::Options options) {
- DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
-
- if (!can_begin_tracing(subscriber))
- return false;
-
-#if defined(OS_ANDROID)
- if (!is_get_category_groups_)
- TraceLog::GetInstance()->AddClockSyncMetadataEvent();
-#endif
-
- // Enable tracing
- TraceLog::GetInstance()->SetEnabled(
- base::debug::CategoryFilter(category_patterns), options);
-
- OnTracingBegan(subscriber);
-
- return true;
-}
-
-bool TraceControllerImpl::EndTracingAsync(TraceSubscriber* subscriber) {
- DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
-
- if (!can_end_tracing() || subscriber != subscriber_)
- return false;
-
- // Disable local trace early to avoid traces during end-tracing process from
- // interfering with the process.
- TraceLog::GetInstance()->SetDisabled();
-
-#if defined(OS_ANDROID)
- if (!is_get_category_groups_)
- TraceLog::GetInstance()->AddClockSyncMetadataEvent();
-#endif
-
- // There could be a case where there are no child processes and filters_
- // is empty. In that case we can immediately tell the subscriber that tracing
- // has ended. To avoid recursive calls back to the subscriber, we will just
- // use the existing asynchronous OnEndTracingAck code.
- // Count myself (local trace) in pending_end_ack_count_, acked below.
- pending_end_ack_count_ = filters_.size() + 1;
-
- // Handle special case of zero child processes.
- if (pending_end_ack_count_ == 1) {
- // Ack asynchronously now, because we don't have any children to wait for.
- std::vector<std::string> category_groups;
- TraceLog::GetInstance()->GetKnownCategoryGroups(&category_groups);
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::OnEndTracingAck,
- base::Unretained(this), category_groups));
- }
-
- // Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
- it->get()->SendEndTracing();
- }
-
- return true;
-}
-
-bool TraceControllerImpl::GetTraceBufferPercentFullAsync(
- TraceSubscriber* subscriber) {
- DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
-
- if (!can_get_buffer_percent_full() || subscriber != subscriber_)
- return false;
-
- maximum_bpf_ = 0.0f;
- pending_bpf_ack_count_ = filters_.size() + 1;
-
- // Handle special case of zero child processes.
- if (pending_bpf_ack_count_ == 1) {
- // Ack asynchronously now, because we don't have any children to wait for.
- float bpf = TraceLog::GetInstance()->GetBufferPercentFull();
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::OnTraceBufferPercentFullReply,
- base::Unretained(this), bpf));
- }
-
- // Message all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
- it->get()->SendGetTraceBufferPercentFull();
- }
-
- return true;
-}
-
-bool TraceControllerImpl::SetWatchEvent(TraceSubscriber* subscriber,
- const std::string& category_name,
- const std::string& event_name) {
- DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
- if (subscriber != subscriber_)
- return false;
-
- watch_category_ = category_name;
- watch_name_ = event_name;
-
- TraceLog::GetInstance()->SetWatchEvent(category_name, event_name);
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it)
- it->get()->SendSetWatchEvent(category_name, event_name);
-
- return true;
-}
-
-bool TraceControllerImpl::CancelWatchEvent(TraceSubscriber* subscriber) {
- DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
- if (subscriber != subscriber_)
- return false;
-
- watch_category_.clear();
- watch_name_.clear();
-
- TraceLog::GetInstance()->CancelWatchEvent();
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it)
- it->get()->SendCancelWatchEvent();
-
- return true;
-}
-
-void TraceControllerImpl::CancelSubscriber(TraceSubscriber* subscriber) {
- DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
-
- if (subscriber == subscriber_) {
- subscriber_ = NULL;
- // End tracing if necessary.
- if (is_tracing_ && pending_end_ack_count_ == 0)
- EndTracingAsync(NULL);
- }
-}
-
-void TraceControllerImpl::AddFilter(TraceMessageFilter* filter) {
- if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::AddFilter, base::Unretained(this),
- make_scoped_refptr(filter)));
- return;
- }
-
- filters_.insert(filter);
- if (is_tracing_enabled()) {
- std::string cf_str = category_filter_.ToString();
- filter->SendBeginTracing(cf_str, trace_options_);
- if (!watch_category_.empty())
- filter->SendSetWatchEvent(watch_category_, watch_name_);
- }
-}
-
-void TraceControllerImpl::RemoveFilter(TraceMessageFilter* filter) {
- if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::RemoveFilter, base::Unretained(this),
- make_scoped_refptr(filter)));
- return;
- }
-
- filters_.erase(filter);
-}
-
-void TraceControllerImpl::OnTracingBegan(TraceSubscriber* subscriber) {
- is_tracing_ = true;
-
- subscriber_ = subscriber;
-
- category_filter_ = TraceLog::GetInstance()->GetCurrentCategoryFilter();
- trace_options_ = TraceLog::GetInstance()->trace_options();
-
- // Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
- it->get()->SendBeginTracing(category_filter_.ToString(), trace_options_);
- }
-}
-
-void TraceControllerImpl::OnEndTracingAck(
- const std::vector<std::string>& known_category_groups) {
- if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::OnEndTracingAck,
- base::Unretained(this), known_category_groups));
- return;
- }
-
- // Merge known_category_groups with known_category_groups_
- known_category_groups_.insert(known_category_groups.begin(),
- known_category_groups.end());
-
- if (pending_end_ack_count_ == 0)
- return;
-
-
- if (--pending_end_ack_count_ == 1) {
- // All acks from subprocesses have been received. Now flush the local trace.
- // During or after this call, our OnLocalTraceDataCollected will be
- // called with the last of the local trace data.
- TraceLog::GetInstance()->Flush(
- base::Bind(&TraceControllerImpl::OnLocalTraceDataCollected,
- base::Unretained(this)));
- }
-
- if (pending_end_ack_count_ == 0) {
- // All acks (including from the subprocesses and the local trace) have been
- // received.
- is_tracing_ = false;
-
- // Trigger callback if one is set.
- if (subscriber_) {
- if (is_get_category_groups_)
- subscriber_->OnKnownCategoriesCollected(known_category_groups_);
- else
- subscriber_->OnEndTracingComplete();
- // Clear subscriber so that others can use TraceController.
- subscriber_ = NULL;
- }
-
- is_get_category_groups_ = false;
- }
-}
-
-void TraceControllerImpl::OnTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& events_str_ptr) {
- // OnTraceDataCollected may be called from any browser thread, either by the
- // local event trace system or from child processes via TraceMessageFilter.
- if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::OnTraceDataCollected,
- base::Unretained(this), events_str_ptr));
- return;
- }
-
- // Drop trace events if we are just getting categories.
- if (subscriber_ && !is_get_category_groups_)
- subscriber_->OnTraceDataCollected(events_str_ptr);
-}
-
-void TraceControllerImpl::OnLocalTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& events_str_ptr,
- bool has_more_events) {
- if (events_str_ptr->data().size())
- OnTraceDataCollected(events_str_ptr);
-
- if (!has_more_events) {
- // Simulate an EndTrackingAck for the local trace.
- std::vector<std::string> category_groups;
- TraceLog::GetInstance()->GetKnownCategoryGroups(&category_groups);
- OnEndTracingAck(category_groups);
- }
-}
-
-void TraceControllerImpl::OnTraceNotification(int notification) {
- // OnTraceNotification may be called from any browser thread, either by the
- // local event trace system or from child processes via TraceMessageFilter.
- if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::OnTraceNotification,
- base::Unretained(this), notification));
- return;
- }
-
- if (notification & base::debug::TraceLog::TRACE_BUFFER_FULL) {
- // EndTracingAsync may return false if tracing is already in the process
- // of being ended. That is ok.
- EndTracingAsync(subscriber_);
- }
- if (notification & base::debug::TraceLog::EVENT_WATCH_NOTIFICATION) {
- if (subscriber_)
- subscriber_->OnEventWatchNotification();
- }
-}
-
-void TraceControllerImpl::OnTraceBufferPercentFullReply(float percent_full) {
- if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::OnTraceBufferPercentFullReply,
- base::Unretained(this), percent_full));
- return;
- }
-
- if (pending_bpf_ack_count_ == 0)
- return;
-
- maximum_bpf_ = (maximum_bpf_ > percent_full)? maximum_bpf_ : percent_full;
-
- if (--pending_bpf_ack_count_ == 0) {
- // Trigger callback if one is set.
- if (subscriber_)
- subscriber_->OnTraceBufferPercentFullReply(maximum_bpf_);
- }
-
- if (pending_bpf_ack_count_ == 1) {
- // The last ack represents local trace, so we need to ack it now. Note that
- // this code only executes if there were child processes.
- float bpf = TraceLog::GetInstance()->GetBufferPercentFull();
- BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TraceControllerImpl::OnTraceBufferPercentFullReply,
- base::Unretained(this), bpf));
- }
-}
-
-} // namespace content
diff --git a/content/browser/tracing/trace_controller_impl.h b/content/browser/tracing/trace_controller_impl.h
deleted file mode 100644
index fc993be..0000000
--- a/content/browser/tracing/trace_controller_impl.h
+++ /dev/null
@@ -1,105 +0,0 @@
-// Copyright 2013 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.
-
-#ifndef CONTENT_BROWSER_TRACING_TRACE_CONTROLLER_IMPL_H_
-#define CONTENT_BROWSER_TRACING_TRACE_CONTROLLER_IMPL_H_
-
-#include <set>
-#include <string>
-#include <vector>
-
-#include "base/debug/trace_event.h"
-#include "base/lazy_instance.h"
-#include "content/public/browser/trace_controller.h"
-
-class CommandLine;
-
-namespace content {
-class TraceMessageFilter;
-
-class TraceControllerImpl : public TraceController {
- public:
- static TraceControllerImpl* GetInstance();
-
- // TraceController implementation:
- virtual bool BeginTracing(TraceSubscriber* subscriber,
- const std::string& category_patterns,
- base::debug::TraceLog::Options options) OVERRIDE;
- virtual bool EndTracingAsync(TraceSubscriber* subscriber) OVERRIDE;
- virtual bool GetTraceBufferPercentFullAsync(
- TraceSubscriber* subscriber) OVERRIDE;
- virtual bool SetWatchEvent(TraceSubscriber* subscriber,
- const std::string& category_name,
- const std::string& event_name) OVERRIDE;
- virtual bool CancelWatchEvent(TraceSubscriber* subscriber) OVERRIDE;
- virtual void CancelSubscriber(TraceSubscriber* subscriber) OVERRIDE;
- virtual bool GetKnownCategoryGroupsAsync(TraceSubscriber* subscriber)
- OVERRIDE;
-
- private:
- typedef std::set<scoped_refptr<TraceMessageFilter> > FilterMap;
-
- friend struct base::DefaultLazyInstanceTraits<TraceControllerImpl>;
- friend class TraceMessageFilter;
-
- TraceControllerImpl();
- virtual ~TraceControllerImpl();
-
- bool is_tracing_enabled() const {
- return can_end_tracing();
- }
-
- bool can_end_tracing() const {
- return is_tracing_ && pending_end_ack_count_ == 0;
- }
-
- // Can get Buffer Percent Full
- bool can_get_buffer_percent_full() const {
- return is_tracing_ &&
- pending_end_ack_count_ == 0 &&
- pending_bpf_ack_count_ == 0;
- }
-
- bool can_begin_tracing(TraceSubscriber* subscriber) const {
- return !is_tracing_ &&
- (subscriber_ == NULL || subscriber == subscriber_);
- }
-
- // Methods for use by TraceMessageFilter.
-
- void AddFilter(TraceMessageFilter* filter);
- void RemoveFilter(TraceMessageFilter* filter);
- void OnTracingBegan(TraceSubscriber* subscriber);
- void OnEndTracingAck(const std::vector<std::string>& known_category_groups);
- void OnTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& events_str_ptr);
- void OnTraceNotification(int notification);
- void OnTraceBufferPercentFullReply(float percent_full);
-
- // Callback of TraceLog::Flush() for the local trace.
- void OnLocalTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& events_str_ptr,
- bool has_more_events);
-
- FilterMap filters_;
- TraceSubscriber* subscriber_;
- // Pending acks for EndTracingAsync:
- int pending_end_ack_count_;
- // Pending acks for GetTraceBufferPercentFullAsync:
- int pending_bpf_ack_count_;
- float maximum_bpf_;
- bool is_tracing_;
- bool is_get_category_groups_;
- std::set<std::string> known_category_groups_;
- std::string watch_category_;
- std::string watch_name_;
- base::debug::TraceLog::Options trace_options_;
- base::debug::CategoryFilter category_filter_;
-
- DISALLOW_COPY_AND_ASSIGN(TraceControllerImpl);
-};
-
-} // namespace content
-
-#endif // CONTENT_BROWSER_TRACING_TRACE_CONTROLLER_IMPL_H_
diff --git a/content/browser/tracing/trace_message_filter.cc b/content/browser/tracing/trace_message_filter.cc
index 00fffb9..35f23dc 100644
--- a/content/browser/tracing/trace_message_filter.cc
+++ b/content/browser/tracing/trace_message_filter.cc
@@ -5,7 +5,6 @@
#include "content/browser/tracing/trace_message_filter.h"
#include "components/tracing/tracing_messages.h"
-#include "content/browser/tracing/trace_controller_impl.h"
#include "content/browser/tracing/tracing_controller_impl.h"
namespace content {
@@ -17,6 +16,8 @@ TraceMessageFilter::TraceMessageFilter() :
is_awaiting_buffer_percent_full_ack_(false) {
}
+TraceMessageFilter::~TraceMessageFilter() {}
+
void TraceMessageFilter::OnChannelClosing() {
if (has_child_) {
if (is_awaiting_end_ack_)
@@ -28,8 +29,7 @@ void TraceMessageFilter::OnChannelClosing() {
if (is_awaiting_buffer_percent_full_ack_)
OnTraceBufferPercentFullReply(0.0f);
- TraceControllerImpl::GetInstance()->RemoveFilter(this);
- TracingControllerImpl::GetInstance()->RemoveFilter(this);
+ TracingControllerImpl::GetInstance()->RemoveTraceMessageFilter(this);
}
}
@@ -47,8 +47,8 @@ bool TraceMessageFilter::OnMessageReceived(const IPC::Message& message,
OnTraceDataCollected)
IPC_MESSAGE_HANDLER(TracingHostMsg_MonitoringTraceDataCollected,
OnMonitoringTraceDataCollected)
- IPC_MESSAGE_HANDLER(TracingHostMsg_TraceNotification,
- OnTraceNotification)
+ IPC_MESSAGE_HANDLER(TracingHostMsg_WatchEventMatched,
+ OnWatchEventMatched)
IPC_MESSAGE_HANDLER(TracingHostMsg_TraceBufferPercentFullReply,
OnTraceBufferPercentFullReply)
IPC_MESSAGE_UNHANDLED(handled = false)
@@ -109,12 +109,9 @@ void TraceMessageFilter::SendCancelWatchEvent() {
Send(new TracingMsg_CancelWatchEvent);
}
-TraceMessageFilter::~TraceMessageFilter() {}
-
void TraceMessageFilter::OnChildSupportsTracing() {
has_child_ = true;
- TraceControllerImpl::GetInstance()->AddFilter(this);
- TracingControllerImpl::GetInstance()->AddFilter(this);
+ TracingControllerImpl::GetInstance()->AddTraceMessageFilter(this);
}
void TraceMessageFilter::OnEndTracingAck(
@@ -123,7 +120,6 @@ void TraceMessageFilter::OnEndTracingAck(
// child process is compromised.
if (is_awaiting_end_ack_) {
is_awaiting_end_ack_ = false;
- TraceControllerImpl::GetInstance()->OnEndTracingAck(known_categories);
TracingControllerImpl::GetInstance()->OnDisableRecordingAcked(
known_categories);
} else {
@@ -145,7 +141,6 @@ void TraceMessageFilter::OnCaptureMonitoringSnapshotAcked() {
void TraceMessageFilter::OnTraceDataCollected(const std::string& data) {
scoped_refptr<base::RefCountedString> data_ptr(new base::RefCountedString());
data_ptr->data() = data;
- TraceControllerImpl::GetInstance()->OnTraceDataCollected(data_ptr);
TracingControllerImpl::GetInstance()->OnTraceDataCollected(data_ptr);
}
@@ -157,15 +152,13 @@ void TraceMessageFilter::OnMonitoringTraceDataCollected(
data_ptr);
}
-void TraceMessageFilter::OnTraceNotification(int notification) {
- TraceControllerImpl::GetInstance()->OnTraceNotification(notification);
+void TraceMessageFilter::OnWatchEventMatched() {
+ TracingControllerImpl::GetInstance()->OnWatchEventMatched();
}
void TraceMessageFilter::OnTraceBufferPercentFullReply(float percent_full) {
if (is_awaiting_buffer_percent_full_ack_) {
is_awaiting_buffer_percent_full_ack_ = false;
- TraceControllerImpl::GetInstance()->OnTraceBufferPercentFullReply(
- percent_full);
TracingControllerImpl::GetInstance()->OnTraceBufferPercentFullReply(
percent_full);
} else {
diff --git a/content/browser/tracing/trace_message_filter.h b/content/browser/tracing/trace_message_filter.h
index c8290d9..0f9e18e 100644
--- a/content/browser/tracing/trace_message_filter.h
+++ b/content/browser/tracing/trace_message_filter.h
@@ -45,7 +45,7 @@ class TraceMessageFilter : public BrowserMessageFilter {
void OnChildSupportsTracing();
void OnEndTracingAck(const std::vector<std::string>& known_categories);
void OnCaptureMonitoringSnapshotAcked();
- void OnTraceNotification(int notification);
+ void OnWatchEventMatched();
void OnTraceBufferPercentFullReply(float percent_full);
void OnTraceDataCollected(const std::string& data);
void OnMonitoringTraceDataCollected(const std::string& data);
diff --git a/content/browser/tracing/trace_subscriber_stdio.cc b/content/browser/tracing/trace_subscriber_stdio.cc
deleted file mode 100644
index 50bc361..0000000
--- a/content/browser/tracing/trace_subscriber_stdio.cc
+++ /dev/null
@@ -1,201 +0,0 @@
-// Copyright 2013 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 "content/browser/tracing/trace_subscriber_stdio.h"
-
-#include "base/bind.h"
-#include "base/debug/trace_event.h"
-#include "base/file_util.h"
-#include "base/logging.h"
-#include "base/threading/sequenced_worker_pool.h"
-#include "content/public/browser/browser_thread.h"
-
-namespace content {
-
-// All method calls on this class are done on a SequencedWorkerPool thread.
-class TraceSubscriberStdio::TraceSubscriberStdioWorker
- : public base::RefCountedThreadSafe<TraceSubscriberStdioWorker> {
- public:
- TraceSubscriberStdioWorker(const base::FilePath& path,
- FileType file_type,
- bool has_system_trace)
- : path_(path),
- file_type_(file_type),
- has_system_trace_(has_system_trace),
- file_(0),
- needs_comma_(false),
- wrote_trace_(false),
- has_pending_system_trace_(false),
- wrote_system_trace_(false) {}
-
- void OnTraceStart() {
- DCHECK(!file_);
- file_ = file_util::OpenFile(path_, "w+");
- if (!IsValid()) {
- LOG(ERROR) << "Failed to open performance trace file: " << path_.value();
- return;
- }
-
- VLOG(0) << "Logging performance trace to file: " << path_.value();
- if (file_type_ == FILE_TYPE_PROPERTY_LIST)
- WriteString("{\"traceEvents\":");
- WriteString("[");
- }
-
- void OnTraceData(const scoped_refptr<base::RefCountedString>& data_ptr) {
- if (!IsValid())
- return;
- DCHECK(!data_ptr->data().empty());
- if (needs_comma_)
- WriteString(",");
- WriteString(data_ptr->data());
- needs_comma_ = true;
- }
-
- void OnSystemTraceData(
- const scoped_refptr<base::RefCountedString>& data_ptr) {
- if (wrote_trace_) {
- WriteSystemTrace(data_ptr);
- End();
- } else {
- pending_system_trace_ = data_ptr;
- has_pending_system_trace_ = true;
- }
- }
-
- void OnTraceEnd() {
- if (!IsValid())
- return;
- WriteString("]");
-
- wrote_trace_ = true;
-
- if (!has_system_trace_ || wrote_system_trace_) {
- End();
- return;
- }
-
- WriteString(",");
- if (has_pending_system_trace_) {
- WriteSystemTrace(pending_system_trace_);
- End();
- }
- }
-
- private:
- friend class base::RefCountedThreadSafe<TraceSubscriberStdioWorker>;
-
- ~TraceSubscriberStdioWorker() {
- CloseFile();
- }
-
- bool IsValid() const {
- return file_ && (0 == ferror(file_));
- }
-
- void CloseFile() {
- if (file_) {
- fclose(file_);
- file_ = 0;
-
- }
- }
-
- void End() {
- if (file_type_ == FILE_TYPE_PROPERTY_LIST)
- WriteString("}");
- CloseFile();
- }
-
- void WriteSystemTrace(const scoped_refptr<base::RefCountedString>& data_ptr) {
- // Newlines need to be replaced with the string "\n" to be parsed correctly.
- // Double quotes need to be replaced with the string "\"".
- // System logs are ASCII.
- const std::string& data = data_ptr->data();
- const char* chars = data.c_str();
- WriteString("\"systemTraceEvents\":\"");
- size_t old_index = 0;
- for (size_t new_index = data.find_first_of("\n\"");
- std::string::npos != new_index;
- old_index = new_index + 1,
- new_index = data.find_first_of("\n\"", old_index)) {
- WriteChars(chars + old_index, new_index - old_index);
- if (chars[new_index] == '\n')
- WriteChars("\\n", 2);
- else
- WriteChars("\\\"", 2);
- }
- WriteChars(chars + old_index, data.size() - old_index);
- WriteString("\"");
- wrote_system_trace_ = true;
- }
-
- void WriteChars(const char* output_chars, size_t size) {
- if (size == 0)
- return;
-
- if (IsValid()) {
- size_t written = fwrite(output_chars, 1, size, file_);
- if (written != size) {
- LOG(ERROR) << "Error " << ferror(file_) << " in fwrite() to trace file";
- CloseFile();
- }
- }
- }
-
- void WriteString(const std::string& output_str) {
- WriteChars(output_str.data(), output_str.size());
- }
-
- base::FilePath path_;
- const FileType file_type_;
- const bool has_system_trace_;
- FILE* file_;
- bool needs_comma_;
- bool wrote_trace_;
- bool has_pending_system_trace_;
- bool wrote_system_trace_;
- scoped_refptr<base::RefCountedString> pending_system_trace_;
- DISALLOW_COPY_AND_ASSIGN(TraceSubscriberStdioWorker);
-};
-
-TraceSubscriberStdio::TraceSubscriberStdio(const base::FilePath& path,
- FileType file_type,
- bool has_system_trace)
- : worker_(new TraceSubscriberStdioWorker(path,
- file_type,
- has_system_trace)) {
- if (has_system_trace)
- CHECK_EQ(FILE_TYPE_PROPERTY_LIST, file_type);
- BrowserThread::PostBlockingPoolSequencedTask(
- __FILE__, FROM_HERE,
- base::Bind(&TraceSubscriberStdioWorker::OnTraceStart, worker_));
-}
-
-TraceSubscriberStdio::~TraceSubscriberStdio() {
-}
-
-void TraceSubscriberStdio::OnEndTracingComplete() {
- BrowserThread::PostBlockingPoolSequencedTask(
- __FILE__, FROM_HERE,
- base::Bind(&TraceSubscriberStdioWorker::OnTraceEnd, worker_));
-}
-
-void TraceSubscriberStdio::OnTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& data_ptr) {
- BrowserThread::PostBlockingPoolSequencedTask(
- __FILE__, FROM_HERE,
- base::Bind(&TraceSubscriberStdioWorker::OnTraceData, worker_, data_ptr));
-}
-
-void TraceSubscriberStdio::OnEndSystemTracing(
- const scoped_refptr<base::RefCountedString>& events_str_ptr) {
- BrowserThread::PostBlockingPoolSequencedTask(
- __FILE__, FROM_HERE,
- base::Bind(&TraceSubscriberStdioWorker::OnSystemTraceData,
- worker_,
- events_str_ptr));
-}
-
-} // namespace content
diff --git a/content/browser/tracing/trace_subscriber_stdio.h b/content/browser/tracing/trace_subscriber_stdio.h
deleted file mode 100644
index 95c8f9f..0000000
--- a/content/browser/tracing/trace_subscriber_stdio.h
+++ /dev/null
@@ -1,57 +0,0 @@
-// Copyright 2013 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.
-
-#ifndef CONTENT_BROWSER_TRACING_TRACE_SUBSCRIBER_STDIO_H_
-#define CONTENT_BROWSER_TRACING_TRACE_SUBSCRIBER_STDIO_H_
-
-#include <string>
-
-#include "base/compiler_specific.h"
-#include "content/public/browser/trace_subscriber.h"
-#include "content/common/content_export.h"
-
-namespace base {
-class FilePath;
-}
-
-namespace content {
-
-// Stdio implementation of TraceSubscriber. Use this to write traces to a file.
-class CONTENT_EXPORT TraceSubscriberStdio
- : NON_EXPORTED_BASE(public TraceSubscriber) {
- public:
- enum FileType {
- // Output file as array, representing trace events:
- // [event1, event2, ...]
- FILE_TYPE_ARRAY,
- // Output file as property list with one or two items:
- // {traceEvents: [event1, event2, ...],
- // systemTraceEvents: "event1\nevent2\n..." // optional}
- FILE_TYPE_PROPERTY_LIST
- };
-
- // has_system_trace indicates whether system trace events are expected.
- TraceSubscriberStdio(const base::FilePath& path,
- FileType file_type,
- bool has_system_trace);
- virtual ~TraceSubscriberStdio();
-
- // Implementation of TraceSubscriber
- virtual void OnEndTracingComplete() OVERRIDE;
- virtual void OnTraceDataCollected(
- const scoped_refptr<base::RefCountedString>& data_ptr) OVERRIDE;
-
- // To be used as callback to DebugDaemonClient::RequestStopSystemTracing().
- virtual void OnEndSystemTracing(
- const scoped_refptr<base::RefCountedString>& events_str_ptr);
-
- private:
- class TraceSubscriberStdioWorker;
- scoped_refptr<TraceSubscriberStdioWorker> worker_;
- DISALLOW_COPY_AND_ASSIGN(TraceSubscriberStdio);
-};
-
-} // namespace content
-
-#endif // CONTENT_BROWSER_TRACING_TRACE_SUBSCRIBER_STDIO_H_
diff --git a/content/browser/tracing/trace_subscriber_stdio_unittest.cc b/content/browser/tracing/trace_subscriber_stdio_unittest.cc
deleted file mode 100644
index 2364299..0000000
--- a/content/browser/tracing/trace_subscriber_stdio_unittest.cc
+++ /dev/null
@@ -1,132 +0,0 @@
-// Copyright 2013 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 "content/browser/tracing/trace_subscriber_stdio.h"
-
-#include "base/file_util.h"
-#include "base/files/scoped_temp_dir.h"
-#include "base/threading/sequenced_worker_pool.h"
-#include "content/public/browser/browser_thread.h"
-#include "testing/gtest/include/gtest/gtest.h"
-
-namespace content {
-
-class TraceSubscriberStdioTest : public ::testing::Test {};
-
-TEST_F(TraceSubscriberStdioTest, CanWriteArray) {
- base::ScopedTempDir trace_dir;
- ASSERT_TRUE(trace_dir.CreateUniqueTempDir());
- base::FilePath trace_file(trace_dir.path().AppendASCII("trace.txt"));
- {
- TraceSubscriberStdio subscriber(trace_file,
- TraceSubscriberStdio::FILE_TYPE_ARRAY,
- false);
-
- std::string foo("foo");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&foo)));
-
- std::string bar("bar");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&bar)));
-
- subscriber.OnEndTracingComplete();
- }
- BrowserThread::GetBlockingPool()->FlushForTesting();
- std::string result;
- EXPECT_TRUE(base::ReadFileToString(trace_file, &result));
- EXPECT_EQ("[foo,bar]", result);
-}
-
-TEST_F(TraceSubscriberStdioTest, CanWritePropertyList) {
- base::ScopedTempDir trace_dir;
- ASSERT_TRUE(trace_dir.CreateUniqueTempDir());
- base::FilePath trace_file(trace_dir.path().AppendASCII("trace.txt"));
- {
- TraceSubscriberStdio subscriber(
- trace_file,
- TraceSubscriberStdio::FILE_TYPE_PROPERTY_LIST,
- false);
-
- std::string foo("foo");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&foo)));
-
- std::string bar("bar");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&bar)));
-
- subscriber.OnEndTracingComplete();
- }
- BrowserThread::GetBlockingPool()->FlushForTesting();
- std::string result;
- EXPECT_TRUE(base::ReadFileToString(trace_file, &result));
- EXPECT_EQ("{\"traceEvents\":[foo,bar]}", result);
-}
-
-TEST_F(TraceSubscriberStdioTest, CanWriteSystemDataFirst) {
- base::ScopedTempDir trace_dir;
- ASSERT_TRUE(trace_dir.CreateUniqueTempDir());
- base::FilePath trace_file(trace_dir.path().AppendASCII("trace.txt"));
- {
- TraceSubscriberStdio subscriber(
- trace_file,
- TraceSubscriberStdio::FILE_TYPE_PROPERTY_LIST,
- true);
-
- std::string foo("foo");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&foo)));
-
- std::string bar("bar");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&bar)));
-
- std::string systemTrace("event1\nev\"ent\"2\n");
- subscriber.OnEndSystemTracing(
- make_scoped_refptr(base::RefCountedString::TakeString(&systemTrace)));
- subscriber.OnEndTracingComplete();
- }
- BrowserThread::GetBlockingPool()->FlushForTesting();
- std::string result;
- EXPECT_TRUE(base::ReadFileToString(trace_file, &result));
- EXPECT_EQ(
- "{\"traceEvents\":[foo,bar],\""
- "systemTraceEvents\":\"event1\\nev\\\"ent\\\"2\\n\"}",
- result);
-}
-
-TEST_F(TraceSubscriberStdioTest, CanWriteSystemDataLast) {
- base::ScopedTempDir trace_dir;
- ASSERT_TRUE(trace_dir.CreateUniqueTempDir());
- base::FilePath trace_file(trace_dir.path().AppendASCII("trace.txt"));
- {
- TraceSubscriberStdio subscriber(
- trace_file,
- TraceSubscriberStdio::FILE_TYPE_PROPERTY_LIST,
- true);
-
- std::string foo("foo");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&foo)));
-
- std::string bar("bar");
- subscriber.OnTraceDataCollected(
- make_scoped_refptr(base::RefCountedString::TakeString(&bar)));
-
- std::string systemTrace("event1\nev\"ent\"2\n");
- subscriber.OnEndTracingComplete();
- subscriber.OnEndSystemTracing(
- make_scoped_refptr(base::RefCountedString::TakeString(&systemTrace)));
- }
- BrowserThread::GetBlockingPool()->FlushForTesting();
- std::string result;
- EXPECT_TRUE(base::ReadFileToString(trace_file, &result));
- EXPECT_EQ(
- "{\"traceEvents\":[foo,bar],\""
- "systemTraceEvents\":\"event1\\nev\\\"ent\\\"2\\n\"}",
- result);
-}
-
-} // namespace content
diff --git a/content/browser/tracing/tracing_controller_browsertest.cc b/content/browser/tracing/tracing_controller_browsertest.cc
index 2be451d..6b2cc35 100644
--- a/content/browser/tracing/tracing_controller_browsertest.cc
+++ b/content/browser/tracing/tracing_controller_browsertest.cc
@@ -122,8 +122,7 @@ class TracingControllerTest : public ContentBrowserTest {
base::Unretained(this),
run_loop.QuitClosure());
bool result = controller->EnableRecording(
- base::debug::CategoryFilter(""), TracingController::Options(),
- callback);
+ "", TracingController::DEFAULT_OPTIONS, callback);
ASSERT_TRUE(result);
run_loop.Run();
EXPECT_EQ(enable_recording_done_callback_count(), 1);
@@ -155,8 +154,7 @@ class TracingControllerTest : public ContentBrowserTest {
base::Unretained(this),
run_loop.QuitClosure());
bool result = controller->EnableMonitoring(
- base::debug::CategoryFilter(""), TracingController::ENABLE_SAMPLING,
- callback);
+ "", TracingController::ENABLE_SAMPLING, callback);
ASSERT_TRUE(result);
run_loop.Run();
EXPECT_EQ(enable_monitoring_done_callback_count(), 1);
@@ -169,7 +167,8 @@ class TracingControllerTest : public ContentBrowserTest {
CaptureMonitoringSnapshotDoneCallbackTest,
base::Unretained(this),
run_loop.QuitClosure());
- controller->CaptureMonitoringSnapshot(result_file_path, callback);
+ ASSERT_TRUE(controller->CaptureMonitoringSnapshot(result_file_path,
+ callback));
run_loop.Run();
EXPECT_EQ(capture_monitoring_snapshot_done_callback_count(), 1);
}
@@ -208,7 +207,7 @@ IN_PROC_BROWSER_TEST_F(TracingControllerTest, GetCategories) {
base::Bind(&TracingControllerTest::GetCategoriesDoneCallbackTest,
base::Unretained(this),
run_loop.QuitClosure());
- controller->GetCategories(callback);
+ ASSERT_TRUE(controller->GetCategories(callback));
run_loop.Run();
EXPECT_EQ(get_categories_done_callback_count(), 1);
}
@@ -231,7 +230,7 @@ IN_PROC_BROWSER_TEST_F(TracingControllerTest,
TracingController* controller = TracingController::GetInstance();
EXPECT_TRUE(controller->EnableRecording(
- base::debug::CategoryFilter(""), TracingController::Options(),
+ "", TracingController::DEFAULT_OPTIONS,
TracingController::EnableRecordingDoneCallback()));
EXPECT_TRUE(controller->DisableRecording(
base::FilePath(), TracingController::TracingFileResultCallback()));
@@ -258,7 +257,7 @@ IN_PROC_BROWSER_TEST_F(
TracingController* controller = TracingController::GetInstance();
EXPECT_TRUE(controller->EnableMonitoring(
- base::debug::CategoryFilter(""), TracingController::ENABLE_SAMPLING,
+ "", TracingController::ENABLE_SAMPLING,
TracingController::EnableMonitoringDoneCallback()));
controller->CaptureMonitoringSnapshot(
base::FilePath(), TracingController::TracingFileResultCallback());
diff --git a/content/browser/tracing/tracing_controller_impl.cc b/content/browser/tracing/tracing_controller_impl.cc
index 1269b7d..24a53e3 100644
--- a/content/browser/tracing/tracing_controller_impl.cc
+++ b/content/browser/tracing/tracing_controller_impl.cc
@@ -5,6 +5,7 @@
#include "content/browser/tracing/tracing_controller_impl.h"
#include "base/bind.h"
+#include "base/debug/trace_event.h"
#include "base/file_util.h"
#include "base/json/string_escape.h"
#include "base/strings/string_number_conversions.h"
@@ -118,9 +119,7 @@ TracingControllerImpl::TracingControllerImpl() :
// Tracing may have been enabled by ContentMainRunner if kTraceStartup
// is specified in command line.
is_recording_(TraceLog::GetInstance()->IsEnabled()),
- is_monitoring_(false),
- category_filter_(
- base::debug::CategoryFilter::kDefaultCategoryFilterString) {
+ is_monitoring_(false) {
}
TracingControllerImpl::~TracingControllerImpl() {
@@ -132,7 +131,7 @@ TracingControllerImpl* TracingControllerImpl::GetInstance() {
return g_controller.Pointer();
}
-void TracingControllerImpl::GetCategories(
+bool TracingControllerImpl::GetCategories(
const GetCategoriesDoneCallback& callback) {
DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
@@ -140,14 +139,19 @@ void TracingControllerImpl::GetCategories(
// message. So to get known categories, just begin and end tracing immediately
// afterwards. This will ping all the child processes for categories.
pending_get_categories_done_callback_ = callback;
- EnableRecording(base::debug::CategoryFilter("*"),
- TracingController::Options(),
- EnableRecordingDoneCallback());
- DisableRecording(base::FilePath(), TracingFileResultCallback());
+ if (!EnableRecording("*", TracingController::Options(),
+ EnableRecordingDoneCallback())) {
+ pending_get_categories_done_callback_.Reset();
+ return false;
+ }
+
+ bool ok = DisableRecording(base::FilePath(), TracingFileResultCallback());
+ DCHECK(ok);
+ return true;
}
bool TracingControllerImpl::EnableRecording(
- const base::debug::CategoryFilter& filter,
+ const std::string& category_filter,
TracingController::Options options,
const EnableRecordingDoneCallback& callback) {
DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
@@ -168,13 +172,14 @@ bool TracingControllerImpl::EnableRecording(
}
// TODO(haraken): How to handle ENABLE_SYSTRACE?
- TraceLog::GetInstance()->SetEnabled(filter, trace_options);
+ TraceLog::GetInstance()->SetEnabled(
+ base::debug::CategoryFilter(category_filter), trace_options);
is_recording_ = true;
- category_filter_ = TraceLog::GetInstance()->GetCurrentCategoryFilter();
// Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
- it->get()->SendBeginTracing(category_filter_.ToString(), trace_options);
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
+ it->get()->SendBeginTracing(category_filter, trace_options);
}
if (!callback.is_null())
@@ -204,15 +209,13 @@ bool TracingControllerImpl::DisableRecording(
if (!callback.is_null() || !result_file_path.empty())
result_file_.reset(new ResultFile(result_file_path));
- // There could be a case where there are no child processes and filters_
- // is empty. In that case we can immediately tell the subscriber that tracing
- // has ended. To avoid recursive calls back to the subscriber, we will just
- // use the existing asynchronous OnDisableRecordingAcked code.
// Count myself (local trace) in pending_disable_recording_ack_count_,
// acked below.
- pending_disable_recording_ack_count_ = filters_.size() + 1;
+ pending_disable_recording_ack_count_ = trace_message_filters_.size() + 1;
- // Handle special case of zero child processes.
+ // Handle special case of zero child processes by immediately telling the
+ // caller that tracing has ended. Use asynchronous OnDisableRecordingAcked
+ // to avoid recursive call back to the caller.
if (pending_disable_recording_ack_count_ == 1) {
// Ack asynchronously now, because we don't have any children to wait for.
std::vector<std::string> category_groups;
@@ -223,14 +226,15 @@ bool TracingControllerImpl::DisableRecording(
}
// Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
it->get()->SendEndTracing();
}
return true;
}
bool TracingControllerImpl::EnableMonitoring(
- const base::debug::CategoryFilter& filter,
+ const std::string& category_filter,
TracingController::Options options,
const EnableMonitoringDoneCallback& callback) {
DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
@@ -248,12 +252,14 @@ bool TracingControllerImpl::EnableMonitoring(
monitoring_tracing_options |= base::debug::TraceLog::MONITOR_SAMPLING;
TraceLog::GetInstance()->SetEnabled(
- filter, base::debug::TraceLog::Options(monitoring_tracing_options));
+ base::debug::CategoryFilter(category_filter),
+ static_cast<TraceLog::Options>(monitoring_tracing_options));
// Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
- it->get()->SendEnableMonitoring(filter.ToString(),
- base::debug::TraceLog::Options(monitoring_tracing_options));
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
+ it->get()->SendEnableMonitoring(category_filter,
+ static_cast<TraceLog::Options>(monitoring_tracing_options));
}
if (!callback.is_null())
@@ -272,7 +278,8 @@ bool TracingControllerImpl::DisableMonitoring(
TraceLog::GetInstance()->SetDisabled();
// Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
it->get()->SendDisableMonitoring();
}
@@ -283,34 +290,34 @@ bool TracingControllerImpl::DisableMonitoring(
void TracingControllerImpl::GetMonitoringStatus(
bool* out_enabled,
- base::debug::CategoryFilter* out_filter,
+ std::string* out_category_filter,
TracingController::Options* out_options) {
NOTIMPLEMENTED();
}
-void TracingControllerImpl::CaptureMonitoringSnapshot(
+bool TracingControllerImpl::CaptureMonitoringSnapshot(
const base::FilePath& result_file_path,
const TracingFileResultCallback& callback) {
DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
if (!can_disable_monitoring())
- return;
+ return false;
if (callback.is_null() && result_file_path.empty())
- return;
+ return false;
pending_capture_monitoring_snapshot_done_callback_ = callback;
monitoring_snapshot_file_.reset(new ResultFile(result_file_path));
- // There could be a case where there are no child processes and filters_
- // is empty. In that case we can immediately tell the subscriber that tracing
- // has ended. To avoid recursive calls back to the subscriber, we will just
- // use the existing asynchronous OnCaptureMonitoringSnapshotAcked code.
// Count myself in pending_capture_monitoring_snapshot_ack_count_,
// acked below.
- pending_capture_monitoring_snapshot_ack_count_ = filters_.size() + 1;
+ pending_capture_monitoring_snapshot_ack_count_ =
+ trace_message_filters_.size() + 1;
- // Handle special case of zero child processes.
+ // Handle special case of zero child processes by immediately telling the
+ // caller that capturing snapshot has ended. Use asynchronous
+ // OnCaptureMonitoringSnapshotAcked to avoid recursive call back to the
+ // caller.
if (pending_capture_monitoring_snapshot_ack_count_ == 1) {
// Ack asynchronously now, because we don't have any children to wait for.
BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
@@ -319,13 +326,16 @@ void TracingControllerImpl::CaptureMonitoringSnapshot(
}
// Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
it->get()->SendCaptureMonitoringSnapshot();
}
#if defined(OS_ANDROID)
TraceLog::GetInstance()->AddClockSyncMetadataEvent();
#endif
+
+ return true;
}
bool TracingControllerImpl::GetTraceBufferPercentFull(
@@ -338,7 +348,8 @@ bool TracingControllerImpl::GetTraceBufferPercentFull(
pending_trace_buffer_percent_full_callback_ = callback;
// Count myself in pending_trace_buffer_percent_full_ack_count_, acked below.
- pending_trace_buffer_percent_full_ack_count_ = filters_.size() + 1;
+ pending_trace_buffer_percent_full_ack_count_ =
+ trace_message_filters_.size() + 1;
maximum_trace_buffer_percent_full_ = 0;
// Handle special case of zero child processes.
@@ -350,36 +361,86 @@ bool TracingControllerImpl::GetTraceBufferPercentFull(
}
// Notify all child processes.
- for (FilterMap::iterator it = filters_.begin(); it != filters_.end(); ++it) {
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
it->get()->SendGetTraceBufferPercentFull();
}
return true;
}
-void TracingControllerImpl::AddFilter(TraceMessageFilter* filter) {
+bool TracingControllerImpl::SetWatchEvent(
+ const std::string& category_name,
+ const std::string& event_name,
+ const WatchEventCallback& callback) {
+ DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
+
+ if (callback.is_null())
+ return false;
+
+ watch_category_name_ = category_name;
+ watch_event_name_ = event_name;
+ watch_event_callback_ = callback;
+
+ TraceLog::GetInstance()->SetWatchEvent(
+ category_name, event_name,
+ base::Bind(&TracingControllerImpl::OnWatchEventMatched,
+ base::Unretained(this)));
+
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
+ it->get()->SendSetWatchEvent(category_name, event_name);
+ }
+ return true;
+}
+
+bool TracingControllerImpl::CancelWatchEvent() {
+ DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
+
+ if (!can_cancel_watch_event())
+ return false;
+
+ for (TraceMessageFilterMap::iterator it = trace_message_filters_.begin();
+ it != trace_message_filters_.end(); ++it) {
+ it->get()->SendCancelWatchEvent();
+ }
+
+ watch_event_callback_.Reset();
+ return true;
+}
+
+void TracingControllerImpl::AddTraceMessageFilter(
+ TraceMessageFilter* trace_message_filter) {
if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TracingControllerImpl::AddFilter, base::Unretained(this),
- make_scoped_refptr(filter)));
+ base::Bind(&TracingControllerImpl::AddTraceMessageFilter,
+ base::Unretained(this),
+ make_scoped_refptr(trace_message_filter)));
return;
}
- filters_.insert(filter);
+ trace_message_filters_.insert(trace_message_filter);
+ if (can_cancel_watch_event()) {
+ trace_message_filter->SendSetWatchEvent(watch_category_name_,
+ watch_event_name_);
+ }
if (can_disable_recording()) {
- std::string cf_str = category_filter_.ToString();
- filter->SendBeginTracing(cf_str, TraceLog::GetInstance()->trace_options());
+ trace_message_filter->SendBeginTracing(
+ TraceLog::GetInstance()->GetCurrentCategoryFilter().ToString(),
+ TraceLog::GetInstance()->trace_options());
}
}
-void TracingControllerImpl::RemoveFilter(TraceMessageFilter* filter) {
+void TracingControllerImpl::RemoveTraceMessageFilter(
+ TraceMessageFilter* trace_message_filter) {
if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
- base::Bind(&TracingControllerImpl::RemoveFilter, base::Unretained(this),
- make_scoped_refptr(filter)));
+ base::Bind(&TracingControllerImpl::RemoveTraceMessageFilter,
+ base::Unretained(this),
+ make_scoped_refptr(trace_message_filter)));
return;
}
- filters_.erase(filter);
+ trace_message_filters_.erase(trace_message_filter);
}
void TracingControllerImpl::OnDisableRecordingAcked(
@@ -405,6 +466,7 @@ void TracingControllerImpl::OnDisableRecordingAcked(
TraceLog::GetInstance()->Flush(
base::Bind(&TracingControllerImpl::OnLocalTraceDataCollected,
base::Unretained(this)));
+ return;
}
if (pending_disable_recording_ack_count_ != 0)
@@ -456,6 +518,7 @@ void TracingControllerImpl::OnCaptureMonitoringSnapshotAcked() {
TraceLog::GetInstance()->FlushButLeaveBufferIntact(
base::Bind(&TracingControllerImpl::OnLocalMonitoringTraceDataCollected,
base::Unretained(this)));
+ return;
}
if (pending_capture_monitoring_snapshot_ack_count_ != 0)
@@ -569,4 +632,15 @@ void TracingControllerImpl::OnTraceBufferPercentFullReply(float percent_full) {
}
}
+void TracingControllerImpl::OnWatchEventMatched() {
+ if (!BrowserThread::CurrentlyOn(BrowserThread::UI)) {
+ BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
+ base::Bind(&TracingControllerImpl::OnWatchEventMatched,
+ base::Unretained(this)));
+ }
+
+ if (!watch_event_callback_.is_null())
+ watch_event_callback_.Run();
+}
+
} // namespace content
diff --git a/content/browser/tracing/tracing_controller_impl.h b/content/browser/tracing/tracing_controller_impl.h
index 7eab907..ed3c8fd 100644
--- a/content/browser/tracing/tracing_controller_impl.h
+++ b/content/browser/tracing/tracing_controller_impl.h
@@ -11,9 +11,12 @@
#include "base/files/file_path.h"
#include "base/lazy_instance.h"
-#include "content/public/browser/trace_subscriber.h"
#include "content/public/browser/tracing_controller.h"
+namespace base {
+class RefCountedString;
+}
+
namespace content {
class TraceMessageFilter;
@@ -23,32 +26,36 @@ class TracingControllerImpl : public TracingController {
static TracingControllerImpl* GetInstance();
// TracingController implementation.
- virtual void GetCategories(
+ virtual bool GetCategories(
const GetCategoriesDoneCallback& callback) OVERRIDE;
virtual bool EnableRecording(
- const base::debug::CategoryFilter& filter,
+ const std::string& category_filter,
TracingController::Options options,
const EnableRecordingDoneCallback& callback) OVERRIDE;
virtual bool DisableRecording(
const base::FilePath& result_file_path,
const TracingFileResultCallback& callback) OVERRIDE;
- virtual bool EnableMonitoring(const base::debug::CategoryFilter& filter,
+ virtual bool EnableMonitoring(const std::string& category_filter,
TracingController::Options options,
const EnableMonitoringDoneCallback& callback) OVERRIDE;
virtual bool DisableMonitoring(
const DisableMonitoringDoneCallback& callback) OVERRIDE;
virtual void GetMonitoringStatus(
bool* out_enabled,
- base::debug::CategoryFilter* out_filter,
+ std::string* out_category_filter,
TracingController::Options* out_options) OVERRIDE;
- virtual void CaptureMonitoringSnapshot(
+ virtual bool CaptureMonitoringSnapshot(
const base::FilePath& result_file_path,
const TracingFileResultCallback& callback) OVERRIDE;
virtual bool GetTraceBufferPercentFull(
const GetTraceBufferPercentFullCallback& callback) OVERRIDE;
+ virtual bool SetWatchEvent(const std::string& category_name,
+ const std::string& event_name,
+ const WatchEventCallback& callback) OVERRIDE;
+ virtual bool CancelWatchEvent() OVERRIDE;
private:
- typedef std::set<scoped_refptr<TraceMessageFilter> > FilterMap;
+ typedef std::set<scoped_refptr<TraceMessageFilter> > TraceMessageFilterMap;
class ResultFile;
friend struct base::DefaultLazyInstanceTraits<TracingControllerImpl>;
@@ -77,9 +84,13 @@ class TracingControllerImpl : public TracingController {
return pending_trace_buffer_percent_full_callback_.is_null();
}
+ bool can_cancel_watch_event() const {
+ return !watch_event_callback_.is_null();
+ }
+
// Methods for use by TraceMessageFilter.
- void AddFilter(TraceMessageFilter* filter);
- void RemoveFilter(TraceMessageFilter* filter);
+ void AddTraceMessageFilter(TraceMessageFilter* trace_message_filter);
+ void RemoveTraceMessageFilter(TraceMessageFilter* trace_message_filter);
void OnTraceDataCollected(
const scoped_refptr<base::RefCountedString>& events_str_ptr);
@@ -102,10 +113,11 @@ class TracingControllerImpl : public TracingController {
void OnCaptureMonitoringSnapshotAcked();
void OnMonitoringSnapshotFileClosed();
- void OnTraceNotification(int notification);
void OnTraceBufferPercentFullReply(float percent_full);
- FilterMap filters_;
+ void OnWatchEventMatched();
+
+ TraceMessageFilterMap trace_message_filters_;
// Pending acks for DisableRecording.
int pending_disable_recording_ack_count_;
// Pending acks for CaptureMonitoringSnapshot.
@@ -122,8 +134,11 @@ class TracingControllerImpl : public TracingController {
TracingFileResultCallback pending_capture_monitoring_snapshot_done_callback_;
GetTraceBufferPercentFullCallback pending_trace_buffer_percent_full_callback_;
+ std::string watch_category_name_;
+ std::string watch_event_name_;
+ WatchEventCallback watch_event_callback_;
+
std::set<std::string> known_category_groups_;
- base::debug::CategoryFilter category_filter_;
scoped_ptr<ResultFile> result_file_;
scoped_ptr<ResultFile> monitoring_snapshot_file_;
DISALLOW_COPY_AND_ASSIGN(TracingControllerImpl);
diff --git a/content/browser/tracing/tracing_ui.cc b/content/browser/tracing/tracing_ui.cc
index 6e471c2..e59f566 100644
--- a/content/browser/tracing/tracing_ui.cc
+++ b/content/browser/tracing/tracing_ui.cc
@@ -86,11 +86,10 @@ bool OnBeginRecording(const std::string& data64,
if (use_continuous_tracing)
tracing_options |= TracingController::RECORD_CONTINUOUSLY;
- base::debug::CategoryFilter category_filter(category_filter_string);
return TracingController::GetInstance()->EnableRecording(
- category_filter,
+ category_filter_string,
static_cast<TracingController::Options>(tracing_options),
- base::Bind(OnRecordingEnabledAck, callback));
+ base::Bind(&OnRecordingEnabledAck, callback));
}
void OnRecordingEnabledAck(const WebUIDataSource::GotDataCallback& callback) {