CVEReports
CVEReports

Automated vulnerability intelligence platform. Comprehensive reports for high-severity CVEs generated by AI.

Product

  • Home
  • Sitemap
  • RSS Feed

Company

  • About
  • Contact
  • Privacy Policy
  • Terms of Service

© 2026 CVEReports. All rights reserved.

Made with love by Amit Schendel & Alon Barad



GHSA-W9HM-4M3M-FXMM

GHSA-W9HM-4M3M-FXMM: Arbitrary JavaScript Execution via Malicious PDF Parsing in ngx-extended-pdf-viewer

Alon Barad
Alon Barad
Software Engineer

Aug 7, 2026·5 min read·0 visits

Executive Summary (TL;DR)

A high-severity Cross-Site Scripting (XSS) vulnerability exists in ngx-extended-pdf-viewer. By parsing a crafted PDF with XML Forms Architecture (XFA) elements, attackers can bypass sanitizers and execute arbitrary script inside the application context.

The ngx-extended-pdf-viewer library embeds a version of Mozilla's pdf.js that contains vulnerability CVE-2026-16633. This vulnerability allows arbitrary JavaScript execution (XSS) upon rendering a malicious PDF file.

Vulnerability Overview

The ngx-extended-pdf-viewer library embeds a customized, direct-bundled version of Mozilla's pdf.js rendering engine instead of relying on standard external package dependency models. This integration model limits vulnerability detection from automated software composition analysis (SCA) tools, introducing risks associated with hidden dependencies (CWE-1103).

Under default configurations, the application enables XML Forms Architecture (XFA) parsing. This default setting exposes a significant attack surface to malicious actors. When a victim opens a specially crafted PDF document, the engine processes malicious parameters in XFA templates without proper sanitization, leading to client-side code execution.

The vulnerability is tracked under GitHub Security Advisory GHSA-W9HM-4M3M-FXMM, mapping upstream to CVE-2026-16633. It permits unauthenticated remote code execution on the client-side, translating directly to Cross-Site Scripting (XSS) in the context of the hosting web application's origin.

Root Cause Analysis

The root cause of this vulnerability lies in the serialization and encoding logic within two core utility functions in pdf.js: escapePDFName and encodeToXmlString.

The first failure is in the character encoding logic of escapePDFName. When encoding PDF Name objects containing control characters (character codes below 0x10), the system does not zero-pad the resulting hexadecimal notation. This results in characters such as \x05 escaping to #5 instead of #05. An attacker can align syntax-active characters directly following a control character, such as appending c to \x05 to yield #5c. When decoded, this sequence evaluates to \ (backslash), allowing the attacker to escape string literal boundaries within dynamically generated scripts.

The second failure occurs within the encodeToXmlString function, which handles serialization for XML/HTML nodes in XFA forms. The logic incorrectly identifies single-unit Basic Multilingual Plane (BMP) non-characters (such as U+FFFE and U+FFFF) as surrogate pairs. When processing these units, the parser increments its loop index artificially, skipping and dropping the next character in the sequence. By strategically inserting non-characters, attackers can drop sanitization filters, allowing raw script tags and active elements to pass into the rendering boundary.

Code Analysis

The code comparison highlights the parsing flaws and the exact remediations applied in the upstream repository.

In the vulnerable version of escapePDFName, the hex serialization lacks padding:

// Vulnerable code in core_utils.js
function escapePDFName(str) {
  return str.replace(/[\x00-\x1f]/g, (char) => {
    // Bug: No zero-padding for character codes lower than 16
    return "#" + char.charCodeAt(0).toString(16);
  });
}

The patch introduces standard zero-padding to secure character alignment:

// Patched code in core_utils.js
function escapePDFName(str) {
  return str.replace(/[\x00-\x1f]/g, (char) => {
    // Correct: Zero-pads the hex representation to exactly 2 digits
    return "#" + char.charCodeAt(0).toString(16).padStart(2, "0");
  });
}

Additionally, the parsing logic in encodeToXmlString mistakenly handled single-unit non-characters as multi-unit surrogate pairs:

// Vulnerable loop check in core_utils.js
if (char > 0xd7ff && (char < 0xe000 || char > 0xfffd)) {
  // Bug: Incorrect index incrementation on single non-characters
  i++;
}

The fix establishes verified evaluation of high/low surrogate pairs before skipping indexes:

// Patched logic in core_utils.js
const next = str.charCodeAt(i + 1);
if (char >= 0xd800 && char <= 0xdbff && next >= 0xdc00 && next <= 0xdfff) {
  // Correct: Only skips index if a valid low surrogate matches the current high surrogate
  i++;
}

Exploitation Methodology

To execute this attack, an offensive actor must first construct a PDF template containing custom XFA structures with malicious name properties or XML definitions. This payload integrates the character truncation and alignment sequences to bypass HTML validators.

The document is then delivered to a target user who views it inside an application using a vulnerable ngx-extended-pdf-viewer build. Because the viewer has XFA enabled by default, it automatically invokes the parser on the malformed elements.

As the client processes the form templates, the parser reconstructs the corrupted XML sequences into functional markup tags. The payload escapes the script string literal context and runs client-side JavaScript on the hosting platform's domain, granting the attacker unauthenticated execution capability.

Impact Assessment

The impact of this vulnerability is high, threatening both application security boundaries and backend operations that rely on trusted client authorization tokens.

An attacker who successfully exploits this flaw achieves full execution capabilities within the security context of the victim's session. This permits access to session cookies, local storage objects, and API interaction secrets, allowing the attacker to spoof client sessions and query internal APIs.

Because the vulnerability operates entirely on client browsers upon loading a document, detection relies on network-level analysis or file-scanning mechanisms before the payload reaches the application interface.

Remediation and Mitigation

The primary recommendation to resolve this vulnerability is to upgrade ngx-extended-pdf-viewer to version 29.0.0-rc.3 or higher. This release integrates patched core parsing utilities from pdf.js 6.2.108.

If immediate software upgrades are not possible, administrators must disable XFA parsing in the application setup module to remove the default exploit path:

pdfDefaultOptions.enableXfa = false;

Furthermore, implementing a strict Content Security Policy (CSP) that prohibits inline scripts prevents injected DOM markup from executing successfully:

Content-Security-Policy: default-src 'self'; script-src 'self';

Fix Analysis (2)

Technical Appendix

CVSS Score
8.6/ 10
CVSS:4.0/AV:N/AC:L/AT:N/PR:N/UI:P/VC:H/VI:H/VA:N/SC:N/SI:N/SA:N

Affected Systems

ngx-extended-pdf-viewerApplications incorporating vulnerable pdf.js libraries with XML Forms Architecture (XFA) enabled

Affected Versions Detail

Product
Affected Versions
Fixed Version
ngx-extended-pdf-viewer
stephanrauh
>= 27.0.0-rc.0, < 29.0.0-rc.329.0.0-rc.3
AttributeDetail
CWE IDCWE-79 / CWE-1103
Attack VectorNetwork
CVSS Score8.6
ImpactArbitrary JavaScript Execution (XSS)
Exploit Statuspoc
KEV StatusNo

MITRE ATT&CK Mapping

T1190Exploit Public-Facing Application
Initial Access
CWE-79
Cross-site Scripting

Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting')

References & Sources

  • [1]Upstream pdf.js Advisory
  • [2]ngx-extended-pdf-viewer Advisory

Attack Flow Diagram

Press enter or space to select a node. You can then use the arrow keys to move the node around. Press delete to remove it and escape to cancel.
Press enter or space to select an edge. You can then press delete to remove it or escape to cancel.

More Reports

•1 minute ago•CVE-2026-71497
4.7

CVE-2026-71497: Parser-Browser Desynchronization leading to XSS in jsoup Sanitizer

jsoup is a widely used Java library for working with real-world HTML. Versions 1.14.3 up to but excluding 1.23.1 contain a Cross-Site Scripting (XSS) vulnerability. When an application configures a custom Safelist that explicitly permits certain raw-text or RCDATA elements, such as style, title, or iframe, an attacker can exploit a parser-browser desynchronization flaw to bypass sanitization. This is achieved by utilizing trailing ASCII control characters that are handled differently by the HTML5 parsing specification and Java's string normalization methods, resulting in unescaped markup execution on the client side.

Amit Schendel
Amit Schendel
0 views•7 min read
•about 2 hours ago•CVE-2026-71430
6.2

CVE-2026-71430: Denial of Service via Native Assertion Failure in node-re2 Replace Operation

A denial-of-service vulnerability in node-re2 prior to version 1.25.1 allows attackers to trigger uncatchable native assertion failures in the Google V8 engine. By supplying output-amplifying replacement templates, an attacker can exceed V8 string limits, resulting in an immediate process crash.

Alon Barad
Alon Barad
1 views•6 min read
•about 3 hours ago•CVE-2026-71498
5.1

CVE-2026-71498: Out-of-bounds Heap Read in node-re2 via Truncated Multi-byte UTF-8 Characters

A medium-severity out-of-bounds (OOB) heap read vulnerability exists in node-re2 prior to version 1.26.1. When a raw binary Node.js Buffer with a truncated multi-byte UTF-8 character at its end is passed to the C++ native addon, the internal lookahead routine getUtf8CharSize() over-reads up to 3 bytes from the heap, leading to memory disclosure.

Alon Barad
Alon Barad
1 views•6 min read
•about 4 hours ago•CVE-2026-67434
7.3

CVE-2026-67434: OS Command Injection via Malicious Filenames in PHP_CodeSniffer Blame Reports

A critical OS command injection vulnerability exists in PHP_CodeSniffer's VCS blame report modules (Gitblame, Hgblame, Svnblame). Due to inadequate escaping of filenames passed to shell execution wrappers like popen(), an attacker who commits a file with a maliciously crafted name can execute arbitrary commands when the victim generates a blame report.

Alon Barad
Alon Barad
4 views•6 min read
•about 5 hours ago•GHSA-2RP4-X2J7-QMCC
8.2

GHSA-2RP4-X2J7-QMCC: Stored Cross-Site Scripting via Draft Names in Craft CMS Control Panel

An authenticated stored Cross-Site Scripting (XSS) vulnerability exists in the Control Panel helper of Craft CMS before version 5.10.8. Due to lack of HTML entity encoding within the elementLabelHtml method, unescaped draft names are rendered directly into administrative interfaces.

Amit Schendel
Amit Schendel
2 views•6 min read
•about 6 hours ago•GHSA-7HXC-F267-H5Q7
4.9

GHSA-7HXC-F267-H5Q7: Path Traversal via Validation-then-Normalization in Craft CMS

A path traversal vulnerability exists in the local filesystem driver of Craft CMS. Due to validation occurring before path normalization, directory containment checks can be bypassed by utilizing specific protocol schemes like 'file://' along with directory traversal sequences. This allows authenticated users with administrative privileges to access or manipulate files outside the defined storage root directory.

Alon Barad
Alon Barad
2 views•8 min read