Detection and Mitigation Advice for PrintNightmare

PrintNightmare(CVE-2021-34527) was released as a proof of concept this week on Github. This post highlights how the exploit PoCs released on Github work and how the specific vulnerability can be fixed and detected.

Introduction

PrintNightmare(CVE-2021-34527) was released as a proof of concept this week on Github. This post highlights how the exploit PoCs released on Github work and how the specific vulnerability can be fixed and detected. The vulnerability itself was found and published by Zhipeng Huo (@R3dF09), Piotr Madej, and Yunhai Zhang.

Caveat: All of the understanding in this post is pulled from the proofs of concept released and fixes/workarounds that have been tested in a lab. It is essential to try in your environment before pushing any advice straight to production.

What is PrintNightmare/CVE-2021-34527?

PrintNightmare/CVE-2021-34527 & CVE-2021-1675 are remote code execution bugs affecting the Windows printer spooler service. The bug exploits a misconfiguration in the spoolsv.exe service on windows servers. It enables an attacker with domain credentials to execute a malicious print driver DLL and achieve privilege escalation to SYSTEM on a domain controller or print server. Specifically, the bug works by adding a driver to the target domain controller via the RpcAddPrinterDriver syscall.

From an attacker perspective, as of 1st July 2021, several exploits have been published on GitHub, and it is more than likely that this bug will be exploited in the wild soon if it is not already.

Microsoft released a second CVE and allocated it to PrintNightmare specifically as CVE-2021-1675 was addressed in the June 8 2021 update however, CVE-2021-34527/PrintNightmare still has no patch at the time of writing, therefore, the mitigations below will help mitigate the risk of exploitation. The detections and advice work for both CVEs.

Mitigating the Issue

The patch released by Microsoft does not, unfortunately, fix the issue. Therefore a workaround fix can be applied by disabling the printer spooler service. Here’s how to do it on both GPO and PowerShell.

Currently, the fix for the issue is to disable the print spooler service; however, in a production environment, this is not always practical as it can break many things, such as printing across the organization and converting documents to PDF. There are several workarounds we have written up and published to our detection repository and detailed below:

GPO

The following GPO can be set to deny client connections to the spooler, a potential workaround where disabling the spooler service altogether might not be an option. This has been tested against domain controllers and endpoints(W7/W10) in a lab environment and users can still add/remove printers and print however, it stops the exploit from working.

Computer Configuration -> Administrative Templates -> Printers -> Allow Print Spooler to accept client connections
set this to Disabled:

Then restart the spooler service on the host; this will deny the exploit from working.

Removal of Authenticated Users from Pre-Windows 2000 Compatible Access

The Pre-Windows 2000 Compatible Access group is legacy and following good practices to remove legacy groups’ access from your environment is always good to do. Specifically the Pre-Windows 2000 Compatible Access group was created to allow Windows NT domains to interoperate with active directory domains by allowing unauthenticated access to specific AD data. The default permissions on many AD objects are set to allow access to the Pre-Windows 2000 Compatible Access group. When the ‘Authenticated Users’ are members of the Pre-Windows 2000 Compatible Access group, any authenticated user can access many AD objects. Thus, in printnightmare it grants the authenticated users an elevated token in some contexts.

Therefore ensure the "Authenticated Users" groups are not members of the "Pre-Windows 2000 Compatible Access group" As shown in the screenshot below, there should be no members:

Example of no members:

If in doubt as to how to do this, the following steps can be taken:

  1. Open "Active Directory Users and Computers" (available from various menus or run "dsa.msc").
  2. Expand the domain being reviewed in the left pane and select the "Builtin" container.
  3. Double-click on the "Pre-Windows 2000 Compatible Access" group in the right pane.
  4. Select the "Members" tab.
  5. If the "Authenticated Users" group is a member, select each and click "Remove".

Defending Against It

Where fixing the issue may not be possible, an organization may shift to accept the risk and detect and respond to exploitation attempts. In this instance, the following tools and techniques can be leveraged.

Caveat: From a detection standpoint, these rules may be circumvented and are based on the current exploits available at the time of writing.

  • Splunk
  • Zeek
  • Sysmon

Splunk

There are two Splunk queries that can be used to help search for exploitation in your environment. The first will query the spoolsv.exe for any loaded images and target file names.

index=sysmon Image="C:\\Windows\\System32\\spoolsv.exe" 
| stats values(ImageLoaded),values(TargetObject),values(Details),values(TargetFilename)

A generic way to hunt for Print Spooler exploitation is looking for error generated by print spooler due to loading of the payload DLL. This can be done either through looking for spawning of WerFault.exe by spoolsv.exe or generation of Event ID 7031 showing unexpected termination of print spooler service:

((index=sysmon EventCode=1 
ParentImage="C:\\Windows\\System32\\spoolsv.exe" Image="C:\\Windows\\System32\\WerFault.exe") 
OR (index=windows Channel=System EventCode=7031 
Message="The Print Spooler service terminated unexpectedly"))

KQL Query for Sentinel / MDE

Olaf Hartong has supplied a handy KQL query for Microsoft Sentinel:

let serverlist=DeviceInfo
| where DeviceType != "Workstation"
| distinct DeviceId;
let suspiciousdrivers=DeviceImageLoadEvents
| where DeviceId in (serverlist)
| where FolderPath startswith @"c:\windows\system32\spool\drivers"
| distinct SHA1
| invoke FileProfile(SHA1, 1000) 
| where GlobalPrevalence < 50 and IsRootSignerMicrosoft != 1 and SignatureState != "SignedValid";
suspiciousdrivers
| join kind=inner (DeviceImageLoadEvents
| where DeviceId in (serverlist)
| where FolderPath startswith @"c:\windows\system32\spool\drivers") on SHA1
| where InitiatingProcessFileName != "ccmexec.exe"

Zeek

Zeek can be used to look for specific fields, the following screenshots show an example file transfer and NTLM authentication from an Attacker machine.

File transfer of DLL:

NTLM Authentication from "Attacking" Machine:

Sysmon

The provided Sysmon configuration CVE-2021-1675.xml file can be installed with Sysmon Config Pusher: https://github.com/LaresLLC/SysmonConfigPusher.

For more information on Sysmon pusher, check out our blog post about it here.

Conclusion

The advice above will help you apply the necessary mitigations to your network and help alleviate exploit attempts in the interim between Microsoft releasing an updated patch and the proofs of concept being available in the wild.

Special thanks to Anton Ovrutsky, who helped with a large proportion of the defensive engineering screenshots and worked on SIEM queries, blue team input and the creation of Sysmon Config Pusher.

References

Twitter Posts where information was referenced from: