diff options
-rw-r--r-- | doc/release-notes.md | 11 | ||||
-rw-r--r-- | src/net.cpp | 22 | ||||
-rw-r--r-- | src/net.h | 11 | ||||
-rw-r--r-- | src/net_processing.cpp | 6 | ||||
-rw-r--r-- | src/rpc/net.cpp | 10 | ||||
-rwxr-xr-x | test/functional/p2p_getdata.py | 2 | ||||
-rwxr-xr-x | test/functional/rpc_getpeerinfo_banscore_deprecation.py | 24 | ||||
-rwxr-xr-x | test/functional/rpc_getpeerinfo_deprecation.py | 39 | ||||
-rwxr-xr-x | test/functional/rpc_net.py | 6 | ||||
-rwxr-xr-x | test/functional/test_runner.py | 2 | ||||
-rwxr-xr-x | test/functional/wallet_resendwallettransactions.py | 2 |
11 files changed, 101 insertions, 34 deletions
diff --git a/doc/release-notes.md b/doc/release-notes.md index 1baff028f3..1580bbd9ae 100644 --- a/doc/release-notes.md +++ b/doc/release-notes.md @@ -105,6 +105,17 @@ will trigger BIP 125 (replace-by-fee) opt-in. (#11413) - The `testmempoolaccept` RPC returns `vsize` and a `fee` object with the `base` fee if the transaction passes validation. (#19940) +- The `getpeerinfo` RPC now returns a `connection_type` field. This indicates + the type of connection established with the peer. It will return one of six + options. For more information, see the `getpeerinfo` help documentation. + (#19725) + +- The `getpeerinfo` RPC no longer returns the `addnode` field by default. This + field will be fully removed in the next major release. It can be accessed + with the configuration option `-deprecatedrpc=getpeerinfo_addnode`. However, + it is recommended to instead use the `connection_type` field (it will return + `manual` when addnode is true). (#19725) + - The `walletcreatefundedpsbt` RPC call will now fail with `Insufficient funds` when inputs are manually selected but are not enough to cover the outputs and fee. Additional inputs can automatically be added through the diff --git a/src/net.cpp b/src/net.cpp index e7d3a146ff..5b533d7d17 100644 --- a/src/net.cpp +++ b/src/net.cpp @@ -488,6 +488,26 @@ void CConnman::AddWhitelistPermissionFlags(NetPermissionFlags& flags, const CNet } } +std::string CNode::ConnectionTypeAsString() const +{ + switch (m_conn_type) { + case ConnectionType::INBOUND: + return "inbound"; + case ConnectionType::MANUAL: + return "manual"; + case ConnectionType::FEELER: + return "feeler"; + case ConnectionType::OUTBOUND_FULL_RELAY: + return "outbound-full-relay"; + case ConnectionType::BLOCK_RELAY: + return "block-relay-only"; + case ConnectionType::ADDR_FETCH: + return "addr-fetch"; + } // no default case, so the compiler can warn about missing cases + + assert(false); +} + std::string CNode::GetAddrName() const { LOCK(cs_addrName); return addrName; @@ -582,6 +602,8 @@ void CNode::copyStats(CNodeStats &stats, const std::vector<bool> &m_asmap) // Leave string empty if addrLocal invalid (not filled in yet) CService addrLocalUnlocked = GetAddrLocal(); stats.addrLocal = addrLocalUnlocked.IsValid() ? addrLocalUnlocked.ToString() : ""; + + stats.m_conn_type_string = ConnectionTypeAsString(); } #undef X @@ -114,6 +114,14 @@ struct CSerializedNetMsg std::string m_type; }; +const std::vector<std::string> CONNECTION_TYPE_DOC{ + "outbound-full-relay (default automatic connections)", + "block-relay-only (does not relay transactions or addresses)", + "inbound (initiated by the peer)", + "manual (added via addnode RPC or -addnode/-connect configuration options)", + "addr-fetch (short-lived automatic connection for soliciting addresses)", + "feeler (short-lived automatic connection for testing addresses)"}; + /** Different types of connections to a peer. This enum encapsulates the * information we have available at the time of opening or accepting the * connection. Aside from INBOUND, all types are initiated by us. */ @@ -691,6 +699,7 @@ public: // Bind address of our side of the connection CAddress addrBind; uint32_t m_mapped_as; + std::string m_conn_type_string; }; @@ -1144,6 +1153,8 @@ public: std::string GetAddrName() const; //! Sets the addrName only if it was not previously set void MaybeSetAddrName(const std::string& addrNameIn); + + std::string ConnectionTypeAsString() const; }; /** Return a timestamp in the future (in microseconds) for exponentially distributed events. */ diff --git a/src/net_processing.cpp b/src/net_processing.cpp index f3f30285d8..d2a76550ea 100644 --- a/src/net_processing.cpp +++ b/src/net_processing.cpp @@ -3520,11 +3520,7 @@ void PeerManager::ProcessMessage(CNode& pfrom, const std::string& msg_type, CDat // Making nodes which are behind NAT and can only make outgoing connections ignore // the getaddr message mitigates the attack. if (!pfrom.IsInboundConn()) { - LogPrint(BCLog::NET, "Ignoring \"getaddr\" from outbound connection. peer=%d\n", pfrom.GetId()); - return; - } - if (!pfrom.RelayAddrsWithConn()) { - LogPrint(BCLog::NET, "Ignoring \"getaddr\" from block-relay-only connection. peer=%d\n", pfrom.GetId()); + LogPrint(BCLog::NET, "Ignoring \"getaddr\" from %s connection. peer=%d\n", pfrom.ConnectionTypeAsString(), pfrom.GetId()); return; } diff --git a/src/rpc/net.cpp b/src/rpc/net.cpp index 11a2d23d85..def21b119e 100644 --- a/src/rpc/net.cpp +++ b/src/rpc/net.cpp @@ -116,7 +116,9 @@ static RPCHelpMan getpeerinfo() {RPCResult::Type::NUM, "version", "The peer version, such as 70001"}, {RPCResult::Type::STR, "subver", "The string version"}, {RPCResult::Type::BOOL, "inbound", "Inbound (true) or Outbound (false)"}, - {RPCResult::Type::BOOL, "addnode", "Whether connection was due to addnode/-connect or if it was an automatic/inbound connection"}, + {RPCResult::Type::BOOL, "addnode", "Whether connection was due to addnode/-connect or if it was an automatic/inbound connection\n" + "(DEPRECATED, returned only if the config option -deprecatedrpc=getpeerinfo_addnode is passed)"}, + {RPCResult::Type::STR, "connection_type", "Type of connection: \n" + Join(CONNECTION_TYPE_DOC, ",\n") + "."}, {RPCResult::Type::NUM, "startingheight", "The starting height (block) of the peer"}, {RPCResult::Type::NUM, "banscore", "The ban score (DEPRECATED, returned only if config option -deprecatedrpc=banscore is passed)"}, {RPCResult::Type::NUM, "synced_headers", "The last header we have in common with this peer"}, @@ -196,7 +198,10 @@ static RPCHelpMan getpeerinfo() // their ver message. obj.pushKV("subver", stats.cleanSubVer); obj.pushKV("inbound", stats.fInbound); - obj.pushKV("addnode", stats.m_manual_connection); + if (IsDeprecatedRPCEnabled("getpeerinfo_addnode")) { + // addnode is deprecated in v0.21 for removal in v0.22 + obj.pushKV("addnode", stats.m_manual_connection); + } obj.pushKV("startingheight", stats.nStartingHeight); if (fStateStats) { if (IsDeprecatedRPCEnabled("banscore")) { @@ -232,6 +237,7 @@ static RPCHelpMan getpeerinfo() recvPerMsgCmd.pushKV(i.first, i.second); } obj.pushKV("bytesrecv_per_msg", recvPerMsgCmd); + obj.pushKV("connection_type", stats.m_conn_type_string); ret.push_back(obj); } diff --git a/test/functional/p2p_getdata.py b/test/functional/p2p_getdata.py index 51921a8ab5..89d68d5ba0 100755 --- a/test/functional/p2p_getdata.py +++ b/test/functional/p2p_getdata.py @@ -42,7 +42,7 @@ class GetdataTest(BitcoinTestFramework): good_getdata = msg_getdata() good_getdata.inv.append(CInv(t=2, h=best_block)) p2p_block_store.send_and_ping(good_getdata) - p2p_block_store.wait_until(lambda: self.nodes[0].p2ps[0].blocks[best_block] == 1) + p2p_block_store.wait_until(lambda: p2p_block_store.blocks[best_block] == 1) if __name__ == '__main__': diff --git a/test/functional/rpc_getpeerinfo_banscore_deprecation.py b/test/functional/rpc_getpeerinfo_banscore_deprecation.py deleted file mode 100755 index b830248e1e..0000000000 --- a/test/functional/rpc_getpeerinfo_banscore_deprecation.py +++ /dev/null @@ -1,24 +0,0 @@ -#!/usr/bin/env python3 -# Copyright (c) 2020 The Bitcoin Core developers -# Distributed under the MIT software license, see the accompanying -# file COPYING or http://www.opensource.org/licenses/mit-license.php. -"""Test deprecation of getpeerinfo RPC banscore field.""" - -from test_framework.test_framework import BitcoinTestFramework - - -class GetpeerinfoBanscoreDeprecationTest(BitcoinTestFramework): - def set_test_params(self): - self.num_nodes = 2 - self.extra_args = [[], ["-deprecatedrpc=banscore"]] - - def run_test(self): - self.log.info("Test getpeerinfo by default no longer returns a banscore field") - assert "banscore" not in self.nodes[0].getpeerinfo()[0].keys() - - self.log.info("Test getpeerinfo returns banscore with -deprecatedrpc=banscore") - assert "banscore" in self.nodes[1].getpeerinfo()[0].keys() - - -if __name__ == "__main__": - GetpeerinfoBanscoreDeprecationTest().main() diff --git a/test/functional/rpc_getpeerinfo_deprecation.py b/test/functional/rpc_getpeerinfo_deprecation.py new file mode 100755 index 0000000000..287c40ae3e --- /dev/null +++ b/test/functional/rpc_getpeerinfo_deprecation.py @@ -0,0 +1,39 @@ +#!/usr/bin/env python3 +# Copyright (c) 2020 The Bitcoin Core developers +# Distributed under the MIT software license, see the accompanying +# file COPYING or http://www.opensource.org/licenses/mit-license.php. +"""Test deprecation of getpeerinfo RPC fields.""" + +from test_framework.test_framework import BitcoinTestFramework +from test_framework.util import connect_nodes + + +class GetpeerinfoDeprecationTest(BitcoinTestFramework): + def set_test_params(self): + self.num_nodes = 2 + self.extra_args = [[], ["-deprecatedrpc=banscore"]] + + def run_test(self): + self.test_banscore_deprecation() + self.test_addnode_deprecation() + + def test_banscore_deprecation(self): + self.log.info("Test getpeerinfo by default no longer returns a banscore field") + assert "banscore" not in self.nodes[0].getpeerinfo()[0].keys() + + self.log.info("Test getpeerinfo returns banscore with -deprecatedrpc=banscore") + assert "banscore" in self.nodes[1].getpeerinfo()[0].keys() + + def test_addnode_deprecation(self): + self.restart_node(1, ["-deprecatedrpc=getpeerinfo_addnode"]) + connect_nodes(self.nodes[0], 1) + + self.log.info("Test getpeerinfo by default no longer returns an addnode field") + assert "addnode" not in self.nodes[0].getpeerinfo()[0].keys() + + self.log.info("Test getpeerinfo returns addnode with -deprecatedrpc=addnode") + assert "addnode" in self.nodes[1].getpeerinfo()[0].keys() + + +if __name__ == "__main__": + GetpeerinfoDeprecationTest().main() diff --git a/test/functional/rpc_net.py b/test/functional/rpc_net.py index bc0e5b458e..b8a04f494d 100755 --- a/test/functional/rpc_net.py +++ b/test/functional/rpc_net.py @@ -175,6 +175,12 @@ class NetTest(BitcoinTestFramework): for info in peer_info: assert_net_servicesnames(int(info[0]["services"], 0x10), info[0]["servicesnames"]) + assert_equal(peer_info[0][0]['connection_type'], 'inbound') + assert_equal(peer_info[0][1]['connection_type'], 'manual') + + assert_equal(peer_info[1][0]['connection_type'], 'manual') + assert_equal(peer_info[1][1]['connection_type'], 'inbound') + def test_service_flags(self): self.log.info("Test service flags") self.nodes[0].add_p2p_connection(P2PInterface(), services=(1 << 4) | (1 << 63)) diff --git a/test/functional/test_runner.py b/test/functional/test_runner.py index 6c3d50df93..c8cf173d5f 100755 --- a/test/functional/test_runner.py +++ b/test/functional/test_runner.py @@ -251,7 +251,7 @@ BASE_SCRIPTS = [ 'feature_config_args.py', 'feature_settings.py', 'rpc_getdescriptorinfo.py', - 'rpc_getpeerinfo_banscore_deprecation.py', + 'rpc_getpeerinfo_deprecation.py', 'rpc_help.py', 'feature_help.py', 'feature_shutdown.py', diff --git a/test/functional/wallet_resendwallettransactions.py b/test/functional/wallet_resendwallettransactions.py index ca1039092d..d3c03c4764 100755 --- a/test/functional/wallet_resendwallettransactions.py +++ b/test/functional/wallet_resendwallettransactions.py @@ -58,7 +58,7 @@ class ResendWalletTransactionsTest(BitcoinTestFramework): two_min = 2 * 60 node.setmocktime(now + twelve_hrs - two_min) time.sleep(2) # ensure enough time has passed for rebroadcast attempt to occur - assert_equal(int(txid, 16) in node.p2ps[1].get_invs(), False) + assert_equal(int(txid, 16) in peer_second.get_invs(), False) self.log.info("Bump time & check that transaction is rebroadcast") # Transaction should be rebroadcast approximately 24 hours in the future, |