Branch data Line data Source code
# 1 : : // Copyright (c) 2020-2021 The Bitcoin Core developers
# 2 : : // Distributed under the MIT software license, see the accompanying
# 3 : : // file COPYING or http://www.opensource.org/licenses/mit-license.php.
# 4 : :
# 5 : : #ifndef BITCOIN_TEST_UTIL_NET_H
# 6 : : #define BITCOIN_TEST_UTIL_NET_H
# 7 : :
# 8 : : #include <compat.h>
# 9 : : #include <netaddress.h>
# 10 : : #include <net.h>
# 11 : : #include <util/sock.h>
# 12 : :
# 13 : : #include <array>
# 14 : : #include <cassert>
# 15 : : #include <cstring>
# 16 : : #include <memory>
# 17 : : #include <string>
# 18 : :
# 19 : : struct ConnmanTestMsg : public CConnman {
# 20 : : using CConnman::CConnman;
# 21 : :
# 22 : : void SetPeerConnectTimeout(std::chrono::seconds timeout)
# 23 : 2 : {
# 24 : 2 : m_peer_connect_timeout = timeout;
# 25 : 2 : }
# 26 : :
# 27 : : void AddTestNode(CNode& node)
# 28 : 30 : {
# 29 : 30 : LOCK(m_nodes_mutex);
# 30 : 30 : m_nodes.push_back(&node);
# 31 : 30 : }
# 32 : : void ClearTestNodes()
# 33 : 6 : {
# 34 : 6 : LOCK(m_nodes_mutex);
# 35 [ + + ]: 30 : for (CNode* node : m_nodes) {
# 36 : 30 : delete node;
# 37 : 30 : }
# 38 : 6 : m_nodes.clear();
# 39 : 6 : }
# 40 : :
# 41 : 0 : void ProcessMessagesOnce(CNode& node) { m_msgproc->ProcessMessages(&node, flagInterruptMsgProc); }
# 42 : :
# 43 : : void NodeReceiveMsgBytes(CNode& node, Span<const uint8_t> msg_bytes, bool& complete) const;
# 44 : :
# 45 : : bool ReceiveMsgFrom(CNode& node, CSerializedNetMsg& ser_msg) const;
# 46 : : };
# 47 : :
# 48 : : constexpr ServiceFlags ALL_SERVICE_FLAGS[]{
# 49 : : NODE_NONE,
# 50 : : NODE_NETWORK,
# 51 : : NODE_BLOOM,
# 52 : : NODE_WITNESS,
# 53 : : NODE_COMPACT_FILTERS,
# 54 : : NODE_NETWORK_LIMITED,
# 55 : : };
# 56 : :
# 57 : : constexpr NetPermissionFlags ALL_NET_PERMISSION_FLAGS[]{
# 58 : : NetPermissionFlags::None,
# 59 : : NetPermissionFlags::BloomFilter,
# 60 : : NetPermissionFlags::Relay,
# 61 : : NetPermissionFlags::ForceRelay,
# 62 : : NetPermissionFlags::NoBan,
# 63 : : NetPermissionFlags::Mempool,
# 64 : : NetPermissionFlags::Addr,
# 65 : : NetPermissionFlags::Download,
# 66 : : NetPermissionFlags::Implicit,
# 67 : : NetPermissionFlags::All,
# 68 : : };
# 69 : :
# 70 : : constexpr ConnectionType ALL_CONNECTION_TYPES[]{
# 71 : : ConnectionType::INBOUND,
# 72 : : ConnectionType::OUTBOUND_FULL_RELAY,
# 73 : : ConnectionType::MANUAL,
# 74 : : ConnectionType::FEELER,
# 75 : : ConnectionType::BLOCK_RELAY,
# 76 : : ConnectionType::ADDR_FETCH,
# 77 : : };
# 78 : :
# 79 : : constexpr auto ALL_NETWORKS = std::array{
# 80 : : Network::NET_UNROUTABLE,
# 81 : : Network::NET_IPV4,
# 82 : : Network::NET_IPV6,
# 83 : : Network::NET_ONION,
# 84 : : Network::NET_I2P,
# 85 : : Network::NET_CJDNS,
# 86 : : Network::NET_INTERNAL,
# 87 : : };
# 88 : :
# 89 : : /**
# 90 : : * A mocked Sock alternative that returns a statically contained data upon read and succeeds
# 91 : : * and ignores all writes. The data to be returned is given to the constructor and when it is
# 92 : : * exhausted an EOF is returned by further reads.
# 93 : : */
# 94 : : class StaticContentsSock : public Sock
# 95 : : {
# 96 : : public:
# 97 : : explicit StaticContentsSock(const std::string& contents) : m_contents{contents}, m_consumed{0}
# 98 : 2 : {
# 99 : : // Just a dummy number that is not INVALID_SOCKET.
# 100 : 2 : m_socket = INVALID_SOCKET - 1;
# 101 : 2 : }
# 102 : :
# 103 : 2 : ~StaticContentsSock() override { Reset(); }
# 104 : :
# 105 : : StaticContentsSock& operator=(Sock&& other) override
# 106 : 0 : {
# 107 : 0 : assert(false && "Move of Sock into MockSock not allowed.");
# 108 : 0 : return *this;
# 109 : 0 : }
# 110 : :
# 111 : : void Reset() override
# 112 : 2 : {
# 113 : 2 : m_socket = INVALID_SOCKET;
# 114 : 2 : }
# 115 : :
# 116 : 2 : ssize_t Send(const void*, size_t len, int) const override { return len; }
# 117 : :
# 118 : : ssize_t Recv(void* buf, size_t len, int flags) const override
# 119 : 512 : {
# 120 : 512 : const size_t consume_bytes{std::min(len, m_contents.size() - m_consumed)};
# 121 : 512 : std::memcpy(buf, m_contents.data() + m_consumed, consume_bytes);
# 122 [ + + ]: 512 : if ((flags & MSG_PEEK) == 0) {
# 123 : 256 : m_consumed += consume_bytes;
# 124 : 256 : }
# 125 : 512 : return consume_bytes;
# 126 : 512 : }
# 127 : :
# 128 : 2 : int Connect(const sockaddr*, socklen_t) const override { return 0; }
# 129 : :
# 130 : : std::unique_ptr<Sock> Accept(sockaddr* addr, socklen_t* addr_len) const override
# 131 : 0 : {
# 132 [ # # ]: 0 : if (addr != nullptr) {
# 133 : : // Pretend all connections come from 5.5.5.5:6789
# 134 : 0 : memset(addr, 0x00, *addr_len);
# 135 : 0 : const socklen_t write_len = static_cast<socklen_t>(sizeof(sockaddr_in));
# 136 [ # # ]: 0 : if (*addr_len >= write_len) {
# 137 : 0 : *addr_len = write_len;
# 138 : 0 : sockaddr_in* addr_in = reinterpret_cast<sockaddr_in*>(addr);
# 139 : 0 : addr_in->sin_family = AF_INET;
# 140 : 0 : memset(&addr_in->sin_addr, 0x05, sizeof(addr_in->sin_addr));
# 141 : 0 : addr_in->sin_port = htons(6789);
# 142 : 0 : }
# 143 : 0 : }
# 144 : 0 : return std::make_unique<StaticContentsSock>("");
# 145 : 0 : };
# 146 : :
# 147 : : int GetSockOpt(int level, int opt_name, void* opt_val, socklen_t* opt_len) const override
# 148 : 0 : {
# 149 : 0 : std::memset(opt_val, 0x0, *opt_len);
# 150 : 0 : return 0;
# 151 : 0 : }
# 152 : :
# 153 : : bool Wait(std::chrono::milliseconds timeout,
# 154 : : Event requested,
# 155 : : Event* occurred = nullptr) const override
# 156 : 256 : {
# 157 [ - + ]: 256 : if (occurred != nullptr) {
# 158 : 0 : *occurred = requested;
# 159 : 0 : }
# 160 : 256 : return true;
# 161 : 256 : }
# 162 : :
# 163 : : private:
# 164 : : const std::string m_contents;
# 165 : : mutable size_t m_consumed;
# 166 : : };
# 167 : :
# 168 : : std::vector<NodeEvictionCandidate> GetRandomNodeEvictionCandidates(int n_candidates, FastRandomContext& random_context);
# 169 : :
# 170 : : #endif // BITCOIN_TEST_UTIL_NET_H
|