Repository: bitcoin/bitcoin
File: src/net_processing.cpp (C++)

Code before:
            return;
        }

        // If an older block is requested (should never happen in practice,
        // but can happen in tests) send a block response instead of a
        // blocktxn response. Sending a full block response instead of a
        // small blocktxn response is preferable in the case where a peer
        // might maliciously send lots of getblocktxn requests to trigger
        // expensive disk reads, because it will require the peer to
        // actually receive all the data read from disk over the network.
        LogDebug(BCLog::NET, "Peer %d sent us a getblocktxn for a block > %i deep\n", pfrom.GetId(), MAX_BLOCKTXN_DEPTH);
        CInv inv{MSG_WITNESS_BLOCK, req.blockhash};
        WITH_LOCK(peer->m_getdata_requests_mutex, peer->m_getdata_requests.push_back(inv));
        // The message processing loop will go around again (without pausing) and we'll respond then
        return;
    }

    if (msg_type == NetMsgType::GETHEADERS) {
        CBlockLocator locator;
        uint256 hashStop;
        vRecv >> locator >> hashStop;

        if (locator.vHave.size() > MAX_LOCATOR_SZ) {
            LogDebug(BCLog::NET, "getheaders locator size %lld > %d, disconnect peer=%d\n", locator.vHave.size(), MAX_LOCATOR_SZ, pfrom.GetId());
            pfrom.fDisconnect = true;
            return;
        }

        if (m_chainman.m_blockman.LoadingBlocks()) {
            LogDebug(BCLog::NET, "Ignoring getheaders from peer=%d while importing/reindexing\n", pfrom.GetId());
            return;
        }

        LOCK(cs_main);

        // Note that if we were to be on a chain that forks from the checkpointed
        // chain, then serving those headers to a peer that has seen the
        // checkpointed chain would cause that peer to disconnect us. Requiring
        // that our chainwork exceed the minimum chain work is a protection against
        // being fed a bogus chain when we started up for the first time and
        // getting partitioned off the honest network for serving that chain to
        // others.
        if (m_chainman.ActiveTip() == nullptr ||
                (m_chainman.ActiveTip()->nChainWork < m_chainman.MinimumChainWork() && !pfrom.HasPermission(NetPermissionFlags::Download))) {
            LogDebug(BCLog::NET, "Ignoring getheaders from peer=%d because active chain has too little work; sending empty response\n", pfrom.GetId());
            // Just respond with an empty headers message, to tell the peer to
            // go away but not treat us as unresponsive.
            MakeAndPushMessage(pfrom, NetMsgType::HEADERS, std::vector<CBlockHeader>());
            return;
        }


Review comment (suggestion):
(Referring to lines further down)

Seems like these should also be calling `DisconnectMsg()` for uniformity?

a:
https://github.com/bitcoin/bitcoin/blob/06443b8f28bcec4315cec262eb03343dee5465a6/src/net_processing.cpp#L4208-L4209

b:
https://github.com/bitcoin/bitcoin/blob/06443b8f28bcec4315cec262eb03343dee5465a6/src/net_processing.cpp#L5210-L5211

I see these following ones were consciously skipped as documented in https://github.com/bitcoin/bitcoin/pull/28521#issuecomment-2244921840 due to concerns over complicating the logging.. and they do include "disconnecting" already, so it's more okay.

c:
https://github.com/bitcoin/bitcoin/blob/06443b8f28bcec4315cec262eb03343dee5465a6/src/net_processing.cpp#L4913-L4915

d:
https://github.com/bitcoin/bitcoin/blob/06443b8f28bcec4315cec262eb03343dee5465a6/src/net_processing.cpp#L5102-L5104

e:
https://github.com/bitcoin/bitcoin/blob/06443b8f28bcec4315cec262eb03343dee5465a6/src/net_processing.cpp#L5154-L5155

Code after:
        }

        // If an older block is requested (should never happen in practice,
        // but can happen in tests) send a block response instead of a
        // blocktxn response. Sending a full block response instead of a
        // small blocktxn response is preferable in the case where a peer
        // might maliciously send lots of getblocktxn requests to trigger
        // expensive disk reads, because it will require the peer to
        // actually receive all the data read from disk over the network.
        LogDebug(BCLog::NET, "Peer %d sent us a getblocktxn for a block > %i deep\n", pfrom.GetId(), MAX_BLOCKTXN_DEPTH);
        CInv inv{MSG_WITNESS_BLOCK, req.blockhash};
        WITH_LOCK(peer->m_getdata_requests_mutex, peer->m_getdata_requests.push_back(inv));
        // The message processing loop will go around again (without pausing) and we'll respond then
        return;
    }

    if (msg_type == NetMsgType::GETHEADERS) {
        CBlockLocator locator;
        uint256 hashStop;
        vRecv >> locator >> hashStop;

        if (locator.vHave.size() > MAX_LOCATOR_SZ) {
            LogDebug(BCLog::NET, "getheaders locator size %lld > %d, %s\n", locator.vHave.size(), MAX_LOCATOR_SZ, pfrom.DisconnectMsg(fLogIPs));
            pfrom.fDisconnect = true;
            return;
        }

        if (m_chainman.m_blockman.LoadingBlocks()) {
            LogDebug(BCLog::NET, "Ignoring getheaders from peer=%d while importing/reindexing\n", pfrom.GetId());
            return;
        }

        LOCK(cs_main);

        // Note that if we were to be on a chain that forks from the checkpointed
        // chain, then serving those headers to a peer that has seen the
        // checkpointed chain would cause that peer to disconnect us. Requiring
        // that our chainwork exceed the minimum chain work is a protection against
        // being fed a bogus chain when we started up for the first time and
        // getting partitioned off the honest network for serving that chain to
        // others.
        if (m_chainman.ActiveTip() == nullptr ||
                (m_chainman.ActiveTip()->nChainWork < m_chainman.MinimumChainWork() && !pfrom.HasPermission(NetPermissionFlags::Download))) {
            LogDebug(BCLog::NET, "Ignoring getheaders from peer=%d because active chain has too little work; sending empty response\n", pfrom.GetId());
            // Just respond with an empty headers message, to tell the peer to
            // go away but not treat us as unresponsive.
            MakeAndPushMessage(pfrom, NetMsgType::HEADERS, std::vector<CBlockHeader>());
            return;
        }

        CNodeState *nodestate = State(pfrom.GetId());