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

Side by Side Diff: services/service_manager/tests/connect/connect_test_package.cc

Issue 2480603004: Service Manager: Implement graceful service termination (Closed)
Patch Set: Created 4 years, 1 month 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 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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 <stddef.h> 5 #include <stddef.h>
6 #include <stdint.h> 6 #include <stdint.h>
7 7
8 #include <memory> 8 #include <memory>
9 #include <utility> 9 #include <utility>
10 10
(...skipping 12 matching lines...) Expand all
23 #include "services/service_manager/public/cpp/service_runner.h" 23 #include "services/service_manager/public/cpp/service_runner.h"
24 #include "services/service_manager/public/interfaces/service_factory.mojom.h" 24 #include "services/service_manager/public/interfaces/service_factory.mojom.h"
25 #include "services/service_manager/tests/connect/connect_test.mojom.h" 25 #include "services/service_manager/tests/connect/connect_test.mojom.h"
26 26
27 // Tests that multiple services can be packaged in a single service by 27 // Tests that multiple services can be packaged in a single service by
28 // implementing ServiceFactory; that these services can be specified by 28 // implementing ServiceFactory; that these services can be specified by
29 // the package's manifest and are thus registered with the PackageManager. 29 // the package's manifest and are thus registered with the PackageManager.
30 30
31 namespace service_manager { 31 namespace service_manager {
32 32
33 namespace {
34
35 void QuitLoop(base::RunLoop* loop) {
36 loop->Quit();
37 }
38
39 } // namespace
40
41 using GetTitleCallback = test::mojom::ConnectTestService::GetTitleCallback; 33 using GetTitleCallback = test::mojom::ConnectTestService::GetTitleCallback;
42 34
43 class ProvidedService 35 class ProvidedService
44 : public Service, 36 : public Service,
45 public InterfaceFactory<test::mojom::ConnectTestService>, 37 public InterfaceFactory<test::mojom::ConnectTestService>,
46 public InterfaceFactory<test::mojom::BlockedInterface>, 38 public InterfaceFactory<test::mojom::BlockedInterface>,
47 public InterfaceFactory<test::mojom::UserIdTest>, 39 public InterfaceFactory<test::mojom::UserIdTest>,
48 public test::mojom::ConnectTestService, 40 public test::mojom::ConnectTestService,
49 public test::mojom::BlockedInterface, 41 public test::mojom::BlockedInterface,
50 public test::mojom::UserIdTest, 42 public test::mojom::UserIdTest,
51 public base::SimpleThread { 43 public base::SimpleThread {
52 public: 44 public:
53 ProvidedService(const std::string& title, mojom::ServiceRequest request) 45 ProvidedService(const std::string& title, mojom::ServiceRequest request)
54 : base::SimpleThread(title), 46 : base::SimpleThread(title),
55 title_(title), 47 title_(title),
56 request_(std::move(request)) { 48 request_(std::move(request)) {
57 Start(); 49 Start();
58 } 50 }
51
59 ~ProvidedService() override { 52 ~ProvidedService() override {
60 Join(); 53 Join();
61 } 54 }
62 55
63 private: 56 private:
57 class ForwardingServiceImpl : public Service {
58 public:
59 explicit ForwardingServiceImpl(Service* service)
60 : service_(service) {}
61 ~ForwardingServiceImpl() override {}
62
63 // Service:
64 void OnStart(ServiceContext* context) override {
65 service_->OnStart(context);
66 }
67
68 bool OnConnect(const ServiceInfo& remote_info,
69 InterfaceRegistry* registry) override {
70 return service_->OnConnect(remote_info, registry);
71 }
72
73 bool OnStop() override { return service_->OnStop(); }
74
75 private:
76 Service* const service_;
77
78 DISALLOW_COPY_AND_ASSIGN(ForwardingServiceImpl);
79 };
80
64 // service_manager::Service: 81 // service_manager::Service:
65 void OnStart(ServiceContext* context) override { 82 void OnStart(ServiceContext* context) override {
66 context_ = context; 83 context_ = context;
67 bindings_.set_connection_error_handler( 84 bindings_.set_connection_error_handler(
68 base::Bind(&ProvidedService::OnConnectionError, 85 base::Bind(&ProvidedService::OnConnectionError,
69 base::Unretained(this))); 86 base::Unretained(this)));
70 } 87 }
71 88
72 bool OnConnect(const ServiceInfo& remote_info, 89 bool OnConnect(const ServiceInfo& remote_info,
73 InterfaceRegistry* registry) override { 90 InterfaceRegistry* registry) override {
(...skipping 28 matching lines...) Expand all
102 // InterfaceFactory<test::mojom::UserIdTest>: 119 // InterfaceFactory<test::mojom::UserIdTest>:
103 void Create(const Identity& remote_identity, 120 void Create(const Identity& remote_identity,
104 test::mojom::UserIdTestRequest request) override { 121 test::mojom::UserIdTestRequest request) override {
105 user_id_test_bindings_.AddBinding(this, std::move(request)); 122 user_id_test_bindings_.AddBinding(this, std::move(request));
106 } 123 }
107 124
108 // test::mojom::ConnectTestService: 125 // test::mojom::ConnectTestService:
109 void GetTitle(const GetTitleCallback& callback) override { 126 void GetTitle(const GetTitleCallback& callback) override {
110 callback.Run(title_); 127 callback.Run(title_);
111 } 128 }
129
112 void GetInstance(const GetInstanceCallback& callback) override { 130 void GetInstance(const GetInstanceCallback& callback) override {
113 callback.Run(context_->identity().instance()); 131 callback.Run(context_->identity().instance());
114 } 132 }
115 133
116 // test::mojom::BlockedInterface: 134 // test::mojom::BlockedInterface:
117 void GetTitleBlocked(const GetTitleBlockedCallback& callback) override { 135 void GetTitleBlocked(const GetTitleBlockedCallback& callback) override {
118 callback.Run("Called Blocked Interface!"); 136 callback.Run("Called Blocked Interface!");
119 } 137 }
120 138
121 // test::mojom::UserIdTest: 139 // test::mojom::UserIdTest:
122 void ConnectToClassAppAsDifferentUser( 140 void ConnectToClassAppAsDifferentUser(
123 const service_manager::Identity& target, 141 const service_manager::Identity& target,
124 const ConnectToClassAppAsDifferentUserCallback& callback) override { 142 const ConnectToClassAppAsDifferentUserCallback& callback) override {
125 Connector::ConnectParams params(target); 143 Connector::ConnectParams params(target);
126 std::unique_ptr<Connection> connection = 144 std::unique_ptr<Connection> connection =
127 context_->connector()->Connect(&params); 145 context_->connector()->Connect(&params);
128 { 146 {
129 base::RunLoop loop; 147 base::RunLoop loop;
130 connection->AddConnectionCompletedClosure(base::Bind(&QuitLoop, &loop)); 148 connection->AddConnectionCompletedClosure(loop.QuitClosure());
131 base::MessageLoop::ScopedNestableTaskAllower allow( 149 base::MessageLoop::ScopedNestableTaskAllower allow(
132 base::MessageLoop::current()); 150 base::MessageLoop::current());
133 loop.Run(); 151 loop.Run();
134 } 152 }
135 callback.Run(static_cast<int32_t>(connection->GetResult()), 153 callback.Run(static_cast<int32_t>(connection->GetResult()),
136 connection->GetRemoteIdentity()); 154 connection->GetRemoteIdentity());
137 } 155 }
138 156
139 // base::SimpleThread: 157 // base::SimpleThread:
140 void Run() override { 158 void Run() override {
141 ServiceRunner(this).Run(request_.PassMessagePipe().release().value(), 159 ServiceRunner(new ForwardingServiceImpl(this)).Run(
142 false); 160 request_.PassMessagePipe().release().value(), false);
143 delete this; 161 caller_.reset();
162 bindings_.CloseAllBindings();
163 blocked_bindings_.CloseAllBindings();
164 user_id_test_bindings_.CloseAllBindings();
144 } 165 }
145 166
146 void OnConnectionError() { 167 void OnConnectionError() {
147 if (bindings_.empty()) 168 if (bindings_.empty())
148 base::MessageLoop::current()->QuitWhenIdle(); 169 base::MessageLoop::current()->QuitWhenIdle();
149 } 170 }
150 171
151 ServiceContext* context_ = nullptr; 172 ServiceContext* context_ = nullptr;
152 const std::string title_; 173 const std::string title_;
153 mojom::ServiceRequest request_; 174 mojom::ServiceRequest request_;
(...skipping 11 matching lines...) Expand all
165 public InterfaceFactory<test::mojom::ConnectTestService>, 186 public InterfaceFactory<test::mojom::ConnectTestService>,
166 public mojom::ServiceFactory, 187 public mojom::ServiceFactory,
167 public test::mojom::ConnectTestService { 188 public test::mojom::ConnectTestService {
168 public: 189 public:
169 ConnectTestService() {} 190 ConnectTestService() {}
170 ~ConnectTestService() override {} 191 ~ConnectTestService() override {}
171 192
172 private: 193 private:
173 // service_manager::Service: 194 // service_manager::Service:
174 void OnStart(ServiceContext* context) override { 195 void OnStart(ServiceContext* context) override {
175 identity_ = context->identity(); 196 context_ = context;
176 bindings_.set_connection_error_handler( 197
198 base::Closure error_handler =
177 base::Bind(&ConnectTestService::OnConnectionError, 199 base::Bind(&ConnectTestService::OnConnectionError,
178 base::Unretained(this))); 200 base::Unretained(this));
201 bindings_.set_connection_error_handler(error_handler);
202 service_factory_bindings_.set_connection_error_handler(error_handler);
179 } 203 }
204
180 bool OnConnect(const ServiceInfo& remote_info, 205 bool OnConnect(const ServiceInfo& remote_info,
181 InterfaceRegistry* registry) override { 206 InterfaceRegistry* registry) override {
182 registry->AddInterface<ServiceFactory>(this); 207 registry->AddInterface<ServiceFactory>(this);
183 registry->AddInterface<test::mojom::ConnectTestService>(this); 208 registry->AddInterface<test::mojom::ConnectTestService>(this);
184 return true; 209 return true;
185 } 210 }
186 211
212 bool OnStop() override {
213 provided_services_.clear();
214 return true;
215 }
216
187 // InterfaceFactory<mojom::ServiceFactory>: 217 // InterfaceFactory<mojom::ServiceFactory>:
188 void Create(const Identity& remote_identity, 218 void Create(const Identity& remote_identity,
189 mojom::ServiceFactoryRequest request) override { 219 mojom::ServiceFactoryRequest request) override {
190 service_factory_bindings_.AddBinding(this, std::move(request)); 220 service_factory_bindings_.AddBinding(this, std::move(request));
191 } 221 }
192 222
193 // InterfaceFactory<test::mojom::ConnectTestService>: 223 // InterfaceFactory<test::mojom::ConnectTestService>:
194 void Create(const Identity& remote_identity, 224 void Create(const Identity& remote_identity,
195 test::mojom::ConnectTestServiceRequest request) override { 225 test::mojom::ConnectTestServiceRequest request) override {
196 bindings_.AddBinding(this, std::move(request)); 226 bindings_.AddBinding(this, std::move(request));
197 } 227 }
198 228
199 // mojom::ServiceFactory: 229 // mojom::ServiceFactory:
200 void CreateService(mojom::ServiceRequest request, 230 void CreateService(mojom::ServiceRequest request,
201 const std::string& name) override { 231 const std::string& name) override {
202 if (name == "service:connect_test_a") 232 if (name == "service:connect_test_a") {
203 new ProvidedService("A", std::move(request)); 233 provided_services_.emplace_back(
204 else if (name == "service:connect_test_b") 234 base::MakeUnique<ProvidedService>("A", std::move(request)));
205 new ProvidedService("B", std::move(request)); 235 } else if (name == "service:connect_test_b") {
236 provided_services_.emplace_back(
237 base::MakeUnique<ProvidedService>("B", std::move(request)));
238 }
206 } 239 }
207 240
208 // test::mojom::ConnectTestService: 241 // test::mojom::ConnectTestService:
209 void GetTitle(const GetTitleCallback& callback) override { 242 void GetTitle(const GetTitleCallback& callback) override {
210 callback.Run("ROOT"); 243 callback.Run("ROOT");
211 } 244 }
245
212 void GetInstance(const GetInstanceCallback& callback) override { 246 void GetInstance(const GetInstanceCallback& callback) override {
213 callback.Run(identity_.instance()); 247 callback.Run(context_->identity().instance());
214 } 248 }
215 249
216 void OnConnectionError() { 250 void OnConnectionError() {
217 if (bindings_.empty()) 251 if (bindings_.empty() && service_factory_bindings_.empty())
218 base::MessageLoop::current()->QuitWhenIdle(); 252 context_->RequestQuit();
219 } 253 }
220 254
221 Identity identity_; 255 ServiceContext* context_ = nullptr;
222 std::vector<std::unique_ptr<Service>> delegates_; 256 std::vector<std::unique_ptr<Service>> delegates_;
223 mojo::BindingSet<mojom::ServiceFactory> service_factory_bindings_; 257 mojo::BindingSet<mojom::ServiceFactory> service_factory_bindings_;
224 mojo::BindingSet<test::mojom::ConnectTestService> bindings_; 258 mojo::BindingSet<test::mojom::ConnectTestService> bindings_;
259 std::list<std::unique_ptr<ProvidedService>> provided_services_;
225 260
226 DISALLOW_COPY_AND_ASSIGN(ConnectTestService); 261 DISALLOW_COPY_AND_ASSIGN(ConnectTestService);
227 }; 262 };
228 263
229 } // namespace service_manager 264 } // namespace service_manager
230 265
231 MojoResult ServiceMain(MojoHandle service_request_handle) { 266 MojoResult ServiceMain(MojoHandle service_request_handle) {
232 service_manager::ServiceRunner runner( 267 service_manager::ServiceRunner runner(
233 new service_manager::ConnectTestService); 268 new service_manager::ConnectTestService);
234 return runner.Run(service_request_handle); 269 return runner.Run(service_request_handle);
235 } 270 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698