Getting Started in Reverse Engineering Software with Crackmes and Command Line Tools Part 1

Intro

Learning how to reverse engineer software has enormous benefits. Whether you want to develop ROM hacks or unlock programming secrets when no source code is available, being able to effectively study and infer functionality from compiled binaries is an extremely useful skill. In cybersecurity, reverse engineering can be used to understand and uncover malware. Software developers can use it to become better programmers by learning reverse engineering to bridge the gap between their high level coding experience and what actually gets executed on the machine. I can’t speak highly enough about its usefulness, and it’s no wonder government entities like the NSA in the United States have developed their own reverse engineering tools.

You may have heard of Ida and Ghidra. Both are powerful reverse engineering software packages with helpful user interfaces and advanced features. These tools are great, and you are likely to bust them out for advanced usage, but they aren't fundamentally required for reverse engineering. You can get a lot done with a handful of command line tools, especially when working with smaller programs. Regardless of the tools you use, you will need to know how to disassemble binaries, find key strings, and use debuggers.

In this tutorial, we will be using command line tools to reverse engineers simple “crackmes”. The website crackmes.one is one of several dedicated websites where users upload executables for others to attempt to crack in order to help them learn how to reverse engineer software.



Many of the simple crackmes involve trying to determine a hidden password or key phrase that the program asks you for when you run it. Upon successfully entering the correct password or phrase, you will typically get a success message indicating that you cracked the code. These are incredibly useful when learning reverse engineering and are also just a lot of fun. We will be cracking Unix executables typically written in C/C++ or x86-64 assembly that run on x86-64 Intel machines. Naturally, you’ll need a computer with x86-64 (AMD64) architecture. We will be using a Linux Virtual Machine to contain our reverse engineering environment so it won't matter whether you are running Windows, MacOS or Linux on your host machine. We'll be creating our Virtual Machine (VM) with VirtualBox.

Prior Experience

This tutorial is intended for relative new comers when it comes to reverse engineering. Hopefully you have some programming experience already in at least one language, but the more the better. It will be especially helpful if you know some basic C/C++ or a from of assembly language. Assembly language in particular is extremely useful for reverse engineering. You do not need to be a master of writing assembly code, but you should know what it is, and some basic commands. If you have never worked with assembly code, I recommend you check out our x86-64 MacOS Hello World assembly tutorial or watch Low Level Learning's excellent video for a beginner friendly 10-minute intro to x86-64 assembly on Linux. I would make sure you can first write, assemble and run a “Hello, World!” program in assembly for x86-64 before you continue with this tutorial.

Security Concerns

The fact that we are downloading executables from the internet and running them as part of our reverse engineering efforts should make you at least a little paranoid. While the programs submitted to crackmes.one are reviewed by the owners of the site, you can never be too careful. And of course, outside of crackmes.one you may download software you want to reverse engineer without putting yourself at major risk. We’ll take the following precautions to get in the habit of good practice while reverse engineering:

  1. We will be doing the reverse engineering on a Virtual Machine, not directly on our host computer
  2. We will be connected to the internet using a VPN or turn off our internet connection altogether while we run the software we’re trying to crack


This gives us at least some reasonable protection. By using a VM, we can usually avoid infecting our host computer if we encounter any real malware. Keep in mind however that if you have shared folders or are allowing communication between the host machine and the VM, it is possible for certain malware to attack your host machine. This is very unlikely, but technically possible. If you do have any shared folders, do not run the executables you are trying to crack from that shared folder. Why a VPN? Certain malware may try to download additional malware from the internet or connect to questionable sites, in which case you don’t want your IP address to be exposed to them. If you are worried about this and don’t have a VPN set up, you can always just disconnect from the internet altogether whenever you run the executable.

If you are really paranoid, you can even do all this on a host computer that is dedicated solely to reverse engineering that you don't use at all for personal data or work. You could even put it on a separate network than your personal computer. This may be overkill for simple crackmes, but you should develop a healthy skepticism about running unknown software on your computer, even if you think it’s unlikely to be malicious.

Getting Setup

First you’ll want to make sure you can create a new Virtual Machine. We will be using an Ubuntu 22.04 VM. Download and install VirtualBox if you don’t already have it. Also make sure you have an Ubuntu 22.04 ISO to use with VirtualBox. Then,

  1. Open VirtualBox and click 'New'
  2. Then select 'Linux' under Type and 'Ubuntu (64-bit)' under Version and give it an appropriate name and press continue.
  3. Set up VM settings in the next few steps in VirtualBox. I used primarily the default settings other than setting the RAM to 4GB. You’ll click a few option pages. Specifically I set mine to 4096 MB (4GB) RAM, Checked 'Create a virtual hard disk now', Checked 'VDI (VirtualBox Disk Image)', Checked 'Dynamically allocated', and set 10 GB storage before clicking the 'Create' button on the last page.
  4. Once your Ubuntu 64-bit VM is set up and you’ve run through the Ubuntu installer (I did a minimal install but included 3rd party software), open Firefox or another browser from within your Ubuntu VM and go to https://crackmes.one/ . You should also open this tutorial from within your VM so that you can click the links in the next step and download the programs directly to your Ubuntu Virtual Machine.
  5. There are two beginner crackmes we will be doing. Notice when you go to these crackme pages you can see the language (C/C++ in our case), platform (Unix/linux etc.) and architecture (x86-64):


  6. The first crackme is by nutcake (Executable name is “crack” when downloaded) [Download Here]:



    The second crackme is by D4RKFL0W (Executable name “crack1_by_D4RK_FL0W” when downloaded) [Download Here]:

  7. Create a new directory named 'crackmes' somewhere on your Ubuntu VM
  8. Extract both crackmes to the crackmes directory you just created. You’ll be prompted with a password to open the zip files. All crackmes have the password 'crackmes.one'. Type this in when prompted for both zip files until you have both executables in your new directory. You should now have two programs in this directory, one named “crack” and one named “crack1_by_D4RK_FL0W”.
  9. Congrats, you are all set up now to start reverse engineering these crackmes. Fortunately Ubuntu, and most Linux distributions come with most of the tools we need to get started.

Command Line tools:

Here is a brief overview of the types of analysis and tools we’ll be using and that you can use going forward for reverse engineering on the command line.

Static Analysis:

Static analysis involves studying the compiled binary when it is not running. You will simply look at the bytes from the compiled binary and use various tools to extract information. The tools we’ll be using for this are:

  1. strings: this command will show you strings longer than 4 characters saved in the binary. In some cases, useful information can be stored in ascii strings that are easily accessible with this tool
  2. objdump: you can use this tool to disassemble the binary (extract assembly code)


Dynamic Analysis:

Dynamic analysis involves studying running programs. These tools will give us information on the fly while the program executes. They sometimes give us a clearer indication of what the program is doing that would be hard to determine from just using static analysis.

  1. ltrace: This tool intercepts and records dynamic library calls which are called by the executed process as well as other potentially useful information received at runtime.
  2. strace: Very similar to ltrace, but shows slightly different information. If one is hard to decipher, it’s worth trying the other.


Tools with Static and Dynamic Analysis Options:

  1. gdb: a suite of tools for debugging programs that is also useful for reverse engineering. We’ll be using it’s dissassembler as it’s nice and readable, although we already get most of this functionality out of objdump

Reverse Engineering:

Let’s start with the the first program by nutcake with the executable name “crack”. Run the program to get a feel for it:

$ ./crack


As you will see it will ask you for the password “Input the password: ”. Try a test password “test”:



Let’s start with our first line of defense: strings:

$ strings crack




As you can see there is a whole host of ascii strings pulled from this executable. Many of the strings starting with “_” are not going to be particularly useful to us and are placed there by the linker in the build process. There is one that does look interesting to me though: 'easycracH'.

Let’s try that out:

$ ./crack


And type “easycracH”:



No dice, we’ll have to try something else. After strings, I like to use a disassembler especially for these smaller programs to see if I can gleam any useful information. Let try with objdump:

$ objdump -d -Mintel crack


The ‘-d’ means we want to disassemble the “crack” executable and -Mintel sets the syntax to Intel syntax which is a little nicer to work with than the default.

Scroll in the terminal to where it says “Disassembly of section .text:”:



Reading through this disassembled code it is hard to see clearly what is happening, especially for someone new to this. We’ll come back to it we can’t find another way, but let’s now try some dynamic analysis to see if we can see anything obvious.

$ ltrace ./crack


And we see:



Nothing yet, just a printf(“\nInput the password: “). The “= 21” is indicating that “\nInput the password: “ is 21 characters long. Let’s enter “test” as the password again and see if we get any new information:



Aha! As you can see a line popped up:



If you know a little C programming you know strcmp means “string compare” or test if these two strings are equal. Evidently the program is testing whether our input password “test” is equal to “easycrack”. I’ll bet that’s the real password:

$ ./crack




We did it! This really was an easy crack, as indicated by the creator of this crackme, but a nice one to start with for sure.

In the next part of this tutorial we’ll tackle the second and slightly more difficult crackme by D4RKFL0W. Go to Part 2 ›