refactor(quic): verify peer identity from libp2p-TLS extension#764
Closed
tcoratger wants to merge 2 commits into
Closed
refactor(quic): verify peer identity from libp2p-TLS extension#764tcoratger wants to merge 2 commits into
tcoratger wants to merge 2 commits into
Conversation
The connection layer previously generated a random peer ID when the multiaddr lacked a p2p component, and unconditionally on the listen side. The comment at the synthesis sites explicitly flagged this as "NOT correct for production". Adds verify_libp2p_certificate(cert) to tls.py: parses the ASN.1 SignedKey envelope from the libp2p extension (OID 1.3.6.1.4.1.53594.1.1), decodes the protobuf PublicKey, reconstructs the secp256k1 identity key, verifies the signature binding the identity key to the TLS public key, and returns the canonical PeerId via the libp2p multihash derivation. Wires the verifier into both directions: - connect(): pulls the server cert from the completed TLS session, verifies, and rejects with QuicTransportError on identity mismatch with the multiaddr's p2p component (MITM defense). - listen(): server-side protocol instances now request the client certificate via aioquic's mTLS hook so the handshake delivers a peer cert in both directions. handle_handshake verifies it and tears down the QUIC session if the cert is missing or fails verification. Test coverage: - 7 verifier tests in test_tls.py: round-trip, distinct keys, missing extension, tampered signature, malformed SEQUENCE, unknown KeyType, truncated envelope. - test_connection.py: replaces the two old random-fallback connect tests with four real-cert tests including peer-ID mismatch and missing-cert; extends the listen tests with the same. Note: aioquic does not expose mTLS as a public configuration option, so the server toggles _request_client_certificate on the TLS context. This is the same mechanism py-libp2p uses on top of aioquic. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…uic-verify-peer-identity # Conflicts: # src/lean_spec/subspecs/networking/transport/quic/tls.py
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
The QUIC connection layer previously generated a random peer ID when the multiaddr lacked a p2p component (in `connect()`) and unconditionally on the server side (in `listen()` / `handle_handshake`). The comment at the synthesis sites explicitly flagged this as NOT correct for production. This PR replaces both fallbacks with real verification of the peer's libp2p TLS extension.
What changed
`tls.py` (+196 lines)
Adds the inverse of the existing certificate generator:
`connection.py` (+61 / −18)
Test plan
Test additions:
Things worth a reviewer's eye
🤖 Generated with Claude Code