Cause 1: Print Driver Bloat (Most Common)
The print spooler service (spoolsv.exe) is a 32-bit process on most Windows print servers, and it has a hard limit on how many DLLs a single process can load — roughly 2,000 on x86, and while 64-bit is higher, drivers still eat into the address space fast. When you install a dozen driver packages from different vendors, each one drops its own DLLs, language monitors, and port monitors into the spooler. Hit the ceiling and Windows throws ERROR_TOO_MANY_MODULES at you. I walked into a client's site last month where the print server had 34 queues, all pointing to the same HP LaserJet model, but each had its own copy of the driver. The spooler would crash every Monday morning when everyone printed their weekly reports.
Here's the fix:
- Open Print Management (
printmanagement.msc) on the server. - Click Print Servers > your server > Drivers.
- Look for duplicate drivers. Same model, different versions — that's your culprit.
- Right-click each duplicate and choose Remove Driver Package. Check "Remove driver package" and "Delete the driver package from the driver store."
- Reboot the spooler:
net stop spooler
net start spooler
After clearing duplicates, my client's server went from 34 loaded driver packages down to 6. Spooler stopped crashing that same day.
Cause 2: Too Many Printer Drivers from Different Vendors
Vendor drivers don't play well together. You've got HP's hpmui.dll, Canon's cnmpu*.dll, Brother's br*.dll, and a random Zebra label driver someone installed for a shipping label printer. Each vendor ships its own language monitor and port monitor, and they all load into the spooler address space. Windows doesn't unload them when you remove a printer — you have to remove the driver package itself.
The real fix is to stop installing vendor drivers when a Microsoft inbox driver will work. For basic LaserJet and inkjet printing, the Microsoft IPP Class Driver or the PCL6 universal driver handles 90% of cases. It's smaller, signed, and doesn't spawn a dozen helper DLLs.
To check what's actually loaded:
tasklist /m /fi "imagename eq spoolsv.exe"
That lists every DLL loaded into the spooler. If you see 200+ entries and half are vendor-specific, you've found the problem. Trim aggressively. Also, uninstall any printer software via Programs and Features — the vendor's "utility suite" is often what installs extra language monitors that never go away.
Cause 3: Language Monitor and Port Monitor Leakage
This one is sneakier. Some software — particularly old print management tools, PDF printer utilities, and fax software — registers a language monitor or port monitor that loads a DLL into the spooler every time a job prints. Over days or weeks, the spooler accumulates hundreds of module handles. You won't see it in Task Manager because the DLLs stack up inside the process without appearing as separate processes.
Check the registry here:
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Print\Monitors
Every subkey is a monitor. Most Windows installs have 3-5 default ones. If you've got 20+, you've got leakage. Remove the ones you don't recognize — but export the key first, because a bad removal can break printing entirely.
For stubborn cases, restart the spooler on a schedule. It's a band-aid, not a fix, but if you can't isolate the offending software right away, a nightly restart at 2 AM keeps things alive until you do:
schtasks /create /tn "Restart Spooler" /tr "cmd /c net stop spooler & net start spooler" /sc daily /st 02:00 /ru SYSTEM
Had a law firm where a legacy document management system was leaking port monitors every time someone printed to PDF. Spooler would crash every 4-5 days. Scheduled restart bought them six months until they migrated off the software.
Quick Reference: ERROR_TOO_MANY_MODULES (0X000000D6)
| Cause | Symptom | Fix |
|---|---|---|
| Duplicate driver packages | Same printer model, multiple driver versions | Remove duplicates in Print Management |
| Multiple vendor drivers | 200+ DLLs in spoolsv.exe | Switch to Microsoft inbox/universal drivers |
| Language/port monitor leak | Registry has 20+ monitor keys | Remove unknown monitors, or schedule spooler restart |
If you've done all three and still get 0X000000D6, it's time to look at whether you're running a 32-bit print server in 2024. Move to 64-bit Windows Server — the address space is larger and the module limit is higher. That's not a fix, that's overdue maintenance, but it works.