1*1a96fba6SXin Li // Copyright 2015 The Chromium OS Authors. All rights reserved.
2*1a96fba6SXin Li // Use of this source code is governed by a BSD-style license that can be
3*1a96fba6SXin Li // found in the LICENSE file.
4*1a96fba6SXin Li
5*1a96fba6SXin Li #include <brillo/streams/fake_stream.h>
6*1a96fba6SXin Li
7*1a96fba6SXin Li #include <memory>
8*1a96fba6SXin Li #include <vector>
9*1a96fba6SXin Li
10*1a96fba6SXin Li #include <base/bind.h>
11*1a96fba6SXin Li #include <base/callback.h>
12*1a96fba6SXin Li #include <base/test/simple_test_clock.h>
13*1a96fba6SXin Li #include <brillo/message_loops/mock_message_loop.h>
14*1a96fba6SXin Li #include <gmock/gmock.h>
15*1a96fba6SXin Li #include <gtest/gtest.h>
16*1a96fba6SXin Li
17*1a96fba6SXin Li using testing::AnyNumber;
18*1a96fba6SXin Li using testing::InSequence;
19*1a96fba6SXin Li using testing::_;
20*1a96fba6SXin Li
21*1a96fba6SXin Li namespace brillo {
22*1a96fba6SXin Li
23*1a96fba6SXin Li class FakeStreamTest : public testing::Test {
24*1a96fba6SXin Li public:
SetUp()25*1a96fba6SXin Li void SetUp() override {
26*1a96fba6SXin Li mock_loop_.SetAsCurrent();
27*1a96fba6SXin Li // Ignore calls to RunOnce().
28*1a96fba6SXin Li EXPECT_CALL(mock_loop_, RunOnce(true)).Times(AnyNumber());
29*1a96fba6SXin Li }
30*1a96fba6SXin Li
CreateStream(Stream::AccessMode mode)31*1a96fba6SXin Li void CreateStream(Stream::AccessMode mode) {
32*1a96fba6SXin Li stream_.reset(new FakeStream{mode, &clock_});
33*1a96fba6SXin Li }
34*1a96fba6SXin Li
35*1a96fba6SXin Li // Performs non-blocking read on the stream and returns the read data
36*1a96fba6SXin Li // as a string in |out_buffer|. Returns true if the read was successful or
37*1a96fba6SXin Li // false when an error occurs. |*eos| is set to true when end of stream is
38*1a96fba6SXin Li // reached.
ReadString(size_t size_to_read,std::string * out_buffer,bool * eos)39*1a96fba6SXin Li bool ReadString(size_t size_to_read, std::string* out_buffer, bool* eos) {
40*1a96fba6SXin Li std::vector<char> data;
41*1a96fba6SXin Li data.resize(size_to_read);
42*1a96fba6SXin Li size_t size_read = 0;
43*1a96fba6SXin Li bool ok = stream_->ReadNonBlocking(data.data(), data.size(), &size_read,
44*1a96fba6SXin Li eos, nullptr);
45*1a96fba6SXin Li if (ok) {
46*1a96fba6SXin Li out_buffer->assign(data.data(), data.data() + size_read);
47*1a96fba6SXin Li } else {
48*1a96fba6SXin Li out_buffer->clear();
49*1a96fba6SXin Li }
50*1a96fba6SXin Li return ok;
51*1a96fba6SXin Li }
52*1a96fba6SXin Li
53*1a96fba6SXin Li // Writes a string to a stream. Returns the number of bytes written or -1
54*1a96fba6SXin Li // in case an error occurred.
WriteString(const std::string & data)55*1a96fba6SXin Li int WriteString(const std::string& data) {
56*1a96fba6SXin Li size_t written = 0;
57*1a96fba6SXin Li if (!stream_->WriteNonBlocking(data.data(), data.size(), &written, nullptr))
58*1a96fba6SXin Li return -1;
59*1a96fba6SXin Li return static_cast<int>(written);
60*1a96fba6SXin Li }
61*1a96fba6SXin Li
62*1a96fba6SXin Li protected:
63*1a96fba6SXin Li base::SimpleTestClock clock_;
64*1a96fba6SXin Li MockMessageLoop mock_loop_{&clock_};
65*1a96fba6SXin Li std::unique_ptr<FakeStream> stream_;
66*1a96fba6SXin Li const base::TimeDelta zero_delay;
67*1a96fba6SXin Li };
68*1a96fba6SXin Li
TEST_F(FakeStreamTest,InitReadOnly)69*1a96fba6SXin Li TEST_F(FakeStreamTest, InitReadOnly) {
70*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
71*1a96fba6SXin Li EXPECT_TRUE(stream_->IsOpen());
72*1a96fba6SXin Li EXPECT_TRUE(stream_->CanRead());
73*1a96fba6SXin Li EXPECT_FALSE(stream_->CanWrite());
74*1a96fba6SXin Li EXPECT_FALSE(stream_->CanSeek());
75*1a96fba6SXin Li EXPECT_FALSE(stream_->CanGetSize());
76*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetSize());
77*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetRemainingSize());
78*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetPosition());
79*1a96fba6SXin Li }
80*1a96fba6SXin Li
TEST_F(FakeStreamTest,InitWriteOnly)81*1a96fba6SXin Li TEST_F(FakeStreamTest, InitWriteOnly) {
82*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
83*1a96fba6SXin Li EXPECT_TRUE(stream_->IsOpen());
84*1a96fba6SXin Li EXPECT_FALSE(stream_->CanRead());
85*1a96fba6SXin Li EXPECT_TRUE(stream_->CanWrite());
86*1a96fba6SXin Li EXPECT_FALSE(stream_->CanSeek());
87*1a96fba6SXin Li EXPECT_FALSE(stream_->CanGetSize());
88*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetSize());
89*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetRemainingSize());
90*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetPosition());
91*1a96fba6SXin Li }
92*1a96fba6SXin Li
TEST_F(FakeStreamTest,InitReadWrite)93*1a96fba6SXin Li TEST_F(FakeStreamTest, InitReadWrite) {
94*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ_WRITE);
95*1a96fba6SXin Li EXPECT_TRUE(stream_->IsOpen());
96*1a96fba6SXin Li EXPECT_TRUE(stream_->CanRead());
97*1a96fba6SXin Li EXPECT_TRUE(stream_->CanWrite());
98*1a96fba6SXin Li EXPECT_FALSE(stream_->CanSeek());
99*1a96fba6SXin Li EXPECT_FALSE(stream_->CanGetSize());
100*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetSize());
101*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetRemainingSize());
102*1a96fba6SXin Li EXPECT_EQ(0, stream_->GetPosition());
103*1a96fba6SXin Li }
104*1a96fba6SXin Li
TEST_F(FakeStreamTest,ReadEmpty)105*1a96fba6SXin Li TEST_F(FakeStreamTest, ReadEmpty) {
106*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
107*1a96fba6SXin Li std::string data;
108*1a96fba6SXin Li bool eos = false;
109*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
110*1a96fba6SXin Li EXPECT_TRUE(eos);
111*1a96fba6SXin Li EXPECT_TRUE(data.empty());
112*1a96fba6SXin Li }
113*1a96fba6SXin Li
TEST_F(FakeStreamTest,ReadFullPacket)114*1a96fba6SXin Li TEST_F(FakeStreamTest, ReadFullPacket) {
115*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
116*1a96fba6SXin Li stream_->AddReadPacketString({}, "foo");
117*1a96fba6SXin Li std::string data;
118*1a96fba6SXin Li bool eos = false;
119*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
120*1a96fba6SXin Li EXPECT_FALSE(eos);
121*1a96fba6SXin Li EXPECT_EQ("foo", data);
122*1a96fba6SXin Li
123*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
124*1a96fba6SXin Li EXPECT_TRUE(eos);
125*1a96fba6SXin Li EXPECT_TRUE(data.empty());
126*1a96fba6SXin Li }
127*1a96fba6SXin Li
TEST_F(FakeStreamTest,ReadPartialPacket)128*1a96fba6SXin Li TEST_F(FakeStreamTest, ReadPartialPacket) {
129*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
130*1a96fba6SXin Li stream_->AddReadPacketString({}, "foobar");
131*1a96fba6SXin Li std::string data;
132*1a96fba6SXin Li bool eos = false;
133*1a96fba6SXin Li EXPECT_TRUE(ReadString(3, &data, &eos));
134*1a96fba6SXin Li EXPECT_FALSE(eos);
135*1a96fba6SXin Li EXPECT_EQ("foo", data);
136*1a96fba6SXin Li
137*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
138*1a96fba6SXin Li EXPECT_FALSE(eos);
139*1a96fba6SXin Li EXPECT_EQ("bar", data);
140*1a96fba6SXin Li
141*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
142*1a96fba6SXin Li EXPECT_TRUE(eos);
143*1a96fba6SXin Li EXPECT_TRUE(data.empty());
144*1a96fba6SXin Li }
145*1a96fba6SXin Li
TEST_F(FakeStreamTest,ReadMultiplePackets)146*1a96fba6SXin Li TEST_F(FakeStreamTest, ReadMultiplePackets) {
147*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
148*1a96fba6SXin Li stream_->AddReadPacketString({}, "foobar");
149*1a96fba6SXin Li stream_->AddReadPacketString({}, "baz");
150*1a96fba6SXin Li stream_->AddReadPacketString({}, "quux");
151*1a96fba6SXin Li std::string data;
152*1a96fba6SXin Li bool eos = false;
153*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
154*1a96fba6SXin Li EXPECT_FALSE(eos);
155*1a96fba6SXin Li EXPECT_EQ("foobar", data);
156*1a96fba6SXin Li
157*1a96fba6SXin Li EXPECT_TRUE(ReadString(2, &data, &eos));
158*1a96fba6SXin Li EXPECT_FALSE(eos);
159*1a96fba6SXin Li EXPECT_EQ("ba", data);
160*1a96fba6SXin Li
161*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
162*1a96fba6SXin Li EXPECT_FALSE(eos);
163*1a96fba6SXin Li EXPECT_EQ("z", data);
164*1a96fba6SXin Li
165*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
166*1a96fba6SXin Li EXPECT_FALSE(eos);
167*1a96fba6SXin Li EXPECT_EQ("quux", data);
168*1a96fba6SXin Li
169*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
170*1a96fba6SXin Li EXPECT_TRUE(eos);
171*1a96fba6SXin Li EXPECT_TRUE(data.empty());
172*1a96fba6SXin Li
173*1a96fba6SXin Li stream_->AddReadPacketString({}, "foo-bar");
174*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
175*1a96fba6SXin Li EXPECT_FALSE(eos);
176*1a96fba6SXin Li EXPECT_EQ("foo-bar", data);
177*1a96fba6SXin Li }
178*1a96fba6SXin Li
TEST_F(FakeStreamTest,ReadPacketsWithDelay)179*1a96fba6SXin Li TEST_F(FakeStreamTest, ReadPacketsWithDelay) {
180*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
181*1a96fba6SXin Li stream_->AddReadPacketString({}, "foobar");
182*1a96fba6SXin Li stream_->AddReadPacketString(base::TimeDelta::FromSeconds(1), "baz");
183*1a96fba6SXin Li std::string data;
184*1a96fba6SXin Li bool eos = false;
185*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
186*1a96fba6SXin Li EXPECT_FALSE(eos);
187*1a96fba6SXin Li EXPECT_EQ("foobar", data);
188*1a96fba6SXin Li
189*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
190*1a96fba6SXin Li EXPECT_FALSE(eos);
191*1a96fba6SXin Li EXPECT_TRUE(data.empty());
192*1a96fba6SXin Li
193*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
194*1a96fba6SXin Li EXPECT_FALSE(eos);
195*1a96fba6SXin Li EXPECT_TRUE(data.empty());
196*1a96fba6SXin Li
197*1a96fba6SXin Li clock_.Advance(base::TimeDelta::FromSeconds(1));
198*1a96fba6SXin Li
199*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
200*1a96fba6SXin Li EXPECT_FALSE(eos);
201*1a96fba6SXin Li EXPECT_EQ("baz", data);
202*1a96fba6SXin Li }
203*1a96fba6SXin Li
TEST_F(FakeStreamTest,ReadPacketsWithError)204*1a96fba6SXin Li TEST_F(FakeStreamTest, ReadPacketsWithError) {
205*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
206*1a96fba6SXin Li stream_->AddReadPacketString({}, "foobar");
207*1a96fba6SXin Li stream_->QueueReadErrorWithMessage(base::TimeDelta::FromSeconds(1),
208*1a96fba6SXin Li "Dummy error");
209*1a96fba6SXin Li stream_->AddReadPacketString({}, "baz");
210*1a96fba6SXin Li
211*1a96fba6SXin Li std::string data;
212*1a96fba6SXin Li bool eos = false;
213*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
214*1a96fba6SXin Li EXPECT_FALSE(eos);
215*1a96fba6SXin Li EXPECT_EQ("foobar", data);
216*1a96fba6SXin Li
217*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
218*1a96fba6SXin Li EXPECT_FALSE(eos);
219*1a96fba6SXin Li EXPECT_TRUE(data.empty());
220*1a96fba6SXin Li
221*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
222*1a96fba6SXin Li EXPECT_FALSE(eos);
223*1a96fba6SXin Li EXPECT_TRUE(data.empty());
224*1a96fba6SXin Li
225*1a96fba6SXin Li clock_.Advance(base::TimeDelta::FromSeconds(1));
226*1a96fba6SXin Li
227*1a96fba6SXin Li EXPECT_FALSE(ReadString(100, &data, &eos));
228*1a96fba6SXin Li
229*1a96fba6SXin Li EXPECT_TRUE(ReadString(100, &data, &eos));
230*1a96fba6SXin Li EXPECT_FALSE(eos);
231*1a96fba6SXin Li EXPECT_EQ("baz", data);
232*1a96fba6SXin Li }
233*1a96fba6SXin Li
TEST_F(FakeStreamTest,WaitForDataRead)234*1a96fba6SXin Li TEST_F(FakeStreamTest, WaitForDataRead) {
235*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
236*1a96fba6SXin Li
237*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, zero_delay)).Times(2);
238*1a96fba6SXin Li
239*1a96fba6SXin Li int call_count = 0;
240*1a96fba6SXin Li auto callback = base::Bind([](int* call_count, Stream::AccessMode mode) {
241*1a96fba6SXin Li (*call_count)++;
242*1a96fba6SXin Li EXPECT_EQ(Stream::AccessMode::READ, mode);
243*1a96fba6SXin Li }, &call_count);
244*1a96fba6SXin Li
245*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::READ,
246*1a96fba6SXin Li callback, nullptr));
247*1a96fba6SXin Li mock_loop_.Run();
248*1a96fba6SXin Li EXPECT_EQ(1, call_count);
249*1a96fba6SXin Li
250*1a96fba6SXin Li stream_->AddReadPacketString({}, "foobar");
251*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::READ,
252*1a96fba6SXin Li callback, nullptr));
253*1a96fba6SXin Li mock_loop_.Run();
254*1a96fba6SXin Li EXPECT_EQ(2, call_count);
255*1a96fba6SXin Li
256*1a96fba6SXin Li stream_->ClearReadQueue();
257*1a96fba6SXin Li
258*1a96fba6SXin Li auto one_sec_delay = base::TimeDelta::FromSeconds(1);
259*1a96fba6SXin Li stream_->AddReadPacketString(one_sec_delay, "baz");
260*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, one_sec_delay)).Times(1);
261*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::READ,
262*1a96fba6SXin Li callback, nullptr));
263*1a96fba6SXin Li mock_loop_.Run();
264*1a96fba6SXin Li EXPECT_EQ(3, call_count);
265*1a96fba6SXin Li }
266*1a96fba6SXin Li
TEST_F(FakeStreamTest,ReadAsync)267*1a96fba6SXin Li TEST_F(FakeStreamTest, ReadAsync) {
268*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ);
269*1a96fba6SXin Li std::string input_data = "foobar-baz";
270*1a96fba6SXin Li size_t split_pos = input_data.find('-');
271*1a96fba6SXin Li
272*1a96fba6SXin Li auto one_sec_delay = base::TimeDelta::FromSeconds(1);
273*1a96fba6SXin Li stream_->AddReadPacketString({}, input_data.substr(0, split_pos));
274*1a96fba6SXin Li stream_->AddReadPacketString(one_sec_delay, input_data.substr(split_pos));
275*1a96fba6SXin Li
276*1a96fba6SXin Li {
277*1a96fba6SXin Li InSequence seq;
278*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, zero_delay)).Times(1);
279*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, one_sec_delay)).Times(1);
280*1a96fba6SXin Li }
281*1a96fba6SXin Li
282*1a96fba6SXin Li std::vector<char> buffer;
283*1a96fba6SXin Li buffer.resize(input_data.size());
284*1a96fba6SXin Li
285*1a96fba6SXin Li int success_count = 0;
286*1a96fba6SXin Li int error_count = 0;
287*1a96fba6SXin Li auto on_success = [](int* success_count) { (*success_count)++; };
288*1a96fba6SXin Li auto on_failure = [](int* error_count, const Error* /* error */) {
289*1a96fba6SXin Li (*error_count)++;
290*1a96fba6SXin Li };
291*1a96fba6SXin Li
292*1a96fba6SXin Li EXPECT_TRUE(stream_->ReadAllAsync(
293*1a96fba6SXin Li buffer.data(),
294*1a96fba6SXin Li buffer.size(),
295*1a96fba6SXin Li base::Bind(on_success, base::Unretained(&success_count)),
296*1a96fba6SXin Li base::Bind(on_failure, base::Unretained(&error_count)),
297*1a96fba6SXin Li nullptr));
298*1a96fba6SXin Li mock_loop_.Run();
299*1a96fba6SXin Li EXPECT_EQ(1, success_count);
300*1a96fba6SXin Li EXPECT_EQ(0, error_count);
301*1a96fba6SXin Li EXPECT_EQ(input_data, (std::string{buffer.begin(), buffer.end()}));
302*1a96fba6SXin Li }
303*1a96fba6SXin Li
TEST_F(FakeStreamTest,WriteEmpty)304*1a96fba6SXin Li TEST_F(FakeStreamTest, WriteEmpty) {
305*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
306*1a96fba6SXin Li EXPECT_EQ(-1, WriteString("foo"));
307*1a96fba6SXin Li }
308*1a96fba6SXin Li
TEST_F(FakeStreamTest,WritePartial)309*1a96fba6SXin Li TEST_F(FakeStreamTest, WritePartial) {
310*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
311*1a96fba6SXin Li stream_->ExpectWritePacketSize({}, 6);
312*1a96fba6SXin Li EXPECT_EQ(3, WriteString("foo"));
313*1a96fba6SXin Li EXPECT_EQ(3, WriteString("bar"));
314*1a96fba6SXin Li EXPECT_EQ(-1, WriteString("baz"));
315*1a96fba6SXin Li
316*1a96fba6SXin Li EXPECT_EQ("foobar", stream_->GetFlushedOutputDataAsString());
317*1a96fba6SXin Li }
318*1a96fba6SXin Li
TEST_F(FakeStreamTest,WriteFullPackets)319*1a96fba6SXin Li TEST_F(FakeStreamTest, WriteFullPackets) {
320*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
321*1a96fba6SXin Li
322*1a96fba6SXin Li stream_->ExpectWritePacketSize({}, 3);
323*1a96fba6SXin Li EXPECT_EQ(3, WriteString("foo"));
324*1a96fba6SXin Li EXPECT_EQ(-1, WriteString("bar"));
325*1a96fba6SXin Li
326*1a96fba6SXin Li stream_->ExpectWritePacketSize({}, 3);
327*1a96fba6SXin Li EXPECT_EQ(3, WriteString("bar"));
328*1a96fba6SXin Li
329*1a96fba6SXin Li stream_->ExpectWritePacketSize({}, 3);
330*1a96fba6SXin Li EXPECT_EQ(3, WriteString("quux"));
331*1a96fba6SXin Li
332*1a96fba6SXin Li EXPECT_EQ("foobarquu", stream_->GetFlushedOutputDataAsString());
333*1a96fba6SXin Li }
334*1a96fba6SXin Li
TEST_F(FakeStreamTest,WriteAndVerifyData)335*1a96fba6SXin Li TEST_F(FakeStreamTest, WriteAndVerifyData) {
336*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
337*1a96fba6SXin Li
338*1a96fba6SXin Li stream_->ExpectWritePacketString({}, "foo");
339*1a96fba6SXin Li stream_->ExpectWritePacketString({}, "bar");
340*1a96fba6SXin Li EXPECT_EQ(3, WriteString("foobar"));
341*1a96fba6SXin Li EXPECT_EQ(3, WriteString("bar"));
342*1a96fba6SXin Li
343*1a96fba6SXin Li stream_->ExpectWritePacketString({}, "foo");
344*1a96fba6SXin Li stream_->ExpectWritePacketString({}, "baz");
345*1a96fba6SXin Li EXPECT_EQ(3, WriteString("foobar"));
346*1a96fba6SXin Li EXPECT_EQ(-1, WriteString("bar"));
347*1a96fba6SXin Li
348*1a96fba6SXin Li stream_->ExpectWritePacketString({}, "foobar");
349*1a96fba6SXin Li EXPECT_EQ(3, WriteString("foo"));
350*1a96fba6SXin Li EXPECT_EQ(2, WriteString("ba"));
351*1a96fba6SXin Li EXPECT_EQ(-1, WriteString("z"));
352*1a96fba6SXin Li }
353*1a96fba6SXin Li
TEST_F(FakeStreamTest,WriteWithDelay)354*1a96fba6SXin Li TEST_F(FakeStreamTest, WriteWithDelay) {
355*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
356*1a96fba6SXin Li
357*1a96fba6SXin Li const auto delay = base::TimeDelta::FromMilliseconds(500);
358*1a96fba6SXin Li
359*1a96fba6SXin Li stream_->ExpectWritePacketSize({}, 3);
360*1a96fba6SXin Li stream_->ExpectWritePacketSize(delay, 3);
361*1a96fba6SXin Li EXPECT_EQ(3, WriteString("foobar"));
362*1a96fba6SXin Li
363*1a96fba6SXin Li EXPECT_EQ(0, WriteString("bar"));
364*1a96fba6SXin Li EXPECT_EQ(0, WriteString("bar"));
365*1a96fba6SXin Li clock_.Advance(delay);
366*1a96fba6SXin Li EXPECT_EQ(3, WriteString("bar"));
367*1a96fba6SXin Li
368*1a96fba6SXin Li EXPECT_EQ("foobar", stream_->GetFlushedOutputDataAsString());
369*1a96fba6SXin Li }
370*1a96fba6SXin Li
TEST_F(FakeStreamTest,WriteWithError)371*1a96fba6SXin Li TEST_F(FakeStreamTest, WriteWithError) {
372*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
373*1a96fba6SXin Li
374*1a96fba6SXin Li const auto delay = base::TimeDelta::FromMilliseconds(500);
375*1a96fba6SXin Li
376*1a96fba6SXin Li stream_->ExpectWritePacketSize({}, 3);
377*1a96fba6SXin Li stream_->QueueWriteError({});
378*1a96fba6SXin Li stream_->ExpectWritePacketSize({}, 3);
379*1a96fba6SXin Li stream_->QueueWriteErrorWithMessage(delay, "Dummy message");
380*1a96fba6SXin Li stream_->ExpectWritePacketString({}, "foobar");
381*1a96fba6SXin Li
382*1a96fba6SXin Li const std::string data = "foobarbaz";
383*1a96fba6SXin Li EXPECT_EQ(3, WriteString(data));
384*1a96fba6SXin Li EXPECT_EQ(-1, WriteString(data)); // Simulated error #1.
385*1a96fba6SXin Li EXPECT_EQ(3, WriteString(data));
386*1a96fba6SXin Li EXPECT_EQ(0, WriteString(data)); // Waiting for data...
387*1a96fba6SXin Li clock_.Advance(delay);
388*1a96fba6SXin Li EXPECT_EQ(-1, WriteString(data)); // Simulated error #2.
389*1a96fba6SXin Li EXPECT_EQ(6, WriteString(data));
390*1a96fba6SXin Li EXPECT_EQ(-1, WriteString(data)); // No more data expected.
391*1a96fba6SXin Li }
392*1a96fba6SXin Li
TEST_F(FakeStreamTest,WaitForDataWrite)393*1a96fba6SXin Li TEST_F(FakeStreamTest, WaitForDataWrite) {
394*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
395*1a96fba6SXin Li
396*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, zero_delay)).Times(2);
397*1a96fba6SXin Li
398*1a96fba6SXin Li int call_count = 0;
399*1a96fba6SXin Li auto callback = base::Bind([](int* call_count, Stream::AccessMode mode) {
400*1a96fba6SXin Li (*call_count)++;
401*1a96fba6SXin Li EXPECT_EQ(Stream::AccessMode::WRITE, mode);
402*1a96fba6SXin Li }, &call_count);
403*1a96fba6SXin Li
404*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::WRITE,
405*1a96fba6SXin Li callback, nullptr));
406*1a96fba6SXin Li mock_loop_.Run();
407*1a96fba6SXin Li EXPECT_EQ(1, call_count);
408*1a96fba6SXin Li
409*1a96fba6SXin Li stream_->ExpectWritePacketString({}, "foobar");
410*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::WRITE,
411*1a96fba6SXin Li callback, nullptr));
412*1a96fba6SXin Li mock_loop_.Run();
413*1a96fba6SXin Li EXPECT_EQ(2, call_count);
414*1a96fba6SXin Li
415*1a96fba6SXin Li stream_->ClearWriteQueue();
416*1a96fba6SXin Li
417*1a96fba6SXin Li auto one_sec_delay = base::TimeDelta::FromSeconds(1);
418*1a96fba6SXin Li stream_->ExpectWritePacketString(one_sec_delay, "baz");
419*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, one_sec_delay)).Times(1);
420*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::WRITE,
421*1a96fba6SXin Li callback, nullptr));
422*1a96fba6SXin Li mock_loop_.Run();
423*1a96fba6SXin Li EXPECT_EQ(3, call_count);
424*1a96fba6SXin Li }
425*1a96fba6SXin Li
TEST_F(FakeStreamTest,WriteAsync)426*1a96fba6SXin Li TEST_F(FakeStreamTest, WriteAsync) {
427*1a96fba6SXin Li CreateStream(Stream::AccessMode::WRITE);
428*1a96fba6SXin Li std::string output_data = "foobar-baz";
429*1a96fba6SXin Li size_t split_pos = output_data.find('-');
430*1a96fba6SXin Li
431*1a96fba6SXin Li auto one_sec_delay = base::TimeDelta::FromSeconds(1);
432*1a96fba6SXin Li stream_->ExpectWritePacketString({}, output_data.substr(0, split_pos));
433*1a96fba6SXin Li stream_->ExpectWritePacketString(one_sec_delay,
434*1a96fba6SXin Li output_data.substr(split_pos));
435*1a96fba6SXin Li
436*1a96fba6SXin Li {
437*1a96fba6SXin Li InSequence seq;
438*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, zero_delay)).Times(1);
439*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, one_sec_delay)).Times(1);
440*1a96fba6SXin Li }
441*1a96fba6SXin Li
442*1a96fba6SXin Li int success_count = 0;
443*1a96fba6SXin Li int error_count = 0;
444*1a96fba6SXin Li auto on_success = [](int* success_count) { (*success_count)++; };
445*1a96fba6SXin Li auto on_failure = [](int* error_count, const Error* /* error */) {
446*1a96fba6SXin Li (*error_count)++;
447*1a96fba6SXin Li };
448*1a96fba6SXin Li
449*1a96fba6SXin Li EXPECT_TRUE(stream_->WriteAllAsync(
450*1a96fba6SXin Li output_data.data(),
451*1a96fba6SXin Li output_data.size(),
452*1a96fba6SXin Li base::Bind(on_success, base::Unretained(&success_count)),
453*1a96fba6SXin Li base::Bind(on_failure, base::Unretained(&error_count)),
454*1a96fba6SXin Li nullptr));
455*1a96fba6SXin Li mock_loop_.Run();
456*1a96fba6SXin Li EXPECT_EQ(1, success_count);
457*1a96fba6SXin Li EXPECT_EQ(0, error_count);
458*1a96fba6SXin Li EXPECT_EQ(output_data, stream_->GetFlushedOutputDataAsString());
459*1a96fba6SXin Li }
460*1a96fba6SXin Li
TEST_F(FakeStreamTest,WaitForDataReadWrite)461*1a96fba6SXin Li TEST_F(FakeStreamTest, WaitForDataReadWrite) {
462*1a96fba6SXin Li CreateStream(Stream::AccessMode::READ_WRITE);
463*1a96fba6SXin Li auto one_sec_delay = base::TimeDelta::FromSeconds(1);
464*1a96fba6SXin Li auto two_sec_delay = base::TimeDelta::FromSeconds(2);
465*1a96fba6SXin Li
466*1a96fba6SXin Li int call_count = 0;
467*1a96fba6SXin Li auto callback = [](int* call_count,
468*1a96fba6SXin Li Stream::AccessMode mode,
469*1a96fba6SXin Li Stream::AccessMode expected_mode) {
470*1a96fba6SXin Li (*call_count)++;
471*1a96fba6SXin Li EXPECT_EQ(static_cast<int>(expected_mode), static_cast<int>(mode));
472*1a96fba6SXin Li };
473*1a96fba6SXin Li
474*1a96fba6SXin Li stream_->AddReadPacketString(one_sec_delay, "foo");
475*1a96fba6SXin Li stream_->ExpectWritePacketString(two_sec_delay, "bar");
476*1a96fba6SXin Li
477*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, one_sec_delay)).Times(1);
478*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::READ_WRITE,
479*1a96fba6SXin Li base::Bind(callback,
480*1a96fba6SXin Li base::Unretained(&call_count),
481*1a96fba6SXin Li Stream::AccessMode::READ),
482*1a96fba6SXin Li nullptr));
483*1a96fba6SXin Li mock_loop_.Run();
484*1a96fba6SXin Li EXPECT_EQ(1, call_count);
485*1a96fba6SXin Li
486*1a96fba6SXin Li // The above step has adjusted the clock by 1 second already.
487*1a96fba6SXin Li stream_->ClearReadQueue();
488*1a96fba6SXin Li stream_->AddReadPacketString(two_sec_delay, "foo");
489*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, one_sec_delay)).Times(1);
490*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::READ_WRITE,
491*1a96fba6SXin Li base::Bind(callback,
492*1a96fba6SXin Li base::Unretained(&call_count),
493*1a96fba6SXin Li Stream::AccessMode::WRITE),
494*1a96fba6SXin Li nullptr));
495*1a96fba6SXin Li mock_loop_.Run();
496*1a96fba6SXin Li EXPECT_EQ(2, call_count);
497*1a96fba6SXin Li
498*1a96fba6SXin Li clock_.Advance(one_sec_delay);
499*1a96fba6SXin Li
500*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, zero_delay)).Times(1);
501*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::READ_WRITE,
502*1a96fba6SXin Li base::Bind(callback,
503*1a96fba6SXin Li base::Unretained(&call_count),
504*1a96fba6SXin Li Stream::AccessMode::READ_WRITE),
505*1a96fba6SXin Li nullptr));
506*1a96fba6SXin Li mock_loop_.Run();
507*1a96fba6SXin Li EXPECT_EQ(3, call_count);
508*1a96fba6SXin Li
509*1a96fba6SXin Li stream_->ClearReadQueue();
510*1a96fba6SXin Li stream_->ClearWriteQueue();
511*1a96fba6SXin Li stream_->AddReadPacketString(one_sec_delay, "foo");
512*1a96fba6SXin Li stream_->ExpectWritePacketString(one_sec_delay, "bar");
513*1a96fba6SXin Li
514*1a96fba6SXin Li EXPECT_CALL(mock_loop_, PostDelayedTask(_, _, one_sec_delay)).Times(1);
515*1a96fba6SXin Li EXPECT_TRUE(stream_->WaitForData(Stream::AccessMode::READ_WRITE,
516*1a96fba6SXin Li base::Bind(callback,
517*1a96fba6SXin Li base::Unretained(&call_count),
518*1a96fba6SXin Li Stream::AccessMode::READ_WRITE),
519*1a96fba6SXin Li nullptr));
520*1a96fba6SXin Li mock_loop_.Run();
521*1a96fba6SXin Li EXPECT_EQ(4, call_count);
522*1a96fba6SXin Li }
523*1a96fba6SXin Li
524*1a96fba6SXin Li } // namespace brillo
525