All vulnerabilities
CVE-2026-107219GHSA-jrfj-fhj2-jjvm

github.com/xuri/excelize/v2: Excelize: Unbounded spinCount in agile decryption burns CPU during OpenFile

qax-os github.com/xuri/excelize/v2goLibraries & packages
CVSS
7.5High
ExploitationNo known exploitationNot in CISA KEV, which does not prove it is unexploitedCISA KEV
Exploit odds (EPSS)0.34%Chance of exploitation activity in the next 30 days, higher than 26% of CVEs. Scored 23 Oct 2026FIRST EPSS
Fixed in2.11.1-0.20260906004932-2badfcd5841dFixed versionGitHub
Published7 Oct 2026Updated 7 Oct 2026CVE List

What fixes it

  • 2.11.1-0.20260906004932-2badfcd5841dgithub.com/xuri/excelize/v2, goGitHubgo get github.com/xuri/excelize/v2@v2.11.1-0.20260906004932-2badfcd5841d
  • 2.11.1-0.20260906004932-2badfcd5841dgithub.com/xuri/excelize/v2, GoOSVgo get github.com/xuri/excelize/v2@v2.11.1-0.20260906004932-2badfcd5841d

A fixed version on one release line is not the upgrade target for every line. Check your exact version and any vendor backports.

Description

Opening a file whose first eight bytes are the OLE magic number sends excelize down the decryption path whether or not the caller set a password, or supports encrypted workbooks at all. openReaderAt (excelize.go:198-215) branches on the header alone, and agileDecrypt calls convertPasswdToKey before the verifier hash is checked, so the key-derivation loop runs spinCount times regardless.

spinCount (crypt.go:98) is a plain int filled by a bare xml.Unmarshal of the file's own EncryptionInfo stream. Nothing bounds it.

A 3072-byte file with spinCount 100000000 makes OpenFile take 58.65s on v2.11.0 with default options, then return zip: not a valid zip file. It is linear at about 0.6 microseconds per iteration and the attacker picks the number, so 1e9 is roughly ten minutes. Nothing on the path takes a context.Context, so the caller cannot cancel it; in an HTTP handler the write timeout returns a response while the goroutine keeps spinning. Memory stays flat at 24 MB, so nothing reclaims it either.

v2.5.0   spinCount=10000000   5.307s
v2.9.1   spinCount=10000000   5.444s
v2.11.0  spinCount=10000000   7.529s
v2.11.0  spinCount=100000000  58.654s

The loop arrived with crypt.go in v2.3.1 and is unchanged through v2.11.0.

Excel and LibreOffice write spinCount 100000, which costs 61ms here, so a ceiling well above the legitimate value would cost real files nothing.

This is availability only, and it is not a vulnerability for a program that only opens files its own operator produced.

Text from GitHub Advisory Database

Affected versions 3

  • github.com/xuri/excelize/v2, go>= 2.3.1, < 2.11.1-0.20260906004932-2badfcd5841dGitHub
  • excelizeaffected: >= 2.3.1, <= 2.11.0CVE List
  • github.com/xuri/excelize/v2, Gofrom 2.3.1, fixed in 2.11.1-0.20260906004932-2badfcd5841dOSV

References 4