The turnout failed: we bring AgentTesla to clean water. Part 3

The turnout failed: we bring AgentTesla to clean water. Part 3

With this article, we complete a cycle of publications devoted to the analysis of malicious software. IN the first part we carried out a detailed analysis of an infected file that a European company received by mail and found the AgentTesla spyware there. In the second part described the results of a phased analysis of the main AgentTesla module.

Today, Ilya Pomerantsev, CERT Group-IB malware analysis specialist, will talk about the first stage of malware analysis β€” semi-automatic unpacking of AgentTesla samples using three mini-cases from the practice of CERT Group-IB specialists as an example.

Usually, the first stage in the analysis of malware is the removal of protection in the form of a packer, cryptor, protector, or loader. In most cases, this problem is solved by running malware and performing a dump, however, there are situations when this method is not suitable. For example, if the malware is an encryptor, if it protects its memory regions from a dump, if the code contains mechanisms for detecting a virtual machine, or if the malware performs a reboot immediately after starting. In such cases, the so-called "semi-automatic" unpacking is used, that is, the researcher has full control over the process and can intervene at any time. Let's consider this procedure using three samples of the AgentTesla family as an example. This is a relatively harmless malware if you disable its access to the network.

Sample #1

The source file is an MS Word document that exploits the CVE-2017-11882 vulnerability.

The turnout failed: we bring AgentTesla to clean water. Part 3
As a result, the payload is loaded and launched.

Analysis of the process tree and behavioral markers shows the injection into the process RegAsm.exe.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
There are behavioral markers specific to AgentTesla.

The turnout failed: we bring AgentTesla to clean water. Part 3
Downloaded sample is executable . NET- Protected file .NET Reactor.

The turnout failed: we bring AgentTesla to clean water. Part 3
Let's open it in the utility dnSpy x86 and go to the entry point.

The turnout failed: we bring AgentTesla to clean water. Part 3
Going to function DateTimeOffset, we will find the initialization code of the new . NET-module. Let's put breakpoints on the line of interest to us and run the file.

The turnout failed: we bring AgentTesla to clean water. Part 3
In one of the returned buffers, you can see the MZ signature (0x4D 0x5A). We save it.

The turnout failed: we bring AgentTesla to clean water. Part 3
The dumped executable file is a dynamic library that is a loader, i.e. retrieves the payload from the resource section and executes it.

The turnout failed: we bring AgentTesla to clean water. Part 3
At the same time, the necessary resources themselves are not in the dump. They are in the parent sample.

Utility dnSpy has two extremely useful features that will help us create a "Frankenstein" from two related files quite quickly.

  1. The first allows you to "paste" a dynamic library into the parent sample.

    The turnout failed: we bring AgentTesla to clean water. Part 3

  2. The second is to rewrite the function code at the entry point to call the desired method of the inserted dynamic library.

    The turnout failed: we bring AgentTesla to clean water. Part 3

We save our "Frankenstein", put breakpoints on the line that returns a buffer with decrypted resources and produce a dump similar to the previous step.

The second dump is written in VB.NET an executable file that is protected by a protector familiar to us ConfuserEx.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
After removing the protector, we use the YARA rules written earlier and make sure that the unpacked malware is indeed AgentTesla.

The turnout failed: we bring AgentTesla to clean water. Part 3

Sample #2

The source file is an MS Excel document. An embedded macro leads to the execution of malicious code.

The turnout failed: we bring AgentTesla to clean water. Part 3
As a result, the PowerShell script is launched.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
The script decrypts the C# code and passes control to it. The code itself is a loader, which is also visible from the sandbox report.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
The payload is an executable . NET-file.

The turnout failed: we bring AgentTesla to clean water. Part 3
Opening the file in dnSpy x86, you can see that it is obfuscated. Removing obfuscation with a utility de4dot and return to the analysis.

When examining the code, you can find the following function:

The turnout failed: we bring AgentTesla to clean water. Part 3
Encoded strings are striking EntryPoint ΠΈ invoke. We put breakpoints to the first line, run and save the value of the buffer byte_0.

The dump is again an application on . NET and protected ConfuserEx.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
Remove obfuscation with de4dot and upload to dnSpy. From the description of the file, we understand that we are faced with CyaX-Sharp loader.

The turnout failed: we bring AgentTesla to clean water. Part 3
This loader has extensive functionality to counter analysis.

The turnout failed: we bring AgentTesla to clean water. Part 3
This functionality includes bypassing built-in Windows security systems, disabling Windows Defender, as well as sandbox and virtual machine detection mechanisms. It is possible to load the payload from the network or store it in the resource section. The launch is performed through an injection into its own process, into a duplicate of its own process, or into processes MSBuild.exe, vbc.exe ΠΈ RegSvcs.exe depending on the parameter chosen by the attacker.

However, for us they are less important than AntiDump- a feature that adds ConfuserEx. Its source code can be found at GitHub.

To disable protection, use the option dnSpywhich allows you to edit IL-code.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
Save and put breakpoints to the call string of the payload decryption function. It is in the constructor of the main class.

The turnout failed: we bring AgentTesla to clean water. Part 3
Launch and dump the payload. Using the previously written YARA rules, we make sure that we have AgentTesla in front of us.

The turnout failed: we bring AgentTesla to clean water. Part 3

Sample #3

The source file is the executable VB Native PE32-file.

The turnout failed: we bring AgentTesla to clean water. Part 3
Entropy analysis shows the presence of a large piece of encrypted data.

The turnout failed: we bring AgentTesla to clean water. Part 3
When analyzing the application form in VB Decompiler you can see a strange pixelated background.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
entropy plot bmp-image is identical to the original file's entropy graph, and the size is 85% of the file size.

The turnout failed: we bring AgentTesla to clean water. Part 3
The general appearance of the image indicates the use of steganography.

Let's pay attention to the appearance of the process tree, as well as the presence of the injection marker.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
This indicates that unpacking is in progress. For loaders in Visual Basic (they are VBKrypt or VBInjector) is characterized by the use shellcode to initialize the payload, as well as to execute the injection itself.

Analysis in VB Decompiler showed an event Load at the form FegatassocAirballoon2.

The turnout failed: we bring AgentTesla to clean water. Part 3
Let's go to IDApro to the specified address and study the function. The code is heavily obfuscated. The part we are interested in is shown below.

The turnout failed: we bring AgentTesla to clean water. Part 3
Here, the address space of the process is scanned for a signature. Such an approach is highly questionable.

First, the address to start scanning 0x400100. This value is static and is not adjusted when the base is shifted. In ideal greenhouse conditions, it will indicate the end PE-header of the executable file. However, the base is not static, its value can change, and the search for the real address of the desired signature, although it will not cause a variable overflow, can take a very long time.

Second, the value of the signature iWGK. I think it's obvious that 4 bytes is too small to guarantee uniqueness. And if you take into account the first point, the probability of making a mistake is quite high.

In fact, the desired fragment is attached to the end of the previously found bmp-pictures by offset 0xA1D0D.

The turnout failed: we bring AgentTesla to clean water. Part 3
Performance Shellcode is carried out in two stages. The first one decrypts the main body. In this case, the key is determined by enumeration.

The turnout failed: we bring AgentTesla to clean water. Part 3
Let's dump the decrypted Shellcode and look at the lines.

First, we now know the function to create a child process: CreateProcessInternalW.

The turnout failed: we bring AgentTesla to clean water. Part 3
Secondly, we became aware of the mechanism of fixing in the system.

The turnout failed: we bring AgentTesla to clean water. Part 3
Let's go back to the original process. Let's put breakpoints on CreateProcessInternalW and continue execution. Next, we observe the connection NtGetContextThread/NtSetContextThread, which changes the execution start address to the address ShellCode.

The turnout failed: we bring AgentTesla to clean water. Part 3
We connect to the created process with a debugger, activate the event Suspend on library load/unload, we resume the process and wait for loading . NET-libraries.

Next, using ProcessHacker dumping regions containing unpacked . NET-Appendix.

We stop all processes and remove the copy of the malware that has entrenched in the system.

The turnout failed: we bring AgentTesla to clean water. Part 3
The turnout failed: we bring AgentTesla to clean water. Part 3
The dumped file is protected by a protector .NET Reactor, which is easily removed using the utility de4dot.

The turnout failed: we bring AgentTesla to clean water. Part 3
Using the YARA rules written earlier, we make sure that we have AgentTesla in front of us.

To sum up

So, we have demonstrated in detail the process of semi-automatic unpacking of samples on the example of three mini-cases, and also conducted a malware analysis based on a full-fledged case, finding out that the sample under study is AgentTesla, installing its functionality and a complete list of indicators of compromise.

The analysis of a malicious object that we conducted requires a lot of time and effort, and this work should be performed by a special employee in the company, but not all companies are ready to have an analyst on staff.

One of the services provided by the Group-IB Computer Forensics and Malicious Code Analysis Laboratory is response to cyber incidents. And so that customers do not waste time coordinating documents and discussing in the midst of a cyber attack, Group-IB launched Incident Response Retainer, a pre-subscription incident response service that also includes a malware analysis step. More information about this can be found here.

If you want to once again learn how AgentTesla samples are unpacked and see how a CERT Group-IB specialist does it, you can download a recording of a webinar on this topic here.

Source: habr.com

Add a comment