ToolShell: The Zombie SharePoint RCE That Wouldn't Die
Jan 31, 2026·5 min read·6 visits
Executive Summary (TL;DR)
A critical RCE in SharePoint Server caused by unsafe deserialization in `ToolPane.aspx`. It bypasses a previous fix for CVE-2025-49704. Attackers send a crafted XML payload to execute code as the service account. Active in the wild (ransomware). Requires patching AND running the configuration wizard.
CVE-2025-53770, affectionately dubbed 'ToolShell', is a critical remote code execution vulnerability in Microsoft SharePoint Server. It represents a catastrophic failure of a previous patch (CVE-2025-49704), proving once again that blocklists in deserialization logic are about as effective as a screen door on a submarine. By abusing the `ToolPane.aspx` endpoint and `System.Data.DataSet` deserialization, unauthenticated attackers can gain SYSTEM-level access to the server, often chaining it with a trivial authentication bypass.
The Hook: Welcome to the ToolPane
SharePoint is essentially a massive, enterprise-grade ball of spaghetti code held together by .NET legacy features and prayers. One of those legacy features is the ToolPane, a component designed to help administrators configure web parts. It resides at /_layouts/15/ToolPane.aspx.
Normally, you'd expect something administrative like this to be locked down tighter than Fort Knox. However, in the chaotic world of SharePoint legacy routing, that's not always the case.
This specific endpoint accepts a parameter called MSOTlPn_DWP. If you're a developer, that name probably looks like a random collision of characters, but to a hacker, it looks like an input vector. This parameter is designed to take a serialized configuration—specifically, a System.Data.DataSet. And if you know anything about .NET security history, hearing "DataSet" and "User Input" in the same sentence should make the hair on the back of your neck stand up.
The Flaw: A Failed Exorcism
To understand CVE-2025-53770, we have to look at its predecessor, CVE-2025-49704. Microsoft attempted to fix a deserialization flaw by implementing a Type Filter (a blocklist). They tried to tell the DataSet parser: "Do not load these specific dangerous types."
Here is the problem with blocklists: they require the defender to know every possible way to instantiate a malicious object. The attackers at Viettel Cyber Security (who demoed this at Pwn2Own Berlin) found a loophole.
The DataSet XML schema allows an attribute called msdata:DataType. This attribute tells the parser, "Hey, this column isn't just a string; it's actually this complex .NET type."
By specifying a complex type that wasn't on the blocklist—specifically a generic list containing a LosFormatter—the attackers could trick the parser. When the DataSet is processed, it inadvertently instantiates the LosFormatter. This formatter is then helpful enough to deserialize a base64 string provided in the XML data (the DiffGram). It's a nested deserialization attack: a Trojan Horse inside a Trojan Horse.
The Code: XML Alchemy
Let's look at the mechanics of the bypass. The vulnerable code handles the MSOTlPn_DWP parameter. The patch for the previous CVE blocked direct instantiation of gadgets, but failed to sanitize nested types definitions in the schema.
Here is a simplified view of the XML structure attackers use to trigger the behavior:
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xs:element name="ExploitSet">
<xs:complexType>
<xs:choice>
<xs:element name="PayloadTable">
<xs:complexType>
<xs:sequence>
<!-- The Magic Bypass -->
<xs:element name="EvilColumn"
msdata:DataType="System.Collections.Generic.List`1[[System.Web.UI.LosFormatter, System.Web, Version=4.0.0.0, ...]]"
type="xs:anyType" />
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:choice>
</xs:complexType>
</xs:element>
</xs:schema>When DataSet.ReadXml() hits this schema, it sees EvilColumn needs to be a List<LosFormatter>. It instantiates LosFormatter. Later in the XML (the data section), the attacker provides the serialized payload. The LosFormatter tries to convert that data into the List, triggering the Deserialize method. Boom. Game over.
The Exploit: Chaining for Glory
RCE is great, but unauthenticated RCE is the holy grail. The ToolPane.aspx endpoint usually requires authentication. However, attackers chained this with a hilarious auth bypass (CVE-2025-49706 or variants).
Step 1: The Doorman Trick
SharePoint has a quirk where referencing the SignOut.aspx page in the Referer header makes the server lower its guard for certain requests. It assumes you are in the process of signing out and might need to access resources anonymously to finish the cleanup.
Step 2: The Attack
- Target:
POST /_layouts/15/ToolPane.aspx - Headers:
Referer: https://target/_layouts/SignOut.aspxContent-Type: application/x-www-form-urlencoded
- Body:
MSOTlPn_DWP=[GZipped Base64 Payload]DisplayMode=Edit
The payload contains the XML schema described above, wrapping a standard .NET gadget chain (like TypeConfuseDelegate) that executes cmd.exe /c powershell ....
Since SharePoint runs as w3wp.exe (often with excessive privileges), the attacker now owns the box.
The Impact: The MachineKey Heist
This isn't just about popping calc.exe. In the wild, we are seeing attackers do something very specific and very dangerous: MachineKey Theft.
Once they have code execution, they immediately run a PowerShell script to dump the ASP.NET Machine Keys:
[System.Web.Configuration.MachineKeySection]::GetApplicationConfig()Why does this matter? The MachineKey is the cryptographic heart of an ASP.NET application. It signs and encrypts ViewState and authentication cookies. If an attacker steals this key, patching the RCE vulnerability does not kick them out.
They can simply forge their own authentication cookies (creating a "Golden Ticket") and log in as the SharePoint Administrator at will, forever. They don't need to exploit the bug again; they effectively have a master key to the front door.
The Fix: Don't Just Click 'Next'
Microsoft released a patch, but this is where many admins will fail. SharePoint patching is notoriously multi-step.
1. Install the Update: Apply the July 2025 security update. This updates the binaries on the disk.
2. Run the Wizard (CRITICAL): You MUST run the SharePoint Products Configuration Wizard (psconfig.exe) after the binary installation. If you don't, the database schema and internal configurations might not update, leaving the deserialization path open.
3. Rotate the Keys: Because this vulnerability was exploited in the wild, you must assume your Machine Keys were compromised. You need to generate new ASP.NET Machine Keys and update the web.config on all SharePoint servers in the farm. If you skip this, the attackers might still be in your walls.
Official Patches
Technical Appendix
CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:HAffected Systems
Affected Versions Detail
| Product | Affected Versions | Fixed Version |
|---|---|---|
SharePoint Server Subscription Edition Microsoft | < 16.0.18526.20508 | 16.0.18526.20508 |
SharePoint Server 2019 Microsoft | < 16.0.10417.20037 | 16.0.10417.20037 |
SharePoint Enterprise Server 2016 Microsoft | < 16.0.5513.1001 | 16.0.5513.1001 |
| Attribute | Detail |
|---|---|
| CWE | CWE-502: Deserialization of Untrusted Data |
| CVSS | 9.8 (Critical) |
| Attack Vector | Network (HTTP POST) |
| Privileges Required | None (with Auth Bypass) |
| EPSS Score | 0.90947 |
| KEV Status | Active Exploitation (Ransomware) |
MITRE ATT&CK Mapping
Vulnerability Timeline
Subscribe to updates
Get the latest CVE analysis reports delivered to your inbox.