Reads network quality provided by the NQE and compares it
[chromium-blink-merge.git] / ipc / mojo / ipc_channel_mojo_unittest.cc
blobdf5b7ba36bb5fe03ed2b7090958ebdf2733f52f7
1 // 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.
5 #include "ipc/mojo/ipc_channel_mojo.h"
7 #include "base/base_paths.h"
8 #include "base/files/file.h"
9 #include "base/location.h"
10 #include "base/path_service.h"
11 #include "base/pickle.h"
12 #include "base/run_loop.h"
13 #include "base/single_thread_task_runner.h"
14 #include "base/test/test_timeouts.h"
15 #include "base/thread_task_runner_handle.h"
16 #include "base/threading/thread.h"
17 #include "ipc/ipc_message.h"
18 #include "ipc/ipc_test_base.h"
19 #include "ipc/ipc_test_channel_listener.h"
20 #include "ipc/mojo/ipc_channel_mojo_host.h"
21 #include "ipc/mojo/ipc_mojo_handle_attachment.h"
22 #include "ipc/mojo/ipc_mojo_message_helper.h"
23 #include "ipc/mojo/ipc_mojo_param_traits.h"
24 #include "ipc/mojo/scoped_ipc_support.h"
26 #if defined(OS_POSIX)
27 #include "base/file_descriptor_posix.h"
28 #include "ipc/ipc_platform_file_attachment_posix.h"
29 #endif
31 namespace {
33 class ListenerThatExpectsOK : public IPC::Listener {
34 public:
35 ListenerThatExpectsOK()
36 : received_ok_(false) {}
38 ~ListenerThatExpectsOK() override {}
40 bool OnMessageReceived(const IPC::Message& message) override {
41 base::PickleIterator iter(message);
42 std::string should_be_ok;
43 EXPECT_TRUE(iter.ReadString(&should_be_ok));
44 EXPECT_EQ(should_be_ok, "OK");
45 received_ok_ = true;
46 base::MessageLoop::current()->Quit();
47 return true;
50 void OnChannelError() override {
51 // The connection should be healthy while the listener is waiting
52 // message. An error can occur after that because the peer
53 // process dies.
54 DCHECK(received_ok_);
57 static void SendOK(IPC::Sender* sender) {
58 IPC::Message* message = new IPC::Message(
59 0, 2, IPC::Message::PRIORITY_NORMAL);
60 message->WriteString(std::string("OK"));
61 ASSERT_TRUE(sender->Send(message));
64 private:
65 bool received_ok_;
68 class ChannelClient {
69 public:
70 explicit ChannelClient(IPC::Listener* listener, const char* name) {
71 channel_ = IPC::ChannelMojo::Create(NULL, main_message_loop_.task_runner(),
72 IPCTestBase::GetChannelName(name),
73 IPC::Channel::MODE_CLIENT, listener);
76 void Connect() {
77 CHECK(channel_->Connect());
80 void Close() {
81 channel_->Close();
83 base::RunLoop run_loop;
84 base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE,
85 run_loop.QuitClosure());
86 run_loop.Run();
89 IPC::ChannelMojo* channel() const { return channel_.get(); }
91 private:
92 base::MessageLoopForIO main_message_loop_;
93 scoped_ptr<IPC::ChannelMojo> channel_;
96 class IPCChannelMojoTestBase : public IPCTestBase {
97 public:
98 void InitWithMojo(const std::string& test_client_name) {
99 Init(test_client_name);
102 void TearDown() override {
103 // Make sure Mojo IPC support is properly shutdown on the I/O loop before
104 // TearDown continues.
105 base::RunLoop run_loop;
106 task_runner()->PostTask(FROM_HERE, run_loop.QuitClosure());
107 run_loop.Run();
109 IPCTestBase::TearDown();
113 class IPCChannelMojoTest : public IPCChannelMojoTestBase {
114 protected:
115 scoped_ptr<IPC::ChannelFactory> CreateChannelFactory(
116 const IPC::ChannelHandle& handle,
117 base::SequencedTaskRunner* runner) override {
118 host_.reset(new IPC::ChannelMojoHost(task_runner()));
119 return IPC::ChannelMojo::CreateServerFactory(host_->channel_delegate(),
120 task_runner(), handle);
123 bool DidStartClient() override {
124 bool ok = IPCTestBase::DidStartClient();
125 DCHECK(ok);
126 host_->OnClientLaunched(client_process().Handle());
127 return ok;
130 private:
131 scoped_ptr<IPC::ChannelMojoHost> host_;
135 class TestChannelListenerWithExtraExpectations
136 : public IPC::TestChannelListener {
137 public:
138 TestChannelListenerWithExtraExpectations()
139 : is_connected_called_(false) {
142 void OnChannelConnected(int32 peer_pid) override {
143 IPC::TestChannelListener::OnChannelConnected(peer_pid);
144 EXPECT_TRUE(base::kNullProcessId != peer_pid);
145 is_connected_called_ = true;
148 bool is_connected_called() const { return is_connected_called_; }
150 private:
151 bool is_connected_called_;
154 TEST_F(IPCChannelMojoTest, ConnectedFromClient) {
155 InitWithMojo("IPCChannelMojoTestClient");
157 // Set up IPC channel and start client.
158 TestChannelListenerWithExtraExpectations listener;
159 CreateChannel(&listener);
160 listener.Init(sender());
161 ASSERT_TRUE(ConnectChannel());
162 ASSERT_TRUE(StartClient());
164 IPC::TestChannelListener::SendOneMessage(
165 sender(), "hello from parent");
167 base::MessageLoop::current()->Run();
168 EXPECT_TRUE(base::kNullProcessId != this->channel()->GetPeerPID());
170 this->channel()->Close();
172 EXPECT_TRUE(WaitForClientShutdown());
173 EXPECT_TRUE(listener.is_connected_called());
174 EXPECT_TRUE(listener.HasSentAll());
176 DestroyChannel();
179 // A long running process that connects to us
180 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestClient) {
181 TestChannelListenerWithExtraExpectations listener;
182 ChannelClient client(&listener, "IPCChannelMojoTestClient");
183 client.Connect();
184 listener.Init(client.channel());
186 IPC::TestChannelListener::SendOneMessage(
187 client.channel(), "hello from child");
188 base::MessageLoop::current()->Run();
189 EXPECT_TRUE(listener.is_connected_called());
190 EXPECT_TRUE(listener.HasSentAll());
192 client.Close();
194 return 0;
197 class ListenerExpectingErrors : public IPC::Listener {
198 public:
199 ListenerExpectingErrors()
200 : has_error_(false) {
203 void OnChannelConnected(int32 peer_pid) override {
204 base::MessageLoop::current()->Quit();
207 bool OnMessageReceived(const IPC::Message& message) override { return true; }
209 void OnChannelError() override {
210 has_error_ = true;
211 base::MessageLoop::current()->Quit();
214 bool has_error() const { return has_error_; }
216 private:
217 bool has_error_;
221 class IPCChannelMojoErrorTest : public IPCChannelMojoTestBase {
222 protected:
223 scoped_ptr<IPC::ChannelFactory> CreateChannelFactory(
224 const IPC::ChannelHandle& handle,
225 base::SequencedTaskRunner* runner) override {
226 host_.reset(new IPC::ChannelMojoHost(task_runner()));
227 return IPC::ChannelMojo::CreateServerFactory(host_->channel_delegate(),
228 task_runner(), handle);
231 bool DidStartClient() override {
232 bool ok = IPCTestBase::DidStartClient();
233 DCHECK(ok);
234 host_->OnClientLaunched(client_process().Handle());
235 return ok;
238 private:
239 scoped_ptr<IPC::ChannelMojoHost> host_;
242 class ListenerThatQuits : public IPC::Listener {
243 public:
244 ListenerThatQuits() {
247 bool OnMessageReceived(const IPC::Message& message) override {
248 return true;
251 void OnChannelConnected(int32 peer_pid) override {
252 base::MessageLoop::current()->Quit();
256 // A long running process that connects to us.
257 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoErraticTestClient) {
258 ListenerThatQuits listener;
259 ChannelClient client(&listener, "IPCChannelMojoErraticTestClient");
260 client.Connect();
262 base::MessageLoop::current()->Run();
264 client.Close();
266 return 0;
269 TEST_F(IPCChannelMojoErrorTest, SendFailWithPendingMessages) {
270 InitWithMojo("IPCChannelMojoErraticTestClient");
272 // Set up IPC channel and start client.
273 ListenerExpectingErrors listener;
274 CreateChannel(&listener);
275 ASSERT_TRUE(ConnectChannel());
277 // This matches a value in mojo/edk/system/constants.h
278 const int kMaxMessageNumBytes = 4 * 1024 * 1024;
279 std::string overly_large_data(kMaxMessageNumBytes, '*');
280 // This messages are queued as pending.
281 for (size_t i = 0; i < 10; ++i) {
282 IPC::TestChannelListener::SendOneMessage(
283 sender(), overly_large_data.c_str());
286 ASSERT_TRUE(StartClient());
287 base::MessageLoop::current()->Run();
289 this->channel()->Close();
291 EXPECT_TRUE(WaitForClientShutdown());
292 EXPECT_TRUE(listener.has_error());
294 DestroyChannel();
297 struct TestingMessagePipe {
298 TestingMessagePipe() {
299 EXPECT_EQ(MOJO_RESULT_OK, mojo::CreateMessagePipe(nullptr, &self, &peer));
302 mojo::ScopedMessagePipeHandle self;
303 mojo::ScopedMessagePipeHandle peer;
306 class HandleSendingHelper {
307 public:
308 static std::string GetSendingFileContent() { return "Hello"; }
310 static void WritePipe(IPC::Message* message, TestingMessagePipe* pipe) {
311 std::string content = HandleSendingHelper::GetSendingFileContent();
312 EXPECT_EQ(MOJO_RESULT_OK,
313 mojo::WriteMessageRaw(pipe->self.get(), &content[0],
314 static_cast<uint32_t>(content.size()),
315 nullptr, 0, 0));
316 EXPECT_TRUE(
317 IPC::MojoMessageHelper::WriteMessagePipeTo(message, pipe->peer.Pass()));
320 static void WritePipeThenSend(IPC::Sender* sender, TestingMessagePipe* pipe) {
321 IPC::Message* message =
322 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
323 WritePipe(message, pipe);
324 ASSERT_TRUE(sender->Send(message));
327 static void ReadReceivedPipe(const IPC::Message& message,
328 base::PickleIterator* iter) {
329 mojo::ScopedMessagePipeHandle pipe;
330 EXPECT_TRUE(
331 IPC::MojoMessageHelper::ReadMessagePipeFrom(&message, iter, &pipe));
332 std::string content(GetSendingFileContent().size(), ' ');
334 uint32_t num_bytes = static_cast<uint32_t>(content.size());
335 EXPECT_EQ(MOJO_RESULT_OK,
336 mojo::ReadMessageRaw(pipe.get(), &content[0], &num_bytes, nullptr,
337 nullptr, 0));
338 EXPECT_EQ(content, GetSendingFileContent());
341 #if defined(OS_POSIX)
342 static base::FilePath GetSendingFilePath() {
343 base::FilePath path;
344 bool ok = PathService::Get(base::DIR_CACHE, &path);
345 EXPECT_TRUE(ok);
346 return path.Append("ListenerThatExpectsFile.txt");
349 static void WriteFile(IPC::Message* message, base::File& file) {
350 std::string content = GetSendingFileContent();
351 file.WriteAtCurrentPos(content.data(), content.size());
352 file.Flush();
353 message->WriteAttachment(new IPC::internal::PlatformFileAttachment(
354 base::ScopedFD(file.TakePlatformFile())));
357 static void WriteFileThenSend(IPC::Sender* sender, base::File& file) {
358 IPC::Message* message =
359 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
360 WriteFile(message, file);
361 ASSERT_TRUE(sender->Send(message));
364 static void WriteFileAndPipeThenSend(IPC::Sender* sender,
365 base::File& file,
366 TestingMessagePipe* pipe) {
367 IPC::Message* message =
368 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
369 WriteFile(message, file);
370 WritePipe(message, pipe);
371 ASSERT_TRUE(sender->Send(message));
374 static void ReadReceivedFile(const IPC::Message& message,
375 base::PickleIterator* iter) {
376 base::ScopedFD fd;
377 scoped_refptr<IPC::MessageAttachment> attachment;
378 EXPECT_TRUE(message.ReadAttachment(iter, &attachment));
379 base::File file(attachment->TakePlatformFile());
380 std::string content(GetSendingFileContent().size(), ' ');
381 file.Read(0, &content[0], content.size());
382 EXPECT_EQ(content, GetSendingFileContent());
384 #endif
387 class ListenerThatExpectsMessagePipe : public IPC::Listener {
388 public:
389 ListenerThatExpectsMessagePipe() : sender_(NULL) {}
391 ~ListenerThatExpectsMessagePipe() override {}
393 bool OnMessageReceived(const IPC::Message& message) override {
394 base::PickleIterator iter(message);
395 HandleSendingHelper::ReadReceivedPipe(message, &iter);
396 base::MessageLoop::current()->Quit();
397 ListenerThatExpectsOK::SendOK(sender_);
398 return true;
401 void OnChannelError() override { NOTREACHED(); }
403 void set_sender(IPC::Sender* sender) { sender_ = sender; }
405 private:
406 IPC::Sender* sender_;
409 TEST_F(IPCChannelMojoTest, SendMessagePipe) {
410 InitWithMojo("IPCChannelMojoTestSendMessagePipeClient");
412 ListenerThatExpectsOK listener;
413 CreateChannel(&listener);
414 ASSERT_TRUE(ConnectChannel());
415 ASSERT_TRUE(StartClient());
417 TestingMessagePipe pipe;
418 HandleSendingHelper::WritePipeThenSend(channel(), &pipe);
420 base::MessageLoop::current()->Run();
421 this->channel()->Close();
423 EXPECT_TRUE(WaitForClientShutdown());
424 DestroyChannel();
427 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestSendMessagePipeClient) {
428 ListenerThatExpectsMessagePipe listener;
429 ChannelClient client(&listener, "IPCChannelMojoTestSendMessagePipeClient");
430 client.Connect();
431 listener.set_sender(client.channel());
433 base::MessageLoop::current()->Run();
435 client.Close();
437 return 0;
440 void ReadOK(mojo::MessagePipeHandle pipe) {
441 std::string should_be_ok("xx");
442 uint32_t num_bytes = static_cast<uint32_t>(should_be_ok.size());
443 CHECK_EQ(MOJO_RESULT_OK,
444 mojo::ReadMessageRaw(pipe, &should_be_ok[0], &num_bytes, nullptr,
445 nullptr, 0));
446 EXPECT_EQ(should_be_ok, std::string("OK"));
449 void WriteOK(mojo::MessagePipeHandle pipe) {
450 std::string ok("OK");
451 CHECK_EQ(MOJO_RESULT_OK,
452 mojo::WriteMessageRaw(pipe, &ok[0], static_cast<uint32_t>(ok.size()),
453 nullptr, 0, 0));
456 class ListenerThatExpectsMessagePipeUsingParamTrait : public IPC::Listener {
457 public:
458 explicit ListenerThatExpectsMessagePipeUsingParamTrait(bool receiving_valid)
459 : sender_(NULL), receiving_valid_(receiving_valid) {}
461 ~ListenerThatExpectsMessagePipeUsingParamTrait() override {}
463 bool OnMessageReceived(const IPC::Message& message) override {
464 base::PickleIterator iter(message);
465 mojo::MessagePipeHandle handle;
466 EXPECT_TRUE(IPC::ParamTraits<mojo::MessagePipeHandle>::Read(&message, &iter,
467 &handle));
468 EXPECT_EQ(handle.is_valid(), receiving_valid_);
469 if (receiving_valid_) {
470 ReadOK(handle);
471 MojoClose(handle.value());
474 base::MessageLoop::current()->Quit();
475 ListenerThatExpectsOK::SendOK(sender_);
476 return true;
479 void OnChannelError() override { NOTREACHED(); }
480 void set_sender(IPC::Sender* sender) { sender_ = sender; }
482 private:
483 IPC::Sender* sender_;
484 bool receiving_valid_;
487 void ParamTraitMessagePipeClient(bool receiving_valid_handle,
488 const char* channel_name) {
489 ListenerThatExpectsMessagePipeUsingParamTrait listener(
490 receiving_valid_handle);
491 ChannelClient client(&listener, channel_name);
492 client.Connect();
493 listener.set_sender(client.channel());
495 base::MessageLoop::current()->Run();
497 client.Close();
500 TEST_F(IPCChannelMojoTest, ParamTraitValidMessagePipe) {
501 InitWithMojo("ParamTraitValidMessagePipeClient");
503 ListenerThatExpectsOK listener;
504 CreateChannel(&listener);
505 ASSERT_TRUE(ConnectChannel());
506 ASSERT_TRUE(StartClient());
508 TestingMessagePipe pipe;
510 scoped_ptr<IPC::Message> message(new IPC::Message());
511 IPC::ParamTraits<mojo::MessagePipeHandle>::Write(message.get(),
512 pipe.peer.release());
513 WriteOK(pipe.self.get());
515 this->channel()->Send(message.release());
516 base::MessageLoop::current()->Run();
517 this->channel()->Close();
519 EXPECT_TRUE(WaitForClientShutdown());
520 DestroyChannel();
523 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(ParamTraitValidMessagePipeClient) {
524 ParamTraitMessagePipeClient(true, "ParamTraitValidMessagePipeClient");
525 return 0;
528 TEST_F(IPCChannelMojoTest, ParamTraitInvalidMessagePipe) {
529 InitWithMojo("ParamTraitInvalidMessagePipeClient");
531 ListenerThatExpectsOK listener;
532 CreateChannel(&listener);
533 ASSERT_TRUE(ConnectChannel());
534 ASSERT_TRUE(StartClient());
536 mojo::MessagePipeHandle invalid_handle;
537 scoped_ptr<IPC::Message> message(new IPC::Message());
538 IPC::ParamTraits<mojo::MessagePipeHandle>::Write(message.get(),
539 invalid_handle);
541 this->channel()->Send(message.release());
542 base::MessageLoop::current()->Run();
543 this->channel()->Close();
545 EXPECT_TRUE(WaitForClientShutdown());
546 DestroyChannel();
549 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(ParamTraitInvalidMessagePipeClient) {
550 ParamTraitMessagePipeClient(false, "ParamTraitInvalidMessagePipeClient");
551 return 0;
554 #if defined(OS_WIN)
555 class IPCChannelMojoDeadHandleTest : public IPCChannelMojoTestBase {
556 protected:
557 scoped_ptr<IPC::ChannelFactory> CreateChannelFactory(
558 const IPC::ChannelHandle& handle,
559 base::SequencedTaskRunner* runner) override {
560 host_.reset(new IPC::ChannelMojoHost(task_runner()));
561 return IPC::ChannelMojo::CreateServerFactory(host_->channel_delegate(),
562 task_runner(), handle);
565 bool DidStartClient() override {
566 IPCTestBase::DidStartClient();
567 const base::ProcessHandle client = client_process().Handle();
568 // Forces GetFileHandleForProcess() fail. It happens occasionally
569 // in production, so we should exercise it somehow.
570 // TODO(morrita): figure out how to safely test this. See crbug.com/464109.
571 // ::CloseHandle(client);
572 host_->OnClientLaunched(client);
573 return true;
576 private:
577 scoped_ptr<IPC::ChannelMojoHost> host_;
580 TEST_F(IPCChannelMojoDeadHandleTest, InvalidClientHandle) {
581 // Any client type is fine as it is going to be killed anyway.
582 InitWithMojo("IPCChannelMojoTestDoNothingClient");
584 // Set up IPC channel and start client.
585 ListenerExpectingErrors listener;
586 CreateChannel(&listener);
587 ASSERT_TRUE(ConnectChannel());
589 ASSERT_TRUE(StartClient());
590 base::MessageLoop::current()->Run();
592 this->channel()->Close();
594 // TODO(morrita): We need CloseHandle() call in DidStartClient(),
595 // which has been disabled since crrev.com/843113003, to
596 // make this fail. See crbug.com/464109.
597 // EXPECT_FALSE(WaitForClientShutdown());
598 WaitForClientShutdown();
599 EXPECT_TRUE(listener.has_error());
601 DestroyChannel();
604 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestDoNothingClient) {
605 ListenerThatQuits listener;
606 ChannelClient client(&listener, "IPCChannelMojoTestDoNothingClient");
607 client.Connect();
609 // Quits without running the message loop as this client won't
610 // receive any messages from the server.
612 return 0;
614 #endif
616 #if defined(OS_POSIX)
617 class ListenerThatExpectsFile : public IPC::Listener {
618 public:
619 ListenerThatExpectsFile()
620 : sender_(NULL) {}
622 ~ListenerThatExpectsFile() override {}
624 bool OnMessageReceived(const IPC::Message& message) override {
625 base::PickleIterator iter(message);
626 HandleSendingHelper::ReadReceivedFile(message, &iter);
627 base::MessageLoop::current()->Quit();
628 ListenerThatExpectsOK::SendOK(sender_);
629 return true;
632 void OnChannelError() override {
633 NOTREACHED();
636 void set_sender(IPC::Sender* sender) { sender_ = sender; }
638 private:
639 IPC::Sender* sender_;
643 TEST_F(IPCChannelMojoTest, SendPlatformHandle) {
644 InitWithMojo("IPCChannelMojoTestSendPlatformHandleClient");
646 ListenerThatExpectsOK listener;
647 CreateChannel(&listener);
648 ASSERT_TRUE(ConnectChannel());
649 ASSERT_TRUE(StartClient());
651 base::File file(HandleSendingHelper::GetSendingFilePath(),
652 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE |
653 base::File::FLAG_READ);
654 HandleSendingHelper::WriteFileThenSend(channel(), file);
655 base::MessageLoop::current()->Run();
657 this->channel()->Close();
659 EXPECT_TRUE(WaitForClientShutdown());
660 DestroyChannel();
663 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestSendPlatformHandleClient) {
664 ListenerThatExpectsFile listener;
665 ChannelClient client(
666 &listener, "IPCChannelMojoTestSendPlatformHandleClient");
667 client.Connect();
668 listener.set_sender(client.channel());
670 base::MessageLoop::current()->Run();
672 client.Close();
674 return 0;
677 class ListenerThatExpectsFileAndPipe : public IPC::Listener {
678 public:
679 ListenerThatExpectsFileAndPipe() : sender_(NULL) {}
681 ~ListenerThatExpectsFileAndPipe() override {}
683 bool OnMessageReceived(const IPC::Message& message) override {
684 base::PickleIterator iter(message);
685 HandleSendingHelper::ReadReceivedFile(message, &iter);
686 HandleSendingHelper::ReadReceivedPipe(message, &iter);
687 base::MessageLoop::current()->Quit();
688 ListenerThatExpectsOK::SendOK(sender_);
689 return true;
692 void OnChannelError() override { NOTREACHED(); }
694 void set_sender(IPC::Sender* sender) { sender_ = sender; }
696 private:
697 IPC::Sender* sender_;
700 TEST_F(IPCChannelMojoTest, SendPlatformHandleAndPipe) {
701 InitWithMojo("IPCChannelMojoTestSendPlatformHandleAndPipeClient");
703 ListenerThatExpectsOK listener;
704 CreateChannel(&listener);
705 ASSERT_TRUE(ConnectChannel());
706 ASSERT_TRUE(StartClient());
708 base::File file(HandleSendingHelper::GetSendingFilePath(),
709 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE |
710 base::File::FLAG_READ);
711 TestingMessagePipe pipe;
712 HandleSendingHelper::WriteFileAndPipeThenSend(channel(), file, &pipe);
714 base::MessageLoop::current()->Run();
715 this->channel()->Close();
717 EXPECT_TRUE(WaitForClientShutdown());
718 DestroyChannel();
721 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(
722 IPCChannelMojoTestSendPlatformHandleAndPipeClient) {
723 ListenerThatExpectsFileAndPipe listener;
724 ChannelClient client(&listener,
725 "IPCChannelMojoTestSendPlatformHandleAndPipeClient");
726 client.Connect();
727 listener.set_sender(client.channel());
729 base::MessageLoop::current()->Run();
731 client.Close();
733 return 0;
736 #endif
738 #if defined(OS_LINUX)
740 const base::ProcessId kMagicChildId = 54321;
742 class ListenerThatVerifiesPeerPid : public IPC::Listener {
743 public:
744 void OnChannelConnected(int32 peer_pid) override {
745 EXPECT_EQ(peer_pid, kMagicChildId);
746 base::MessageLoop::current()->Quit();
749 bool OnMessageReceived(const IPC::Message& message) override {
750 NOTREACHED();
751 return true;
755 TEST_F(IPCChannelMojoTest, VerifyGlobalPid) {
756 InitWithMojo("IPCChannelMojoTestVerifyGlobalPidClient");
758 ListenerThatVerifiesPeerPid listener;
759 CreateChannel(&listener);
760 ASSERT_TRUE(ConnectChannel());
761 ASSERT_TRUE(StartClient());
763 base::MessageLoop::current()->Run();
764 channel()->Close();
766 EXPECT_TRUE(WaitForClientShutdown());
767 DestroyChannel();
770 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestVerifyGlobalPidClient) {
771 IPC::Channel::SetGlobalPid(kMagicChildId);
772 ListenerThatQuits listener;
773 ChannelClient client(&listener,
774 "IPCChannelMojoTestVerifyGlobalPidClient");
775 client.Connect();
777 base::MessageLoop::current()->Run();
779 client.Close();
781 return 0;
784 #endif // OS_LINUX
786 } // namespace