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