Radix uses node and client identities (IDs) as a means of identification on the network. The manner in which node identities are created is important. It needs to be easy and user friendly, but must also not make it possible for malicious actors to carry out Sybil and Eclipse attacks without great expense.
This article is a slightly extended version of this video of Radix CTO and founder, Dan Hughes, explaining how ID works in Radix:
Please note - there is also a correction at 5:38 - the proof of work has been extended to 30 minutes as the network sync time when first joining the network is typically also around that amount of time.
What are IDs?
Every node and client has a unique and random ID which is generated the first time they join the network.
A new node or client first generates a public and private key pair, similar to other DLTs, which are used to sign and verify events. From their public key they then generate an ID. This unique ID is used to identify a node or client on the network and serves two purposes, determining:
This means IDs are used to form a reliable and efficient peer to peer network. When a node or client joins the network and receives its ID, it is ‘placed’ next to neighbours with the closest matching ID numbers. At this point it establishes a connection with this set of neighbours. This connection can be initiated by either the new node or the one already currently on the network.
Because the generated ID is random (as it is derived from the public key), ID numbers aren’t created sequentially. For example, five nodes joining might receive the IDs 1,5,9,13 and 25. Let us assume each node has a maximum of four neighbours and therefore node 9 is neighboured with 1,5,13 and 25. However, if a new node joins with ID 8 then node 9 will need to replace one of its existing neighbours. Because it is furthest away from 25, 25 is jettisoned and 9 now connects with 8. This process continually repeats as nodes and clients come and go on/offline.
Nodes find their neighbours through Radix’s use of a gossip protocol. Nodes gossip not just events amongst one another, but also their IDs. Nodes then switch their neighbours, following the process above, when they are informed of a closer neighbour.
Because Radix uses a gossip protocol, the network can also easily adapt to a node going down. There will always be a route that events can be propagated along to get to the required destination – if node 8 goes offline or is faulty then the transactions will still be routed through 1,5 and 13. Node 8 will subsequently be removed and replaced, and node 9 can simply reconnect to the next closest node (node 25 for example).
The problem with generating IDs in such a manner lies in the potential attack vectors they provide. If made too easy, a malicious actor could generate trillions of IDs in a short space of time. This would mean they could dominate and crowd the network, leading to the threat of a Sybil attack. Similarly, the bad actor could game the ID generation system in order to generate specific IDs to isolate certain nodes and clients. This could lead to an Eclipse attack.
To prevent Sybil attacks the act of generating a node ID (but not a client ID) requires a small Proof of Work (PoW) exercise. Instead of IDs being generated instantly from a public key derivation, they are instead created following a 30 minute (changed from 120 seconds) PoW algorithm, generated as part of the network syncing process for a new node.
This means honest actors are not inconvenienced but simultaneously makes the generation of IDs on a vast enough scale for a Sybil attack both expensive and time consuming. This PoW exercise is created in such a manner to not allow for ASIC hardware to be used to solve it, as this would speed up the process by which nodes could be generated. More details on this to follow in future blog posts.
An Eclipse attack would be possible if a malicious actor could generate specific IDs, as they would be able to use these to isolate a target from the rest of the network. However, the PoW exercise means that specific ID numbers in a 2^94 address space cannot be trivially generated, preventing this threat without great expense. It also prevents someone from concentrating their IDs on one shard, thus isolating that shard. An attacker would have to do on average 2^32 identity generations in order to put two keys they control on to the same shard. This would take approximately 244,983 years.
Additionally, because a node’s neighbours are constantly changing it means that:
These preventative measures protect the network from malicious actors, whilst being almost invisible to regular users.