hsd icon indicating copy to clipboard operation
hsd copied to clipboard

Discussion: can clearnet peers "upgrade" to brontide by sending their public key?

Open pinheadmz opened this issue 5 years ago • 4 comments

Context: hsd used to only connect to peers with brontide (encrypted p2p), and all peers had a public key attached to their hostname like this:

aonetsezqp4m52w4jpfq2gv3dggy2wqfwqtkfjyttgdidbvhgp5as@165.22.151.242

This applied to all the hostnames in the address book and in p2p addr messages.

However there is an issue with that:

Node ID keys are malleable: preventing connections possible #315

Clearnet p2p was added and now we only connect to peers with brontide if the user inputs the public key (obtained from a trusted source like a hard-coded seed node or provided by the node's owner in some way): https://github.com/handshake-org/hsd/commit/a333a24d40ddfcd7878c4daa69bccedac46fb31b

So here's what I'm wondering -- sort of in the same way that websocket connections start off with a regular http connection and then pass an "upgrade" command -- can we add something to the clearnet p2p handshake that upgrades to brontide?

This way, we can gossip clearnet IP addresses only, like usual. But then maybe when we connect, part of the VERACK message could include a service flag and their public key itself, in the verack message. (We may only trust such keys from outbound peers). Then we can drop the clearnet connection and reconnect on the brontide port with the static key provided by the remote node.

pinheadmz avatar Aug 07 '20 14:08 pinheadmz

I like this idea a lot -> This somewhat accomplishes the same thing as changing the noise protocol pattern to something like XX, but without having to make those changes to the brontide construction.

That being said, I think we'd also need to pass along the port as well, since if I recall correctly Brontide and Clearnet are served on 2 different ports. I don't believe the ports on which those are served over is forced, and so we'd need to communicate to the peer which port to attempt to listen to as well.

Thoughts on rather than including this in the Verack packet, we just create a new packet that mimics websockets' upgrade command?

EDIT: I think we can also upgrade the address manager such that we can gossip brontide addresses provided that they have been connected to already if we go this route, but I'll need to brainstorm on that a bit more.

kilpatty avatar Aug 07 '20 15:08 kilpatty

Good thoughts. We also need to consider what the attacks are and what we ban nodes for. For example, this pubkey is sent in the clear, meaning it can be MITM'ed. So if we try the brontide connection and it fails, maybe we throw away the pubkey and reconnect back on clearnet - but dont ban the node, because it might not be their fault that key was a lie. I dunno. Stuff like that adds up to DoS vectors to...

pinheadmz avatar Aug 07 '20 15:08 pinheadmz

It may be possible to use a peer authentication scheme like bip 150 before upgrading to the brontide connection.

This BIP describes a way for peers to authenticate to other peers to guarantee
node ownership and/or allow peers to access additional or limited node services,
without the possibility of fingerprinting.

This idea came from https://gist.github.com/jonasschnelli/c530ea8421b8d0e80c51486325587c52#risks

tynes avatar Aug 07 '20 19:08 tynes

@tynes this is cool - do we need to use the session ID mechanism though? Brontide will fail if the remote node doesn't have the private key we expect them to.

pinheadmz avatar Aug 07 '20 19:08 pinheadmz