Aug 21, 2026·5 min read·11 visits
Unsanitized user query parameters reflected inside an HTML script template block allow attackers to terminate the container early and execute arbitrary JavaScript in the victim's browser session.
A reflected Cross-Site Scripting (XSS) vulnerability exists in the backend Table widget of Winter CMS. The vulnerability is located within the search input template partial, where the application retrieves raw user inputs from the query parameters and renders them directly inside a raw-text script container without sanitization. An attacker can exploit this behavior by passing a crafted tag containing raw-text terminators, leading to code execution in the context of the victim's session.
The vulnerability affects the backend Table widget component in Winter CMS. This component is responsible for rendering interactive data grids, complete with search, filtering, and sorting utilities, which administrative users access inside the control panel.
The attack surface exists in the search input element located at modules/backend/widgets/table/partials/_table.php. Because this input is part of a template that is processed dynamically on the client side, the developers enclosed the markup in a script element of type text/template.
By leveraging the unique parsing rules that browsers apply to raw-text HTML elements, an unauthenticated attacker can craft a malicious hyperlink that targets this endpoint. If an authenticated administrator visits the link, arbitrary script commands run in their browser context, compromising the administrative session.
The root cause of this vulnerability lies in the combination of raw parameter reflection and browser HTML tokenization rules. The application retrieves the value of the search GET query parameter directly via the get('search') helper and embeds it into the value attribute of an HTML input tag.
To prevent the browser from rendering the toolbar controls on page load before the JavaScript framework initializes, the entire block is enclosed inside <script type="text/template">. According to the HTML5 specifications, <script> tags are treated as Raw Text Elements.
When the browser's parser encounters a Raw Text Element, it switches to the Script Data State. In this state, the parser does not recognize standard HTML attributes, single quotes, or double quotes as value boundaries. Instead, it scans the character stream exclusively for the literal ending sequence </script>. When an attacker passes a payload containing </script> inside the query string, the parser matches this sequence, closes the initial template block early, and treats the remaining payload as executable code.
The vulnerable code path is situated in the table partial file. Reviewing the difference between the vulnerable and patched versions highlights how the vulnerability was introduced and resolved.
Below is the code before the patch:
<!-- Vulnerable Code -->
<input
placeholder="<?= e(trans('backend::lang.list.search_prompt')) ?>"
name="search"
id="search"
value="<?= get('search') ?>"
type="text"
autocomplete="off"
class="table-search-input form-control icon search" />In the block above, get('search') retrieves the raw parameter and emits it directly. Below is the code after the patch:
<!-- Patched Code -->
<input
placeholder="<?= e(trans('backend::lang.list.search_prompt')) ?>"
name="search"
id="search"
value="<?= e(get('search')); ?>"
type="text"
autocomplete="off"
class="table-search-input form-control icon search" />The patch routes the output through the e() helper function, which runs htmlspecialchars() under the hood. This converts dangerous characters such as < and > into their equivalent HTML entities (< and >). When the browser's parser scans the script block, it sees </script> instead of the literal closing sequence, preventing the early termination of the raw-text element.
Exploitation requires targeting an administrative user who has access to the backend table interface. The attacker must construct a URL that points to a backend controller utilizing the table widget and includes the malicious payload in the query string.
A verified exploitation payload uses the raw-text terminator sequence combined with a secondary script block:
</script><script>alert(document.cookie)</script>
When encoded and appended to the target URL, the full request looks as follows:
https://example.com/backend/acme/plugin/items?search=%3C%2Fscript%3E%3Cscript%3Ealert%28document.cookie%29%3C%2Fscript%3E
Once the administrator loads this link, the browser tokenizes the response, terminates the template block at the first occurrence of </script>, and executes the secondary script block immediately, allowing the attacker to read the session cookie or perform actions on behalf of the administrator.
The impact of this vulnerability is classified as Medium, reflecting the classic risks associated with session hijacking and client-side privilege escalation. Because the payload executes within the administrative console of Winter CMS, the script runs with the authorization level of the logged-in administrator.
An attacker exploiting this vulnerability can perform unauthorized state modifications, steal session identifiers, or inject persistent backdoors into other sections of the content management system.
The vector breakdown under CVSS v3.1 is CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:N. While exploitation requires user interaction to click the crafted link, the lack of prior authorization requirements and the potential for complete control over the CMS backend emphasize the need for immediate remediation.
To fully resolve the vulnerability, administrators must update Winter CMS to version v1.2.14 or higher. This update applies the escaping helper systematically across the affected templates.
If an immediate upgrade of the framework is not feasible, the vulnerability can be mitigated manually by applying the patch to the template partial at modules/backend/widgets/table/partials/_table.php on line 44. Ensure that the raw call to get('search') is wrapped inside the escaping helper e() as shown in the code analysis.
In addition, deploying a Web Application Firewall (WAF) with rules that detect and block raw closing HTML tags inside URL parameters can act as a temporary workaround until the patch is successfully applied.
CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:N| Product | Affected Versions | Fixed Version |
|---|---|---|
winter wintercms | < 1.2.14 | 1.2.14 |
| Attribute | Detail |
|---|---|
| CWE ID | CWE-79 |
| Attack Vector | Network |
| CVSS Score | 6.1 (Medium) |
| Exploit Status | Proof of Concept |
| KEV Status | Not Listed |
The product does not sanitize or incorrectly sanitizes user-controlled input before it is placed in output that is used as a web page that is served to other users.
CVE-2026-109619 (PHP2Shell) is a critical Use-After-Free vulnerability in the core PHP engine caused by improper global state cleanup during out-of-memory exception handling across persistent worker requests.
In Python virtualenv prior to version 21.14.9, activation script generators and configuration writers use Path.exists() before writing files. Because Path.exists() resolves symbolic links, it returns False for dangling symlinks. Consequently, virtualenv skips unlinking pre-planted symbolic links or hard links, writing data directly to target locations outside the intended virtual environment directory.
A remote code execution vulnerability exists in Microsoft .NET due to untrusted data deserialization within the PresentationCore component. The flaw stems from implicit auto-conversion flags during clipboard data retrieval operations.
An out-of-bounds write vulnerability in Microsoft .NET Framework, .NET runtime, and Visual Studio allows unauthenticated remote attackers to execute arbitrary code via crafted pixel-shader bytecode or auto-converted clipboard payloads.
ASP.NET Core contains a thread deadlock vulnerability (CWE-833) that allows an unauthenticated remote attacker to cause a denial of service over the network by exhausting server thread pool resources.
CVE-2026-70035 is a high-severity Remote Code Execution (RCE) vulnerability in Microsoft .NET Framework, .NET runtime, and Visual Studio caused by improper handling during the deserialization of untrusted data (CWE-502). An unauthenticated attacker can execute arbitrary code within the context of the affected process by delivering a crafted serialized payload.