Some may say this is crazy, I call it Wednesday.
This came across my desk yesterday and I worked it out today. It came as the payload following a java exploit from an old 2012 CVE (SecurityManager one I think). I’m calling it 0day because there were no listing for the exe in VirusTotal / Malwr both packed and unpacked.
This means the asshat who made this probably knew at some point, someone like me would be taking a look. There are actually quite a few modifications you can do to an exe that will mess up disassemblers but that windows will ignore.
Inspecting the exe with CFF Explorer, we see an error with one of the NT headers, specifically within ‘Data Directories’ at the Delay Import Directory RVA field. CFF is nice enough to highlight for us that the value 0x00000040 is wrong. Zeroing this out seems to fix it.
Saving the exe and re-opening in IDA, we no longer get the error and the thing open’s without a hitch.
A quick glance over the exe in IDA shows us its an MFC application. How do I know this? It says so right in the imports section under Library:
The application is of course, packed. Memory packed. No section header modification, just your typical memory pack.
What this means is that, static analysis is out of the question. We need to do dynamic analysis in order to probe further. Immunity away!
Before we get into immunity and the VM, there are a couple of interesting things inside the exe that aren’t immediately apparent in IDA, but show in CFF explorer. For starters, there are a couple files that stick out like a sore thumb hidden in the resources directory.
Why this is in the resources section and not packed with the other code is a mystery, but keep the resources section in mind for later. Now lets get back to unpacking this thing.
I see a few memory ranges marked Read Write Execute (RWE). One at address 00910000, one at 00930000, one at 00940000, and lastly, one at 00970000. Inspecting a few shows us only 3 of the 4 contain programs. Still 3 programs hiding in 1? Cool beans.
Now we need to dump our programs from memory into a file for further analysis. Bringing up OllyDumpEx and feeding it our 0090 ranges, we see the programs at 0091000 and 00970000 match the original program based on their size, section headers and characteristics. The memory range at 00950000 however is different from the others. We see different section headers, different sizes. This must be our golden egg.
What’s this? HTTP request info. Looks like this thing sends home to Mamma using POST requests.
But what about the C&C server you may ask? It doesn’t appear to be in plain text in our program. Remember what I said earlier about the resources section? Let’s take a peek in the resources section of our golden_egg.exe.
Bingo. http://126.96.36.199. How nice of the coder to leave this in plain text for us. Security through obscurity strikes again.
Now I’m sure you’re wondering what happens when this main application runs. Let’s see what happens:
Upon launch, it automatically closed my process explorer app and any attempts to load task manager are prompted with a quick message box stating “task manager has been disabled by the administrator” before closing very quickly. I wish I could have showed you in the screenshot, but I am not that quick. Improvising with Immunity, we see our original program ‘golden_egg.exe’ is no longer running. Instead some other program named ‘zpNvNKSi.exe’ instead is running, and from the temp folder. Comparing the hashes, they appear to be the same:
Like my hasher? Download it here.
Free advertising aside, its clear what this program does – it disables task manager, kills off “undesirable” applications and runs from the temp folder. Checking msconfig shows it also adds 2 files to start up:
I checked both and they are byte for byte copies of the original program.
Attaching to the program with Immunity and inspecting the program’s memory and thread count (the ‘t’ button) reveals the program is multithreaded. I count 12 threads.
I’m assuming each one of these threads watches one another in case one is killed, however with the main process suspended, we can now open the thing up with Process Explorer and take a peek at the memory. Inspecting, we see a few things that weren’t in our IDA strings:
Going out on a limb, I think the program checks for these programs and force kills them if they are run. This would explain why process explorer was killed when the program running. Kind of makes it difficult to run any of these tools when the malware kills them immediately. I see regedit, LordPE, wireshark, regmon, filemon, procmon, tcpview, taskmgr, and even Windows Defender. Harsh. I do not however see Process Explorer’s bastard cousin Process Hacker.
Going back to memory, this means the program was obviously either obfuscating these strings, or is packed a second time. Either way, lets find out.
Doing a unicode search for one of the strings we saw in memory from Process Explorer shows the string ‘taskmgr’ is located in the .data section. Did IDA lie to me about the strings? No, not quite. Looking again and doing a slow binary search does show the other strings. I guess IDA doesn’t show unicode strings when it does its search by default. You can change this in IDA by using the shortcut ‘alt+A’ and choosing option 6 for unicode.
Given the program will kill our attempts to run with WireShark open, we need to locate the functionality responsible for killing the program and patch over it. How do we do this? Locate the TerminateProcess() api call.
It appears to be some sort of looping logic that looks up process names with the ‘CreateToolhelp32Snapshot’ api and if they meet a certain condition, kills them. That list of names we saw earlier likely corresponds to this.
So what can we do? We could change the logic of the program so that way it doesn’t call TerminateProcess and instead does nothing. Checking the sub routine’s Xref’s (eXternal REFerenceS), we see the function is called from sub routine 00401D2A. There is a ‘jnz’ instruction responsible for the determining whether or not to call into the sub routine responsible for looking up processes and killing them. If we can patch the program to never call into this routine, we can skip over the sub routine and run any black listed program we want.
let’s get to it. I prefer to do my patching with Immunity since its easier and I am more familiar. We start by bringing up the sub routine in our running exe. The instruction that has our conditional jump is at ‘0x00401d4e’. By nop’ing out the area, we are forcing the instruction flow to ‘ret’ instead of jumping to 00401d2c which contains our blacklist process killer.
Unpausing our program and letting it run, we test trying to invoke one of the blacklisted programs. It seems to be working because ‘regedit’ worked and ‘process explorer’ wasn’t killed.
Now we can perform a detailed network analysis with wireshark, file analysis and registry analysis with procmon, and mess around with Process Explorer with the program running live.
We can see with Process Explorer a syn packet being sent to our C&C server (the one we pulled from the resources section) via port 80.
Wireshark is a bit more revealing. We see our syn packets to our HTTP based C&C, however we also see a bunch of DNS requests to some unknown domain names. What’s up with that?
The server will continue to call home, but I don’t want it to. I could modify the resources section in our ‘golden_egg.exe’ file and make it point to my own HTTP server and inspect its functionality, but that’s a lot of work. For now, we have what we need. We have the C&C, we have the unpacked program, we have its HTTP signature, and we have its behavior. Case closed. Another 0day Wednesday come and gone.
If you wish to download the malware and see it for yourself, you may download it here. The password is ‘infected’.
Hope you all learned something. Happy cracking!