Initial analysis

When we run the final challenge, we see a dialog where we have to enter 30 characters. We can also see that the icon is different and that it’s the default Delphi 7 executable icon. If we enter any text and press enter we see that the label changes to “Wrong”. That means that we have to enter the correct flag and press enter to verify it.

If we open that sample in a PE viewer, we see that it’s using an unknown EXE crypter to hide its code (actually that crypter is Morphine 2.7 which is also written in Delphi). We can see that by looking at the import table there are just LoadLibraryA, GetProcAddress, and the PE sections.

We can solve this challenge pretty fast if we know what we have to look for. We want to identify the routine that is checking for a valid flag. We can start our analysis at the function which sets the status to “Wrong”, but before we can do that we have to dump the executable so we can load it in IDA Pro.

Dump the executable

We can use Scylla x86 to dump the process, so let’s execute the challenge and run Scylla. Select “DelphiChallenge.exe”, press “IAT Autosearch”, after that press “Get Imports” and Scylla should be able to find the imports.  You can already see the correct imports in next screenshot:

We can save the PE dump using “Dump” and “Fix dump” functions in Scylla. We can’t run that dumped file but it’s enough for a static analysis in IDA Pro. We can dump the file correctly but it takes a few extra steps (see extra part).

Static analysis

Now open the file in IDA Pro and go directly to “strings window” by using Shift+F12. Search in strings window for “Wrong” and you should see these 5 entries:

If we follow the first string using cross-references, we can see that it’s referenced in sub_4C17BC and there is one more interesting string:

If byte_4C4C5C is nonzero then it will show “Correct!! You are so g00d”. Following byte_4C4C5C we can see that its set to 1 at offset 0x004C127F and that function starts at offset 0x004C0E1C. This function looks like our testing flag routine.

We have identified pretty quickly the routine which is checking for the correct flag, now we have to analyze that function. It’s pretty similar to Windows track challenge 8. We know that the flag must start with “PAN{“ and we can see that the function is checking for that at the beginning:

We have to follow the function and revert the calculations again like in Windows challenge 8. The final decoder script would look like this:

key = "PAN{"
key += chr(0xcf ^ 0xab)
key += chr(0x1e ^ 0x2d)
key += chr(0x3e ^ 0x52)
key += chr(0x52 ^ 0x22)
key += chr(0x08 ^ 0x60)
key += chr(0x68 + 0x01)
key += chr(0xe5 ^ 0xba)
key += chr(0xd7 ^ 0xbe)
key += chr(0xe6 / 2)
key += chr((0x2f << 1) + 1)
key += chr(0x194 >> 2)
key += chr((0x19 << 1) + 2)
key += chr((0x1c0 ^ 0x0c) >> 2)
key += chr(((0x38 ^0x04) << 1) + 1)
key += chr(((0x28 + 0x07) << 1) + 1)
key += chr(((0x8c / 0x0A) << 3) + 4)
key += chr(0x60 / 2)
key += chr(0x17c >> 2)
key += chr((0x59 ^ 0x60) << 1)
key += chr((0x42 ^ 0x88) / 2)
key += chr((0x0c0 ^ 0x2c) / 2)
key += chr((0x16 << 1) + 7)
key += chr((0x36 ^ 0x29a) / 6)
key += chr(((0x130f0 / 8) ^ 0x2486) / 8)
key += chr(((0x2950 ^0x25a0) / 0x30))
key += chr(0x7d)
print key

python decoder.py
PAN{d3lphi_is_e4sy_t0_rev3rSE}

We can now test and verify if that flag is correct.

Extra: Manual unpacking

If we want do dump the process correctly we can use OllyDbg and OllyDump. To identify the original entry point (OEP) we can use the “set hardware breakpoint at current ESP” technique. For that we have to run the first instruction, go to the dump window and jump to the ESP. Then we can set a “Hardware, on access” breakpoint at current address.

If we press F9 a few times we will reach the original entry point. Now we have to do some calculations and dump it to a new file.

For calculating the real OEP we need to know at which address the executable has been loaded.

Now we just have to subtract these offsets and we get the correct offsets for OllyDump.

Calculations:
OEP:               0x00941b60
Address:        0x008F0000
Size:                0x001F0000
ImageBase:   0x008F0000

New EP: 	(0x00941b60 - 0x008F0000) = 0x51B60

Now let’s fill that data into OllyDump and dump the file as “dumped.exe”:

But something is still wrong if we try to execute the unpacked sample:

It’s probably the import table that causes problems, but we can use Scylla to fix that for us. For that we have to run DelphiChallenge.exe again (new process) and search for the import table. We also have to enter the correct entry point + image base:

EP + Imagebase: 0x51B60 + 0x8F0000 = 0x941B60

Now we can use “Fix dump” and fix the dumped.exe executable:

Scylla has created a new import table and now we can run the unpacked executable. Yey.