| OLD | NEW |
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "mojo/public/cpp/bindings/allocation_scope.h" | 5 #include "mojo/public/cpp/bindings/allocation_scope.h" |
| 6 #include "mojo/public/cpp/bindings/remote_ptr.h" | 6 #include "mojo/public/cpp/bindings/tests/test_bindings_utils.h" |
| 7 #include "mojo/public/cpp/environment/environment.h" | 7 #include "mojo/public/cpp/environment/environment.h" |
| 8 #include "mojo/public/cpp/test_support/test_utils.h" | 8 #include "mojo/public/cpp/test_support/test_utils.h" |
| 9 #include "mojo/public/cpp/utility/run_loop.h" | 9 #include "mojo/public/cpp/utility/run_loop.h" |
| 10 #include "mojo/public/interfaces/bindings/tests/sample_factory.mojom.h" | 10 #include "mojo/public/interfaces/bindings/tests/sample_factory.mojom.h" |
| 11 #include "testing/gtest/include/gtest/gtest.h" | 11 #include "testing/gtest/include/gtest/gtest.h" |
| 12 | 12 |
| 13 namespace mojo { | 13 namespace mojo { |
| 14 namespace test { | 14 namespace test { |
| 15 namespace { | 15 namespace { |
| 16 | 16 |
| 17 const char kText1[] = "hello"; | 17 const char kText1[] = "hello"; |
| 18 const char kText2[] = "world"; | 18 const char kText2[] = "world"; |
| 19 | 19 |
| 20 class SampleFactoryImpl : public sample::Factory { | 20 class SampleFactoryImpl : public sample::Factory { |
| 21 public: | 21 public: |
| 22 explicit SampleFactoryImpl(sample::ScopedFactoryClientHandle handle) | 22 virtual void SetClient(sample::FactoryClient* client) MOJO_OVERRIDE { |
| 23 : client_(handle.Pass(), this) { | 23 client_ = client; |
| 24 } | 24 } |
| 25 | 25 |
| 26 virtual void DoStuff(const sample::Request& request, | 26 virtual void DoStuff(const sample::Request& request, |
| 27 ScopedMessagePipeHandle pipe) MOJO_OVERRIDE { | 27 ScopedMessagePipeHandle pipe) MOJO_OVERRIDE { |
| 28 std::string text1; | 28 std::string text1; |
| 29 if (pipe.is_valid()) | 29 if (pipe.is_valid()) |
| 30 EXPECT_TRUE(ReadTextMessage(pipe.get(), &text1)); | 30 EXPECT_TRUE(ReadTextMessage(pipe.get(), &text1)); |
| 31 | 31 |
| 32 std::string text2; | 32 std::string text2; |
| 33 if (request.pipe().is_valid()) { | 33 if (request.pipe().is_valid()) { |
| (...skipping 29 matching lines...) Expand all Loading... |
| 63 ASSERT_LT(static_cast<int>(data_size), 64); | 63 ASSERT_LT(static_cast<int>(data_size), 64); |
| 64 ASSERT_EQ(MOJO_RESULT_OK, | 64 ASSERT_EQ(MOJO_RESULT_OK, |
| 65 ReadDataRaw(pipe.get(), data, &data_size, | 65 ReadDataRaw(pipe.get(), data, &data_size, |
| 66 MOJO_READ_DATA_FLAG_ALL_OR_NONE)); | 66 MOJO_READ_DATA_FLAG_ALL_OR_NONE)); |
| 67 | 67 |
| 68 AllocationScope scope; | 68 AllocationScope scope; |
| 69 client_->DidStuff2(String(std::string(data))); | 69 client_->DidStuff2(String(std::string(data))); |
| 70 } | 70 } |
| 71 | 71 |
| 72 private: | 72 private: |
| 73 RemotePtr<sample::FactoryClient> client_; | 73 sample::FactoryClient* client_; |
| 74 ScopedMessagePipeHandle pipe1_; | 74 ScopedMessagePipeHandle pipe1_; |
| 75 }; | 75 }; |
| 76 | 76 |
| 77 class SampleFactoryClientImpl : public sample::FactoryClient { | 77 class SampleFactoryClientImpl : public sample::FactoryClient { |
| 78 public: | 78 public: |
| 79 explicit SampleFactoryClientImpl(sample::ScopedFactoryHandle handle) | 79 SampleFactoryClientImpl() : got_response_(false) { |
| 80 : factory_(handle.Pass(), this), | |
| 81 got_response_(false) { | |
| 82 } | 80 } |
| 83 | 81 |
| 84 void Start() { | 82 void set_expected_text_reply(const std::string& expected_text_reply) { |
| 85 expected_text_reply_ = kText1; | 83 expected_text_reply_ = expected_text_reply; |
| 86 | |
| 87 ScopedMessagePipeHandle pipe0; | |
| 88 CreateMessagePipe(&pipe0, &pipe1_); | |
| 89 | |
| 90 EXPECT_TRUE(WriteTextMessage(pipe1_.get(), kText1)); | |
| 91 | |
| 92 ScopedMessagePipeHandle pipe2; | |
| 93 CreateMessagePipe(&pipe2, &pipe3_); | |
| 94 | |
| 95 EXPECT_TRUE(WriteTextMessage(pipe3_.get(), kText2)); | |
| 96 | |
| 97 AllocationScope scope; | |
| 98 sample::Request::Builder request; | |
| 99 request.set_x(1); | |
| 100 request.set_pipe(pipe2.Pass()); | |
| 101 factory_->DoStuff(request.Finish(), pipe0.Pass()); | |
| 102 } | |
| 103 | |
| 104 void StartNoPipes() { | |
| 105 expected_text_reply_.clear(); | |
| 106 | |
| 107 AllocationScope scope; | |
| 108 sample::Request::Builder request; | |
| 109 request.set_x(1); | |
| 110 factory_->DoStuff(request.Finish(), ScopedMessagePipeHandle().Pass()); | |
| 111 } | |
| 112 | |
| 113 // Writes a string to a data pipe and passes the data pipe (consumer) to the | |
| 114 // factory. | |
| 115 void StartDataPipe() { | |
| 116 expected_text_reply_.clear(); | |
| 117 | |
| 118 ScopedDataPipeProducerHandle producer_handle; | |
| 119 ScopedDataPipeConsumerHandle consumer_handle; | |
| 120 MojoCreateDataPipeOptions options = { | |
| 121 sizeof(MojoCreateDataPipeOptions), | |
| 122 MOJO_CREATE_DATA_PIPE_OPTIONS_FLAG_NONE, | |
| 123 1, | |
| 124 1024}; | |
| 125 ASSERT_EQ(MOJO_RESULT_OK, | |
| 126 CreateDataPipe(&options, &producer_handle, &consumer_handle)); | |
| 127 expected_text_reply_ = "got it"; | |
| 128 // +1 for \0. | |
| 129 uint32_t data_size = static_cast<uint32_t>(expected_text_reply_.size() + 1); | |
| 130 ASSERT_EQ(MOJO_RESULT_OK, | |
| 131 WriteDataRaw(producer_handle.get(), expected_text_reply_.c_str(), | |
| 132 &data_size, MOJO_WRITE_DATA_FLAG_ALL_OR_NONE)); | |
| 133 | |
| 134 AllocationScope scope; | |
| 135 factory_->DoStuff2(consumer_handle.Pass()); | |
| 136 } | 84 } |
| 137 | 85 |
| 138 bool got_response() const { | 86 bool got_response() const { |
| 139 return got_response_; | 87 return got_response_; |
| 140 } | 88 } |
| 141 | 89 |
| 142 virtual void DidStuff(const sample::Response& response, | 90 virtual void DidStuff(const sample::Response& response, |
| 143 const String& text_reply) MOJO_OVERRIDE { | 91 const String& text_reply) MOJO_OVERRIDE { |
| 144 EXPECT_EQ(expected_text_reply_, text_reply.To<std::string>()); | 92 EXPECT_EQ(expected_text_reply_, text_reply.To<std::string>()); |
| 145 | 93 |
| (...skipping 14 matching lines...) Expand all Loading... |
| 160 | 108 |
| 161 got_response_ = true; | 109 got_response_ = true; |
| 162 } | 110 } |
| 163 | 111 |
| 164 virtual void DidStuff2(const String& text_reply) MOJO_OVERRIDE { | 112 virtual void DidStuff2(const String& text_reply) MOJO_OVERRIDE { |
| 165 got_response_ = true; | 113 got_response_ = true; |
| 166 EXPECT_EQ(expected_text_reply_, text_reply.To<std::string>()); | 114 EXPECT_EQ(expected_text_reply_, text_reply.To<std::string>()); |
| 167 } | 115 } |
| 168 | 116 |
| 169 private: | 117 private: |
| 170 RemotePtr<sample::Factory> factory_; | |
| 171 ScopedMessagePipeHandle pipe1_; | 118 ScopedMessagePipeHandle pipe1_; |
| 172 ScopedMessagePipeHandle pipe3_; | 119 ScopedMessagePipeHandle pipe3_; |
| 173 std::string expected_text_reply_; | 120 std::string expected_text_reply_; |
| 174 bool got_response_; | 121 bool got_response_; |
| 175 }; | 122 }; |
| 176 | 123 |
| 177 class HandlePassingTest : public testing::Test { | 124 class HandlePassingTest : public testing::Test { |
| 178 public: | 125 public: |
| 126 virtual void TearDown() { |
| 127 PumpMessages(); |
| 128 } |
| 129 |
| 179 void PumpMessages() { | 130 void PumpMessages() { |
| 180 loop_.RunUntilIdle(); | 131 loop_.RunUntilIdle(); |
| 181 } | 132 } |
| 182 | 133 |
| 183 private: | 134 private: |
| 184 Environment env_; | 135 Environment env_; |
| 185 RunLoop loop_; | 136 RunLoop loop_; |
| 186 }; | 137 }; |
| 187 | 138 |
| 188 TEST_F(HandlePassingTest, Basic) { | 139 TEST_F(HandlePassingTest, Basic) { |
| 189 InterfacePipe<sample::Factory> pipe; | 140 sample::FactoryPtr factory; |
| 141 MakeRemote(new SampleFactoryImpl(), &factory); |
| 190 | 142 |
| 191 SampleFactoryImpl factory(pipe.handle_to_peer.Pass()); | 143 SampleFactoryClientImpl factory_client; |
| 192 SampleFactoryClientImpl factory_client(pipe.handle_to_self.Pass()); | 144 factory_client.set_expected_text_reply(kText1); |
| 193 | 145 |
| 194 factory_client.Start(); | 146 factory->SetClient(&factory_client); |
| 147 |
| 148 ScopedMessagePipeHandle pipe0, pipe1; |
| 149 CreateMessagePipe(&pipe0, &pipe1); |
| 150 |
| 151 EXPECT_TRUE(WriteTextMessage(pipe1.get(), kText1)); |
| 152 |
| 153 ScopedMessagePipeHandle pipe2, pipe3; |
| 154 CreateMessagePipe(&pipe2, &pipe3); |
| 155 |
| 156 EXPECT_TRUE(WriteTextMessage(pipe3.get(), kText2)); |
| 157 |
| 158 { |
| 159 AllocationScope scope; |
| 160 sample::Request::Builder request; |
| 161 request.set_x(1); |
| 162 request.set_pipe(pipe2.Pass()); |
| 163 factory->DoStuff(request.Finish(), pipe0.Pass()); |
| 164 } |
| 195 | 165 |
| 196 EXPECT_FALSE(factory_client.got_response()); | 166 EXPECT_FALSE(factory_client.got_response()); |
| 197 | 167 |
| 198 PumpMessages(); | 168 PumpMessages(); |
| 199 | 169 |
| 200 EXPECT_TRUE(factory_client.got_response()); | 170 EXPECT_TRUE(factory_client.got_response()); |
| 201 } | 171 } |
| 202 | 172 |
| 203 TEST_F(HandlePassingTest, PassInvalid) { | 173 TEST_F(HandlePassingTest, PassInvalid) { |
| 204 InterfacePipe<sample::Factory> pipe; | 174 sample::FactoryPtr factory; |
| 175 MakeRemote(new SampleFactoryImpl(), &factory); |
| 205 | 176 |
| 206 SampleFactoryImpl factory(pipe.handle_to_peer.Pass()); | 177 SampleFactoryClientImpl factory_client; |
| 207 SampleFactoryClientImpl factory_client(pipe.handle_to_self.Pass()); | 178 factory->SetClient(&factory_client); |
| 208 | 179 |
| 209 factory_client.StartNoPipes(); | 180 { |
| 181 AllocationScope scope; |
| 182 sample::Request::Builder request; |
| 183 request.set_x(1); |
| 184 factory->DoStuff(request.Finish(), ScopedMessagePipeHandle().Pass()); |
| 185 } |
| 210 | 186 |
| 211 EXPECT_FALSE(factory_client.got_response()); | 187 EXPECT_FALSE(factory_client.got_response()); |
| 212 | 188 |
| 213 PumpMessages(); | 189 PumpMessages(); |
| 214 | 190 |
| 215 EXPECT_TRUE(factory_client.got_response()); | 191 EXPECT_TRUE(factory_client.got_response()); |
| 216 } | 192 } |
| 217 | 193 |
| 218 // Verifies DataPipeConsumer can be passed and read from. | 194 // Verifies DataPipeConsumer can be passed and read from. |
| 219 TEST_F(HandlePassingTest, DataPipe) { | 195 TEST_F(HandlePassingTest, DataPipe) { |
| 220 InterfacePipe<sample::Factory> pipe; | 196 sample::FactoryPtr factory; |
| 197 MakeRemote(new SampleFactoryImpl(), &factory); |
| 221 | 198 |
| 222 SampleFactoryImpl factory(pipe.handle_to_peer.Pass()); | 199 SampleFactoryClientImpl factory_client; |
| 223 SampleFactoryClientImpl factory_client(pipe.handle_to_self.Pass()); | 200 factory->SetClient(&factory_client); |
| 224 | 201 |
| 225 ASSERT_NO_FATAL_FAILURE(factory_client.StartDataPipe()); | 202 // Writes a string to a data pipe and passes the data pipe (consumer) to the |
| 203 // factory. |
| 204 ScopedDataPipeProducerHandle producer_handle; |
| 205 ScopedDataPipeConsumerHandle consumer_handle; |
| 206 MojoCreateDataPipeOptions options = { |
| 207 sizeof(MojoCreateDataPipeOptions), |
| 208 MOJO_CREATE_DATA_PIPE_OPTIONS_FLAG_NONE, |
| 209 1, |
| 210 1024}; |
| 211 ASSERT_EQ(MOJO_RESULT_OK, |
| 212 CreateDataPipe(&options, &producer_handle, &consumer_handle)); |
| 213 std::string expected_text_reply = "got it"; |
| 214 factory_client.set_expected_text_reply(expected_text_reply); |
| 215 // +1 for \0. |
| 216 uint32_t data_size = static_cast<uint32_t>(expected_text_reply.size() + 1); |
| 217 ASSERT_EQ(MOJO_RESULT_OK, |
| 218 WriteDataRaw(producer_handle.get(), expected_text_reply.c_str(), |
| 219 &data_size, MOJO_WRITE_DATA_FLAG_ALL_OR_NONE)); |
| 220 |
| 221 { |
| 222 AllocationScope scope; |
| 223 factory->DoStuff2(consumer_handle.Pass()); |
| 224 } |
| 226 | 225 |
| 227 EXPECT_FALSE(factory_client.got_response()); | 226 EXPECT_FALSE(factory_client.got_response()); |
| 228 | 227 |
| 229 PumpMessages(); | 228 PumpMessages(); |
| 230 | 229 |
| 231 EXPECT_TRUE(factory_client.got_response()); | 230 EXPECT_TRUE(factory_client.got_response()); |
| 232 } | 231 } |
| 233 | 232 |
| 234 TEST_F(HandlePassingTest, PipesAreClosed) { | 233 TEST_F(HandlePassingTest, PipesAreClosed) { |
| 235 InterfacePipe<sample::Factory> pipe; | 234 sample::FactoryPtr factory; |
| 236 RemotePtr<sample::Factory> factory(pipe.handle_to_self.Pass(), NULL); | 235 MakeRemote(new SampleFactoryImpl(), &factory); |
| 236 |
| 237 SampleFactoryClientImpl factory_client; |
| 238 factory->SetClient(&factory_client); |
| 237 | 239 |
| 238 MessagePipe extra_pipe; | 240 MessagePipe extra_pipe; |
| 239 | 241 |
| 240 MojoHandle handle0_value = extra_pipe.handle0.get().value(); | 242 MojoHandle handle0_value = extra_pipe.handle0.get().value(); |
| 241 MojoHandle handle1_value = extra_pipe.handle1.get().value(); | 243 MojoHandle handle1_value = extra_pipe.handle1.get().value(); |
| 242 | 244 |
| 243 { | 245 { |
| 244 AllocationScope scope; | 246 AllocationScope scope; |
| 245 | 247 |
| 246 Array<MessagePipeHandle>::Builder pipes(2); | 248 Array<MessagePipeHandle>::Builder pipes(2); |
| (...skipping 13 matching lines...) Expand all Loading... |
| 260 } | 262 } |
| 261 | 263 |
| 262 // We expect the pipes to have been closed. | 264 // We expect the pipes to have been closed. |
| 263 EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, MojoClose(handle0_value)); | 265 EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, MojoClose(handle0_value)); |
| 264 EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, MojoClose(handle1_value)); | 266 EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, MojoClose(handle1_value)); |
| 265 } | 267 } |
| 266 | 268 |
| 267 } // namespace | 269 } // namespace |
| 268 } // namespace test | 270 } // namespace test |
| 269 } // namespace mojo | 271 } // namespace mojo |
| OLD | NEW |