BIP: ??? (tbr after sending to mailing list) Layer: Peer Services Title: addrv2 message Author: Wladimir J. van der Laan <firstname.lastname@example.org> Comments-Summary: No comments yet. Comments-URI: Status: Draft Type: Standards Track Created: 2018-06-01 License: BSD-2-Clause
Table of Contents
This document proposes a new P2P message to gossip longer node addresses over the P2P network.
This is required to support new-generation Onion addresses, I2P, and potentially other networks
that have longer endpoint addresses than fit in the 128 bits of the current
This BIP is licensed under the 2-clause BSD license.
Tor v3 hidden services are part of the stable release of Tor since version 0.3.2.9. They have
various advantages compared to the old hidden services, among which better encryption and privacy
These services have 256 bit addresses and thus do not fit in the existing
addr message, which encapsulates onion addresses in OnionCat IPv6 addresses.
Other transport-layer protocols such as I2P have always used longer addresses. This change would make it possible to gossip such addresses over the P2P network, so that other peers can connect to them.
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119.
addrv2 message is defined as a message where
pchCommand == "addrv2".
It is serialized in the standard encoding for P2P messages.
Its format is similar to the current
addr message format
, with the difference that the
fixed 16-byte IP address is replaced by a network ID and a variable-length address, and the time and services format has been changed to VARINT.
This means that the message contains a serialized
std::vector of the following structure:
||Time that this node was last seen as connected to the network. A time in Unix epoch time format, up to 64 bits wide.|
||Service bits. A 64-wide bit field.|
||Network identifier. An 8-bit value that specifies which network is addressed.|
||Network address. The interpretation depends on networkID.|
||Network port. If not relevant for the network this MUST be 0.|
One message can contain up to 1,000 addresses. Clients SHOULD reject messages with more addresses.
addr has a variable length, with a maximum of 32 bytes (256 bits). Clients SHOULD reject
The list of reserved network IDs is as follows:
|Network ID||Enumeration||Address length (bytes)||Description|
||4||IPv4 address (globally routed internet)|
||16||IPv6 address (globally routed internet)|
||10||Tor v2 hidden service address|
||32||Tor v3 hidden service address|
||32||I2P overlay network address|
||16||Cjdns overlay network address|
To allow for future extensibility, clients MUST ignore address types that they do not know about. Client MAY store and gossip address formats that they do not know about. Further network ID numbers MUST be reserved in a new BIP document.
Clients SHOULD reject addresses that have a different length than specified in this table for a specific address ID, as these are meaningless.
See the appendices for the address encodings to be used for the various networks.
addrv2 messages only, and exclusively, when the peer has a certain protocol version (or higher):
//! gossiping using `addrv2` messages starts with this version static const int GOSSIP_ADDRV2_VERSION = 70016;
addrmessage, ignoring addresses with the newly introduced address types.
The reference implementation is available at (to be done)
(to be discussed)
- Client MAY store and gossip address formats that they do not know about: does it ever make sense to gossip addresses outside a certain overlay network? Say, I2P addresses to Tor? I'm not sure. Especially for networks that have no exit nodes as there is no overlap with the globally routed internet at all.
- Lower precision of
timefield? seconds precision seems overkill, and can even be harmful, there have been attacks that exploited high precision timestamps for mapping the current network topology.
- (gmaxwell) If you care about space time field could be reduced to 16 bits easily. Turn it into a "time ago seen" quantized to 1 hour precision. (IIRC we quantize times to 2hrs regardless).
addr, or making the port optional, would make it possible to shave off two bytes for address types that don't have ports (however, all of the currently listed formats have a concept of port.). It could also be an optional data item (see below).
- (gmaxwell) Optional (per-service) data could be useful for various things:
- Node-flavors for striping (signalling which slice of the blocks the node has in selective pruning)
- Payload for is alternative ports for other transports (e.g. UDP ports)
- If we want optional flags. I guess the best thing would just be a byte to include the count of them, then a byte "type" for each one where the type also encodes if the payload is 0/8/16/32 bits. (using the two MSB of the type to encode the length). And then bound the count of them so that the total is still reasonably sized.
(ideas that were considered but ae probably not the way to go)
- Another option for backwards compatbility would be: Old clients will ignore the
addrv2message, so using
addrv2format for only the larger addresses (TORV3, I2P) would naturally preserve backward compatibility. However, there are some disadvantages as well:
- The advantage of more compact representation of IPv4 addresses would be lost
- There is no path toward deprecating legacy
- Jonas Schnelli: change
services field to VARINT, to make the message more compact in the likely case instead of always using 8 bytes.
- Luke-Jr: change
time field to VARINT, for post-2038 compatibility.
- Gregory Maxwell: various suggestions regarding extensibility
The new message introduces a separate network ID for
Clients MUST send Tor hidden service addresses with this network ID, with the 80-bit hidden service ID in the address field. This is the same as the representation in the legacy
addr message, minus the 6 byte prefix of the OnionCat wrapping.
Clients SHOULD ignore OnionCat (
fd87:d87e:eb43::/48) addresses on receive if they come with the
IPV6 network ID.
According to the spec , next-gen
.onion addresses are encoded as follows:
onion_address = base32(PUBKEY | CHECKSUM | VERSION) + ".onion" CHECKSUM = H(".onion checksum" | PUBKEY | VERSION)[:2] where: - PUBKEY is the 32 bytes ed25519 master pubkey of the hidden service. - VERSION is an one byte version field (default value '\x03') - ".onion checksum" is a constant string - CHECKSUM is truncated to two bytes before inserting it in onion_address
Tor v3 addresses MUST be sent with the
TORV3 network ID, with the 32-byte PUBKEY part in the address field. As VERSION will always be '\x03' in the case of v3 addresses, this is enough to reconstruct the onion address.
Like Tor, I2P naming uses a base32-encoded address format.
I2P uses 52 characters (256 bits) to represent the full SHA-256 hash, followed by
I2P addresses MUST be sent with the
I2P network ID, with the decoded SHA-256 hash as address field.
Cjdns addresses are simply IPv6 addresses in the
fc00::/8 range. They MUST be sent with the
CJDNS network ID.