Cross-site Scripting (XSS) on DVWA

Cross-site Scripting (XSS) is one of the common vulnerabilities found in web applications. It is considered as a type of injection in the client-side that will affect the other users. It also may be used by attackers to bypass access controls such as the same-origin policy.
In this post, I’m going to show you some examples of Reflected, Stored, and DOM-Based XSS in DVWA (click here for DVWA’s installation guide on Linux) and why is it considered as a vulnerability.

How does XSS works?

First, malicious scripts are injected into a website by the attacker and the other users’ browsers will automatically execute the script because it thinks that the script come from the web application itself.

With XSS, we can access any cookies, session tokens, or other sensitive information retained by the browser and used on that site. These scripts can even rewrite the content of the HTML page.

There are three types of XSS:

  1. Stored XSS (Type I): It occurs when user input is stored on the target server, such as in a database, in a message forum, visitor log, comment field, etc. And then a victim is able to retrieve the stored data from the web application without that data being made safe to render in the browser.
  2. Reflected XSS (Type II): It occurs when user input is immediately returned by a web application in an error message, search result, or any other response that includes some or all of the input provided by the user as part of the request, without that data being made safe to render in the browser, and without permanently storing the user provided data. In some cases, the user-provided data may never even leave the browser.
  3. DOM-Based XSS (Type 0): It is a form of XSS which appears in document object model or DOM environment instead of HTML page. For example, the source (where malicious data is read) could be the URL of the page (e.g., document.location.href), or it could be an element of the HTML.

DVWA has 4 security levels; low, medium, high and impossible. To change the security level, just click DVWA Security and change the Security Level that you want. You can also see the current security level in the bottom left corner of the web page.


Security Level: Low

In this level, there is no protection whatsoever from the client side. The application will print execute whatever the user input as long as the field is not empty.

Source Code for Low Level Reflected XSS

Therefore, we can inject using Javascript code easily by typing

<script> insert malicious code here </script>

and the browser will execute the code just like it is shown below.

alert(“This website is exposed to XSS vulnerability”);

Security Level: Medium

At this level, the application tries to prevent XSS by removing any string that contains <script> in the input field.

If we pay close attention to the code, it will only replace the string with <script> in it and it is case sensitive which means it will distinguish between uppercase and lowercase. It will treat the command <sCriPt> differently from <script>.

<scRipt> insert malicious code here </sCrIpt>


<scri<script>pt> insert malicious code here </scri<script>pt>

I’ve mentioned at the beginning of this post that XSS can be used for cookie stealing which can be useful for the attacker. To do cookie stealing, you just need to type 


inside the script tag.


Security Level: High

Now, all JavaScript will be blocked because the code will remove the pattern “<s*c*r*i*p*t”. 

Since we cannot inject any code that starts with <script> tag, we can use HTML events for code injection since there won’t be any <script> tag included.

Example of HTML events:

<img src=x onError= insert malicious code here >


<body onload= insert malicious code here>

Executing alert(document.cookie) inside the HTML event.


In DOM-Based XSS, there is only a dropbox with 4 choices. The user cannot type or input anything like we can do in Reflected XSS. So, how can we inject the code? Write it in the URL 🙂

Security Level: Low

As you can see there are no protections for this level. So we can simply inject the script in the URL.

Cookie stealing in DOM-Based XSS

Security Level: Medium

The application now will remove any references to “<script” to prevent the execution of javascript code hidden in the URL.

Unfortunately, we can exploit this vulnerability by breaking out of the select block using </select> then add the code using HTML events like we did in Reflected XSS.

Security Level: High

At this level, the default parameter in the URL can only change if the input is one of the 4 options given by the application, otherwise, it will automatically set English as the default parameter.

In this case, we can take advantage of the fragment section of a URL (anything after the # symbol) since it will not get sent to the server and this means the code won’t have to go through the validation process (the switch function).

To do that, just insert malicious code after # symbol like in the picture below. The code will read the content from the page when creating it.


Security Level: Low

Like other low-level XSS vulnerabilities, there is no protection in the server-side code to prevent XSS.

So we can simply insert the script in both Name and Message field and it will be saved in the database. If we open the page again, it will execute both script tags from the Name & Message tables.

Security Level: Medium

The application now will remove all script tag found in the Message field to prevent XSS and it is case insensitive. However, the Name field is still exposed to XSS injection since the prevention implemented in the code is only by removing ‘<script>’ string like they’ve done in medium-level Reflected XSS.

That’s why we can simply inject the code by changing one of the alphabets into UPPERCASE.

Security Level: High

Same like high-level Reflected XSS, it will remove all string that has “<s*c*r*i*p*t” pattern and the solution is also the same. Just use HTML events code instead of Javascript code.

Even though I only show you how to show stored cookie using XSS, remember that there are still so many things you can do when injecting the code.

One of them is redirecting to another page, or in most attacker’s case, redirect it to his/her malicious website.

<body onload=alert(window.location=<insert_url_here>)>

I write in the window.location and the page is redirected to Google after the alert window showed up.