In a recently-concluded engagement, Sophos’ Rapid Response team was called in to investigate an attack targeting an Exchange server. During the course of the work, the responders discovered that the attackers were still taking actions inside the target’s network, and stopped the slow-rolling, manually controlled attack before any lasting damage could be done.
The target was a large enterprise that has around 15,000 endpoints spread across North America. Sophos discovered the attack, which began with the target’s Exchange server becoming compromised through the use of the ProxyLogon exploit.
What made the attack stand out was the attackers’ use of an unusual combination of commercial remote management tools not typically observed during the early phases of attacks, and the attackers’ careful avoidance of some of the more obvious (and forensically noisy) techniques we typically observe in attacks like this, such as the widespread use of RDP to take control of machines inside the network. They did, however, scan the network and deploy Cobalt Strike as they moved from machine to machine.
During the incident, which took place over a period of just over two weeks, the attackers dumped stored credentials from the Exchange server, and then leveraged some of those credentials to pivot to other machines in the network. They also used a commercial remote access software tool called Remote Utilities, and limited their use of RDP within the network to just one session per machine, possibly as an attempt to remain below the radar.
The initial attack phase, and its tooling
The vulnerable server was compromised on March 16th, when a log entry reveals that the attacker leveraged two vulnerabilities – CVE-2021-26855 and CVE-2021-27065 – in order to execute a malicious PowerShell command on the server.
Within the next 90 minutes, the attackers had enumerated the Domain Administrator accounts from the now-compromised computer, dumped the credentials from memory so they could work on cracking the passwords offline, and had modified a Registry key on the computer that forced it to clear any stored credentials from memory. This final action would force any users to log in using their current password the next time they used the machine.
The password dump file was left in a location where the attackers could retrieve it directly from the public-facing web interface of Outlook Web Access, but where it would not be obvious to employees who used the server to check their email.
The attackers took a one day break and returned on March 18th to begin moving laterally through the target’s network and to establish multiple new footholds on different machines. They dumped the credentials from memory a second time, and used WMI and PowerShell to issue commands on other machines on the network.
This was clearly an information-gathering and “establishing control over lots of machines” phase of the attack, as the threat actors mapped the network using a tool called ADRecon, and identified additional machines they would later pivot to. They used PowerShell commands to dump memory from LSASS on some of these other internal machines remotely, and then pulled those dump files back to the Exchange sever – their initial foothold – for retrieval and offline extraction of more credentials.
They also took this opportunity to set up a backdoor into the network by executing the first of several malicious payloads on the Exchange server – an open-source utility called Chisel, which its Github page describes as “a fast TCP/UDP tunnel, transported over HTTP, secured by SSH.” While Chisel, like ADRecon, isn’t inherently malicious, it obviously can be used that way, as it was here.
The attackers also ran a command that remotely installed a PowerShell backdoor (named bot.ps1) and a script that pulled down and executed a Cobalt Strike payload (called cobalt.ps1) on multiple machines on the network.
The threat actors actually built themselves a sizeable collection of tools they used during this attack, the details of which are discussed below.
Attackers find expediency outweighs security
For all the effort involved, the attackers did not employ particularly good security, themselves. They created accounts named admin on several machines (with a password of “P@ssw0rd“) and added them to the Administrators group.
But they didn’t log on with these accounts; Rather, as the day went on, they used the credentials that belonged to network administrators extracted from the LSASS memory dumps to connect from one machine to another, just one time over Remote Desktop, executing their bot.ps1 tool on the remote machine.
They also used this access to install a commercial IT helpdesk access tool called Remote Utilities, and three days later, a Cobalt Strike beacon (signed with a stolen digital certificate that, as of this writing, currently passes validation), on some machines.
The Cobalt Strike beacon was a DLL that was given a random name, and executed from the C:\Windows\Temp directory by a command issued through the bot.ps1 backdoor. These payloads were all signed by a Sectigo-issued certificate assigned to OASIS COURT LIMITED, with validity that does not expire until the end of 2021, tied to a yahoo.com email address.
The attackers then went silent for more than a week. On March 27, they returned and tried to execute another Cobalt Strike beacon in memory, but were prevented from doing so by our endpoint protection tools. On March 29, they performed reconnaissance of the Active Directory server (using one of the administrators’ stolen credentials), exported the results to a series of CSV files, then compressed those into a single Windows .cab archive file.
The attackers continued their slow-roll approach, only taking a small number of actions on any given day for the next few days. Sophos detected and stopped the execution of another Cobalt Strike beacon on March 30, and blocked a PowerShell command that would have deployed the bot.ps1 backdoor to four more servers the attackers had identified. They then recompiled the Cobalt Strike beacon in an attempt to evade our detection and tried again on March 31.
By April 1, the attackers had begun to use the commercial Remote Utilities tool to open a connection from a computer based in Paris to one of the targeted internal servers. They used this connection to deliver a number of malware files, including a copy of Mimikatz and a new PowerShell script named p.ps1, and to create new users with administrative privileges on additional machines. They also named one of the Chisel executable payloads Sophos.exe and tried to drop it into the Windows directory and execute it.
On April 2, the targeted company decided to engage with Sophos Rapid Response to deal with the growing problem. Within a few hours, we had identified a number of malicious programs they had delivered onto the network. The attack appeared to be a precursor to delivering ransomware to the entire corporate IT infrastructure, but our intervention prevented any further harm from being done.
Handcrafted tools used in the attack
In addition to the PowerShell remote access tool, bot.ps1, the threat actors created a series of other PowerShell scripts, which they deployed as modules to enhance the core functionality of bot.ps1. These were run across the target’s network in an attempt to conduct reconnaissance and give themselves the privileges they needed to complete the attack.
- Module_AMSIBypassMaybe_regthrgrwfgterw.ps1: a dropper that delivers either a 32-bit or 64-bit DLL as a payload, and then patches the payload’s entrycode in an attempt to defeat AMSI-based malware detection.
- Module_RunPsExecMaybe.ps1: Despite its name, this module has nothing to do with the Windows PSExec utility. It creates a service entry that runs a PowerShell backdoor it refers to as a “RemoteBulletFile.”
- Module_ADRecon.ps1: A one-line script that literally just calls the PowerShell script for ADRecon directly from its Github page.
- Module_RunByWMI.ps1: A script that copies the PowerShell backdoor to a remote computer. The only difference between it and Module_RunPsExecMaybe.ps1 is this version includes a variable called $urlConsole that defines a command-and-control address.
- Module_GetAllServers.ps1: Collects information about the current domain, and any physical or virtual machines hosted in the domain.
- Module_GetDomainControllers.ps1: Collects information about the domain controllers, including its hostname, operating system version, and its operational status.
- Module_EnumerateAdmins.ps1: Collects domain admin, enterprise admin, and domain user information.
- Module_Mod-EnumerateHyperV.ps1: Enumerates and collects information about HyperV virtual machines within a domain.
Lessons learned from the attack
The threat actors engaged in this attack were canny and evasive. They tried to stay below the radar by avoiding using RDP extensively, and by using commercially-available IT management tools to conceal the true nature of their work. Despite gaining initial access through a “low hanging fruit” Exchange server, they understood they might only have a limited window in which to gain the level of access they needed in order to deliver a final payload.
Fortunately in this case, the target never was hit with this destructive payload. Quick action by Labs and MTR ensured that the attackers’ actions were countered by reactions that prevented them from doing more damage. The greatest harm they caused resulted in the organization requiring all employees to change their passwords.
In most attacks of this nature we investigate, the eventual deliverable is usually a ransomware payload. When attackers begin to see their customized tooling get blocked by security products, they often rapidly escalate to deploy ransomware before they lose all access to the network. The countermeasures Sophos deployed effectively prevented them from taking that final step.
The target told their Sophos team that they thought they had patched the Exchange server correctly, and then had tested whether the server was compromised using some scripts provided by Microsoft. Unfortunately, they relied too heavily on those scripts, which Microsoft had subsequently revised. The initial tests showed the server had not been compromised, but the followup tests using the revised scripts revealed that the server had, in fact, been taken over. While it was a useful exercise to run the “have I been compromised” scripts, it also serves as a cautionary tale that organizations should not rely on a test script alone to give themselves peace of mind.
Sophos also learned a valuable lesson in dealing with these attackers: It pays dividends to recognize the hallmarks of an active attack, even if the attackers are using tooling you’re unfamiliar with. Detecting the launch of Cobalt Strike in memory is just one such hallmark, and helped convince the customer that a serious (potentially very costly) attack was actively underway even though we didn’t observe many of the other common indicators of an attack, such as widespread use of RDP over a prolonged period of time, which would have appeared in log entries.
Detections and indicators of compromise
Sophos detects the payloads involved in this attack and others like it as Mem/Meter-A, Troj/PSDrop-CV, AMSI/Cobalt-E, or Troj/PS-FX. SophosLabs has published indicators of compromise relating to this attack to our Github page.
SophosLabs wishes to thank Peter Mackenzie, Vikas Singh, Gabor Szappanos, and the Rapid Response team for their help protecting this customer and producing the research that underlies this report.