diff options
author | wangxianzhu@chromium.org <wangxianzhu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-12-03 19:48:19 +0000 |
---|---|---|
committer | wangxianzhu@chromium.org <wangxianzhu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-12-03 19:48:19 +0000 |
commit | 6174a36970df96acaa6a4bc00bb46727ddb6e7a7 (patch) | |
tree | fd540c556137ed279c13ddabe8ac3f0ed0fb3697 /content/browser | |
parent | 6a3ad06b4dc301ff395a13605e7ab7439d9680d4 (diff) | |
download | chromium_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')
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) { |