DOM XSS using web messages and a JavaScript URL

Description

This lab demonstrates a DOM-based redirection vulnerability that is triggered by web messaging.

Reproduction and proof of concept

  1. Analysis:

<script>
    window.addEventListener('message', function(e) {
        var url = e.data;
        if (url.indexOf('http:') > -1 || url.indexOf('https:') > -1) {
            location.href = url;
        }
    }, false);
</script>

The home page contains an addEventListener() call that listens for a web message. The JavaScript contains a flawed indexOf() check that looks for the strings http: or https: anywhere within the web message. It also contains the sink location.href.

And see Window.postMessage():

In this lab, a payload can be transported in the message, while the targetOrigin is the target domain or a * as a synonym for the full world:

<iframe src="URL" onload="contentWindow.postMessage('PAYLOAD','*');">
  1. Go to the exploit server and add this iframe to the body:

DOM-based

  1. Store the exploit and deliver it to the victim.

This script sends a web message containing an arbitrary JavaScript payload, along with the string http:. The second argument specifies that any targetOrigin is allowed for the web message.

When the iframe loads, the postMessage() method sends the JavaScript payload to the main page. The event listener spots the http: string and proceeds to send the payload to the location.href sink, where the print() function is called.

Exploitability

An attacker needs to construct an HTML page on the exploit server that exploits this vulnerability and calls the print() function.