In this blog post, I'm going to describe how I made my CS:GO cheat (for educational reasons only). In the video (sorry for potato quality) you can see me using bhop and no recoil cheats.
Goal of this project was to put my reverse-engineering "skills" to use, by writing a CS:GO cheat. Anything will do. There are may different cheat types:
- Aimbot - the most obvious one. I wrote one, but didn't publish it online (since I'm not proud of it). My implementation wasn't subtle at all. Instant headshots on every player that enters the area of my monitor.
- Wallhack - I almost instantly crossed this one out, since I had no idea how to approach problem of rendering on someone else's thread.
- RCS - name comes from Recoil Control System, usually a cheat that removes recoil from your gun.
- Bhop - Bunny Hop is a type of script that allows faster movement by abousing jumping mechanic in Source Engine. There is a common misconception, that bhoping can be achieved by using scripts and macros (for example on mouse). Proper reliable Bhop cheat requires memory manipulation.
- Radar hack - excluded for same reasons as wallhack.
External or Internal
There are different ways to write a cheat:
- External - executable file, which reads from/writes to game's memory.
- Internal - shared library, which you need to inject into game's process using an injector program.
- Driver - advanced technique that I haven't explored yet, but it gives you ring0 privileges. Most anti-cheats don't allow unsigned drivers, so you'll have to get a signing certificate, that you have to buy.
In this post, we'll only talk about #1 and #2. Generally speaking, external cheats are easier to write (since they ususally use simple OS api to interact with game's memory), but don't offer as much flexibility as internal, which can e.g. hook functions.
The easier way (and also, the way I started). I used
CreateToolhelp32Snapshot to find correct process and modules (example) and a simple
PROCESS_ALL_ACCESS to obtain process to handle. Some anticheats detect this as cheat, but most don't, since that would flag most antivirus' software as cheats as well. Let's not focuss on detection for now, since that's entierly different topic of it's own.
ReadProcessMemory](https://docs.microsoft.com/en-us/windows/desktop/api/memoryapi/nf-memoryapi-readprocessmemory) and [WriteProcessMemory functions to interact with game's memory.
This is the hard way, but it also allows to have more fun. First, you need to reverse engineer some part of code, you want to edit. After that, you can hook the function, by editing:
(both names are used).This way, whenever game tries to call specific function it will actually call your function instead of the original one. This is extremly powerfull. example implementation.
As internal cheat is in library format, it needs to be injected into target executable. Some ways to do that include:
- Standard - This is the injection technique used in nearly every injector out there. It uses
LoadLibrary. It is the simpliest and injection technique.
- Process Hollowing - Idea is simple. Create sacrificial process and suspend it. Write your code into the remote process. Resume remote thread. Profit.
- Manual Map - One of best, stealthiest ways to inject. You can find plenty of reference implementations online like this one.
There are plenty more ways detailed here. The most popular (and probably the best) public injector is Extreme Injector.
TODO: offsets vs pattern matching
If you want to dive into cheating (for educational purposes), feel free to use:
- Blackbone - windows memory hacking library. It should provide you with plenty of boilerplate and ideas.
- Ghidra - free IDA Pro alternative (which is SUPER expensive). It even has a decompiler from many languages (C++, Go, etc.)!
- UnknownCheats - ucforums itself.