In June 2018, the famous MalwareTech released a series of introductory malware reverse engineering challenges.

In case you’re unfamiliar with MalwareTech (aka Marcus Hutchins) (aka @MalwareTechBlog), you can find plenty of articles about him and his exploits (pardon the pun).

In this post I’ll be providing a walkthrough of each of the three “Hide and Seek” or “Strings” challenges. All of them are rated “super easy” or “very easy.” The goal is to solve them using a disassembler like IDA and NOT an debugger like GDB which would allow a much easier path to finding the flags in memory and not provide an actual reverse engineering challenge.

The core concept of these challenges is that each program computes the MD5 hash of the flag, and then displays it via text box to the user. Your goal is to deconstruct the flow of each program and find the flag before it is hashed.

I would consider the prerequisites to these challenges to have a basic familiarity with x86 assembly, IDA, and hexadecimal. I spent anywhere from 20 minutes to a few hours solving each of these. They’re very CTF style, down to the use of the ubiquitous FLAG{} format. If you’re looking for something to throw up on a projector and use to teach newbies on your CTF team about IDA and RE these would work great.

Before starting, all you will need is IDA (or a competing disassembler you’re more comfortable with) running inside a VM. While not strictly necessary in this case, using a VM to examine possibly malicious files is highly reccomended.

strings1 — [super easy]

This isn’t an IDA tutorial, so I’ll jump right in to the first challenge.

The famous light blue gradient

Since we’re looking for a piece of text, my first instinct is to use the useful Strings window. It can opened in the menu under View -> Open subviews -> Strings .

Who knew Marcus was such a historian?

Inside we find an extremely large number of possible flags, any of which could be the answer. Let’s take a look at the assembly code itself.

The first several lines are standard, and among other things, setup a new stack frame.

But what’s this in the next line?

mov eax, off_432294

This command copies the contents of memory address off_432294 into the accumulator register EAX . By mousing over the memory address, we can see what’s saved there.

A-ha! The flag! Go ahead and enter it on the appropriate MTB page and get that coveted “Correct Flag!” message. This challenge lives up to its “super easy” tag.

The rest of the code is concerned with using a library hashing function and then displaying the resulting MD5 hash. You can ignore it for purposes of the challenge but it’s worth examining to learn more about assembly.

strings2 — [very easy]

Time to step it up from “super easy” to “very easy!”

What a mess

For our second challenge, we’re confronted with a series of variable declarations and then assignments. The trailing “h” designates that these are hex numbers, so let’s open up an online hex to ASCII calculator and see what we’re dealing with.

Converting the first 5 characters shows we’re on the right track, and finishing the rest of the translation reveals that we’ve found the entire flag.

The rest of the program creates a pointer to the entire flag and then hashes and displays it as before. Of particular interest are the lines:

lea eax, [ebp+var_28]

push eax

These do the aforementioned creating, and then pushing, the pointer to the stack.

strings3 — [very easy]

Though still “very easy,” the final strings challenge gave me the most trouble. There’s a few moving pieces here, and I ended up having to use an additional tool. I also learned a lot about Windows resource files.

A portion of strings3.exe_

Although this assembly file is shorter than the previous one, there’s a lot more going on here. At the top we see some pointer declarations.

Below that, the standard setting up of a new stack frame.

One piece of code a little further on caught my eye:

There are some instructions here that standout from the rest of the code, and only reference each other and themselves. We can also see that later on eax gets pushed onto the stack.

Let’s examine what this code does. The first line mov eax, 1 simply moves the number 1 into the eax register. The shl instruction shifts left eax by 8. Using an online calculator leaves us with the hexadecimal result of 100.

Next, the edx register is xor 'd by itself, which is an efficient way to zero out a register. Next, it’s inc remented by 1, and then also shl 'd but by 4 in this case leaving us with 16 in hex.

Finally, the registers are bitwise or 'd against each other, and the resulting hex 0110 (dec 272) is stored in eax .

OK, all very interesting, but what to do with this information?

There are several other clues. One of these is the pointer uID . A second is the reference to “.rcrc.” Another is the call to LoadStringA . Investing this function further, I came across the relevant Windows documentation. It takes several parameters, including:

It turns out that uID isn’t an offset, but an identifier that will need to be passed as a parameter to this function in order to find a String — presumably our flag.

There aren’t any flags visible in IDA, not even ones intended to obfuscate. So where could the flag be hiding? Even if it’s encrypted, it needs to be stored somewhere.

This is the part I was stuck on for the longest time. It turns out that by default, IDA doesn’t load content designated as resources unless you tell it to when opening the file for the first time.

After loading the file again, nothing looks different in the Function view, and there aren’t any new Strings that look like flags. However, if we open the Hex view:

About as intelligible as any other EULA

Once again, we’re presented with a number of false flags.

While investigating this further, I came across the incredibly useful Resource Hacker tool. Its Windows specific, but if you’re doing your RE in a Linux VM like me, you can still use it with Wine.

Running Reshack on the file provides the resources for the executable, which in our case is a String Table filled with the flags we saw in the hex.

We have the String identifier from before, which we know is 272 in decimal. Scrolling through the tool until we get to entry 272 reveals a flag which contains a legible sentence — plug it back into MTB’s site and we’re done!

Once again, the rest of the code here is concerned with displaying a hash of the flag.

Fin!

I look forward to finishing the rest of these challenges and to Marcus’ promised walkthroughs! The shellcode ones look particularly interesting.