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

Side by Side Diff: mojo/edk/embedder/embedder_unittest.cc

Issue 774673003: Added MojoNewWait and MojoNewWaitMany, along with unit tests. (Closed) Base URL: https://github.com/domokit/mojo.git@master
Patch Set: Created 6 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | mojo/edk/embedder/entrypoints.cc » ('j') | mojo/public/c/system/functions.h » ('J')
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
viettrungluu 2014/12/02 17:24:55 The same comments as for core_unittest.cc ("below"
jimbe 2014/12/02 19:21:18 Done.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "mojo/edk/embedder/embedder.h" 5 #include "mojo/edk/embedder/embedder.h"
6 6
7 #include <string.h> 7 #include <string.h>
8 8
9 #include "base/bind.h" 9 #include "base/bind.h"
10 #include "base/location.h" 10 #include "base/location.h"
11 #include "base/logging.h" 11 #include "base/logging.h"
(...skipping 478 matching lines...) Expand 10 before | Expand all | Expand 10 after
490 490
491 EXPECT_TRUE(test::Shutdown()); 491 EXPECT_TRUE(test::Shutdown());
492 } 492 }
493 493
494 // TODO(vtl): Test immediate write & close. 494 // TODO(vtl): Test immediate write & close.
495 // TODO(vtl): Test broken-connection cases. 495 // TODO(vtl): Test broken-connection cases.
496 496
497 } // namespace 497 } // namespace
498 } // namespace embedder 498 } // namespace embedder
499 } // namespace mojo 499 } // namespace mojo
500
501 // TODO(jimbe) Remove code above and rename calls to wait below.
502
503 namespace mojo {
504 namespace embedder {
505 namespace new_wait {
506
507 const MojoHandleSignals MOJO_HANDLE_SIGNAL_READWRITABLE =
508 MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE;
509
510 const MojoHandleSignals MOJO_HANDLE_SIGNAL_ALL = MOJO_HANDLE_SIGNAL_READABLE |
511 MOJO_HANDLE_SIGNAL_WRITABLE |
512 MOJO_HANDLE_SIGNAL_PEER_CLOSED;
513
514 class ScopedTestChannel {
515 public:
516 // Creates a channel that lives on a given I/O thread (determined by the given
517 // |TaskRunner|) attached to the given |platform_handle|. After construction,
518 // |bootstrap_message_pipe()| gives the Mojo handle for the bootstrap message
519 // pipe on this channel; it is up to the caller to close this handle.
520 // Note: The I/O thread must outlive this object (and its message loop must
521 // continue pumping messages while this object is alive).
522 ScopedTestChannel(scoped_refptr<base::TaskRunner> io_thread_task_runner,
523 ScopedPlatformHandle platform_handle)
524 : io_thread_task_runner_(io_thread_task_runner),
525 bootstrap_message_pipe_(MOJO_HANDLE_INVALID),
526 did_create_channel_event_(true, false),
527 channel_info_(nullptr) {
528 bootstrap_message_pipe_ =
529 CreateChannel(platform_handle.Pass(), io_thread_task_runner_,
530 base::Bind(&ScopedTestChannel::DidCreateChannel,
531 base::Unretained(this)),
532 nullptr)
533 .release()
534 .value();
535 CHECK_NE(bootstrap_message_pipe_, MOJO_HANDLE_INVALID);
536 }
537
538 // Destructor: Shuts down the channel. (As noted above, for this to happen,
539 // the I/O thread must be alive and pumping messages.)
540 ~ScopedTestChannel() { DestroyChannel(channel_info_); }
541
542 // Waits for channel creation to be completed.
543 void WaitForChannelCreationCompletion() { did_create_channel_event_.Wait(); }
544
545 MojoHandle bootstrap_message_pipe() const { return bootstrap_message_pipe_; }
546
547 // Call only after |WaitForChannelCreationCompletion()|. Use only to check
548 // that it's not null.
549 const ChannelInfo* channel_info() const { return channel_info_; }
550
551 private:
552 void DidCreateChannel(ChannelInfo* channel_info) {
553 CHECK(channel_info);
554 CHECK(!channel_info_);
555 channel_info_ = channel_info;
556 did_create_channel_event_.Signal();
557 }
558
559 scoped_refptr<base::TaskRunner> io_thread_task_runner_;
560
561 // Valid from creation until whenever it gets closed (by the "owner" of this
562 // object).
563 // Note: We don't want use the C++ wrappers here, since we want to test the
564 // API at the lowest level.
565 MojoHandle bootstrap_message_pipe_;
566
567 // Set after channel creation has been completed (i.e., the callback to
568 // |CreateChannel()| has been called).
569 base::WaitableEvent did_create_channel_event_;
570
571 // Valid after channel creation completion until destruction.
572 ChannelInfo* channel_info_;
573
574 DISALLOW_COPY_AND_ASSIGN(ScopedTestChannel);
575 };
576
577 class NewEmbedderTest : public testing::Test {
578 public:
579 NewEmbedderTest() : test_io_thread_(base::TestIOThread::kAutoStart) {}
580 ~NewEmbedderTest() override {}
581
582 protected:
583 base::TestIOThread* test_io_thread() { return &test_io_thread_; }
584
585 private:
586 base::TestIOThread test_io_thread_;
587
588 DISALLOW_COPY_AND_ASSIGN(NewEmbedderTest);
589 };
590
591 TEST_F(NewEmbedderTest, ChannelsBasic) {
592 mojo::embedder::test::InitWithSimplePlatformSupport();
593
594 {
595 PlatformChannelPair channel_pair;
596 ScopedTestChannel server_channel(test_io_thread()->task_runner(),
597 channel_pair.PassServerHandle());
598 MojoHandle server_mp = server_channel.bootstrap_message_pipe();
599 EXPECT_NE(server_mp, MOJO_HANDLE_INVALID);
600 ScopedTestChannel client_channel(test_io_thread()->task_runner(),
601 channel_pair.PassClientHandle());
602 MojoHandle client_mp = client_channel.bootstrap_message_pipe();
603 EXPECT_NE(client_mp, MOJO_HANDLE_INVALID);
604
605 // We can write to a message pipe handle immediately.
606 const char kHello[] = "hello";
607 EXPECT_EQ(MOJO_RESULT_OK,
608 MojoWriteMessage(server_mp, kHello,
609 static_cast<uint32_t>(sizeof(kHello)), nullptr,
610 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
611
612 // Now wait for the other side to become readable.
613 MojoHandleSignalsState state;
614 EXPECT_EQ(MOJO_RESULT_OK,
615 MojoNewWait(client_mp, MOJO_HANDLE_SIGNAL_READABLE,
616 MOJO_DEADLINE_INDEFINITE, &state));
617 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
618 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
619
620 char buffer[1000] = {};
621 uint32_t num_bytes = static_cast<uint32_t>(sizeof(buffer));
622 EXPECT_EQ(MOJO_RESULT_OK,
623 MojoReadMessage(client_mp, buffer, &num_bytes, nullptr, nullptr,
624 MOJO_READ_MESSAGE_FLAG_NONE));
625 EXPECT_EQ(sizeof(kHello), num_bytes);
626 EXPECT_STREQ(kHello, buffer);
627
628 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(server_mp));
629 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(client_mp));
630
631 // By this point, these waits should basically be no-ops (since we've waited
632 // for the client message pipe to become readable, which implies that both
633 // the server and client channels were completely created).
634 server_channel.WaitForChannelCreationCompletion();
635 client_channel.WaitForChannelCreationCompletion();
636 EXPECT_TRUE(server_channel.channel_info());
637 EXPECT_TRUE(client_channel.channel_info());
638 }
639
640 EXPECT_TRUE(test::Shutdown());
641 }
642
643 TEST_F(NewEmbedderTest, ChannelsHandlePassing) {
644 mojo::embedder::test::InitWithSimplePlatformSupport();
645
646 {
647 PlatformChannelPair channel_pair;
648 ScopedTestChannel server_channel(test_io_thread()->task_runner(),
649 channel_pair.PassServerHandle());
650 MojoHandle server_mp = server_channel.bootstrap_message_pipe();
651 EXPECT_NE(server_mp, MOJO_HANDLE_INVALID);
652 ScopedTestChannel client_channel(test_io_thread()->task_runner(),
653 channel_pair.PassClientHandle());
654 MojoHandle client_mp = client_channel.bootstrap_message_pipe();
655 EXPECT_NE(client_mp, MOJO_HANDLE_INVALID);
656
657 MojoHandle h0, h1;
658 EXPECT_EQ(MOJO_RESULT_OK, MojoCreateMessagePipe(nullptr, &h0, &h1));
659
660 // Write a message to |h0| (attaching nothing).
661 const char kHello[] = "hello";
662 EXPECT_EQ(
663 MOJO_RESULT_OK,
664 MojoWriteMessage(h0, kHello, static_cast<uint32_t>(sizeof(kHello)),
665 nullptr, 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
666
667 // Write one message to |server_mp|, attaching |h1|.
668 const char kWorld[] = "world!!!";
669 EXPECT_EQ(MOJO_RESULT_OK,
670 MojoWriteMessage(server_mp, kWorld,
671 static_cast<uint32_t>(sizeof(kWorld)), &h1, 1,
672 MOJO_WRITE_MESSAGE_FLAG_NONE));
673 h1 = MOJO_HANDLE_INVALID;
674
675 // Write another message to |h0|.
676 const char kFoo[] = "foo";
677 EXPECT_EQ(MOJO_RESULT_OK,
678 MojoWriteMessage(h0, kFoo, static_cast<uint32_t>(sizeof(kFoo)),
679 nullptr, 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
680
681 // Wait for |client_mp| to become readable.
682 MojoHandleSignalsState state;
683 EXPECT_EQ(MOJO_RESULT_OK,
684 MojoNewWait(client_mp, MOJO_HANDLE_SIGNAL_READABLE,
685 MOJO_DEADLINE_INDEFINITE, &state));
686 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
687 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
688
689 // Read a message from |client_mp|.
690 char buffer[1000] = {};
691 uint32_t num_bytes = static_cast<uint32_t>(sizeof(buffer));
692 MojoHandle handles[10] = {};
693 uint32_t num_handles = arraysize(handles);
694 EXPECT_EQ(MOJO_RESULT_OK,
695 MojoReadMessage(client_mp, buffer, &num_bytes, handles,
696 &num_handles, MOJO_READ_MESSAGE_FLAG_NONE));
697 EXPECT_EQ(sizeof(kWorld), num_bytes);
698 EXPECT_STREQ(kWorld, buffer);
699 EXPECT_EQ(1u, num_handles);
700 EXPECT_NE(handles[0], MOJO_HANDLE_INVALID);
701 h1 = handles[0];
702
703 // Wait for |h1| to become readable.
704 EXPECT_EQ(MOJO_RESULT_OK, MojoNewWait(h1, MOJO_HANDLE_SIGNAL_READABLE,
705 MOJO_DEADLINE_INDEFINITE, &state));
706 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
707 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
708
709 // Read a message from |h1|.
710 memset(buffer, 0, sizeof(buffer));
711 num_bytes = static_cast<uint32_t>(sizeof(buffer));
712 memset(handles, 0, sizeof(handles));
713 num_handles = arraysize(handles);
714 EXPECT_EQ(MOJO_RESULT_OK,
715 MojoReadMessage(h1, buffer, &num_bytes, handles, &num_handles,
716 MOJO_READ_MESSAGE_FLAG_NONE));
717 EXPECT_EQ(sizeof(kHello), num_bytes);
718 EXPECT_STREQ(kHello, buffer);
719 EXPECT_EQ(0u, num_handles);
720
721 // Wait for |h1| to become readable (again).
722 EXPECT_EQ(MOJO_RESULT_OK, MojoNewWait(h1, MOJO_HANDLE_SIGNAL_READABLE,
723 MOJO_DEADLINE_INDEFINITE, &state));
724 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
725 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
726
727 // Read the second message from |h1|.
728 memset(buffer, 0, sizeof(buffer));
729 num_bytes = static_cast<uint32_t>(sizeof(buffer));
730 EXPECT_EQ(MOJO_RESULT_OK,
731 MojoReadMessage(h1, buffer, &num_bytes, nullptr, nullptr,
732 MOJO_READ_MESSAGE_FLAG_NONE));
733 EXPECT_EQ(sizeof(kFoo), num_bytes);
734 EXPECT_STREQ(kFoo, buffer);
735
736 // Write a message to |h1|.
737 const char kBarBaz[] = "barbaz";
738 EXPECT_EQ(
739 MOJO_RESULT_OK,
740 MojoWriteMessage(h1, kBarBaz, static_cast<uint32_t>(sizeof(kBarBaz)),
741 nullptr, 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
742
743 // Wait for |h0| to become readable.
744 EXPECT_EQ(MOJO_RESULT_OK, MojoNewWait(h0, MOJO_HANDLE_SIGNAL_READABLE,
745 MOJO_DEADLINE_INDEFINITE, &state));
746 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
747 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
748
749 // Read a message from |h0|.
750 memset(buffer, 0, sizeof(buffer));
751 num_bytes = static_cast<uint32_t>(sizeof(buffer));
752 EXPECT_EQ(MOJO_RESULT_OK,
753 MojoReadMessage(h0, buffer, &num_bytes, nullptr, nullptr,
754 MOJO_READ_MESSAGE_FLAG_NONE));
755 EXPECT_EQ(sizeof(kBarBaz), num_bytes);
756 EXPECT_STREQ(kBarBaz, buffer);
757
758 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(server_mp));
759 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(client_mp));
760 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(h0));
761 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(h1));
762
763 server_channel.WaitForChannelCreationCompletion();
764 client_channel.WaitForChannelCreationCompletion();
765 EXPECT_TRUE(server_channel.channel_info());
766 EXPECT_TRUE(client_channel.channel_info());
767 }
768
769 EXPECT_TRUE(test::Shutdown());
770 }
771
772 // The sequence of messages sent is:
773 // server_mp client_mp mp0 mp1 mp2 mp3
774 // 1. "hello"
775 // 2. "world!"
776 // 3. "FOO"
777 // 4. "Bar"+mp1
778 // 5. (close)
779 // 6. (close)
780 // 7. "baz"
781 // 8. (closed)
782 // 9. "quux"+mp2
783 // 10. (close)
784 // 11. (wait/cl.)
785 // 12. (wait/cl.)
786 TEST_F(NewEmbedderTest, MultiprocessChannels) {
787 mojo::embedder::test::InitWithSimplePlatformSupport();
788 mojo::test::MultiprocessTestHelper multiprocess_test_helper;
789 multiprocess_test_helper.StartChild("MultiprocessChannelsClient");
790
791 {
792 ScopedTestChannel server_channel(
793 test_io_thread()->task_runner(),
794 multiprocess_test_helper.server_platform_handle.Pass());
795 MojoHandle server_mp = server_channel.bootstrap_message_pipe();
796 EXPECT_NE(server_mp, MOJO_HANDLE_INVALID);
797 server_channel.WaitForChannelCreationCompletion();
798 EXPECT_TRUE(server_channel.channel_info());
799
800 // 1. Write a message to |server_mp| (attaching nothing).
801 const char kHello[] = "hello";
802 EXPECT_EQ(MOJO_RESULT_OK,
803 MojoWriteMessage(server_mp, kHello,
804 static_cast<uint32_t>(sizeof(kHello)), nullptr,
805 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
806
807 // TODO(vtl): If the scope were ended immediately here (maybe after closing
808 // |server_mp|), we die with a fatal error in |Channel::HandleLocalError()|.
809
810 // 2. Read a message from |server_mp|.
811 MojoHandleSignalsState state;
812 EXPECT_EQ(MOJO_RESULT_OK,
813 MojoNewWait(server_mp, MOJO_HANDLE_SIGNAL_READABLE,
814 MOJO_DEADLINE_INDEFINITE, &state));
815 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
816 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
817
818 char buffer[1000] = {};
819 uint32_t num_bytes = static_cast<uint32_t>(sizeof(buffer));
820 EXPECT_EQ(MOJO_RESULT_OK,
821 MojoReadMessage(server_mp, buffer, &num_bytes, nullptr, nullptr,
822 MOJO_READ_MESSAGE_FLAG_NONE));
823 const char kWorld[] = "world!";
824 EXPECT_EQ(sizeof(kWorld), num_bytes);
825 EXPECT_STREQ(kWorld, buffer);
826
827 // Create a new message pipe (endpoints |mp0| and |mp1|).
828 MojoHandle mp0, mp1;
829 EXPECT_EQ(MOJO_RESULT_OK, MojoCreateMessagePipe(nullptr, &mp0, &mp1));
830
831 // 3. Write something to |mp0|.
832 const char kFoo[] = "FOO";
833 EXPECT_EQ(MOJO_RESULT_OK,
834 MojoWriteMessage(mp0, kFoo, static_cast<uint32_t>(sizeof(kFoo)),
835 nullptr, 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
836
837 // 4. Write a message to |server_mp|, attaching |mp1|.
838 const char kBar[] = "Bar";
839 EXPECT_EQ(
840 MOJO_RESULT_OK,
841 MojoWriteMessage(server_mp, kBar, static_cast<uint32_t>(sizeof(kBar)),
842 &mp1, 1, MOJO_WRITE_MESSAGE_FLAG_NONE));
843 mp1 = MOJO_HANDLE_INVALID;
844
845 // 5. Close |server_mp|.
846 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(server_mp));
847
848 // 9. Read a message from |mp0|, which should have |mp2| attached.
849 EXPECT_EQ(MOJO_RESULT_OK, MojoNewWait(mp0, MOJO_HANDLE_SIGNAL_READABLE,
850 MOJO_DEADLINE_INDEFINITE, &state));
851 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
852 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
853
854 memset(buffer, 0, sizeof(buffer));
855 num_bytes = static_cast<uint32_t>(sizeof(buffer));
856 MojoHandle mp2 = MOJO_HANDLE_INVALID;
857 uint32_t num_handles = 1;
858 EXPECT_EQ(MOJO_RESULT_OK,
859 MojoReadMessage(mp0, buffer, &num_bytes, &mp2, &num_handles,
860 MOJO_READ_MESSAGE_FLAG_NONE));
861 const char kQuux[] = "quux";
862 EXPECT_EQ(sizeof(kQuux), num_bytes);
863 EXPECT_STREQ(kQuux, buffer);
864 EXPECT_EQ(1u, num_handles);
865 EXPECT_NE(mp2, MOJO_HANDLE_INVALID);
866
867 // 7. Read a message from |mp2|.
868 EXPECT_EQ(MOJO_RESULT_OK, MojoNewWait(mp2, MOJO_HANDLE_SIGNAL_READABLE,
869 MOJO_DEADLINE_INDEFINITE, &state));
870 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED,
871 state.satisfied_signals);
872 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED,
873 state.satisfiable_signals);
874
875 memset(buffer, 0, sizeof(buffer));
876 num_bytes = static_cast<uint32_t>(sizeof(buffer));
877 EXPECT_EQ(MOJO_RESULT_OK,
878 MojoReadMessage(mp2, buffer, &num_bytes, nullptr, nullptr,
879 MOJO_READ_MESSAGE_FLAG_NONE));
880 const char kBaz[] = "baz";
881 EXPECT_EQ(sizeof(kBaz), num_bytes);
882 EXPECT_STREQ(kBaz, buffer);
883
884 // 10. Close |mp0|.
885 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(mp0));
886
887 // 12. Wait on |mp2| (which should eventually fail) and then close it.
888 // TODO(vtl): crbug.com/351768
889 #if 0
890 EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
891 MojoNewWait(mp2, MOJO_HANDLE_SIGNAL_READABLE,
892 MOJO_DEADLINE_INDEFINITE,
893 &state));
894 EXPECT_EQ(MOJO_HANDLE_SIGNAL_NONE, state.satisfied_signals);
895 EXPECT_EQ(MOJO_HANDLE_SIGNAL_NONE, state.satisfiable_signals);
896 #endif
897 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(mp2));
898 }
899
900 EXPECT_TRUE(multiprocess_test_helper.WaitForChildTestShutdown());
901 EXPECT_TRUE(test::Shutdown());
902 }
903
904 MOJO_MULTIPROCESS_TEST_CHILD_TEST(MultiprocessChannelsClient) {
905 ScopedPlatformHandle client_platform_handle =
906 mojo::test::MultiprocessTestHelper::client_platform_handle.Pass();
907 EXPECT_TRUE(client_platform_handle.is_valid());
908
909 base::TestIOThread test_io_thread(base::TestIOThread::kAutoStart);
910 mojo::embedder::test::InitWithSimplePlatformSupport();
911
912 {
913 ScopedTestChannel client_channel(test_io_thread.task_runner(),
914 client_platform_handle.Pass());
915 MojoHandle client_mp = client_channel.bootstrap_message_pipe();
916 EXPECT_NE(client_mp, MOJO_HANDLE_INVALID);
917 client_channel.WaitForChannelCreationCompletion();
918 CHECK(client_channel.channel_info() != nullptr);
919
920 // 1. Read the first message from |client_mp|.
921 MojoHandleSignalsState state;
922 EXPECT_EQ(MOJO_RESULT_OK,
923 MojoNewWait(client_mp, MOJO_HANDLE_SIGNAL_READABLE,
924 MOJO_DEADLINE_INDEFINITE, &state));
925 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
926 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
927
928 char buffer[1000] = {};
929 uint32_t num_bytes = static_cast<uint32_t>(sizeof(buffer));
930 EXPECT_EQ(MOJO_RESULT_OK,
931 MojoReadMessage(client_mp, buffer, &num_bytes, nullptr, nullptr,
932 MOJO_READ_MESSAGE_FLAG_NONE));
933 const char kHello[] = "hello";
934 EXPECT_EQ(sizeof(kHello), num_bytes);
935 EXPECT_STREQ(kHello, buffer);
936
937 // 2. Write a message to |client_mp| (attaching nothing).
938 const char kWorld[] = "world!";
939 EXPECT_EQ(MOJO_RESULT_OK,
940 MojoWriteMessage(client_mp, kWorld,
941 static_cast<uint32_t>(sizeof(kWorld)), nullptr,
942 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
943
944 // 4. Read a message from |client_mp|, which should have |mp1| attached.
945 EXPECT_EQ(MOJO_RESULT_OK,
946 MojoNewWait(client_mp, MOJO_HANDLE_SIGNAL_READABLE,
947 MOJO_DEADLINE_INDEFINITE, &state));
948 // The other end of the handle may or may not be closed at this point, so we
949 // can't test MOJO_HANDLE_SIGNAL_WRITABLE or MOJO_HANDLE_SIGNAL_PEER_CLOSED.
950 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE,
951 state.satisfied_signals & MOJO_HANDLE_SIGNAL_READABLE);
952 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE,
953 state.satisfiable_signals & MOJO_HANDLE_SIGNAL_READABLE);
954 // TODO(vtl): If the scope were to end here (and |client_mp| closed), we'd
955 // die (again due to |Channel::HandleLocalError()|).
956 memset(buffer, 0, sizeof(buffer));
957 num_bytes = static_cast<uint32_t>(sizeof(buffer));
958 MojoHandle mp1 = MOJO_HANDLE_INVALID;
959 uint32_t num_handles = 1;
960 EXPECT_EQ(MOJO_RESULT_OK,
961 MojoReadMessage(client_mp, buffer, &num_bytes, &mp1, &num_handles,
962 MOJO_READ_MESSAGE_FLAG_NONE));
963 const char kBar[] = "Bar";
964 EXPECT_EQ(sizeof(kBar), num_bytes);
965 EXPECT_STREQ(kBar, buffer);
966 EXPECT_EQ(1u, num_handles);
967 EXPECT_NE(mp1, MOJO_HANDLE_INVALID);
968 // TODO(vtl): If the scope were to end here (and the two handles closed),
969 // we'd die due to |Channel::RunRemoteMessagePipeEndpoint()| not handling
970 // write errors (assuming the parent had closed the pipe).
971
972 // 6. Close |client_mp|.
973 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(client_mp));
974
975 // Create a new message pipe (endpoints |mp2| and |mp3|).
976 MojoHandle mp2, mp3;
977 EXPECT_EQ(MOJO_RESULT_OK, MojoCreateMessagePipe(nullptr, &mp2, &mp3));
978
979 // 7. Write a message to |mp3|.
980 const char kBaz[] = "baz";
981 EXPECT_EQ(MOJO_RESULT_OK,
982 MojoWriteMessage(mp3, kBaz, static_cast<uint32_t>(sizeof(kBaz)),
983 nullptr, 0, MOJO_WRITE_MESSAGE_FLAG_NONE));
984
985 // 8. Close |mp3|.
986 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(mp3));
987
988 // 9. Write a message to |mp1|, attaching |mp2|.
989 const char kQuux[] = "quux";
990 EXPECT_EQ(MOJO_RESULT_OK,
991 MojoWriteMessage(mp1, kQuux, static_cast<uint32_t>(sizeof(kQuux)),
992 &mp2, 1, MOJO_WRITE_MESSAGE_FLAG_NONE));
993 mp2 = MOJO_HANDLE_INVALID;
994
995 // 3. Read a message from |mp1|.
996 EXPECT_EQ(MOJO_RESULT_OK, MojoNewWait(mp1, MOJO_HANDLE_SIGNAL_READABLE,
997 MOJO_DEADLINE_INDEFINITE, &state));
998 EXPECT_EQ(MOJO_HANDLE_SIGNAL_READWRITABLE, state.satisfied_signals);
999 EXPECT_EQ(MOJO_HANDLE_SIGNAL_ALL, state.satisfiable_signals);
1000
1001 memset(buffer, 0, sizeof(buffer));
1002 num_bytes = static_cast<uint32_t>(sizeof(buffer));
1003 EXPECT_EQ(MOJO_RESULT_OK,
1004 MojoReadMessage(mp1, buffer, &num_bytes, nullptr, nullptr,
1005 MOJO_READ_MESSAGE_FLAG_NONE));
1006 const char kFoo[] = "FOO";
1007 EXPECT_EQ(sizeof(kFoo), num_bytes);
1008 EXPECT_STREQ(kFoo, buffer);
1009
1010 // 11. Wait on |mp1| (which should eventually fail) and then close it.
1011 EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION,
1012 MojoNewWait(mp1, MOJO_HANDLE_SIGNAL_READABLE,
1013 MOJO_DEADLINE_INDEFINITE, &state));
1014 EXPECT_EQ(MOJO_HANDLE_SIGNAL_PEER_CLOSED, state.satisfied_signals);
1015 EXPECT_EQ(MOJO_HANDLE_SIGNAL_PEER_CLOSED, state.satisfiable_signals);
1016 EXPECT_EQ(MOJO_RESULT_OK, MojoClose(mp1));
1017 }
1018
1019 EXPECT_TRUE(test::Shutdown());
1020 }
1021
1022 // TODO(vtl): Test immediate write & close.
1023 // TODO(vtl): Test broken-connection cases.
1024
1025 } // namespace
1026 } // namespace embedder
1027 } // namespace mojo
1028
1029 // End TODO(jimbe)
OLDNEW
« no previous file with comments | « no previous file | mojo/edk/embedder/entrypoints.cc » ('j') | mojo/public/c/system/functions.h » ('J')

Powered by Google App Engine
This is Rietveld 408576698