Client server game packet injection - security

I am trying to learn more about security while developing my online game.
Is it possible and how difficult is it to intercept a packet sent from the server, modify it by using some software and send back data to the server?
Here's a scenario:
A player enters a battle against an AI enemy. A player loses the battle and at the end of the battle, the packet is sent back to the server of what has happened. Would it be possible to modify this packet before it is sent and tell the server that the player has won the battle instead? How would one read this data, and modify it?
Would it be possible to go as far as to say the player entered a battle against 1 enemy but send a packet to the server saying the player has won the battle against 20 enemies? (assuming the server has no implementation of protecting itself from this)

Considering your scenario, if you assume the packets between the clients and the server are encrypted then the possibility of the attack happening is fairly low (Of course this depends on the encryption used).
But let's consider unencrypted packets, a man-in-the-middle attack could be possible and is not difficult to perform. This would require the attacker to be able to understand your packet being sent: for instance, if you have a 'win/lose' bit somewhere and the attacker knows its exact position then he could craft a different packet (check out scapy module in python if you're into crafting packets).
There are tools for intercepting packets, the most common one is Wireshark. The Scapy module for example allows you to sniff packets and send a packet at the same time making it easy for this scenario.
The winning against 20 at once scenario also depends on how the server is handling the game on its end (e.g. does it accept more than one game per user at a time?)

Related

Minecraft packet sniffing in python

My aim is to sniff through the Minecraft packets in python and decode the data to get this information:
The server the person is playing on
The player's coordinates on that server
The direction the player is pointing
The player's health
So far, this is my code:
from scapy.all import *
def test(pkt):
payload = pkt
payload = bytes(payload)
if __name__ == '__main__':
single = sniff(filter="tcp and port 25565", prn=test)
The pkt variable is a scapy packet object and therefore has attributes such as .original and .payload. The code so far displays Minecraft's packets, however, I am unsure of how to decode them or what attribute to use. I have found the protocol documentation for 1.12.2 servers.
Thank you for any help in advance.
"As of 12w17a, Minecraft uses encrypted connections for online-mode servers."
https://wiki.vg/Protocol_Encryption
Packet sniffing the connection between a minecraft client and an online-mode server for the purpose of collecting the data you are attempting to collect would be almost impossible.
Maybe consider reading minecraft's memory instead? It would be much simpler if you are attempting to collect this data from a game instance on the same device.
Better late then never I guess.
Public private key encryption is a way to prevent others reading it.
Even by other means you could negotiate a secret:
Let's say you have a chest, put something in it (secret key) and put a padlock on it and send it to someone. The receiver can't open it but he can put an additional padlock on it.
So he locks the chest with an additional lock and sends it back to you. Once you receive the chest it has 2 locks. You remove your lock and send it back again. The chest now only contains the lock of the receiver which he will be able to open when he recieves the chest again.
The chest was never in an unlocked state while in transit and anyone other then the sender or receiver will have been able to see what's inside.

Is my Arduino security scheme good?

I am working on a project where an Arduino will send measurements and receive commands through an Ethernet interface and a REST API to open and lock a door. For all means, we can consider that the devices are protected, but that the Ethernet network may be accessed. Therefore, a Man-in-the-middle attack is plausible.
The commands to open/lock the door will be part of the reply of an HTTP GET request. In order to prevent a MITM attack where the response is faked to open the lock, I want to use some kind of encrypted response. Now, Arduinos lack the power to use HTTPS, and I want it to be Arduinos because of costs and ease of development.
I have come up with the following scheme:
Both the Arduino and the server have an identical set of index-value registers. The value will be used as a code to encrypt using AES-128.
When the Arduino sends its GET request, it also sends a randomly selected index, indicating to the server which value to use to encrypt the open/lock command.
The server sends a clear text response (JSON) where the command field is an encrypted text.
The Arduino will decode it and apply the required action.
The Arduino will also send some sensor data from time to time. In this case, it will send the index of the code it used to encrypt the data and the encrypted data.
The set of index-value keys is large, so repetitions are rare (but may occur from time to time).
My question is, is this scheme secure? Am I missing something? Is there any other more tested alternative for securing these interactions that doesn't involve using a more advanced platform?
Thanks in advance!
Use an ESP2866 based Arduino. It does not cost significantly more, it uses the same tools but you can use SSL instead of rolling your own solution. I have used the Wemos D1 boards and they work as a drop in Arduino replacement.

Do I need to concern security about my game server? [closed]

Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 7 years ago.
Improve this question
I have a game server where clients can connect and communicate with via TCP. Any device can connect the server if it knows the IP and port.
I am wondering if I need to add some security to the server. For example,
(1) Add some encryption for the messages sent/received. (To prevent the protocol content is revealed)
(2) Add some key to the message so if the server cannot recognize the key after decryption, the message will be dropped. (To prevent unknown connections/messages flooding in)
Do you think these things are necessary and is there any other thing I should add for such a game server.
I would have rather posted this to the gamedev question but the mods there are apparently faster than here. Before you quote me, I'd like to point out that the following isn't based on 100% book-knowledge, nor do I have a degree in any of these topics. Please improve this answer if you know better, rather than comment and/or compete.
This is a pretty comprehensive list of client/server/security issues that I've gathered from research and/or experience:
Data
The "back-end" server contains everyone's username, password, credit card details, etc., and should be a fortress. This server is for authentication only and should be on a private subnet; it will communicate only with the login server, only when a well-formed login request is received, and will only reply with "allow" or "deny". If you take people's personal information, you are obligated to protect it, and it would be wise to off-load the liability of everything security-related to a professional or hosting company. There is no non-critical attack to this server; if it is breached, you are finished. Many/most/all companies now draw their pretty login screen on top of another companies' back-end credit card/billing system.
Login
Connections to the login server should be secure. The login server is just a message pump between the public login mechanism, the private data store, and the client/server connection state. For security purposes, any HTTP access to the login system should be hosted on a separate HTTP server; the WWW server crashing should not shut down your online game (my opinion).
World/UDP
Upon successful login and authentication, the server informs the client to begin listening for "bulk data" or to initiate an in-bound connection on a specific UDP port (could be random and per-connection-attempt). Either way, the server should remain silent and wait for the client to IDENT with some type of handshake to verify that the "alleged client" is actually your code. It is easier to guess when the server asks for input sequentially; instead rely on the client knowing the proper handshake when connecting to the world and drop those that don't. The correct handshake to use can be a function of the CPU clock-ticks or whatever. The TCP will be minimally used and/or disconnected from that point on. The initial bulk data is a good place to advertise the current server-side software revision so clients that are out-of-date can update. A common pool of UDP ports can be handed out among multiple servers and the clients can be load-balanced into the correct port/server. Within the game, "zone transfers" can mean a literal disconnect from one server/port and reconnection to a different server/port. In MMO's, this usually appears as a <2 second loading screen; enough time to disconnect, reconnect, start getting data, and synchronize to the new server clock, not to mention the actual content loading.
"World server" describes a single, multiple-client, state-pumping thread running on a single core of a single processor of a single blade. One, physical, server-of-worlds can have many worlds running on it at once. Worlds can be dynamically split/merged (in a quad-tree fashion), dividing the clients between them, again, for load-balancing; synchronization between the servers occurs at LAN speeds or better. The world server will probably only serve UDP connections and should have nothing to do except process state-changes to/from the UDP connections. UDP is "blind, deaf, and dumb", so-to-speak. Messages are sent with no flow control, no error checking, etc; they are basically assumed to be received as soon as they are sent and may actually arrive late, in the wrong order, or just never arrive. Using UDP, neither the server nor the client are ever stalled, hand-shaking, error-correcting, or waiting for data. Messages need time-stamps because they may arrive late and/or out-of-order. If a UDP channel gets clogged, switch valid clients dynamically to another (potentially random) port. The world server only initiates UDP connections with successfully authenticated clients and ignores all other traffic (world servers hosted separately from HTTP and everything else).
Overly simplified and, using only the position data as an example, each client tells the server "Time:Client###:(X, Y)" over and over. If the server doesn't hear, oh well. The server says "Time:listOfClients(X, Y)" over and over, to everyone at once. If one or more of the clients doesn't hear, oh well.
This implies using prediction/extrapolation on the client; the clients will need to "guess" what should be happening and then correct themselves to agree with the server when they start getting data again. Any time you get a packet with a "future" time, even if the packet doesn't make sense or isn't useful, you can at least advance the client clock to that point and discard any now-late packets, helping a lagging client to catch up.
Un-verified supposition:
Besides the existing security concerns, I don't see a reason why two or more clients could not maintain independent, but server-managed, UDP channels between each other. By notifying other clients within close game-proximity in addition to the server, the clients, themselves, can help to load-balance. The server should always verify that what the clients say happened could/should/would happen, and has the ability to undo all of it and reset both clients to it's own known-good state. The information that the clients are able to share, internally, should be extremely restricted; basically just the most-time-critical positional and/or state-data. Client's should probably not be allowed to request specific information and, again, rely only on "dumb" broadcasts. This begins to approach distributed/cloud computing, where the clients are actually doing a lot of the server work, while the server just watches and "referees," calling foul, when appropriate.
Client1 - "I fought Client2 and won"
Client2 - "I fought Client1 and won"
Server - "I watched and Client2 cheated. Client1 wins. (Client2 is forced to agree)"
The server doesn't necessarily even need to watch; if Client2 damages Client1 in an unusual/impossible way, Client1 can request arbitration from the server.
Side-effects
If the player moves around, but the data isn't getting to the server, the player experiences "rubber-banding", where the player appears to be moving on the client but, server-side, they are not. When the client gets the next server state, the client snaps the player back to where they were when the server stopped getting updates, creating the rubber-band effect.
This often manifests another way, too. If the server sees a player moving, then fails to receive the "stopped moving" message, the server will predict their continued path for all of the other clients. In MMO-RPG's, for example, you can see "lagging" players running directly into/at walls.
Holes
The last thing I can think of is just basic code security. This is especially important if your game is moddable. Mods are, by definition, a way for users to insert their own code into yours. If you are careless about the amount of "API" access you give away, inevitably, someone WILL feel the need to be malicious. Pay particular attention to string termination/handling if the language you are using requires it. Do not build your game from plain-text ASCII content files. If your game has even one "text box," someone WILL be trying to feed HTML/LUA/etc. code into it.
Lastly, paths should use appropriate system variables whenever possible to avoid platform shenanigans and/or access violations (x86/x64, no savegames in ProgramFiles, etc.)

how to avoid replay attack without using time-stamp

I am developing a mobile application which sends some encrypted data to a Bluetooth device and this Bluetooth device sends the data to server. My question is that in this case how can I prevent replay attacks. Someone might use a fake Bluetooth device to get the signals and send them to the server.
The mobile application works in offline mode and has no connection to server. So using a synchronized nonce or counter doesn't help.
I can not also use time-stamp to narrow the attack window because mobile phone's time might not be correct (synchronized with a time server).
Communication between my mobile application and Bluetooth device is one-way and my mobile application can only send data to the device.
One way to do this would be to use a counter, but allow it to skip a large number of steps. For example if the last counter value you've seen from phone A is 123 and you get something with a counter value of 156 then you accept it, but anything outside the range of [124, 1000123] you discard (1000000 being completely arbitrary and dependent on your use case).
This would prevent a replay attack, but you do have to take care that the transmissions aren't malleable or it would be trivial to forge counter numbers. This could be accomplished by having a secret per device MAC key (which would only be possible if the server and phone communicate beforehand).
It's worth stating that it would be good for the transactions to be authenticated (only phone A has the capability to generate a message saying it's from phone A) or an attacker could move up the counter very quickly and do a denial of service on phone A. However, from the way you phrased the question it sounds like it's something you've already dealt with.

a UDP socket based rateless file transmission

I'm new to socket programming and I need to implement a UDP based rateless file transmission system to verify a scheme in my research. Here is what I need to do:
I want a server S to send a file to a group of peers A, B, C.., etc. The file is divided into a number of packets. At the beginning, peers will send a Request message to the server to initialize transmission. Whenever S receives a request from a client, it ratelessly transmit encoded packets(how to encode is done by my design, the encoding itself has the erasure-correction capability, that's why I can transmit ratelessly via UDP) to that client. The client keeps collecting packets and try to decode them. When it finally decodes all packets and re-construct the file successfully, it sends back a Stop message to the server and S will stop transmitting to this client.
Peers request the file asynchronously (they may request the file at different time). And the server will have to be able to concurrently serve multiple peers. The encoded packets for different clients are different (they are all encoded from the same set source packets, though).
Here is what I'm thinking about the implementation. I have not much experience with unix network programming though, so I'm wondering if you can help me assess it, and see if it is possible or efficient.
I'm gonna implement the server as a concurrent UDP server with two socket ports(similar to TFTP according to the UNP book). One is to receive controlling messages, as in my context it is for the Request and Stop messages. The server will maintain a flag (=1 initially) for each request. When it receives a Stop message from the client, the flag will be set to 0.
When the serve receives a request, it will fork() a new process that use the second socket and port to send encoded packets to the client. The server keeps sending packets to the client as long as the flag is 1. When it turns to 0, the sending ends.
The client program is easy to do. Just send a Request, recvfrom() the server, progressively decode the file and send a Stop message in the end.
Is this design workable? The main concerns I have are: (1), is that efficient by forking multiple processes? Or should I use threads? (2), If I have to use multiple processes, how can the flag bit be known by the child process? Thanks for your comments.
Using UDB for file transfer is not best idea. There is no way for server or client to know if any packet has been lost so you would only know that during reconstruction assuming you have some mechanism (like counter) to detect lost packes. It would then be hard to request just one of those packets that got lost. And in the end you would have a code that would do what TCP sockets do. So I suggest to start with TCP.
Typical design of a server involves a listener thread that spawns a worker thread whenever there is a new client request. That new thread would handle communication with that particular client and then end. You should keep a limit of clients (threads) that are served simultaneously. Do not spawn a new process for each client - that is inefficient and not needed as this will get you nothing that you can't achieve with threads.
Thread programming requires carefulness so do not cut corners. Otherwise you will have hard time finding and diagnosing problems.
File transfer with UDP wil be fun :(
Your struct/class for each message should contain a sequence number and a checksum. This should enable each client to detect, and ask for the retransmission of, any missing blocks at the end of the transfer.
Where UDP might be a huge winner is on a local LAN. You could UDP-broadcast the entire file to all clients at once and then, at the end, ask each client in turn which blocks it has missing and send just those. I wish Kaspersky etc. would use such a scheme for updating all my local boxes.
I have used such a broadcast scheme on a CANBUS network where there are dozens of microControllers that need new images downloaded. Software upgrades take minutes instead of hours.

Resources