ABADBABE 8BADF00D: Discovering BADHATCH and a Detailed Look at FIN8’s Tooling By ATR Published: 2019-07-23 · Archived: 2026-04-05 12:46:09 UTC by Kristina Savelesky, Ed Miles, Justin Warner FIN8 is a financially-motivated threat group originally identified by FireEye in January of 2016, with capabilities further reported on by Palo Alto Networks’ Unit 42 and root9B. This blog will introduce a new reverse shell from FIN8, dubbed BADHATCH and compare publicly reported versions of ShellTea and PoSlurp to variants observed by Gigamon Applied Threat Research (ATR). With these comparisons, we aim to show how FIN8 continues to evolve and adapt their tooling. Our goal in sharing this intelligence is to enable defenders to better prevent, discover, or disrupt FIN8’s operations and offer a greater understanding of their capabilities. Evolving Toolsets Gigamon ATR, along with incident response partners, observed FIN8 on numerous occasions and on each occasion collected and analyzed malicious samples for detection research. We analyzed variants of the ShellTea implant and PoSlurp memory scraper malware, designated ShellTea.B and PoSlurp.B. One of the most interesting samples analyzed appears to be a previously unreported tool, BADHATCH, that provides file transfer and reverse shell functionality.    As part of our research, Gigamon ATR reviewed previously reported samples when available, assessed public reports, and compared intelligence to our own observations from incident response engagements. Previous reporting on FIN8 indicates that initial infection typically begins with a malicious email campaign, using weaponized Microsoft Word document attachments aimed at enticing the user to enable macros. These macros execute a PowerShell command which downloads a second PowerShell script containing the shellcode of the first stage of a downloader, called PowerSniff by root9B and Unit 42, or PUNCHBUGGY by FireEye. While Gigamon ATR does not have phishing documents available for comparison, an incident response partner recovered the BADHATCH PowerShell script that, at first sight, appears comparable to PowerSniff/PUNCHBUGGY. BADHATCH Malware The BADHATCH sample begins with a self-deleting PowerShell script containing a large byte array of 64-bit shellcode that it copies into the PowerShell process’s memory and executes with a call to CreateThread. This script differs slightly from publicly reported samples in that the commands following the byte array are base64 encoded, possibly to evade security products. While previous analyses saw PowerSniff downloaded from online sources and executed, Gigamon ATR incident response partners recorded the attackers launching the initial PowerShell script via WMIC as visible in Figure 1. wmic /node:“” process call create “powershell –ep bypass –c .\.ps1” Figure 1: WMIC command used to launch BADHATCH PowerShell script. The first stage of the malware then loads an embedded second stage DLL into the same memory space (using the Carberp function hash resolution routine to hide the names of API functions being used) and executes it. The use of hexadecimal constants 0xABADBABE 0x8BADF00D to locate the beginning of the embedded DLL was a common trait across all first stages of the FIN8 PowerShell scripts we analyzed (see Figure 2). Figure 2: The BADHATCH first stage locates the embedded DLL using 0xABADBABE 0x8BADF00D constants. The hex dump of the embedded DLL is shown on the left, with the disassembly of instructions and constants used for locating the DLL on the right Once executed, depending on the session ID, the embedded DLL either APC injects into a svchost.exe process (launched with svchost.exe -k netsvcs), or injects into explorer.exe (using the ToolHelp32 API functions and RtlAdjustPrivilege to enable SeDebugPrivilege). The malware creates a local event object, with the hardcoded name Local\{45292C4F-AABA-49ae-9D2E-EAF338F50DF4}, which is used similarly to a mutex (to ensure only one copy is running at a time). On startup, and every 5 minutes thereafter, the sample beacons to a hardcoded command and control (C2) IP (149.28.203[.]102) using TLS encryption, and sends a host identification string derived from several system configuration details and formatted as %08X-%08X-%08X-%08X-%08X-SH. Only the one hardcoded IP address and no C2 domains https://blog.gigamon.com/2019/07/23/abadbabe-8badf00d-discovering-badhatch-and-a-detailed-look-at-fin8s-tooling/ Page 1 of 14 were observed. Upon connecting back to the C2 server and sending the system ID, the shell will offer the banner shown in Figure 3, with the OS version and bitness as well as the hostname values filled in. ---------------------------------------- * SUPER REMOTE SHELL v2.2 SSL ---------------------------------------- OS: %s SP %d %s HOSTNAME: %s Press i+enter to impersonate shell or just press enter Figure 3: banner of the BADHATCH reverse shell. The shell even includes a small bit of online help with troubleshooting suggestions (displayed in Figure 4) if there are issues with launching the cmd.exe process the shell uses for command execution. Logon failure: unknown user name or bad password. Logon failure: user account restriction. Possible reasons are blank passwords not allowed, logon hour restrict The trust relationship between this workstation and the primary domain failed. The service cannot be started, either because it is disabled or because it has no enabled devices associated w Run 'sc start seclogon' if you can ;) Failed to execute shell, error %u Figure 4: Plaintext error messages present in the strings of the BADHATCH DLL. An option for impersonating a specific user via the Windows APIs is given, but both execution paths will start a cmd.exe process for command execution. Upload and download functions are available, and the shell looks for those commands, as well as a ‘terminate’ command, before sending any input to the cmd.exe process. BADHATCH uses the Windows IO Completion Port APIs and low-level encryption APIs from the Security Support Provider Interface to implement an asynchronous TLS-wrapped TCP/IP channel. As a side effect of this implementation, port 3885 will be opened and bound on localhost. The malware connects back to itself on this port and uses this as a loopback transmission channel in the course of encrypting and transferring data between threads. Internally, this mechanism uses CompletionKeys of ’nScS’ and ‘rScS’. These keys are used to track which IO operations have completed and identify the sender/receiver threads that handle the shell communication. Besides the networking behavior, BADHATCH appears to be considerably different from PowerSniff in that it contains no methods for sandbox detection or anti-analysis features apart from some slight string obfuscation. It includes none of the environmental checks to evaluate if it is running on possible education or healthcare systems and has no observed built-in, long-term persistence mechanisms. Below, Table 1 summarizes the differences between PowerSniff, PUNCHBUGGY, and BADHATCH. Shared Component root9B PowerSniff Unit 42 PowerSniff VirusTotal PUNCHBUGGY SHA-256 Hash not provided in report Hash for maldoc provided in report 5024306ade133b0 ebd415f01cf64c23 a586c99450afa9b7 9176f87179d78c51d Infection vector is a spearphishing email with an attached maldoc that downloads a PowerShell stager ✓ ✓ ✓ Target architecture is 32- or 64-bit ✓ ✓ ✓ https://blog.gigamon.com/2019/07/23/abadbabe-8badf00d-discovering-badhatch-and-a-detailed-look-at-fin8s-tooling/ Page 2 of 14 Shared Component root9B PowerSniff Unit 42 PowerSniff VirusTotal PUNCHBUGGY First stage loads and runs shellcode in memory that loads a DLL second stage ✓ ✓ 0xABADBABE 0x8BADF00D checks to find embedded DLL Use of Carberp function hash resolution routine in shellcode to find API functions ✓ Unmentioned in report Same hashes and algorithm as BADHATCH Embedded DLL decrypts strings using algorithm with seed 0xDDBC9D5B, multiplier 0x19660D, increment 0x3C6EF35F Unmentioned in report Same seed and constants as PUNCHBUGGY Same seed and constants as Unit 42 PowerSniff sample Includes methods for sandbox detection Slightly different than Unit 42 sample/PUNCHBUGGY Identical to PUNCHBUGGY Identical to Unit 42 sample Ability to write DLL to %%userprofile%%\AppData\LocalLow\%u.db and run via rundll32 ✓ ✓ ✓ Ability to write an executable and run it ✓ Unmentioned ✓ Ability to write a DLL and load into calling process with LoadLibraryW ✓ Unmentioned ✓ Performs HTTP requests with user agent of Mozilla/4.0 (compatible; MSIE 8.0; Windows NT %u.%u%s) ✓ Contacts C2 via HTTP, user agent unspecified in report ✓ Persistence Ability to write a DLL and add it to HKLM\System\CurrentControlSet\ Control\Session Manger\AppCertDlls for persistence Persistence unspecified No observed registry modifications Memory string similarity Similar to PUNCHBUGGY and Unit 42 PowerSniff Seem identical to PUNCHBUGGY, similar to root9B PowerSniff Seem identical to Unit 42 PowerSniff, similar to root9B PowerSniff Ability to inject into explorer.exe ✓ Unmentioned Unobserved Ability to spawn and inject into svchost.exe process if sessionID = 1 Unmentioned Unmentioned Unobserved Ability to download/uploaded files to/from user-supplied path Unmentioned Unmentioned Unobserved Ability to start interactive shell Unmentioned Unmentioned Unobserved Ephemeral localhost port 3885 usage Unmentioned Unmentioned Unobserved Command and control vseflijkoindex[.]net vortexclothings[.]biz unkerdubsonics[.]org popskentown[.]com supratimewest[.]com letterinklandoix[.]net supratimewest[.]biz starwoodhotels[.]pw oklinjgreirestacks[.]biz www.starwoodhotels[.]pw brookmensoklinherz[.]org supratimewest[.]com letterinklandoix[.]net supratimewest[.]biz starwoodhotels[.]pw oklinjgreirestacks[.]biz www.starwoodhotels[.]pw brookmensoklinherz[.]or Table 1: A comparison table showing shared and differentiating components between root9B’s PowerSniff (as reported), Unit 42’s PowerSniff (as reported), a PUNCHBUGGY sample from VirusTotal, and the BADHATCH sample from Gigamon ATR. ShellTea.B Implant https://blog.gigamon.com/2019/07/23/abadbabe-8badf00d-discovering-badhatch-and-a-detailed-look-at-fin8s-tooling/ Page 3 of 14 ShellTea is a memory-resident implant that includes multiple methods for downloading and executing additional code and can install persistence via the registry. Its primary use case appears to be serving as a stealthy foothold in the victim network and deploying additional payloads. During two previous incident response engagements involving FIN8, response partners recovered registry keys containing hexadecimal-encoded data and corresponding PowerShell scripts. Gigamon ATR discovered these to be persistence artifacts of ShellTea variants, with a few differences from root9B’s ShellTea sample. Table 2 presents a comparison of differentiating features between ShellTea and ShellTea.B. root9B ShellTea ATR ShellTea.B Hash not provided in report Shellcode from registry: 385538451e59f630db6f1b 367aacfdbb85b7d730210 fc6d5b2bee7037f0362a5 PowerShell script waits five seconds for thread to complete PowerShell script includes Start-Sleep 2; then waits for one minute for thread to complete Uses a custom function resolver with 4-byte hashes and seed 0x463283F5, multiplier 0x19660D, increment 0x3C6EF35F Uses a custom function resolver with 4-byte hashes and seed 0x463283F5, multiplier 0x19660D, increment 0x3C6EF35F Use of Ws2_32.dll exports for network functionality (connect, send, etc.) Use of wininet.dll exports for network functionality (InternetConnectA, HttpSendRequestA, etc.) Connects to command and control over port 443 using a custom binary protocol with XTEA encryption in CBC mode, can communicate through proxies via CONNECT Communicates with command and control servers using HTTPS POST requests, with XTEA-encrypted payload in the body (see Figure 5 for headers) The command and control servers utilized a standard self-signed “Internet Widgets” Apache TLS certificate C2 domains include: neofilgestunin[.]org verfgainling[.]net straubeoldscles[.]org olohvikoend[.]org menoograskilllev[.]net asojinoviesder[.]org C2 domains include: moreflorecast[.]org preploadert[.]net troxymuntisex[.]org nduropasture[.]net No encoded DNS traffic mentioned Encoded DNS requests to generated subdomains of nduropasture[.]net Table 2: A comparison table showing differentiating components between root9B’s ShellTea implant (as reported) and the ShellTea.B sample from Gigamon ATR. POST json/ Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; Trident/4.0 Accept: application/octet-stream Content-Type: application/octet-stream Connection: close Figure 5: Strings output of hardcoded HTTP POST headers used in ShellTea.B communications, note the missing right parenthesis of the user agent string. In addition to the HTTPS channel, ShellTea.B uses DNS to communicate with C2 infrastructure. Small messages, usually 39 bytes, are encoded in the subdomain field of DNS A-record queries. These messages are composed of several pieces of internal state encoded in the character space “abcdefghijklmnopqrstuvwxyz012345”. The state transmitted includes an internal PRNG seed as well as several hardcoded values embedded in the malware at compile time, while the query responses consist of single IP addresses. The DNS channel is initiated from within several nested loops, that can cause https://blog.gigamon.com/2019/07/23/abadbabe-8badf00d-discovering-badhatch-and-a-detailed-look-at-fin8s-tooling/ Page 4 of 14 repeated lookups depending on the IP address. If the IP doesn’t conform to several value checks, the inner loop will run again after a 30 second delay, up to 3 times. Iterations of the inner loop are controlled by checking if the IPs first octet plus 7 is not equal to the second octet, or if the fourth octet modulo 10 does not result in 0, 1, 2, or 3 (see Figure 6). If the inner loop terminates while the result of the modulo is greater than 0, the outer loop will run again after a delay based on the modulo value, causing the cycle to begin again. NOTE: On initialization, this DNS channel will be active before the HTTP channel. Figure 6: The ShellTea.B DNS channel processing. The differences in communication protocols between ShellTea and ShellTea.B suggest minor changes to this element of the FIN8 attack chain, possibly to adapt to target environments by blending in with other HTTPS or DNS traffic in lieu of a more suspicious custom protocol. PoSlurp.B Scraper The final, perhaps most important component in the FIN8 toolkit, is the one that actually retrieves credit card numbers as they pass through payment card processing systems. Credit card numbers are 15 or 16 digits long and conform to the Luhn algorithm. This algorithm defines valid credit card numbers, and most scrapers check card numbers against it. Notably, PoSlurp does not run the Luhn algorithm on card numbers it collects. Verification may be performed offline, after the exfiltration of the card data, but either way, FIN8 knows the environment and PoSlurp targets the card processing software directly for scraping rather than arbitrarily scraping other process memory. During previous incident response engagements involving FIN8, response partners also recovered POS memory-scraping samples: one, an executable binary that appears to be a 32-bit version of the PoSlurp malware reported by root9B (reported as PUNCHTRACK by FireEye), and another, a PowerShell script highly similar to the BADHATCH PowerShell script. This script was also observed being executed via WMIC, illustrated in Figure 7. wmic /node:”@t.txt” /user:”” /password:”” process call create “powershell -ep bypass –c c Figure 7: WMIC command used to launch the PoSlurp.B script. Like the BADHATCH script, this script base64 decodes and executes further commands which load a byte array of shellcode into memory and begin execution. The PowerShell script is then moved to a temporary file before being overwritten with a copy of the Regedit executable and then deleted. True to the previously analyzed first stage scripts, the shellcode uses the Carberp function hash resolution routine to locate an embedded DLL by parsing for the same hexadecimal constants, loads the DLL into memory, and executes it. Unlike the notable use of low-level API functions and anti-analysis techniques in PoSlurp, PoSlurp.B’s first stage simply calls VirtualAlloc, LoadLibrary, and GetProcAddress to dynamically resolve imported functions, without other tricks to thwart analysis. Where PoSlurp and PUNCHTRACK arguments are passed in as part of the command line, PoSlurp.B arguments are passed in an environment variable and are pipe-delimited instead of hash- or asterisk-delimited (see Figure 8). $env:PRMS = “i|||t|2800|”; Figure 8: Pipe-delimited PoSlurp.B arguments passed in an environment variable in the PowerShell script. Major functional differences in PoSlurp.B include the ability to: Inject into the target process given an ‘i’ argument. Create a svchost netsvcs process and APC inject the main loop given an ‘s’ argument. Run the main loop without injection given a ‘p’ argument. The PUNCHTRACK sample that we analyzed (downloaded from VirusTotal) also had the ability to create and inject into a svchost process, though it did so regardless of command line arguments.   Additionally, the call to DeleteFile that cleaned up old output files has been removed. Incident response partners captured these actions being performed manually, show in Figure 9. for /F %i in (.txt) DO attrib -h \\%i\c$\users\\appdata\local\temp\.tmp for /F %i in (.txt) DO net use \\%i\c$ /user:%i\ for /F %i in (.txt) DO copy \\%i\c$\users\\\appdata\local\temp\.tmp %i.t https://blog.gigamon.com/2019/07/23/abadbabe-8badf00d-discovering-badhatch-and-a-detailed-look-at-fin8s-tooling/ Page 5 of 14 for /F %i in ((.txt) DO del \\%i\c$\users\\\\appdata\local\temp\\.tmp Figure 9: Commands to manually unhide, copy, and delete encrypted PoSlurp.B log files. The following table (Table 3) provides a comparison between features observed in two versions of PoSlurp, a PUNCHTRACK sample downloaded from VirusTotal, and PoSlurp.B. Shared component root9B PoSlurp ATR PoSlurp VirusTotal PUNCHTRACK ATR P SHA-256 Hash not provided in report cc952950a73909a 655044dbb87f85f 66d44d1d4e3a1e0 96777bbc938a62bd 080 (link) ffc133ea83deac 94bce5db1a4202 57304931e6d3cfb 82c6d9e50a2a98 f43d310 (link) 8c6fe4c b756d5 230ceaf 91dac42 Invocation wmic /node:”@targets.txt” process call create “cmd /c [PoSlurp_filename].exe TARGET1.EXE #TARGET2.exe*1234*winlogon.exe” cmd /c psv.exe TARGET1.EXE #TARGET2.EXE*1400*winlogon.exe Takes 3 args: PUNCHTRACK filename (psvc.exe), POS target process, and timeout wmic /n /user:”< /passwo process “power –c c:\us