blob: 5951f0c140aee61578074e251a1739ab3107d7aa [file] [log] [blame]
[email protected]64860882014-08-04 23:44:171// Copyright 2014 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
amistryd4aa70d2016-06-23 07:52:375#include "ipc/ipc_channel_mojo.h"
[email protected]64860882014-08-04 23:44:176
avi246998d82015-12-22 02:39:047#include <stddef.h>
tfarina10a5c062015-09-04 18:47:578#include <stdint.h>
rockot7c6bf952016-07-14 00:34:119
danakj03de39b22016-04-23 04:21:0910#include <memory>
dchenge48600452015-12-28 02:24:5011#include <utility>
tfarina10a5c062015-09-04 18:47:5712
[email protected]64860882014-08-04 23:44:1713#include "base/base_paths.h"
rockot8d890f62016-07-14 16:37:1414#include "base/bind.h"
Ken Rockot942af102020-06-04 05:48:4615#include "base/bind_helpers.h"
sammc5c8a6c62017-02-04 01:33:3816#include "base/callback_helpers.h"
Brett Wilsona62d9c02017-09-20 20:53:2017#include "base/containers/queue.h"
[email protected]64860882014-08-04 23:44:1718#include "base/files/file.h"
amistry20e2b1d62016-06-23 06:12:3519#include "base/files/scoped_temp_dir.h"
skyostile687bdff2015-05-12 11:29:2120#include "base/location.h"
rockot8d890f62016-07-14 16:37:1421#include "base/macros.h"
Alexandr Ilind497eee2018-04-19 22:50:5422#include "base/memory/platform_shared_memory_region.h"
Alex Ilinf2c7fa232019-11-20 14:09:5823#include "base/memory/read_only_shared_memory_region.h"
Alexandr Ilind497eee2018-04-19 22:50:5424#include "base/memory/shared_memory_mapping.h"
Alex Ilinf2c7fa232019-11-20 14:09:5825#include "base/memory/unsafe_shared_memory_region.h"
26#include "base/memory/writable_shared_memory_region.h"
Carlos Caballerodd8bf7b042019-07-30 14:14:1527#include "base/message_loop/message_pump_type.h"
Ken Rockot138153b2018-07-13 23:31:5728#include "base/optional.h"
[email protected]64860882014-08-04 23:44:1729#include "base/path_service.h"
30#include "base/pickle.h"
rockotcbca72f2015-03-03 16:31:0431#include "base/run_loop.h"
skyostile687bdff2015-05-12 11:29:2132#include "base/single_thread_task_runner.h"
rockot7c6bf952016-07-14 00:34:1133#include "base/strings/stringprintf.h"
rockot9abe09b2016-08-02 20:57:3434#include "base/synchronization/waitable_event.h"
Guido Urdanetaef4e91942020-11-09 15:06:2435#include "base/test/bind.h"
Gabriel Charettec7108742019-08-23 03:31:4036#include "base/test/task_environment.h"
sammc57ed9f982016-03-10 06:28:3537#include "base/test/test_io_thread.h"
Alexandr Ilind497eee2018-04-19 22:50:5438#include "base/test/test_shared_memory_util.h"
morrita0bd20bd2015-02-25 20:11:2739#include "base/test/test_timeouts.h"
[email protected]64860882014-08-04 23:44:1740#include "base/threading/thread.h"
gabf08ccc02016-05-11 18:51:1141#include "base/threading/thread_task_runner_handle.h"
avi246998d82015-12-22 02:39:0442#include "build/build_config.h"
[email protected]64860882014-08-04 23:44:1743#include "ipc/ipc_message.h"
Wez831ae412017-08-30 00:29:3644#include "ipc/ipc_message_utils.h"
amistryd4aa70d2016-06-23 07:52:3745#include "ipc/ipc_mojo_handle_attachment.h"
46#include "ipc/ipc_mojo_message_helper.h"
47#include "ipc/ipc_mojo_param_traits.h"
rockot9abe09b2016-08-02 20:57:3448#include "ipc/ipc_sync_channel.h"
49#include "ipc/ipc_sync_message.h"
rockot7c6bf952016-07-14 00:34:1150#include "ipc/ipc_test.mojom.h"
[email protected]64860882014-08-04 23:44:1751#include "ipc/ipc_test_base.h"
52#include "ipc/ipc_test_channel_listener.h"
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:1553#include "mojo/public/cpp/bindings/associated_receiver.h"
54#include "mojo/public/cpp/bindings/associated_remote.h"
Ken Rockot138153b2018-07-13 23:31:5755#include "mojo/public/cpp/bindings/lib/validation_errors.h"
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:1556#include "mojo/public/cpp/bindings/pending_associated_receiver.h"
Ken Rockot942af102020-06-04 05:48:4657#include "mojo/public/cpp/system/functions.h"
rockota9d566a2017-03-17 19:36:1558#include "mojo/public/cpp/system/wait.h"
sammc57ed9f982016-03-10 06:28:3559#include "testing/gtest/include/gtest/gtest.h"
[email protected]64860882014-08-04 23:44:1760
Fabrice de Gans-Riberi894661c2018-05-24 18:43:2261#if defined(OS_POSIX) || defined(OS_FUCHSIA)
[email protected]64860882014-08-04 23:44:1762#include "base/file_descriptor_posix.h"
morrita1aa788c2015-01-31 05:45:4263#include "ipc/ipc_platform_file_attachment_posix.h"
[email protected]64860882014-08-04 23:44:1764#endif
65
66namespace {
67
rockot7c6bf952016-07-14 00:34:1168void SendString(IPC::Sender* sender, const std::string& str) {
69 IPC::Message* message = new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
70 message->WriteString(str);
71 ASSERT_TRUE(sender->Send(message));
72}
73
rockot9abe09b2016-08-02 20:57:3474void SendValue(IPC::Sender* sender, int32_t value) {
75 IPC::Message* message = new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
76 message->WriteInt(value);
77 ASSERT_TRUE(sender->Send(message));
78}
79
[email protected]64860882014-08-04 23:44:1780class ListenerThatExpectsOK : public IPC::Listener {
81 public:
Wezfdb98482018-07-12 01:21:3982 explicit ListenerThatExpectsOK(base::OnceClosure quit_closure)
83 : received_ok_(false), quit_closure_(std::move(quit_closure)) {}
[email protected]64860882014-08-04 23:44:1784
Chris Watkins2d879af2017-11-30 02:11:5985 ~ListenerThatExpectsOK() override = default;
[email protected]64860882014-08-04 23:44:1786
dchengfe61fca2014-10-22 02:29:5287 bool OnMessageReceived(const IPC::Message& message) override {
brettwbd4d7112015-06-03 04:29:2588 base::PickleIterator iter(message);
[email protected]64860882014-08-04 23:44:1789 std::string should_be_ok;
90 EXPECT_TRUE(iter.ReadString(&should_be_ok));
91 EXPECT_EQ(should_be_ok, "OK");
[email protected]e5c27752014-08-08 21:45:1392 received_ok_ = true;
Wezfdb98482018-07-12 01:21:3993 std::move(quit_closure_).Run();
[email protected]64860882014-08-04 23:44:1794 return true;
95 }
96
dchengfe61fca2014-10-22 02:29:5297 void OnChannelError() override {
[email protected]e5c27752014-08-08 21:45:1398 // The connection should be healthy while the listener is waiting
99 // message. An error can occur after that because the peer
100 // process dies.
Wezd95d48042018-02-26 20:50:47101 CHECK(received_ok_);
[email protected]64860882014-08-04 23:44:17102 }
103
rockot7c6bf952016-07-14 00:34:11104 static void SendOK(IPC::Sender* sender) { SendString(sender, "OK"); }
[email protected]e5c27752014-08-08 21:45:13105
106 private:
107 bool received_ok_;
Wezfdb98482018-07-12 01:21:39108 base::OnceClosure quit_closure_;
Wez831ae412017-08-30 00:29:36109};
110
111class TestListenerBase : public IPC::Listener {
112 public:
Wezfdb98482018-07-12 01:21:39113 explicit TestListenerBase(base::OnceClosure quit_closure)
114 : quit_closure_(std::move(quit_closure)) {}
Wez831ae412017-08-30 00:29:36115
Chris Watkins2d879af2017-11-30 02:11:59116 ~TestListenerBase() override = default;
Wezfdb98482018-07-12 01:21:39117 void OnChannelError() override { RunQuitClosure(); }
Wez831ae412017-08-30 00:29:36118
119 void set_sender(IPC::Sender* sender) { sender_ = sender; }
120 IPC::Sender* sender() const { return sender_; }
Ken Rockot138153b2018-07-13 23:31:57121 void RunQuitClosure() {
122 if (quit_closure_)
123 std::move(quit_closure_).Run();
124 }
Wez831ae412017-08-30 00:29:36125
126 private:
127 IPC::Sender* sender_ = nullptr;
Wezfdb98482018-07-12 01:21:39128 base::OnceClosure quit_closure_;
[email protected]64860882014-08-04 23:44:17129};
130
sammc4bcc4ed62016-10-27 10:13:59131using IPCChannelMojoTest = IPCChannelMojoTestBase;
rockotcbca72f2015-03-03 16:31:04132
[email protected]64860882014-08-04 23:44:17133class TestChannelListenerWithExtraExpectations
134 : public IPC::TestChannelListener {
135 public:
sammc57ed9f982016-03-10 06:28:35136 TestChannelListenerWithExtraExpectations() : is_connected_called_(false) {}
[email protected]64860882014-08-04 23:44:17137
tfarina10a5c062015-09-04 18:47:57138 void OnChannelConnected(int32_t peer_pid) override {
[email protected]64860882014-08-04 23:44:17139 IPC::TestChannelListener::OnChannelConnected(peer_pid);
140 EXPECT_TRUE(base::kNullProcessId != peer_pid);
141 is_connected_called_ = true;
142 }
143
144 bool is_connected_called() const { return is_connected_called_; }
145
146 private:
147 bool is_connected_called_;
148};
149
amistry0027a0952016-05-03 00:52:47150TEST_F(IPCChannelMojoTest, ConnectedFromClient) {
sammc4bcc4ed62016-10-27 10:13:59151 Init("IPCChannelMojoTestClient");
[email protected]64860882014-08-04 23:44:17152
153 // Set up IPC channel and start client.
154 TestChannelListenerWithExtraExpectations listener;
morrita373af03b2014-09-09 19:35:24155 CreateChannel(&listener);
[email protected]64860882014-08-04 23:44:17156 listener.Init(sender());
157 ASSERT_TRUE(ConnectChannel());
[email protected]64860882014-08-04 23:44:17158
sammc57ed9f982016-03-10 06:28:35159 IPC::TestChannelListener::SendOneMessage(sender(), "hello from parent");
[email protected]64860882014-08-04 23:44:17160
fdoray8e32586852016-06-22 19:56:16161 base::RunLoop().Run();
[email protected]64860882014-08-04 23:44:17162
sammc57ed9f982016-03-10 06:28:35163 channel()->Close();
[email protected]64860882014-08-04 23:44:17164
165 EXPECT_TRUE(WaitForClientShutdown());
166 EXPECT_TRUE(listener.is_connected_called());
167 EXPECT_TRUE(listener.HasSentAll());
168
169 DestroyChannel();
170}
171
172// A long running process that connects to us
sammc4bcc4ed62016-10-27 10:13:59173DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(IPCChannelMojoTestClient) {
[email protected]64860882014-08-04 23:44:17174 TestChannelListenerWithExtraExpectations listener;
sammc57ed9f982016-03-10 06:28:35175 Connect(&listener);
176 listener.Init(channel());
[email protected]64860882014-08-04 23:44:17177
sammc57ed9f982016-03-10 06:28:35178 IPC::TestChannelListener::SendOneMessage(channel(), "hello from child");
fdoray8e32586852016-06-22 19:56:16179 base::RunLoop().Run();
[email protected]64860882014-08-04 23:44:17180 EXPECT_TRUE(listener.is_connected_called());
181 EXPECT_TRUE(listener.HasSentAll());
182
sammc57ed9f982016-03-10 06:28:35183 Close();
[email protected]64860882014-08-04 23:44:17184}
185
Wez831ae412017-08-30 00:29:36186class ListenerExpectingErrors : public TestListenerBase {
morrita0a24cfc92014-09-16 03:20:48187 public:
Wezfdb98482018-07-12 01:21:39188 ListenerExpectingErrors(base::OnceClosure quit_closure)
189 : TestListenerBase(std::move(quit_closure)), has_error_(false) {}
morrita0a24cfc92014-09-16 03:20:48190
dchengfe61fca2014-10-22 02:29:52191 bool OnMessageReceived(const IPC::Message& message) override { return true; }
morrita0a24cfc92014-09-16 03:20:48192
dchengfe61fca2014-10-22 02:29:52193 void OnChannelError() override {
morrita0a24cfc92014-09-16 03:20:48194 has_error_ = true;
Wez831ae412017-08-30 00:29:36195 TestListenerBase::OnChannelError();
morrita0a24cfc92014-09-16 03:20:48196 }
197
198 bool has_error() const { return has_error_; }
199
200 private:
201 bool has_error_;
202};
203
morrita0a24cfc92014-09-16 03:20:48204class ListenerThatQuits : public IPC::Listener {
205 public:
Wezfdb98482018-07-12 01:21:39206 explicit ListenerThatQuits(base::OnceClosure quit_closure)
207 : quit_closure_(std::move(quit_closure)) {}
morrita0a24cfc92014-09-16 03:20:48208
sammc57ed9f982016-03-10 06:28:35209 bool OnMessageReceived(const IPC::Message& message) override { return true; }
morrita0a24cfc92014-09-16 03:20:48210
Wezfdb98482018-07-12 01:21:39211 void OnChannelConnected(int32_t peer_pid) override {
212 std::move(quit_closure_).Run();
213 }
Wez831ae412017-08-30 00:29:36214
215 private:
Wezfdb98482018-07-12 01:21:39216 base::OnceClosure quit_closure_;
morrita0a24cfc92014-09-16 03:20:48217};
218
219// A long running process that connects to us.
sammc4bcc4ed62016-10-27 10:13:59220DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(IPCChannelMojoErraticTestClient) {
Wez831ae412017-08-30 00:29:36221 base::RunLoop run_loop;
222 ListenerThatQuits listener(run_loop.QuitClosure());
sammc57ed9f982016-03-10 06:28:35223 Connect(&listener);
morrita0a24cfc92014-09-16 03:20:48224
Wez831ae412017-08-30 00:29:36225 run_loop.Run();
morrita0a24cfc92014-09-16 03:20:48226
sammc57ed9f982016-03-10 06:28:35227 Close();
morrita0a24cfc92014-09-16 03:20:48228}
229
rockot8c23d462016-07-25 17:33:04230TEST_F(IPCChannelMojoTest, SendFailWithPendingMessages) {
sammc4bcc4ed62016-10-27 10:13:59231 Init("IPCChannelMojoErraticTestClient");
morrita0a24cfc92014-09-16 03:20:48232
233 // Set up IPC channel and start client.
Wez831ae412017-08-30 00:29:36234 base::RunLoop run_loop;
235 ListenerExpectingErrors listener(run_loop.QuitClosure());
morrita0a24cfc92014-09-16 03:20:48236 CreateChannel(&listener);
237 ASSERT_TRUE(ConnectChannel());
238
jamesra03ae492014-10-03 04:26:48239 // This matches a value in mojo/edk/system/constants.h
morritabe6c4cc2014-09-24 23:38:44240 const int kMaxMessageNumBytes = 4 * 1024 * 1024;
241 std::string overly_large_data(kMaxMessageNumBytes, '*');
morrita0a24cfc92014-09-16 03:20:48242 // This messages are queued as pending.
morritabe6c4cc2014-09-24 23:38:44243 for (size_t i = 0; i < 10; ++i) {
sammc57ed9f982016-03-10 06:28:35244 IPC::TestChannelListener::SendOneMessage(sender(),
245 overly_large_data.c_str());
morrita0a24cfc92014-09-16 03:20:48246 }
247
Wez831ae412017-08-30 00:29:36248 run_loop.Run();
morrita0a24cfc92014-09-16 03:20:48249
sammc57ed9f982016-03-10 06:28:35250 channel()->Close();
morrita0a24cfc92014-09-16 03:20:48251
252 EXPECT_TRUE(WaitForClientShutdown());
253 EXPECT_TRUE(listener.has_error());
254
255 DestroyChannel();
256}
257
Ken Rockot138153b2018-07-13 23:31:57258class ListenerThatBindsATestStructPasser : public IPC::Listener,
259 public IPC::mojom::TestStructPasser {
260 public:
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:54261 ListenerThatBindsATestStructPasser() = default;
262 ~ListenerThatBindsATestStructPasser() override = default;
Ken Rockot138153b2018-07-13 23:31:57263
264 bool OnMessageReceived(const IPC::Message& message) override { return true; }
265
266 void OnChannelConnected(int32_t peer_pid) override {}
267
268 void OnChannelError() override { NOTREACHED(); }
269
270 void OnAssociatedInterfaceRequest(
271 const std::string& interface_name,
272 mojo::ScopedInterfaceEndpointHandle handle) override {
273 CHECK_EQ(interface_name, IPC::mojom::TestStructPasser::Name_);
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:54274 receiver_.Bind(
275 mojo::PendingAssociatedReceiver<IPC::mojom::TestStructPasser>(
276 std::move(handle)));
Ken Rockot138153b2018-07-13 23:31:57277 }
278
279 private:
280 // IPC::mojom::TestStructPasser:
281 void Pass(IPC::mojom::TestStructPtr) override { NOTREACHED(); }
282
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:54283 mojo::AssociatedReceiver<IPC::mojom::TestStructPasser> receiver_{this};
Ken Rockot138153b2018-07-13 23:31:57284};
285
286class ListenerThatExpectsNoError : public IPC::Listener {
287 public:
288 ListenerThatExpectsNoError(base::OnceClosure connect_closure,
289 base::OnceClosure quit_closure)
290 : connect_closure_(std::move(connect_closure)),
291 quit_closure_(std::move(quit_closure)) {}
292
293 bool OnMessageReceived(const IPC::Message& message) override {
294 base::PickleIterator iter(message);
295 std::string should_be_ok;
296 EXPECT_TRUE(iter.ReadString(&should_be_ok));
297 EXPECT_EQ(should_be_ok, "OK");
298 std::move(quit_closure_).Run();
299 return true;
300 }
301
302 void OnChannelConnected(int32_t peer_pid) override {
303 std::move(connect_closure_).Run();
304 }
305
306 void OnChannelError() override { NOTREACHED(); }
307
308 private:
309 base::OnceClosure connect_closure_;
310 base::OnceClosure quit_closure_;
311};
312
313DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(
314 IPCChannelMojoNoImplicitChanelClosureClient) {
315 base::RunLoop wait_to_connect_loop;
316 base::RunLoop wait_to_quit_loop;
317 ListenerThatExpectsNoError listener(wait_to_connect_loop.QuitClosure(),
318 wait_to_quit_loop.QuitClosure());
319 Connect(&listener);
320 wait_to_connect_loop.Run();
321
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:54322 mojo::AssociatedRemote<IPC::mojom::TestStructPasser> passer;
Ken Rockot138153b2018-07-13 23:31:57323 channel()->GetAssociatedInterfaceSupport()->GetRemoteAssociatedInterface(
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:54324 passer.BindNewEndpointAndPassReceiver());
Ken Rockot138153b2018-07-13 23:31:57325
326 // This avoids hitting DCHECKs in the serialization code meant to stop us from
327 // making such "mistakes" as the one we're about to make below.
328 mojo::internal::SerializationWarningObserverForTesting suppress_those_dchecks;
329
330 // Send an invalid message. The TestStruct argument is not allowed to be null.
331 // This will elicit a validation error in the parent process, but should not
332 // actually disconnect the channel.
333 passer->Pass(nullptr);
334
335 // Wait until the parent says it's OK to quit, so it has time to verify its
336 // expected behavior.
337 wait_to_quit_loop.Run();
338
339 Close();
340}
341
342TEST_F(IPCChannelMojoTest, NoImplicitChannelClosure) {
343 // Verifies that OnChannelError is not invoked due to conditions other than
344 // peer closure (e.g. a malformed inbound message). Instead we should always
345 // be able to handle validation errors via Mojo bad message reporting.
346
347 // NOTE: We can't create a RunLoop before Init() is called, but we have to set
348 // the default ProcessErrorCallback (which we want to reference the RunLoop)
349 // before Init() launches a child process. Hence the base::Optional here.
350 base::Optional<base::RunLoop> wait_for_error_loop;
351 bool process_error_received = false;
Ken Rockot942af102020-06-04 05:48:46352 mojo::SetDefaultProcessErrorHandler(
Ken Rockot138153b2018-07-13 23:31:57353 base::BindLambdaForTesting([&](const std::string&) {
354 process_error_received = true;
355 wait_for_error_loop->Quit();
356 }));
357
358 Init("IPCChannelMojoNoImplicitChanelClosureClient");
359
360 wait_for_error_loop.emplace();
361 ListenerThatBindsATestStructPasser listener;
362 CreateChannel(&listener);
363 ASSERT_TRUE(ConnectChannel());
364
365 wait_for_error_loop->Run();
366 EXPECT_TRUE(process_error_received);
Ken Rockot942af102020-06-04 05:48:46367 mojo::SetDefaultProcessErrorHandler(base::NullCallback());
Ken Rockot138153b2018-07-13 23:31:57368
369 // Tell the child it can quit and wait for it to shut down.
370 ListenerThatExpectsOK::SendOK(channel());
371 EXPECT_TRUE(WaitForClientShutdown());
372 DestroyChannel();
373}
374
morrita81b17e02015-02-06 00:58:30375struct TestingMessagePipe {
376 TestingMessagePipe() {
377 EXPECT_EQ(MOJO_RESULT_OK, mojo::CreateMessagePipe(nullptr, &self, &peer));
378 }
379
380 mojo::ScopedMessagePipeHandle self;
381 mojo::ScopedMessagePipeHandle peer;
382};
383
384class HandleSendingHelper {
385 public:
386 static std::string GetSendingFileContent() { return "Hello"; }
387
388 static void WritePipe(IPC::Message* message, TestingMessagePipe* pipe) {
389 std::string content = HandleSendingHelper::GetSendingFileContent();
390 EXPECT_EQ(MOJO_RESULT_OK,
391 mojo::WriteMessageRaw(pipe->self.get(), &content[0],
392 static_cast<uint32_t>(content.size()),
393 nullptr, 0, 0));
dchenge48600452015-12-28 02:24:50394 EXPECT_TRUE(IPC::MojoMessageHelper::WriteMessagePipeTo(
395 message, std::move(pipe->peer)));
morrita81b17e02015-02-06 00:58:30396 }
397
398 static void WritePipeThenSend(IPC::Sender* sender, TestingMessagePipe* pipe) {
399 IPC::Message* message =
400 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
401 WritePipe(message, pipe);
402 ASSERT_TRUE(sender->Send(message));
403 }
404
405 static void ReadReceivedPipe(const IPC::Message& message,
brettwbd4d7112015-06-03 04:29:25406 base::PickleIterator* iter) {
morrita81b17e02015-02-06 00:58:30407 mojo::ScopedMessagePipeHandle pipe;
408 EXPECT_TRUE(
409 IPC::MojoMessageHelper::ReadMessagePipeFrom(&message, iter, &pipe));
Ken Rockotfada7d282017-06-12 21:25:13410 std::vector<uint8_t> content;
morrita81b17e02015-02-06 00:58:30411
sammc57ed9f982016-03-10 06:28:35412 ASSERT_EQ(MOJO_RESULT_OK,
rockota9d566a2017-03-17 19:36:15413 mojo::Wait(pipe.get(), MOJO_HANDLE_SIGNAL_READABLE));
morrita81b17e02015-02-06 00:58:30414 EXPECT_EQ(MOJO_RESULT_OK,
Ken Rockotfada7d282017-06-12 21:25:13415 mojo::ReadMessageRaw(pipe.get(), &content, nullptr, 0));
416 EXPECT_EQ(std::string(content.begin(), content.end()),
417 GetSendingFileContent());
morrita81b17e02015-02-06 00:58:30418 }
419
Fabrice de Gans-Riberi894661c2018-05-24 18:43:22420#if defined(OS_POSIX) || defined(OS_FUCHSIA)
amistry20e2b1d62016-06-23 06:12:35421 static base::FilePath GetSendingFilePath(const base::FilePath& dir_path) {
422 return dir_path.Append("ListenerThatExpectsFile.txt");
morrita81b17e02015-02-06 00:58:30423 }
424
425 static void WriteFile(IPC::Message* message, base::File& file) {
426 std::string content = GetSendingFileContent();
427 file.WriteAtCurrentPos(content.data(), content.size());
428 file.Flush();
429 message->WriteAttachment(new IPC::internal::PlatformFileAttachment(
430 base::ScopedFD(file.TakePlatformFile())));
431 }
432
433 static void WriteFileThenSend(IPC::Sender* sender, base::File& file) {
434 IPC::Message* message =
435 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
436 WriteFile(message, file);
437 ASSERT_TRUE(sender->Send(message));
438 }
439
440 static void WriteFileAndPipeThenSend(IPC::Sender* sender,
441 base::File& file,
442 TestingMessagePipe* pipe) {
443 IPC::Message* message =
444 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
445 WriteFile(message, file);
446 WritePipe(message, pipe);
447 ASSERT_TRUE(sender->Send(message));
448 }
449
450 static void ReadReceivedFile(const IPC::Message& message,
brettwbd4d7112015-06-03 04:29:25451 base::PickleIterator* iter) {
rockot502c94f2016-02-03 20:20:16452 scoped_refptr<base::Pickle::Attachment> attachment;
morrita81b17e02015-02-06 00:58:30453 EXPECT_TRUE(message.ReadAttachment(iter, &attachment));
sammc6ed3efb2016-11-23 03:17:35454 EXPECT_EQ(
455 IPC::MessageAttachment::Type::PLATFORM_FILE,
456 static_cast<IPC::MessageAttachment*>(attachment.get())->GetType());
457 base::File file(
458 static_cast<IPC::internal::PlatformFileAttachment*>(attachment.get())
459 ->TakePlatformFile());
morrita81b17e02015-02-06 00:58:30460 std::string content(GetSendingFileContent().size(), ' ');
461 file.Read(0, &content[0], content.size());
462 EXPECT_EQ(content, GetSendingFileContent());
463 }
464#endif
465};
466
Wez831ae412017-08-30 00:29:36467class ListenerThatExpectsMessagePipe : public TestListenerBase {
morrita81b17e02015-02-06 00:58:30468 public:
Wezfdb98482018-07-12 01:21:39469 ListenerThatExpectsMessagePipe(base::OnceClosure quit_closure)
470 : TestListenerBase(std::move(quit_closure)) {}
morrita81b17e02015-02-06 00:58:30471
Chris Watkins2d879af2017-11-30 02:11:59472 ~ListenerThatExpectsMessagePipe() override = default;
morrita81b17e02015-02-06 00:58:30473
474 bool OnMessageReceived(const IPC::Message& message) override {
brettwbd4d7112015-06-03 04:29:25475 base::PickleIterator iter(message);
morrita81b17e02015-02-06 00:58:30476 HandleSendingHelper::ReadReceivedPipe(message, &iter);
Wez831ae412017-08-30 00:29:36477 ListenerThatExpectsOK::SendOK(sender());
morrita81b17e02015-02-06 00:58:30478 return true;
479 }
morrita81b17e02015-02-06 00:58:30480};
481
amistry0027a0952016-05-03 00:52:47482TEST_F(IPCChannelMojoTest, SendMessagePipe) {
sammc4bcc4ed62016-10-27 10:13:59483 Init("IPCChannelMojoTestSendMessagePipeClient");
morrita81b17e02015-02-06 00:58:30484
Wez831ae412017-08-30 00:29:36485 base::RunLoop run_loop;
486 ListenerThatExpectsOK listener(run_loop.QuitClosure());
morrita81b17e02015-02-06 00:58:30487 CreateChannel(&listener);
488 ASSERT_TRUE(ConnectChannel());
morrita81b17e02015-02-06 00:58:30489
490 TestingMessagePipe pipe;
491 HandleSendingHelper::WritePipeThenSend(channel(), &pipe);
492
Wez831ae412017-08-30 00:29:36493 run_loop.Run();
sammc57ed9f982016-03-10 06:28:35494 channel()->Close();
morrita81b17e02015-02-06 00:58:30495
496 EXPECT_TRUE(WaitForClientShutdown());
497 DestroyChannel();
498}
499
sammc4bcc4ed62016-10-27 10:13:59500DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(IPCChannelMojoTestSendMessagePipeClient) {
Wez831ae412017-08-30 00:29:36501 base::RunLoop run_loop;
502 ListenerThatExpectsMessagePipe listener(run_loop.QuitClosure());
sammc57ed9f982016-03-10 06:28:35503 Connect(&listener);
504 listener.set_sender(channel());
morrita81b17e02015-02-06 00:58:30505
Wez831ae412017-08-30 00:29:36506 run_loop.Run();
morrita81b17e02015-02-06 00:58:30507
sammc57ed9f982016-03-10 06:28:35508 Close();
morrita81b17e02015-02-06 00:58:30509}
510
morrita438a2ee2015-04-03 05:28:21511void ReadOK(mojo::MessagePipeHandle pipe) {
Ken Rockotfada7d282017-06-12 21:25:13512 std::vector<uint8_t> should_be_ok;
rockota9d566a2017-03-17 19:36:15513 CHECK_EQ(MOJO_RESULT_OK, mojo::Wait(pipe, MOJO_HANDLE_SIGNAL_READABLE));
morrita438a2ee2015-04-03 05:28:21514 CHECK_EQ(MOJO_RESULT_OK,
Ken Rockotfada7d282017-06-12 21:25:13515 mojo::ReadMessageRaw(pipe, &should_be_ok, nullptr, 0));
516 EXPECT_EQ("OK", std::string(should_be_ok.begin(), should_be_ok.end()));
morrita438a2ee2015-04-03 05:28:21517}
518
519void WriteOK(mojo::MessagePipeHandle pipe) {
520 std::string ok("OK");
521 CHECK_EQ(MOJO_RESULT_OK,
522 mojo::WriteMessageRaw(pipe, &ok[0], static_cast<uint32_t>(ok.size()),
523 nullptr, 0, 0));
524}
525
Wez831ae412017-08-30 00:29:36526class ListenerThatExpectsMessagePipeUsingParamTrait : public TestListenerBase {
morrita438a2ee2015-04-03 05:28:21527 public:
Wez831ae412017-08-30 00:29:36528 explicit ListenerThatExpectsMessagePipeUsingParamTrait(
Wezfdb98482018-07-12 01:21:39529 base::OnceClosure quit_closure,
Wez831ae412017-08-30 00:29:36530 bool receiving_valid)
Wezfdb98482018-07-12 01:21:39531 : TestListenerBase(std::move(quit_closure)),
532 receiving_valid_(receiving_valid) {}
morrita438a2ee2015-04-03 05:28:21533
Chris Watkins2d879af2017-11-30 02:11:59534 ~ListenerThatExpectsMessagePipeUsingParamTrait() override = default;
morrita438a2ee2015-04-03 05:28:21535
536 bool OnMessageReceived(const IPC::Message& message) override {
brettwbd4d7112015-06-03 04:29:25537 base::PickleIterator iter(message);
morrita438a2ee2015-04-03 05:28:21538 mojo::MessagePipeHandle handle;
539 EXPECT_TRUE(IPC::ParamTraits<mojo::MessagePipeHandle>::Read(&message, &iter,
540 &handle));
541 EXPECT_EQ(handle.is_valid(), receiving_valid_);
542 if (receiving_valid_) {
543 ReadOK(handle);
544 MojoClose(handle.value());
545 }
546
Wez831ae412017-08-30 00:29:36547 ListenerThatExpectsOK::SendOK(sender());
morrita438a2ee2015-04-03 05:28:21548 return true;
549 }
550
morrita438a2ee2015-04-03 05:28:21551 private:
morrita438a2ee2015-04-03 05:28:21552 bool receiving_valid_;
553};
554
sammc4bcc4ed62016-10-27 10:13:59555class ParamTraitMessagePipeClient : public IpcChannelMojoTestClient {
sammc57ed9f982016-03-10 06:28:35556 public:
557 void RunTest(bool receiving_valid_handle) {
Wez831ae412017-08-30 00:29:36558 base::RunLoop run_loop;
sammc57ed9f982016-03-10 06:28:35559 ListenerThatExpectsMessagePipeUsingParamTrait listener(
Wez831ae412017-08-30 00:29:36560 run_loop.QuitClosure(), receiving_valid_handle);
sammc57ed9f982016-03-10 06:28:35561 Connect(&listener);
562 listener.set_sender(channel());
morrita438a2ee2015-04-03 05:28:21563
Wez831ae412017-08-30 00:29:36564 run_loop.Run();
morrita438a2ee2015-04-03 05:28:21565
sammc57ed9f982016-03-10 06:28:35566 Close();
567 }
568};
morrita438a2ee2015-04-03 05:28:21569
amistry0027a0952016-05-03 00:52:47570TEST_F(IPCChannelMojoTest, ParamTraitValidMessagePipe) {
sammc4bcc4ed62016-10-27 10:13:59571 Init("ParamTraitValidMessagePipeClient");
morrita438a2ee2015-04-03 05:28:21572
Wez831ae412017-08-30 00:29:36573 base::RunLoop run_loop;
574 ListenerThatExpectsOK listener(run_loop.QuitClosure());
morrita438a2ee2015-04-03 05:28:21575 CreateChannel(&listener);
576 ASSERT_TRUE(ConnectChannel());
morrita438a2ee2015-04-03 05:28:21577
578 TestingMessagePipe pipe;
579
danakj03de39b22016-04-23 04:21:09580 std::unique_ptr<IPC::Message> message(new IPC::Message());
morrita438a2ee2015-04-03 05:28:21581 IPC::ParamTraits<mojo::MessagePipeHandle>::Write(message.get(),
582 pipe.peer.release());
583 WriteOK(pipe.self.get());
584
sammc57ed9f982016-03-10 06:28:35585 channel()->Send(message.release());
Wez831ae412017-08-30 00:29:36586 run_loop.Run();
sammc57ed9f982016-03-10 06:28:35587 channel()->Close();
morrita438a2ee2015-04-03 05:28:21588
589 EXPECT_TRUE(WaitForClientShutdown());
590 DestroyChannel();
591}
592
sammc4bcc4ed62016-10-27 10:13:59593DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT_WITH_CUSTOM_FIXTURE(
594 ParamTraitValidMessagePipeClient,
595 ParamTraitMessagePipeClient) {
sammc57ed9f982016-03-10 06:28:35596 RunTest(true);
morrita438a2ee2015-04-03 05:28:21597}
598
amistry0027a0952016-05-03 00:52:47599TEST_F(IPCChannelMojoTest, ParamTraitInvalidMessagePipe) {
sammc4bcc4ed62016-10-27 10:13:59600 Init("ParamTraitInvalidMessagePipeClient");
morrita438a2ee2015-04-03 05:28:21601
Wez831ae412017-08-30 00:29:36602 base::RunLoop run_loop;
603 ListenerThatExpectsOK listener(run_loop.QuitClosure());
morrita438a2ee2015-04-03 05:28:21604 CreateChannel(&listener);
605 ASSERT_TRUE(ConnectChannel());
morrita438a2ee2015-04-03 05:28:21606
607 mojo::MessagePipeHandle invalid_handle;
danakj03de39b22016-04-23 04:21:09608 std::unique_ptr<IPC::Message> message(new IPC::Message());
morrita438a2ee2015-04-03 05:28:21609 IPC::ParamTraits<mojo::MessagePipeHandle>::Write(message.get(),
610 invalid_handle);
611
sammc57ed9f982016-03-10 06:28:35612 channel()->Send(message.release());
Wez831ae412017-08-30 00:29:36613 run_loop.Run();
sammc57ed9f982016-03-10 06:28:35614 channel()->Close();
morrita438a2ee2015-04-03 05:28:21615
616 EXPECT_TRUE(WaitForClientShutdown());
617 DestroyChannel();
618}
619
sammc4bcc4ed62016-10-27 10:13:59620DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT_WITH_CUSTOM_FIXTURE(
621 ParamTraitInvalidMessagePipeClient,
622 ParamTraitMessagePipeClient) {
sammc57ed9f982016-03-10 06:28:35623 RunTest(false);
morrita438a2ee2015-04-03 05:28:21624}
625
amistry0027a0952016-05-03 00:52:47626TEST_F(IPCChannelMojoTest, SendFailAfterClose) {
sammc4bcc4ed62016-10-27 10:13:59627 Init("IPCChannelMojoTestSendOkClient");
morrita17137e62015-06-23 22:29:36628
Wez831ae412017-08-30 00:29:36629 base::RunLoop run_loop;
630 ListenerThatExpectsOK listener(run_loop.QuitClosure());
morrita17137e62015-06-23 22:29:36631 CreateChannel(&listener);
632 ASSERT_TRUE(ConnectChannel());
morrita17137e62015-06-23 22:29:36633
Wez831ae412017-08-30 00:29:36634 run_loop.Run();
sammc57ed9f982016-03-10 06:28:35635 channel()->Close();
636 ASSERT_FALSE(channel()->Send(new IPC::Message()));
morrita17137e62015-06-23 22:29:36637
638 EXPECT_TRUE(WaitForClientShutdown());
639 DestroyChannel();
640}
641
Wez831ae412017-08-30 00:29:36642class ListenerSendingOneOk : public TestListenerBase {
morrita17137e62015-06-23 22:29:36643 public:
Wezfdb98482018-07-12 01:21:39644 ListenerSendingOneOk(base::OnceClosure quit_closure)
645 : TestListenerBase(std::move(quit_closure)) {}
morrita17137e62015-06-23 22:29:36646
sammc57ed9f982016-03-10 06:28:35647 bool OnMessageReceived(const IPC::Message& message) override { return true; }
morrita17137e62015-06-23 22:29:36648
tfarina10a5c062015-09-04 18:47:57649 void OnChannelConnected(int32_t peer_pid) override {
Wez831ae412017-08-30 00:29:36650 ListenerThatExpectsOK::SendOK(sender());
Wezfdb98482018-07-12 01:21:39651 RunQuitClosure();
morrita17137e62015-06-23 22:29:36652 }
morrita17137e62015-06-23 22:29:36653};
654
sammc4bcc4ed62016-10-27 10:13:59655DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(IPCChannelMojoTestSendOkClient) {
Wez831ae412017-08-30 00:29:36656 base::RunLoop run_loop;
657 ListenerSendingOneOk listener(run_loop.QuitClosure());
sammc57ed9f982016-03-10 06:28:35658 Connect(&listener);
659 listener.set_sender(channel());
morrita17137e62015-06-23 22:29:36660
Wez831ae412017-08-30 00:29:36661 run_loop.Run();
morrita17137e62015-06-23 22:29:36662
sammc57ed9f982016-03-10 06:28:35663 Close();
morrita17137e62015-06-23 22:29:36664}
665
rockot7c6bf952016-07-14 00:34:11666class ListenerWithSimpleAssociatedInterface
667 : public IPC::Listener,
668 public IPC::mojom::SimpleTestDriver {
669 public:
670 static const int kNumMessages;
671
Wezfdb98482018-07-12 01:21:39672 explicit ListenerWithSimpleAssociatedInterface(base::OnceClosure quit_closure)
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15673 : quit_closure_(std::move(quit_closure)) {}
rockot7c6bf952016-07-14 00:34:11674
Chris Watkins2d879af2017-11-30 02:11:59675 ~ListenerWithSimpleAssociatedInterface() override = default;
rockot7c6bf952016-07-14 00:34:11676
677 bool OnMessageReceived(const IPC::Message& message) override {
678 base::PickleIterator iter(message);
rockot9abe09b2016-08-02 20:57:34679 int32_t should_be_expected;
680 EXPECT_TRUE(iter.ReadInt(&should_be_expected));
681 EXPECT_EQ(should_be_expected, next_expected_value_);
rockot7c6bf952016-07-14 00:34:11682 num_messages_received_++;
683 return true;
684 }
685
Wezfdb98482018-07-12 01:21:39686 void OnChannelError() override { CHECK(!quit_closure_); }
rockot7c6bf952016-07-14 00:34:11687
688 void RegisterInterfaceFactory(IPC::Channel* channel) {
689 channel->GetAssociatedInterfaceSupport()->AddAssociatedInterface(
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15690 base::BindRepeating(
691 &ListenerWithSimpleAssociatedInterface::BindReceiver,
692 base::Unretained(this)));
rockot7c6bf952016-07-14 00:34:11693 }
694
695 private:
696 // IPC::mojom::SimpleTestDriver:
rockot9abe09b2016-08-02 20:57:34697 void ExpectValue(int32_t value) override {
698 next_expected_value_ = value;
699 }
700
tzikdd76ce712017-06-08 05:27:04701 void GetExpectedValue(GetExpectedValueCallback callback) override {
rockot9abe09b2016-08-02 20:57:34702 NOTREACHED();
703 }
704
tzikdd76ce712017-06-08 05:27:04705 void RequestValue(RequestValueCallback callback) override { NOTREACHED(); }
rockot7c6bf952016-07-14 00:34:11706
tzikdd76ce712017-06-08 05:27:04707 void RequestQuit(RequestQuitCallback callback) override {
rockot7c6bf952016-07-14 00:34:11708 EXPECT_EQ(kNumMessages, num_messages_received_);
tzikdd76ce712017-06-08 05:27:04709 std::move(callback).Run();
Wezfdb98482018-07-12 01:21:39710 std::move(quit_closure_).Run();
rockot7c6bf952016-07-14 00:34:11711 }
712
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15713 void BindReceiver(
714 mojo::PendingAssociatedReceiver<IPC::mojom::SimpleTestDriver> receiver) {
715 DCHECK(!receiver_.is_bound());
716 receiver_.Bind(std::move(receiver));
rockot7c6bf952016-07-14 00:34:11717 }
718
rockot9abe09b2016-08-02 20:57:34719 int32_t next_expected_value_ = 0;
rockot7c6bf952016-07-14 00:34:11720 int num_messages_received_ = 0;
Wezfdb98482018-07-12 01:21:39721 base::OnceClosure quit_closure_;
rockot7c6bf952016-07-14 00:34:11722
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15723 mojo::AssociatedReceiver<IPC::mojom::SimpleTestDriver> receiver_{this};
rockot7c6bf952016-07-14 00:34:11724};
725
726const int ListenerWithSimpleAssociatedInterface::kNumMessages = 1000;
727
728class ListenerSendingAssociatedMessages : public IPC::Listener {
729 public:
Wezfdb98482018-07-12 01:21:39730 explicit ListenerSendingAssociatedMessages(base::OnceClosure quit_closure)
731 : quit_closure_(std::move(quit_closure)) {}
rockot7c6bf952016-07-14 00:34:11732
733 bool OnMessageReceived(const IPC::Message& message) override { return true; }
734
735 void OnChannelConnected(int32_t peer_pid) override {
736 DCHECK(channel_);
737 channel_->GetAssociatedInterfaceSupport()->GetRemoteAssociatedInterface(
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15738 driver_.BindNewEndpointAndPassReceiver());
rockot7c6bf952016-07-14 00:34:11739
740 // Send a bunch of interleaved messages, alternating between the associated
741 // interface and a legacy IPC::Message.
742 for (int i = 0; i < ListenerWithSimpleAssociatedInterface::kNumMessages;
743 ++i) {
rockot9abe09b2016-08-02 20:57:34744 driver_->ExpectValue(i);
745 SendValue(channel_, i);
rockot7c6bf952016-07-14 00:34:11746 }
Wezfdb98482018-07-12 01:21:39747 driver_->RequestQuit(base::BindOnce(
748 &ListenerSendingAssociatedMessages::OnQuitAck, base::Unretained(this)));
rockot7c6bf952016-07-14 00:34:11749 }
750
751 void set_channel(IPC::Channel* channel) { channel_ = channel; }
752
753 private:
Wezfdb98482018-07-12 01:21:39754 void OnQuitAck() { std::move(quit_closure_).Run(); }
rockot7c6bf952016-07-14 00:34:11755
756 IPC::Channel* channel_ = nullptr;
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15757 mojo::AssociatedRemote<IPC::mojom::SimpleTestDriver> driver_;
Wezfdb98482018-07-12 01:21:39758 base::OnceClosure quit_closure_;
rockot7c6bf952016-07-14 00:34:11759};
760
761TEST_F(IPCChannelMojoTest, SimpleAssociatedInterface) {
sammc4bcc4ed62016-10-27 10:13:59762 Init("SimpleAssociatedInterfaceClient");
rockot7c6bf952016-07-14 00:34:11763
Wezfdb98482018-07-12 01:21:39764 base::RunLoop run_loop;
765 ListenerWithSimpleAssociatedInterface listener(run_loop.QuitClosure());
rockot7c6bf952016-07-14 00:34:11766 CreateChannel(&listener);
767 ASSERT_TRUE(ConnectChannel());
768
769 listener.RegisterInterfaceFactory(channel());
770
Wezfdb98482018-07-12 01:21:39771 run_loop.Run();
rockot7c6bf952016-07-14 00:34:11772 channel()->Close();
773
774 EXPECT_TRUE(WaitForClientShutdown());
775 DestroyChannel();
776}
777
sammc4bcc4ed62016-10-27 10:13:59778DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(SimpleAssociatedInterfaceClient) {
Wezfdb98482018-07-12 01:21:39779 base::RunLoop run_loop;
780 ListenerSendingAssociatedMessages listener(run_loop.QuitClosure());
rockot7c6bf952016-07-14 00:34:11781 Connect(&listener);
782 listener.set_channel(channel());
783
Wezfdb98482018-07-12 01:21:39784 run_loop.Run();
rockot7c6bf952016-07-14 00:34:11785
786 Close();
787}
788
rockot8d890f62016-07-14 16:37:14789class ChannelProxyRunner {
790 public:
rockota34707ca2016-07-20 04:28:32791 ChannelProxyRunner(mojo::ScopedMessagePipeHandle handle,
792 bool for_server)
793 : for_server_(for_server),
794 handle_(std::move(handle)),
rockot9abe09b2016-08-02 20:57:34795 io_thread_("ChannelProxyRunner IO thread"),
796 never_signaled_(base::WaitableEvent::ResetPolicy::MANUAL,
797 base::WaitableEvent::InitialState::NOT_SIGNALED) {
rockot8d890f62016-07-14 16:37:14798 }
799
800 void CreateProxy(IPC::Listener* listener) {
801 io_thread_.StartWithOptions(
Carlos Caballerodd8bf7b042019-07-30 14:14:15802 base::Thread::Options(base::MessagePumpType::IO, 0));
Hajime Hoshiff15e972017-11-09 06:37:09803 proxy_ = IPC::SyncChannel::Create(listener, io_thread_.task_runner(),
804 base::ThreadTaskRunnerHandle::Get(),
805 &never_signaled_);
rockot8d890f62016-07-14 16:37:14806 }
rockota34707ca2016-07-20 04:28:32807
rockot10188752016-09-08 18:24:56808 void RunProxy() {
rockota34707ca2016-07-20 04:28:32809 std::unique_ptr<IPC::ChannelFactory> factory;
810 if (for_server_) {
811 factory = IPC::ChannelMojo::CreateServerFactory(
Hajime Hoshia98f1102017-11-20 06:34:35812 std::move(handle_), io_thread_.task_runner(),
813 base::ThreadTaskRunnerHandle::Get());
rockota34707ca2016-07-20 04:28:32814 } else {
815 factory = IPC::ChannelMojo::CreateClientFactory(
Hajime Hoshia98f1102017-11-20 06:34:35816 std::move(handle_), io_thread_.task_runner(),
817 base::ThreadTaskRunnerHandle::Get());
rockota34707ca2016-07-20 04:28:32818 }
rockot10188752016-09-08 18:24:56819 proxy_->Init(std::move(factory), true);
rockota34707ca2016-07-20 04:28:32820 }
rockot8d890f62016-07-14 16:37:14821
822 IPC::ChannelProxy* proxy() { return proxy_.get(); }
823
824 private:
rockota34707ca2016-07-20 04:28:32825 const bool for_server_;
rockot8d890f62016-07-14 16:37:14826
rockota34707ca2016-07-20 04:28:32827 mojo::ScopedMessagePipeHandle handle_;
rockot8d890f62016-07-14 16:37:14828 base::Thread io_thread_;
rockot9abe09b2016-08-02 20:57:34829 base::WaitableEvent never_signaled_;
rockotb62e2e32017-03-24 18:36:44830 std::unique_ptr<IPC::ChannelProxy> proxy_;
rockot8d890f62016-07-14 16:37:14831
832 DISALLOW_COPY_AND_ASSIGN(ChannelProxyRunner);
833};
834
835class IPCChannelProxyMojoTest : public IPCChannelMojoTestBase {
836 public:
sammc4bcc4ed62016-10-27 10:13:59837 void Init(const std::string& client_name) {
838 IPCChannelMojoTestBase::Init(client_name);
rockota34707ca2016-07-20 04:28:32839 runner_.reset(new ChannelProxyRunner(TakeHandle(), true));
rockot8d890f62016-07-14 16:37:14840 }
841 void CreateProxy(IPC::Listener* listener) { runner_->CreateProxy(listener); }
rockot10188752016-09-08 18:24:56842 void RunProxy() {
843 runner_->RunProxy();
rockot401fb2c2016-09-06 18:35:57844 }
rockot0e4de5f2016-07-22 21:18:07845 void DestroyProxy() {
846 runner_.reset();
847 base::RunLoop().RunUntilIdle();
848 }
rockot8d890f62016-07-14 16:37:14849
850 IPC::ChannelProxy* proxy() { return runner_->proxy(); }
851
852 private:
rockot8d890f62016-07-14 16:37:14853 std::unique_ptr<ChannelProxyRunner> runner_;
854};
855
856class ListenerWithSimpleProxyAssociatedInterface
857 : public IPC::Listener,
858 public IPC::mojom::SimpleTestDriver {
859 public:
860 static const int kNumMessages;
861
Wezfdb98482018-07-12 01:21:39862 explicit ListenerWithSimpleProxyAssociatedInterface(
863 base::OnceClosure quit_closure)
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15864 : quit_closure_(std::move(quit_closure)) {}
rockot8d890f62016-07-14 16:37:14865
Chris Watkins2d879af2017-11-30 02:11:59866 ~ListenerWithSimpleProxyAssociatedInterface() override = default;
rockot8d890f62016-07-14 16:37:14867
868 bool OnMessageReceived(const IPC::Message& message) override {
869 base::PickleIterator iter(message);
rockot9abe09b2016-08-02 20:57:34870 int32_t should_be_expected;
871 EXPECT_TRUE(iter.ReadInt(&should_be_expected));
872 EXPECT_EQ(should_be_expected, next_expected_value_);
rockot8d890f62016-07-14 16:37:14873 num_messages_received_++;
874 return true;
875 }
876
Wezfdb98482018-07-12 01:21:39877 void OnChannelError() override { CHECK(!quit_closure_); }
rockot8d890f62016-07-14 16:37:14878
rockotf62002a2016-09-15 00:08:59879 void OnAssociatedInterfaceRequest(
880 const std::string& interface_name,
881 mojo::ScopedInterfaceEndpointHandle handle) override {
882 DCHECK_EQ(interface_name, IPC::mojom::SimpleTestDriver::Name_);
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15883 receiver_.Bind(
884 mojo::PendingAssociatedReceiver<IPC::mojom::SimpleTestDriver>(
885 std::move(handle)));
rockot8d890f62016-07-14 16:37:14886 }
887
888 bool received_all_messages() const {
Wezfdb98482018-07-12 01:21:39889 return num_messages_received_ == kNumMessages && !quit_closure_;
rockot8d890f62016-07-14 16:37:14890 }
891
892 private:
893 // IPC::mojom::SimpleTestDriver:
rockot9abe09b2016-08-02 20:57:34894 void ExpectValue(int32_t value) override {
895 next_expected_value_ = value;
896 }
897
tzikdd76ce712017-06-08 05:27:04898 void GetExpectedValue(GetExpectedValueCallback callback) override {
899 std::move(callback).Run(next_expected_value_);
rockot9abe09b2016-08-02 20:57:34900 }
901
tzikdd76ce712017-06-08 05:27:04902 void RequestValue(RequestValueCallback callback) override { NOTREACHED(); }
rockot8d890f62016-07-14 16:37:14903
tzikdd76ce712017-06-08 05:27:04904 void RequestQuit(RequestQuitCallback callback) override {
tzikdd76ce712017-06-08 05:27:04905 std::move(callback).Run();
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15906 receiver_.reset();
Wezfdb98482018-07-12 01:21:39907 std::move(quit_closure_).Run();
rockot8d890f62016-07-14 16:37:14908 }
909
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15910 void BindReceiver(
911 mojo::PendingAssociatedReceiver<IPC::mojom::SimpleTestDriver> receiver) {
912 DCHECK(!receiver_.is_bound());
913 receiver_.Bind(std::move(receiver));
rockot8d890f62016-07-14 16:37:14914 }
915
rockot9abe09b2016-08-02 20:57:34916 int32_t next_expected_value_ = 0;
rockot8d890f62016-07-14 16:37:14917 int num_messages_received_ = 0;
Wezfdb98482018-07-12 01:21:39918 base::OnceClosure quit_closure_;
rockot8d890f62016-07-14 16:37:14919
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15920 mojo::AssociatedReceiver<IPC::mojom::SimpleTestDriver> receiver_{this};
rockot8d890f62016-07-14 16:37:14921};
922
923const int ListenerWithSimpleProxyAssociatedInterface::kNumMessages = 1000;
924
925TEST_F(IPCChannelProxyMojoTest, ProxyThreadAssociatedInterface) {
sammc4bcc4ed62016-10-27 10:13:59926 Init("ProxyThreadAssociatedInterfaceClient");
rockot8d890f62016-07-14 16:37:14927
Wezfdb98482018-07-12 01:21:39928 base::RunLoop run_loop;
929 ListenerWithSimpleProxyAssociatedInterface listener(run_loop.QuitClosure());
rockot8d890f62016-07-14 16:37:14930 CreateProxy(&listener);
rockot8d890f62016-07-14 16:37:14931 RunProxy();
932
Wezfdb98482018-07-12 01:21:39933 run_loop.Run();
rockot8d890f62016-07-14 16:37:14934
935 EXPECT_TRUE(WaitForClientShutdown());
936 EXPECT_TRUE(listener.received_all_messages());
937
rockot0e4de5f2016-07-22 21:18:07938 DestroyProxy();
rockot8d890f62016-07-14 16:37:14939}
940
941class ChannelProxyClient {
942 public:
943 void Init(mojo::ScopedMessagePipeHandle handle) {
rockota34707ca2016-07-20 04:28:32944 runner_.reset(new ChannelProxyRunner(std::move(handle), false));
rockot8d890f62016-07-14 16:37:14945 }
rockot9abe09b2016-08-02 20:57:34946
rockot8d890f62016-07-14 16:37:14947 void CreateProxy(IPC::Listener* listener) { runner_->CreateProxy(listener); }
rockot9abe09b2016-08-02 20:57:34948
rockot10188752016-09-08 18:24:56949 void RunProxy() { runner_->RunProxy(); }
rockot9abe09b2016-08-02 20:57:34950
rockot0e4de5f2016-07-22 21:18:07951 void DestroyProxy() {
952 runner_.reset();
953 base::RunLoop().RunUntilIdle();
954 }
rockot8d890f62016-07-14 16:37:14955
rockot9abe09b2016-08-02 20:57:34956 void RequestQuitAndWaitForAck(IPC::mojom::SimpleTestDriver* driver) {
957 base::RunLoop loop;
958 driver->RequestQuit(loop.QuitClosure());
959 loop.Run();
960 }
961
rockot8d890f62016-07-14 16:37:14962 IPC::ChannelProxy* proxy() { return runner_->proxy(); }
963
964 private:
Gabriel Charettec523fa62019-09-09 23:03:32965 base::test::SingleThreadTaskEnvironment task_environment_;
rockot8d890f62016-07-14 16:37:14966 std::unique_ptr<ChannelProxyRunner> runner_;
967};
968
rockot0e4de5f2016-07-22 21:18:07969class DummyListener : public IPC::Listener {
rockot8d890f62016-07-14 16:37:14970 public:
rockot8d890f62016-07-14 16:37:14971 // IPC::Listener
972 bool OnMessageReceived(const IPC::Message& message) override { return true; }
rockot8d890f62016-07-14 16:37:14973};
974
sammc4bcc4ed62016-10-27 10:13:59975DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT_WITH_CUSTOM_FIXTURE(
976 ProxyThreadAssociatedInterfaceClient,
977 ChannelProxyClient) {
rockot0e4de5f2016-07-22 21:18:07978 DummyListener listener;
rockot8d890f62016-07-14 16:37:14979 CreateProxy(&listener);
980 RunProxy();
rockot8d890f62016-07-14 16:37:14981
982 // Send a bunch of interleaved messages, alternating between the associated
983 // interface and a legacy IPC::Message.
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:15984 mojo::AssociatedRemote<IPC::mojom::SimpleTestDriver> driver;
rockot8d890f62016-07-14 16:37:14985 proxy()->GetRemoteAssociatedInterface(&driver);
986 for (int i = 0; i < ListenerWithSimpleProxyAssociatedInterface::kNumMessages;
987 ++i) {
rockot9abe09b2016-08-02 20:57:34988 driver->ExpectValue(i);
989 SendValue(proxy(), i);
rockot8d890f62016-07-14 16:37:14990 }
Wezfdb98482018-07-12 01:21:39991 base::RunLoop run_loop;
992 driver->RequestQuit(run_loop.QuitClosure());
993 run_loop.Run();
rockot0e4de5f2016-07-22 21:18:07994
995 DestroyProxy();
rockot8d890f62016-07-14 16:37:14996}
997
rockot401fb2c2016-09-06 18:35:57998class ListenerWithIndirectProxyAssociatedInterface
999 : public IPC::Listener,
1000 public IPC::mojom::IndirectTestDriver,
1001 public IPC::mojom::PingReceiver {
1002 public:
Julie Jeongeun Kimac82819f2019-11-20 00:01:271003 ListenerWithIndirectProxyAssociatedInterface() = default;
Chris Watkins2d879af2017-11-30 02:11:591004 ~ListenerWithIndirectProxyAssociatedInterface() override = default;
rockot401fb2c2016-09-06 18:35:571005
rockot70bbb59492017-01-25 00:56:511006 // IPC::Listener:
rockot401fb2c2016-09-06 18:35:571007 bool OnMessageReceived(const IPC::Message& message) override { return true; }
1008
rockot70bbb59492017-01-25 00:56:511009 void OnAssociatedInterfaceRequest(
1010 const std::string& interface_name,
1011 mojo::ScopedInterfaceEndpointHandle handle) override {
Julie Jeongeun Kimac82819f2019-11-20 00:01:271012 DCHECK(!driver_receiver_.is_bound());
rockot70bbb59492017-01-25 00:56:511013 DCHECK_EQ(interface_name, IPC::mojom::IndirectTestDriver::Name_);
Julie Jeongeun Kimac82819f2019-11-20 00:01:271014 driver_receiver_.Bind(
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:541015 mojo::PendingAssociatedReceiver<IPC::mojom::IndirectTestDriver>(
1016 std::move(handle)));
rockot401fb2c2016-09-06 18:35:571017 }
1018
Wezfdb98482018-07-12 01:21:391019 void set_ping_handler(const base::RepeatingClosure& handler) {
rockot401fb2c2016-09-06 18:35:571020 ping_handler_ = handler;
1021 }
1022
1023 private:
1024 // IPC::mojom::IndirectTestDriver:
Julie Jeongeun Kim761a8ff2019-09-27 01:56:491025 void GetPingReceiver(mojo::PendingAssociatedReceiver<IPC::mojom::PingReceiver>
1026 receiver) override {
1027 ping_receiver_receiver_.Bind(std::move(receiver));
rockot401fb2c2016-09-06 18:35:571028 }
1029
1030 // IPC::mojom::PingReceiver:
tzikdd76ce712017-06-08 05:27:041031 void Ping(PingCallback callback) override {
1032 std::move(callback).Run();
rockot401fb2c2016-09-06 18:35:571033 ping_handler_.Run();
1034 }
1035
Julie Jeongeun Kimac82819f2019-11-20 00:01:271036 mojo::AssociatedReceiver<IPC::mojom::IndirectTestDriver> driver_receiver_{
1037 this};
Julie Jeongeun Kim761a8ff2019-09-27 01:56:491038 mojo::AssociatedReceiver<IPC::mojom::PingReceiver> ping_receiver_receiver_{
1039 this};
rockot401fb2c2016-09-06 18:35:571040
Wezfdb98482018-07-12 01:21:391041 base::RepeatingClosure ping_handler_;
rockot401fb2c2016-09-06 18:35:571042};
1043
1044TEST_F(IPCChannelProxyMojoTest, ProxyThreadAssociatedInterfaceIndirect) {
1045 // Tests that we can pipeline interface requests and subsequent messages
1046 // targeting proxy thread bindings, and the channel will still dispatch
1047 // messages appropriately.
1048
sammc4bcc4ed62016-10-27 10:13:591049 Init("ProxyThreadAssociatedInterfaceIndirectClient");
rockot401fb2c2016-09-06 18:35:571050
1051 ListenerWithIndirectProxyAssociatedInterface listener;
1052 CreateProxy(&listener);
rockot401fb2c2016-09-06 18:35:571053 RunProxy();
1054
1055 base::RunLoop loop;
1056 listener.set_ping_handler(loop.QuitClosure());
1057 loop.Run();
1058
1059 EXPECT_TRUE(WaitForClientShutdown());
1060
1061 DestroyProxy();
1062}
1063
sammc4bcc4ed62016-10-27 10:13:591064DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT_WITH_CUSTOM_FIXTURE(
rockot401fb2c2016-09-06 18:35:571065 ProxyThreadAssociatedInterfaceIndirectClient,
1066 ChannelProxyClient) {
1067 DummyListener listener;
1068 CreateProxy(&listener);
1069 RunProxy();
1070
1071 // Use an interface requested via another interface. On the remote end both
1072 // interfaces are bound on the proxy thread. This ensures that the Ping
1073 // message we send will still be dispatched properly even though the remote
1074 // endpoint may not have been bound yet by the time the message is initially
1075 // processed on the IO thread.
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:541076 mojo::AssociatedRemote<IPC::mojom::IndirectTestDriver> driver;
Julie Jeongeun Kim761a8ff2019-09-27 01:56:491077 mojo::AssociatedRemote<IPC::mojom::PingReceiver> ping_receiver;
rockot401fb2c2016-09-06 18:35:571078 proxy()->GetRemoteAssociatedInterface(&driver);
Julie Jeongeun Kim761a8ff2019-09-27 01:56:491079 driver->GetPingReceiver(ping_receiver.BindNewEndpointAndPassReceiver());
rockot401fb2c2016-09-06 18:35:571080
1081 base::RunLoop loop;
1082 ping_receiver->Ping(loop.QuitClosure());
1083 loop.Run();
1084
1085 DestroyProxy();
1086}
1087
rockot9abe09b2016-08-02 20:57:341088class ListenerWithSyncAssociatedInterface
1089 : public IPC::Listener,
1090 public IPC::mojom::SimpleTestDriver {
1091 public:
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151092 ListenerWithSyncAssociatedInterface() = default;
Chris Watkins2d879af2017-11-30 02:11:591093 ~ListenerWithSyncAssociatedInterface() override = default;
rockot9abe09b2016-08-02 20:57:341094
1095 void set_sync_sender(IPC::Sender* sync_sender) { sync_sender_ = sync_sender; }
1096
rockot9abe09b2016-08-02 20:57:341097 void RunUntilQuitRequested() {
1098 base::RunLoop loop;
1099 quit_closure_ = loop.QuitClosure();
1100 loop.Run();
1101 }
1102
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151103 void CloseBinding() { receiver_.reset(); }
rockot9abe09b2016-08-02 20:57:341104
1105 void set_response_value(int32_t response) {
1106 response_value_ = response;
1107 }
1108
1109 private:
1110 // IPC::mojom::SimpleTestDriver:
1111 void ExpectValue(int32_t value) override {
1112 next_expected_value_ = value;
1113 }
1114
tzikdd76ce712017-06-08 05:27:041115 void GetExpectedValue(GetExpectedValueCallback callback) override {
1116 std::move(callback).Run(next_expected_value_);
rockot9abe09b2016-08-02 20:57:341117 }
1118
tzikdd76ce712017-06-08 05:27:041119 void RequestValue(RequestValueCallback callback) override {
1120 std::move(callback).Run(response_value_);
rockot9abe09b2016-08-02 20:57:341121 }
1122
tzikdd76ce712017-06-08 05:27:041123 void RequestQuit(RequestQuitCallback callback) override {
Wezfdb98482018-07-12 01:21:391124 std::move(quit_closure_).Run();
tzikdd76ce712017-06-08 05:27:041125 std::move(callback).Run();
rockot9abe09b2016-08-02 20:57:341126 }
1127
1128 // IPC::Listener:
1129 bool OnMessageReceived(const IPC::Message& message) override {
1130 EXPECT_EQ(0u, message.type());
1131 EXPECT_TRUE(message.is_sync());
1132 EXPECT_TRUE(message.should_unblock());
1133 std::unique_ptr<IPC::Message> reply(
1134 IPC::SyncMessage::GenerateReply(&message));
1135 reply->WriteInt(response_value_);
1136 DCHECK(sync_sender_);
1137 EXPECT_TRUE(sync_sender_->Send(reply.release()));
1138 return true;
1139 }
1140
rockot70bbb59492017-01-25 00:56:511141 void OnAssociatedInterfaceRequest(
1142 const std::string& interface_name,
1143 mojo::ScopedInterfaceEndpointHandle handle) override {
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151144 DCHECK(!receiver_.is_bound());
rockot70bbb59492017-01-25 00:56:511145 DCHECK_EQ(interface_name, IPC::mojom::SimpleTestDriver::Name_);
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151146 receiver_.Bind(
1147 mojo::PendingAssociatedReceiver<IPC::mojom::SimpleTestDriver>(
1148 std::move(handle)));
rockot70bbb59492017-01-25 00:56:511149 }
1150
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151151 void BindReceiver(
1152 mojo::PendingAssociatedReceiver<IPC::mojom::SimpleTestDriver> receiver) {
1153 DCHECK(!receiver_.is_bound());
1154 receiver_.Bind(std::move(receiver));
rockot9abe09b2016-08-02 20:57:341155 }
1156
1157 IPC::Sender* sync_sender_ = nullptr;
1158 int32_t next_expected_value_ = 0;
1159 int32_t response_value_ = 0;
Wezfdb98482018-07-12 01:21:391160 base::OnceClosure quit_closure_;
rockot9abe09b2016-08-02 20:57:341161
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151162 mojo::AssociatedReceiver<IPC::mojom::SimpleTestDriver> receiver_{this};
rockot9abe09b2016-08-02 20:57:341163};
1164
1165class SyncReplyReader : public IPC::MessageReplyDeserializer {
1166 public:
1167 explicit SyncReplyReader(int32_t* storage) : storage_(storage) {}
Chris Watkins2d879af2017-11-30 02:11:591168 ~SyncReplyReader() override = default;
rockot9abe09b2016-08-02 20:57:341169
1170 private:
1171 // IPC::MessageReplyDeserializer:
1172 bool SerializeOutputParameters(const IPC::Message& message,
1173 base::PickleIterator iter) override {
1174 if (!iter.ReadInt(storage_))
1175 return false;
1176 return true;
1177 }
1178
1179 int32_t* storage_;
1180
1181 DISALLOW_COPY_AND_ASSIGN(SyncReplyReader);
1182};
1183
1184TEST_F(IPCChannelProxyMojoTest, SyncAssociatedInterface) {
sammc4bcc4ed62016-10-27 10:13:591185 Init("SyncAssociatedInterface");
rockot9abe09b2016-08-02 20:57:341186
1187 ListenerWithSyncAssociatedInterface listener;
1188 CreateProxy(&listener);
1189 listener.set_sync_sender(proxy());
rockot9abe09b2016-08-02 20:57:341190 RunProxy();
1191
1192 // Run the client's simple sanity check to completion.
1193 listener.RunUntilQuitRequested();
1194
1195 // Verify that we can send a sync IPC and service an incoming sync request
1196 // while waiting on it
1197 listener.set_response_value(42);
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151198 mojo::AssociatedRemote<IPC::mojom::SimpleTestClient> client;
rockot9abe09b2016-08-02 20:57:341199 proxy()->GetRemoteAssociatedInterface(&client);
1200 int32_t received_value;
1201 EXPECT_TRUE(client->RequestValue(&received_value));
1202 EXPECT_EQ(42, received_value);
1203
1204 // Do it again. This time the client will send a classical sync IPC to us
1205 // while we wait.
1206 received_value = 0;
1207 EXPECT_TRUE(client->RequestValue(&received_value));
1208 EXPECT_EQ(42, received_value);
1209
1210 // Now make a classical sync IPC request to the client. It will send a
1211 // sync associated interface message to us while we wait.
1212 received_value = 0;
1213 std::unique_ptr<IPC::SyncMessage> request(
1214 new IPC::SyncMessage(0, 0, IPC::Message::PRIORITY_NORMAL,
1215 new SyncReplyReader(&received_value)));
1216 EXPECT_TRUE(proxy()->Send(request.release()));
1217 EXPECT_EQ(42, received_value);
1218
1219 listener.CloseBinding();
1220 EXPECT_TRUE(WaitForClientShutdown());
1221
1222 DestroyProxy();
1223}
1224
1225class SimpleTestClientImpl : public IPC::mojom::SimpleTestClient,
1226 public IPC::Listener {
1227 public:
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151228 SimpleTestClientImpl() = default;
1229 ~SimpleTestClientImpl() override = default;
rockot9abe09b2016-08-02 20:57:341230
1231 void set_driver(IPC::mojom::SimpleTestDriver* driver) { driver_ = driver; }
1232 void set_sync_sender(IPC::Sender* sync_sender) { sync_sender_ = sync_sender; }
1233
rockot9abe09b2016-08-02 20:57:341234 void WaitForValueRequest() {
1235 run_loop_.reset(new base::RunLoop);
1236 run_loop_->Run();
1237 }
1238
1239 void UseSyncSenderForRequest(bool use_sync_sender) {
1240 use_sync_sender_ = use_sync_sender;
1241 }
1242
1243 private:
1244 // IPC::mojom::SimpleTestClient:
tzikdd76ce712017-06-08 05:27:041245 void RequestValue(RequestValueCallback callback) override {
rockot9abe09b2016-08-02 20:57:341246 int32_t response = 0;
1247 if (use_sync_sender_) {
1248 std::unique_ptr<IPC::SyncMessage> reply(new IPC::SyncMessage(
1249 0, 0, IPC::Message::PRIORITY_NORMAL, new SyncReplyReader(&response)));
1250 EXPECT_TRUE(sync_sender_->Send(reply.release()));
1251 } else {
1252 DCHECK(driver_);
1253 EXPECT_TRUE(driver_->RequestValue(&response));
1254 }
1255
tzikdd76ce712017-06-08 05:27:041256 std::move(callback).Run(response);
rockot9abe09b2016-08-02 20:57:341257
1258 DCHECK(run_loop_);
1259 run_loop_->Quit();
1260 }
1261
1262 // IPC::Listener:
1263 bool OnMessageReceived(const IPC::Message& message) override {
1264 int32_t response;
1265 DCHECK(driver_);
1266 EXPECT_TRUE(driver_->RequestValue(&response));
1267 std::unique_ptr<IPC::Message> reply(
1268 IPC::SyncMessage::GenerateReply(&message));
1269 reply->WriteInt(response);
1270 EXPECT_TRUE(sync_sender_->Send(reply.release()));
1271
1272 DCHECK(run_loop_);
1273 run_loop_->Quit();
1274 return true;
1275 }
1276
rockot70bbb59492017-01-25 00:56:511277 void OnAssociatedInterfaceRequest(
1278 const std::string& interface_name,
1279 mojo::ScopedInterfaceEndpointHandle handle) override {
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151280 DCHECK(!receiver_.is_bound());
rockot70bbb59492017-01-25 00:56:511281 DCHECK_EQ(interface_name, IPC::mojom::SimpleTestClient::Name_);
1282
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151283 receiver_.Bind(
Julie Jeongeun Kim761a8ff2019-09-27 01:56:491284 mojo::PendingAssociatedReceiver<IPC::mojom::SimpleTestClient>(
1285 std::move(handle)));
rockot70bbb59492017-01-25 00:56:511286 }
1287
rockot9abe09b2016-08-02 20:57:341288 bool use_sync_sender_ = false;
Julie Jeongeun Kim761a8ff2019-09-27 01:56:491289 mojo::AssociatedReceiver<IPC::mojom::SimpleTestClient> receiver_{this};
rockot9abe09b2016-08-02 20:57:341290 IPC::Sender* sync_sender_ = nullptr;
1291 IPC::mojom::SimpleTestDriver* driver_ = nullptr;
1292 std::unique_ptr<base::RunLoop> run_loop_;
1293
1294 DISALLOW_COPY_AND_ASSIGN(SimpleTestClientImpl);
1295};
1296
sammc4bcc4ed62016-10-27 10:13:591297DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT_WITH_CUSTOM_FIXTURE(SyncAssociatedInterface,
1298 ChannelProxyClient) {
rockot9abe09b2016-08-02 20:57:341299 SimpleTestClientImpl client_impl;
1300 CreateProxy(&client_impl);
1301 client_impl.set_sync_sender(proxy());
rockot9abe09b2016-08-02 20:57:341302 RunProxy();
1303
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151304 mojo::AssociatedRemote<IPC::mojom::SimpleTestDriver> driver;
rockot9abe09b2016-08-02 20:57:341305 proxy()->GetRemoteAssociatedInterface(&driver);
1306 client_impl.set_driver(driver.get());
1307
1308 // Simple sync message sanity check.
1309 driver->ExpectValue(42);
1310 int32_t expected_value = 0;
1311 EXPECT_TRUE(driver->GetExpectedValue(&expected_value));
1312 EXPECT_EQ(42, expected_value);
1313 RequestQuitAndWaitForAck(driver.get());
1314
1315 // Wait for the test driver to perform a sync call test with our own sync
1316 // associated interface message nested inside.
1317 client_impl.UseSyncSenderForRequest(false);
1318 client_impl.WaitForValueRequest();
1319
1320 // Wait for the test driver to perform a sync call test with our own classical
1321 // sync IPC nested inside.
1322 client_impl.UseSyncSenderForRequest(true);
1323 client_impl.WaitForValueRequest();
1324
1325 // Wait for the test driver to perform a classical sync IPC request, with our
1326 // own sync associated interface message nested inside.
1327 client_impl.UseSyncSenderForRequest(false);
1328 client_impl.WaitForValueRequest();
1329
1330 DestroyProxy();
1331}
1332
rockot10188752016-09-08 18:24:561333TEST_F(IPCChannelProxyMojoTest, Pause) {
1334 // Ensures that pausing a channel elicits the expected behavior when sending
1335 // messages, unpausing, sending more messages, and then manually flushing.
1336 // Specifically a sequence like:
rockot401fb2c2016-09-06 18:35:571337 //
1338 // Connect()
1339 // Send(A)
rockot10188752016-09-08 18:24:561340 // Pause()
rockot401fb2c2016-09-06 18:35:571341 // Send(B)
rockot401fb2c2016-09-06 18:35:571342 // Send(C)
rockot10188752016-09-08 18:24:561343 // Unpause(false)
1344 // Send(D)
1345 // Send(E)
rockot401fb2c2016-09-06 18:35:571346 // Flush()
1347 //
rockot10188752016-09-08 18:24:561348 // must result in the other end receiving messages A, D, E, B, D; in that
rockot401fb2c2016-09-06 18:35:571349 // order.
1350 //
1351 // This behavior is required by some consumers of IPC::Channel, and it is not
1352 // sufficient to leave this up to the consumer to implement since associated
1353 // interface requests and messages also need to be queued according to the
1354 // same policy.
sammc4bcc4ed62016-10-27 10:13:591355 Init("CreatePausedClient");
rockot401fb2c2016-09-06 18:35:571356
1357 DummyListener listener;
1358 CreateProxy(&listener);
rockot10188752016-09-08 18:24:561359 RunProxy();
1360
1361 // This message must be sent immediately since the channel is unpaused.
1362 SendValue(proxy(), 1);
1363
1364 proxy()->Pause();
rockot401fb2c2016-09-06 18:35:571365
1366 // These messages must be queued internally since the channel is paused.
rockot401fb2c2016-09-06 18:35:571367 SendValue(proxy(), 2);
rockot10188752016-09-08 18:24:561368 SendValue(proxy(), 3);
rockot401fb2c2016-09-06 18:35:571369
1370 proxy()->Unpause(false /* flush */);
1371
1372 // These messages must be sent immediately since the channel is unpaused.
rockot401fb2c2016-09-06 18:35:571373 SendValue(proxy(), 4);
rockot10188752016-09-08 18:24:561374 SendValue(proxy(), 5);
rockot401fb2c2016-09-06 18:35:571375
1376 // Now we flush the previously queued messages.
1377 proxy()->Flush();
1378
1379 EXPECT_TRUE(WaitForClientShutdown());
1380 DestroyProxy();
1381}
1382
1383class ExpectValueSequenceListener : public IPC::Listener {
1384 public:
Wezfdb98482018-07-12 01:21:391385 ExpectValueSequenceListener(base::queue<int32_t>* expected_values,
1386 base::OnceClosure quit_closure)
1387 : expected_values_(expected_values),
1388 quit_closure_(std::move(quit_closure)) {}
Chris Watkins2d879af2017-11-30 02:11:591389 ~ExpectValueSequenceListener() override = default;
rockot401fb2c2016-09-06 18:35:571390
1391 // IPC::Listener:
1392 bool OnMessageReceived(const IPC::Message& message) override {
1393 DCHECK(!expected_values_->empty());
1394 base::PickleIterator iter(message);
1395 int32_t should_be_expected;
1396 EXPECT_TRUE(iter.ReadInt(&should_be_expected));
1397 EXPECT_EQ(expected_values_->front(), should_be_expected);
1398 expected_values_->pop();
1399 if (expected_values_->empty())
Wezfdb98482018-07-12 01:21:391400 std::move(quit_closure_).Run();
rockot401fb2c2016-09-06 18:35:571401 return true;
1402 }
1403
1404 private:
Brett Wilsona62d9c02017-09-20 20:53:201405 base::queue<int32_t>* expected_values_;
Wezfdb98482018-07-12 01:21:391406 base::OnceClosure quit_closure_;
rockot401fb2c2016-09-06 18:35:571407
1408 DISALLOW_COPY_AND_ASSIGN(ExpectValueSequenceListener);
1409};
1410
sammc4bcc4ed62016-10-27 10:13:591411DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT_WITH_CUSTOM_FIXTURE(CreatePausedClient,
1412 ChannelProxyClient) {
Brett Wilsona62d9c02017-09-20 20:53:201413 base::queue<int32_t> expected_values;
Wezfdb98482018-07-12 01:21:391414 base::RunLoop run_loop;
1415 ExpectValueSequenceListener listener(&expected_values,
1416 run_loop.QuitClosure());
rockot401fb2c2016-09-06 18:35:571417 CreateProxy(&listener);
rockot401fb2c2016-09-06 18:35:571418 expected_values.push(1);
rockot10188752016-09-08 18:24:561419 expected_values.push(4);
1420 expected_values.push(5);
rockot401fb2c2016-09-06 18:35:571421 expected_values.push(2);
rockot10188752016-09-08 18:24:561422 expected_values.push(3);
rockot401fb2c2016-09-06 18:35:571423 RunProxy();
Wezfdb98482018-07-12 01:21:391424 run_loop.Run();
rockot401fb2c2016-09-06 18:35:571425 EXPECT_TRUE(expected_values.empty());
1426 DestroyProxy();
1427}
1428
sammc5c8a6c62017-02-04 01:33:381429TEST_F(IPCChannelProxyMojoTest, AssociatedRequestClose) {
1430 Init("DropAssociatedRequest");
1431
1432 DummyListener listener;
1433 CreateProxy(&listener);
1434 RunProxy();
1435
Julie Jeongeun Kim6eb409ed2019-09-28 01:27:541436 mojo::AssociatedRemote<IPC::mojom::AssociatedInterfaceVendor> vendor;
sammc5c8a6c62017-02-04 01:33:381437 proxy()->GetRemoteAssociatedInterface(&vendor);
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151438 mojo::AssociatedRemote<IPC::mojom::SimpleTestDriver> tester;
1439 vendor->GetTestInterface(tester.BindNewEndpointAndPassReceiver());
sammc5c8a6c62017-02-04 01:33:381440 base::RunLoop run_loop;
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151441 tester.set_disconnect_handler(run_loop.QuitClosure());
sammc5c8a6c62017-02-04 01:33:381442 run_loop.Run();
1443
Julie Jeongeun Kim3f9e09e2019-09-26 04:56:151444 tester.reset();
sammc5c8a6c62017-02-04 01:33:381445 proxy()->GetRemoteAssociatedInterface(&tester);
1446 EXPECT_TRUE(WaitForClientShutdown());
1447 DestroyProxy();
1448}
1449
1450class AssociatedInterfaceDroppingListener : public IPC::Listener {
1451 public:
Wezfdb98482018-07-12 01:21:391452 AssociatedInterfaceDroppingListener(base::OnceClosure callback)
1453 : callback_(std::move(callback)) {}
sammc5c8a6c62017-02-04 01:33:381454 bool OnMessageReceived(const IPC::Message& message) override { return false; }
1455
1456 void OnAssociatedInterfaceRequest(
1457 const std::string& interface_name,
1458 mojo::ScopedInterfaceEndpointHandle handle) override {
1459 if (interface_name == IPC::mojom::SimpleTestDriver::Name_)
Wezfdb98482018-07-12 01:21:391460 std::move(callback_).Run();
sammc5c8a6c62017-02-04 01:33:381461 }
1462
1463 private:
Wezfdb98482018-07-12 01:21:391464 base::OnceClosure callback_;
sammc5c8a6c62017-02-04 01:33:381465};
1466
1467DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT_WITH_CUSTOM_FIXTURE(DropAssociatedRequest,
1468 ChannelProxyClient) {
1469 base::RunLoop run_loop;
1470 AssociatedInterfaceDroppingListener listener(run_loop.QuitClosure());
1471 CreateProxy(&listener);
1472 RunProxy();
1473 run_loop.Run();
1474 DestroyProxy();
1475}
1476
Avi Drissman2b97d032020-07-30 03:02:261477#if !defined(OS_APPLE)
Wez831ae412017-08-30 00:29:361478// TODO(wez): On Mac we need to set up a MachPortBroker before we can transfer
1479// Mach ports (which underpin Sharedmemory on Mac) across IPC.
1480
Alexandr Ilind497eee2018-04-19 22:50:541481template <class SharedMemoryRegionType>
1482class IPCChannelMojoSharedMemoryRegionTypedTest : public IPCChannelMojoTest {};
1483
1484struct WritableRegionTraits {
1485 using RegionType = base::WritableSharedMemoryRegion;
1486 static const char kClientName[];
1487};
1488const char WritableRegionTraits::kClientName[] =
1489 "IPCChannelMojoTestSendWritableSharedMemoryRegionClient";
1490struct UnsafeRegionTraits {
1491 using RegionType = base::UnsafeSharedMemoryRegion;
1492 static const char kClientName[];
1493};
1494const char UnsafeRegionTraits::kClientName[] =
1495 "IPCChannelMojoTestSendUnsafeSharedMemoryRegionClient";
1496struct ReadOnlyRegionTraits {
1497 using RegionType = base::ReadOnlySharedMemoryRegion;
1498 static const char kClientName[];
1499};
1500const char ReadOnlyRegionTraits::kClientName[] =
1501 "IPCChannelMojoTestSendReadOnlySharedMemoryRegionClient";
1502
1503typedef ::testing::
1504 Types<WritableRegionTraits, UnsafeRegionTraits, ReadOnlyRegionTraits>
1505 AllSharedMemoryRegionTraits;
Victor Costanebc52732019-02-15 02:39:471506TYPED_TEST_SUITE(IPCChannelMojoSharedMemoryRegionTypedTest,
1507 AllSharedMemoryRegionTraits);
Alexandr Ilind497eee2018-04-19 22:50:541508
1509template <class SharedMemoryRegionType>
1510class ListenerThatExpectsSharedMemoryRegion : public TestListenerBase {
1511 public:
Wezfdb98482018-07-12 01:21:391512 explicit ListenerThatExpectsSharedMemoryRegion(base::OnceClosure quit_closure)
Alexandr Ilind497eee2018-04-19 22:50:541513 : TestListenerBase(std::move(quit_closure)) {}
1514
1515 bool OnMessageReceived(const IPC::Message& message) override {
1516 base::PickleIterator iter(message);
1517
1518 SharedMemoryRegionType region;
1519 EXPECT_TRUE(IPC::ReadParam(&message, &iter, &region));
1520 EXPECT_TRUE(region.IsValid());
1521
1522 // Verify the shared memory region has expected content.
1523 typename SharedMemoryRegionType::MappingType mapping = region.Map();
1524 std::string content = HandleSendingHelper::GetSendingFileContent();
1525 EXPECT_EQ(0, memcmp(mapping.memory(), content.data(), content.size()));
1526
1527 ListenerThatExpectsOK::SendOK(sender());
1528 return true;
1529 }
1530};
1531
1532TYPED_TEST(IPCChannelMojoSharedMemoryRegionTypedTest, Send) {
1533 this->Init(TypeParam::kClientName);
1534
1535 const size_t size = 1004;
1536 typename TypeParam::RegionType region;
1537 base::WritableSharedMemoryMapping mapping;
1538 std::tie(region, mapping) =
1539 base::CreateMappedRegion<typename TypeParam::RegionType>(size);
1540
1541 std::string content = HandleSendingHelper::GetSendingFileContent();
1542 memcpy(mapping.memory(), content.data(), content.size());
1543
1544 // Create a success listener, and launch the child process.
1545 base::RunLoop run_loop;
1546 ListenerThatExpectsOK listener(run_loop.QuitClosure());
1547 this->CreateChannel(&listener);
1548 ASSERT_TRUE(this->ConnectChannel());
1549
1550 // Send the child process an IPC with |shmem| attached, to verify
1551 // that is is correctly wrapped, transferred and unwrapped.
1552 IPC::Message* message = new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
1553 IPC::WriteParam(message, region);
1554 ASSERT_TRUE(this->channel()->Send(message));
1555
1556 run_loop.Run();
1557
1558 this->channel()->Close();
1559
1560 EXPECT_TRUE(this->WaitForClientShutdown());
1561 EXPECT_FALSE(region.IsValid());
1562 this->DestroyChannel();
1563}
1564
1565DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(
1566 IPCChannelMojoTestSendWritableSharedMemoryRegionClient) {
1567 base::RunLoop run_loop;
1568 ListenerThatExpectsSharedMemoryRegion<base::WritableSharedMemoryRegion>
1569 listener(run_loop.QuitClosure());
1570 Connect(&listener);
1571 listener.set_sender(channel());
1572
1573 run_loop.Run();
1574
1575 Close();
1576}
1577DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(
1578 IPCChannelMojoTestSendUnsafeSharedMemoryRegionClient) {
1579 base::RunLoop run_loop;
1580 ListenerThatExpectsSharedMemoryRegion<base::UnsafeSharedMemoryRegion>
1581 listener(run_loop.QuitClosure());
1582 Connect(&listener);
1583 listener.set_sender(channel());
1584
1585 run_loop.Run();
1586
1587 Close();
1588}
1589DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(
1590 IPCChannelMojoTestSendReadOnlySharedMemoryRegionClient) {
1591 base::RunLoop run_loop;
1592 ListenerThatExpectsSharedMemoryRegion<base::ReadOnlySharedMemoryRegion>
1593 listener(run_loop.QuitClosure());
1594 Connect(&listener);
1595 listener.set_sender(channel());
1596
1597 run_loop.Run();
1598
1599 Close();
1600}
Avi Drissman2b97d032020-07-30 03:02:261601#endif // !defined(OS_APPLE)
Wez831ae412017-08-30 00:29:361602
Fabrice de Gans-Riberi894661c2018-05-24 18:43:221603#if defined(OS_POSIX) || defined(OS_FUCHSIA)
rockot8d890f62016-07-14 16:37:141604
Wez831ae412017-08-30 00:29:361605class ListenerThatExpectsFile : public TestListenerBase {
[email protected]64860882014-08-04 23:44:171606 public:
Wezfdb98482018-07-12 01:21:391607 explicit ListenerThatExpectsFile(base::OnceClosure quit_closure)
1608 : TestListenerBase(std::move(quit_closure)) {}
[email protected]64860882014-08-04 23:44:171609
dchengfe61fca2014-10-22 02:29:521610 bool OnMessageReceived(const IPC::Message& message) override {
brettwbd4d7112015-06-03 04:29:251611 base::PickleIterator iter(message);
morrita81b17e02015-02-06 00:58:301612 HandleSendingHelper::ReadReceivedFile(message, &iter);
Wez831ae412017-08-30 00:29:361613 ListenerThatExpectsOK::SendOK(sender());
[email protected]64860882014-08-04 23:44:171614 return true;
1615 }
[email protected]64860882014-08-04 23:44:171616};
1617
Wez831ae412017-08-30 00:29:361618TEST_F(IPCChannelMojoTest, SendPlatformFile) {
1619 Init("IPCChannelMojoTestSendPlatformFileClient");
[email protected]64860882014-08-04 23:44:171620
Wez831ae412017-08-30 00:29:361621 base::RunLoop run_loop;
1622 ListenerThatExpectsOK listener(run_loop.QuitClosure());
morrita373af03b2014-09-09 19:35:241623 CreateChannel(&listener);
[email protected]64860882014-08-04 23:44:171624 ASSERT_TRUE(ConnectChannel());
[email protected]64860882014-08-04 23:44:171625
amistry20e2b1d62016-06-23 06:12:351626 base::ScopedTempDir temp_dir;
1627 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
vabr16e5f602016-09-15 18:14:001628 base::File file(HandleSendingHelper::GetSendingFilePath(temp_dir.GetPath()),
[email protected]64860882014-08-04 23:44:171629 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE |
morrita81b17e02015-02-06 00:58:301630 base::File::FLAG_READ);
1631 HandleSendingHelper::WriteFileThenSend(channel(), file);
Wez831ae412017-08-30 00:29:361632 run_loop.Run();
[email protected]64860882014-08-04 23:44:171633
sammc57ed9f982016-03-10 06:28:351634 channel()->Close();
[email protected]64860882014-08-04 23:44:171635
1636 EXPECT_TRUE(WaitForClientShutdown());
1637 DestroyChannel();
1638}
1639
Wez831ae412017-08-30 00:29:361640DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(IPCChannelMojoTestSendPlatformFileClient) {
1641 base::RunLoop run_loop;
1642 ListenerThatExpectsFile listener(run_loop.QuitClosure());
sammc57ed9f982016-03-10 06:28:351643 Connect(&listener);
1644 listener.set_sender(channel());
[email protected]64860882014-08-04 23:44:171645
Wez831ae412017-08-30 00:29:361646 run_loop.Run();
[email protected]64860882014-08-04 23:44:171647
sammc57ed9f982016-03-10 06:28:351648 Close();
[email protected]64860882014-08-04 23:44:171649}
morrita81b17e02015-02-06 00:58:301650
Wez831ae412017-08-30 00:29:361651class ListenerThatExpectsFileAndMessagePipe : public TestListenerBase {
morrita81b17e02015-02-06 00:58:301652 public:
Wezfdb98482018-07-12 01:21:391653 explicit ListenerThatExpectsFileAndMessagePipe(base::OnceClosure quit_closure)
1654 : TestListenerBase(std::move(quit_closure)) {}
morrita81b17e02015-02-06 00:58:301655
Chris Watkins2d879af2017-11-30 02:11:591656 ~ListenerThatExpectsFileAndMessagePipe() override = default;
morrita81b17e02015-02-06 00:58:301657
1658 bool OnMessageReceived(const IPC::Message& message) override {
brettwbd4d7112015-06-03 04:29:251659 base::PickleIterator iter(message);
morrita81b17e02015-02-06 00:58:301660 HandleSendingHelper::ReadReceivedFile(message, &iter);
1661 HandleSendingHelper::ReadReceivedPipe(message, &iter);
Wez831ae412017-08-30 00:29:361662 ListenerThatExpectsOK::SendOK(sender());
morrita81b17e02015-02-06 00:58:301663 return true;
1664 }
morrita81b17e02015-02-06 00:58:301665};
1666
Wez831ae412017-08-30 00:29:361667TEST_F(IPCChannelMojoTest, SendPlatformFileAndMessagePipe) {
1668 Init("IPCChannelMojoTestSendPlatformFileAndMessagePipeClient");
morrita81b17e02015-02-06 00:58:301669
Wez831ae412017-08-30 00:29:361670 base::RunLoop run_loop;
1671 ListenerThatExpectsOK listener(run_loop.QuitClosure());
morrita81b17e02015-02-06 00:58:301672 CreateChannel(&listener);
1673 ASSERT_TRUE(ConnectChannel());
morrita81b17e02015-02-06 00:58:301674
amistry20e2b1d62016-06-23 06:12:351675 base::ScopedTempDir temp_dir;
1676 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
vabr16e5f602016-09-15 18:14:001677 base::File file(HandleSendingHelper::GetSendingFilePath(temp_dir.GetPath()),
morrita81b17e02015-02-06 00:58:301678 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE |
1679 base::File::FLAG_READ);
1680 TestingMessagePipe pipe;
1681 HandleSendingHelper::WriteFileAndPipeThenSend(channel(), file, &pipe);
1682
Wez831ae412017-08-30 00:29:361683 run_loop.Run();
sammc57ed9f982016-03-10 06:28:351684 channel()->Close();
morrita81b17e02015-02-06 00:58:301685
1686 EXPECT_TRUE(WaitForClientShutdown());
1687 DestroyChannel();
1688}
1689
sammc57ed9f982016-03-10 06:28:351690DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(
Wez831ae412017-08-30 00:29:361691 IPCChannelMojoTestSendPlatformFileAndMessagePipeClient) {
1692 base::RunLoop run_loop;
1693 ListenerThatExpectsFileAndMessagePipe listener(run_loop.QuitClosure());
sammc57ed9f982016-03-10 06:28:351694 Connect(&listener);
1695 listener.set_sender(channel());
morrita81b17e02015-02-06 00:58:301696
Wez831ae412017-08-30 00:29:361697 run_loop.Run();
morrita81b17e02015-02-06 00:58:301698
sammc57ed9f982016-03-10 06:28:351699 Close();
morrita81b17e02015-02-06 00:58:301700}
1701
Fabrice de Gans-Riberi894661c2018-05-24 18:43:221702#endif // defined(OS_POSIX) || defined(OS_FUCHSIA)
[email protected]64860882014-08-04 23:44:171703
Sean McAllister82700412020-08-19 20:10:351704#if defined(OS_LINUX) || defined(OS_CHROMEOS)
morrita0bd20bd2015-02-25 20:11:271705
1706const base::ProcessId kMagicChildId = 54321;
1707
Wez831ae412017-08-30 00:29:361708class ListenerThatVerifiesPeerPid : public TestListenerBase {
morrita0bd20bd2015-02-25 20:11:271709 public:
Wezfdb98482018-07-12 01:21:391710 explicit ListenerThatVerifiesPeerPid(base::OnceClosure quit_closure)
1711 : TestListenerBase(std::move(quit_closure)) {}
Wez831ae412017-08-30 00:29:361712
tfarina10a5c062015-09-04 18:47:571713 void OnChannelConnected(int32_t peer_pid) override {
morrita0bd20bd2015-02-25 20:11:271714 EXPECT_EQ(peer_pid, kMagicChildId);
Wezfdb98482018-07-12 01:21:391715 RunQuitClosure();
morrita0bd20bd2015-02-25 20:11:271716 }
1717
1718 bool OnMessageReceived(const IPC::Message& message) override {
1719 NOTREACHED();
1720 return true;
1721 }
1722};
1723
sammc57ed9f982016-03-10 06:28:351724TEST_F(IPCChannelMojoTest, VerifyGlobalPid) {
sammc4bcc4ed62016-10-27 10:13:591725 Init("IPCChannelMojoTestVerifyGlobalPidClient");
morrita0bd20bd2015-02-25 20:11:271726
Wez831ae412017-08-30 00:29:361727 base::RunLoop run_loop;
1728 ListenerThatVerifiesPeerPid listener(run_loop.QuitClosure());
morrita0bd20bd2015-02-25 20:11:271729 CreateChannel(&listener);
1730 ASSERT_TRUE(ConnectChannel());
morrita0bd20bd2015-02-25 20:11:271731
Wez831ae412017-08-30 00:29:361732 run_loop.Run();
rockotcbca72f2015-03-03 16:31:041733 channel()->Close();
morrita0bd20bd2015-02-25 20:11:271734
1735 EXPECT_TRUE(WaitForClientShutdown());
1736 DestroyChannel();
1737}
1738
sammc4bcc4ed62016-10-27 10:13:591739DEFINE_IPC_CHANNEL_MOJO_TEST_CLIENT(IPCChannelMojoTestVerifyGlobalPidClient) {
morrita0bd20bd2015-02-25 20:11:271740 IPC::Channel::SetGlobalPid(kMagicChildId);
Wez831ae412017-08-30 00:29:361741
1742 base::RunLoop run_loop;
1743 ListenerThatQuits listener(run_loop.QuitClosure());
sammc57ed9f982016-03-10 06:28:351744 Connect(&listener);
morrita0bd20bd2015-02-25 20:11:271745
Wez831ae412017-08-30 00:29:361746 run_loop.Run();
morrita0bd20bd2015-02-25 20:11:271747
sammc57ed9f982016-03-10 06:28:351748 Close();
morrita0bd20bd2015-02-25 20:11:271749}
1750
Sean McAllister82700412020-08-19 20:10:351751#endif // defined(OS_LINUX) || defined(OS_CHROMEOS)
morrita0bd20bd2015-02-25 20:11:271752
[email protected]64860882014-08-04 23:44:171753} // namespace