Mesh Networks

In a typical networked game, there are two main forms of network topology. The first, and the most simple, is the client-server topology. Sometimes the server is an active instance of the game in which a player has chosen to host a game on their PC to which other players can connect to, other times it is running as a standalone instance in which all players have to connect to.

Client-server topology has many benefits. It’s easy to secure. Cheating is much more difficult if implemented correctly. It’s well understood and, with a bit of practise, is easy to implement. Connection problems are mitigated through a single point of failure, meaning that as long as people can connect to the host, the game can easily be played. Running a standalone(also known as “headless”) instance in a server farm or on the cloud is trivial.

Another form of network topology is peer to peer(P2P). P2P games allow users to connect and interact with the world, but there is no central server acting as an authority over what can and can not be done. Each player sends messages to other players indicating what they are doing in the world, but no single person is responsible for simulating the results and broadcasting the final state to all other players, instead, it’s a collective effort.

P2P is much more difficult to implement in the case of most games. Without a central point of authority, cheating can happen, connection issues will become prevalent(more on that in a bit), and wrapping your head around the state of objects when anyone can literally do anything at any moment becomes a development nightmare.

So why bother with P2P? it sounds like a nightmare!

To put it in a single word… Cost!

Running a server costs money. When you’re a large game like Rocket League, then you can afford to run the servers without any worry, but if you’re a smaller game development company, then the costs can add up. Sure, you could just allow your users to host and forget about the hosting, but then you run in to connection issues. What do I mean by connection issues? Well, read on.

Most games use UDP as the base protocol. UDP is stateless, meaning it doesn’t maintain a connection like TCP/IP does. Because it doesn’t maintain a connection, it’s fast. Very fast! You need that kind of speed when you’re dealing with characters moving and objects interacting, so UDP is typically the protocol of choice. But, there’s downside to all this speed. UDP doesn’t guarantee that packets will arrive in the order you sent them, or even if they will be received at all. Sure, reliable UDP(AKA RUDP) protocols exist and are used extensively in games, but UDP doesn’t have that feature out of the box.

However, despite all this, there’s a hidden feature of UDP that also makes it more attractive. TCP/IP connections require an open port. If you’re hosting a game server on a server rack somewhere, this isn’t a problem. If you’re hosting a game from some dormitory or office building, then it becomes a problem. That’s because a firewall will typically block any open ports. However, most routers allow for something called NAT Traversal. When it sees a UDP packet originating from within the network, like Bob, going to a specific user, say Alice, it assumes that any packets coming from the Alice must go to Bob. This is known as NAT punchthrough. It allows anyone, anywhere to become a host, with some obvious caveats, like overly restrictive firewall rules, but it works %97 of the time. For the remaining %3 of users, they will require a relay server. The relay server simply relays packets back and forth between Alice and Bob in the example above.

Wait, so if anyone can become a host, then why bother with P2P? Just set it up so that anyone can be a host and call it done!

Well, that works, and is actually used in a lot of commercial games, but there are security issues with it. First, if anyone can become host, then what’s stopping someone with a modified version of the game(AKA hacked copy) from just dominating every game? There’s no easy way to tell, and this has been an issue for games that allow for self-hosting. Another issue is dropouts. If the host loses their connection to the internet, then everyone would be forced to leave(unless you have host-migration, but that’s another can of worms for another blog post sometime). This isn’t the ideal situation for many games that are highly competitive and require accurate reporting.

But wait a second, earlier I said that P2P was insecure as well. Yes, and it’s true. Pure P2P is insecure. That is why the title of this article is called “Mesh Networks”. Mesh networks are not a new idea. Put simply, there is no central authority, but collectively, everyone has authority. Let’s use an example for this.

Let’s say Alice and Bob are playing together. There’s a button that lowers a bridge in a separate part of the level, so Alice goes to press the button while Bob goes and waits at the bridge. Since there are only two people, each player is responsible for checking the other players actions. When Alice moves, Bob is responsible for simulating her movement. When Bob moves, Alice is responsible for checking his movements. When Alice goes to press the button, it’s Bob’s simulation that receives the request to press that button and feed the result back to Alice. This means that no action Alice could take on her local copy of the game is actually done on her machine, limiting the possibility of cheating.

But wait, couldn’t she just teleport Bob over a pit of lava? No. Every action would have a set of possible results. Pressing forward means moving a certain distance forward. Bob would know that on his client. If he pressed forward and was told by Alice that his new position was over a lava pit, and that didn’t match up with a possible result, then he would know that Alice is attempting to cheat. This would result in an immediate disconnection as neither Alice or Bob could be trusted, even though Bob did nothing wrong.

Now that you understand the basics of cross connection authority, let’s expand that a bit and add two more players. Fred and Dan. Instead of having a single authority per player, let’s say we have two. When Bob goes to move forward, he now needs Alice and Fred to do the simulation. When Alice moves forward, she now needs Fred and Dan to simulate her results. Everything is running smoothly and everyone is able to send messages back and forth, but then Alice tries her cheating once again and attempts to send Bob over the lava pit. In this case, Bob would have his potential results list, and Fred’s simulation would match, but Alice’s would not. He could disregard Alice in this scenario, and the game would carry on, but we could go a step further and mark Alice with an untrustworthy flag. If too many untrustworthy results come from her machine, then her connection to the game could be terminated and the game would carry on.

In fact, that’s the beauty of this setup. If you have 3 or more players, then anyone could be disconnected at any time and the game would carry on. Maybe you’d need to rebalance the network, but for the most part, it just works.

Of course, this comes at a price. Implementing this type of setup requires painstakingly going through and crafting each and every action in the game to retain a list of potential results and verifying that with a peer. Any mistakes could be exploited which would allow cheaters to potentially gain the upper hand, but no solution is perfect.

In conclusion, I’d like to see mesh networks explored more in games. I’ve talked about this type of setup for years, but I’ve never had the time or resources to build this type of setup, but if done properly, it would eliminate the need for hosted client-server solutions which would drastically reduce the overhead costs of many games. I think it’s something worth exploring and if you have any questions or comments, please feel free to leave them below.

Cheers,
-Ken