Commit 1d19b802 authored by sky's avatar sky Committed by Commit bot

Revert of Global Resource Coordinator: Basic service internals (patchset #30...

Revert of Global Resource Coordinator: Basic service internals (patchset #30 id:560001 of https://codereview.chromium.org/2798713002/ )

Reason for revert:
Reverting as CoordinationUnitImplTest.CyclicGraphUnits is crashing on windows dbg. The output isn't very helpful:
https://luci-logdog.appspot.com/v/?s=chromium%2Fbb%2Fchromium.win%2FWin7_Tests__dbg__1_%2F59514%2F%2B%2Frecipes%2Fsteps%2Fservice_unittests%2F0%2Fstdout

 RUN      ] CoordinationUnitImplTest.CyclicGraphUnits

[114/116] CoordinationUnitImplTest.CyclicGraphUnits (CRASHED)
[115/116] CoordinatorImplTest.NoProcessLocalManagers (1 ms)
[116/116] CoordinatorImplTest.SeveralProcessLocalManagers (4 ms)
Retrying 1 test (retry #1)
[ RUN      ] CoordinationUnitImplTest.CyclicGraphUnits

[117/117] CoordinationUnitImplTest.CyclicGraphUnits (CRASHED)
Retrying 1 test (retry #2)
[ RUN      ] CoordinationUnitImplTest.CyclicGraphUnits

[118/118] CoordinationUnitImplTest.CyclicGraphUnits (CRASHED)
Retrying 1 test (retry #3)
[ RUN      ] CoordinationUnitImplTest.CyclicGraphUnits

[119/119] CoordinationUnitImplTest.CyclicGraphUnits (CRASHED)

Original issue's description:
> Global Resource Coordinator: Basic service internals
>
> This adds the basic internals of the GRC; CoordinationUnits which can form a DAG, receive events, and send back updated resource usage policies.
>
> A full prototype of GRC usage can be seen here: https://codereview.chromium.org/2710823003
>
> Service architecture doc: https://docs.google.com/document/d/1qec4DNDM2pLLIFfCBtnNQTxlNXQzjml69yC8SGU9bzI/edit#
>
> GRC parent doc (internal only): https://docs.google.com/document/d/1dx4KDbDFvP-GWwwrSPg8Gxx4kboIoPi8kDKTSXoTbC4/edit#heading=h.td4yhfm12fe3
>
> R=primiano@chromium.org,skyostil@chromium.org,fmeawad@chromium.org,rockot@chromium.org
> BUG=691886
>
> Review-Url: https://codereview.chromium.org/2798713002
> Cr-Commit-Position: refs/heads/master@{#468002}
> Committed: https://chromium.googlesource.com/chromium/src/+/de0f39d2a625433e60b5e22e1d2d3803f3d219e5

TBR=chrisha@chromium.org,dcheng@chromium.org,fmeawad@chromium.org,jam@chromium.org,nasko@chromium.org,primiano@chromium.org,rockot@chromium.org,skyostil@chromium.org,oysteine@chromium.org
# Skipping CQ checks because original CL landed less than 1 days ago.
NOPRESUBMIT=true
NOTREECHECKS=true
NOTRY=true
BUG=691886

Review-Url: https://codereview.chromium.org/2851813002
Cr-Commit-Position: refs/heads/master@{#468061}
parent 2f0dc808
...@@ -2,24 +2,13 @@ ...@@ -2,24 +2,13 @@
# Use of this source code is governed by a BSD-style license that can be # Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file. # found in the LICENSE file.
# There should be only one resource coordinator. It is currently # There should be only one memory instrumentaiton coordinator. It is currently
# in the browser process. So, only //content/browser should link to this target. # in the browser process. So, only //content/browser should link to this target.
# Others modules should only need the public targets. # Others modules should only need the public targets.
import("//services/catalog/public/tools/catalog.gni")
import("//services/service_manager/public/cpp/service.gni")
import("//services/service_manager/public/service_manifest.gni")
import("//services/service_manager/public/tools/test/service_test.gni")
source_set("lib") { source_set("lib") {
sources = [ sources = [
"coordination_unit/coordination_unit_impl.cc",
"coordination_unit/coordination_unit_impl.h",
"coordination_unit/coordination_unit_provider_impl.cc",
"coordination_unit/coordination_unit_provider_impl.h",
"memory/coordinator/coordinator_impl.cc", "memory/coordinator/coordinator_impl.cc",
"memory/coordinator/coordinator_impl.h", "memory/coordinator/coordinator_impl.h",
"resource_coordinator_service.cc",
"resource_coordinator_service.h",
] ]
public_deps = [ public_deps = [
...@@ -27,33 +16,12 @@ source_set("lib") { ...@@ -27,33 +16,12 @@ source_set("lib") {
"//mojo/public/cpp/bindings", "//mojo/public/cpp/bindings",
"//services/resource_coordinator/public/cpp:resource_coordinator_cpp", "//services/resource_coordinator/public/cpp:resource_coordinator_cpp",
] ]
data_deps = [
":manifest",
]
}
service_manifest("manifest") {
name = "resource_coordinator"
source = "manifest.json"
}
service("resource_coordinator") {
sources = [
"service_main.cc",
]
deps = [
":lib",
"//mojo/public/cpp/system",
]
} }
source_set("tests") { source_set("tests") {
testonly = true testonly = true
sources = [ sources = [
"coordination_unit/coordination_unit_impl_unittest.cc",
"memory/coordinator/coordinator_impl_unittest.cc", "memory/coordinator/coordinator_impl_unittest.cc",
"public/cpp/memory/process_local_dump_manager_impl_unittest.cc", "public/cpp/memory/process_local_dump_manager_impl_unittest.cc",
] ]
...@@ -66,31 +34,3 @@ source_set("tests") { ...@@ -66,31 +34,3 @@ source_set("tests") {
"//testing/gtest", "//testing/gtest",
] ]
} }
service_test("resource_coordinator_unittests") {
sources = [
"resource_coordinator_service_unittest.cc",
]
catalog = ":resource_coordinator_unittests_catalog"
deps = [
"//base",
"//mojo/public/cpp/bindings",
"//services/resource_coordinator/public/cpp:resource_coordinator_cpp",
"//services/service_manager/public/cpp",
"//services/service_manager/public/cpp:service_test_support",
"//services/service_manager/public/interfaces",
"//testing/gtest",
]
}
service_manifest("unittest_manifest") {
name = "resource_coordinator_unittests"
source = "unittest_manifest.json"
}
catalog("resource_coordinator_unittests_catalog") {
embedded_services = [ ":unittest_manifest" ]
standalone_services = [ ":manifest" ]
}
include_rules = [
"+third_party/smhasher",
]
// Copyright 2017 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 "services/resource_coordinator/coordination_unit/coordination_unit_impl.h"
#include <memory>
#include <utility>
#include "base/logging.h"
#include "base/process/process_handle.h"
#include "base/strings/string_number_conversions.h"
#include "base/unguessable_token.h"
#include "mojo/public/cpp/bindings/strong_binding.h"
#include "services/resource_coordinator/public/cpp/coordination_unit_id.h"
namespace resource_coordinator {
namespace {
using CUIDMap = std::unordered_map<CoordinationUnitID, CoordinationUnitImpl*>;
CUIDMap& g_cu_map() {
static CUIDMap* instance = new CUIDMap();
return *instance;
}
} // namespace
CoordinationUnitImpl::CoordinationUnitImpl(
const CoordinationUnitID& id,
std::unique_ptr<service_manager::ServiceContextRef> service_ref) {
if (!id.id) {
id_ = CoordinationUnitID(id.type,
base::UnguessableToken().Create().ToString());
} else {
id_ = id;
}
auto it = g_cu_map().insert(std::make_pair(id_, this));
DCHECK(it.second); // Inserted successfully
service_ref_ = std::move(service_ref);
}
CoordinationUnitImpl::~CoordinationUnitImpl() {
g_cu_map().erase(id_);
for (CoordinationUnitImpl* child : children_) {
child->RemoveParent(this);
}
for (CoordinationUnitImpl* parent : parents_) {
parent->RemoveChild(this);
}
}
bool CoordinationUnitImpl::SelfOrParentHasFlagSet(StateFlags state) {
const base::Optional<bool>& state_flag = state_flags_[state];
if (state_flag && *state_flag) {
return true;
}
for (CoordinationUnitImpl* parent : parents_) {
if (parent->SelfOrParentHasFlagSet(state)) {
return true;
}
}
return false;
}
void CoordinationUnitImpl::RecalcCoordinationPolicy() {
for (CoordinationUnitImpl* child : children_) {
child->RecalcCoordinationPolicy();
}
if (!policy_callback_) {
return;
}
bool background_priority = !SelfOrParentHasFlagSet(kTabVisible) &&
!SelfOrParentHasFlagSet(kAudioPlaying);
// Send the priority to the client if it's new or changed.
if (!current_policy_) {
current_policy_ = mojom::CoordinationPolicy::New();
} else if ((current_policy_->use_background_priority ==
background_priority) &&
!SelfOrParentHasFlagSet(StateFlags::kTestState)) {
return;
}
// current_policy_ should be kept in sync with the policy we
// send to the client, to avoid redundant updates.
// TODO(oysteine): Once this object becomes more complex, make
// copying more robust.
mojom::CoordinationPolicyPtr policy = mojom::CoordinationPolicy::New();
policy->use_background_priority = background_priority;
current_policy_->use_background_priority = background_priority;
policy_callback_->SetCoordinationPolicy(std::move(policy));
}
void CoordinationUnitImpl::SendEvent(mojom::EventPtr event) {
switch (event->type) {
case mojom::EventType::kOnWebContentsShown:
state_flags_[kTabVisible] = true;
break;
case mojom::EventType::kOnWebContentsHidden:
state_flags_[kTabVisible] = false;
break;
case mojom::EventType::kOnProcessAudioStarted:
state_flags_[kAudioPlaying] = true;
break;
case mojom::EventType::kOnProcessAudioStopped:
state_flags_[kAudioPlaying] = false;
break;
case mojom::EventType::kTestEvent:
state_flags_[kTestState] = true;
break;
default:
return;
}
RecalcCoordinationPolicy();
}
void CoordinationUnitImpl::GetID(const GetIDCallback& callback) {
callback.Run(id_);
}
void CoordinationUnitImpl::Duplicate(mojom::CoordinationUnitRequest request) {
bindings_.AddBinding(this, std::move(request));
}
void CoordinationUnitImpl::AddChild(const CoordinationUnitID& child_id) {
if (child_id == id_) {
return;
}
auto child_iter = g_cu_map().find(child_id);
if (child_iter != g_cu_map().end()) {
CoordinationUnitImpl* child = child_iter->second;
if (HasParent(child) || HasChild(child)) {
return;
}
DCHECK(child->id_ == child_id);
DCHECK(child != this);
if (AddChild(child)) {
child->AddParent(this);
}
}
}
bool CoordinationUnitImpl::AddChild(CoordinationUnitImpl* child) {
// We don't recalculate the policy here as policies are only dependent
// on the current CU or its parents, not its children. In other words,
// policies only bubble down.
return children_.count(child) ? false : children_.insert(child).second;
}
void CoordinationUnitImpl::RemoveChild(CoordinationUnitImpl* child) {
size_t children_removed = children_.erase(child);
DCHECK_EQ(1u, children_removed);
}
void CoordinationUnitImpl::AddParent(CoordinationUnitImpl* parent) {
DCHECK_EQ(0u, parents_.count(parent));
parents_.insert(parent);
RecalcCoordinationPolicy();
}
void CoordinationUnitImpl::RemoveParent(CoordinationUnitImpl* parent) {
size_t parents_removed = parents_.erase(parent);
DCHECK_EQ(1u, parents_removed);
RecalcCoordinationPolicy();
}
bool CoordinationUnitImpl::HasParent(CoordinationUnitImpl* unit) {
for (CoordinationUnitImpl* parent : parents_) {
if (parent == unit || parent->HasParent(unit)) {
return true;
}
}
return false;
}
bool CoordinationUnitImpl::HasChild(CoordinationUnitImpl* unit) {
for (CoordinationUnitImpl* child : children_) {
if (child == unit || child->HasChild(unit)) {
return true;
}
}
return false;
}
void CoordinationUnitImpl::SetCoordinationPolicyCallback(
mojom::CoordinationPolicyCallbackPtr callback) {
callback.set_connection_error_handler(
base::Bind(&CoordinationUnitImpl::UnregisterCoordinationPolicyCallback,
base::Unretained(this)));
policy_callback_ = std::move(callback);
RecalcCoordinationPolicy();
}
void CoordinationUnitImpl::UnregisterCoordinationPolicyCallback() {
policy_callback_.reset();
current_policy_.reset();
}
} // namespace resource_coordinator
// Copyright 2017 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 SERVICES_RESOURCE_COORDINATOR_COORDINATION_UNIT_COORDINATION_UNIT_IMPL_H_
#define SERVICES_RESOURCE_COORDINATOR_COORDINATION_UNIT_COORDINATION_UNIT_IMPL_H_
#include <list>
#include "base/optional.h"
#include "mojo/public/cpp/bindings/binding_set.h"
#include "mojo/public/cpp/bindings/interface_request.h"
#include "mojo/public/cpp/bindings/strong_binding.h"
#include "services/resource_coordinator/public/cpp/coordination_unit_id.h"
#include "services/resource_coordinator/public/interfaces/coordination_unit.mojom.h"
#include "services/resource_coordinator/public/interfaces/coordination_unit_provider.mojom.h"
#include "services/service_manager/public/cpp/service_context_ref.h"
namespace resource_coordinator {
class CoordinationUnitImpl : public mojom::CoordinationUnit {
public:
CoordinationUnitImpl(
const CoordinationUnitID& id,
std::unique_ptr<service_manager::ServiceContextRef> service_ref);
~CoordinationUnitImpl() override;
// Overridden from mojom::CoordinationUnit:
void SendEvent(mojom::EventPtr event) override;
void GetID(const GetIDCallback& callback) override;
void Duplicate(mojom::CoordinationUnitRequest request) override;
void AddChild(const CoordinationUnitID& child_id) override;
void SetCoordinationPolicyCallback(
mojom::CoordinationPolicyCallbackPtr callback) override;
private:
bool AddChild(CoordinationUnitImpl* child);
void RemoveChild(CoordinationUnitImpl* child);
void AddParent(CoordinationUnitImpl* parent);
void RemoveParent(CoordinationUnitImpl* parent);
bool HasParent(CoordinationUnitImpl* unit);
bool HasChild(CoordinationUnitImpl* unit);
void RecalcCoordinationPolicy();
void UnregisterCoordinationPolicyCallback();
enum StateFlags : uint8_t {
kTestState,
kTabVisible,
kAudioPlaying,
kNumStateFlags
};
bool SelfOrParentHasFlagSet(StateFlags state);
std::unique_ptr<service_manager::ServiceContextRef> service_ref_;
mojo::BindingSet<mojom::CoordinationUnit> bindings_;
CoordinationUnitID id_;
std::set<CoordinationUnitImpl*> children_;
std::set<CoordinationUnitImpl*> parents_;
mojom::CoordinationPolicyCallbackPtr policy_callback_;
mojom::CoordinationPolicyPtr current_policy_;
base::Optional<bool> state_flags_[kNumStateFlags];
DISALLOW_COPY_AND_ASSIGN(CoordinationUnitImpl);
};
} // namespace resource_coordinator
#endif // SERVICES_RESOURCE_COORDINATOR_COORDINATION_UNIT_COORDINATION_UNIT_IMPL_H_
// Copyright 2017 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 <memory>
#include <vector>
#include "base/bind.h"
#include "base/message_loop/message_loop.h"
#include "base/run_loop.h"
#include "services/resource_coordinator/coordination_unit/coordination_unit_provider_impl.h"
#include "services/service_manager/public/cpp/service_context_ref.h"
#include "testing/gtest/include/gtest/gtest.h"
namespace resource_coordinator {
namespace {
void OnLastServiceRefDestroyed() {
// No-op. This is required by service_manager::ServiceContextRefFactory
// construction but not needed for the tests.
}
class CoordinationUnitImplTest : public testing::Test {
public:
CoordinationUnitImplTest()
: service_ref_factory_(base::Bind(&OnLastServiceRefDestroyed)),
provider_(&service_ref_factory_) {}
~CoordinationUnitImplTest() override {}
// testing::Test:
void TearDown() override { base::RunLoop().RunUntilIdle(); }
protected:
CoordinationUnitProviderImpl* provider() { return &provider_; }
private:
base::MessageLoop message_loop_;
service_manager::ServiceContextRefFactory service_ref_factory_;
CoordinationUnitProviderImpl provider_;
};
class TestCoordinationUnit : public mojom::CoordinationPolicyCallback {
public:
TestCoordinationUnit(CoordinationUnitProviderImpl* provider,
const CoordinationUnitType& type,
const std::string& id)
: binding_(this) {
CHECK(provider);
CoordinationUnitID new_cu_id(type, id);
mojom::CoordinationUnitPtr coordination_unit;
provider->CreateCoordinationUnit(mojo::MakeRequest(&coordination_unit_),
new_cu_id);
base::RunLoop callback;
SetGetIDClosure(callback.QuitClosure());
coordination_unit_->SetCoordinationPolicyCallback(GetPolicyCallback());
// Forces us to wait for the creation of the CUID to finish.
coordination_unit_->GetID(base::Bind(&TestCoordinationUnit::GetIDCallback,
base::Unretained(this)));
callback.Run();
}
void GetIDCallback(const CoordinationUnitID& cu_id) {
id_ = cu_id;
get_id_closure_.Run();
}
void SetGetIDClosure(const base::Closure& get_id_closure) {
get_id_closure_ = get_id_closure;
}
void SetPolicyClosure(const base::Closure& policy_closure) {
policy_update_closure_ = policy_closure;
}
mojom::CoordinationPolicyCallbackPtr GetPolicyCallback() {
return binding_.CreateInterfacePtrAndBind();
}
// The CU will always send policy updates on events (including parent events)
void ForcePolicyUpdates() {
base::RunLoop callback;
SetPolicyClosure(callback.QuitClosure());
mojom::EventPtr event = mojom::Event::New();
event->type = mojom::EventType::kTestEvent;
coordination_unit_->SendEvent(std::move(event));
callback.Run();
}
const mojom::CoordinationUnitPtr& interface() const {
return coordination_unit_;
}
const CoordinationUnitID& id() const { return id_; }
// mojom::CoordinationPolicyCallback:
void SetCoordinationPolicy(
resource_coordinator::mojom::CoordinationPolicyPtr policy) override {
if (policy_update_closure_) {
policy_update_closure_.Run();
}
}
private:
base::Closure policy_update_closure_;
base::Closure get_id_closure_;
mojo::Binding<mojom::CoordinationPolicyCallback> binding_;
mojom::CoordinationUnitPtr coordination_unit_;
CoordinationUnitID id_;
};
} // namespace
TEST_F(CoordinationUnitImplTest, BasicPolicyCallback) {
TestCoordinationUnit test_coordination_unit(
provider(), CoordinationUnitType::kWebContents, "test_id");
test_coordination_unit.ForcePolicyUpdates();
}
TEST_F(CoordinationUnitImplTest, AddChild) {
TestCoordinationUnit parent_unit(
provider(), CoordinationUnitType::kWebContents, "parent_unit");
TestCoordinationUnit child_unit(
provider(), CoordinationUnitType::kWebContents, "child_unit");
child_unit.ForcePolicyUpdates();
parent_unit.ForcePolicyUpdates();
{
base::RunLoop callback;
child_unit.SetPolicyClosure(callback.QuitClosure());
parent_unit.interface()->AddChild(child_unit.id());
callback.Run();
}
{
base::RunLoop parent_callback;
base::RunLoop child_callback;
parent_unit.SetPolicyClosure(parent_callback.QuitClosure());
child_unit.SetPolicyClosure(child_callback.QuitClosure());
// This event should force the policy to recalculated for all children.
mojom::EventPtr event = mojom::Event::New();
event->type = mojom::EventType::kTestEvent;
parent_unit.interface()->SendEvent(std::move(event));
parent_callback.Run();
child_callback.Run();
}
}
TEST_F(CoordinationUnitImplTest, CyclicGraphUnits) {
TestCoordinationUnit parent_unit(
provider(), CoordinationUnitType::kWebContents, std::string());
TestCoordinationUnit child_unit(
provider(), CoordinationUnitType::kWebContents, std::string());
child_unit.ForcePolicyUpdates();
parent_unit.ForcePolicyUpdates();
{
base::RunLoop callback;
child_unit.SetPolicyClosure(callback.QuitClosure());
parent_unit.interface()->AddChild(child_unit.id());
callback.Run();
}
// This should fail, due to the existing child-parent relationship.
// Otherwise we end up with infinite recursion and crash when recalculating
// policies below.
child_unit.interface()->AddChild(parent_unit.id());
{
base::RunLoop parent_callback;
base::RunLoop child_callback;
parent_unit.SetPolicyClosure(parent_callback.QuitClosure());
child_unit.SetPolicyClosure(child_callback.QuitClosure());
// This event should force the policy to recalculated for all children.
mojom::EventPtr event = mojom::Event::New();
event->type = mojom::EventType::kTestEvent;
parent_unit.interface()->SendEvent(std::move(event));
parent_callback.Run();
child_callback.Run();
}
}
} // namespace resource_coordinator
// Copyright 2017 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 "services/resource_coordinator/coordination_unit/coordination_unit_provider_impl.h"
#include <memory>
#include <utility>
#include "base/logging.h"
#include "mojo/public/cpp/bindings/strong_binding.h"
#include "services/resource_coordinator/coordination_unit/coordination_unit_impl.h"
#include "services/service_manager/public/cpp/service_context_ref.h"
namespace resource_coordinator {
CoordinationUnitProviderImpl::CoordinationUnitProviderImpl(
service_manager::ServiceContextRefFactory* service_ref_factory)
: service_ref_factory_(service_ref_factory) {
DCHECK(service_ref_factory);
service_ref_ = service_ref_factory->CreateRef();
}
CoordinationUnitProviderImpl::~CoordinationUnitProviderImpl() = default;
void CoordinationUnitProviderImpl::CreateCoordinationUnit(
mojom::CoordinationUnitRequest request,
const CoordinationUnitID& id) {
// TODO(oysteine): A strong binding here means the first binding set up
// to a CoordinationUnit via CoordinationUnitProvider, i.e. the authoritative
// one in terms of setting the context, has to outlive all of the other
// connections (as the rest are just duplicated and held within
// CoordinationUnit). Make sure this assumption is correct, or refactor into
// some kind of refcounted thing.
// Once there's a need for custom code for various types of CUs (tabs,
// processes, etc) then this could become a factory function and instantiate
// different subclasses of CoordinationUnitImpl based on the id.type.
mojo::MakeStrongBinding(base::MakeUnique<CoordinationUnitImpl>(
id, service_ref_factory_->CreateRef()),
std::move(request));
};
// static
void CoordinationUnitProviderImpl::Create(
service_manager::ServiceContextRefFactory* service_ref_factory,
resource_coordinator::mojom::CoordinationUnitProviderRequest request) {
mojo::MakeStrongBinding(
base::MakeUnique<CoordinationUnitProviderImpl>(service_ref_factory),
std::move(request));
}
} // namespace resource_coordinator
// Copyright 2017 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 SERVICES_RESOURCE_COORDINATOR_COORDINATION_UNIT_COORDINATION_UNIT_PROVIDER_IMPL_H_
#define SERVICES_RESOURCE_COORDINATOR_COORDINATION_UNIT_COORDINATION_UNIT_PROVIDER_IMPL_H_
#include "mojo/public/cpp/bindings/interface_request.h"
#include "mojo/public/cpp/bindings/strong_binding.h"
#include "services/resource_coordinator/public/interfaces/coordination_unit_provider.mojom.h"
namespace service_manager {
class ServiceContextRefFactory;
class ServiceContextRef;
} // service_manager
namespace resource_coordinator {
class CoordinationUnitProviderImpl : public mojom::CoordinationUnitProvider {
public:
CoordinationUnitProviderImpl(
service_manager::ServiceContextRefFactory* service_ref_factory);
~CoordinationUnitProviderImpl() override;
static void Create(
service_manager::ServiceContextRefFactory* service_ref_factory,
resource_coordinator::mojom::CoordinationUnitProviderRequest request);
// Overridden from mojom::CoordinationUnitProvider:
void CreateCoordinationUnit(
resource_coordinator::mojom::CoordinationUnitRequest request,
const CoordinationUnitID& id) override;
private:
service_manager::ServiceContextRefFactory* service_ref_factory_;
std::unique_ptr<service_manager::ServiceContextRef> service_ref_;
DISALLOW_COPY_AND_ASSIGN(CoordinationUnitProviderImpl);
};
} // namespace resource_coordinator
#endif // SERVICES_RESOURCE_COORDINATOR_COORDINATION_UNIT_COORDINATION_UNIT_PROVIDER_IMPL_H_
{
"name": "resource_coordinator",
"display_name": "Global Resource Coordinator",
"interface_provider_specs": {
"service_manager:connector": {
"provides": {
"coordination_unit": [ "resource_coordinator::mojom::CoordinationUnitProvider"],
"tests": [ "*" ]
},
"requires": {
"service_manager": [ "service_manager:all_users" ]
}
}
}
}
...@@ -4,17 +4,12 @@ ...@@ -4,17 +4,12 @@
component("resource_coordinator_cpp") { component("resource_coordinator_cpp") {
sources = [ sources = [
"coordination_unit_id.cc",
"coordination_unit_id.h",
"coordination_unit_types.h",
"memory/coordinator.h", "memory/coordinator.h",
"memory/process_local_dump_manager_impl.cc", "memory/process_local_dump_manager_impl.cc",
"memory/process_local_dump_manager_impl.h", "memory/process_local_dump_manager_impl.h",
"resource_coordinator_interface.cc",
"resource_coordinator_interface.h",
] ]
defines = [ "SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_IMPLEMENTATION" ] defines = [ "SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_IMPLEMENTATION" ]
deps = [ deps = [
":struct_traits", ":struct_traits",
...@@ -25,7 +20,6 @@ component("resource_coordinator_cpp") { ...@@ -25,7 +20,6 @@ component("resource_coordinator_cpp") {
"//mojo/public/cpp/bindings", "//mojo/public/cpp/bindings",
"//services/resource_coordinator/public/interfaces:interfaces_internal", "//services/resource_coordinator/public/interfaces:interfaces_internal",
"//services/service_manager/public/cpp", "//services/service_manager/public/cpp",
"//third_party/smhasher:murmurhash2",
] ]
allow_circular_includes_from = [ "//services/resource_coordinator/public/interfaces:interfaces_internal" ] allow_circular_includes_from = [ "//services/resource_coordinator/public/interfaces:interfaces_internal" ]
...@@ -33,13 +27,11 @@ component("resource_coordinator_cpp") { ...@@ -33,13 +27,11 @@ component("resource_coordinator_cpp") {
source_set("struct_traits") { source_set("struct_traits") {
sources = [ sources = [
"coordination_unit_struct_traits.cc",
"coordination_unit_struct_traits.h",
"memory/memory_instrumentation_struct_traits.cc", "memory/memory_instrumentation_struct_traits.cc",
"memory/memory_instrumentation_struct_traits.h", "memory/memory_instrumentation_struct_traits.h",
] ]
defines = [ "SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_IMPLEMENTATION" ] defines = [ "SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_IMPLEMENTATION" ]
public_deps = [ public_deps = [
"//base", "//base",
......
per-file *.typemap=set noparent
per-file *.typemap=file://ipc/SECURITY_OWNERS
per-file *_struct_traits*.*=set noparent
per-file *_struct_traits*.*=file://ipc/SECURITY_OWNERS
# Copyright 2017 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.
mojom =
"//services/resource_coordinator/public/interfaces/coordination_unit.mojom"
public_headers = [
"//services/resource_coordinator/public/cpp/coordination_unit_id.h",
"//services/resource_coordinator/public/cpp/coordination_unit_types.h",
]
traits_headers = [ "//services/resource_coordinator/public/cpp/coordination_unit_struct_traits.h" ]
deps = []
type_mappings = [
"resource_coordinator.mojom.CoordinationUnitType=::resource_coordinator::CoordinationUnitType",
"resource_coordinator.mojom.CoordinationUnitID=::resource_coordinator::CoordinationUnitID",
]
// Copyright 2017 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 "services/resource_coordinator/public/cpp/coordination_unit_id.h"
#include "base/logging.h"
#include "base/numerics/safe_conversions.h"
#include "third_party/smhasher/src/MurmurHash2.h"
namespace resource_coordinator {
// The seed to use when taking the murmur2 hash of the id.
const uint64_t kMurmur2HashSeed = 0;
CoordinationUnitID::CoordinationUnitID()
: id(0), type(CoordinationUnitType::kInvalidType) {}
CoordinationUnitID::CoordinationUnitID(const CoordinationUnitType& type,
const std::string& new_id)
: type(type) {
DCHECK(base::IsValueInRangeForNumericType<int>(new_id.size()));
id = MurmurHash64A(&new_id.front(), static_cast<int>(new_id.size()),
kMurmur2HashSeed);
}
} // resource_coordinator
// Copyright 2017 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 SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_ID_H_
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_ID_H_
#include <string>
#include "services/resource_coordinator/public/cpp/coordination_unit_types.h"
#include "services/resource_coordinator/public/cpp/resource_coordinator_export.h"
namespace resource_coordinator {
// This is a native struct rather than a mojom struct as we eventually want
// to annotate base::TaskRunner with CUs for cost attribution purses and
// would like to move it to base/ as easily as possible at that point.
struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT CoordinationUnitID {
CoordinationUnitID();
CoordinationUnitID(const CoordinationUnitType& type,
const std::string& new_id);
bool operator==(const CoordinationUnitID& b) const {
return id == b.id && type == b.type;
}
int64_t id;
CoordinationUnitType type;
};
} // resource_coordinator
namespace std {
template <>
struct hash<resource_coordinator::CoordinationUnitID> {
uint64_t operator()(
const resource_coordinator::CoordinationUnitID& id) const {
return ((static_cast<uint64_t>(id.type)) << 32) | id.id;
}
};
} // namespace std
#endif // SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_ID_H_
// Copyright 2017 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 "services/resource_coordinator/public/cpp/coordination_unit_struct_traits.h"
namespace mojo {
// static
resource_coordinator::mojom::CoordinationUnitType
EnumTraits<resource_coordinator::mojom::CoordinationUnitType,
resource_coordinator::CoordinationUnitType>::
ToMojom(resource_coordinator::CoordinationUnitType type) {
switch (type) {
case resource_coordinator::CoordinationUnitType::kWebContents:
return resource_coordinator::mojom::CoordinationUnitType::kWebContents;
case resource_coordinator::CoordinationUnitType::kFrame:
return resource_coordinator::mojom::CoordinationUnitType::kFrame;
case resource_coordinator::CoordinationUnitType::kNavigation:
return resource_coordinator::mojom::CoordinationUnitType::kNavigation;
case resource_coordinator::CoordinationUnitType::kProcess:
return resource_coordinator::mojom::CoordinationUnitType::kProcess;
default:
NOTREACHED() << "Invalid type: " << static_cast<uint8_t>(type);
// This should not be reached. Just return a random value.
return resource_coordinator::mojom::CoordinationUnitType::kWebContents;
}
}
// static
bool EnumTraits<resource_coordinator::mojom::CoordinationUnitType,
resource_coordinator::CoordinationUnitType>::
FromMojom(resource_coordinator::mojom::CoordinationUnitType input,
resource_coordinator::CoordinationUnitType* out) {
switch (input) {
case resource_coordinator::mojom::CoordinationUnitType::kWebContents:
*out = resource_coordinator::CoordinationUnitType::kWebContents;
break;
case resource_coordinator::mojom::CoordinationUnitType::kFrame:
*out = resource_coordinator::CoordinationUnitType::kFrame;
break;
case resource_coordinator::mojom::CoordinationUnitType::kNavigation:
*out = resource_coordinator::CoordinationUnitType::kNavigation;
break;
case resource_coordinator::mojom::CoordinationUnitType::kProcess:
*out = resource_coordinator::CoordinationUnitType::kProcess;
break;
default:
NOTREACHED() << "Invalid type: " << static_cast<uint8_t>(input);
return false;
}
return true;
}
// static
bool StructTraits<resource_coordinator::mojom::CoordinationUnitIDDataView,
resource_coordinator::CoordinationUnitID>::
Read(resource_coordinator::mojom::CoordinationUnitIDDataView input,
resource_coordinator::CoordinationUnitID* out) {
out->id = input.id();
if (!input.ReadType(&out->type))
return false;
return true;
}
} // namespace mojo
// Copyright 2017 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 SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_COORDINATION_UNIT_STRUCT_TRAITS_H_
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_COORDINATION_UNIT_STRUCT_TRAITS_H_
#include "services/resource_coordinator/public/cpp/coordination_unit_types.h"
#include "services/resource_coordinator/public/interfaces/coordination_unit.mojom.h"
namespace mojo {
template <>
struct EnumTraits<resource_coordinator::mojom::CoordinationUnitType,
resource_coordinator::CoordinationUnitType> {
static resource_coordinator::mojom::CoordinationUnitType ToMojom(
resource_coordinator::CoordinationUnitType type);
static bool FromMojom(resource_coordinator::mojom::CoordinationUnitType input,
resource_coordinator::CoordinationUnitType* out);
};
template <>
struct StructTraits<resource_coordinator::mojom::CoordinationUnitIDDataView,
resource_coordinator::CoordinationUnitID> {
static uint64_t id(const resource_coordinator::CoordinationUnitID& id) {
return id.id;
}
static resource_coordinator::CoordinationUnitType type(
const resource_coordinator::CoordinationUnitID& id) {
return id.type;
}
static bool Read(
resource_coordinator::mojom::CoordinationUnitIDDataView input,
resource_coordinator::CoordinationUnitID* out);
};
} // namespace mojo
#endif // SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_COORDINATION_UNIT_STRUCT_TRAITS_H_
// Copyright 2017 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 SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_TYPES_H_
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_TYPES_H_
#include <stdint.h>
namespace resource_coordinator {
// Any new type here needs to be mirrored between coordination_unit_types.h and
// coordination_unit.mojom, and have mappings between the two defined in
// coordination_unit_struct_traits.h/.cc
enum class CoordinationUnitType : uint8_t {
kInvalidType,
kWebContents,
kFrame,
kNavigation,
kProcess,
};
} // resource_coordinator
#endif // SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_TYPES_H_
...@@ -2,29 +2,31 @@ ...@@ -2,29 +2,31 @@
// Use of this source code is governed by a BSD-style license that can be // Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file. // found in the LICENSE file.
#ifndef SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_RESOURCE_COORDINATOR_EXPORT_H_ #ifndef SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_MEMORY_EXPORT_H_
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_RESOURCE_COORDINATOR_EXPORT_H_ #define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_MEMORY_EXPORT_H_
#if defined(COMPONENT_BUILD) #if defined(COMPONENT_BUILD)
#if defined(WIN32) #if defined(WIN32)
#if defined(SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_IMPLEMENTATION) #if defined(SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_IMPLEMENTATION)
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT __declspec(dllexport) #define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT \
__declspec(dllexport)
#else #else
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT __declspec(dllimport) #define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT \
#endif // defined(SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_IMPLEMENTATION) __declspec(dllimport)
#endif // defined(SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_IMPLEMENTATION)
#else // defined(WIN32) #else // defined(WIN32)
#if defined(SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_IMPLEMENTATION) #if defined(SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_IMPLEMENTATION)
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT \ #define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT \
__attribute__((visibility("default"))) __attribute__((visibility("default")))
#else #else
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT #define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
#endif #endif
#endif #endif
#else // defined(COMPONENT_BUILD) #else // defined(COMPONENT_BUILD)
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT #define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
#endif #endif
#endif // SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_RESOURCE_COORDINATOR_EXPORT_H_ #endif // SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_MEMORY_EXPORT_H_
...@@ -8,13 +8,13 @@ ...@@ -8,13 +8,13 @@
#include "base/process/process_handle.h" #include "base/process/process_handle.h"
#include "base/trace_event/memory_dump_request_args.h" #include "base/trace_event/memory_dump_request_args.h"
#include "mojo/common/common_custom_types_struct_traits.h" #include "mojo/common/common_custom_types_struct_traits.h"
#include "services/resource_coordinator/public/cpp/resource_coordinator_export.h" #include "services/resource_coordinator/public/cpp/memory/memory_export.h"
#include "services/resource_coordinator/public/interfaces/memory/memory_instrumentation.mojom.h" #include "services/resource_coordinator/public/interfaces/memory/memory_instrumentation.mojom.h"
namespace mojo { namespace mojo {
template <> template <>
struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
EnumTraits<memory_instrumentation::mojom::DumpType, EnumTraits<memory_instrumentation::mojom::DumpType,
base::trace_event::MemoryDumpType> { base::trace_event::MemoryDumpType> {
static memory_instrumentation::mojom::DumpType ToMojom( static memory_instrumentation::mojom::DumpType ToMojom(
...@@ -24,7 +24,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT ...@@ -24,7 +24,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT
}; };
template <> template <>
struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
EnumTraits<memory_instrumentation::mojom::LevelOfDetail, EnumTraits<memory_instrumentation::mojom::LevelOfDetail,
base::trace_event::MemoryDumpLevelOfDetail> { base::trace_event::MemoryDumpLevelOfDetail> {
static memory_instrumentation::mojom::LevelOfDetail ToMojom( static memory_instrumentation::mojom::LevelOfDetail ToMojom(
...@@ -34,7 +34,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT ...@@ -34,7 +34,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT
}; };
template <> template <>
struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
StructTraits<memory_instrumentation::mojom::RequestArgsDataView, StructTraits<memory_instrumentation::mojom::RequestArgsDataView,
base::trace_event::MemoryDumpRequestArgs> { base::trace_event::MemoryDumpRequestArgs> {
static uint64_t dump_guid( static uint64_t dump_guid(
...@@ -54,7 +54,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT ...@@ -54,7 +54,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT
}; };
template <> template <>
struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
StructTraits<memory_instrumentation::mojom::ChromeMemDumpDataView, StructTraits<memory_instrumentation::mojom::ChromeMemDumpDataView,
base::trace_event::MemoryDumpCallbackResult::ChromeMemDump> { base::trace_event::MemoryDumpCallbackResult::ChromeMemDump> {
static uint32_t malloc_total_kb( static uint32_t malloc_total_kb(
...@@ -79,7 +79,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT ...@@ -79,7 +79,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT
}; };
template <> template <>
struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
StructTraits<memory_instrumentation::mojom::OSMemDumpDataView, StructTraits<memory_instrumentation::mojom::OSMemDumpDataView,
base::trace_event::MemoryDumpCallbackResult::OSMemDump> { base::trace_event::MemoryDumpCallbackResult::OSMemDump> {
static uint32_t resident_set_kb( static uint32_t resident_set_kb(
...@@ -91,7 +91,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT ...@@ -91,7 +91,7 @@ struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT
}; };
template <> template <>
struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT StructTraits< struct SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT StructTraits<
memory_instrumentation::mojom::MemoryDumpCallbackResultDataView, memory_instrumentation::mojom::MemoryDumpCallbackResultDataView,
base::trace_event::MemoryDumpCallbackResult> { base::trace_event::MemoryDumpCallbackResult> {
static base::trace_event::MemoryDumpCallbackResult::OSMemDump os_dump( static base::trace_event::MemoryDumpCallbackResult::OSMemDump os_dump(
......
...@@ -12,7 +12,7 @@ ...@@ -12,7 +12,7 @@
#include "base/trace_event/memory_dump_request_args.h" #include "base/trace_event/memory_dump_request_args.h"
#include "mojo/public/cpp/bindings/binding.h" #include "mojo/public/cpp/bindings/binding.h"
#include "services/resource_coordinator/public/cpp/memory/coordinator.h" #include "services/resource_coordinator/public/cpp/memory/coordinator.h"
#include "services/resource_coordinator/public/cpp/resource_coordinator_export.h" #include "services/resource_coordinator/public/cpp/memory/memory_export.h"
#include "services/resource_coordinator/public/interfaces/memory/memory_instrumentation.mojom.h" #include "services/resource_coordinator/public/interfaces/memory/memory_instrumentation.mojom.h"
#include "services/service_manager/public/cpp/connector.h" #include "services/service_manager/public/cpp/connector.h"
...@@ -26,11 +26,11 @@ namespace memory_instrumentation { ...@@ -26,11 +26,11 @@ namespace memory_instrumentation {
// no Coordinator service in child processes. So, in a child process, the // no Coordinator service in child processes. So, in a child process, the
// local dump manager remotely connects to the Coordinator service. In the // local dump manager remotely connects to the Coordinator service. In the
// browser process, it locally connects to the Coordinator service. // browser process, it locally connects to the Coordinator service.
class SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT class SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT
ProcessLocalDumpManagerImpl ProcessLocalDumpManagerImpl
: public NON_EXPORTED_BASE(mojom::ProcessLocalDumpManager) { : public NON_EXPORTED_BASE(mojom::ProcessLocalDumpManager) {
public: public:
class SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT Config { class SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT Config {
public: public:
Config(service_manager::Connector* connector, Config(service_manager::Connector* connector,
const std::string& service_name) const std::string& service_name)
......
// Copyright 2017 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 "services/resource_coordinator/public/cpp/resource_coordinator_interface.h"
#include "mojo/public/cpp/bindings/binding.h"
#include "services/resource_coordinator/public/interfaces/coordination_unit_provider.mojom.h"
#include "services/resource_coordinator/public/interfaces/service_constants.mojom.h"
#include "services/service_manager/public/cpp/connector.h"
namespace {
void OnConnectionError() {
DCHECK(false);
}
} // namespace
namespace resource_coordinator {
ResourceCoordinatorInterface::ResourceCoordinatorInterface(
service_manager::Connector* connector,
const CoordinationUnitType& type)
: weak_ptr_factory_(this) {
ConnectToService(connector, type, std::string());
}
ResourceCoordinatorInterface::ResourceCoordinatorInterface(
service_manager::Connector* connector,
const CoordinationUnitType& type,
const std::string& id)
: weak_ptr_factory_(this) {
ConnectToService(connector, type, id);
}
ResourceCoordinatorInterface::~ResourceCoordinatorInterface() = default;
void ResourceCoordinatorInterface::ConnectToService(
service_manager::Connector* connector,
const CoordinationUnitType& type,
const std::string& id) {
DCHECK(thread_checker_.CalledOnValidThread());
DCHECK(connector);
mojom::CoordinationUnitProviderPtr provider;
connector->BindInterface(mojom::kServiceName, mojo::MakeRequest(&provider));
CoordinationUnitID new_cu_id(type, id);
provider->CreateCoordinationUnit(mojo::MakeRequest(&service_), new_cu_id);
service_.set_connection_error_handler(base::Bind(&OnConnectionError));
}
void ResourceCoordinatorInterface::SendEvent(
const mojom::EventType& event_type) {
DCHECK(thread_checker_.CalledOnValidThread());
mojom::EventPtr event = mojom::Event::New();
event->type = event_type;
service_->SendEvent(std::move(event));
}
void ResourceCoordinatorInterface::AddChild(
const ResourceCoordinatorInterface& child) {
DCHECK(thread_checker_.CalledOnValidThread());
DCHECK(service_);
// We could keep the ID around ourselves, but this hop ensures that the child
// has been created on the service-side.
child.service()->GetID(base::Bind(&ResourceCoordinatorInterface::AddChildByID,
weak_ptr_factory_.GetWeakPtr()));
}
void ResourceCoordinatorInterface::AddChildByID(
const CoordinationUnitID& child_id) {
DCHECK(thread_checker_.CalledOnValidThread());
service_->AddChild(child_id);
}
} // namespace resource_coordinator
// Copyright 2017 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 SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_RESOURCE_COORDINATOR_INTERFACE_H_
#define SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_RESOURCE_COORDINATOR_INTERFACE_H_
#include <stdint.h>
#include "base/macros.h"
#include "base/memory/weak_ptr.h"
#include "base/threading/thread_checker.h"
#include "services/resource_coordinator/public/interfaces/coordination_unit.mojom.h"
namespace service_manager {
class Connector;
}
namespace resource_coordinator {
using EventType = mojom::EventType;
class ResourceCoordinatorInterface {
public:
ResourceCoordinatorInterface(service_manager::Connector* connector,
const CoordinationUnitType& type);
ResourceCoordinatorInterface(service_manager::Connector* connector,
const CoordinationUnitType& type,
const std::string& id);
~ResourceCoordinatorInterface();
const mojom::CoordinationUnitPtr& service() const { return service_; }
void SendEvent(const mojom::EventType& event_type);
void AddChild(const ResourceCoordinatorInterface& child);
private:
void ConnectToService(service_manager::Connector* connector,
const CoordinationUnitType& type,
const std::string& id);
void AddChildByID(const CoordinationUnitID& child_id);
mojom::CoordinationUnitPtr service_;
base::ThreadChecker thread_checker_;
// The WeakPtrFactory should come last so the weak ptrs are invalidated
// before the rest of the member variables.
base::WeakPtrFactory<ResourceCoordinatorInterface> weak_ptr_factory_;
DISALLOW_COPY_AND_ASSIGN(ResourceCoordinatorInterface);
};
} // namespace resource_coordinator
#endif // SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_RESOURCE_COORDINATOR_INTERFACE_H_
...@@ -2,7 +2,4 @@ ...@@ -2,7 +2,4 @@
# Use of this source code is governed by a BSD-style license that can be # Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file. # found in the LICENSE file.
typemaps = [ typemaps = [ "//services/resource_coordinator/public/cpp/memory/memory_instrumentation.typemap" ]
"//services/resource_coordinator/public/cpp/memory/memory_instrumentation.typemap",
"//services/resource_coordinator/public/cpp/coordination_unit.typemap",
]
...@@ -8,12 +8,8 @@ mojom("interfaces_internal") { ...@@ -8,12 +8,8 @@ mojom("interfaces_internal") {
visibility = [ "//services/resource_coordinator/public/cpp:*" ] visibility = [ "//services/resource_coordinator/public/cpp:*" ]
sources = [ sources = [
"coordination_unit.mojom",
"coordination_unit_provider.mojom",
"events.mojom",
"memory/constants.mojom", "memory/constants.mojom",
"memory/memory_instrumentation.mojom", "memory/memory_instrumentation.mojom",
"service_constants.mojom",
"tracing/tracing.mojom", "tracing/tracing.mojom",
] ]
...@@ -21,8 +17,10 @@ mojom("interfaces_internal") { ...@@ -21,8 +17,10 @@ mojom("interfaces_internal") {
"//mojo/common:common_custom_types", "//mojo/common:common_custom_types",
] ]
export_class_attribute = "SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_EXPORT" export_class_attribute =
export_define = "SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_IMPLEMENTATION=1" "SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_EXPORT"
export_define =
"SERVICES_RESOURCE_COORDINATOR_PUBLIC_CPP_MEMORY_IMPLEMENTATION=1"
export_header = export_header =
"services/resource_coordinator/public/cpp/resource_coordinator_export.h" "services/resource_coordinator/public/cpp/memory/memory_export.h"
} }
// Copyright 2017 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.
module resource_coordinator.mojom;
import "events.mojom";
// Any new type here needs to be mirrored between coordination_unit_types.h and
// coordination_unit.mojom, and have mappings between the two defined in
// coordination_unit_struct_traits.h/.cc (see comment in coordination_unit_id.h).
enum CoordinationUnitType {
kWebContents,
kFrame,
kNavigation,
kProcess,
};
struct CoordinationUnitID {
CoordinationUnitType type;
int64 id;
};
struct CoordinationPolicy {
bool use_background_priority;
};
interface CoordinationPolicyCallback {
SetCoordinationPolicy(CoordinationPolicy policy);
};
interface CoordinationUnit {
SendEvent(Event event);
// Mainly used to force a round-trip to the service over the pipe for
// a specific unit, so we don't have to deal with possibly-not-yet-created
// children in AddChild()
GetID() => (CoordinationUnitID id);
Duplicate(CoordinationUnit& request);
// child_id must represent a CU which already exists service-side,
// and can't be a direct ascendent or descendent of the current unit.
AddChild(CoordinationUnitID child_id);
SetCoordinationPolicyCallback(CoordinationPolicyCallback callback);
};
// Copyright 2017 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.
module resource_coordinator.mojom;
import "coordination_unit.mojom";
interface CoordinationUnitProvider {
CreateCoordinationUnit(CoordinationUnit& request, CoordinationUnitID id);
};
// Copyright 2017 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.
module resource_coordinator.mojom;
enum EventType {
kTestEvent,
kOnNavigationCommit,
kOnWebContentsShown,
kOnWebContentsHidden,
kOnRendererFrameCreated,
kOnProcessAudioStarted,
kOnProcessAudioStopped,
};
struct Event {
EventType type;
};
// Copyright 2017 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.
module resource_coordinator.mojom;
const string kServiceName = "resource_coordinator";
// Copyright 2017 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 "services/resource_coordinator/resource_coordinator_service.h"
#include "base/macros.h"
#include "services/resource_coordinator/coordination_unit/coordination_unit_provider_impl.h"
#include "services/service_manager/public/cpp/service_context.h"
namespace resource_coordinator {
std::unique_ptr<service_manager::Service> ResourceCoordinatorService::Create() {
return base::MakeUnique<ResourceCoordinatorService>();
}
ResourceCoordinatorService::ResourceCoordinatorService()
: weak_factory_(this) {}
ResourceCoordinatorService::~ResourceCoordinatorService() = default;
void ResourceCoordinatorService::OnStart() {
ref_factory_.reset(new service_manager::ServiceContextRefFactory(
base::Bind(&service_manager::ServiceContext::RequestQuit,
base::Unretained(context()))));
registry_.AddInterface(base::Bind(&CoordinationUnitProviderImpl::Create,
base::Unretained(ref_factory_.get())));
}
void ResourceCoordinatorService::OnBindInterface(
const service_manager::ServiceInfo& source_info,
const std::string& interface_name,
mojo::ScopedMessagePipeHandle interface_pipe) {
registry_.BindInterface(source_info.identity, interface_name,
std::move(interface_pipe));
}
} // namespace speed
// Copyright 2017 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 SERVICES_SPEED_SPEED_SERVICE_H_
#define SERVICES_SPEED_SPEED_SERVICE_H_
#include <memory>
#include "base/callback.h"
#include "base/macros.h"
#include "base/memory/weak_ptr.h"
#include "services/service_manager/public/cpp/binder_registry.h"
#include "services/service_manager/public/cpp/service.h"
#include "services/service_manager/public/cpp/service_context_ref.h"
namespace resource_coordinator {
class ResourceCoordinatorService : public service_manager::Service {
public:
ResourceCoordinatorService();
~ResourceCoordinatorService() override;
// service_manager::Service:
// Factory function for use as an embedded service.
static std::unique_ptr<service_manager::Service> Create();
// service_manager::Service:
void OnStart() override;
void OnBindInterface(const service_manager::ServiceInfo& source_info,
const std::string& interface_name,
mojo::ScopedMessagePipeHandle interface_pipe) override;
private:
service_manager::BinderRegistry registry_;
std::unique_ptr<service_manager::ServiceContextRefFactory> ref_factory_;
// WeakPtrFactory members should always come last so WeakPtrs are destructed
// before other members.
base::WeakPtrFactory<ResourceCoordinatorService> weak_factory_;
DISALLOW_COPY_AND_ASSIGN(ResourceCoordinatorService);
};
} // namespace resource_coordinator
#endif // SERVICES_SPEED_SPEED_SERVICE_H_
// Copyright 2015 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 <memory>
#include "base/macros.h"
#include "base/run_loop.h"
#include "mojo/public/cpp/bindings/binding.h"
#include "services/resource_coordinator/public/interfaces/coordination_unit_provider.mojom.h"
#include "services/resource_coordinator/public/interfaces/service_constants.mojom.h"
#include "services/service_manager/public/cpp/service.h"
#include "services/service_manager/public/cpp/service_test.h"
namespace resource_coordinator {
class ResourceCoordinatorTest : public service_manager::test::ServiceTest,
public mojom::CoordinationPolicyCallback {
public:
ResourceCoordinatorTest()
: service_manager::test::ServiceTest("resource_coordinator_unittests"),
binding_(this) {}
~ResourceCoordinatorTest() override {}
protected:
void SetUp() override {
service_manager::test::ServiceTest::SetUp();
connector()->StartService(mojom::kServiceName);
}
mojom::CoordinationPolicyCallbackPtr GetPolicyCallback() {
return binding_.CreateInterfacePtrAndBind();
}
void QuitOnPolicyCallback(base::RunLoop* loop) { loop_ = loop; }
private:
// mojom::CoordinationPolicyCallback:
void SetCoordinationPolicy(
resource_coordinator::mojom::CoordinationPolicyPtr policy) override {
loop_->Quit();
}
mojo::Binding<mojom::CoordinationPolicyCallback> binding_;
base::RunLoop* loop_ = nullptr;
DISALLOW_COPY_AND_ASSIGN(ResourceCoordinatorTest);
};
TEST_F(ResourceCoordinatorTest, ResourceCoordinatorInstantiate) {
mojom::CoordinationUnitProviderPtr provider;
connector()->BindInterface(mojom::kServiceName, mojo::MakeRequest(&provider));
CoordinationUnitID new_id(CoordinationUnitType::kWebContents, "test_id");
mojom::CoordinationUnitPtr coordination_unit;
provider->CreateCoordinationUnit(mojo::MakeRequest(&coordination_unit),
new_id);
coordination_unit->SetCoordinationPolicyCallback(GetPolicyCallback());
base::RunLoop loop;
QuitOnPolicyCallback(&loop);
loop.Run();
}
} // namespace resource_coordinator
// Copyright 2017 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 "services/resource_coordinator/resource_coordinator_service.h"
#include "services/service_manager/public/c/main.h"
#include "services/service_manager/public/cpp/service_runner.h"
MojoResult ServiceMain(MojoHandle service_request_handle) {
return service_manager::ServiceRunner(
new resource_coordinator::ResourceCoordinatorService())
.Run(service_request_handle);
}
{
"name": "resource_coordinator_unittests",
"display_name": "Resource Coordinator Unittests",
"interface_provider_specs": {
"service_manager:connector": {
"requires": {
"resource_coordinator": [ "tests" ]
}
}
}
}
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