Anti-Analysis Techniques Used in Excel 4.0 Macros
24 March 2021
I recently reversed another Excel document with 4.0 Macros that was similar to my previous post on the subject but had some added anti-analysis features that I wanted to share. I recommend reading the previous post to learn more as this article will not be going step-by-step through the analysis process.
New Obfuscation Style
Instead of storing the encrypted data as a blob of characters in cells, the sample stores them as integers in
Sheet1 of the document. It will then loop through these and subtract them from a stored key in
R50C3:R59:C3. If the integer value at the current index of
Sheet1 is greater than 1000, then the end of the string has been reached. This is very similar to the old sample, but the use of integer values seemed interesting to me.
Integer arrays in
Like the previous analysis, the document performs a lot of the same VM/Analysis checks such as: checking for the presence of a cursor, if macros are set to run by default, etc. This specific sample, however, had a few more tricks.
The sample will use the
=CALL macro to make a call to the
Excel4 function from the
Xlcall32 library. This is a callback function that is used to continue running the macros at a defined cell. This is a good way to prevent an analyst from just debugging the macros since this would spawn in a new process and won’t show in the debugger.
This will continue running the macros at
R106C1 and evade debugging
In this sample, the call to
Excel4 is dynamically generated via the deobfuscation code from earlier. When running the deobfuscation code, I will put a
=HALT() instruction at the end to prevent further execution. Once the anti-analysis technique is bypassed, I will continue running the macros at the location passed as a parameter to
Excel4. This gives the same results as calling the
Excel4 function except now I can see what the code is doing.
Visualization of how I bypass the anti-analysis technique
Alternate Data Streams (ADS)
Alternate Data Streams (ADS) are a feature of the NT File System (NTFS) that allows a user to store additional content in a file apart from its original content. ADS is used legitimately for file integrity and storing metadata; however, attackers can use it to hide malicious code. In older versions of SQL Server, for example, the DBCC CHECKDB process would create alternate data streams to store information.
When a file is downloaded from the internet, it will contain an ADS called
Zone.Identifier which has data about where the file originated. In this case, the sample I downloaded was from Zoho Docs, therefore, it contained that URL in the stream. This particular sample checks to see if the ADS is present by actually trying to delete the ADS itself. If this sample were run in a sandbox, there would be no ADS, thus triggering this anti-analysis technique and halting the execution of the macros.
The alternate data stream of the sample
Zone.Identifier alternate data stream by trying to delete it
As with the previous analysis, once all the checks are complete, the sample will reach out to C2s to try to grab the second stage payload and execute it. In this case, it appears to be a DLL that will be executed through
DllRegisterServer. Both of the C2s were down when I found the sample, so I could not get the second stage to continue the analysis.
Downloading the second stage from C2
Hopefully, this provided insight into a few anti-analysis techniques seen in the wild and can be a good reference to other analysts in the future. The call to
Xlcall32 was new to me, and I had not seen the alternate data stream check used before. If you have any questions or comments on this analysis feel free to reach out to me on my Twitter or LinkedIn.
Thanks for reading and happy reversing!