gecko/dom/tests/mochitest/chrome/test_sandbox_bindings.xul

228 lines
10 KiB
XML

<?xml version="1.0"?>
<?xml-stylesheet type="text/css" href="chrome://global/skin"?>
<?xml-stylesheet type="text/css" href="chrome://mochikit/content/tests/SimpleTest/test.css"?>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=741267
-->
<window title="Mozilla Bug 741267"
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
<script type="application/javascript" src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"/>
<iframe id="t"></iframe>
<!-- test results are displayed in the html:body -->
<body xmlns="http://www.w3.org/1999/xhtml">
<a href="https://bugzilla.mozilla.org/show_bug.cgi?id=741267"
target="_blank">Mozilla Bug 741267</a>
</body>
<!-- test code goes here -->
<script type="application/javascript">
<![CDATA[
/** Test for Bug 741267 **/
function isXrayWrapper(x) {
return XPCNativeWrapper.unwrap(x) != x;
}
function doTest() {
var win = $("t").contentWindow;
var sandbox = Components.utils.Sandbox(win, { sandboxPrototype: win });
try {
var css = Components.utils.evalInSandbox("CSSStyleDeclaration", sandbox);
is(css.prototype, "[object CSSStyleDeclarationPrototype]", "'CSSStyleDeclaration.prototype' in a sandbox should return the CSSStyleDeclaration interface prototype object");
} catch (e) {
ok(false, "'CSSStyleDeclaration' shouldn't throw in a sandbox");
}
try {
var et = Components.utils.evalInSandbox("EventTarget", sandbox);
ok(et, "'EventTarget' in a sandbox should return the EventTarget interface object");
ok(isXrayWrapper(et), "Getting an interface object on an Xray wrapper should return an Xray wrapper");
} catch (e) {
ok(false, "'EventTarget' shouldn't throw in a sandbox");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest.prototype", sandbox);
ok(xhr, "'XMLHttpRequest.prototype' in a sandbox should return the XMLHttpRequest interface prototype object");
ok(isXrayWrapper(xhr), "Getting an interface prototype object on an Xray wrapper should return an Xray wrapper");
ok(isXrayWrapper(xhr.constructor), "Getting the constructor property on an Xray wrapper of an interface prototype object should return an Xray wrapper");
} catch (e) {
ok(false, "'XMLHttpRequest.prototype' shouldn't throw in a sandbox");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest", sandbox);
xhr.prototype = false;
} catch (e) {
ok(true, "'XMLHttpRequest.prototype' should be readonly");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest", sandbox);
delete xhr.prototype;
} catch (e) {
ok(true, "'XMLHttpRequest.prototype' should be permanent");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest.prototype", sandbox);
xhr.constructor = "ok";
} catch (e) {
is(xhr.constructor, "ok", "'XMLHttpRequest.prototype.constructor' should be writeable");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest.prototype", sandbox);
delete xhr.constructor;
} catch (e) {
is(xhr.constructor, undefined, "'XMLHttpRequest.prototype.constructor' should be permanent");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest", sandbox);
is(xhr, "[object XrayWrapper " + XMLHttpRequest + "]", "'XMLHttpRequest' in a sandbox should return the XMLHttpRequest interface object");
ok(isXrayWrapper(xhr.prototype), "Getting the prototype property on an Xray wrapper of an interface object should return an Xray wrapper");
} catch (e) {
ok(false, "'XMLHttpRequest' shouldn't throw in a sandbox");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest()", sandbox);
is("" + xhr, "" + XMLHttpRequest(), "'XMLHttpRequest()' in a sandbox should create an XMLHttpRequest object");
} catch (e) {
ok(false, "'XMLHttpRequest()' shouldn't throw in a sandbox");
}
try {
var xhr = Components.utils.evalInSandbox("XMLHttpRequest.prototype.toString = function () { return 'Failed'; }; XMLHttpRequest();", sandbox);
is(xhr.toString(), "[object XrayWrapper " + XMLHttpRequest() + "]", "XMLHttpRequest.prototype.toString in the sandbox should not override the native toString behaviour");
} catch (e) {
ok(false, "'new XMLHttpRequest()' shouldn't throw in a sandbox");
}
try {
// have to run this test before document.defaultView.XMLHttpRequest
// gets munged in the sandbox.
var proto = Components.utils.evalInSandbox("XMLHttpRequest.prototype", sandbox);
props = [];
for (var i in proto) {
props.push(i);
}
isnot(props.indexOf("dispatchEvent"), -1,
"'dispatchEvent' property should be enumerable on XMLHttpRequest.prototype");
props = Object.getOwnPropertyNames(proto);
is(props.indexOf("dispatchEvent"), -1,
"'dispatchEvent' is not an own property on XMLHttpRequest.prototype; it's on EventTarget.prototype")
} catch (e) {
ok(false, "XMLHttpRequest.prototype manipulation via an Xray shouldn't throw" + e);
}
try {
Components.utils.evalInSandbox("document.defaultView.XMLHttpRequest = function() {};", sandbox);
var win = Components.utils.evalInSandbox("document.defaultView", sandbox);
var xhr = win.XMLHttpRequest();
is("" + xhr, "" + XMLHttpRequest(), "'XMLHttpRequest()' in a sandbox should create an XMLHttpRequest object");
} catch (e) {
ok(false, "'XMLHttpRequest()' shouldn't throw in a sandbox");
}
try {
var canvas = Components.utils.evalInSandbox("document.createElement('canvas').getContext('2d')", sandbox);
is(canvas.DRAWWINDOW_DRAW_CARET, CanvasRenderingContext2D.DRAWWINDOW_DRAW_CARET, "Constants should be defined on DOM objects in a sandbox");
} catch (e) {
ok(false, "'document.createElement('canvas').getContext('2D')' shouldn't throw in a sandbox");
}
try {
var classList = Components.utils.evalInSandbox("document.body.className = 'a b'; document.body.classList", sandbox);
is(classList.toString(), "a b", "Stringifier should be called");
} catch (e) {
ok(false, "'document.createElement('canvas').getContext('2D')' shouldn't throw in a sandbox");
}
try {
var ctx = Components.utils.evalInSandbox("var ctx = document.createElement('canvas').getContext('2d'); ctx.foopy = 5; ctx", sandbox);
ok(!("foopy" in ctx), "We should have an Xray here");
var data = ctx.createImageData(1, 1);
for (var i = 0; i < data.data.length; ++i) {
// Watch out for premultiplied bits... just set all the alphas to 255
if (i % 4 == 3) {
data.data[i] = 255;
} else {
data.data[i] = i;
}
}
ctx.putImageData(data, 0, 0);
var data2 = ctx.getImageData(0, 0, 1, 1);
is(data2.data.length, data.data.length, "Lengths must match");
for (i = 0; i < data.data.length; ++i)
is(data.data[i], data2.data[i], "Data at " + i + " should match");
} catch (e) {
ok(false, "Imagedata manipulation via an Xray shouldn't throw " + e);
}
try {
var list = Components.utils.evalInSandbox("document.getElementsByTagName('*')", sandbox);
props = [];
for (var i in list) {
props.push(i);
}
is(props.indexOf("constructor"), -1,
"'constructor' property should not be enumerable on list object");
props = Object.getOwnPropertyNames(list);
is(props.indexOf("constructor"), -1,
"'constructor' property should not be an own property name on list object");
} catch (e) {
ok(false, "NodeList.prototype manipulation via an Xray shouldn't throw" + e);
}
try {
var proto = Components.utils.evalInSandbox("NodeList.prototype", sandbox);
props = [];
for (var i in proto) {
props.push(i);
}
is(props.indexOf("constructor"), -1,
"'constructor' property should not be enumerable on proto directly");
props = Object.getOwnPropertyNames(proto);
isnot(props.indexOf("constructor"), -1,
"'constructor' property should be an own property name on proto");
} catch (e) {
ok(false, "NodeList.prototype manipulation via an Xray shouldn't throw" + e);
}
try {
var url = Components.utils.evalInSandbox("URL", sandbox);
for (var i in url) {
url[i];
}
isnot(url.createObjectURL, undefined, "Should have a createObjectURL");
ok(true, "We didn't crash!");
} catch (e) {
ok(false, "URL interface object manipulation via an Xray shouldn't throw" + e);
}
try {
url.revokeObjectURL("");
} catch (e) {
// Just testing whether revokeObjectURL crashes us
}
ok(true, "We didn't crash!");
// And now tests that don't use a window-associated sandbox
sandbox = Components.utils.Sandbox(win.document.nodePrincipal,
{ sandboxPrototype: win });
try {
var ws = Components.utils.evalInSandbox('var ws = new WebSocket("ws://example.org"); ws', sandbox);
// Test that we actually got a WebSocket object, probably
ok("bufferedAmount" in ws, "What is this object?");
} catch (e) {
ok(false, "Should be able to create a WebSocket in a sandbox " + e);
}
try {
var es = Components.utils.evalInSandbox('var es = new EventSource("about:blank"); es', sandbox);
// Test that we actually got a EventSource object, probably
is(es.url, "about:blank", "What is this object?");
} catch (e) {
ok(false, "Should be able to create an EventSource in a sandbox " + e);
}
SimpleTest.finish();
}
SimpleTest.waitForExplicitFinish();
addLoadEvent(doTest);
]]>
</script>
</window>