Using static analysis to dissect malicious office macros

Posted on 23 May 2017

Phishing with malicious attachments has been the main delivery method that attackers use to compromise user endpoints for several years. All it takes is just one victim to fall for a phishing attack and the possibility of the attackers gaining a foothold inside the victim’s network rises significantly.

Dissecting VBA macros 1
Source: Verizon 2017 DBIR*


Considering the successful rate of phishing attacks, there are a variety of different types of attachments usually used to deliver a malicious payload, such as executable files, office documents embedded with macros, or programs written in Java or JavaScript.


In this post, we are going to focus on office documents with embedded macros. Often, an efficient first step is to use a dynamic analysis sandbox to study the behavior of the malware. However, static analysis is also a useful technique and this post will demonstrate the use of “olevba” for static analysis, a script to parse OLE and OpenXML files that was created by Decalage.


The sample

For this post, we are going to use a sample that was delivered through phishing that is related to the Emotet malware.

Dissecting VBA macros 2 3

 Analyzing the streams of the OLE file

Running the olevba tool allows you to extract all VBA macros found in the streams of the OLE container:

Dissecting VBA macros 4
Dissecting VBA macros 4b

Malicious macros are usually obfuscated to make signature detection more difficult and generally make analysis more time consuming. Often, a key objective is to quickly discover if there is a remote command and control channel that the macro will connect to and/or a command that the macro will execute.


We will start by analyzing the first stream:

Dissecting VBA macros 5

The AutoOpen() function is a built-in macro function that runs when the document is opened. From analysis of the code, it is clear that some of the code is unnecessary but that it concludes by calling the “l2B9S” function at the end of the subroutine.

Dissecting VBA macros 6

The function l2B9S can be found in Module3, which also contains more unnecessary code due to obfuscation techniques and is intended to frustrate analysis. However, further analysis of the code in Module3 reveals a call to another function named “EUwBq”.

Dissecting VBA macros 7

The “EuwBG” function can be traced back to Module4 and contains some more interesting functionality than we have not seen until now:

Dissecting VBA macros 8

Apart from the noise (unnecessary code), there are references to base64 and additionally a base64 encoded string, which may contain interesting data. This is concatenated with some other variables to form a larger string.

Dissecting VBA macros 9

Tracing the variables, we then find later that this is then concatenated into an even larger string with a number of other variables, as shown below:

Dissecting VBA macros 10

Tracing it further brings us back to Module3, which calls a Shell function that is used to execute a command on the system:

Dissecting VBA macros 11

This certainly looks highly suspicious and is likely the end goal of the macro payload. Generally, base64 encoded strings along with a combination of string concatenation is used as an obfuscation technique to hide what commands are being executed by the macro.


With further analysis, we can summarize the following key components of the payload:


  • AutoOpen()  is used to load the payload on document open, which is calling the 12B9S function.

    Dissecting VBA macros 12

  • 12B9S() is the main function using the Shell function to execute a system command and that calls functions from other modules.

    Dissecting VBA macros 13

  • twpbFK is the payload that is essentially split up into multiple base64 encoded chunks.

    Dissecting VBA macros 14
    Dissecting VBA macros 14b

  • ASVQLWow is the decode function.

    Dissecting VBA macros 15

After the base64 encoded payload is pieced together and then decoded, it results in the following command being executed:

Dissecting VBA macros 20

Breaking the PowerShell command down, we can see that the following key steps are performed:


  1. The script makes a GET request to each of the URLs contained.
  2. The file returned from each URL is saved to disk with a random number for each file and a .exe extension in the location pointed to by the "temp" environment variable (which is often %USERPROFILE%\AppData\Local\Temp).
  3. Each of these files is then executed.


As we can see, this macro is simply acting as a stager to remotely fetch some malicious executables from some external domains, save them to disk and then execute them.


At the time of analysis, the following behavior was observed for the domains involved:

Dissecting VBA macros 21

The two files that were successfully downloaded were found to have the same hash. In this case, this was likely done to provide some redundancy against individual C2 channels being blocked as malicious.

Dissecting VBA macros 22


Hopefully, this blog post has given some context into how to use static analysis of obfuscated malicious macros to identify the end goal of the payload and any related C2 channels or dropped executables. Part two of this blog post will look into using dynamic analysis to analyze the binaries dropped by the malicious macro.