1 /*
2  * Copyright (C) 2016 The Android Open Source Project
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *  * Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  *  * Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in
12  *    the documentation and/or other materials provided with the
13  *    distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
18  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
19  * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
20  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
21  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
22  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
23  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
25  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26  * SUCH DAMAGE.
27  */
28 
29 #include "socket_mock.h"
30 
31 #include <gtest/gtest.h>
32 
SocketMock()33 SocketMock::SocketMock() : Socket(INVALID_SOCKET) {}
34 
~SocketMock()35 SocketMock::~SocketMock() {
36     if (!events_.empty()) {
37         ADD_FAILURE() << events_.size() << " event(s) were not handled";
38     }
39 }
40 
Send(const void * data,size_t length)41 bool SocketMock::Send(const void* data, size_t length) {
42     if (events_.empty()) {
43         ADD_FAILURE() << "Send() was called when no message was expected";
44         return false;
45     }
46 
47     if (events_.front().type != EventType::kSend) {
48         ADD_FAILURE() << "Send() was called out-of-order";
49         return false;
50     }
51 
52     std::string message(reinterpret_cast<const char*>(data), length);
53     if (events_.front().message != message) {
54         ADD_FAILURE() << "Send() expected " << events_.front().message << ", but got " << message;
55         return false;
56     }
57 
58     bool return_value = events_.front().status;
59     events_.pop();
60     return return_value;
61 }
62 
63 // Mock out multi-buffer send to be one large send, since that's what it should looks like from
64 // the user's perspective.
Send(std::vector<cutils_socket_buffer_t> buffers)65 bool SocketMock::Send(std::vector<cutils_socket_buffer_t> buffers) {
66     std::string data;
67     for (const auto& buffer : buffers) {
68         data.append(reinterpret_cast<const char*>(buffer.data), buffer.length);
69     }
70     return Send(data.data(), data.size());
71 }
72 
Receive(void * data,size_t length,int)73 ssize_t SocketMock::Receive(void* data, size_t length, int /*timeout_ms*/) {
74     if (events_.empty()) {
75         ADD_FAILURE() << "Receive() was called when no message was ready";
76         return -1;
77     }
78 
79     const Event& event = events_.front();
80     if (event.type != EventType::kReceive) {
81         ADD_FAILURE() << "Receive() was called out-of-order";
82         return -1;
83     }
84 
85     const std::string& message = event.message;
86     if (message.length() > length) {
87         ADD_FAILURE() << "Receive(): not enough bytes (" << length << ") for " << message;
88         return -1;
89     }
90 
91     receive_timed_out_ = event.status;
92     ssize_t return_value = message.length();
93 
94     // Empty message indicates failure.
95     if (message.empty()) {
96         return_value = -1;
97     } else {
98         memcpy(data, message.data(), message.length());
99     }
100 
101     events_.pop();
102     return return_value;
103 }
104 
Close()105 int SocketMock::Close() {
106     return 0;
107 }
108 
Accept()109 std::unique_ptr<Socket> SocketMock::Accept() {
110     if (events_.empty()) {
111         ADD_FAILURE() << "Accept() was called when no socket was ready";
112         return nullptr;
113     }
114 
115     if (events_.front().type != EventType::kAccept) {
116         ADD_FAILURE() << "Accept() was called out-of-order";
117         return nullptr;
118     }
119 
120     std::unique_ptr<Socket> sock = std::move(events_.front().sock);
121     events_.pop();
122     return sock;
123 }
124 
ExpectSend(std::string message)125 void SocketMock::ExpectSend(std::string message) {
126     events_.push(Event(EventType::kSend, std::move(message), true, nullptr));
127 }
128 
ExpectSendFailure(std::string message)129 void SocketMock::ExpectSendFailure(std::string message) {
130     events_.push(Event(EventType::kSend, std::move(message), false, nullptr));
131 }
132 
AddReceive(std::string message)133 void SocketMock::AddReceive(std::string message) {
134     events_.push(Event(EventType::kReceive, std::move(message), false, nullptr));
135 }
136 
AddReceiveTimeout()137 void SocketMock::AddReceiveTimeout() {
138     events_.push(Event(EventType::kReceive, "", true, nullptr));
139 }
140 
AddReceiveFailure()141 void SocketMock::AddReceiveFailure() {
142     events_.push(Event(EventType::kReceive, "", false, nullptr));
143 }
144 
AddAccept(std::unique_ptr<Socket> sock)145 void SocketMock::AddAccept(std::unique_ptr<Socket> sock) {
146     events_.push(Event(EventType::kAccept, "", false, std::move(sock)));
147 }
148 
Event(EventType _type,std::string _message,ssize_t _status,std::unique_ptr<Socket> _sock)149 SocketMock::Event::Event(EventType _type, std::string _message, ssize_t _status,
150                          std::unique_ptr<Socket> _sock)
151         : type(_type), message(_message), status(_status), sock(std::move(_sock)) {}
152