← All posts

Group Policy Preferences cpassword: The AES Key Microsoft Published, and Why It Still Leaks Admin Passwords

Old GPP drive-map and local-account XML files still hide AES-encrypted passwords anyone can decrypt with a key Microsoft published. Here is how to find and kill them.

Group Policy Preferences (GPP) shipped with Windows Server 2008 and gave admins something they had wanted for years: a point-and-click way to map drives, create scheduled tasks, and — fatefully — set local account passwords across an entire domain. The convenience came with a design flaw that has never fully gone away. When you stored a password in a GPP item, it was encrypted with AES-256 and written into an XML file in SYSVOL. That sounds fine until you learn that Microsoft published the AES key in its own MSDN documentation. Anyone with a domain account — which is to say, any authenticated user, and therefore any attacker who has phished a single mailbox — can read that XML and decrypt the password in seconds.

Microsoft patched the feature in MS14-025 (2014) so you can no longer create new password-bearing GPP items. What the patch did not do is remove the XML files that already exist. Twelve years later, those files are still sitting in SYSVOL on a huge number of domains, quietly handing out local administrator and service account credentials to anyone who looks.

Why this is still a live problem in 2026

Three things keep GPP cpassword relevant long after the patch:

What the vulnerable files look like

The password lives in a cpassword attribute inside one of a handful of GPP XML files. The usual suspects are Groups.xml, Services.xml, ScheduledTasks.xml, DataSources.xml, Printers.xml, and Drives.xml. A vulnerable entry looks like this:

<Groups clsid="{...}">
  <User name="Administrator (built-in)"
        image="2" changed="2013-04-11 03:20:15"
        uid="{...}">
    <Properties action="U" newName=""
        fullName="" description=""
        cpassword="j1Uyj3Vx8TY9LtLZil2uAuZkFQA/4latT76ZwgdHdhw"
        changeLogon="0" ... />
  </User>
</Groups>

That cpassword string is not a hash — it is reversible ciphertext. Tooling that decrypts it (Get-GPPPassword, gpp-decrypt, and countless one-liners) has been in every red team's pocket for a decade.

Finding it yourself before an attacker does

You do not need offensive tooling to audit for this. Any domain-joined machine can grep the replicated policy tree. From an elevated PowerShell prompt:

Get-ChildItem "\\$env:USERDNSDOMAIN\SYSVOL" -Recurse -Include `
  Groups.xml,Services.xml,ScheduledTasks.xml,DataSources.xml, `
  Printers.xml,Drives.xml -ErrorAction SilentlyContinue |
  Select-String -Pattern 'cpassword' |
  Select-Object Path, LineNumber

Any hit is a finding. There is no such thing as an acceptable cpassword value — the encryption is worthless, so treat every match as an exposed plaintext credential.

Remediation, in the right order

The instinct is to delete the XML files. Do that, but do it as the last step, because the password in them is almost certainly still valid on live machines. Work in this order:

  1. Rotate the exposed credential first. Assume every password in a discovered cpassword is already known to an adversary. Change the local admin / service account password everywhere it was deployed before you remove the evidence, or you will just leave a still-valid credential lying around in backups and replication history.
  2. Delete the offending GPP items from the Group Policy Management Console, then confirm the XML files are gone from SYSVOL after replication.
  3. Replace the whole pattern with LAPS. Windows LAPS gives every machine a unique, automatically rotated local admin password stored in a protected AD attribute — the correct answer to the problem GPP was misused to solve. See our companion piece on LAPS and local admin password rotation.
  4. Ensure MS14-025 is applied on all machines that author policy, so no one can recreate a password-bearing GPP item by accident.
Rotate, then delete, then replace with LAPS. Deleting first just hides a credential that still works.

How WinSentinel catches this

GPP cpassword is exactly the kind of finding that hides in plain sight: it is not a running process, not an open port, and not something a signature-based scanner flags. It is a static artifact that requires you to know where to look. WinSentinel's credential-exposure auditing walks the reachable policy and configuration surface for this class of leaked secret and reports the exact file and account, alongside the rest of its 33 audit modules — all running free, with no limits, on any single machine. There is no dashboard to babysit; the agent does the hunting and hands you the remediation.

For organizations, the risk is not one machine — it is that a single leaked GPP password unlocks local admin across the entire estate. WinSentinel Pro rolls these findings up across the fleet from a central node, so you can see every host still carrying a vulnerable SYSVOL artifact, track remediation as passwords are rotated, and get drift alerts if a legacy policy file reappears after a migration. Whether you run one workstation or a hundred servers, the fix is the same three steps — WinSentinel just makes sure you never miss one of them.