Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1061)

Side by Side Diff: chrome/browser/metrics/thread_watcher.cc

Issue 2300133002: Fix memory leak in ThreadWatcher. (Closed)
Patch Set: Use unique_ptr; return ptr from Register Created 4 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/metrics/thread_watcher.h" 5 #include "chrome/browser/metrics/thread_watcher.h"
6 6
7 #include <math.h> // ceil 7 #include <math.h> // ceil
8 8
9 #include "base/bind.h" 9 #include "base/bind.h"
10 #include "base/compiler_specific.h" 10 #include "base/compiler_specific.h"
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
72 if (!WatchDogThread::CurrentlyOnWatchDogThread()) { 72 if (!WatchDogThread::CurrentlyOnWatchDogThread()) {
73 WatchDogThread::PostTask( 73 WatchDogThread::PostTask(
74 FROM_HERE, 74 FROM_HERE,
75 base::Bind(&ThreadWatcher::StartWatching, params)); 75 base::Bind(&ThreadWatcher::StartWatching, params));
76 return; 76 return;
77 } 77 }
78 78
79 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread()); 79 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread());
80 80
81 // Create a new thread watcher object for the given thread and activate it. 81 // Create a new thread watcher object for the given thread and activate it.
82 ThreadWatcher* watcher = new ThreadWatcher(params); 82 std::unique_ptr<ThreadWatcher> watcher(new ThreadWatcher(params));
83 83
84 DCHECK(watcher);
85 // If we couldn't register the thread watcher object, we are shutting down, 84 // If we couldn't register the thread watcher object, we are shutting down,
86 // then don't activate thread watching. 85 // so don't activate thread watching.
87 if (!ThreadWatcherList::IsRegistered(params.thread_id)) 86 ThreadWatcher* registered_watcher =
88 return; 87 ThreadWatcherList::Register(std::move(watcher));
89 watcher->ActivateThreadWatching(); 88 if (registered_watcher != nullptr) {
89 registered_watcher->ActivateThreadWatching();
90 }
Ilya Sherman 2016/09/01 20:30:25 nit: No need for curlies here.
Joshua LeVasseur 2016/09/01 21:28:22 Done.
90 } 91 }
91 92
92 void ThreadWatcher::ActivateThreadWatching() { 93 void ThreadWatcher::ActivateThreadWatching() {
93 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread()); 94 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread());
94 if (active_) return; 95 if (active_) return;
95 active_ = true; 96 active_ = true;
96 ping_count_ = unresponsive_threshold_; 97 ping_count_ = unresponsive_threshold_;
97 ResetHangCounters(); 98 ResetHangCounters();
98 base::ThreadTaskRunnerHandle::Get()->PostTask( 99 base::ThreadTaskRunnerHandle::Get()->PostTask(
99 FROM_HERE, base::Bind(&ThreadWatcher::PostPingMessage, 100 FROM_HERE, base::Bind(&ThreadWatcher::PostPingMessage,
(...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after
217 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( 218 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
218 FROM_HERE, 219 FROM_HERE,
219 base::Bind(&ThreadWatcher::OnCheckResponsiveness, 220 base::Bind(&ThreadWatcher::OnCheckResponsiveness,
220 weak_ptr_factory_.GetWeakPtr(), ping_sequence_number_), 221 weak_ptr_factory_.GetWeakPtr(), ping_sequence_number_),
221 unresponsive_time_); 222 unresponsive_time_);
222 responsive_ = false; 223 responsive_ = false;
223 } 224 }
224 225
225 void ThreadWatcher::Initialize() { 226 void ThreadWatcher::Initialize() {
226 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread()); 227 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread());
227 ThreadWatcherList::Register(this);
228 228
229 const std::string response_time_histogram_name = 229 const std::string response_time_histogram_name =
230 "ThreadWatcher.ResponseTime." + thread_name_; 230 "ThreadWatcher.ResponseTime." + thread_name_;
231 response_time_histogram_ = base::Histogram::FactoryTimeGet( 231 response_time_histogram_ = base::Histogram::FactoryTimeGet(
232 response_time_histogram_name, 232 response_time_histogram_name,
233 base::TimeDelta::FromMilliseconds(1), 233 base::TimeDelta::FromMilliseconds(1),
234 base::TimeDelta::FromSeconds(100), 50, 234 base::TimeDelta::FromSeconds(100), 50,
235 base::Histogram::kUmaTargetedHistogramFlag); 235 base::Histogram::kUmaTargetedHistogramFlag);
236 236
237 const std::string unresponsive_time_histogram_name = 237 const std::string unresponsive_time_histogram_name =
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after
375 } 375 }
376 376
377 // static 377 // static
378 void ThreadWatcherList::StopWatchingAll() { 378 void ThreadWatcherList::StopWatchingAll() {
379 // TODO(rtenneti): Enable ThreadWatcher. 379 // TODO(rtenneti): Enable ThreadWatcher.
380 ThreadWatcherObserver::RemoveNotifications(); 380 ThreadWatcherObserver::RemoveNotifications();
381 DeleteAll(); 381 DeleteAll();
382 } 382 }
383 383
384 // static 384 // static
385 void ThreadWatcherList::Register(ThreadWatcher* watcher) { 385 ThreadWatcher* ThreadWatcherList::Register(
386 std::unique_ptr<ThreadWatcher> watcher) {
386 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread()); 387 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread());
387 if (!g_thread_watcher_list_) 388 if (!g_thread_watcher_list_)
388 return; 389 return nullptr;
389 DCHECK(!g_thread_watcher_list_->Find(watcher->thread_id())); 390 content::BrowserThread::ID thread_id = watcher->thread_id();
390 g_thread_watcher_list_->registered_[watcher->thread_id()] = watcher; 391 DCHECK(g_thread_watcher_list_->registered_.count(thread_id) == 0);
392 return g_thread_watcher_list_->registered_[thread_id] = watcher.release();
391 } 393 }
392 394
393 // static 395 // static
394 bool ThreadWatcherList::IsRegistered(const BrowserThread::ID thread_id) {
395 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread());
396 return nullptr != ThreadWatcherList::Find(thread_id);
397 }
398
399 // static
400 void ThreadWatcherList::GetStatusOfThreads( 396 void ThreadWatcherList::GetStatusOfThreads(
401 uint32_t* responding_thread_count, 397 uint32_t* responding_thread_count,
402 uint32_t* unresponding_thread_count) { 398 uint32_t* unresponding_thread_count) {
403 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread()); 399 DCHECK(WatchDogThread::CurrentlyOnWatchDogThread());
404 *responding_thread_count = 0; 400 *responding_thread_count = 0;
405 *unresponding_thread_count = 0; 401 *unresponding_thread_count = 0;
406 if (!g_thread_watcher_list_) 402 if (!g_thread_watcher_list_)
407 return; 403 return;
408 404
409 for (RegistrationList::iterator it = 405 for (RegistrationList::iterator it =
(...skipping 594 matching lines...) Expand 10 before | Expand all | Expand 10 after
1004 1000
1005 #if defined(OS_WIN) 1001 #if defined(OS_WIN)
1006 // On Windows XP, give twice the time for shutdown. 1002 // On Windows XP, give twice the time for shutdown.
1007 if (base::win::GetVersion() <= base::win::VERSION_XP) 1003 if (base::win::GetVersion() <= base::win::VERSION_XP)
1008 actual_duration *= 2; 1004 actual_duration *= 2;
1009 #endif 1005 #endif
1010 1006
1011 shutdown_watchdog_ = new ShutdownWatchDogThread(actual_duration); 1007 shutdown_watchdog_ = new ShutdownWatchDogThread(actual_duration);
1012 shutdown_watchdog_->Arm(); 1008 shutdown_watchdog_->Arm();
1013 } 1009 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698