Amiti Uttarwar - Attacking Bitcoin Core (2020-04-16)
Transcript By: Michael Folkson
Name: Amiti Uttarwar
Topic: Attacking Bitcoin Core
Location: BitDevs LA
Date: April 16th 2020
I’m going to talk to you today about attacking Bitcoin Core.
To start with the fundamentals. As we all know Bitcoin is a money and it is different to our existing centralized solution of money because instead we have nodes that are running all around the world.
Fundamentally what is required for this to work is the idea of consensus where all the nodes must agree on the same fundamental values. Who has how much money? This is the core innovation of the blockchain. What it comes down to is the concept of each node has the ability to validate blocks and transactions independently. But there is another element in that these nodes aren’t just totally independent. They are talking to each other and interacting. The messages they send and how they find one another. These are concerns of the peer-to-peer network which is what this talk is going to be focusing on.
Node on P2P network
Concerns of a node on a peer-to-peer network include but are not limited to what nodes to connect to, identifying if there is a sufficient number of peers, identifying which transactions to relay, managing resources such as bandwidth, privacy around revealing transactions, trying to identify if the transaction is able to get mined, trying to know if I have the latest block and trying to figure out if any peers are malicious. This is a subset of the concerns but it can give you an idea of the kinds of questions we are focused on in P2P.
Fundamentally we can distill the concerns around three main topics which are the three pieces of inventory that get gossiped across the network. Those are blocks, the blocks of the blockchain and the transactions that are within them. There are also transactions which are the unconfirmed transactions in the mempool and addresses which identify where a node is and allow them to connect to new peers.
P2P design goals
I have come up with a framework around the design goals of the network to help incorporate all of the different aspect of what we are trying to achieve. It is still a work in progress. I welcome any feedback. Hopefully you will find it helpful for navigating the conceptual space that I am talking about. The five goals are reliable, timely, accessible, private and upgradeable. So what do I mean? Reliable means that if the node submits a valid message to the network it will eventually be delivered to all other nodes on the network. This should be done in a timely fashion which is different according to what the message is or who the user is. What is a reasonable amount of time for a transaction is different than for a block. The reasonable amount of time for a block to be propagated for a normal user versus a miner is very different as well. Each of the messages have to make it out in a reasonable amount of time. That is great if you can have a network and your messages make it out in a reasonable amount of time but you also have to get onto the network. In Bitcoin we try to keep that as a very low requirement. It is possible to run a node on a Raspberry Pi so we try to make the network very accessible. Another aspect of accessibility is the idea that a node should be in control of whether or not it is participating on the network aka an adversary shouldn’t be able to keep it off the network to disconnect it or take it down. I think these three are important for any peer-to-peer network to be successful but in Bitcoin we have two additional values: privacy and upgradeability. Privacy is important because it is money and fundamentally it comes down to the idea of not wanting to connect your real world identity with your onchain interactions. We will discuss that in more depth later. There is also this idea of upgradeability which stems from the ethos that if a user decides to buy into the rule set at a specific point in time they should always be able to transact with that rule set. If a development cycle has moved forward and is on a different software version but they haven’t participated in that or maybe they didn’t agree with it, they should still be able to transact with the rule set they initially bought into. So the majority of this comes to consensus but there are aspects that we have to consider in the peer-to-peer network. We will talk a little bit more about that as well. Here are the five goals. In this talk I want to dig into a couple of them to see why it is hard to design a system that achieves this.
Let’s start with the idea of reliability. Here I have a network of nodes and say this is your node. If you form a mempool transaction you want it to get to all of the nodes which is prudent because you don’t know where the miners are. One way that it might not make it to miners is if there was a split in the network and there were no miners on your side of the split. Then your transaction wouldn’t be able to make it into a block. Another configuration with a split could be that there is a miner on your side but there is actually more hash power on the other side. In this situation this would lead to a chain split and you would be on the losing side of the fork. In this case everyone loses because Bitcoin wouldn’t be functioning as intended.
One idea that we strive for with reliability is trying to prevent network partitions. There are a lot of ways that that can occur, some of which are unintentional. An example of this is you could imagine it would be reasonable to say “As a node I am going to give a little boost to nodes that are able to serve me transactions and blocks quicker.” You start prioritizing peers that give you the information fast. But over time it can have a very unintended side effect of a partition because it prioritizes geographic location and what could happen is that the nodes that are in Australia and New Zealand start prioritizing one another and get disconnected from the nodes in the Americas. This is a different network than the nodes in Europe and Asia. So that is one example of how unintentionally a design decision can lead to a partition over time.
Q - What was the attack by omission? What was that?
A - There are a couple of ways that you can omit information. One is that the victim can try to send a transaction to the network and since the adversary has entire control of what the network sees they can censor those transactions. Also they can identify that that was coming from the victim. Obviously there is no privacy there. The other way they could lie is broadcast fake transactions to the victim. By fake I mean potentially conflicting with what is going on in the mempool of the main network. They can also omit information like if another node broadcasted a transaction then the victim might not be able to find out about those mempool transactions or even when it is picked up into a block. In general this adversary has so much control of the message passing that the victim is in a really bad position. They just don’t know what attacks they’ve been subjected to.
We don’t want that to happen. There are a lot of techniques that we can use to prevent it. One of them is to increase the number of connections. You can imagine the more connections we have, the more expensive for an adversary to take control of all of those connections. But we are bounded by the idea of accessibility because bandwidth is a limited resource. It is not just limited on the individual level. There is also an aspect of limitation at the network level. What do I mean by this? There is a difference between the idea of inbound versus outbound connections. All of the nodes will have outbound connections which is how they bootstrap but not all nodes accept incoming connections. So when we are looking at the network as a whole we need to ensure that the nodes providing incoming connections are sufficient to serve all of the nodes that want outbound. These are the number that are default in Bitcoin today. We have 8 outbound and up to 125 total. Another technique is to choose diverse peers which is a great technique but we come up against the fact that we have very limited amount of information about these peers. This is mostly at the network layer and there is logic that looks at the IP addresses and buckets and chooses different outbound connections from those different buckets. This helps for making it harder for an attacker, more expensive for them to spin up nodes that have the diversity. But it is bounded in how far it can go. Another technique as a node operator is to run multiple nodes on different network interfaces. This way a malicious entity would have to identify all of your nodes and eclipse all of them. Hopefully at least one of your nodes has access to the main chain. That’s great but this is how the user runs the software. This is out of scope for what we can design for in the peer-to-peer layer of Bitcoin Core. One more technique is to value long lasting connections. The theme of increasing the cost to the adversary, the idea here is that it would be much cheaper for an adversary to spin up a node and connect to you for a hour than it would be to be running that node for a week or a month. The idea here is if it is a longer lasting connection you can give it a little bit more weight because there is a higher chance that it is a honest peer. We are going to dig into this more because the goal it comes against is that of privacy.
Why does privacy matter to you? How is Bitcoin’s current state in comparison to the ways that you want privacy? Is it sufficient? Are there different features you are looking for? What use cases are important? Opening it up to the floor.
Audience: Right now if you have a light wallet it is not private because you are relying on a service that can see all your public keys or all your addresses which makes you easier to track. That is difficult right now in the light client world. I also think on the full node it is tricky to run. Even if you are running a full node you are still exposed if people are watching your connections.
Audience: I have some research that even Tor with Bitcoin wouldn’t be a good idea.
Audience: He read some research where Tor may not be the best to use with Bitcoin.
I’m not familiar but I’d definitely be interested if you are willing to send that research my way. I haven’t heard of it.
Audience: I think one thing that sucks about Bitcoin transactions right now if that I have to be mindful of my UTXO set meaning if I send 0.5 Bitcoin to a Bitcoin address and I am paying for a coffee or maybe even a $100 gift card with Bitcoin I have to think about do I want to let the other person know that I am breaking up 0.5 Bitcoin on my end to send you $100 of Bitcoin. That doesn’t sound very private to me. That person should only know how much Bitcoin I am sending them. He shouldn’t know how much Bitcoin I am taking from. That is something I wish could be a little bit better about Bitcoin and its transactions.
Audience: That is one of the points of Lightning?
Audience: Lightning definitely would make it a lot faster and cheaper and they wouldn’t be able to see where the Bitcoin came from.
I think privacy is a very complex thing. The way we all think about it is very different. It is very interesting because a lot of it is application layer. If you have an application that is able to manage your UTXO set and make it invisible for you as a user then what happens onchain might actually provide another privacy where the heuristics for a spy are insufficient to identify what your actions are. But right now the way that applications are, the way that Bitcoin is, if you truly want your transactions to be private there are features that are available but you have to be extremely involved in managing your UTXO set. You can form a transaction offline and then send it to someone via US Mail or whatever and they can broadcast it from their node. That would be really hard to link but obviously that is a terrible user experience. It is interesting and I think that this is something that has so many different layers. The privacy guarantees of Lightning are different, the privacy guarantees of software are different and the network. When we are thinking about it in the P2P network the element that we are carefully considering is trying to not let a spy link your IP address to your Bitcoin addresses. One of the easiest ways that they can do this is by identifying who is the source that initially broadcasts this transaction because then there is a really high degree of confidence that whoever initially broadcast was participating in the transaction. Specifically probably the one spending funds. An element of information that really helps with this is knowing the network topology. As we’ve said there are a lot more layers.
Let me talk more about the network topology idea. If this is you and you have a mempool transaction then ideally what would happen is that it would appear in everybody else’s mempool at exactly the same time. That’s not really how computers work. What we do is we add a random timing element in the Bitcoin application so that there is a delay. The message gets propagated in way that maybe a node four hops away gets it before your direct neighbor. This is helpful. But you can imagine that a spy that is paying attention and there is a lot of transactions over time, is able to use the information and a random interval to figure out what the topology is and who is broadcasting each transaction. What would make it harder is if they were trying to hit a moving target and the connections were changing over time. The fundamental idea here is that they mimic connections and help maintain transaction privacy.
But now we are talking about protection against eclipse attacks. Long lasting connections can help for reliable delivery. So between these two ideas there is a little bit of an intrinsic tension. If we zoom out to a bird’s eye view it seems kind of intuitive. Reliability is saying you want everyone to know your message but privacy is saying you don’t want them to know who you told. Said in another way you want to tell everyone your message but you don’t want them to know that it is your message. This is a tension that is really hard to design and achieve both of them at the same time.
Let’s look a little closer at privacy. When we are talking about leaking node topology each message offers a unique set of information that allows an adversary to identify who your neighbors are. If you remember the beginning of the presentation there are three main messages that are gossiped around the network. Addresses, transactions and blocks. Let’s take a look at how each one of these can be used to identify neighbors.
Privacy Attack Vectors
First, addresses. This is the network graph. This is the victim and this is the adversary. What the adversary can do is spin up another node and IP address number one and send that only to the victim. The victim tells its neighbors and when those neighbors try to connect the adversary identifies those connections. A disclaimer. This is oversimplified. This is not actually how easy it is. We have a lot more nuance to it but fundamentally this is the idea. This can help you get some intuition into how it would work. Transactions can also be used to identify topology. I’m going to put this out to the group again. Does anyone know how this can be used? How would an adversary potentially use a transaction to figure out the network graph of nodes?
Audience: Is one idea when you broadcast a transaction and find out how fast it propagates and to what node?
Audience: Setting up lots of sybil nodes that are listening to all the transactions seeing where they are coming from.
Yeah definitely. Spinning up a lot of nodes. Having a lot of connections and tapping into who is propagating it when is a fundamental aspect of using transactions. That is one of the aspects, the timing of how it propagates around the network. If you have a lot of data points around that you can use that as we saw in the example we just talked about. Another attack is to create a transaction that is a double spend. To have conflicting versions of a similar transaction and then send the two different ones to two nodes. Then you can query other nodes and figure out which one they are closely connected to because they will only accept the first of those two transactions that they see. It is pretty cool. There is also a nuance around how you can query nodes because we do have some mechanisms like in the mempool you won’t serve a transaction that you just saw. You will have a little bit of time before you respond and say “Yeah I have it.” But there are ways that people in different points in time have been able to get around it. One of them is using the child-pays-for-parent idea of having chains of unconfirmed transactions and using the child to query to see if they request the parent. Or if they already have it. If this is something you find interesting the TxProbe paper uses all of these techniques and is one of the more recent extremely effective attacks. A lot of which has been mitigated at this point but that paper really helped catalyze some of the vulnerabilities. I was going to ask if anyone knows about attack vectors for an adversary to use a block to figure out node topology?
I won’t leave this here for too long because it is a trick question. I don’t know of any, it is actually really hard. This slide is mostly to talk about why it is hard. First blocks are really infrequent. Addresses and transactions can be occurring all the time and you can spin up nodes or make transactions very frequently whereas blocks have this cadence where it is difficult to mine and target ten minutes. They are extremely infrequent in comparison. Another aspect is the FIBRE network which stands for Fast Internet Bitcoin Relay Engine and this is a private network that miners are on that they use to propagate blocks to one another extremely quickly. If you are not part of that network then it appears as if blocks just showed up in a bunch of different nodes all at the same time making it very hard for the adversary to identify and track. Then we don’t have the same sort of trying to obfuscate where the source of the block came from as we do with transactions. We don’t have any random time delay in the software at the application level. Really it is just the internet level latency. I have these videos here that are super cool. The link is on the bottom right for the project that I pulled this from. This is showing a visualization of a transaction making it to different people’s mempools all around the world. Now we are at almost four seconds and you can see that it is kind of consistent. There has been a steady trickle of yellow lights popping up. That is going to be in contrast to what we see here with blocks. In the first second there is a huge rush of blocks making it to most of the nodes and then there is a slow trickle. These are probably nodes that are running on… maybe they have less bandwidth or a weaker internet connection. That is the long tail of them downloading it. That hopefully gives an idea of the difference between transaction propagation versus block propagation.
The concept we just talked about here was that addresses, transactions and blocks are the three pieces of inventory that are gossiped around the entire network. The mechanisms and the logic that is used to relay each one of these gives us different sets of information in order to identify what your topology is, who your neighbors are. Blocks however leak the least information.
We can put all this together for a feature called block-relay-only connections. The idea here is that a full relay uses all three of these and sends that back and forth. Block-relay-only connections as you might imagine doesn’t send addresses, doesn’t send transactions, just sends blocks. This can increase privacy and reliability.
The idea is that on a network you have full relay connections in blue and block-relay-only connections in purple. If there is a victim and an adversary was able to take control of all of full relay connections then hopefully it will still have the block-relay-only. From that they would be able to find out what the mainchain tip is which would really reduce the set of attacks that the adversary can execute. Because the victim knows at the very least what the mainchain of the blockchain is. There are also huge guarantees for the network as a whole. If a malicious entity was able to identify the topography of the network then they could see by taking these two nodes down, maybe via a DOS service or any attack that they can use, they can cause a partition in the entire network. But block-relay-only connections can be kind of invisible and potentially keep the network on the same chain. I think it is super cool because earlier we were talking about how privacy and reliability can be in tension with one another. But here we have a feature that increases privacy and thus increases reliability bringing the two concepts together.
Bitcoin Core P2P PRs
This is something that is fairly recent. It got merged in September of last year. As you might be able to see in some of this content we are really talking about the heart of why this is a feature that is getting merged and is currently making Bitcoin software more robust. Based on that hebasto opened an issue about how we can further increase security guarantees by introducing the idea of anchors.
The anchor idea is that if you are running a node and you are connected to some peers you can persist some of them. If you shut down either intentionally or unintentionally when you start up you can try to reconnect to those same peers. This is you. You can choose to.. nodes and when you restart to try to reconnect to them. That is great for reliability but because of what we were talking about with network topology and long lasting connections it would not be very good for privacy if we were to reconnect to the full relay connections. So instead we can use the block-relay-only idea and reconnect to those. The idea here is that we increase the reliability and we are ok for privacy because we are not sending transactions to these connections. This is a PR that is currently open. If you are interested you can go to GitHub and see all the nitty gritty of what is being discussed to consider this improvement. Another step if you are interested in learning more is that I hosted a Bitcoin Core PR review club a couple of weeks ago on this topic. There are a lot of notes. You can read the logs on what the conversation was about. That can also be a helpful ramp up. At this point from this presentation you do have the fundamentals that would allow you to engage in the concepts that were considered when trying to implement these solutions.
So that’s the content. I have covered a lot so let’s review. I created a framework for five design goals of the peer-to-peer network. Reliable, timely, accessible, private and upgradeable. What we mean is that we want valid messages to make it out to the network in a reasonable amount of time and for nodes to be able to get onto the network and stay on the network of their own accord. These three values seem quite important for any peer-to-peer network to be successful but in Bitcoin we have two additional. Privacy because it is money and upgradeability because of the ethos of Bitcoin. We use that to dig into reliability versus privacy and take a look at why these two can seem at odds with one another. We talked about a threat to reliability that is network partitions. And a specific type of network partition that is an eclipse attack. A malicious entity trying to isolate a victim. We took a look at how privacy and network topology can be leaked from each of the three different kinds of messages gossiped around the network. And we put it all together to present the idea of block-relay-only connections that can help increase privacy and increase reliability. We took a look at a feature that is developing on that now which is the idea of anchors and persisting connections when you restart and try to reconnect. That is all I’ve got today. Does anyone have any questions?
Q - How do full nodes currently find their peers? Is it always though DNS or do they have other methods?
A - I think there are four main mechanisms. There is DNS seeds. There is the ability to hardcode, I think it is called
addnode. Basically you can explicitly put in certain peers that you want to connect too. The outbound connections are using… There is quite a lot of logic and I am not familiar with all of it. Using the addr messages that get sent around a node identifies different nodes on the network, which ones are accepting incoming connections and is able to form connections to those. Then if your node accepts incoming connections then people might just connect.
Q - What are the trade-offs of having out of band message relays working with the mainchain on the internet with Bitcoin Core? The Blockstream satellite or the cool stuff that GoTenna is attempting with the mesh or dandelion, relaying using other means. The network will be partitioned because these are all different mediums to exchange messages. It is worth the eclipse attack that is possible in theory still?
A - I think having more communication layers makes it more difficult to partition the network because what I am talking about is not that we need one layer of network and if that is broken up into pieces, that is not what we are partitioning. What we are trying to partition is nodes from one another. If you are able to cut off all of the mechanisms a node has to talk to the other nodes that’s the kind of partition we are talking about. If we have the Bitcoin Core P2P layer and then we have another mesh network and then we have all of these layers that these same nodes are talking to each other in different ways. It actually increases the robustness and the difficulty for an attacker to be able to say “Now I have to stop you over here and over there and over there.” Does that make sense? I find this direction really interesting. Historically we have only had this one P2P network but even in Bitcoin Core introducing block-relay-only connections introduces the idea of having multiple types of networks. Now there is a network of people only talking blocks to one another. That is slightly separate to the main one. We might see development in the future for these reasons of having multiple different layers.
Q - The idea with the FIBRE network is that it is harder to identify the nodes because it is more of a flood protocol than a gossip protocol. It is infrequent and it doesn’t send transactions. With the anchor PR couldn’t you just spin up a bunch of nodes and identify the nodes that all the anchors are attaching to and dox the FIBRE network?
A - The main reason the FIBRE network exists isn’t for any sort of privacy. Any tiny delay between them getting the most recent block and somebody else having it is huge loss to their profit or potential profit. So FIBRE is a network that they use in a very specific way. I think there is a predetermined layout for how the nodes are connected to one another to get blocks out as fast as possible. This is an entirely independent network. The Chaincode podcast, there is an episode with Matt Corallo and he talks about it. It was so fascinating. I recommend that if you are interested in learning more. FIRBE is a totally independent network to the Bitcoin P2P network and so anchors would be in the Bitcoin P2P network. The second part of what you were saying was could an adversary take over and be all the anchors? That is possible and that is something we are trying to very carefully identify. If you do anchor an adversarial connection what is the extent that they can use that against you. But also what is it providing protection against? If they are your anchor but then you try to reconnect to them and you are unable to that is not a big deal because you have your other outbound connections. Up until now that is how Bitcoin has been working. They can’t really take away too much of your privacy around transactions because you won’t be telling that to them. There are some super nuanced considerations around if they were DOS attacking you. There is actually an open conversation on the PR right now. I think probably a little too heavy to dig into right now but we did talk about it in the Bitcoin Core PR review club. There are a lot of resources. If you want to follow up with me after I love nerding out about this.
Q - One concern I have seen about the FIBRE network is that it could potentially be a source of centralization. Do you have any more insight into the FIBRE network and how it functions? And whether or not it is like that?
A - I really am not very familiar with the details of FIBRE. I can’t comment.
Q - What do you think about Erlay? I believe one of its characteristics is it allows lower bandwidth so you can have a greater number of connections. How does that affect privacy and some of these other things?
A - I definitely think Erlay is an exciting development. I think there is a tonne of potential for improvements and different kinds of trade-offs of features. But also it is a huge change. We have to evaluate that very carefully. That is why we are going through the rounds of rigor. Right now I think as a concept it has been evaluated very carefully but recently Gleb (Naumenko) has put up a PR that is a huge diff of what that would look like. It is in the very early stages of analyzing what implementation would look like. I have not taken a super in depth look myself. For the reason you say as well as a couple of others I think that if done correctly… I think we are looking at a different set of trade-offs. Having higher number of connections for a lower bandwidth usage has all of these cascading effects that could really benefit the network. But also it is so hard to think about all these second order effects that might happen over time. I think it is super exciting and I definitely want to fully dig in at some point.
Q - Given the Bitcoin network is dominated by the Bitcoin Core implementation, how much would more diversity in the implementations of the Bitcoin P2P help to solve the issues we are talking about here?
A - It is not a question I have thought a lot about. I don’t have any great answers offhand. I could see ways in which having multiple implementations could help execute a partition attack. For example if there was an extreme of five nodes using a particular kind of network then you could be nodes six through ten and potentially get all of those connections or something like that. On the other hand if there was a healthy split of 50/50 as well as nodes that were connected to both networks then maybe that would increase the cost of attack in an order of magnitude. In terms of the hypothetical I don’t think there is any clear answer but it is definitely a possibility that could help or make it worse. Which is pretty much my answer for everything.
Q - There is also an element of client diversity through versioning as well. That is another factor to consider.
A - Which breaks my brain when I am designing features in Bitcoin because it is so different to any other software project. With all software you prioritize the current version and you support a couple more and then the old ones you tell them to upgrade. Bitcoin is the first project I’ve seen where all software versions are first class citizens.
Q - It has dug its roots in deep and it is not moving. It is completely entrenched.
A - It is wild and really requires a different approach when thinking about how to develop features.
Q - Would you consider that technical debt? There are some parts of Bitcoin Core that are pretty Frankenstein-ish. It is not the easiest solution but it was an adhoc thing. It got set in stone and they built on top of it. At what point is that considered mega bad technical debt and what point is it just consensus now?
A - That is exactly the question. It has been strange for me to come on and be like “We are going to support this forever”. There are some ideas for an extremely long timescale. Since we are only ten years in I don’t think we have ever truly gone through a full deprecation process. It is not theoretically impossible while still withholding the ethos but there are lot of things. Even in consensus because we don’t hard fork we are building features in a totally different way. SegWit would have been entirely different if our community said “Hard forks are ok. We’ll do a hard fork over the course of five years or whatever it was.” It is hard to call it debt because it stems from such a fundamental ethos for all of this voluntary action from all of the users. It is a different constraint you are designing the system within.
Q - If you can add anything to the wishlist of stuff to fix what would it be?
A - It is a hard question because I have so many answers that are kind of small. I’ll get it in net_processing.cpp and we can just clean this up. That is so outside of my brain space from designing in this project. There are things in consensus we could clean up. There are things in P2P that we could clean up. But then it would be a different network entirely.