Commit 3d3ca68d authored by Kuo-Hsin Yang's avatar Kuo-Hsin Yang Committed by Commit Bot

chromeos: Implement D-Bus memory pressure signals

Implement CriticalMemoryPressure and ModerateMemoryPressure signals.
Rename kGetMemoryMarginKBMethod to kGetMemoryMarginsKBMethod.

Bug: b/149833548
Change-Id: Id7655695e565638fe34a2f7c3bb7cdac79039725
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2532158Reviewed-by: default avatarSteven Bennetts <stevenjb@chromium.org>
Reviewed-by: default avatarBrian Geffon <bgeffon@chromium.org>
Commit-Queue: Kuo-Hsin Yang <vovoy@chromium.org>
Cr-Commit-Position: refs/heads/master@{#826831}
parent 2c36a5f3
...@@ -566,7 +566,7 @@ void ChromeBrowserMainPartsChromeos::PostMainMessageLoopStart() { ...@@ -566,7 +566,7 @@ void ChromeBrowserMainPartsChromeos::PostMainMessageLoopStart() {
dbus_services_.reset(new internal::DBusServices(parameters())); dbus_services_.reset(new internal::DBusServices(parameters()));
// Need to be done after LoginState has been initialized in DBusServices(). // Need to be done after LoginState has been initialized in DBusServices().
memory::MemoryKillsMonitor::Initialize(); ::memory::MemoryKillsMonitor::Initialize();
ChromeBrowserMainPartsLinux::PostMainMessageLoopStart(); ChromeBrowserMainPartsLinux::PostMainMessageLoopStart();
} }
......
...@@ -6,7 +6,6 @@ ...@@ -6,7 +6,6 @@
#include "base/bind.h" #include "base/bind.h"
#include "base/logging.h" #include "base/logging.h"
#include "chromeos/memory/pressure/pressure.h"
#include "dbus/bus.h" #include "dbus/bus.h"
#include "dbus/message.h" #include "dbus/message.h"
#include "third_party/cros_system_api/dbus/service_constants.h" #include "third_party/cros_system_api/dbus/service_constants.h"
...@@ -15,10 +14,17 @@ namespace chromeos { ...@@ -15,10 +14,17 @@ namespace chromeos {
MemoryPressureServiceProvider::MemoryPressureServiceProvider() = default; MemoryPressureServiceProvider::MemoryPressureServiceProvider() = default;
MemoryPressureServiceProvider::~MemoryPressureServiceProvider() = default; MemoryPressureServiceProvider::~MemoryPressureServiceProvider() {
if (exported_object_) {
chromeos::memory::pressure::PressureChecker::GetInstance()->RemoveObserver(
this);
}
}
void MemoryPressureServiceProvider::Start( void MemoryPressureServiceProvider::Start(
scoped_refptr<dbus::ExportedObject> exported_object) { scoped_refptr<dbus::ExportedObject> exported_object) {
DCHECK(!exported_object_);
exported_object_ = exported_object;
exported_object->ExportMethod( exported_object->ExportMethod(
memory_pressure::kMemoryPressureInterface, memory_pressure::kMemoryPressureInterface,
memory_pressure::kGetAvailableMemoryKBMethod, memory_pressure::kGetAvailableMemoryKBMethod,
...@@ -28,11 +34,12 @@ void MemoryPressureServiceProvider::Start( ...@@ -28,11 +34,12 @@ void MemoryPressureServiceProvider::Start(
weak_ptr_factory_.GetWeakPtr())); weak_ptr_factory_.GetWeakPtr()));
exported_object->ExportMethod( exported_object->ExportMethod(
memory_pressure::kMemoryPressureInterface, memory_pressure::kMemoryPressureInterface,
memory_pressure::kGetMemoryMarginKBMethod, memory_pressure::kGetMemoryMarginsKBMethod,
base::BindRepeating(&MemoryPressureServiceProvider::GetMemoryMarginsKB, base::BindRepeating(&MemoryPressureServiceProvider::GetMemoryMarginsKB,
weak_ptr_factory_.GetWeakPtr()), weak_ptr_factory_.GetWeakPtr()),
base::BindRepeating(&MemoryPressureServiceProvider::OnExported, base::BindRepeating(&MemoryPressureServiceProvider::OnExported,
weak_ptr_factory_.GetWeakPtr())); weak_ptr_factory_.GetWeakPtr()));
chromeos::memory::pressure::PressureChecker::GetInstance()->AddObserver(this);
} }
void MemoryPressureServiceProvider::OnExported( void MemoryPressureServiceProvider::OnExported(
...@@ -66,4 +73,20 @@ void MemoryPressureServiceProvider::GetMemoryMarginsKB( ...@@ -66,4 +73,20 @@ void MemoryPressureServiceProvider::GetMemoryMarginsKB(
std::move(response_sender).Run(std::move(response)); std::move(response_sender).Run(std::move(response));
} }
void MemoryPressureServiceProvider::OnCriticalPressure() {
DCHECK(exported_object_);
dbus::Signal signal(memory_pressure::kMemoryPressureInterface,
memory_pressure::kCriticalMemoryPressure);
exported_object_->SendSignal(&signal);
}
void MemoryPressureServiceProvider::OnModeratePressure() {
DCHECK(exported_object_);
dbus::Signal signal(memory_pressure::kMemoryPressureInterface,
memory_pressure::kModerateMemoryPressure);
exported_object_->SendSignal(&signal);
}
} // namespace chromeos } // namespace chromeos
...@@ -11,6 +11,7 @@ ...@@ -11,6 +11,7 @@
#include "base/memory/ref_counted.h" #include "base/memory/ref_counted.h"
#include "base/memory/weak_ptr.h" #include "base/memory/weak_ptr.h"
#include "chromeos/dbus/services/cros_dbus_service.h" #include "chromeos/dbus/services/cros_dbus_service.h"
#include "chromeos/memory/pressure/pressure.h"
#include "dbus/exported_object.h" #include "dbus/exported_object.h"
namespace dbus { namespace dbus {
...@@ -26,7 +27,8 @@ namespace chromeos { ...@@ -26,7 +27,8 @@ namespace chromeos {
// --dest=org.chromium.MemoryPressure /org/chromium/MemoryPressure // --dest=org.chromium.MemoryPressure /org/chromium/MemoryPressure
// org.chromium.MemoryPressure.GetAvailableMemoryKB // org.chromium.MemoryPressure.GetAvailableMemoryKB
class MemoryPressureServiceProvider class MemoryPressureServiceProvider
: public CrosDBusService::ServiceProviderInterface { : public CrosDBusService::ServiceProviderInterface,
public chromeos::memory::pressure::PressureObserver {
public: public:
MemoryPressureServiceProvider(); MemoryPressureServiceProvider();
MemoryPressureServiceProvider& operator=( MemoryPressureServiceProvider& operator=(
...@@ -49,9 +51,16 @@ class MemoryPressureServiceProvider ...@@ -49,9 +51,16 @@ class MemoryPressureServiceProvider
void GetMemoryMarginsKB(dbus::MethodCall* method_call, void GetMemoryMarginsKB(dbus::MethodCall* method_call,
dbus::ExportedObject::ResponseSender response_sender); dbus::ExportedObject::ResponseSender response_sender);
// chromeos::memory::pressure::PressureObserver:
void OnCriticalPressure() override;
void OnModeratePressure() override;
// TODO(b/149833548): Implement signals CriticalMemoryPressure and // TODO(b/149833548): Implement signals CriticalMemoryPressure and
// ModerateMemoryPressure. // ModerateMemoryPressure.
// A reference on ExportedObject for sending signals.
scoped_refptr<dbus::ExportedObject> exported_object_;
base::WeakPtrFactory<MemoryPressureServiceProvider> weak_ptr_factory_{this}; base::WeakPtrFactory<MemoryPressureServiceProvider> weak_ptr_factory_{this};
}; };
......
...@@ -6,6 +6,7 @@ ...@@ -6,6 +6,7 @@
#include "base/files/file_util.h" #include "base/files/file_util.h"
#include "base/logging.h" #include "base/logging.h"
#include "base/memory/singleton.h"
#include "base/strings/string_number_conversions.h" #include "base/strings/string_number_conversions.h"
#include "base/strings/string_split.h" #include "base/strings/string_split.h"
#include "base/strings/string_util.h" #include "base/strings/string_util.h"
...@@ -240,6 +241,53 @@ void UpdateMemoryParameters() { ...@@ -240,6 +241,53 @@ void UpdateMemoryParameters() {
ram_swap_weight = kRamVsSwapWeightDefault; ram_swap_weight = kRamVsSwapWeightDefault;
} }
PressureChecker::PressureChecker() : weak_ptr_factory_(this) {}
PressureChecker::~PressureChecker() = default;
PressureChecker* PressureChecker::GetInstance() {
return base::Singleton<PressureChecker>::get();
}
void PressureChecker::SetCheckingDelay(base::TimeDelta delay) {
if (checking_timer_.GetCurrentDelay() == delay)
return;
if (delay.is_zero()) {
checking_timer_.Stop();
} else {
checking_timer_.Start(FROM_HERE, delay,
base::BindRepeating(&PressureChecker::CheckPressure,
weak_ptr_factory_.GetWeakPtr()));
}
}
void PressureChecker::AddObserver(PressureObserver* observer) {
pressure_observers_.AddObserver(observer);
}
void PressureChecker::RemoveObserver(PressureObserver* observer) {
pressure_observers_.RemoveObserver(observer);
}
void PressureChecker::CheckPressure() {
std::pair<uint64_t, uint64_t> margins_kb =
chromeos::memory::pressure::GetMemoryMarginsKB();
uint64_t critical_margin_kb = margins_kb.first;
uint64_t moderate_margin_kb = margins_kb.second;
uint64_t available_kb = GetAvailableMemoryKB();
if (available_kb < critical_margin_kb) {
for (auto& observer : pressure_observers_) {
observer.OnCriticalPressure();
}
} else if (available_kb < moderate_margin_kb) {
for (auto& observer : pressure_observers_) {
observer.OnModeratePressure();
}
}
}
} // namespace pressure } // namespace pressure
} // namespace memory } // namespace memory
} // namespace chromeos } // namespace chromeos
...@@ -9,9 +9,17 @@ ...@@ -9,9 +9,17 @@
#include <string> #include <string>
#include <utility> #include <utility>
#include "base/component_export.h"
#include "base/observer_list.h"
#include "base/process/process_metrics.h" #include "base/process/process_metrics.h"
#include "base/timer/timer.h"
#include "chromeos/chromeos_export.h" #include "chromeos/chromeos_export.h"
namespace base {
template <typename T>
struct DefaultSingletonTraits;
}
namespace chromeos { namespace chromeos {
namespace memory { namespace memory {
namespace pressure { namespace pressure {
...@@ -42,6 +50,48 @@ CHROMEOS_EXPORT std::pair<uint64_t, uint64_t> GetMemoryMarginsKB(); ...@@ -42,6 +50,48 @@ CHROMEOS_EXPORT std::pair<uint64_t, uint64_t> GetMemoryMarginsKB();
// parameters are changed, call this function to update the saved values. // parameters are changed, call this function to update the saved values.
void UpdateMemoryParameters(); void UpdateMemoryParameters();
class PressureObserver : public base::CheckedObserver {
public:
// Called when the system is under critical memory pressure.
virtual void OnCriticalPressure() = 0;
// Called when the system is under moderate memory pressure.
virtual void OnModeratePressure() = 0;
};
// Check memory pressure periodically and notify the observers when memory
// pressure is high.
class COMPONENT_EXPORT(CHROMEOS_MEMORY) PressureChecker {
public:
static PressureChecker* GetInstance();
// Set the delay between checks. Setting zero delay stops the checking timer.
void SetCheckingDelay(base::TimeDelta delay);
void AddObserver(PressureObserver* observer);
void RemoveObserver(PressureObserver* observer);
private:
friend struct base::DefaultSingletonTraits<PressureChecker>;
PressureChecker();
~PressureChecker();
// Check memory pressure and notify the observers when memory pressure is
// high.
void CheckPressure();
base::ObserverList<PressureObserver> pressure_observers_;
// A timer to check the memory pressure periodically.
base::RepeatingTimer checking_timer_;
base::WeakPtrFactory<PressureChecker> weak_ptr_factory_;
DISALLOW_COPY_AND_ASSIGN(PressureChecker);
};
} // namespace pressure } // namespace pressure
} // namespace memory } // namespace memory
} // namespace chromeos } // namespace chromeos
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment