| Index: components/arc/metrics/oom_kills_monitor.cc
|
| diff --git a/components/arc/metrics/oom_kills_monitor.cc b/components/arc/metrics/oom_kills_monitor.cc
|
| index 3dc4de62ae9e4f2c07cf35a23871c1267ed2ee41..719b778eaf9dbc3e54d9939ce11a0eb2e6fe233d 100644
|
| --- a/components/arc/metrics/oom_kills_monitor.cc
|
| +++ b/components/arc/metrics/oom_kills_monitor.cc
|
| @@ -11,10 +11,12 @@
|
| #include <vector>
|
|
|
| #include "base/bind.h"
|
| +#include "base/debug/leak_annotations.h"
|
| #include "base/files/file_util.h"
|
| #include "base/files/scoped_file.h"
|
| #include "base/location.h"
|
| #include "base/logging.h"
|
| +#include "base/memory/ptr_util.h"
|
| #include "base/metrics/histogram_macros.h"
|
| #include "base/posix/safe_strerror.h"
|
| #include "base/sequenced_task_runner.h"
|
| @@ -33,25 +35,6 @@ using base::StringPiece;
|
| using base::SequencedWorkerPool;
|
| using base::TimeDelta;
|
|
|
| -OomKillsMonitor::OomKillsMonitor()
|
| - : worker_pool_(
|
| - new SequencedWorkerPool(1, "oom_kills_monitor")) {}
|
| -
|
| -OomKillsMonitor::~OomKillsMonitor() {
|
| - Stop();
|
| -}
|
| -
|
| -void OomKillsMonitor::Start() {
|
| - auto task_runner = worker_pool_->GetTaskRunnerWithShutdownBehavior(
|
| - SequencedWorkerPool::CONTINUE_ON_SHUTDOWN);
|
| - task_runner->PostTask(
|
| - FROM_HERE, base::Bind(&OomKillsMonitor::Run, worker_pool_));
|
| -}
|
| -
|
| -void OomKillsMonitor::Stop() {
|
| - worker_pool_->Shutdown();
|
| -}
|
| -
|
| namespace {
|
|
|
| int64_t GetTimestamp(const StringPiece& line) {
|
| @@ -154,9 +137,48 @@ void LogLowMemoryKill(const StringPiece& line) {
|
|
|
| } // namespace
|
|
|
| +OomKillsMonitor::Handle::Handle(OomKillsMonitor* outer) : outer_(outer) {
|
| + DCHECK(outer_);
|
| +}
|
| +
|
| +OomKillsMonitor::Handle::~Handle() {
|
| + outer_->is_shutting_down_.Set();
|
| +}
|
| +
|
| +OomKillsMonitor::OomKillsMonitor() {
|
| + base::SimpleThread::Options non_joinable_options;
|
| + non_joinable_options.joinable = false;
|
| + non_joinable_worker_thread_ = base::MakeUnique<base::DelegateSimpleThread>(
|
| + this, "oom_kills_monitor", non_joinable_options);
|
| + non_joinable_worker_thread_->Start();
|
| +}
|
| +
|
| +OomKillsMonitor::~OomKillsMonitor() {
|
| + // The instance has to be leaked on shutdown as it is referred to by a
|
| + // non-joinable thread but ~OomKillsMonitor() can't be explicitly deleted as
|
| + // it overrides ~SimpleThread(), it should nevertheless never be invoked.
|
| + NOTREACHED();
|
| +}
|
| +
|
| // static
|
| -void OomKillsMonitor::Run(
|
| - scoped_refptr<base::SequencedWorkerPool> worker_pool) {
|
| +OomKillsMonitor::Handle OomKillsMonitor::StartMonitoring() {
|
| +#if DCHECK_IS_ON()
|
| + static volatile bool monitoring_active = false;
|
| + DCHECK(!monitoring_active);
|
| + monitoring_active = true;
|
| +#endif
|
| +
|
| + // Instantiate the OomKillsMonitor and its underlying thread. The
|
| + // OomKillsMonitor itself has to be leaked on shutdown per having a
|
| + // non-joinable thread associated to its state. The OomKillsMonitor::Handle
|
| + // will notify the OomKillsMonitor when it is destroyed so that the underlying
|
| + // thread can at a minimum not do extra work during shutdown.
|
| + OomKillsMonitor* instance = new OomKillsMonitor;
|
| + ANNOTATE_LEAKING_OBJECT_PTR(instance);
|
| + return Handle(instance);
|
| +}
|
| +
|
| +void OomKillsMonitor::Run() {
|
| base::ScopedFILE kmsg_handle(
|
| base::OpenFile(base::FilePath("/dev/kmsg"), "r"));
|
| if (!kmsg_handle) {
|
| @@ -171,7 +193,7 @@ void OomKillsMonitor::Run(
|
| char buf[kMaxBufSize];
|
|
|
| while (fgets(buf, kMaxBufSize, kmsg_handle.get())) {
|
| - if (worker_pool->IsShutdownInProgress()) {
|
| + if (is_shutting_down_.IsSet()) {
|
| DVLOG(1) << "Chrome is shutting down, exit now.";
|
| break;
|
| }
|
|
|