Bitcoin Core  25.99.0
P2P Digital Currency
net.h
Go to the documentation of this file.
1 // Copyright (c) 2009-2022 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_FUZZ_UTIL_NET_H
6 #define BITCOIN_TEST_FUZZ_UTIL_NET_H
7 
8 #include <net.h>
9 #include <net_permissions.h>
10 #include <netaddress.h>
11 #include <node/connection_types.h>
12 #include <node/eviction.h>
13 #include <protocol.h>
15 #include <test/fuzz/util.h>
16 #include <test/util/net.h>
17 #include <threadsafety.h>
18 #include <util/sock.h>
19 
20 #include <chrono>
21 #include <cstdint>
22 #include <limits>
23 #include <memory>
24 #include <optional>
25 #include <string>
26 
27 CNetAddr ConsumeNetAddr(FuzzedDataProvider& fuzzed_data_provider) noexcept;
28 
29 class FuzzedSock : public Sock
30 {
32 
38  mutable std::optional<uint8_t> m_peek_data;
39 
45  const bool m_selectable;
46 
47 public:
48  explicit FuzzedSock(FuzzedDataProvider& fuzzed_data_provider);
49 
50  ~FuzzedSock() override;
51 
52  FuzzedSock& operator=(Sock&& other) override;
53 
54  ssize_t Send(const void* data, size_t len, int flags) const override;
55 
56  ssize_t Recv(void* buf, size_t len, int flags) const override;
57 
58  int Connect(const sockaddr*, socklen_t) const override;
59 
60  int Bind(const sockaddr*, socklen_t) const override;
61 
62  int Listen(int backlog) const override;
63 
64  std::unique_ptr<Sock> Accept(sockaddr* addr, socklen_t* addr_len) const override;
65 
66  int GetSockOpt(int level, int opt_name, void* opt_val, socklen_t* opt_len) const override;
67 
68  int SetSockOpt(int level, int opt_name, const void* opt_val, socklen_t opt_len) const override;
69 
70  int GetSockName(sockaddr* name, socklen_t* name_len) const override;
71 
72  bool SetNonBlocking() const override;
73 
74  bool IsSelectable() const override;
75 
76  bool Wait(std::chrono::milliseconds timeout, Event requested, Event* occurred = nullptr) const override;
77 
78  bool WaitMany(std::chrono::milliseconds timeout, EventsPerSock& events_per_sock) const override;
79 
80  bool IsConnected(std::string& errmsg) const override;
81 };
82 
83 [[nodiscard]] inline FuzzedSock ConsumeSock(FuzzedDataProvider& fuzzed_data_provider)
84 {
85  return FuzzedSock{fuzzed_data_provider};
86 }
87 
88 inline CSubNet ConsumeSubNet(FuzzedDataProvider& fuzzed_data_provider) noexcept
89 {
90  return {ConsumeNetAddr(fuzzed_data_provider), fuzzed_data_provider.ConsumeIntegral<uint8_t>()};
91 }
92 
93 inline CService ConsumeService(FuzzedDataProvider& fuzzed_data_provider) noexcept
94 {
95  return {ConsumeNetAddr(fuzzed_data_provider), fuzzed_data_provider.ConsumeIntegral<uint16_t>()};
96 }
97 
98 CAddress ConsumeAddress(FuzzedDataProvider& fuzzed_data_provider) noexcept;
99 
100 template <bool ReturnUniquePtr = false>
101 auto ConsumeNode(FuzzedDataProvider& fuzzed_data_provider, const std::optional<NodeId>& node_id_in = std::nullopt) noexcept
102 {
103  const NodeId node_id = node_id_in.value_or(fuzzed_data_provider.ConsumeIntegralInRange<NodeId>(0, std::numeric_limits<NodeId>::max()));
104  const auto sock = std::make_shared<FuzzedSock>(fuzzed_data_provider);
105  const CAddress address = ConsumeAddress(fuzzed_data_provider);
106  const uint64_t keyed_net_group = fuzzed_data_provider.ConsumeIntegral<uint64_t>();
107  const uint64_t local_host_nonce = fuzzed_data_provider.ConsumeIntegral<uint64_t>();
108  const CAddress addr_bind = ConsumeAddress(fuzzed_data_provider);
109  const std::string addr_name = fuzzed_data_provider.ConsumeRandomLengthString(64);
110  const ConnectionType conn_type = fuzzed_data_provider.PickValueInArray(ALL_CONNECTION_TYPES);
111  const bool inbound_onion{conn_type == ConnectionType::INBOUND ? fuzzed_data_provider.ConsumeBool() : false};
112  NetPermissionFlags permission_flags = ConsumeWeakEnum(fuzzed_data_provider, ALL_NET_PERMISSION_FLAGS);
113  if constexpr (ReturnUniquePtr) {
114  return std::make_unique<CNode>(node_id,
115  sock,
116  address,
117  keyed_net_group,
118  local_host_nonce,
119  addr_bind,
120  addr_name,
121  conn_type,
122  inbound_onion,
123  CNodeOptions{ .permission_flags = permission_flags });
124  } else {
125  return CNode{node_id,
126  sock,
127  address,
128  keyed_net_group,
129  local_host_nonce,
130  addr_bind,
131  addr_name,
132  conn_type,
133  inbound_onion,
134  CNodeOptions{ .permission_flags = permission_flags }};
135  }
136 }
137 inline std::unique_ptr<CNode> ConsumeNodeAsUniquePtr(FuzzedDataProvider& fdp, const std::optional<NodeId>& node_id_in = std::nullopt) { return ConsumeNode<true>(fdp, node_id_in); }
138 
140 
141 #endif // BITCOIN_TEST_FUZZ_UTIL_NET_H
int flags
Definition: bitcoin-tx.cpp:528
A CService with information about it as peer.
Definition: protocol.h:360
Network address.
Definition: netaddress.h:112
Information about a peer.
Definition: net.h:667
A combination of a network address (CNetAddr) and a (TCP) port.
Definition: netaddress.h:531
Definition: net.h:30
std::unique_ptr< Sock > Accept(sockaddr *addr, socklen_t *addr_len) const override
accept(2) wrapper.
Definition: net.cpp:258
int GetSockOpt(int level, int opt_name, void *opt_val, socklen_t *opt_len) const override
getsockopt(2) wrapper.
Definition: net.cpp:272
bool Wait(std::chrono::milliseconds timeout, Event requested, Event *occurred=nullptr) const override
Wait for readiness for input (recv) or output (send).
Definition: net.cpp:336
int Listen(int backlog) const override
listen(2) wrapper.
Definition: net.cpp:239
const bool m_selectable
Whether to pretend that the socket is select(2)-able.
Definition: net.h:45
bool WaitMany(std::chrono::milliseconds timeout, EventsPerSock &events_per_sock) const override
Same as Wait(), but wait on many sockets within the same timeout.
Definition: net.cpp:353
bool IsConnected(std::string &errmsg) const override
Check if still connected.
Definition: net.cpp:362
int Connect(const sockaddr *, socklen_t) const override
connect(2) wrapper.
Definition: net.cpp:197
ssize_t Send(const void *data, size_t len, int flags) const override
send(2) wrapper.
Definition: net.cpp:100
FuzzedSock & operator=(Sock &&other) override
Move assignment operator, grab the socket from another object and close ours (if set).
Definition: net.cpp:94
std::optional< uint8_t > m_peek_data
Data to return when MSG_PEEK is used as a Recv() flag.
Definition: net.h:38
FuzzedDataProvider & m_fuzzed_data_provider
Definition: net.h:31
bool IsSelectable() const override
Check if the underlying socket can be used for select(2) (or the Wait() method).
Definition: net.cpp:331
bool SetNonBlocking() const override
Set the non-blocking option on the socket.
Definition: net.cpp:318
int SetSockOpt(int level, int opt_name, const void *opt_val, socklen_t opt_len) const override
setsockopt(2) wrapper.
Definition: net.cpp:291
ssize_t Recv(void *buf, size_t len, int flags) const override
recv(2) wrapper.
Definition: net.cpp:132
~FuzzedSock() override
Definition: net.cpp:85
int GetSockName(sockaddr *name, socklen_t *name_len) const override
getsockname(2) wrapper.
Definition: net.cpp:304
FuzzedSock(FuzzedDataProvider &fuzzed_data_provider)
Definition: net.cpp:79
int Bind(const sockaddr *, socklen_t) const override
bind(2) wrapper.
Definition: net.cpp:219
static Mutex g_msgproc_mutex
Mutex for anything that is only accessed via the msg processing thread.
Definition: net.h:988
RAII helper class that manages a socket.
Definition: sock.h:28
uint8_t Event
Definition: sock.h:148
std::unordered_map< std::shared_ptr< const Sock >, Events, HashSharedPtrSock, EqualSharedPtrSock > EventsPerSock
On which socket to wait for what events in WaitMany().
Definition: sock.h:218
ConnectionType
Different types of connections to a peer.
@ INBOUND
Inbound connections are those initiated by a peer.
Definition: init.h:25
int64_t NodeId
Definition: net.h:97
NetPermissionFlags
const char * name
Definition: rest.cpp:45
NetPermissionFlags permission_flags
Definition: net.h:659
void FillNode(FuzzedDataProvider &fuzzed_data_provider, ConnmanTestMsg &connman, CNode &node) noexcept
Definition: net.cpp:371
CService ConsumeService(FuzzedDataProvider &fuzzed_data_provider) noexcept
Definition: net.h:93
CSubNet ConsumeSubNet(FuzzedDataProvider &fuzzed_data_provider) noexcept
Definition: net.h:88
std::unique_ptr< CNode > ConsumeNodeAsUniquePtr(FuzzedDataProvider &fdp, const std::optional< NodeId > &node_id_in=std::nullopt)
Definition: net.h:137
auto ConsumeNode(FuzzedDataProvider &fuzzed_data_provider, const std::optional< NodeId > &node_id_in=std::nullopt) noexcept
Definition: net.h:101
CNetAddr ConsumeNetAddr(FuzzedDataProvider &fuzzed_data_provider) noexcept
Definition: net.cpp:28
CAddress ConsumeAddress(FuzzedDataProvider &fuzzed_data_provider) noexcept
Definition: net.cpp:53
FuzzedSock ConsumeSock(FuzzedDataProvider &fuzzed_data_provider)
Definition: net.h:83
WeakEnumType ConsumeWeakEnum(FuzzedDataProvider &fuzzed_data_provider, const WeakEnumType(&all_types)[size]) noexcept
Definition: util.h:132
constexpr ConnectionType ALL_CONNECTION_TYPES[]
Definition: net.h:83
constexpr NetPermissionFlags ALL_NET_PERMISSION_FLAGS[]
Definition: net.h:70
#define EXCLUSIVE_LOCKS_REQUIRED(...)
Definition: threadsafety.h:49