| OLD | NEW | 
|---|
|  | (Empty) | 
| 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 |  | 
| 3 // found in the LICENSE file. |  | 
| 4 |  | 
| 5 #include "mojo/edk/system/core.h" |  | 
| 6 |  | 
| 7 #include <stdint.h> |  | 
| 8 |  | 
| 9 #include <limits> |  | 
| 10 |  | 
| 11 #include "base/bind.h" |  | 
| 12 #include "base/threading/platform_thread.h" |  | 
| 13 #include "base/time/time.h" |  | 
| 14 #include "mojo/edk/system/awakable.h" |  | 
| 15 #include "mojo/edk/system/core_test_base.h" |  | 
| 16 |  | 
| 17 namespace mojo { |  | 
| 18 namespace system { |  | 
| 19 namespace { |  | 
| 20 |  | 
| 21 const MojoHandleSignalsState kEmptyMojoHandleSignalsState = {0u, 0u}; |  | 
| 22 const MojoHandleSignalsState kFullMojoHandleSignalsState = {~0u, ~0u}; |  | 
| 23 const MojoHandleSignals kAllSignals = MOJO_HANDLE_SIGNAL_READABLE | |  | 
| 24                                       MOJO_HANDLE_SIGNAL_WRITABLE | |  | 
| 25                                       MOJO_HANDLE_SIGNAL_PEER_CLOSED; |  | 
| 26 |  | 
| 27 typedef test::CoreTestBase CoreTest; |  | 
| 28 |  | 
| 29 TEST_F(CoreTest, GetTimeTicksNow) { |  | 
| 30   const MojoTimeTicks start = core()->GetTimeTicksNow(); |  | 
| 31   EXPECT_NE(static_cast<MojoTimeTicks>(0), start) |  | 
| 32       << "GetTimeTicksNow should return nonzero value"; |  | 
| 33   base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(15)); |  | 
| 34   const MojoTimeTicks finish = core()->GetTimeTicksNow(); |  | 
| 35   // Allow for some fuzz in sleep. |  | 
| 36   EXPECT_GE((finish - start), static_cast<MojoTimeTicks>(8000)) |  | 
| 37       << "Sleeping should result in increasing time ticks"; |  | 
| 38 } |  | 
| 39 |  | 
| 40 TEST_F(CoreTest, Basic) { |  | 
| 41   MockHandleInfo info; |  | 
| 42 |  | 
| 43   EXPECT_EQ(0u, info.GetCtorCallCount()); |  | 
| 44   MojoHandle h = CreateMockHandle(&info); |  | 
| 45   EXPECT_EQ(1u, info.GetCtorCallCount()); |  | 
| 46   EXPECT_NE(h, MOJO_HANDLE_INVALID); |  | 
| 47 |  | 
| 48   EXPECT_EQ(0u, info.GetWriteMessageCallCount()); |  | 
| 49   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 50             core()->WriteMessage(h, NullUserPointer(), 0, NullUserPointer(), 0, |  | 
| 51                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 52   EXPECT_EQ(1u, info.GetWriteMessageCallCount()); |  | 
| 53 |  | 
| 54   EXPECT_EQ(0u, info.GetReadMessageCallCount()); |  | 
| 55   uint32_t num_bytes = 0; |  | 
| 56   EXPECT_EQ( |  | 
| 57       MOJO_RESULT_OK, |  | 
| 58       core()->ReadMessage(h, NullUserPointer(), MakeUserPointer(&num_bytes), |  | 
| 59                           NullUserPointer(), NullUserPointer(), |  | 
| 60                           MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 61   EXPECT_EQ(1u, info.GetReadMessageCallCount()); |  | 
| 62   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 63             core()->ReadMessage(h, NullUserPointer(), NullUserPointer(), |  | 
| 64                                 NullUserPointer(), NullUserPointer(), |  | 
| 65                                 MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 66   EXPECT_EQ(2u, info.GetReadMessageCallCount()); |  | 
| 67 |  | 
| 68   EXPECT_EQ(0u, info.GetWriteDataCallCount()); |  | 
| 69   EXPECT_EQ(MOJO_RESULT_UNIMPLEMENTED, |  | 
| 70             core()->WriteData(h, NullUserPointer(), NullUserPointer(), |  | 
| 71                               MOJO_WRITE_DATA_FLAG_NONE)); |  | 
| 72   EXPECT_EQ(1u, info.GetWriteDataCallCount()); |  | 
| 73 |  | 
| 74   EXPECT_EQ(0u, info.GetBeginWriteDataCallCount()); |  | 
| 75   EXPECT_EQ(MOJO_RESULT_UNIMPLEMENTED, |  | 
| 76             core()->BeginWriteData(h, NullUserPointer(), NullUserPointer(), |  | 
| 77                                    MOJO_WRITE_DATA_FLAG_NONE)); |  | 
| 78   EXPECT_EQ(1u, info.GetBeginWriteDataCallCount()); |  | 
| 79 |  | 
| 80   EXPECT_EQ(0u, info.GetEndWriteDataCallCount()); |  | 
| 81   EXPECT_EQ(MOJO_RESULT_UNIMPLEMENTED, core()->EndWriteData(h, 0)); |  | 
| 82   EXPECT_EQ(1u, info.GetEndWriteDataCallCount()); |  | 
| 83 |  | 
| 84   EXPECT_EQ(0u, info.GetReadDataCallCount()); |  | 
| 85   EXPECT_EQ(MOJO_RESULT_UNIMPLEMENTED, |  | 
| 86             core()->ReadData(h, NullUserPointer(), NullUserPointer(), |  | 
| 87                              MOJO_READ_DATA_FLAG_NONE)); |  | 
| 88   EXPECT_EQ(1u, info.GetReadDataCallCount()); |  | 
| 89 |  | 
| 90   EXPECT_EQ(0u, info.GetBeginReadDataCallCount()); |  | 
| 91   EXPECT_EQ(MOJO_RESULT_UNIMPLEMENTED, |  | 
| 92             core()->BeginReadData(h, NullUserPointer(), NullUserPointer(), |  | 
| 93                                   MOJO_READ_DATA_FLAG_NONE)); |  | 
| 94   EXPECT_EQ(1u, info.GetBeginReadDataCallCount()); |  | 
| 95 |  | 
| 96   EXPECT_EQ(0u, info.GetEndReadDataCallCount()); |  | 
| 97   EXPECT_EQ(MOJO_RESULT_UNIMPLEMENTED, core()->EndReadData(h, 0)); |  | 
| 98   EXPECT_EQ(1u, info.GetEndReadDataCallCount()); |  | 
| 99 |  | 
| 100   EXPECT_EQ(0u, info.GetAddAwakableCallCount()); |  | 
| 101   EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 102             core()->Wait(h, ~MOJO_HANDLE_SIGNAL_NONE, MOJO_DEADLINE_INDEFINITE, |  | 
| 103                          NullUserPointer())); |  | 
| 104   EXPECT_EQ(1u, info.GetAddAwakableCallCount()); |  | 
| 105   EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 106             core()->Wait(h, ~MOJO_HANDLE_SIGNAL_NONE, 0, NullUserPointer())); |  | 
| 107   EXPECT_EQ(2u, info.GetAddAwakableCallCount()); |  | 
| 108   MojoHandleSignalsState hss = kFullMojoHandleSignalsState; |  | 
| 109   EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 110             core()->Wait(h, ~MOJO_HANDLE_SIGNAL_NONE, MOJO_DEADLINE_INDEFINITE, |  | 
| 111                          MakeUserPointer(&hss))); |  | 
| 112   EXPECT_EQ(3u, info.GetAddAwakableCallCount()); |  | 
| 113   EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 114   EXPECT_EQ(0u, hss.satisfiable_signals); |  | 
| 115   EXPECT_EQ( |  | 
| 116       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 117       core()->Wait(h, ~MOJO_HANDLE_SIGNAL_NONE, 10 * 1000, NullUserPointer())); |  | 
| 118   EXPECT_EQ(4u, info.GetAddAwakableCallCount()); |  | 
| 119   hss = kFullMojoHandleSignalsState; |  | 
| 120   EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 121             core()->Wait(h, ~MOJO_HANDLE_SIGNAL_NONE, 10 * 1000, |  | 
| 122                          MakeUserPointer(&hss))); |  | 
| 123   EXPECT_EQ(5u, info.GetAddAwakableCallCount()); |  | 
| 124   EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 125   EXPECT_EQ(0u, hss.satisfiable_signals); |  | 
| 126 |  | 
| 127   MojoHandleSignals handle_signals = ~MOJO_HANDLE_SIGNAL_NONE; |  | 
| 128   EXPECT_EQ( |  | 
| 129       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 130       core()->WaitMany(MakeUserPointer(&h), MakeUserPointer(&handle_signals), 1, |  | 
| 131                        MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 132                        NullUserPointer())); |  | 
| 133   EXPECT_EQ(6u, info.GetAddAwakableCallCount()); |  | 
| 134   uint32_t result_index = static_cast<uint32_t>(-1); |  | 
| 135   EXPECT_EQ( |  | 
| 136       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 137       core()->WaitMany(MakeUserPointer(&h), MakeUserPointer(&handle_signals), 1, |  | 
| 138                        MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&result_index), |  | 
| 139                        NullUserPointer())); |  | 
| 140   EXPECT_EQ(7u, info.GetAddAwakableCallCount()); |  | 
| 141   EXPECT_EQ(0u, result_index); |  | 
| 142   hss = kFullMojoHandleSignalsState; |  | 
| 143   EXPECT_EQ( |  | 
| 144       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 145       core()->WaitMany(MakeUserPointer(&h), MakeUserPointer(&handle_signals), 1, |  | 
| 146                        MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 147                        MakeUserPointer(&hss))); |  | 
| 148   EXPECT_EQ(8u, info.GetAddAwakableCallCount()); |  | 
| 149   EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 150   EXPECT_EQ(0u, hss.satisfiable_signals); |  | 
| 151   result_index = static_cast<uint32_t>(-1); |  | 
| 152   hss = kFullMojoHandleSignalsState; |  | 
| 153   EXPECT_EQ( |  | 
| 154       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 155       core()->WaitMany(MakeUserPointer(&h), MakeUserPointer(&handle_signals), 1, |  | 
| 156                        MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&result_index), |  | 
| 157                        MakeUserPointer(&hss))); |  | 
| 158   EXPECT_EQ(9u, info.GetAddAwakableCallCount()); |  | 
| 159   EXPECT_EQ(0u, result_index); |  | 
| 160   EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 161   EXPECT_EQ(0u, hss.satisfiable_signals); |  | 
| 162 |  | 
| 163   EXPECT_EQ(0u, info.GetDtorCallCount()); |  | 
| 164   EXPECT_EQ(0u, info.GetCloseCallCount()); |  | 
| 165   EXPECT_EQ(0u, info.GetCancelAllAwakablesCallCount()); |  | 
| 166   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h)); |  | 
| 167   EXPECT_EQ(1u, info.GetCancelAllAwakablesCallCount()); |  | 
| 168   EXPECT_EQ(1u, info.GetCloseCallCount()); |  | 
| 169   EXPECT_EQ(1u, info.GetDtorCallCount()); |  | 
| 170 |  | 
| 171   // No awakables should ever have ever been added. |  | 
| 172   EXPECT_EQ(0u, info.GetRemoveAwakableCallCount()); |  | 
| 173 } |  | 
| 174 |  | 
| 175 TEST_F(CoreTest, InvalidArguments) { |  | 
| 176   // |Close()|: |  | 
| 177   { |  | 
| 178     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, core()->Close(MOJO_HANDLE_INVALID)); |  | 
| 179     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, core()->Close(10)); |  | 
| 180     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, core()->Close(1000000000)); |  | 
| 181 |  | 
| 182     // Test a double-close. |  | 
| 183     MockHandleInfo info; |  | 
| 184     MojoHandle h = CreateMockHandle(&info); |  | 
| 185     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h)); |  | 
| 186     EXPECT_EQ(1u, info.GetCloseCallCount()); |  | 
| 187     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, core()->Close(h)); |  | 
| 188     EXPECT_EQ(1u, info.GetCloseCallCount()); |  | 
| 189   } |  | 
| 190 |  | 
| 191   // |Wait()|: |  | 
| 192   { |  | 
| 193     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 194               core()->Wait(MOJO_HANDLE_INVALID, ~MOJO_HANDLE_SIGNAL_NONE, |  | 
| 195                            MOJO_DEADLINE_INDEFINITE, NullUserPointer())); |  | 
| 196     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 197               core()->Wait(10, ~MOJO_HANDLE_SIGNAL_NONE, |  | 
| 198                            MOJO_DEADLINE_INDEFINITE, NullUserPointer())); |  | 
| 199 |  | 
| 200     MojoHandleSignalsState hss = kFullMojoHandleSignalsState; |  | 
| 201     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 202               core()->Wait(MOJO_HANDLE_INVALID, ~MOJO_HANDLE_SIGNAL_NONE, |  | 
| 203                            MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&hss))); |  | 
| 204     // On invalid argument, it shouldn't modify the handle signals state. |  | 
| 205     EXPECT_EQ(kFullMojoHandleSignalsState.satisfied_signals, |  | 
| 206               hss.satisfied_signals); |  | 
| 207     EXPECT_EQ(kFullMojoHandleSignalsState.satisfiable_signals, |  | 
| 208               hss.satisfiable_signals); |  | 
| 209     hss = kFullMojoHandleSignalsState; |  | 
| 210     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 211               core()->Wait(10, ~MOJO_HANDLE_SIGNAL_NONE, |  | 
| 212                            MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&hss))); |  | 
| 213     // On invalid argument, it shouldn't modify the handle signals state. |  | 
| 214     EXPECT_EQ(kFullMojoHandleSignalsState.satisfied_signals, |  | 
| 215               hss.satisfied_signals); |  | 
| 216     EXPECT_EQ(kFullMojoHandleSignalsState.satisfiable_signals, |  | 
| 217               hss.satisfiable_signals); |  | 
| 218   } |  | 
| 219 |  | 
| 220   // |WaitMany()|: |  | 
| 221   { |  | 
| 222     MojoHandle handles[2] = {MOJO_HANDLE_INVALID, MOJO_HANDLE_INVALID}; |  | 
| 223     MojoHandleSignals signals[2] = {~MOJO_HANDLE_SIGNAL_NONE, |  | 
| 224                                     ~MOJO_HANDLE_SIGNAL_NONE}; |  | 
| 225     EXPECT_EQ( |  | 
| 226         MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 227         core()->WaitMany(MakeUserPointer(handles), MakeUserPointer(signals), 0, |  | 
| 228                          MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 229                          NullUserPointer())); |  | 
| 230     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 231               core()->WaitMany(NullUserPointer(), MakeUserPointer(signals), 0, |  | 
| 232                                MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 233                                NullUserPointer())); |  | 
| 234     // If |num_handles| is invalid, it should leave |result_index| and |  | 
| 235     // |signals_states| alone. |  | 
| 236     // (We use -1 internally; make sure that doesn't leak.) |  | 
| 237     uint32_t result_index = 123; |  | 
| 238     MojoHandleSignalsState hss = kFullMojoHandleSignalsState; |  | 
| 239     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 240               core()->WaitMany(NullUserPointer(), MakeUserPointer(signals), 0, |  | 
| 241                                MOJO_DEADLINE_INDEFINITE, |  | 
| 242                                MakeUserPointer(&result_index), |  | 
| 243                                MakeUserPointer(&hss))); |  | 
| 244     EXPECT_EQ(123u, result_index); |  | 
| 245     EXPECT_EQ(kFullMojoHandleSignalsState.satisfied_signals, |  | 
| 246               hss.satisfied_signals); |  | 
| 247     EXPECT_EQ(kFullMojoHandleSignalsState.satisfiable_signals, |  | 
| 248               hss.satisfiable_signals); |  | 
| 249 |  | 
| 250     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 251               core()->WaitMany(MakeUserPointer(handles), NullUserPointer(), 0, |  | 
| 252                                MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 253                                NullUserPointer())); |  | 
| 254     EXPECT_EQ( |  | 
| 255         MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 256         core()->WaitMany(MakeUserPointer(handles), MakeUserPointer(signals), 1, |  | 
| 257                          MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 258                          NullUserPointer())); |  | 
| 259     // But if a handle is bad, then it should set |result_index| but still leave |  | 
| 260     // |signals_states| alone. |  | 
| 261     result_index = static_cast<uint32_t>(-1); |  | 
| 262     hss = kFullMojoHandleSignalsState; |  | 
| 263     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 264               core()->WaitMany( |  | 
| 265                   MakeUserPointer(handles), MakeUserPointer(signals), 1, |  | 
| 266                   MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&result_index), |  | 
| 267                   MakeUserPointer(&hss))); |  | 
| 268     EXPECT_EQ(0u, result_index); |  | 
| 269     EXPECT_EQ(kFullMojoHandleSignalsState.satisfied_signals, |  | 
| 270               hss.satisfied_signals); |  | 
| 271     EXPECT_EQ(kFullMojoHandleSignalsState.satisfiable_signals, |  | 
| 272               hss.satisfiable_signals); |  | 
| 273 |  | 
| 274     MockHandleInfo info[2]; |  | 
| 275     handles[0] = CreateMockHandle(&info[0]); |  | 
| 276 |  | 
| 277     result_index = static_cast<uint32_t>(-1); |  | 
| 278     hss = kFullMojoHandleSignalsState; |  | 
| 279     EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 280               core()->WaitMany( |  | 
| 281                   MakeUserPointer(handles), MakeUserPointer(signals), 1, |  | 
| 282                   MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&result_index), |  | 
| 283                   MakeUserPointer(&hss))); |  | 
| 284     EXPECT_EQ(0u, result_index); |  | 
| 285     EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 286     EXPECT_EQ(0u, hss.satisfiable_signals); |  | 
| 287 |  | 
| 288     // On invalid argument, it'll leave |signals_states| alone. |  | 
| 289     result_index = static_cast<uint32_t>(-1); |  | 
| 290     hss = kFullMojoHandleSignalsState; |  | 
| 291     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 292               core()->WaitMany( |  | 
| 293                   MakeUserPointer(handles), MakeUserPointer(signals), 2, |  | 
| 294                   MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&result_index), |  | 
| 295                   MakeUserPointer(&hss))); |  | 
| 296     EXPECT_EQ(1u, result_index); |  | 
| 297     EXPECT_EQ(kFullMojoHandleSignalsState.satisfied_signals, |  | 
| 298               hss.satisfied_signals); |  | 
| 299     EXPECT_EQ(kFullMojoHandleSignalsState.satisfiable_signals, |  | 
| 300               hss.satisfiable_signals); |  | 
| 301     handles[1] = handles[0] + 1;  // Invalid handle. |  | 
| 302     EXPECT_EQ( |  | 
| 303         MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 304         core()->WaitMany(MakeUserPointer(handles), MakeUserPointer(signals), 2, |  | 
| 305                          MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 306                          NullUserPointer())); |  | 
| 307     handles[1] = CreateMockHandle(&info[1]); |  | 
| 308     EXPECT_EQ( |  | 
| 309         MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 310         core()->WaitMany(MakeUserPointer(handles), MakeUserPointer(signals), 2, |  | 
| 311                          MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 312                          NullUserPointer())); |  | 
| 313 |  | 
| 314     // TODO(vtl): Test one where we get "failed precondition" only for the |  | 
| 315     // second handle (and the first one is valid to wait on). |  | 
| 316 |  | 
| 317     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(handles[0])); |  | 
| 318     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(handles[1])); |  | 
| 319   } |  | 
| 320 |  | 
| 321   // |CreateMessagePipe()|: Nothing to check (apart from things that cause |  | 
| 322   // death). |  | 
| 323 |  | 
| 324   // |WriteMessage()|: |  | 
| 325   // Only check arguments checked by |Core|, namely |handle|, |handles|, and |  | 
| 326   // |num_handles|. |  | 
| 327   { |  | 
| 328     EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 329               core()->WriteMessage(MOJO_HANDLE_INVALID, NullUserPointer(), 0, |  | 
| 330                                    NullUserPointer(), 0, |  | 
| 331                                    MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 332 |  | 
| 333     MockHandleInfo info; |  | 
| 334     MojoHandle h = CreateMockHandle(&info); |  | 
| 335     MojoHandle handles[2] = {MOJO_HANDLE_INVALID, MOJO_HANDLE_INVALID}; |  | 
| 336 |  | 
| 337     // Huge handle count (implausibly big on some systems -- more than can be |  | 
| 338     // stored in a 32-bit address space). |  | 
| 339     // Note: This may return either |MOJO_RESULT_INVALID_ARGUMENT| or |  | 
| 340     // |MOJO_RESULT_RESOURCE_EXHAUSTED|, depending on whether it's plausible or |  | 
| 341     // not. |  | 
| 342     EXPECT_NE( |  | 
| 343         MOJO_RESULT_OK, |  | 
| 344         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 345                              std::numeric_limits<uint32_t>::max(), |  | 
| 346                              MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 347     EXPECT_EQ(0u, info.GetWriteMessageCallCount()); |  | 
| 348 |  | 
| 349     // Huge handle count (plausibly big). |  | 
| 350     EXPECT_EQ(MOJO_RESULT_RESOURCE_EXHAUSTED, |  | 
| 351               core()->WriteMessage( |  | 
| 352                   h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 353                   std::numeric_limits<uint32_t>::max() / sizeof(handles[0]), |  | 
| 354                   MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 355     EXPECT_EQ(0u, info.GetWriteMessageCallCount()); |  | 
| 356 |  | 
| 357     // Invalid handle in |handles|. |  | 
| 358     EXPECT_EQ( |  | 
| 359         MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 360         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 361                              1, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 362     EXPECT_EQ(0u, info.GetWriteMessageCallCount()); |  | 
| 363 |  | 
| 364     // Two invalid handles in |handles|. |  | 
| 365     EXPECT_EQ( |  | 
| 366         MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 367         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 368                              2, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 369     EXPECT_EQ(0u, info.GetWriteMessageCallCount()); |  | 
| 370 |  | 
| 371     // Can't send a handle over itself. |  | 
| 372     handles[0] = h; |  | 
| 373     EXPECT_EQ( |  | 
| 374         MOJO_RESULT_BUSY, |  | 
| 375         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 376                              1, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 377     EXPECT_EQ(0u, info.GetWriteMessageCallCount()); |  | 
| 378 |  | 
| 379     MockHandleInfo info2; |  | 
| 380     MojoHandle h2 = CreateMockHandle(&info2); |  | 
| 381 |  | 
| 382     // This is "okay", but |MockDispatcher| doesn't implement it. |  | 
| 383     handles[0] = h2; |  | 
| 384     EXPECT_EQ( |  | 
| 385         MOJO_RESULT_UNIMPLEMENTED, |  | 
| 386         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 387                              1, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 388     EXPECT_EQ(1u, info.GetWriteMessageCallCount()); |  | 
| 389 |  | 
| 390     // One of the |handles| is still invalid. |  | 
| 391     EXPECT_EQ( |  | 
| 392         MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 393         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 394                              2, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 395     EXPECT_EQ(1u, info.GetWriteMessageCallCount()); |  | 
| 396 |  | 
| 397     // One of the |handles| is the same as |handle|. |  | 
| 398     handles[1] = h; |  | 
| 399     EXPECT_EQ( |  | 
| 400         MOJO_RESULT_BUSY, |  | 
| 401         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 402                              2, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 403     EXPECT_EQ(1u, info.GetWriteMessageCallCount()); |  | 
| 404 |  | 
| 405     // Can't send a handle twice in the same message. |  | 
| 406     handles[1] = h2; |  | 
| 407     EXPECT_EQ( |  | 
| 408         MOJO_RESULT_BUSY, |  | 
| 409         core()->WriteMessage(h, NullUserPointer(), 0, MakeUserPointer(handles), |  | 
| 410                              2, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 411     EXPECT_EQ(1u, info.GetWriteMessageCallCount()); |  | 
| 412 |  | 
| 413     // Note: Since we never successfully sent anything with it, |h2| should |  | 
| 414     // still be valid. |  | 
| 415     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h2)); |  | 
| 416 |  | 
| 417     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h)); |  | 
| 418   } |  | 
| 419 |  | 
| 420   // |ReadMessage()|: |  | 
| 421   // Only check arguments checked by |Core|, namely |handle|, |handles|, and |  | 
| 422   // |num_handles|. |  | 
| 423   { |  | 
| 424     EXPECT_EQ( |  | 
| 425         MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 426         core()->ReadMessage(MOJO_HANDLE_INVALID, NullUserPointer(), |  | 
| 427                             NullUserPointer(), NullUserPointer(), |  | 
| 428                             NullUserPointer(), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 429 |  | 
| 430     MockHandleInfo info; |  | 
| 431     MojoHandle h = CreateMockHandle(&info); |  | 
| 432 |  | 
| 433     // Okay. |  | 
| 434     uint32_t handle_count = 0; |  | 
| 435     EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 436               core()->ReadMessage( |  | 
| 437                   h, NullUserPointer(), NullUserPointer(), NullUserPointer(), |  | 
| 438                   MakeUserPointer(&handle_count), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 439     // Checked by |Core|, shouldn't go through to the dispatcher. |  | 
| 440     EXPECT_EQ(1u, info.GetReadMessageCallCount()); |  | 
| 441 |  | 
| 442     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h)); |  | 
| 443   } |  | 
| 444 } |  | 
| 445 |  | 
| 446 // These test invalid arguments that should cause death if we're being paranoid |  | 
| 447 // about checking arguments (which we would want to do if, e.g., we were in a |  | 
| 448 // true "kernel" situation, but we might not want to do otherwise for |  | 
| 449 // performance reasons). Probably blatant errors like passing in null pointers |  | 
| 450 // (for required pointer arguments) will still cause death, but perhaps not |  | 
| 451 // predictably. |  | 
| 452 TEST_F(CoreTest, InvalidArgumentsDeath) { |  | 
| 453   const char kMemoryCheckFailedRegex[] = "Check failed"; |  | 
| 454 |  | 
| 455   // |WaitMany()|: |  | 
| 456   { |  | 
| 457     MojoHandle handle = MOJO_HANDLE_INVALID; |  | 
| 458     MojoHandleSignals signals = ~MOJO_HANDLE_SIGNAL_NONE; |  | 
| 459     EXPECT_DEATH_IF_SUPPORTED( |  | 
| 460         core()->WaitMany(NullUserPointer(), MakeUserPointer(&signals), 1, |  | 
| 461                          MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 462                          NullUserPointer()), |  | 
| 463         kMemoryCheckFailedRegex); |  | 
| 464     EXPECT_DEATH_IF_SUPPORTED( |  | 
| 465         core()->WaitMany(MakeUserPointer(&handle), NullUserPointer(), 1, |  | 
| 466                          MOJO_DEADLINE_INDEFINITE, NullUserPointer(), |  | 
| 467                          NullUserPointer()), |  | 
| 468         kMemoryCheckFailedRegex); |  | 
| 469     // TODO(vtl): |result_index| and |signals_states| are optional. Test them |  | 
| 470     // with non-null invalid pointers? |  | 
| 471   } |  | 
| 472 |  | 
| 473   // |CreateMessagePipe()|: |  | 
| 474   { |  | 
| 475     MojoHandle h; |  | 
| 476     EXPECT_DEATH_IF_SUPPORTED( |  | 
| 477         core()->CreateMessagePipe(NullUserPointer(), NullUserPointer(), |  | 
| 478                                   NullUserPointer()), |  | 
| 479         kMemoryCheckFailedRegex); |  | 
| 480     EXPECT_DEATH_IF_SUPPORTED( |  | 
| 481         core()->CreateMessagePipe(NullUserPointer(), MakeUserPointer(&h), |  | 
| 482                                   NullUserPointer()), |  | 
| 483         kMemoryCheckFailedRegex); |  | 
| 484     EXPECT_DEATH_IF_SUPPORTED( |  | 
| 485         core()->CreateMessagePipe(NullUserPointer(), NullUserPointer(), |  | 
| 486                                   MakeUserPointer(&h)), |  | 
| 487         kMemoryCheckFailedRegex); |  | 
| 488   } |  | 
| 489 |  | 
| 490   // |WriteMessage()|: |  | 
| 491   // Only check arguments checked by |Core|, namely |handle|, |handles|, and |  | 
| 492   // |num_handles|. |  | 
| 493   { |  | 
| 494     MockHandleInfo info; |  | 
| 495     MojoHandle h = CreateMockHandle(&info); |  | 
| 496 |  | 
| 497     // Null |handles| with nonzero |num_handles|. |  | 
| 498     EXPECT_DEATH_IF_SUPPORTED( |  | 
| 499         core()->WriteMessage(h, NullUserPointer(), 0, NullUserPointer(), 1, |  | 
| 500                              MOJO_WRITE_MESSAGE_FLAG_NONE), |  | 
| 501         kMemoryCheckFailedRegex); |  | 
| 502 |  | 
| 503     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h)); |  | 
| 504   } |  | 
| 505 |  | 
| 506   // |ReadMessage()|: |  | 
| 507   // Only check arguments checked by |Core|, namely |handle|, |handles|, and |  | 
| 508   // |num_handles|. |  | 
| 509   { |  | 
| 510     MockHandleInfo info; |  | 
| 511     MojoHandle h = CreateMockHandle(&info); |  | 
| 512 |  | 
| 513     uint32_t handle_count = 1; |  | 
| 514     EXPECT_DEATH_IF_SUPPORTED( |  | 
| 515         core()->ReadMessage(h, NullUserPointer(), NullUserPointer(), |  | 
| 516                             NullUserPointer(), MakeUserPointer(&handle_count), |  | 
| 517                             MOJO_READ_MESSAGE_FLAG_NONE), |  | 
| 518         kMemoryCheckFailedRegex); |  | 
| 519 |  | 
| 520     EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h)); |  | 
| 521   } |  | 
| 522 } |  | 
| 523 |  | 
| 524 // TODO(vtl): test |Wait()| and |WaitMany()| properly |  | 
| 525 //  - including |WaitMany()| with the same handle more than once (with |  | 
| 526 //    same/different signals) |  | 
| 527 |  | 
| 528 TEST_F(CoreTest, MessagePipe) { |  | 
| 529   MojoHandle h[2]; |  | 
| 530   MojoHandleSignalsState hss[2]; |  | 
| 531   uint32_t result_index; |  | 
| 532 |  | 
| 533   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 534             core()->CreateMessagePipe(NullUserPointer(), MakeUserPointer(&h[0]), |  | 
| 535                                       MakeUserPointer(&h[1]))); |  | 
| 536   // Should get two distinct, valid handles. |  | 
| 537   EXPECT_NE(h[0], MOJO_HANDLE_INVALID); |  | 
| 538   EXPECT_NE(h[1], MOJO_HANDLE_INVALID); |  | 
| 539   EXPECT_NE(h[0], h[1]); |  | 
| 540 |  | 
| 541   // Neither should be readable. |  | 
| 542   MojoHandleSignals signals[2] = {MOJO_HANDLE_SIGNAL_READABLE, |  | 
| 543                                   MOJO_HANDLE_SIGNAL_READABLE}; |  | 
| 544   result_index = static_cast<uint32_t>(-1); |  | 
| 545   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 546   hss[1] = kEmptyMojoHandleSignalsState; |  | 
| 547   EXPECT_EQ( |  | 
| 548       MOJO_RESULT_DEADLINE_EXCEEDED, |  | 
| 549       core()->WaitMany(MakeUserPointer(h), MakeUserPointer(signals), 2, 0, |  | 
| 550                        MakeUserPointer(&result_index), MakeUserPointer(hss))); |  | 
| 551   EXPECT_EQ(static_cast<uint32_t>(-1), result_index); |  | 
| 552   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[0].satisfied_signals); |  | 
| 553   EXPECT_EQ(kAllSignals, hss[0].satisfiable_signals); |  | 
| 554   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[1].satisfied_signals); |  | 
| 555   EXPECT_EQ(kAllSignals, hss[1].satisfiable_signals); |  | 
| 556 |  | 
| 557   // Try to read anyway. |  | 
| 558   char buffer[1] = {'a'}; |  | 
| 559   uint32_t buffer_size = 1; |  | 
| 560   EXPECT_EQ( |  | 
| 561       MOJO_RESULT_SHOULD_WAIT, |  | 
| 562       core()->ReadMessage(h[0], UserPointer<void>(buffer), |  | 
| 563                           MakeUserPointer(&buffer_size), NullUserPointer(), |  | 
| 564                           NullUserPointer(), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 565   // Check that it left its inputs alone. |  | 
| 566   EXPECT_EQ('a', buffer[0]); |  | 
| 567   EXPECT_EQ(1u, buffer_size); |  | 
| 568 |  | 
| 569   // Both should be writable. |  | 
| 570   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 571   EXPECT_EQ(MOJO_RESULT_OK, core()->Wait(h[0], MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 572                                          1000000000, MakeUserPointer(&hss[0]))); |  | 
| 573   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[0].satisfied_signals); |  | 
| 574   EXPECT_EQ(kAllSignals, hss[0].satisfiable_signals); |  | 
| 575   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 576   EXPECT_EQ(MOJO_RESULT_OK, core()->Wait(h[1], MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 577                                          1000000000, MakeUserPointer(&hss[0]))); |  | 
| 578   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[0].satisfied_signals); |  | 
| 579   EXPECT_EQ(kAllSignals, hss[0].satisfiable_signals); |  | 
| 580 |  | 
| 581   // Also check that |h[1]| is writable using |WaitMany()|. |  | 
| 582   signals[0] = MOJO_HANDLE_SIGNAL_READABLE; |  | 
| 583   signals[1] = MOJO_HANDLE_SIGNAL_WRITABLE; |  | 
| 584   result_index = static_cast<uint32_t>(-1); |  | 
| 585   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 586   hss[1] = kEmptyMojoHandleSignalsState; |  | 
| 587   EXPECT_EQ( |  | 
| 588       MOJO_RESULT_OK, |  | 
| 589       core()->WaitMany(MakeUserPointer(h), MakeUserPointer(signals), 2, |  | 
| 590                        MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&result_index), |  | 
| 591                        MakeUserPointer(hss))); |  | 
| 592   EXPECT_EQ(1u, result_index); |  | 
| 593   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[0].satisfied_signals); |  | 
| 594   EXPECT_EQ(kAllSignals, hss[0].satisfiable_signals); |  | 
| 595   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[1].satisfied_signals); |  | 
| 596   EXPECT_EQ(kAllSignals, hss[1].satisfiable_signals); |  | 
| 597 |  | 
| 598   // Write to |h[1]|. |  | 
| 599   buffer[0] = 'b'; |  | 
| 600   EXPECT_EQ( |  | 
| 601       MOJO_RESULT_OK, |  | 
| 602       core()->WriteMessage(h[1], UserPointer<const void>(buffer), 1, |  | 
| 603                            NullUserPointer(), 0, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 604 |  | 
| 605   // Check that |h[0]| is now readable. |  | 
| 606   signals[0] = MOJO_HANDLE_SIGNAL_READABLE; |  | 
| 607   signals[1] = MOJO_HANDLE_SIGNAL_READABLE; |  | 
| 608   result_index = static_cast<uint32_t>(-1); |  | 
| 609   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 610   hss[1] = kEmptyMojoHandleSignalsState; |  | 
| 611   EXPECT_EQ( |  | 
| 612       MOJO_RESULT_OK, |  | 
| 613       core()->WaitMany(MakeUserPointer(h), MakeUserPointer(signals), 2, |  | 
| 614                        MOJO_DEADLINE_INDEFINITE, MakeUserPointer(&result_index), |  | 
| 615                        MakeUserPointer(hss))); |  | 
| 616   EXPECT_EQ(0u, result_index); |  | 
| 617   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 618             hss[0].satisfied_signals); |  | 
| 619   EXPECT_EQ(kAllSignals, hss[0].satisfiable_signals); |  | 
| 620   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[1].satisfied_signals); |  | 
| 621   EXPECT_EQ(kAllSignals, hss[1].satisfiable_signals); |  | 
| 622 |  | 
| 623   // Read from |h[0]|. |  | 
| 624   // First, get only the size. |  | 
| 625   buffer_size = 0; |  | 
| 626   EXPECT_EQ( |  | 
| 627       MOJO_RESULT_RESOURCE_EXHAUSTED, |  | 
| 628       core()->ReadMessage(h[0], NullUserPointer(), |  | 
| 629                           MakeUserPointer(&buffer_size), NullUserPointer(), |  | 
| 630                           NullUserPointer(), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 631   EXPECT_EQ(1u, buffer_size); |  | 
| 632   // Then actually read it. |  | 
| 633   buffer[0] = 'c'; |  | 
| 634   buffer_size = 1; |  | 
| 635   EXPECT_EQ( |  | 
| 636       MOJO_RESULT_OK, |  | 
| 637       core()->ReadMessage(h[0], UserPointer<void>(buffer), |  | 
| 638                           MakeUserPointer(&buffer_size), NullUserPointer(), |  | 
| 639                           NullUserPointer(), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 640   EXPECT_EQ('b', buffer[0]); |  | 
| 641   EXPECT_EQ(1u, buffer_size); |  | 
| 642 |  | 
| 643   // |h[0]| should no longer be readable. |  | 
| 644   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 645   EXPECT_EQ(MOJO_RESULT_DEADLINE_EXCEEDED, |  | 
| 646             core()->Wait(h[0], MOJO_HANDLE_SIGNAL_READABLE, 0, |  | 
| 647                          MakeUserPointer(&hss[0]))); |  | 
| 648   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss[0].satisfied_signals); |  | 
| 649   EXPECT_EQ(kAllSignals, hss[0].satisfiable_signals); |  | 
| 650 |  | 
| 651   // Write to |h[0]|. |  | 
| 652   buffer[0] = 'd'; |  | 
| 653   EXPECT_EQ( |  | 
| 654       MOJO_RESULT_OK, |  | 
| 655       core()->WriteMessage(h[0], UserPointer<const void>(buffer), 1, |  | 
| 656                            NullUserPointer(), 0, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 657 |  | 
| 658   // Close |h[0]|. |  | 
| 659   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h[0])); |  | 
| 660 |  | 
| 661   // Check that |h[1]| is no longer writable (and will never be). |  | 
| 662   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 663   EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 664             core()->Wait(h[1], MOJO_HANDLE_SIGNAL_WRITABLE, 1000000000, |  | 
| 665                          MakeUserPointer(&hss[0]))); |  | 
| 666   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 667             hss[0].satisfied_signals); |  | 
| 668   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 669             hss[0].satisfiable_signals); |  | 
| 670 |  | 
| 671   // Check that |h[1]| is still readable (for the moment). |  | 
| 672   hss[0] = kEmptyMojoHandleSignalsState; |  | 
| 673   EXPECT_EQ(MOJO_RESULT_OK, core()->Wait(h[1], MOJO_HANDLE_SIGNAL_READABLE, |  | 
| 674                                          1000000000, MakeUserPointer(&hss[0]))); |  | 
| 675   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 676             hss[0].satisfied_signals); |  | 
| 677   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 678             hss[0].satisfiable_signals); |  | 
| 679 |  | 
| 680   // Discard a message from |h[1]|. |  | 
| 681   EXPECT_EQ(MOJO_RESULT_RESOURCE_EXHAUSTED, |  | 
| 682             core()->ReadMessage(h[1], NullUserPointer(), NullUserPointer(), |  | 
| 683                                 NullUserPointer(), NullUserPointer(), |  | 
| 684                                 MOJO_READ_MESSAGE_FLAG_MAY_DISCARD)); |  | 
| 685 |  | 
| 686   // |h[1]| is no longer readable (and will never be). |  | 
| 687   hss[0] = kFullMojoHandleSignalsState; |  | 
| 688   EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 689             core()->Wait(h[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 690                          MakeUserPointer(&hss[0]))); |  | 
| 691   EXPECT_EQ(MOJO_HANDLE_SIGNAL_PEER_CLOSED, hss[0].satisfied_signals); |  | 
| 692   EXPECT_EQ(MOJO_HANDLE_SIGNAL_PEER_CLOSED, hss[0].satisfiable_signals); |  | 
| 693 |  | 
| 694   // Try writing to |h[1]|. |  | 
| 695   buffer[0] = 'e'; |  | 
| 696   EXPECT_EQ( |  | 
| 697       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 698       core()->WriteMessage(h[1], UserPointer<const void>(buffer), 1, |  | 
| 699                            NullUserPointer(), 0, MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 700 |  | 
| 701   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h[1])); |  | 
| 702 } |  | 
| 703 |  | 
| 704 // Tests passing a message pipe handle. |  | 
| 705 TEST_F(CoreTest, MessagePipeBasicLocalHandlePassing1) { |  | 
| 706   const char kHello[] = "hello"; |  | 
| 707   const uint32_t kHelloSize = static_cast<uint32_t>(sizeof(kHello)); |  | 
| 708   const char kWorld[] = "world!!!"; |  | 
| 709   const uint32_t kWorldSize = static_cast<uint32_t>(sizeof(kWorld)); |  | 
| 710   char buffer[100]; |  | 
| 711   const uint32_t kBufferSize = static_cast<uint32_t>(sizeof(buffer)); |  | 
| 712   uint32_t num_bytes; |  | 
| 713   MojoHandle handles[10]; |  | 
| 714   uint32_t num_handles; |  | 
| 715   MojoHandleSignalsState hss; |  | 
| 716   MojoHandle h_received; |  | 
| 717 |  | 
| 718   MojoHandle h_passing[2]; |  | 
| 719   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 720             core()->CreateMessagePipe(NullUserPointer(), |  | 
| 721                                       MakeUserPointer(&h_passing[0]), |  | 
| 722                                       MakeUserPointer(&h_passing[1]))); |  | 
| 723 |  | 
| 724   // Make sure that |h_passing[]| work properly. |  | 
| 725   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 726             core()->WriteMessage(h_passing[0], UserPointer<const void>(kHello), |  | 
| 727                                  kHelloSize, NullUserPointer(), 0, |  | 
| 728                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 729   hss = kEmptyMojoHandleSignalsState; |  | 
| 730   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 731             core()->Wait(h_passing[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 732                          MakeUserPointer(&hss))); |  | 
| 733   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 734             hss.satisfied_signals); |  | 
| 735   EXPECT_EQ(kAllSignals, hss.satisfiable_signals); |  | 
| 736   num_bytes = kBufferSize; |  | 
| 737   num_handles = arraysize(handles); |  | 
| 738   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 739             core()->ReadMessage( |  | 
| 740                 h_passing[1], UserPointer<void>(buffer), |  | 
| 741                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 742                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 743   EXPECT_EQ(kHelloSize, num_bytes); |  | 
| 744   EXPECT_STREQ(kHello, buffer); |  | 
| 745   EXPECT_EQ(0u, num_handles); |  | 
| 746 |  | 
| 747   // Make sure that you can't pass either of the message pipe's handles over |  | 
| 748   // itself. |  | 
| 749   EXPECT_EQ(MOJO_RESULT_BUSY, |  | 
| 750             core()->WriteMessage(h_passing[0], UserPointer<const void>(kHello), |  | 
| 751                                  kHelloSize, MakeUserPointer(&h_passing[0]), 1, |  | 
| 752                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 753   EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 754             core()->WriteMessage(h_passing[0], UserPointer<const void>(kHello), |  | 
| 755                                  kHelloSize, MakeUserPointer(&h_passing[1]), 1, |  | 
| 756                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 757 |  | 
| 758   MojoHandle h_passed[2]; |  | 
| 759   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 760             core()->CreateMessagePipe(NullUserPointer(), |  | 
| 761                                       MakeUserPointer(&h_passed[0]), |  | 
| 762                                       MakeUserPointer(&h_passed[1]))); |  | 
| 763 |  | 
| 764   // Make sure that |h_passed[]| work properly. |  | 
| 765   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 766             core()->WriteMessage(h_passed[0], UserPointer<const void>(kHello), |  | 
| 767                                  kHelloSize, NullUserPointer(), 0, |  | 
| 768                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 769   hss = kEmptyMojoHandleSignalsState; |  | 
| 770   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 771             core()->Wait(h_passed[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 772                          MakeUserPointer(&hss))); |  | 
| 773   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 774             hss.satisfied_signals); |  | 
| 775   EXPECT_EQ(kAllSignals, hss.satisfiable_signals); |  | 
| 776   num_bytes = kBufferSize; |  | 
| 777   num_handles = arraysize(handles); |  | 
| 778   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 779             core()->ReadMessage( |  | 
| 780                 h_passed[1], UserPointer<void>(buffer), |  | 
| 781                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 782                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 783   EXPECT_EQ(kHelloSize, num_bytes); |  | 
| 784   EXPECT_STREQ(kHello, buffer); |  | 
| 785   EXPECT_EQ(0u, num_handles); |  | 
| 786 |  | 
| 787   // Send |h_passed[1]| from |h_passing[0]| to |h_passing[1]|. |  | 
| 788   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 789             core()->WriteMessage(h_passing[0], UserPointer<const void>(kWorld), |  | 
| 790                                  kWorldSize, MakeUserPointer(&h_passed[1]), 1, |  | 
| 791                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 792   hss = kEmptyMojoHandleSignalsState; |  | 
| 793   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 794             core()->Wait(h_passing[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 795                          MakeUserPointer(&hss))); |  | 
| 796   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 797             hss.satisfied_signals); |  | 
| 798   EXPECT_EQ(kAllSignals, hss.satisfiable_signals); |  | 
| 799   num_bytes = kBufferSize; |  | 
| 800   num_handles = arraysize(handles); |  | 
| 801   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 802             core()->ReadMessage( |  | 
| 803                 h_passing[1], UserPointer<void>(buffer), |  | 
| 804                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 805                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 806   EXPECT_EQ(kWorldSize, num_bytes); |  | 
| 807   EXPECT_STREQ(kWorld, buffer); |  | 
| 808   EXPECT_EQ(1u, num_handles); |  | 
| 809   h_received = handles[0]; |  | 
| 810   EXPECT_NE(h_received, MOJO_HANDLE_INVALID); |  | 
| 811   EXPECT_NE(h_received, h_passing[0]); |  | 
| 812   EXPECT_NE(h_received, h_passing[1]); |  | 
| 813   EXPECT_NE(h_received, h_passed[0]); |  | 
| 814 |  | 
| 815   // Note: We rely on the Mojo system not re-using handle values very often. |  | 
| 816   EXPECT_NE(h_received, h_passed[1]); |  | 
| 817 |  | 
| 818   // |h_passed[1]| should no longer be valid; check that trying to close it |  | 
| 819   // fails. See above note. |  | 
| 820   EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, core()->Close(h_passed[1])); |  | 
| 821 |  | 
| 822   // Write to |h_passed[0]|. Should receive on |h_received|. |  | 
| 823   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 824             core()->WriteMessage(h_passed[0], UserPointer<const void>(kHello), |  | 
| 825                                  kHelloSize, NullUserPointer(), 0, |  | 
| 826                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 827   hss = kEmptyMojoHandleSignalsState; |  | 
| 828   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 829             core()->Wait(h_received, MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 830                          MakeUserPointer(&hss))); |  | 
| 831   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 832             hss.satisfied_signals); |  | 
| 833   EXPECT_EQ(kAllSignals, hss.satisfiable_signals); |  | 
| 834   num_bytes = kBufferSize; |  | 
| 835   num_handles = arraysize(handles); |  | 
| 836   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 837             core()->ReadMessage( |  | 
| 838                 h_received, UserPointer<void>(buffer), |  | 
| 839                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 840                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 841   EXPECT_EQ(kHelloSize, num_bytes); |  | 
| 842   EXPECT_STREQ(kHello, buffer); |  | 
| 843   EXPECT_EQ(0u, num_handles); |  | 
| 844 |  | 
| 845   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h_passing[0])); |  | 
| 846   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h_passing[1])); |  | 
| 847   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h_passed[0])); |  | 
| 848   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h_received)); |  | 
| 849 } |  | 
| 850 |  | 
| 851 TEST_F(CoreTest, DataPipe) { |  | 
| 852   MojoHandle ph, ch;  // p is for producer and c is for consumer. |  | 
| 853   MojoHandleSignalsState hss; |  | 
| 854 |  | 
| 855   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 856             core()->CreateDataPipe(NullUserPointer(), MakeUserPointer(&ph), |  | 
| 857                                    MakeUserPointer(&ch))); |  | 
| 858   // Should get two distinct, valid handles. |  | 
| 859   EXPECT_NE(ph, MOJO_HANDLE_INVALID); |  | 
| 860   EXPECT_NE(ch, MOJO_HANDLE_INVALID); |  | 
| 861   EXPECT_NE(ph, ch); |  | 
| 862 |  | 
| 863   // Producer should be never-readable, but already writable. |  | 
| 864   hss = kEmptyMojoHandleSignalsState; |  | 
| 865   EXPECT_EQ( |  | 
| 866       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 867       core()->Wait(ph, MOJO_HANDLE_SIGNAL_READABLE, 0, MakeUserPointer(&hss))); |  | 
| 868   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss.satisfied_signals); |  | 
| 869   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 870             hss.satisfiable_signals); |  | 
| 871   hss = kEmptyMojoHandleSignalsState; |  | 
| 872   EXPECT_EQ(MOJO_RESULT_OK, core()->Wait(ph, MOJO_HANDLE_SIGNAL_WRITABLE, 0, |  | 
| 873                                          MakeUserPointer(&hss))); |  | 
| 874   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE, hss.satisfied_signals); |  | 
| 875   EXPECT_EQ(MOJO_HANDLE_SIGNAL_WRITABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 876             hss.satisfiable_signals); |  | 
| 877 |  | 
| 878   // Consumer should be never-writable, and not yet readable. |  | 
| 879   hss = kFullMojoHandleSignalsState; |  | 
| 880   EXPECT_EQ( |  | 
| 881       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 882       core()->Wait(ch, MOJO_HANDLE_SIGNAL_WRITABLE, 0, MakeUserPointer(&hss))); |  | 
| 883   EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 884   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 885             hss.satisfiable_signals); |  | 
| 886   hss = kFullMojoHandleSignalsState; |  | 
| 887   EXPECT_EQ( |  | 
| 888       MOJO_RESULT_DEADLINE_EXCEEDED, |  | 
| 889       core()->Wait(ch, MOJO_HANDLE_SIGNAL_READABLE, 0, MakeUserPointer(&hss))); |  | 
| 890   EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 891   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 892             hss.satisfiable_signals); |  | 
| 893 |  | 
| 894   // Write. |  | 
| 895   signed char elements[2] = {'A', 'B'}; |  | 
| 896   uint32_t num_bytes = 2u; |  | 
| 897   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 898             core()->WriteData(ph, UserPointer<const void>(elements), |  | 
| 899                               MakeUserPointer(&num_bytes), |  | 
| 900                               MOJO_WRITE_DATA_FLAG_NONE)); |  | 
| 901   EXPECT_EQ(2u, num_bytes); |  | 
| 902 |  | 
| 903   // Consumer should now be readable. |  | 
| 904   hss = kEmptyMojoHandleSignalsState; |  | 
| 905   EXPECT_EQ(MOJO_RESULT_OK, core()->Wait(ch, MOJO_HANDLE_SIGNAL_READABLE, 0, |  | 
| 906                                          MakeUserPointer(&hss))); |  | 
| 907   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE, hss.satisfied_signals); |  | 
| 908   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 909             hss.satisfiable_signals); |  | 
| 910 |  | 
| 911   // Peek one character. |  | 
| 912   elements[0] = -1; |  | 
| 913   elements[1] = -1; |  | 
| 914   num_bytes = 1u; |  | 
| 915   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 916             core()->ReadData( |  | 
| 917                 ch, UserPointer<void>(elements), MakeUserPointer(&num_bytes), |  | 
| 918                 MOJO_READ_DATA_FLAG_NONE | MOJO_READ_DATA_FLAG_PEEK)); |  | 
| 919   EXPECT_EQ('A', elements[0]); |  | 
| 920   EXPECT_EQ(-1, elements[1]); |  | 
| 921 |  | 
| 922   // Read one character. |  | 
| 923   elements[0] = -1; |  | 
| 924   elements[1] = -1; |  | 
| 925   num_bytes = 1u; |  | 
| 926   EXPECT_EQ(MOJO_RESULT_OK, core()->ReadData(ch, UserPointer<void>(elements), |  | 
| 927                                              MakeUserPointer(&num_bytes), |  | 
| 928                                              MOJO_READ_DATA_FLAG_NONE)); |  | 
| 929   EXPECT_EQ('A', elements[0]); |  | 
| 930   EXPECT_EQ(-1, elements[1]); |  | 
| 931 |  | 
| 932   // Two-phase write. |  | 
| 933   void* write_ptr = nullptr; |  | 
| 934   num_bytes = 0u; |  | 
| 935   ASSERT_EQ(MOJO_RESULT_OK, |  | 
| 936             core()->BeginWriteData(ph, MakeUserPointer(&write_ptr), |  | 
| 937                                    MakeUserPointer(&num_bytes), |  | 
| 938                                    MOJO_WRITE_DATA_FLAG_NONE)); |  | 
| 939   // We count on the default options providing a decent buffer size. |  | 
| 940   ASSERT_GE(num_bytes, 3u); |  | 
| 941 |  | 
| 942   // Trying to do a normal write during a two-phase write should fail. |  | 
| 943   elements[0] = 'X'; |  | 
| 944   num_bytes = 1u; |  | 
| 945   EXPECT_EQ(MOJO_RESULT_BUSY, |  | 
| 946             core()->WriteData(ph, UserPointer<const void>(elements), |  | 
| 947                               MakeUserPointer(&num_bytes), |  | 
| 948                               MOJO_WRITE_DATA_FLAG_NONE)); |  | 
| 949 |  | 
| 950   // Actually write the data, and complete it now. |  | 
| 951   static_cast<char*>(write_ptr)[0] = 'C'; |  | 
| 952   static_cast<char*>(write_ptr)[1] = 'D'; |  | 
| 953   static_cast<char*>(write_ptr)[2] = 'E'; |  | 
| 954   EXPECT_EQ(MOJO_RESULT_OK, core()->EndWriteData(ph, 3u)); |  | 
| 955 |  | 
| 956   // Query how much data we have. |  | 
| 957   num_bytes = 0; |  | 
| 958   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 959             core()->ReadData(ch, NullUserPointer(), MakeUserPointer(&num_bytes), |  | 
| 960                              MOJO_READ_DATA_FLAG_QUERY)); |  | 
| 961   EXPECT_EQ(4u, num_bytes); |  | 
| 962 |  | 
| 963   // Try to query with peek. Should fail. |  | 
| 964   num_bytes = 0; |  | 
| 965   EXPECT_EQ( |  | 
| 966       MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 967       core()->ReadData(ch, NullUserPointer(), MakeUserPointer(&num_bytes), |  | 
| 968                        MOJO_READ_DATA_FLAG_QUERY | MOJO_READ_DATA_FLAG_PEEK)); |  | 
| 969   EXPECT_EQ(0u, num_bytes); |  | 
| 970 |  | 
| 971   // Try to discard ten characters, in all-or-none mode. Should fail. |  | 
| 972   num_bytes = 10; |  | 
| 973   EXPECT_EQ(MOJO_RESULT_OUT_OF_RANGE, |  | 
| 974             core()->ReadData( |  | 
| 975                 ch, NullUserPointer(), MakeUserPointer(&num_bytes), |  | 
| 976                 MOJO_READ_DATA_FLAG_DISCARD | MOJO_READ_DATA_FLAG_ALL_OR_NONE)); |  | 
| 977 |  | 
| 978   // Try to discard two characters, in peek mode. Should fail. |  | 
| 979   num_bytes = 2; |  | 
| 980   EXPECT_EQ( |  | 
| 981       MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 982       core()->ReadData(ch, NullUserPointer(), MakeUserPointer(&num_bytes), |  | 
| 983                        MOJO_READ_DATA_FLAG_DISCARD | MOJO_READ_DATA_FLAG_PEEK)); |  | 
| 984 |  | 
| 985   // Discard two characters. |  | 
| 986   num_bytes = 2; |  | 
| 987   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 988             core()->ReadData( |  | 
| 989                 ch, NullUserPointer(), MakeUserPointer(&num_bytes), |  | 
| 990                 MOJO_READ_DATA_FLAG_DISCARD | MOJO_READ_DATA_FLAG_ALL_OR_NONE)); |  | 
| 991 |  | 
| 992   // Try a two-phase read of the remaining two bytes with peek. Should fail. |  | 
| 993   const void* read_ptr = nullptr; |  | 
| 994   num_bytes = 2; |  | 
| 995   ASSERT_EQ(MOJO_RESULT_INVALID_ARGUMENT, |  | 
| 996             core()->BeginReadData(ch, MakeUserPointer(&read_ptr), |  | 
| 997                                   MakeUserPointer(&num_bytes), |  | 
| 998                                   MOJO_READ_DATA_FLAG_PEEK)); |  | 
| 999 |  | 
| 1000   // Read the remaining two characters, in two-phase mode (all-or-none). |  | 
| 1001   num_bytes = 2; |  | 
| 1002   ASSERT_EQ(MOJO_RESULT_OK, |  | 
| 1003             core()->BeginReadData(ch, MakeUserPointer(&read_ptr), |  | 
| 1004                                   MakeUserPointer(&num_bytes), |  | 
| 1005                                   MOJO_READ_DATA_FLAG_ALL_OR_NONE)); |  | 
| 1006   // Note: Count on still being able to do the contiguous read here. |  | 
| 1007   ASSERT_EQ(2u, num_bytes); |  | 
| 1008 |  | 
| 1009   // Discarding right now should fail. |  | 
| 1010   num_bytes = 1; |  | 
| 1011   EXPECT_EQ(MOJO_RESULT_BUSY, |  | 
| 1012             core()->ReadData(ch, NullUserPointer(), MakeUserPointer(&num_bytes), |  | 
| 1013                              MOJO_READ_DATA_FLAG_DISCARD)); |  | 
| 1014 |  | 
| 1015   // Actually check our data and end the two-phase read. |  | 
| 1016   EXPECT_EQ('D', static_cast<const char*>(read_ptr)[0]); |  | 
| 1017   EXPECT_EQ('E', static_cast<const char*>(read_ptr)[1]); |  | 
| 1018   EXPECT_EQ(MOJO_RESULT_OK, core()->EndReadData(ch, 2u)); |  | 
| 1019 |  | 
| 1020   // Consumer should now be no longer readable. |  | 
| 1021   hss = kFullMojoHandleSignalsState; |  | 
| 1022   EXPECT_EQ( |  | 
| 1023       MOJO_RESULT_DEADLINE_EXCEEDED, |  | 
| 1024       core()->Wait(ch, MOJO_HANDLE_SIGNAL_READABLE, 0, MakeUserPointer(&hss))); |  | 
| 1025   EXPECT_EQ(0u, hss.satisfied_signals); |  | 
| 1026   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 1027             hss.satisfiable_signals); |  | 
| 1028 |  | 
| 1029   // TODO(vtl): More. |  | 
| 1030 |  | 
| 1031   // Close the producer. |  | 
| 1032   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(ph)); |  | 
| 1033 |  | 
| 1034   // The consumer should now be never-readable. |  | 
| 1035   hss = kFullMojoHandleSignalsState; |  | 
| 1036   EXPECT_EQ( |  | 
| 1037       MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 1038       core()->Wait(ch, MOJO_HANDLE_SIGNAL_READABLE, 0, MakeUserPointer(&hss))); |  | 
| 1039   EXPECT_EQ(MOJO_HANDLE_SIGNAL_PEER_CLOSED, hss.satisfied_signals); |  | 
| 1040   EXPECT_EQ(MOJO_HANDLE_SIGNAL_PEER_CLOSED, hss.satisfiable_signals); |  | 
| 1041 |  | 
| 1042   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(ch)); |  | 
| 1043 } |  | 
| 1044 |  | 
| 1045 // Tests passing data pipe producer and consumer handles. |  | 
| 1046 TEST_F(CoreTest, MessagePipeBasicLocalHandlePassing2) { |  | 
| 1047   const char kHello[] = "hello"; |  | 
| 1048   const uint32_t kHelloSize = static_cast<uint32_t>(sizeof(kHello)); |  | 
| 1049   const char kWorld[] = "world!!!"; |  | 
| 1050   const uint32_t kWorldSize = static_cast<uint32_t>(sizeof(kWorld)); |  | 
| 1051   char buffer[100]; |  | 
| 1052   const uint32_t kBufferSize = static_cast<uint32_t>(sizeof(buffer)); |  | 
| 1053   uint32_t num_bytes; |  | 
| 1054   MojoHandle handles[10]; |  | 
| 1055   uint32_t num_handles; |  | 
| 1056   MojoHandleSignalsState hss; |  | 
| 1057 |  | 
| 1058   MojoHandle h_passing[2]; |  | 
| 1059   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1060             core()->CreateMessagePipe(NullUserPointer(), |  | 
| 1061                                       MakeUserPointer(&h_passing[0]), |  | 
| 1062                                       MakeUserPointer(&h_passing[1]))); |  | 
| 1063 |  | 
| 1064   MojoHandle ph, ch; |  | 
| 1065   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1066             core()->CreateDataPipe(NullUserPointer(), MakeUserPointer(&ph), |  | 
| 1067                                    MakeUserPointer(&ch))); |  | 
| 1068 |  | 
| 1069   // Send |ch| from |h_passing[0]| to |h_passing[1]|. |  | 
| 1070   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1071             core()->WriteMessage(h_passing[0], UserPointer<const void>(kHello), |  | 
| 1072                                  kHelloSize, MakeUserPointer(&ch), 1, |  | 
| 1073                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 1074   hss = kEmptyMojoHandleSignalsState; |  | 
| 1075   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1076             core()->Wait(h_passing[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 1077                          MakeUserPointer(&hss))); |  | 
| 1078   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 1079             hss.satisfied_signals); |  | 
| 1080   EXPECT_EQ(kAllSignals, hss.satisfiable_signals); |  | 
| 1081   num_bytes = kBufferSize; |  | 
| 1082   num_handles = arraysize(handles); |  | 
| 1083   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1084             core()->ReadMessage( |  | 
| 1085                 h_passing[1], UserPointer<void>(buffer), |  | 
| 1086                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 1087                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 1088   EXPECT_EQ(kHelloSize, num_bytes); |  | 
| 1089   EXPECT_STREQ(kHello, buffer); |  | 
| 1090   EXPECT_EQ(1u, num_handles); |  | 
| 1091   MojoHandle ch_received = handles[0]; |  | 
| 1092   EXPECT_NE(ch_received, MOJO_HANDLE_INVALID); |  | 
| 1093   EXPECT_NE(ch_received, h_passing[0]); |  | 
| 1094   EXPECT_NE(ch_received, h_passing[1]); |  | 
| 1095   EXPECT_NE(ch_received, ph); |  | 
| 1096 |  | 
| 1097   // Note: We rely on the Mojo system not re-using handle values very often. |  | 
| 1098   EXPECT_NE(ch_received, ch); |  | 
| 1099 |  | 
| 1100   // |ch| should no longer be valid; check that trying to close it fails. See |  | 
| 1101   // above note. |  | 
| 1102   EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, core()->Close(ch)); |  | 
| 1103 |  | 
| 1104   // Write to |ph|. Should receive on |ch_received|. |  | 
| 1105   num_bytes = kWorldSize; |  | 
| 1106   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1107             core()->WriteData(ph, UserPointer<const void>(kWorld), |  | 
| 1108                               MakeUserPointer(&num_bytes), |  | 
| 1109                               MOJO_WRITE_DATA_FLAG_ALL_OR_NONE)); |  | 
| 1110   hss = kEmptyMojoHandleSignalsState; |  | 
| 1111   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1112             core()->Wait(ch_received, MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 1113                          MakeUserPointer(&hss))); |  | 
| 1114   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE, hss.satisfied_signals); |  | 
| 1115   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 1116             hss.satisfiable_signals); |  | 
| 1117   num_bytes = kBufferSize; |  | 
| 1118   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1119             core()->ReadData(ch_received, UserPointer<void>(buffer), |  | 
| 1120                              MakeUserPointer(&num_bytes), |  | 
| 1121                              MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 1122   EXPECT_EQ(kWorldSize, num_bytes); |  | 
| 1123   EXPECT_STREQ(kWorld, buffer); |  | 
| 1124 |  | 
| 1125   // Now pass |ph| in the same direction. |  | 
| 1126   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1127             core()->WriteMessage(h_passing[0], UserPointer<const void>(kWorld), |  | 
| 1128                                  kWorldSize, MakeUserPointer(&ph), 1, |  | 
| 1129                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 1130   hss = kEmptyMojoHandleSignalsState; |  | 
| 1131   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1132             core()->Wait(h_passing[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 1133                          MakeUserPointer(&hss))); |  | 
| 1134   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 1135             hss.satisfied_signals); |  | 
| 1136   EXPECT_EQ(kAllSignals, hss.satisfiable_signals); |  | 
| 1137   num_bytes = kBufferSize; |  | 
| 1138   num_handles = arraysize(handles); |  | 
| 1139   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1140             core()->ReadMessage( |  | 
| 1141                 h_passing[1], UserPointer<void>(buffer), |  | 
| 1142                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 1143                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 1144   EXPECT_EQ(kWorldSize, num_bytes); |  | 
| 1145   EXPECT_STREQ(kWorld, buffer); |  | 
| 1146   EXPECT_EQ(1u, num_handles); |  | 
| 1147   MojoHandle ph_received = handles[0]; |  | 
| 1148   EXPECT_NE(ph_received, MOJO_HANDLE_INVALID); |  | 
| 1149   EXPECT_NE(ph_received, h_passing[0]); |  | 
| 1150   EXPECT_NE(ph_received, h_passing[1]); |  | 
| 1151   EXPECT_NE(ph_received, ch_received); |  | 
| 1152 |  | 
| 1153   // Again, rely on the Mojo system not re-using handle values very often. |  | 
| 1154   EXPECT_NE(ph_received, ph); |  | 
| 1155 |  | 
| 1156   // |ph| should no longer be valid; check that trying to close it fails. See |  | 
| 1157   // above note. |  | 
| 1158   EXPECT_EQ(MOJO_RESULT_INVALID_ARGUMENT, core()->Close(ph)); |  | 
| 1159 |  | 
| 1160   // Write to |ph_received|. Should receive on |ch_received|. |  | 
| 1161   num_bytes = kHelloSize; |  | 
| 1162   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1163             core()->WriteData(ph_received, UserPointer<const void>(kHello), |  | 
| 1164                               MakeUserPointer(&num_bytes), |  | 
| 1165                               MOJO_WRITE_DATA_FLAG_ALL_OR_NONE)); |  | 
| 1166   hss = kEmptyMojoHandleSignalsState; |  | 
| 1167   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1168             core()->Wait(ch_received, MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 1169                          MakeUserPointer(&hss))); |  | 
| 1170   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE, hss.satisfied_signals); |  | 
| 1171   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 1172             hss.satisfiable_signals); |  | 
| 1173   num_bytes = kBufferSize; |  | 
| 1174   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1175             core()->ReadData(ch_received, UserPointer<void>(buffer), |  | 
| 1176                              MakeUserPointer(&num_bytes), |  | 
| 1177                              MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 1178   EXPECT_EQ(kHelloSize, num_bytes); |  | 
| 1179   EXPECT_STREQ(kHello, buffer); |  | 
| 1180 |  | 
| 1181   ph = ph_received; |  | 
| 1182   ph_received = MOJO_HANDLE_INVALID; |  | 
| 1183   ch = ch_received; |  | 
| 1184   ch_received = MOJO_HANDLE_INVALID; |  | 
| 1185 |  | 
| 1186   // Make sure that |ph| can't be sent if it's in a two-phase write. |  | 
| 1187   void* write_ptr = nullptr; |  | 
| 1188   num_bytes = 0; |  | 
| 1189   ASSERT_EQ(MOJO_RESULT_OK, |  | 
| 1190             core()->BeginWriteData(ph, MakeUserPointer(&write_ptr), |  | 
| 1191                                    MakeUserPointer(&num_bytes), |  | 
| 1192                                    MOJO_WRITE_DATA_FLAG_NONE)); |  | 
| 1193   ASSERT_GE(num_bytes, 1u); |  | 
| 1194   EXPECT_EQ(MOJO_RESULT_BUSY, |  | 
| 1195             core()->WriteMessage(h_passing[0], UserPointer<const void>(kHello), |  | 
| 1196                                  kHelloSize, MakeUserPointer(&ph), 1, |  | 
| 1197                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 1198 |  | 
| 1199   // But |ch| can, even if |ph| is in a two-phase write. |  | 
| 1200   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1201             core()->WriteMessage(h_passing[0], UserPointer<const void>(kHello), |  | 
| 1202                                  kHelloSize, MakeUserPointer(&ch), 1, |  | 
| 1203                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 1204   ch = MOJO_HANDLE_INVALID; |  | 
| 1205   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1206             core()->Wait(h_passing[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 1207                          NullUserPointer())); |  | 
| 1208   num_bytes = kBufferSize; |  | 
| 1209   num_handles = arraysize(handles); |  | 
| 1210   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1211             core()->ReadMessage( |  | 
| 1212                 h_passing[1], UserPointer<void>(buffer), |  | 
| 1213                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 1214                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 1215   EXPECT_EQ(kHelloSize, num_bytes); |  | 
| 1216   EXPECT_STREQ(kHello, buffer); |  | 
| 1217   EXPECT_EQ(1u, num_handles); |  | 
| 1218   ch = handles[0]; |  | 
| 1219   EXPECT_NE(ch, MOJO_HANDLE_INVALID); |  | 
| 1220 |  | 
| 1221   // Complete the two-phase write. |  | 
| 1222   static_cast<char*>(write_ptr)[0] = 'x'; |  | 
| 1223   EXPECT_EQ(MOJO_RESULT_OK, core()->EndWriteData(ph, 1)); |  | 
| 1224 |  | 
| 1225   // Wait for |ch| to be readable. |  | 
| 1226   hss = kEmptyMojoHandleSignalsState; |  | 
| 1227   EXPECT_EQ(MOJO_RESULT_OK, core()->Wait(ch, MOJO_HANDLE_SIGNAL_READABLE, |  | 
| 1228                                          1000000000, MakeUserPointer(&hss))); |  | 
| 1229   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE, hss.satisfied_signals); |  | 
| 1230   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_PEER_CLOSED, |  | 
| 1231             hss.satisfiable_signals); |  | 
| 1232 |  | 
| 1233   // Make sure that |ch| can't be sent if it's in a two-phase read. |  | 
| 1234   const void* read_ptr = nullptr; |  | 
| 1235   num_bytes = 1; |  | 
| 1236   ASSERT_EQ(MOJO_RESULT_OK, |  | 
| 1237             core()->BeginReadData(ch, MakeUserPointer(&read_ptr), |  | 
| 1238                                   MakeUserPointer(&num_bytes), |  | 
| 1239                                   MOJO_READ_DATA_FLAG_ALL_OR_NONE)); |  | 
| 1240   EXPECT_EQ(MOJO_RESULT_BUSY, |  | 
| 1241             core()->WriteMessage(h_passing[0], UserPointer<const void>(kHello), |  | 
| 1242                                  kHelloSize, MakeUserPointer(&ch), 1, |  | 
| 1243                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 1244 |  | 
| 1245   // But |ph| can, even if |ch| is in a two-phase read. |  | 
| 1246   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1247             core()->WriteMessage(h_passing[0], UserPointer<const void>(kWorld), |  | 
| 1248                                  kWorldSize, MakeUserPointer(&ph), 1, |  | 
| 1249                                  MOJO_WRITE_MESSAGE_FLAG_NONE)); |  | 
| 1250   ph = MOJO_HANDLE_INVALID; |  | 
| 1251   hss = kEmptyMojoHandleSignalsState; |  | 
| 1252   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1253             core()->Wait(h_passing[1], MOJO_HANDLE_SIGNAL_READABLE, 1000000000, |  | 
| 1254                          MakeUserPointer(&hss))); |  | 
| 1255   EXPECT_EQ(MOJO_HANDLE_SIGNAL_READABLE | MOJO_HANDLE_SIGNAL_WRITABLE, |  | 
| 1256             hss.satisfied_signals); |  | 
| 1257   EXPECT_EQ(kAllSignals, hss.satisfiable_signals); |  | 
| 1258   num_bytes = kBufferSize; |  | 
| 1259   num_handles = arraysize(handles); |  | 
| 1260   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1261             core()->ReadMessage( |  | 
| 1262                 h_passing[1], UserPointer<void>(buffer), |  | 
| 1263                 MakeUserPointer(&num_bytes), MakeUserPointer(handles), |  | 
| 1264                 MakeUserPointer(&num_handles), MOJO_READ_MESSAGE_FLAG_NONE)); |  | 
| 1265   EXPECT_EQ(kWorldSize, num_bytes); |  | 
| 1266   EXPECT_STREQ(kWorld, buffer); |  | 
| 1267   EXPECT_EQ(1u, num_handles); |  | 
| 1268   ph = handles[0]; |  | 
| 1269   EXPECT_NE(ph, MOJO_HANDLE_INVALID); |  | 
| 1270 |  | 
| 1271   // Complete the two-phase read. |  | 
| 1272   EXPECT_EQ('x', static_cast<const char*>(read_ptr)[0]); |  | 
| 1273   EXPECT_EQ(MOJO_RESULT_OK, core()->EndReadData(ch, 1)); |  | 
| 1274 |  | 
| 1275   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h_passing[0])); |  | 
| 1276   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h_passing[1])); |  | 
| 1277   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(ph)); |  | 
| 1278   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(ch)); |  | 
| 1279 } |  | 
| 1280 |  | 
| 1281 struct TestAsyncWaiter { |  | 
| 1282   TestAsyncWaiter() : result(MOJO_RESULT_UNKNOWN) {} |  | 
| 1283 |  | 
| 1284   void Awake(MojoResult r) { result = r; } |  | 
| 1285 |  | 
| 1286   MojoResult result; |  | 
| 1287 }; |  | 
| 1288 |  | 
| 1289 TEST_F(CoreTest, AsyncWait) { |  | 
| 1290   TestAsyncWaiter waiter; |  | 
| 1291   MockHandleInfo info; |  | 
| 1292   MojoHandle h = CreateMockHandle(&info); |  | 
| 1293 |  | 
| 1294   EXPECT_EQ(MOJO_RESULT_FAILED_PRECONDITION, |  | 
| 1295             core()->AsyncWait(h, MOJO_HANDLE_SIGNAL_READABLE, |  | 
| 1296                               base::Bind(&TestAsyncWaiter::Awake, |  | 
| 1297                                          base::Unretained(&waiter)))); |  | 
| 1298   EXPECT_EQ(0u, info.GetAddedAwakableSize()); |  | 
| 1299 |  | 
| 1300   info.AllowAddAwakable(true); |  | 
| 1301   EXPECT_EQ(MOJO_RESULT_OK, |  | 
| 1302             core()->AsyncWait(h, MOJO_HANDLE_SIGNAL_READABLE, |  | 
| 1303                               base::Bind(&TestAsyncWaiter::Awake, |  | 
| 1304                                          base::Unretained(&waiter)))); |  | 
| 1305   EXPECT_EQ(1u, info.GetAddedAwakableSize()); |  | 
| 1306 |  | 
| 1307   EXPECT_FALSE(info.GetAddedAwakableAt(0)->Awake(MOJO_RESULT_BUSY, 0)); |  | 
| 1308   EXPECT_EQ(MOJO_RESULT_BUSY, waiter.result); |  | 
| 1309 |  | 
| 1310   EXPECT_EQ(MOJO_RESULT_OK, core()->Close(h)); |  | 
| 1311 } |  | 
| 1312 |  | 
| 1313 // TODO(vtl): Test |DuplicateBufferHandle()| and |MapBuffer()|. |  | 
| 1314 |  | 
| 1315 }  // namespace |  | 
| 1316 }  // namespace system |  | 
| 1317 }  // namespace mojo |  | 
| OLD | NEW | 
|---|