Skip to content

fix(network): evict stale BSC protocol peers from registry on disconnect#349

Open
tsutsu wants to merge 1 commit into
bnb-chain:developfrom
tsutsu:fix/bsc-protocol-registry-lifecycle
Open

fix(network): evict stale BSC protocol peers from registry on disconnect#349
tsutsu wants to merge 1 commit into
bnb-chain:developfrom
tsutsu:fix/bsc-protocol-registry-lifecycle

Conversation

@tsutsu
Copy link
Copy Markdown

@tsutsu tsutsu commented May 11, 2026

Resolves #348.

Description

  • Unregisters BSC protocol-extension peers from the global command-sender registry when their connection stream drops or when a send to their channel fails, preventing the registry from accumulating stale entries that can never succeed.

  • Refactors the command-sender registry to use per-connection tokens, preventing a data race where a peer reconnecting with the same PeerId could have its new (live) registry entry removed by the de-registration of an older (dead) session.

Rationale

The BSC protocol-extension peer registry (REGISTRY) maps PeerIds to UnboundedSender<BscCommand>s. Entries are inserted when a BSC subprotocol connection is established, but are never fully removed. The map entry is not removed by peer disconnect, nor by BscCommand send failure.

I observed code comments that noted that "failed sends will lazily clean up entries," but this cleanup was incomplete: request_blocks_by_range did not remove the peer on send failure, and there was no Drop-based eviction at all. (The only code path that can currently trigger peer removal from the registry is vote-broadcast processing.)

When peers disconnect (especially in bulk, e.g. due to a netsplit, or due to a bug like #312), the registry retains dead senders. If this happens during fork recovery, then fork recovery picks peers from this stale registry, fails to send GetBlocksByRange through the closed channels, and so fails to ever make progress.

Testing

Existing unit tests pass.

Remove stale UnboundedSender entries when the BSC subprotocol stream
drops, when GetBlocksByRange send fails, and on vote broadcast failures.
Use per-connection tokens so same-PeerId reconnects are not removed by
older sessions.

Co-authored-by: Cursor <cursoragent@cursor.com>
@tsutsu tsutsu requested a review from joey0612 as a code owner May 11, 2026 15:27
@hashdit-bot
Copy link
Copy Markdown

hashdit-bot Bot commented May 11, 2026

Pull Request Review

This PR fixes stale peer handling in a Rust-based blockchain networking module (BSC protocol extension) by introducing per-connection registry tokens and explicit cleanup paths. It refactors the global peer sender registry to store {sender, conn_token} entries, unregisters peers on send failure and on connection drop, and threads the token through connection creation. The changes are aimed at preventing dead channel accumulation and avoiding incorrect removal when a peer reconnects with the same PeerId.

Sensitive Content

No sensitive content detected.

Security Issues

No serious security issues detected.


Generated by Hashdit Bot. This tool can absolutely NOT replace manual audits.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant