Add ICU message format support
[chromium-blink-merge.git] / ipc / mojo / ipc_channel_mojo_unittest.cc
blobc82e0119d4177a265ed18bb71a9b66244a9ac987
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_mojo_handle_attachment.h"
21 #include "ipc/mojo/ipc_mojo_message_helper.h"
22 #include "ipc/mojo/ipc_mojo_param_traits.h"
23 #include "ipc/mojo/scoped_ipc_support.h"
25 #if defined(OS_POSIX)
26 #include "base/file_descriptor_posix.h"
27 #include "ipc/ipc_platform_file_attachment_posix.h"
28 #endif
30 namespace {
32 class ListenerThatExpectsOK : public IPC::Listener {
33 public:
34 ListenerThatExpectsOK()
35 : received_ok_(false) {}
37 ~ListenerThatExpectsOK() override {}
39 bool OnMessageReceived(const IPC::Message& message) override {
40 base::PickleIterator iter(message);
41 std::string should_be_ok;
42 EXPECT_TRUE(iter.ReadString(&should_be_ok));
43 EXPECT_EQ(should_be_ok, "OK");
44 received_ok_ = true;
45 base::MessageLoop::current()->Quit();
46 return true;
49 void OnChannelError() override {
50 // The connection should be healthy while the listener is waiting
51 // message. An error can occur after that because the peer
52 // process dies.
53 DCHECK(received_ok_);
56 static void SendOK(IPC::Sender* sender) {
57 IPC::Message* message = new IPC::Message(
58 0, 2, IPC::Message::PRIORITY_NORMAL);
59 message->WriteString(std::string("OK"));
60 ASSERT_TRUE(sender->Send(message));
63 private:
64 bool received_ok_;
67 class ChannelClient {
68 public:
69 explicit ChannelClient(IPC::Listener* listener, const char* name) {
70 channel_ = IPC::ChannelMojo::Create(
71 main_message_loop_.task_runner(), IPCTestBase::GetChannelName(name),
72 IPC::Channel::MODE_CLIENT, listener, nullptr);
75 void Connect() {
76 CHECK(channel_->Connect());
79 void Close() {
80 channel_->Close();
82 base::RunLoop run_loop;
83 base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE,
84 run_loop.QuitClosure());
85 run_loop.Run();
88 IPC::ChannelMojo* channel() const { return channel_.get(); }
90 private:
91 base::MessageLoopForIO main_message_loop_;
92 scoped_ptr<IPC::ChannelMojo> channel_;
95 class IPCChannelMojoTestBase : public IPCTestBase {
96 public:
97 void InitWithMojo(const std::string& test_client_name) {
98 Init(test_client_name);
101 void TearDown() override {
102 // Make sure Mojo IPC support is properly shutdown on the I/O loop before
103 // TearDown continues.
104 base::RunLoop run_loop;
105 task_runner()->PostTask(FROM_HERE, run_loop.QuitClosure());
106 run_loop.Run();
108 IPCTestBase::TearDown();
112 class IPCChannelMojoTest : public IPCChannelMojoTestBase {
113 protected:
114 scoped_ptr<IPC::ChannelFactory> CreateChannelFactory(
115 const IPC::ChannelHandle& handle,
116 base::SequencedTaskRunner* runner) override {
117 return IPC::ChannelMojo::CreateServerFactory(task_runner(), handle,
118 nullptr);
121 bool DidStartClient() override {
122 bool ok = IPCTestBase::DidStartClient();
123 DCHECK(ok);
124 return ok;
129 class TestChannelListenerWithExtraExpectations
130 : public IPC::TestChannelListener {
131 public:
132 TestChannelListenerWithExtraExpectations()
133 : is_connected_called_(false) {
136 void OnChannelConnected(int32 peer_pid) override {
137 IPC::TestChannelListener::OnChannelConnected(peer_pid);
138 EXPECT_TRUE(base::kNullProcessId != peer_pid);
139 is_connected_called_ = true;
142 bool is_connected_called() const { return is_connected_called_; }
144 private:
145 bool is_connected_called_;
148 // Times out on Android; see http://crbug.com/502290
149 #if defined(OS_ANDROID)
150 #define MAYBE_ConnectedFromClient DISABLED_ConnectedFromClient
151 #else
152 #define MAYBE_ConnectedFromClient ConnectedFromClient
153 #endif
154 TEST_F(IPCChannelMojoTest, MAYBE_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 return IPC::ChannelMojo::CreateServerFactory(task_runner(), handle,
227 nullptr);
230 bool DidStartClient() override {
231 bool ok = IPCTestBase::DidStartClient();
232 DCHECK(ok);
233 return ok;
237 class ListenerThatQuits : public IPC::Listener {
238 public:
239 ListenerThatQuits() {
242 bool OnMessageReceived(const IPC::Message& message) override {
243 return true;
246 void OnChannelConnected(int32 peer_pid) override {
247 base::MessageLoop::current()->Quit();
251 // A long running process that connects to us.
252 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoErraticTestClient) {
253 ListenerThatQuits listener;
254 ChannelClient client(&listener, "IPCChannelMojoErraticTestClient");
255 client.Connect();
257 base::MessageLoop::current()->Run();
259 client.Close();
261 return 0;
264 // Times out on Android; see http://crbug.com/502290
265 #if defined(OS_ANDROID)
266 #define MAYBE_SendFailWithPendingMessages DISABLED_SendFailWithPendingMessages
267 #else
268 #define MAYBE_SendFailWithPendingMessages SendFailWithPendingMessages
269 #endif
270 TEST_F(IPCChannelMojoErrorTest, MAYBE_SendFailWithPendingMessages) {
271 InitWithMojo("IPCChannelMojoErraticTestClient");
273 // Set up IPC channel and start client.
274 ListenerExpectingErrors listener;
275 CreateChannel(&listener);
276 ASSERT_TRUE(ConnectChannel());
278 // This matches a value in mojo/edk/system/constants.h
279 const int kMaxMessageNumBytes = 4 * 1024 * 1024;
280 std::string overly_large_data(kMaxMessageNumBytes, '*');
281 // This messages are queued as pending.
282 for (size_t i = 0; i < 10; ++i) {
283 IPC::TestChannelListener::SendOneMessage(
284 sender(), overly_large_data.c_str());
287 ASSERT_TRUE(StartClient());
288 base::MessageLoop::current()->Run();
290 this->channel()->Close();
292 EXPECT_TRUE(WaitForClientShutdown());
293 EXPECT_TRUE(listener.has_error());
295 DestroyChannel();
298 struct TestingMessagePipe {
299 TestingMessagePipe() {
300 EXPECT_EQ(MOJO_RESULT_OK, mojo::CreateMessagePipe(nullptr, &self, &peer));
303 mojo::ScopedMessagePipeHandle self;
304 mojo::ScopedMessagePipeHandle peer;
307 class HandleSendingHelper {
308 public:
309 static std::string GetSendingFileContent() { return "Hello"; }
311 static void WritePipe(IPC::Message* message, TestingMessagePipe* pipe) {
312 std::string content = HandleSendingHelper::GetSendingFileContent();
313 EXPECT_EQ(MOJO_RESULT_OK,
314 mojo::WriteMessageRaw(pipe->self.get(), &content[0],
315 static_cast<uint32_t>(content.size()),
316 nullptr, 0, 0));
317 EXPECT_TRUE(
318 IPC::MojoMessageHelper::WriteMessagePipeTo(message, pipe->peer.Pass()));
321 static void WritePipeThenSend(IPC::Sender* sender, TestingMessagePipe* pipe) {
322 IPC::Message* message =
323 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
324 WritePipe(message, pipe);
325 ASSERT_TRUE(sender->Send(message));
328 static void ReadReceivedPipe(const IPC::Message& message,
329 base::PickleIterator* iter) {
330 mojo::ScopedMessagePipeHandle pipe;
331 EXPECT_TRUE(
332 IPC::MojoMessageHelper::ReadMessagePipeFrom(&message, iter, &pipe));
333 std::string content(GetSendingFileContent().size(), ' ');
335 uint32_t num_bytes = static_cast<uint32_t>(content.size());
336 EXPECT_EQ(MOJO_RESULT_OK,
337 mojo::ReadMessageRaw(pipe.get(), &content[0], &num_bytes, nullptr,
338 nullptr, 0));
339 EXPECT_EQ(content, GetSendingFileContent());
342 #if defined(OS_POSIX)
343 static base::FilePath GetSendingFilePath() {
344 base::FilePath path;
345 bool ok = PathService::Get(base::DIR_CACHE, &path);
346 EXPECT_TRUE(ok);
347 return path.Append("ListenerThatExpectsFile.txt");
350 static void WriteFile(IPC::Message* message, base::File& file) {
351 std::string content = GetSendingFileContent();
352 file.WriteAtCurrentPos(content.data(), content.size());
353 file.Flush();
354 message->WriteAttachment(new IPC::internal::PlatformFileAttachment(
355 base::ScopedFD(file.TakePlatformFile())));
358 static void WriteFileThenSend(IPC::Sender* sender, base::File& file) {
359 IPC::Message* message =
360 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
361 WriteFile(message, file);
362 ASSERT_TRUE(sender->Send(message));
365 static void WriteFileAndPipeThenSend(IPC::Sender* sender,
366 base::File& file,
367 TestingMessagePipe* pipe) {
368 IPC::Message* message =
369 new IPC::Message(0, 2, IPC::Message::PRIORITY_NORMAL);
370 WriteFile(message, file);
371 WritePipe(message, pipe);
372 ASSERT_TRUE(sender->Send(message));
375 static void ReadReceivedFile(const IPC::Message& message,
376 base::PickleIterator* iter) {
377 base::ScopedFD fd;
378 scoped_refptr<IPC::MessageAttachment> attachment;
379 EXPECT_TRUE(message.ReadAttachment(iter, &attachment));
380 base::File file(attachment->TakePlatformFile());
381 std::string content(GetSendingFileContent().size(), ' ');
382 file.Read(0, &content[0], content.size());
383 EXPECT_EQ(content, GetSendingFileContent());
385 #endif
388 class ListenerThatExpectsMessagePipe : public IPC::Listener {
389 public:
390 ListenerThatExpectsMessagePipe() : sender_(NULL) {}
392 ~ListenerThatExpectsMessagePipe() override {}
394 bool OnMessageReceived(const IPC::Message& message) override {
395 base::PickleIterator iter(message);
396 HandleSendingHelper::ReadReceivedPipe(message, &iter);
397 base::MessageLoop::current()->Quit();
398 ListenerThatExpectsOK::SendOK(sender_);
399 return true;
402 void OnChannelError() override { NOTREACHED(); }
404 void set_sender(IPC::Sender* sender) { sender_ = sender; }
406 private:
407 IPC::Sender* sender_;
410 // Times out on Android; see http://crbug.com/502290
411 #if defined(OS_ANDROID)
412 #define MAYBE_SendMessagePipe DISABLED_SendMessagePipe
413 #else
414 #define MAYBE_SendMessagePipe SendMessagePipe
415 #endif
416 TEST_F(IPCChannelMojoTest, MAYBE_SendMessagePipe) {
417 InitWithMojo("IPCChannelMojoTestSendMessagePipeClient");
419 ListenerThatExpectsOK listener;
420 CreateChannel(&listener);
421 ASSERT_TRUE(ConnectChannel());
422 ASSERT_TRUE(StartClient());
424 TestingMessagePipe pipe;
425 HandleSendingHelper::WritePipeThenSend(channel(), &pipe);
427 base::MessageLoop::current()->Run();
428 this->channel()->Close();
430 EXPECT_TRUE(WaitForClientShutdown());
431 DestroyChannel();
434 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestSendMessagePipeClient) {
435 ListenerThatExpectsMessagePipe listener;
436 ChannelClient client(&listener, "IPCChannelMojoTestSendMessagePipeClient");
437 client.Connect();
438 listener.set_sender(client.channel());
440 base::MessageLoop::current()->Run();
442 client.Close();
444 return 0;
447 void ReadOK(mojo::MessagePipeHandle pipe) {
448 std::string should_be_ok("xx");
449 uint32_t num_bytes = static_cast<uint32_t>(should_be_ok.size());
450 CHECK_EQ(MOJO_RESULT_OK,
451 mojo::ReadMessageRaw(pipe, &should_be_ok[0], &num_bytes, nullptr,
452 nullptr, 0));
453 EXPECT_EQ(should_be_ok, std::string("OK"));
456 void WriteOK(mojo::MessagePipeHandle pipe) {
457 std::string ok("OK");
458 CHECK_EQ(MOJO_RESULT_OK,
459 mojo::WriteMessageRaw(pipe, &ok[0], static_cast<uint32_t>(ok.size()),
460 nullptr, 0, 0));
463 class ListenerThatExpectsMessagePipeUsingParamTrait : public IPC::Listener {
464 public:
465 explicit ListenerThatExpectsMessagePipeUsingParamTrait(bool receiving_valid)
466 : sender_(NULL), receiving_valid_(receiving_valid) {}
468 ~ListenerThatExpectsMessagePipeUsingParamTrait() override {}
470 bool OnMessageReceived(const IPC::Message& message) override {
471 base::PickleIterator iter(message);
472 mojo::MessagePipeHandle handle;
473 EXPECT_TRUE(IPC::ParamTraits<mojo::MessagePipeHandle>::Read(&message, &iter,
474 &handle));
475 EXPECT_EQ(handle.is_valid(), receiving_valid_);
476 if (receiving_valid_) {
477 ReadOK(handle);
478 MojoClose(handle.value());
481 base::MessageLoop::current()->Quit();
482 ListenerThatExpectsOK::SendOK(sender_);
483 return true;
486 void OnChannelError() override { NOTREACHED(); }
487 void set_sender(IPC::Sender* sender) { sender_ = sender; }
489 private:
490 IPC::Sender* sender_;
491 bool receiving_valid_;
494 void ParamTraitMessagePipeClient(bool receiving_valid_handle,
495 const char* channel_name) {
496 ListenerThatExpectsMessagePipeUsingParamTrait listener(
497 receiving_valid_handle);
498 ChannelClient client(&listener, channel_name);
499 client.Connect();
500 listener.set_sender(client.channel());
502 base::MessageLoop::current()->Run();
504 client.Close();
507 // Times out on Android; see http://crbug.com/502290
508 #if defined(OS_ANDROID)
509 #define MAYBE_ParamTraitValidMessagePipe DISABLED_ParamTraitValidMessagePipe
510 #else
511 #define MAYBE_ParamTraitValidMessagePipe ParamTraitValidMessagePipe
512 #endif
513 TEST_F(IPCChannelMojoTest, MAYBE_ParamTraitValidMessagePipe) {
514 InitWithMojo("ParamTraitValidMessagePipeClient");
516 ListenerThatExpectsOK listener;
517 CreateChannel(&listener);
518 ASSERT_TRUE(ConnectChannel());
519 ASSERT_TRUE(StartClient());
521 TestingMessagePipe pipe;
523 scoped_ptr<IPC::Message> message(new IPC::Message());
524 IPC::ParamTraits<mojo::MessagePipeHandle>::Write(message.get(),
525 pipe.peer.release());
526 WriteOK(pipe.self.get());
528 this->channel()->Send(message.release());
529 base::MessageLoop::current()->Run();
530 this->channel()->Close();
532 EXPECT_TRUE(WaitForClientShutdown());
533 DestroyChannel();
536 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(ParamTraitValidMessagePipeClient) {
537 ParamTraitMessagePipeClient(true, "ParamTraitValidMessagePipeClient");
538 return 0;
541 // Times out on Android; see http://crbug.com/502290
542 #if defined(OS_ANDROID)
543 #define MAYBE_ParamTraitInvalidMessagePipe DISABLED_ParamTraitInvalidMessagePipe
544 #else
545 #define MAYBE_ParamTraitInvalidMessagePipe ParamTraitInvalidMessagePipe
546 #endif
547 TEST_F(IPCChannelMojoTest, MAYBE_ParamTraitInvalidMessagePipe) {
548 InitWithMojo("ParamTraitInvalidMessagePipeClient");
550 ListenerThatExpectsOK listener;
551 CreateChannel(&listener);
552 ASSERT_TRUE(ConnectChannel());
553 ASSERT_TRUE(StartClient());
555 mojo::MessagePipeHandle invalid_handle;
556 scoped_ptr<IPC::Message> message(new IPC::Message());
557 IPC::ParamTraits<mojo::MessagePipeHandle>::Write(message.get(),
558 invalid_handle);
560 this->channel()->Send(message.release());
561 base::MessageLoop::current()->Run();
562 this->channel()->Close();
564 EXPECT_TRUE(WaitForClientShutdown());
565 DestroyChannel();
568 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(ParamTraitInvalidMessagePipeClient) {
569 ParamTraitMessagePipeClient(false, "ParamTraitInvalidMessagePipeClient");
570 return 0;
573 TEST_F(IPCChannelMojoTest, SendFailAfterClose) {
574 InitWithMojo("IPCChannelMojoTestSendOkClient");
576 ListenerThatExpectsOK listener;
577 CreateChannel(&listener);
578 ASSERT_TRUE(ConnectChannel());
579 ASSERT_TRUE(StartClient());
581 base::MessageLoop::current()->Run();
582 this->channel()->Close();
583 ASSERT_FALSE(this->channel()->Send(new IPC::Message()));
585 EXPECT_TRUE(WaitForClientShutdown());
586 DestroyChannel();
589 class ListenerSendingOneOk : public IPC::Listener {
590 public:
591 ListenerSendingOneOk() {
594 bool OnMessageReceived(const IPC::Message& message) override {
595 return true;
598 void OnChannelConnected(int32 peer_pid) override {
599 ListenerThatExpectsOK::SendOK(sender_);
600 base::MessageLoop::current()->Quit();
603 void set_sender(IPC::Sender* sender) { sender_ = sender; }
605 private:
606 IPC::Sender* sender_;
609 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestSendOkClient) {
610 ListenerSendingOneOk listener;
611 ChannelClient client(&listener, "IPCChannelMojoTestSendOkClient");
612 client.Connect();
613 listener.set_sender(client.channel());
615 base::MessageLoop::current()->Run();
617 client.Close();
619 return 0;
622 #if defined(OS_WIN)
623 class IPCChannelMojoDeadHandleTest : public IPCChannelMojoTestBase {
624 protected:
625 scoped_ptr<IPC::ChannelFactory> CreateChannelFactory(
626 const IPC::ChannelHandle& handle,
627 base::SequencedTaskRunner* runner) override {
628 return IPC::ChannelMojo::CreateServerFactory(task_runner(), handle,
629 nullptr);
632 bool DidStartClient() override {
633 IPCTestBase::DidStartClient();
634 // const base::ProcessHandle client = client_process().Handle();
635 // Forces GetFileHandleForProcess() fail. It happens occasionally
636 // in production, so we should exercise it somehow.
637 // TODO(morrita): figure out how to safely test this. See crbug.com/464109.
638 // ::CloseHandle(client);
639 return true;
643 TEST_F(IPCChannelMojoDeadHandleTest, InvalidClientHandle) {
644 // Any client type is fine as it is going to be killed anyway.
645 InitWithMojo("IPCChannelMojoTestDoNothingClient");
647 // Set up IPC channel and start client.
648 ListenerExpectingErrors listener;
649 CreateChannel(&listener);
650 ASSERT_TRUE(ConnectChannel());
652 ASSERT_TRUE(StartClient());
653 base::MessageLoop::current()->Run();
655 this->channel()->Close();
657 // TODO(morrita): We need CloseHandle() call in DidStartClient(),
658 // which has been disabled since crrev.com/843113003, to
659 // make this fail. See crbug.com/464109.
660 // EXPECT_FALSE(WaitForClientShutdown());
661 WaitForClientShutdown();
662 EXPECT_TRUE(listener.has_error());
664 DestroyChannel();
667 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestDoNothingClient) {
668 ListenerThatQuits listener;
669 ChannelClient client(&listener, "IPCChannelMojoTestDoNothingClient");
670 client.Connect();
672 // Quits without running the message loop as this client won't
673 // receive any messages from the server.
675 return 0;
677 #endif
679 #if defined(OS_POSIX)
680 class ListenerThatExpectsFile : public IPC::Listener {
681 public:
682 ListenerThatExpectsFile()
683 : sender_(NULL) {}
685 ~ListenerThatExpectsFile() override {}
687 bool OnMessageReceived(const IPC::Message& message) override {
688 base::PickleIterator iter(message);
689 HandleSendingHelper::ReadReceivedFile(message, &iter);
690 base::MessageLoop::current()->Quit();
691 ListenerThatExpectsOK::SendOK(sender_);
692 return true;
695 void OnChannelError() override {
696 NOTREACHED();
699 void set_sender(IPC::Sender* sender) { sender_ = sender; }
701 private:
702 IPC::Sender* sender_;
705 // Times out on Android; see http://crbug.com/502290
706 #if defined(OS_ANDROID)
707 #define MAYBE_SendPlatformHandle DISABLED_SendPlatformHandle
708 #else
709 #define MAYBE_SendPlatformHandle SendPlatformHandle
710 #endif
711 TEST_F(IPCChannelMojoTest, MAYBE_SendPlatformHandle) {
712 InitWithMojo("IPCChannelMojoTestSendPlatformHandleClient");
714 ListenerThatExpectsOK listener;
715 CreateChannel(&listener);
716 ASSERT_TRUE(ConnectChannel());
717 ASSERT_TRUE(StartClient());
719 base::File file(HandleSendingHelper::GetSendingFilePath(),
720 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE |
721 base::File::FLAG_READ);
722 HandleSendingHelper::WriteFileThenSend(channel(), file);
723 base::MessageLoop::current()->Run();
725 this->channel()->Close();
727 EXPECT_TRUE(WaitForClientShutdown());
728 DestroyChannel();
731 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestSendPlatformHandleClient) {
732 ListenerThatExpectsFile listener;
733 ChannelClient client(
734 &listener, "IPCChannelMojoTestSendPlatformHandleClient");
735 client.Connect();
736 listener.set_sender(client.channel());
738 base::MessageLoop::current()->Run();
740 client.Close();
742 return 0;
745 class ListenerThatExpectsFileAndPipe : public IPC::Listener {
746 public:
747 ListenerThatExpectsFileAndPipe() : sender_(NULL) {}
749 ~ListenerThatExpectsFileAndPipe() override {}
751 bool OnMessageReceived(const IPC::Message& message) override {
752 base::PickleIterator iter(message);
753 HandleSendingHelper::ReadReceivedFile(message, &iter);
754 HandleSendingHelper::ReadReceivedPipe(message, &iter);
755 base::MessageLoop::current()->Quit();
756 ListenerThatExpectsOK::SendOK(sender_);
757 return true;
760 void OnChannelError() override { NOTREACHED(); }
762 void set_sender(IPC::Sender* sender) { sender_ = sender; }
764 private:
765 IPC::Sender* sender_;
768 // Times out on Android; see http://crbug.com/502290
769 #if defined(OS_ANDROID)
770 #define MAYBE_SendPlatformHandleAndPipe DISABLED_SendPlatformHandleAndPipe
771 #else
772 #define MAYBE_SendPlatformHandleAndPipe SendPlatformHandleAndPipe
773 #endif
774 TEST_F(IPCChannelMojoTest, MAYBE_SendPlatformHandleAndPipe) {
775 InitWithMojo("IPCChannelMojoTestSendPlatformHandleAndPipeClient");
777 ListenerThatExpectsOK listener;
778 CreateChannel(&listener);
779 ASSERT_TRUE(ConnectChannel());
780 ASSERT_TRUE(StartClient());
782 base::File file(HandleSendingHelper::GetSendingFilePath(),
783 base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE |
784 base::File::FLAG_READ);
785 TestingMessagePipe pipe;
786 HandleSendingHelper::WriteFileAndPipeThenSend(channel(), file, &pipe);
788 base::MessageLoop::current()->Run();
789 this->channel()->Close();
791 EXPECT_TRUE(WaitForClientShutdown());
792 DestroyChannel();
795 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(
796 IPCChannelMojoTestSendPlatformHandleAndPipeClient) {
797 ListenerThatExpectsFileAndPipe listener;
798 ChannelClient client(&listener,
799 "IPCChannelMojoTestSendPlatformHandleAndPipeClient");
800 client.Connect();
801 listener.set_sender(client.channel());
803 base::MessageLoop::current()->Run();
805 client.Close();
807 return 0;
810 #endif
812 #if defined(OS_LINUX)
814 const base::ProcessId kMagicChildId = 54321;
816 class ListenerThatVerifiesPeerPid : public IPC::Listener {
817 public:
818 void OnChannelConnected(int32 peer_pid) override {
819 EXPECT_EQ(peer_pid, kMagicChildId);
820 base::MessageLoop::current()->Quit();
823 bool OnMessageReceived(const IPC::Message& message) override {
824 NOTREACHED();
825 return true;
829 TEST_F(IPCChannelMojoTest, VerifyGlobalPid) {
830 InitWithMojo("IPCChannelMojoTestVerifyGlobalPidClient");
832 ListenerThatVerifiesPeerPid listener;
833 CreateChannel(&listener);
834 ASSERT_TRUE(ConnectChannel());
835 ASSERT_TRUE(StartClient());
837 base::MessageLoop::current()->Run();
838 channel()->Close();
840 EXPECT_TRUE(WaitForClientShutdown());
841 DestroyChannel();
844 MULTIPROCESS_IPC_TEST_CLIENT_MAIN(IPCChannelMojoTestVerifyGlobalPidClient) {
845 IPC::Channel::SetGlobalPid(kMagicChildId);
846 ListenerThatQuits listener;
847 ChannelClient client(&listener,
848 "IPCChannelMojoTestVerifyGlobalPidClient");
849 client.Connect();
851 base::MessageLoop::current()->Run();
853 client.Close();
855 return 0;
858 #endif // OS_LINUX
860 } // namespace