Every CVE Search/ Get API key

CVE-2026-41673

xmldom: Denial of service via uncontrolled recursion in XML serialization

8.7 HighFix available

xmldom is a pure JavaScript W3C standard-based (XML DOM Level 2 Core) DOMParser and XMLSerializer module. In @xmldom/xmldom prior to versions 0.9.10 and 0.8.13 and xmldom version 0.6.0 and prior, seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application. This issue has been patched in versions @xmldom/xmldom versions 0.9.10 and 0.8.13.

Attack profile

How easy it is to exploit

Attack vector
Network
Complexity
Low
Privileges needed
None
User interaction
None

What an attacker can affect

Confidentiality
None
Integrity
None
Availability
High

Exploit likelihood

0.64%Up 0.6 points since May 7, 2026
90%50%10%1%

What each source reports

CVE List Score used 8.7

xmldom: Denial of service via uncontrolled recursion in XML serialization

xmldom is a pure JavaScript W3C standard-based (XML DOM Level 2 Core) DOMParser and XMLSerializer module. In @xmldom/xmldom prior to versions 0.9.10 and 0.8.13 and xmldom version 0.6.0 and prior, seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application. This issue has been patched in versions @xmldom/xmldom versions 0.9.10 and 0.8.13.

Record
CVE-2026-41673
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N
CVSS 3.1
7.5 HighCVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H
Weakness
CWE-674, CWE-776
Updated
2026-11-02
EUVDEUVD-2026-28288 8.7

xmldom is a pure JavaScript W3C standard-based (XML DOM Level 2 Core) DOMParser and XMLSerializer module. In @xmldom/xmldom prior to versions 0.9.10 and 0.8.13 and xmldom version 0.6.0 and prior, seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application. This issue has been patched in versions @xmldom/xmldom versions 0.9.10 and 0.8.13.

Record
EUVD-2026-28288
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N
Updated
2026-11-02
GitHub AdvisoriesGHSA-2v35-w6hq-6mfw 8.7

xmldom: Uncontrolled recursion in XML serialization leads to DoS

Summary

Seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application.

Reported operations:

  • Node.prototype.normalize() — reported by @praveen-kv (email 2026-04-05) and @KarimTantawey (GHSA-fwmp-8wwc-qhv6, via DOMParser.parseFromString())
  • XMLSerializer.serializeToString() — reported by @Jvr2022 (GHSA-2v35-w6hq-6mfw) and @KarimTantawey (GHSA-j2hf-fqwf-rrjf)

Additionally, discovered in research:

  • Element.getElementsByTagName() / getElementsByTagNameNS() / getElementsByClassName() / getElementById()
  • Node.cloneNode(true)
  • Document.importNode(node, true)
  • node.textContent (getter)
  • Node.isEqualNode(other)

All seven share the same root cause: pure-JavaScript recursive tree traversal with no depth guard. A single deeply nested document (parsed successfully) triggers any or all of these operations.


Details

Root cause

lib/dom.js implements DOM tree traversals as depth-first recursive functions. Each level of element nesting adds one JavaScript call frame. The JS engine's call stack is finite; once exhausted, a RangeError: Maximum call stack size exceeded is thrown. This error may not be caught reliably at stack-exhaustion depths because the catch handler itself requires stack frames to execute — especially in async scenarios, where an uncaught RangeError inside a callback or promise chain can crash the entire Node.js process.

Parsing a deeply nested document succeeds — the SAX parser in lib/sax.js is iterative. The crash occurs during subsequent operations on the parsed DOM.

Node.prototype.normalize() — reported by @praveen-kv

lib/dom.js:1296–1308 (main):

normalize: function () {
    var child = this.firstChild;
    while (child) {
        var next = child.nextSibling;
        if (next && next.nodeType == TEXT_NODE && child.nodeType == TEXT_NODE) {
            this.removeChild(next);
            child.appendData(next.data);
        } else {
            child.normalize();   // recursive call — no depth guard
            child = next;
        }
    }
},

Crash threshold (Node.js 18, default stack): ~10,000 levels.

XMLSerializer.serializeToString() — reported by @Jvr2022

lib/dom.js:2790–2974 (main): The internal serializeToString worker recurses into child nodes at four call sites, each passing a visibleNamespaces.slice() copy. The per-frame allocation causes earlier stack exhaustion than normalize().

Crash threshold (Node.js 18, default stack): ~5,000 levels.

Additional recursive entry points

All five crash at ~10,000 levels on Node.js 18.

| Function | Definition | Public API entry point(s) | Crash depth (Node.js 18) | |-----------------------------|----------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------------------------------------------|--------------------------| | _visitNode | lib/dom.js:1529 | getElementsByTagName(), getElementsByTagNameNS(), getElementsByClassName(), getElementById() | ~10,000 levels | | cloneNode (module fn) | lib/dom.js:3037 | Node.prototype.cloneNode(true) …

Record
GHSA-2v35-w6hq-6mfw
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N
Weakness
CWE-674
Updated
2026-11-02
NVD 8.7

xmldom is a pure JavaScript W3C standard-based (XML DOM Level 2 Core) DOMParser and XMLSerializer module. In @xmldom/xmldom prior to versions 0.9.10 and 0.8.13 and xmldom version 0.6.0 and prior, seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application. This issue has been patched in versions @xmldom/xmldom versions 0.9.10 and 0.8.13.

Record
CVE-2026-41673
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:X/U:X
CVSS 3.1
7.5 HighCVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H
Weakness
CWE-674, CWE-776
Updated
2026-11-02
OSV 8.7

xmldom: Denial of service via uncontrolled recursion in XML serialization

xmldom is a pure JavaScript W3C standard-based (XML DOM Level 2 Core) DOMParser and XMLSerializer module. In @xmldom/xmldom prior to versions 0.9.10 and 0.8.13 and xmldom version 0.6.0 and prior, seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application. This issue has been patched in versions @xmldom/xmldom versions 0.9.10 and 0.8.13.

Record
CVE-2026-41673
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N
Weakness
CWE-674
Updated
2026-11-02
OSVDEBIAN-CVE-2026-41673 8.7

xmldom is a pure JavaScript W3C standard-based (XML DOM Level 2 Core) DOMParser and XMLSerializer module. In @xmldom/xmldom prior to versions 0.9.10 and 0.8.13 and xmldom version 0.6.0 and prior, seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application. This issue has been patched in versions @xmldom/xmldom versions 0.9.10 and 0.8.13.

Record
DEBIAN-CVE-2026-41673
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:X/U:X
Updated
2026-11-02
Show 6 moreShow less
OSVGHSA-2v35-w6hq-6mfw 8.7

xmldom: Uncontrolled recursion in XML serialization leads to DoS

Summary

Seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application.

Reported operations:

  • Node.prototype.normalize() — reported by @praveen-kv (email 2026-04-05) and @KarimTantawey (GHSA-fwmp-8wwc-qhv6, via DOMParser.parseFromString())
  • XMLSerializer.serializeToString() — reported by @Jvr2022 (GHSA-2v35-w6hq-6mfw) and @KarimTantawey (GHSA-j2hf-fqwf-rrjf)

Additionally, discovered in research:

  • Element.getElementsByTagName() / getElementsByTagNameNS() / getElementsByClassName() / getElementById()
  • Node.cloneNode(true)
  • Document.importNode(node, true)
  • node.textContent (getter)
  • Node.isEqualNode(other)

All seven share the same root cause: pure-JavaScript recursive tree traversal with no depth guard. A single deeply nested document (parsed successfully) triggers any or all of these operations.


Details

Root cause

lib/dom.js implements DOM tree traversals as depth-first recursive functions. Each level of element nesting adds one JavaScript call frame. The JS engine's call stack is finite; once exhausted, a RangeError: Maximum call stack size exceeded is thrown. This error may not be caught reliably at stack-exhaustion depths because the catch handler itself requires stack frames to execute — especially in async scenarios, where an uncaught RangeError inside a callback or promise chain can crash the entire Node.js process.

Parsing a deeply nested document succeeds — the SAX parser in lib/sax.js is iterative. The crash occurs during subsequent operations on the parsed DOM.

Node.prototype.normalize() — reported by @praveen-kv

lib/dom.js:1296–1308 (main):

normalize: function () {
    var child = this.firstChild;
    while (child) {
        var next = child.nextSibling;
        if (next && next.nodeType == TEXT_NODE && child.nodeType == TEXT_NODE) {
            this.removeChild(next);
            child.appendData(next.data);
        } else {
            child.normalize();   // recursive call — no depth guard
            child = next;
        }
    }
},

Crash threshold (Node.js 18, default stack): ~10,000 levels.

XMLSerializer.serializeToString() — reported by @Jvr2022

lib/dom.js:2790–2974 (main): The internal serializeToString worker recurses into child nodes at four call sites, each passing a visibleNamespaces.slice() copy. The per-frame allocation causes earlier stack exhaustion than normalize().

Crash threshold (Node.js 18, default stack): ~5,000 levels.

Additional recursive entry points

All five crash at ~10,000 levels on Node.js 18.

| Function | Definition | Public API entry point(s) | Crash depth (Node.js 18) | |-----------------------------|----------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------------------------------------------|--------------------------| | _visitNode | lib/dom.js:1529 | getElementsByTagName(), getElementsByTagNameNS(), getElementsByClassName(), getElementById() | ~10,000 levels | | cloneNode (module fn) | lib/dom.js:3037 | Node.prototype.cloneNode(true) …

Record
GHSA-2v35-w6hq-6mfw
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N
Weakness
CWE-674
Updated
2026-11-02
OSVUBUNTU-CVE-2026-41673 8.7

xmldom is a pure JavaScript W3C standard-based (XML DOM Level 2 Core) DOMParser and XMLSerializer module. In @xmldom/xmldom prior to versions 0.9.10 and 0.8.13 and xmldom version 0.6.0 and prior, seven recursive traversals in lib/dom.js operate without a depth limit. A sufficiently deeply nested DOM tree causes a RangeError: Maximum call stack size exceeded, crashing the application. This issue has been patched in versions @xmldom/xmldom versions 0.9.10 and 0.8.13.

Record
UBUNTU-CVE-2026-41673
CVSS 4.0
8.7 HighCVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:N/VC:N/VI:N/VA:H/SC:N/SI:N/SA:N
CVSS 3.1
7.5 HighCVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H
Updated
2026-11-02
OSVCLSA-2026-1778114662 No score

TuxCare security update for xmldom (3 CVEs)

TuxCare rebuilt xmldom to address 3 CVEs. Fixed in 0.6.0-tuxcare.2.

Record
CLSA-2026-1778114662
Updated
2026-11-05
OSVCLSA-2026-1790755546 No score

TuxCare security update for @xmldom/xmldom (14 CVEs)

TuxCare rebuilt @xmldom/xmldom to address 14 CVEs. Fixed in 0.7.13-tuxcare.1.

Record
CLSA-2026-1790755546
Updated
2026-11-02
OSVCLSA-2026-1791028067 No score

TuxCare security update for @xmldom/xmldom (3 CVEs)

TuxCare rebuilt @xmldom/xmldom to address 3 CVEs. Fixed in 0.9.8-tuxcare.1.

Record
CLSA-2026-1791028067
Updated
2026-11-02
OSVROOT-APP-NPM-CVE-2026-41673 No score

CVE-2026-41673 in @xmldom/xmldom - Patched by Root

Root has patched CVE-2026-41673 in the @xmldom/xmldom package for Root:npm. Multiple fixed versions available.

Record
ROOT-APP-NPM-CVE-2026-41673
Updated
2026-11-02

Affected products

Affected packages

Affected packages
PackageAffectedFixed
@xmldom/xmldom
npm
before 0.8.13
0.8.13
@xmldom/xmldom
npm
0.9.0 up to 0.9.10
0.9.10
xmldom
npm
through 0.6.0 None known
xmldom
TuxCare:npm
From an advisory covering 3 CVEs
0.6.0-tuxcare.0 up to 0.6.0-tuxcare.2, plus listed versions
0.6.00.6.0-tuxcare.1
0.6.0-tuxcare.2
@xmldom/xmldom
TuxCare:npm
From an advisory covering 14 CVEs
0.7.13-tuxcare.0 up to 0.7.13-tuxcare.1, plus listed versions
0.7.13
0.7.13-tuxcare.1
@xmldom/xmldom
TuxCare:npm
From an advisory covering 3 CVEs
0.9.8-tuxcare.0 up to 0.9.8-tuxcare.1, plus listed versions
0.9.8
0.9.8-tuxcare.1
node-xmldom
Debian:12
All versions, plus listed versions
0.8.6-10.9.10-10.9.10-20.9.11-10.9.12-1
Show 5 moreShow less
0.9.5-10.9.6-10.9.8-10.9.8-20.9.9-1
None known
node-xmldom
Debian:13
All versions, plus listed versions
0.9.10-10.9.10-20.9.11-10.9.12-10.9.6-10.9.8-10.9.8-20.9.9-1
None known
node-xmldom
Debian:14
before 0.9.10-1, plus listed versions
0.9.6-10.9.8-10.9.8-20.9.9-1
0.9.10-1
@xmldom/xmldom
Root:npm
before 0.7.13-aikido.2
0.7.13-aikido.20.7.13-aikido.30.9.8-aikido.20.8.11-aikido.20.7.13-aikido.50.8.13-aikido.20.7.13-aikido.40.8.13-aikido.1
Show 7 moreShow less
Affected packages
PackageAffectedFixed
@rootio/xmldom__xmldom
Root:npm
before 0.9.8-root.io.1
0.9.8-root.io.10.8.11-root.io.10.7.13-root.io.10.7.13-root.io.20.7.13-root.io.30.9.8-root.io.20.8.11-root.io.20.7.13-root.io.50.8.13-root.io.20.7.13-root.io.40.8.13-root.io.1
node-xmldom
Ubuntu:20.04:LTS
All versions, plus listed versions
0.1.27+ds-10.1.27+ds-1+deb10u2build0.20.04.1
None known
node-xmldom
Ubuntu:22.04:LTS
All versions, plus listed versions
0.5.0-10.7.3-10.7.5-10.7.5-1ubuntu0.22.04.1
None known
node-xmldom
Ubuntu:24.04:LTS
All versions, plus listed versions
0.8.6-1
None known
node-xmldom
Ubuntu:25.10
All versions, plus listed versions
0.9.6-1
None known
node-xmldom
Ubuntu:26.10
All versions, plus listed versions
0.9.8-20.9.10-20.9.11-1
None known
node-xmldom
Ubuntu:26.04:LTS
All versions, plus listed versions
0.9.6-10.9.8-10.9.8-2
None known

History

History
RecordedChangedSources
affected
factsOSV
first indexedCVE List, EUVD, GitHub Advisories, NVD, OSV

Dates are when Every CVE recorded each change. Upstream dates may differ.

In short

CVE-2026-41673 is a high vulnerability (CVSS 8.7) in Xmldom, published April 22, 2026. No source lists public exploit code. EPSS puts the chance of exploitation in the next 30 days at 0.64%, the 51st percentile. Fixed in @xmldom/xmldom 0.8.13.

References

Show 19 moreShow less
This page doesn't list everything

Left out here: the rest of 2 source descriptions. The JSON record has them.

MoveEnter Open