Skip to content

Latest commit

 

History

History
218 lines (131 loc) · 12.3 KB

0x4 - Graftor.md

File metadata and controls

218 lines (131 loc) · 12.3 KB

⚠️ WORK IN PROGRESS ⚠️

Background - Graftor

"... past versions of Graftor were capable of browser hijacking, injecting advertising banners, installing other unwanted applications, changing a user’s homepage and search provider, and launching other adware. They also had anti-detection capabilities such as antivirus and sandbox detection".

- Historically, Graftor was delivered via phishing email with an attachment that exploits `CVE-2017-11882`, which is a remote code execution flaw found in Microsoft Office's Equation Editor. 
"CVE-2017-11882 is a RCE vulnerability in the equation editor from the Microsoft Office and it is associated with a failure to handle objects in RAM. To exploit the vulnerability, an attacker must create a malicious file and somehow convince the victim to open it. Most often, such file is sent by e-mail or is hosted on a compromised site.

Successful exploitation of the CVE-2017-11882 vulnerability allows an attacker to execute arbitrary code with the privileges of the user who opened the malicious file. Thus, if the victim has administrator rights, the attacker will be able to take full control of his system — install programs; view, modify or destroy data; and even create new accounts."
  • Next, I researched CVE-2017-11882 POCs and found one from Palo Alto's Unit 42. The RTF file they mention is actually hosted on Github by a user named embedi.

Pasted image 20240621125506

  • Above is a screenshot of what the POC looks like. The POC itself is an actual .rtf document. .rtf documents are typically structured as follows:

-> Header

  • \rtf1 specifies the RTF version.
  • \ansi specifies the character set.
  • \ansicpg1252 specifies the code page.
  • \deff0 specifies the default font number.
  • \nouicompat indicates no user interface compatibility.
  • \deflang1033 specifies the default language.

-> Control Words

  • \b makes the text bold.
  • \i makes the text italic.
  • \ul underlines the text.
  • \par creates a new paragraph.

-> Groups

  • Enclosed in braces, these are used to control words and text together to apply specific formatting.

-> Text

  • The actual plain text content of the document.

-> Character Encoding

  • I.e. Unicode or ANSI

-> Font Table

  • Defines the fonts in the document

-> Color Table

  • Defines the colors used in the document.

Static Analysis

Hash Type File Hash
MD5 b0f2328750d22b52025015e9ada820a2
SHA1 46b0fc8f46a9bda8ee1a85e0002ec1a9e31db223
SHA-256 1e9f21f514ee4793cfae7baa21549be0d9b432c59513d2efed860c2b1501da39
  • This particular Graftor sample is in the form of a .dll.

  • It has 5 DLL imports:

    • user32.dll - Very commonly found in most PEs.
    • kernel32.dll - Also very commonly found.
    • gdi32.dll - I recognize this from when I analyzed ZBot. This is the Graphics Device Interface DLL which provides a lot of functions for graphical operations involving things like bitmaps.
    • ws2_32.dll - This contains a lot of functions related to network communications like sockets, sending and receiving data, and resolving remote hosts.
    • ntdll.dll - This is another commonly found DLL. It supports low-level system services like I/O, file system manipulation, token manipulation, etc.
  • It exports 3 functions:

    • gewayX
    • gewayZ
    • vdaudio
  • There are a few contacted domains, one or more of which might be C2-related.

Pasted image 20240621133513

  • I also see lots of .tmp files being dumped to C:\ProgramData\Microsoft\Windows\WER\Temp\.
  • It looks like this specific directory is a temporary storage location used by WER to store error report files before they are processed and either sent to Microsoft or discarded (source).

Pasted image 20240621181816

  • I also see a lot of .tmp files getting deleted.

Pasted image 20240621181809

  • From what I understand after reading through Microsoft documentation, WER kicks in when unhandled exceptions arise. This appears to be the most common condition when a file gets generated under that directory.

  • Let's extract some strings next. We see a very low string count for static strings, and 1 stack string.

Pasted image 20240621182534

  • Several API names can be found. Remember, we only saw 5 APIs in pestudio.

Pasted image 20240621182619

Pasted image 20240621182645

  • advapi32 is the only additional DLL in the strings output that was not already previously found. This particular library provides functionalities related to system security, registry, and services management. I wonder how we'll see it used (if at all).

Pasted image 20240621183037

Pasted image 20240621183126

  • Some network-based IOCs as well - nice. We can reference these later.

  • Next, let's run capa to get an overview of the capabilities of the specimen.

  • Right away, capa tells us that this specimen is likely packed.

Pasted image 20240621183344

  • That's interesting because Exeinfo PE and a few other tools did not detect any packing.

Pasted image 20240621183513

  • Not sure yet, but we might end up having to use a debugger to manually unpack this sample.

  • Taking a look at the capa output, we see a pushad + popad sequence in two functions:

0x10001C58

Pasted image 20240621183928

and

0x10002974

Pasted image 20240621183942

  • We also see that it uses some type of receive function component of ws2_32 to receive data on a socket at address 0x10003220.

Pasted image 20240621184030

  • Some more indications of TCP-based C2.

Pasted image 20240621184049

Dynamic Analysis

Step 1 - Learning to Debug DLLs

  • I have never debugged a DLL with x32dbg before, so I'll have to do some research.
  • SecurityBreak Author Thomas Roccia wrote an article on the subject.

Pasted image 20240624131726

Pasted image 20240624133855

  • Once the DLL is loaded into x32dbg, we have to set a command line to specify the exported function by its ordinal.

Pasted image 20240624134039

  • Then, we have to run it to the Entry Point and begin analyzing.

Pasted image 20240624134106

  • In this case, we have 3 functions to look at.

Pasted image 20240624133951

  • I followed the instructions in the article. In the below screenshot, we've arrived the Entry Point, and can begin analysis.

Pasted image 20240624134658

Function 1 - gewayx

  • Single stepping through the program, we see some assembly instructions to manipulate registers, the stack, and move data around, etc.
  • Shortly after the entry point, we see the value of ecx being moved to fs:[0]. fs:[0] is a pointer to the first (most recently added) exception handler. At this point, it seems this is a possible indication of SEH abuse.
  • Here is the new exception handler in grey that got added. It doesn't appear to be a custom handler, but rather a specific address in ntdll.dll.

Pasted image 20240624135721

  • If we continue single-stepping through the user code, it eventually reaches this call to C71B1A. If we Step Over (F8), the process terminates.

Pasted image 20240624142156

  • We need to take a closer look at this function. I suspect it contains anti-analysis code.
  • To do this, we'll set a breakpoint there and single-step into it.

Pasted image 20240624142547

  • After several function calls, we see the below:

Pasted image 20240624143112

  • Between 003924E0 and 00E9251E, the code performs the following tasks:
  1. Pushes a return address and the previous SEH frame.
  2. Sets up the stack and local variables, adjusting the stack pointer.
  3. Saves the context of several registers (ebx, esi, edi).
  4. Sets up a new SEH frame with XOR operations, possibly as part of an obfuscation or anti-debugging technique.
  5. Updates the SEH chain with a new handler.
  6. Returns from the function.
  • This code appears to be setting up a structured exception handling (SEH) frame, which is often used for managing exceptions or implementing anti-debugging techniques in malware. The usage of XOR operations and manipulation of the SEH frame suggests it could be part of an obfuscation or anti-analysis technique.

  • Interesting method for function calls. It moves the address of a the desired API call to a CPU register, and then calls the CPU register.

  • If we keep stepping through, we can eventually figure out how the specimen manages to terminate the process.

Pasted image 20240624144208

  • The code above pushes 1 to the stack and calls ExitProcess, causing the process to terminate with Exit Code 1. This doesn't normally mean anything by itself, but typically an exit code of 0 means that the process completed its execution and exited successfully without any errors.

  • Any non-zero codes typically indicate that an error was encountered.

Function 2 - gewayz

Function 3- vdaudio

Summary