Hunting Down MS Exchange Attacks. Part 2 (CVE-2020–0688, CVE-2020–16875, CVE-2021–24085)
The article written by Anton Medvedev, reviewed by Vadim Khrykov
Our previous article focused on the different techniques used to detect ProxyLogon exploitation. This time we will talk about the techniques used to detect other notorious MS Exchange Server vulnerabilities, namely CVE-2020–0688, CVE-2020–16875 and CVE-2021–24085.
Although these vulnerabilities are not as recent as ProxyLogon, we continue to find signs of their exploitation (including successful exploitation). The sooner an exploitation attempt is detected, the more likely it is to minimise or avoid the impact of the attack on the organisation.
Logs and Useful Events
We will use the previously mentioned MS Exchange and Windows logs as event sources.
Detecting Exploitation of CVE-2020–0688
The CVE-2020–0688 vulnerability is contained in the Exchange Control Panel (ECP) component and is related to the the server being unable to properly create unique cryptographic keys because the keys are not randomly generated but are preset with identical values. If we examine the content of the ECP settings in the web.config
file from C:\Program Files\Microsoft\Exchange Server\<Version Number>\ClientAccess\ecp
, we see that the validationKey
and decryptionKey
values are already set. These keys are used to secure the ViewState
parameter.
One of the articles on the Microsoft website describes the ViewState
parameter as follows:
On the ASP.NET pages View State presents the state of the page when it was last processed on the server. This parameter is used to create a call context and store values in two consecutive requests for the same page. By default, the state is saved on the client using a hidden field added to the page and restored on the server before the page request is processed. View State moves back and forth with the page itself, but does not represent or contain any information relating to the display of the page on the client side.
As such, pre-shared keys allow an authenticated user to send a deliberate ViewState
parameter to the ECP application, which when deserialised will cause malicious code to be executed on the Exchange server in the context of System.
The ysoserial
utility which exploits insecure deserialisation in .NET applications can help us create a malicious object.
Below is an example of ViewState
generation, its payload in turn runs whoami
.
The validationkey
and generator
parameters, as described earlier, are preset and cannot be changed. The viewstateuserkey
value must be taken from the ASP.NET_SessionId
value of the user authorised on the ECP service.
Once the ViewState
has been generated, a request is sent to the vulnerable ECP service, resulting in the server returning an error code 500.
If you run the request through the BurpSuite
utility, you can see in the ViewState
decoder that the payload is passed in the <System> tag along with other user parameters:
If the vulnerability is successfully exploited, the w3wp.exe
process responsible for the ECP (MSExchangeECPAppPool) will execute the payload transferred in the ViewState
parameter. Below is the correlation rule to detect cmd.exe
commands or the PowerShell interpreter being executed by a w3wp.exe
web server process:
event_log_source:'Security' AND event_id:'4688' AND proc_parent_file_path end with:'\w3wp.exe' AND proc_file_path end with:('\cmd.exe' OR '\powershell.exe')
The IIS access logs contain a request for the URL /ecp/default.aspx
to which the server responded with status 500 (internal server error). Below is the rule for detecting the exploitation of CVE-2020-0688 using IIS events:
event_log_source:’IIS’ AND http_method=’GET’ AND http_status_code=’500’ AND url_path=’/ecp/default.aspx’ AND url_query contains ‘__VIEWSTATEGENERATOR’ AND hurl _query contains ‘__VIEWSTATE’
The Application log contains an event which indicates an error in the MSExchange Control Panel application with Event ID = 4.
Below is the rule for detecting CVE-2020–0688 exploitation using Application log events:
event_log_source:’Application’ AND event_id=’4’ AND (Message contains ‘__VIEWSTATE’)
Detecting Exploitation of CVE-2020–16875
Successful exploitation of the CVE-2020–16875 vulnerability allows an attacker to execute arbitrary code on the Exchange server in the context of the System user. The attacker can then escalate their domain privileges and compromise the entire company network.
Successful authentication requires a domain account from a corporate mailbox that is a member of a group with Data Loss Prevention (DLP) privileges. The exploitation itself is done through the DLP component. DLP is configured through the ECP interface. The DLP engine allows you to filter mail flow according to predefined patterns and rules for content analysis of emails and attachments.
Since we already know that in order for the exploit to succeed, the attacker must be a member of the DLP group, a rule can be implemented to create a new group with the Data Loss Prevention
role, and a new user can be added to that group. This can be done from either the ECP interface or from the Exchange Management Shell using the following commands:
New-RoleGroup -Name "dlp users" -Roles "Data Loss Prevention" -Members "user1"
(create group dlp users with roleData Loss Prevention
and add user1 to the group);Update-RoleGroupMember -Members "dadmin" -identity "dlp users"
(add dadmin to group dlp users).
The screenshot below shows the event of adding the user dadmin to the group using the ECP interface. This activity can also be traced back to PowerShell audit events (Event ID 800 and 4104).
The new Data Loss Prevention
creation event can be dected in PowerShell and MSExchange Management log events using the following rule:
Use the rule below to track down events of Data Loss Prevention rights being issued using PowerShell audit events and MSExchange Management logs:
event_log_source:('PowershellAudit' OR 'MSExchange Management') AND event_id:('1' OR ’800’ OR '4104') AND ((Message contains ‘New-RoleGroup’ AND Message contains ‘Data Loss Prevention’) OR (Message contains ‘Update-RoleGroupMember’ AND Message contains ‘<Group with DLP rights>’ AND Message contains '-Members'))
The exploit for this vulnerability performs the following steps in sequence:
- Authenticate under a given account to retrieve a session through OWA.
- Obtain the
ViewState
parameter by accessing the DLP policy management functionality. - Add a new malicious DLP policy that contains an executable command that runs from PowerShell.
Let’s run the utility and see what the Exchange events look like. Below you can see that the exploit run under the dadmin account was successful.
The access logs of ECP contain an event of a new DLP policy being successfully added:
2021-03-09 12:03:31 10.3.132.20 POST /ecp/DLPPolicy/ManagePolicyFromISV.aspx ActID=3b6c5adc-c7d0-4aeb-82ec-711c2257ece6 444 LAB\dadmin 192.168.1.20 python-requests/2.22.0 - 200 0 0 863
The rule to create a new DLP policy using IIS events:
event_log_source:’IIS’ AND http_method=’POST’ AND http_code='200' AND url_path='/ecp/DLPPolicy/ManagePolicyFromISV.aspx'
To exploit the vulnerability, we have to create a new policy, this will come up in the MSExchange Management log as a new event with a random name that contains a malicious payload in the TemplateData
parameter:
The creation of a new DLP policy can be dected in PowerShell and MSExchange Management log events using the following rule:
event_log_source:('PowershellAudit' OR 'MSExchange Management') AND event_id:('1' OR ’800’ OR '4104') AND (Message contains ‘New-DlpPolicy’ AND Message contains '-TemplateData')
The exploition of this vulnerability launches Notepad. Looking at the process start events in the Security log, we see that the Notepad
process is initiated by the parent process w3wp.exe
with System privileges.
Use the rules above to detect a successful exploitation of the CVE-2020–16875 vulnerability:
event_log_source:'Security' AND event_id:'4688' AND proc_parent_file_path end with:'\w3wp.exe' AND proc_file_path end with:('\cmd.exe' OR '\powershell.exe')
Another variant of the PowerShell exploit has similar logic and performs the following actions:
- It creates a remote PowerShell session using the PowerShell component of the Exchange server. The account attempting the connection must have the
Data Loss Prevention
role.
2. It creates a new policy using the New-DlpPolicy
commandlet. The payload is stored in the variable $xml:
Below is the result of running the PowerShell exploit, successfully connecting as user1 with no privileges and running the whoami
command with System privileges.
IIS events show the creation of a remote session:
2021-03-09 13:47:04 10.3.132.20 POST /powershell serializationLevel=Full;ExchClientVer=15.1.1591.10;clientApplication=ManagementShell;TargetServer=;PSVersion=5.1.14393.693&sessionID=Version_15.1_(Build_1590.10)=rJqNiZqNgZqHnJeekZia0bO+vdGzsLy+s4HOxsvNz8nNycvIgc3Pzc7Sz8zSz8arzszFysvFz8s= 444 lab\dadmin 192.168.1.20 Microsoft+WinRM+Client - 500 687 0 180002
The rule that detects this activity is as follows:
event_log_source:’IIS’ AND http_method=’POST’ AND url_path='/powershell' AND (Message contains ‘serializationLevel=Full AND Message contains 'clientApplication=ManagementShell') AND user_agent='Microsoft+WinRM+Client'
The Security log detects a successful start of the whoami process with w3wp.exe
as the parent process. Execution of the New-DlpPolicy
command can be detected in the PowerShell audit log using one of the previously mentioned rules.
Detecting Exploitation of CVE-2021–24085
The process for exploiting CVE-2021–24085 is more complex. The following steps are required to execute the attack successfully:
- Compromise an arbitrary domain account that has a mailbox.
- Use the ECP interface to export the certificate.
- Using the certificate obtained, generate a CSRF token, aka the
msExchEcpCanary
parameter. - Get the Exchange administrator to go to the attacker’s malicious page, which will send a request to the Exchange server with the preset token value on behalf of the administrator.
A successful exploitation would allow the attacker to escalate their privileges to Exchange administrator.
A GitHub project can be used to implement the attack, where the poc.py
file is responsible for obtaining the certificate that will be used to generate the CSRF token.
YellowCanary — a project coded in C# that is responsible for generating the token.
Poc.js — the JavaScript payload placed by the attacker on a monitored web server designed to lure the Exchange administrator.
The screenshot below shows that the poc.py
script has successfully exported the certificate to the testcert.der
file.
An ECP access-log event that contains traces of a certificate being saved:
2021-03-09 15:52:55 10.3.132.20 POST /ecp/DDI/DDIService.svc/SetObject schema=ExportCertificate&msExchEcpCanary=yylkJJJocUWa3HVCEcQli7B3FcF--tgI2nbpJpHLcFZ60E9sZ2gmDpi_sFqf3jl9YcG9qcRMzek.&ActID=cf99b7d2-4eac-4435-a041-f0adaa44ed94 444 LAB\dadmin 192.168.1.20 python-requests/2.22.0 - 200 0 0 500
The certificate is saved in the Exchange server file system — in the poc.png
file located in the IIS directory and then downloaded successfully using the same poc.py
script.
Certificate download event:
2021-03-09 15:52:55 10.3.132.20 GET /ecp/poc.png - 444 LAB\EXCHANGE$ 192.168.1.20 python-requests/2.22.0 - 200 0 0 7
In this way, we can implement a rule that detects the event of a certificate export in the IIS access logs:
event_log_source:’IIS’ AND http_method=’POST’ AND http_code='200' AND url_path='/ecp/DDI/DDIService.svc/SetObject' AND (Message contains 'schema=ExportCertificate')
Once the certificate is obtained, the attacker uses the YellowCanary
utility to generate the msExchEcpCanary
parameter needed to implement the CSRF attack. The first parameter is the SID of the user on whose behalf we want to perform an action on the ECP:
The attacker must then trick a privileged user (ideally an Exchange administrator) into clicking on a prepared link containing the malicious JavaScript code. This code can send requests to the ECP on behalf of the administrator. This could, for example, be used to exploit the CVE-2021–27065 vulnerability, which we covered in the previous article. As a result, the attacker would gain access to the Exchange server with System privileges via the downloaded web shell.
In addition to the above technique, this attack can be performed by adding a malicious MS Outlook add-in, an application that provides users with advanced capabilities.
There are three ways to add an Outlook add-in:
- Add via the URL where the add-in is located.
- Download from the Office Store.
- Download a new add-in from file.
The add-in is an XML format configuration file. An attacker can create a malicious config that will, for example, forward the contents of client emails to an attacker’s controlled server. The /ecp/Handlers/UploadHandler.ashx
interface is used to upload the config file.
Below is a snippet of the JavaScript code that will be executed by the Exchange administrator after being redirected to the attacker’s website. This code fetches the content of the malicious evil.xml
add-in, which is also located on the attacker's website, and sends it with a POST request to /ecp/Handlers/UploadHandler.ashx
. The msExchEcpCanary
parameter contains the CSRF token that was generated in the previous step. It is also worth keeping in mind that when the administrator accesses the attacker's website, their ECP session must still be active.
The following rule can be used to detect the loading of an add-in:
event_log_source:’IIS’ AND http_method=’POST’ AND http_code='200' AND url_path='/ecp/Handlers/UploadHandler.ashx'
Conclusion
The vulnerabilities discussed in this article are still being exploited today. Most of the time they are unsuccessful, but there are exceptions. Collecting significant security events and implementing detection rules will allow you to react to a possible attack in time to eliminate the fallout from the incident at an early stage.
In the next article, we will talk about Windows domain privilege escalation vectors through the MS Exchange server and how to detect them.