Home | History | Annotate | Download | only in streams
      1 // Copyright 2015 The Chromium OS 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 <brillo/streams/stream.h>
      6 
      7 #include <limits>
      8 
      9 #include <base/callback.h>
     10 #include <gmock/gmock.h>
     11 #include <gtest/gtest.h>
     12 
     13 #include <brillo/bind_lambda.h>
     14 #include <brillo/message_loops/fake_message_loop.h>
     15 #include <brillo/streams/stream_errors.h>
     16 
     17 using testing::DoAll;
     18 using testing::InSequence;
     19 using testing::Return;
     20 using testing::SaveArg;
     21 using testing::SetArgPointee;
     22 using testing::_;
     23 
     24 namespace brillo {
     25 
     26 using AccessMode = Stream::AccessMode;
     27 using Whence = Stream::Whence;
     28 
     29 // To verify "non-trivial" methods implemented in Stream, mock out the
     30 // "trivial" methods to make sure the ones we are interested in testing
     31 // actually end up calling the expected methods with right parameters.
     32 class MockStreamImpl : public Stream {
     33  public:
     34   MockStreamImpl() = default;
     35 
     36   MOCK_CONST_METHOD0(IsOpen, bool());
     37   MOCK_CONST_METHOD0(CanRead, bool());
     38   MOCK_CONST_METHOD0(CanWrite, bool());
     39   MOCK_CONST_METHOD0(CanSeek, bool());
     40   MOCK_CONST_METHOD0(CanGetSize, bool());
     41 
     42   MOCK_CONST_METHOD0(GetSize, uint64_t());
     43   MOCK_METHOD2(SetSizeBlocking, bool(uint64_t, ErrorPtr*));
     44   MOCK_CONST_METHOD0(GetRemainingSize, uint64_t());
     45 
     46   MOCK_CONST_METHOD0(GetPosition, uint64_t());
     47   MOCK_METHOD4(Seek, bool(int64_t, Whence, uint64_t*, ErrorPtr*));
     48 
     49   // Omitted: ReadAsync
     50   // Omitted: ReadAllAsync
     51   MOCK_METHOD5(ReadNonBlocking, bool(void*, size_t, size_t*, bool*, ErrorPtr*));
     52   // Omitted: ReadBlocking
     53   // Omitted: ReadAllBlocking
     54 
     55   // Omitted: WriteAsync
     56   // Omitted: WriteAllAsync
     57   MOCK_METHOD4(WriteNonBlocking, bool(const void*, size_t, size_t*, ErrorPtr*));
     58   // Omitted: WriteBlocking
     59   // Omitted: WriteAllBlocking
     60 
     61   MOCK_METHOD1(FlushBlocking, bool(ErrorPtr*));
     62   MOCK_METHOD1(CloseBlocking, bool(ErrorPtr*));
     63 
     64   MOCK_METHOD3(WaitForData, bool(AccessMode,
     65                                  const base::Callback<void(AccessMode)>&,
     66                                  ErrorPtr*));
     67   MOCK_METHOD4(WaitForDataBlocking,
     68                bool(AccessMode, base::TimeDelta, AccessMode*, ErrorPtr*));
     69 
     70  private:
     71   DISALLOW_COPY_AND_ASSIGN(MockStreamImpl);
     72 };
     73 
     74 TEST(Stream, TruncateBlocking) {
     75   MockStreamImpl stream_mock;
     76   EXPECT_CALL(stream_mock, GetPosition()).WillOnce(Return(123));
     77   EXPECT_CALL(stream_mock, SetSizeBlocking(123, _)).WillOnce(Return(true));
     78   EXPECT_TRUE(stream_mock.TruncateBlocking(nullptr));
     79 }
     80 
     81 TEST(Stream, SetPosition) {
     82   MockStreamImpl stream_mock;
     83   EXPECT_CALL(stream_mock, Seek(12345, Whence::FROM_BEGIN, _, _))
     84       .WillOnce(Return(true));
     85   EXPECT_TRUE(stream_mock.SetPosition(12345, nullptr));
     86 
     87   // Test too large an offset (that doesn't fit in signed 64 bit value).
     88   ErrorPtr error;
     89   uint64_t max_offset = std::numeric_limits<int64_t>::max();
     90   EXPECT_CALL(stream_mock, Seek(max_offset, _, _, _))
     91       .WillOnce(Return(true));
     92   EXPECT_TRUE(stream_mock.SetPosition(max_offset, nullptr));
     93 
     94   EXPECT_FALSE(stream_mock.SetPosition(max_offset + 1, &error));
     95   EXPECT_EQ(errors::stream::kDomain, error->GetDomain());
     96   EXPECT_EQ(errors::stream::kInvalidParameter, error->GetCode());
     97 }
     98 
     99 TEST(Stream, ReadAsync) {
    100   size_t read_size = 0;
    101   bool succeeded = false;
    102   bool failed = false;
    103   auto success_callback = [](size_t* read_size, bool* succeeded,size_t size) {
    104     *read_size = size;
    105     *succeeded = true;
    106   };
    107   auto error_callback = [](bool* failed, const Error* /* error */) {
    108     *failed = true;
    109   };
    110 
    111   MockStreamImpl stream_mock;
    112   base::Callback<void(AccessMode)> data_callback;
    113   char buf[10];
    114 
    115   // This sets up an initial non blocking read that would block, so ReadAsync()
    116   // should wait for more data.
    117   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 10, _, _, _))
    118       .WillOnce(
    119           DoAll(SetArgPointee<2>(0), SetArgPointee<3>(false), Return(true)));
    120   EXPECT_CALL(stream_mock, WaitForData(AccessMode::READ, _, _))
    121       .WillOnce(DoAll(SaveArg<1>(&data_callback), Return(true)));
    122   EXPECT_TRUE(stream_mock.ReadAsync(
    123       buf,
    124       sizeof(buf),
    125       base::Bind(success_callback,
    126                  base::Unretained(&read_size),
    127                  base::Unretained(&succeeded)),
    128       base::Bind(error_callback, base::Unretained(&failed)),
    129       nullptr));
    130   EXPECT_EQ(0u, read_size);
    131   EXPECT_FALSE(succeeded);
    132   EXPECT_FALSE(failed);
    133 
    134   // Since the previous call is waiting for the data to be available, we can't
    135   // schedule another read.
    136   ErrorPtr error;
    137   EXPECT_FALSE(stream_mock.ReadAsync(
    138       buf,
    139       sizeof(buf),
    140       base::Bind(success_callback,
    141                  base::Unretained(&read_size),
    142                  base::Unretained(&succeeded)),
    143       base::Bind(error_callback, base::Unretained(&failed)),
    144       &error));
    145   EXPECT_EQ(errors::stream::kDomain, error->GetDomain());
    146   EXPECT_EQ(errors::stream::kOperationNotSupported, error->GetCode());
    147   EXPECT_EQ("Another asynchronous operation is still pending",
    148             error->GetMessage());
    149 
    150   // Making the data available via data_callback should not schedule the
    151   // success callback from the main loop and run it directly instead.
    152   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 10, _, _, _))
    153       .WillOnce(DoAll(SetArgPointee<2>(7),
    154                       SetArgPointee<3>(false),
    155                       Return(true)));
    156   data_callback.Run(AccessMode::READ);
    157   EXPECT_EQ(7u, read_size);
    158   EXPECT_FALSE(failed);
    159 }
    160 
    161 TEST(Stream, ReadAsync_DontWaitForData) {
    162   bool succeeded = false;
    163   bool failed = false;
    164   auto success_callback = [](bool* succeeded, size_t /* size */) {
    165     *succeeded = true;
    166   };
    167   auto error_callback = [](bool* failed, const Error* /* error */) {
    168     *failed = true;
    169   };
    170 
    171   MockStreamImpl stream_mock;
    172   char buf[10];
    173   FakeMessageLoop fake_loop_{nullptr};
    174   fake_loop_.SetAsCurrent();
    175 
    176   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 10, _, _, _))
    177       .WillOnce(
    178           DoAll(SetArgPointee<2>(5), SetArgPointee<3>(false), Return(true)));
    179   EXPECT_CALL(stream_mock, WaitForData(_, _, _)).Times(0);
    180   EXPECT_TRUE(stream_mock.ReadAsync(
    181       buf,
    182       sizeof(buf),
    183       base::Bind(success_callback, base::Unretained(&succeeded)),
    184       base::Bind(error_callback, base::Unretained(&failed)),
    185       nullptr));
    186   // Even if ReadNonBlocking() returned some data without waiting, the
    187   // |success_callback| should not run yet.
    188   EXPECT_TRUE(fake_loop_.PendingTasks());
    189   EXPECT_FALSE(succeeded);
    190   EXPECT_FALSE(failed);
    191 
    192   // Since the previous callback is still waiting in the main loop, we can't
    193   // schedule another read yet.
    194   ErrorPtr error;
    195   EXPECT_FALSE(stream_mock.ReadAsync(
    196       buf,
    197       sizeof(buf),
    198       base::Bind(success_callback, base::Unretained(&succeeded)),
    199       base::Bind(error_callback, base::Unretained(&failed)),
    200       &error));
    201   EXPECT_EQ(errors::stream::kDomain, error->GetDomain());
    202   EXPECT_EQ(errors::stream::kOperationNotSupported, error->GetCode());
    203   EXPECT_EQ("Another asynchronous operation is still pending",
    204             error->GetMessage());
    205 
    206   fake_loop_.Run();
    207   EXPECT_TRUE(succeeded);
    208   EXPECT_FALSE(failed);
    209 }
    210 
    211 TEST(Stream, ReadAllAsync) {
    212   bool succeeded = false;
    213   bool failed = false;
    214   auto success_callback = [](bool* succeeded) { *succeeded = true; };
    215   auto error_callback = [](bool* failed, const Error* /* error */) {
    216     *failed = true;
    217   };
    218 
    219   MockStreamImpl stream_mock;
    220   base::Callback<void(AccessMode)> data_callback;
    221   char buf[10];
    222 
    223   // This sets up an initial non blocking read that would block, so
    224   // ReadAllAsync() should wait for more data.
    225   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 10, _, _, _))
    226       .WillOnce(
    227           DoAll(SetArgPointee<2>(0), SetArgPointee<3>(false), Return(true)));
    228   EXPECT_CALL(stream_mock, WaitForData(AccessMode::READ, _, _))
    229       .WillOnce(DoAll(SaveArg<1>(&data_callback), Return(true)));
    230   EXPECT_TRUE(stream_mock.ReadAllAsync(
    231       buf,
    232       sizeof(buf),
    233       base::Bind(success_callback, base::Unretained(&succeeded)),
    234       base::Bind(error_callback, base::Unretained(&failed)),
    235       nullptr));
    236   EXPECT_FALSE(succeeded);
    237   EXPECT_FALSE(failed);
    238   testing::Mock::VerifyAndClearExpectations(&stream_mock);
    239 
    240   // ReadAllAsync() will try to read non blocking until the read would block
    241   // before it waits for the data to be available again.
    242   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 10, _, _, _))
    243       .WillOnce(DoAll(SetArgPointee<2>(7),
    244                       SetArgPointee<3>(false),
    245                       Return(true)));
    246   EXPECT_CALL(stream_mock, ReadNonBlocking(buf + 7, 3, _, _, _))
    247       .WillOnce(
    248           DoAll(SetArgPointee<2>(0), SetArgPointee<3>(false), Return(true)));
    249   EXPECT_CALL(stream_mock, WaitForData(AccessMode::READ, _, _))
    250       .WillOnce(DoAll(SaveArg<1>(&data_callback), Return(true)));
    251   data_callback.Run(AccessMode::READ);
    252   EXPECT_FALSE(succeeded);
    253   EXPECT_FALSE(failed);
    254   testing::Mock::VerifyAndClearExpectations(&stream_mock);
    255 
    256   EXPECT_CALL(stream_mock, ReadNonBlocking(buf + 7, 3, _, _, _))
    257       .WillOnce(DoAll(SetArgPointee<2>(3),
    258                       SetArgPointee<3>(true),
    259                       Return(true)));
    260   data_callback.Run(AccessMode::READ);
    261   EXPECT_TRUE(succeeded);
    262   EXPECT_FALSE(failed);
    263 }
    264 
    265 TEST(Stream, ReadAllAsync_EOS) {
    266   bool succeeded = false;
    267   bool failed = false;
    268   auto success_callback = [](bool* succeeded) { *succeeded = true; };
    269   auto error_callback = [](bool* failed, const Error* error) {
    270     ASSERT_EQ(errors::stream::kDomain, error->GetDomain());
    271     ASSERT_EQ(errors::stream::kPartialData, error->GetCode());
    272     *failed = true;
    273   };
    274 
    275   MockStreamImpl stream_mock;
    276   base::Callback<void(AccessMode)> data_callback;
    277   char buf[10];
    278 
    279   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 10, _, _, _))
    280       .WillOnce(
    281           DoAll(SetArgPointee<2>(0), SetArgPointee<3>(false), Return(true)));
    282   EXPECT_CALL(stream_mock, WaitForData(AccessMode::READ, _, _))
    283       .WillOnce(DoAll(SaveArg<1>(&data_callback), Return(true)));
    284   EXPECT_TRUE(stream_mock.ReadAllAsync(
    285       buf,
    286       sizeof(buf),
    287       base::Bind(success_callback, base::Unretained(&succeeded)),
    288       base::Bind(error_callback, base::Unretained(&failed)),
    289       nullptr));
    290 
    291   // ReadAsyncAll() should finish and fail once ReadNonBlocking() returns an
    292   // end-of-stream condition.
    293   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 10, _, _, _))
    294       .WillOnce(DoAll(SetArgPointee<2>(7),
    295                       SetArgPointee<3>(true),
    296                       Return(true)));
    297   data_callback.Run(AccessMode::READ);
    298   EXPECT_FALSE(succeeded);
    299   EXPECT_TRUE(failed);
    300 }
    301 
    302 TEST(Stream, ReadBlocking) {
    303   MockStreamImpl stream_mock;
    304   char buf[1024];
    305   size_t read = 0;
    306 
    307   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 1024, _, _, _))
    308       .WillOnce(DoAll(SetArgPointee<2>(24),
    309                       SetArgPointee<3>(false),
    310                       Return(true)));
    311   EXPECT_TRUE(stream_mock.ReadBlocking(buf, sizeof(buf), &read, nullptr));
    312   EXPECT_EQ(24, read);
    313 
    314   EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 1024, _, _, _))
    315       .WillOnce(DoAll(SetArgPointee<2>(0),
    316                       SetArgPointee<3>(true),
    317                       Return(true)));
    318   EXPECT_TRUE(stream_mock.ReadBlocking(buf, sizeof(buf), &read, nullptr));
    319   EXPECT_EQ(0, read);
    320 
    321   {
    322     InSequence seq;
    323     EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 1024, _, _, _))
    324         .WillOnce(DoAll(SetArgPointee<2>(0),
    325                         SetArgPointee<3>(false),
    326                         Return(true)));
    327     EXPECT_CALL(stream_mock, WaitForDataBlocking(AccessMode::READ, _, _, _))
    328         .WillOnce(Return(true));
    329     EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 1024, _, _, _))
    330         .WillOnce(DoAll(SetArgPointee<2>(0),
    331                         SetArgPointee<3>(false),
    332                         Return(true)));
    333     EXPECT_CALL(stream_mock, WaitForDataBlocking(AccessMode::READ, _, _, _))
    334         .WillOnce(Return(true));
    335     EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 1024, _, _, _))
    336         .WillOnce(DoAll(SetArgPointee<2>(124),
    337                         SetArgPointee<3>(false),
    338                         Return(true)));
    339   }
    340   EXPECT_TRUE(stream_mock.ReadBlocking(buf, sizeof(buf), &read, nullptr));
    341   EXPECT_EQ(124, read);
    342 
    343   {
    344     InSequence seq;
    345     EXPECT_CALL(stream_mock, ReadNonBlocking(buf, 1024, _, _, _))
    346         .WillOnce(DoAll(SetArgPointee<2>(0),
    347                         SetArgPointee<3>(false),
    348                         Return(true)));
    349     EXPECT_CALL(stream_mock, WaitForDataBlocking(AccessMode::READ, _, _, _))
    350         .WillOnce(Return(false));
    351   }
    352   EXPECT_FALSE(stream_mock.ReadBlocking(buf, sizeof(buf), &read, nullptr));
    353 }
    354 
    355 TEST(Stream, ReadAllBlocking) {
    356   class MockReadBlocking : public MockStreamImpl {
    357    public:
    358     MOCK_METHOD4(ReadBlocking, bool(void*, size_t, size_t*, ErrorPtr*));
    359   } stream_mock;
    360 
    361   char buf[1024];
    362 
    363   EXPECT_CALL(stream_mock, ReadBlocking(buf, 1024, _, _))
    364       .WillOnce(DoAll(SetArgPointee<2>(24), Return(true)));
    365   EXPECT_CALL(stream_mock, ReadBlocking(buf + 24, 1000, _, _))
    366       .WillOnce(DoAll(SetArgPointee<2>(1000), Return(true)));
    367   EXPECT_TRUE(stream_mock.ReadAllBlocking(buf, sizeof(buf), nullptr));
    368 
    369   ErrorPtr error;
    370   EXPECT_CALL(stream_mock, ReadBlocking(buf, 1024, _, _))
    371       .WillOnce(DoAll(SetArgPointee<2>(24), Return(true)));
    372   EXPECT_CALL(stream_mock, ReadBlocking(buf + 24, 1000, _, _))
    373       .WillOnce(DoAll(SetArgPointee<2>(0), Return(true)));
    374   EXPECT_FALSE(stream_mock.ReadAllBlocking(buf, sizeof(buf), &error));
    375   EXPECT_EQ(errors::stream::kDomain, error->GetDomain());
    376   EXPECT_EQ(errors::stream::kPartialData, error->GetCode());
    377 }
    378 
    379 TEST(Stream, WriteAsync) {
    380   size_t write_size = 0;
    381   bool failed = false;
    382   auto success_callback = [](size_t* write_size, size_t size) {
    383     *write_size = size;
    384   };
    385   auto error_callback = [](bool* failed, const Error* /* error */) {
    386     *failed = true;
    387   };
    388 
    389   MockStreamImpl stream_mock;
    390   InSequence s;
    391   base::Callback<void(AccessMode)> data_callback;
    392   char buf[10] = {};
    393 
    394   // WriteNonBlocking returns a blocking situation (size_written = 0) so the
    395   // WaitForData() is run.
    396   EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 10, _, _))
    397       .WillOnce(DoAll(SetArgPointee<2>(0), Return(true)));
    398   EXPECT_CALL(stream_mock, WaitForData(AccessMode::WRITE, _, _))
    399       .WillOnce(DoAll(SaveArg<1>(&data_callback), Return(true)));
    400   EXPECT_TRUE(stream_mock.WriteAsync(
    401       buf,
    402       sizeof(buf),
    403       base::Bind(success_callback, base::Unretained(&write_size)),
    404       base::Bind(error_callback, base::Unretained(&failed)),
    405       nullptr));
    406   EXPECT_EQ(0u, write_size);
    407   EXPECT_FALSE(failed);
    408 
    409   ErrorPtr error;
    410   EXPECT_FALSE(stream_mock.WriteAsync(
    411       buf,
    412       sizeof(buf),
    413       base::Bind(success_callback, base::Unretained(&write_size)),
    414       base::Bind(error_callback, base::Unretained(&failed)),
    415       &error));
    416   EXPECT_EQ(errors::stream::kDomain, error->GetDomain());
    417   EXPECT_EQ(errors::stream::kOperationNotSupported, error->GetCode());
    418   EXPECT_EQ("Another asynchronous operation is still pending",
    419             error->GetMessage());
    420 
    421   EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 10, _, _))
    422       .WillOnce(DoAll(SetArgPointee<2>(7), Return(true)));
    423   data_callback.Run(AccessMode::WRITE);
    424   EXPECT_EQ(7u, write_size);
    425   EXPECT_FALSE(failed);
    426 }
    427 
    428 TEST(Stream, WriteAllAsync) {
    429   bool succeeded = false;
    430   bool failed = false;
    431   auto success_callback = [](bool* succeeded) { *succeeded = true; };
    432   auto error_callback = [](bool* failed, const Error* /* error */) {
    433     *failed = true;
    434   };
    435 
    436   MockStreamImpl stream_mock;
    437   base::Callback<void(AccessMode)> data_callback;
    438   char buf[10] = {};
    439 
    440   EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 10, _, _))
    441       .WillOnce(DoAll(SetArgPointee<2>(0), Return(true)));
    442   EXPECT_CALL(stream_mock, WaitForData(AccessMode::WRITE, _, _))
    443       .WillOnce(DoAll(SaveArg<1>(&data_callback), Return(true)));
    444   EXPECT_TRUE(stream_mock.WriteAllAsync(
    445       buf,
    446       sizeof(buf),
    447       base::Bind(success_callback, base::Unretained(&succeeded)),
    448       base::Bind(error_callback, base::Unretained(&failed)),
    449       nullptr));
    450   testing::Mock::VerifyAndClearExpectations(&stream_mock);
    451   EXPECT_FALSE(succeeded);
    452   EXPECT_FALSE(failed);
    453 
    454   EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 10, _, _))
    455       .WillOnce(DoAll(SetArgPointee<2>(7), Return(true)));
    456   EXPECT_CALL(stream_mock, WriteNonBlocking(buf + 7, 3, _, _))
    457       .WillOnce(DoAll(SetArgPointee<2>(0), Return(true)));
    458   EXPECT_CALL(stream_mock, WaitForData(AccessMode::WRITE, _, _))
    459       .WillOnce(DoAll(SaveArg<1>(&data_callback), Return(true)));
    460   data_callback.Run(AccessMode::WRITE);
    461   testing::Mock::VerifyAndClearExpectations(&stream_mock);
    462   EXPECT_FALSE(succeeded);
    463   EXPECT_FALSE(failed);
    464 
    465   EXPECT_CALL(stream_mock, WriteNonBlocking(buf + 7, 3, _, _))
    466       .WillOnce(DoAll(SetArgPointee<2>(3), Return(true)));
    467   data_callback.Run(AccessMode::WRITE);
    468   EXPECT_TRUE(succeeded);
    469   EXPECT_FALSE(failed);
    470 }
    471 
    472 TEST(Stream, WriteBlocking) {
    473   MockStreamImpl stream_mock;
    474   char buf[1024];
    475   size_t written = 0;
    476 
    477   EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 1024, _, _))
    478       .WillOnce(DoAll(SetArgPointee<2>(24), Return(true)));
    479   EXPECT_TRUE(stream_mock.WriteBlocking(buf, sizeof(buf), &written, nullptr));
    480   EXPECT_EQ(24, written);
    481 
    482   {
    483     InSequence seq;
    484     EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 1024, _, _))
    485           .WillOnce(DoAll(SetArgPointee<2>(0), Return(true)));
    486     EXPECT_CALL(stream_mock, WaitForDataBlocking(AccessMode::WRITE, _, _, _))
    487         .WillOnce(Return(true));
    488     EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 1024, _, _))
    489           .WillOnce(DoAll(SetArgPointee<2>(0), Return(true)));
    490     EXPECT_CALL(stream_mock, WaitForDataBlocking(AccessMode::WRITE, _, _, _))
    491         .WillOnce(Return(true));
    492     EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 1024, _, _))
    493           .WillOnce(DoAll(SetArgPointee<2>(124), Return(true)));
    494   }
    495   EXPECT_TRUE(stream_mock.WriteBlocking(buf, sizeof(buf), &written, nullptr));
    496   EXPECT_EQ(124, written);
    497 
    498   {
    499     InSequence seq;
    500     EXPECT_CALL(stream_mock, WriteNonBlocking(buf, 1024, _, _))
    501           .WillOnce(DoAll(SetArgPointee<2>(0), Return(true)));
    502     EXPECT_CALL(stream_mock, WaitForDataBlocking(AccessMode::WRITE, _, _, _))
    503         .WillOnce(Return(false));
    504   }
    505   EXPECT_FALSE(stream_mock.WriteBlocking(buf, sizeof(buf), &written, nullptr));
    506 }
    507 
    508 TEST(Stream, WriteAllBlocking) {
    509   class MockWritelocking : public MockStreamImpl {
    510    public:
    511     MOCK_METHOD4(WriteBlocking, bool(const void*, size_t, size_t*, ErrorPtr*));
    512   } stream_mock;
    513 
    514   char buf[1024];
    515 
    516   EXPECT_CALL(stream_mock, WriteBlocking(buf, 1024, _, _))
    517       .WillOnce(DoAll(SetArgPointee<2>(24), Return(true)));
    518   EXPECT_CALL(stream_mock, WriteBlocking(buf + 24, 1000, _, _))
    519       .WillOnce(DoAll(SetArgPointee<2>(1000), Return(true)));
    520   EXPECT_TRUE(stream_mock.WriteAllBlocking(buf, sizeof(buf), nullptr));
    521 }
    522 
    523 }  // namespace brillo
    524