
This repository contains a practical research and validation toolkit for CVE-2025-4396, an unauthenticated Time-Based Blind SQL Injection affecting the WordPress Relevanssi plugin through the `cats` parameter.
This repository contains a practical research and validation toolkit for CVE-2025-4396, an unauthenticated Time-Based Blind SQL Injection affecting the WordPress Relevanssi plugin through the cats parameter.
The project was built for authorized Purple Team engagements in order to:
The repository includes:
Disclaimer
This project is provided for educational, defensive validation, and authorized security testing only.
Do not use it against systems you do not own or do not have explicit written permission to assess.
CVE-2025-4396 is a SQL Injection vulnerability affecting the Relevanssi search functionality in WordPress.
In the tested scenario, the issue is reachable through the search workflow and more specifically through the cats parameter. The vulnerable code path allows attacker-controlled input to influence the SQL query generated by the plugin.
Because the vulnerable endpoint is accessible without prior authentication, the flaw can be exploited by a remote attacker to perform unauthenticated SQL injection.
The practical impact includes:
The vulnerability exists because user-controlled input from a search-related parameter is not safely handled before being incorporated into a SQL query.
In practice, this means an attacker can inject SQL expressions into the backend query logic and force the database to evaluate additional conditions.
The vulnerability is exploited in blind mode, which means the application does not directly display SQL errors or raw database results.
Instead of reading query output from the page, the attacker asks the database a series of true/false questions and observes one side effect:
The exploitation relies on SQL functions such as SLEEP() to create a measurable difference in server response time.
This allows an attacker to infer data without ever seeing it directly.
For example, the attacker can ask questions such as:
$?”By repeating this process, the attacker can reconstruct a full hash character by character.
The standard approach iterates through a known character set and tests each candidate one by one.
For each position in the target hash:
This method is simple and reliable, but relatively slow because it may require many requests per character.
The faster approach uses binary search on the ASCII value of each character.
Instead of asking:
a?”b?”c?”it asks:
This divides the search space in half on every request and reduces the number of HTTP requests dramatically.
The attack allows the operator to extract the user_pass value from wp_users, typically for a chosen WordPress user ID such as:
1 for the default administrator,In recent WordPress versions, this value may use the new WordPress 6.8+ password pipeline, which combines:
CVE_2025_4396.pyThis is the standard extraction script.
It performs a classic Time-Based Blind SQL Injection and extracts the target hash character by character using a linear search over a fixed charset.
For each character position:
python3requestsurllib3pip3 install requests urllib3
python3 CVE_2025_4396.py -t "https://target.local/?s=test&cats=" -u 1 -s 3 -v
Arguments :
-t, --target : vulnerable target URL including the injectable parameter
-u, --userid : WordPress user ID to target
-s, --sleep : sleep threshold in seconds
-v, --verbose : enable debug logging
CVE_2025_4396_Stealth.pyThis is the binary search edition.
It performs the same extraction objective as the standard script, but replaces the linear character-by-character search with a binary search on ASCII values.
For each position:
python3requestsurllib3pip3 install requests urllib3
python3 CVE_2025_4396_Stealth.py -t "https://target.local/?s=test&cats=" -u 1 -s 3 -v
Once the password hash has been extracted from WordPress, the next step is to crack it offline.
WordPress 6.8+ Hashing Notes. In the tested workflow, the extracted value may look like:
$wp$2y$10$zPA8xGJMvr.kvAAIIYaCreIMnTDpgw/9o8K7.ONBm/KBbNIywQtu.
For Hashcat, the usable bcrypt portion is:
$2y$10$zPA8xGJMvr.kvAAIIYaCreIMnTDpgw/9o8K7.ONBm/KBbNIywQtu.
However, this bcrypt is not applied directly to the raw password. WordPress first applies a preprocessing stage: