XACT_E_INVALIDCOOKIE (0x8004D015) – Fix the Invalid Transaction Cookie
This error means your transaction cookie is stale or mismatched. It usually shows up in distributed transactions across SQL Server and MSDTC. Here's how to fix it fast.
1. Stale or Mismatched MSDTC Connection (Most Common)
This is the one that bites most people. When you're running a distributed transaction across two SQL Servers (or between a .NET app and SQL Server), the transaction manager hands out a cookie – a pointer to the transaction state. If something resets the connection or the MSDTC service restarts mid-transaction, that cookie turns into garbage. You'll see this error right after the transaction starts, or when you try to commit it.
Here's the fix: reset the MSDTC service on both machines involved in the transaction. Don't just restart it – do a full stop, clear the logs, then start it fresh.
- Open an admin Command Prompt or PowerShell.
- Type
net stop msdtcand hit Enter. Wait until you see "The Distributed Transaction Coordinator service was stopped successfully." - Now delete the MSDTC log files. Go to
C:\Windows\System32\MsDtc\and delete everything inside theLogfolder. You'll see files namedlog_*.log– delete them all. Don't worry, MSDTC re-creates them on startup. - Back in the admin prompt, type
net start msdtcand hit Enter. You should see "The Distributed Transaction Coordinator service is starting." Then "was started successfully." - Repeat these steps on every machine participating in the transaction – the app server and each SQL Server.
After you do this, test the transaction. If the error is gone, you're golden. If not, move to cause #2.
2. Firewall Blocking RPC and MSDTC Ports
MSDTC needs specific ports open between machines. If Windows Firewall or a third-party firewall blocks them, the transaction manager can't pass the cookie back to the requesting machine. The error shows up as XACT_E_INVALIDCOOKIE, but it's really a network handshake failure. You'll often see this when you're working across different subnets or if someone changed firewall rules recently.
Here's how to check and fix it:
- On each SQL Server, open Windows Firewall with Advanced Security.
- Look for an inbound rule named Distributed Transaction Coordinator (RPC-EpMapper). If it's disabled, enable it.
- If you don't have that rule, create three rules manually:
- Allow TCP port 135 (RPC Endpoint Mapper). This is the handshake port.
- Allow TCP port 5000-5100 (or whatever range MSDTC is configured to use – check
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\MSDTCfor the port range). By default, MSDTC uses dynamic ports, which is bad for firewalls. I recommend setting a static port range. - Allow UDP port 135 as well.
- Open Registry Editor on each machine. Go to
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\MSDTC. Create a DWORD namedServerTcpPortand set it to decimal5000(or your chosen port). Create another DWORD namedServerTcpPortRangeand set it to decimal100(this gives you ports 5000-5099). - Restart MSDTC as described in cause #1.
- Test the transaction again.
If the error still appears, move to cause #3.
3. DNS or NetBIOS Name Resolution Mismatch
This one's sneaky. The transaction cookie includes the machine name that started the transaction. If the machine name in the cookie doesn't match the name that the other machine uses to reach it (due to DNS aliases, secondary DNS suffixes, or hosts file entries), MSDTC rejects the cookie as invalid. You'll see the error sporadically – sometimes it works, sometimes it doesn't.
The quick fix: make sure all machines in the transaction use the same fully qualified domain name (FQDN) to identify each other. Here's what to do:
- On each SQL Server, run
SELECT @@SERVERNAME. Write down the exact name returned – it's usuallySERVERNAME\INSTANCENAME. - On the app server, open a command prompt and run
ping SERVERNAMEandping SERVERNAME.domain.com(where domain.com is your domain). Make sure both resolve to the same IP address. If they don't, you have a DNS problem. - Add an entry to the hosts file on the app server (
C:\Windows\System32\drivers\etc\hosts) that maps the short name to the correct IP. For example:192.168.1.10 SQLPROD01. This bypasses DNS and forces the correct name resolution. - Restart MSDTC on all machines again.
- Test the transaction.
I've seen this one drive teams crazy for days because it only fails under load or after a DNS change. The hosts file trick is your best card here.
Quick-Reference Summary Table
| Cause | Symptom | Fix |
|---|---|---|
| Stale MSDTC connection | Error right when transaction starts or commits | Stop MSDTC, delete log files, restart service |
| Firewall blocking ports | Error across subnets or after firewall change | Open TCP 135, set static MSDTC port range |
| DNS name mismatch | Sporadic failures, different ping results | Add hosts file entry, restart MSDTC |
These three causes cover about 95% of XACT_E_INVALIDCOOKIE occurrences. Start with the MSDTC restart and log deletion – it's the fastest test and fixes most cases. If that doesn't work, check the firewall and DNS. Don't waste time on other theories until you've ruled out these three.
Was this solution helpful?