PowerPoint-Präsentation SquirrelWaffle From Maldoc to Cobalt Strike Joel Dönne | @jxd_io Background ▪ A new spam mail campaign has been running since mid-September 2021, which delivered a new kind of malware loader → SquirrelWaffle ▪ Similar to other campaigns before, this one sends a mail with a malicious attachment or a link to download one. ▪ Let‘s analyze it! Virustotal Research ▪ Campaign uses similar naming scheme: „diagram-.doc“ – Sample Case 1) diagram-721.doc – Sample Case 2) diagram-623.doc ▪ Search results on VT: 76 files since 10.09. ▪ Submissions from DE, FR, HU, IN, US ▪ In some other cases .xlm files are used for initial compromise, but the delivered samples in stage 2 and afterwards are the same Analysis – Stage 1 ▪ Word document with obfuscated VBA macro ▪ Analysis via olevba --deobf – Some decoy code – Dropper & CnC communication Analysis – Stage 1 drop C:\ProgramData\pin.vbs download drop hxxps://priyacareers.com/u9hDQN9Yy7g/pt.html hxxps://perfectdemos.com/Gv1iNAuMKZ/pt.html hxxps://bussiness-z.ml/ze8pCNTIkrIS/pt.html hxxps://cablingpoint.com/ByH5NDoE3kQA/pt.html hxxps://bonus.corporatebusinessmachines.co.in/1Y0qVNce/pt.html www1.dll www2.dll www3.dll www4.dll www5.dll execute 1) "cmd /c rundll32.exe C:\ProgramData\www1.dll,ldr" 2) "cmd /c rundll32.exe C:\ProgramData\www2.dll,ldr" 3) "cmd /c rundll32.exe C:\ProgramData\www3.dll,ldr" 4) "cmd /c rundll32.exe C:\ProgramData\www4.dll,ldr" 5) "cmd /c rundll32.exe C:\ProgramData\www5.dll,ldr" Analysis – Stage 2 ▪ Dropped PE-DLLs www[1-5].dll vary on requested dropper URLs ▪ Code is obfuscated ▪ The called „ldr“ function is not available… Analysis – Stage 2 Flow Graph Analysis – Stage 2 ▪ Some interesting Imports of this sample are not referenced directly… FLARE CAPA explorer Analysis – Stage 2 ▪ Lets start with the dynamic analysis setting a breakpoint at kernel32.dll VirtualAlloc ▪ 1) Call is coming from call dword ptr ds:[ebx+2113E4] ▪ 2) Allocated memory is written by rep movsb ▪ 3) Jumping into buffer shellcode via jmp eax 1) 2) 3) Analysis – Stage 2 ▪ Lets start with the dynamic analysis setting a breakpoint at kernel32.dll VirtualAlloc ▪ 1) Call is coming from call dword ptr ds:[ebx+2113E4] ▪ 2) Allocated memory is written by rep movsb ▪ 3) Jumping into buffer shellcode via jmp eax E8 00 00 00 00 = shellcode call instruction Analysis – Stage 2 ▪ A further call of VirtualAlloc leads to a new buffer ▪ Setting a HW,Write breakpoint on that buffer leads to the routine which fills this buffer ▪ Remove this breakpoint and set another one at the end of the filling routine (leave instruction) ▪ Magic Bytes: M8Z → aPLib compression Analysis – Stage 2 ▪ To reveal the aPLib decompression routine remove all further breakpoints and set a new one (HW,Access) at the M8Z header bytes → Breakpoint triggerd in the aPLib decompression function → The EDI register reveals the destination offset for the decompressed content ▪ Replace the breakpoint with one at the end of the decompression routine (ret instruction) → Decompressed PE-DLL ▪ Dump PE-DLL Analysis – Stage 2 ▪ „ldr“ function has only one call instruction to the main function ▪ To start „ldr“ function, do the following steps: 1) Load PE-DLL in x32dbg 2) Run DllEntryPoint function till returning to initial ntdll call (at least function at offset 0x1000) 3) Move EIP manually to „ldr“ entry point Analysis – Stage 3 The interesting parts of that function are mainly the decryption of the CnC server list and the ones which are used to generate the payload for the further communication. The output from the function calls are concatenated in a string like and XORd with the static key „KJKLO“ XOR crypt function XOR the concatenated string Analysis – Stage 3 To follow the preparation, set breakpoints to the XOR crypt function calls. The result of the call is returned as a pointer in the EAX register Analysis – Stage 3 After XORing the concatenated string, the result is encoded base64 Input XOR B64 Output Key CyberChef decryption Analysis – Stage 3 Like mentioned before, the XOR crypt routine is also used to decrypt the embedded CnC server, but using a different key. CnC communication function Key for CnC server list decryption Analysis – Stage 3 Analysis – Stage 3 In the next step the malware does more preparation for a further communication with the CnC server It concatenates a random string with the the local IP address, XORs and encodes it base64 CyberChef decryption Analysis – Stage 3 Set breakpoints on communication functions (send & recv) to follow the further communication Analysis – Stage 3 Prepared HTTP request sent to the CnC server Analysis – Stage 3 HTTP response received from CnC server Analysis – Stage 3/4 Unfortunately curren‘t requests to the CnC Server doesn‘t result in a further infection... I got a successful infection in my lab environment in the past resulting in a dropped and executed file .txt in C:\User\\AppData\Local\Temp This file was similar to the one uploaded by malware-traffic-analysis.com Name: RVOgDko8fnP.txt (MD5 ef799b5261fd69b56c8b70a3d22d5120) Analysis – Stage 4 ▪ Don‘t get fooled by .txt ending, actually it‘s a PE-DLL ▪ Interesting Imports LoadLibrary VirtualAlloc ▪ Libraries are mostly linked at runtime ▪ Dynamic Analysis Set breakpoints at relevant functions LoadLibrary VirtualAlloc ▪ After multiple LoadLibrary calls, a VirtualAlloc follows ▪ Set HW,Write breakpoint at the new allocated buffer VirtualAlloc Filling the buffer Buffer completely filled HW,Write End of loop Analysis – Stage 4 ▪ Jump to the new buffer takes place immediately after the end of the loop → Shellcode execution EB = jmp 670005 03 = add eax, edx C2 = ret C Analysis – Stage 5 ▪ Dump the PE-EXE ▪ Static analysis reveals, that there is one „main“ function, which is a shellcode wrapper ▪ Breakpoint on LoadLibrary shows, that wininet.dll is used during runtime ▪ Additional Breakpoints on wininet functions InternetConnectA InternetOpenA InternetReadFile HttpOpenRequestA HttpSendRequestA Analysis – Stage 5 1) InternetConnectA 2) HttpOpenRequestA 3) HttpSendRequestA Analysis – Stage 5 HTTP GET Request The crafted request looks like a harmless HTTP GET Request to receive a JQuery Javascript file Setting up a simple request with no additions, results in a blank answer… To receive the .js file, reproducing the whole GET request including HTTP Header fields is required, e.g.: Referer hxxp://code.jquery.com/ Analysis – Stage 5 4) VirtulAlloc Response of the request is saved into a buffer Size: 4MB 5) InternetReadFile Buffer is filled in multiple chunks Important offset 0xFAF stored in ECX register Analysis – Stage 5 Breakpoint at the end of the loop → Buffer is filled completely On the first look, the response looks like a valid JQuery response Looking more in detail and following the code execution, the buffer contains a shellcode which is called directly afterwards, by jumping to offset 0xFAF Pseudo JQuery Embedded Shellcode ... ... Pseudo JQuery Analysis – Stage 5/6 Dump the memory page Extract the PE-DLL from dumped page Offsets for extraction: Begin 0xFAF -- End 0x3440E Analyze it using Cobalt Strike Parser! Recap Spam mail with link Encrypted .zip archive Word document with obfuscated VBA VBS Loader CnC-Server Stage 2 PE-DLL www[1-5].dll Extract Drop Execute DropDownload aPLib compressed Stage 3 PE-DLL Dll1.dll,ldr Stage 4 PE-DLL RVOgDko8fnP.txt CnC-Server Download Drop Execute Stage 5 PE-EXE Cobalt Strike Beacon Loader Embedded Execute CnC-Server Execute Stage 6 PE-DLL Cobalt Strike Beacon SquirrelWaffle Loader YARA To detect the SquirrelWaffle loader i created a YARA rule based on the decryption function used in Stage 3 https://github.com/0xjxd/YARA-rules/blob/main/Loader.SquirrelWaffle.yara IOCs ▪ Stage 1 - 2 Dropper Server hxxps://priyacareers.com hxxps://perfectdemos.com hxxps://bussiness-z.ml hxxps://cablingpoint.com hxxps://bonus.corporatebusinessmachines.co.in ▪ Stage 3 CnC Server hxxp://celulasmadreenmexico.com.mx hxxp://gerencial.institutoacqua.org.br hxxp://dashboard.adlytic.ai hxxp://bussiness-z.ml hxxp://ifiengineers.com hxxp://bonusvulkanvegas.srdm.in hxxp://ebrouteindia.com ▪ Stage 4 - 6 Cobalt Strike Server hxxps://systemmentorsec.com:8080/jquery-3.3.1.min.js ▪ Sample Hashes Stage 1: f0a3d4e47b098d302ad13bc4e51a03adeb9428e5c34630428222e989792f7a6d Stage 2: 00d045c89934c776a70318a36655dcdd77e1fedae0d33c98e301723f323f234c Stage 3: ab05d6335b06a0dbc41386c7c356202b4e07dcf76a4932ed4d4e7dd69b7a3101 Stage 4: 3c280f4b81ca4773f89dc4882c1c1e50ab1255e1975372109b37cf782974e96f Stage 5: 964c5933844de7ed5a7813cdb36b9974a5a819b046e73a0bc6754d7299374a9f Stage 6: 804f83a9754cfa2e43f167cc22980b1eca2ff11c05029e7ce0a8c2aae524a8b5 hxxp://test.dirigu.ro hxxp://cablingpoint.com hxxp://perfectdemos.com hxxp://afrizam.360cyberlink.com hxxp://giasuphire.tddvn.com hxxp://priyacareers.com hxxp://assurant.360cyberlink.com hxxp://sig.institutoacqua.org.br