Bug 916939 - Drop support for named and indexed access on cross-origin windows. r=bz

This commit is contained in:
Bobby Holley 2013-09-18 08:39:48 -07:00
parent 0a856e7ab2
commit 75ca6697e7
9 changed files with 27 additions and 81 deletions

View File

@ -93,6 +93,10 @@ function isInaccessible(wnd, message) {
}
}
function getSubframe(win, i) {
return SpecialPowers.unwrap(SpecialPowers.wrap(win)[i]);
}
///////////////////////////////////////////////////////////////////////////
// Functions that require UniversalXPConnect privilege
///////////////////////////////////////////////////////////////////////////

View File

@ -9,17 +9,18 @@
iframe { width: 90%; height: 50px; }
</style>
<script>
window.onload = function () {
navigateByLocation(window0.frames[0]);
navigateByLocation(getSubframe(window0, 0));
navigateByOpen("window1_child0");
navigateByForm("window2_child0");
navigateByHyperlink("window3_child0");
xpcWaitForFinishedFrames(function() {
isInaccessible(window0.frames[0], "Should not be able to navigate off-domain frame by setting location.");
isInaccessible(window1.frames[0], "Should not be able to navigate off-domain frame by calling window.open.");
isInaccessible(window2.frames[0], "Should not be able to navigate off-domain frame by submitting form.");
isInaccessible(window3.frames[0], "Should not be able to navigate off-domain frame by targeted hyperlink.");
isInaccessible(getSubframe(window0, 0), "Should not be able to navigate off-domain frame by setting location.");
isInaccessible(getSubframe(window1, 0), "Should not be able to navigate off-domain frame by calling window.open.");
isInaccessible(getSubframe(window2, 0), "Should not be able to navigate off-domain frame by submitting form.");
isInaccessible(getSubframe(window3, 0), "Should not be able to navigate off-domain frame by targeted hyperlink.");
window0.close();
window1.close();

View File

@ -14,16 +14,16 @@ if (!navigator.platform.startsWith("Win")) {
}
window.onload = function () {
navigateByLocation(frames[0].frames[0]);
navigateByLocation(getSubframe(getSubframe(frames, 0), 0));
navigateByOpen("child1_child0");
navigateByForm("child2_child0");
navigateByHyperlink("child3_child0");
xpcWaitForFinishedFrames(function() {
isNavigated(frames[0].frames[0], "Should be able to navigate off-domain grandchild by setting location.");
isNavigated(frames[1].frames[0], "Should be able to navigate off-domain grandchild by calling window.open.");
isNavigated(frames[2].frames[0], "Should be able to navigate off-domain grandchild by submitting form.");
isNavigated(frames[3].frames[0], "Should be able to navigate off-domain grandchild by targeted hyperlink.");
isNavigated(getSubframe(getSubframe(frames, 0), 0), "Should be able to navigate off-domain grandchild by setting location.");
isNavigated(getSubframe(getSubframe(frames, 1), 0), "Should be able to navigate off-domain grandchild by calling window.open.");
isNavigated(getSubframe(getSubframe(frames, 2), 0), "Should be able to navigate off-domain grandchild by submitting form.");
isNavigated(getSubframe(getSubframe(frames, 3), 0), "Should be able to navigate off-domain grandchild by targeted hyperlink.");
xpcCleanupWindows();
SimpleTest.finish();

View File

@ -11,7 +11,7 @@
<script>
window.onload = function () {
document.getElementById('active').innerHTML =
'<iframe src="http://test1.example.org:80/tests/docshell/test/navigation/navigate.html#parent.frames[0],location"></iframe>' +
'<iframe src="http://test1.example.org:80/tests/docshell/test/navigation/navigate.html#SpecialPowers.unwrap(SpecialPowers.wrap(parent).frames[0]),location"></iframe>' +
'<iframe src="http://test1.example.org:80/tests/docshell/test/navigation/navigate.html#child1,open"></iframe>' +
'<iframe src="http://test1.example.org:80/tests/docshell/test/navigation/navigate.html#child2,form"></iframe>' +
'<iframe src="http://test1.example.org:80/tests/docshell/test/navigation/navigate.html#child3,hyperlink"></iframe>';

View File

@ -5,7 +5,7 @@
var success = 0;
try {
parent[name].success = 1;
SpecialPowers.unwrap(SpecialPowers.wrap(parent)[name]).success = 1;
} catch (e) {
parent.postMessage(e, "http://mochi.test:8888");
}

View File

@ -16,7 +16,7 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=850517
function go() {
var ifrA = $('a');
var ifrB = $('b');
var sb = new SpecialPowers.Cu.Sandbox('http://www.example.com');
var sb = new SpecialPowers.Cu.Sandbox(SpecialPowers.Services.scriptSecurityManager.getSystemPrincipal());
sb.win = window;
sb.childA = ifrA.contentWindow;
sb.childB = ifrB.contentWindow;
@ -26,8 +26,7 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=850517
SpecialPowers.Cu.evalInSandbox('is(win.theoneandonly, childA, "Named child resolution works via Xray");', sb);
ifrA.removeAttribute('name');
is(typeof window.theoneandonly, 'undefined', "Revocation works");
SpecialPowers.Cu.evalInSandbox('try { win.theoneandonly; ok(false, "Should have thrown"); } ' +
'catch (e) {ok(!!/denied/.exec(e) && !!/theoneandonly/.exec(e), "Revocation works via Xray");};', sb);
SpecialPowers.Cu.evalInSandbox('is(typeof win.theoneandonly, "undefined", "Revocation works via Xray");', sb);
ifrB.setAttribute('name', 'theoneandonly');
is(window.theoneandonly.frameElement, ifrB, "Another mule kicking in the same old stall");
SpecialPowers.Cu.evalInSandbox('is(win.theoneandonly, childB, "Another mule via Xray");', sb);

View File

@ -50,6 +50,8 @@
function receiveSubDomain(evt)
{
var topframe =
SpecialPowers.unwrap(SpecialPowers.wrap(window).parent.topDomainFrame);
if (evt.origin !== "http://mochi.test:8888")
{
fail("wrong top-domain origin: " + evt.origin);
@ -62,12 +64,13 @@
}
document.domain = "example.com";
window.parent.topDomainFrame.postMessage("domain-switch",
"http://example.com");
topframe.postMessage("domain-switch", "http://example.com");
}
function receiveTopDomain(evt)
{
var subframe =
SpecialPowers.unwrap(SpecialPowers.wrap(window).parent.subDomainFrame);
if (evt.origin !== "http://test1.example.com")
{
fail("wrong subdomain origin: " + evt.origin);
@ -78,14 +81,14 @@
fail("wrong subdomain message: " + evt.origin);
return;
}
if (evt.source !== window.parent.subDomainFrame)
if (evt.source !== subframe)
{
fail("wrong source on message from subdomain");
return;
}
document.domain = "example.com";
window.parent.subDomainFrame.testSiblingPostMessage();
subframe.testSiblingPostMessage();
}
function testSiblingPostMessage()

View File

@ -40,9 +40,7 @@ function check(obj, prop, allowed, write) {
var crossOriginReadableWindowProps = ['blur', 'close', 'closed', 'focus',
'frames', 'location', 'length',
'opener', 'parent', 'postMessage',
'self', 'top', 'window',
/* indexed and named accessors */
'0', 'subframe'];
'self', 'top', 'window'];
function isCrossOriginReadable(obj, prop) {
if (obj == "Window")

View File

@ -165,49 +165,6 @@ IsPermitted(const char *name, JSFlatString *prop, bool set)
#undef R
#undef W
static bool
IsFrameId(JSContext *cx, JSObject *objArg, jsid idArg)
{
RootedObject obj(cx, objArg);
RootedId id(cx, idArg);
obj = JS_ObjectToInnerObject(cx, obj);
MOZ_ASSERT(!js::IsWrapper(obj));
XPCWrappedNative *wn = IS_WN_REFLECTOR(obj) ? XPCWrappedNative::Get(obj)
: nullptr;
if (!wn) {
return false;
}
nsCOMPtr<nsIDOMWindow> domwin(do_QueryWrappedNative(wn));
if (!domwin) {
return false;
}
nsCOMPtr<nsIDOMWindowCollection> col;
domwin->GetFrames(getter_AddRefs(col));
if (!col) {
return false;
}
if (JSID_IS_INT(id)) {
col->Item(JSID_TO_INT(id), getter_AddRefs(domwin));
} else if (JSID_IS_STRING(id)) {
nsAutoString str(JS_GetInternedStringChars(JSID_TO_STRING(id)));
col->NamedItem(str, getter_AddRefs(domwin));
} else {
return false;
}
return domwin != nullptr;
}
static bool
IsWindow(const char *name)
{
return name[0] == 'W' && !strcmp(name, "Window");
}
bool
AccessCheck::isCrossOriginAccessPermitted(JSContext *cx, JSObject *wrapperArg, jsid idArg,
Wrapper::Action act)
@ -243,22 +200,6 @@ AccessCheck::isCrossOriginAccessPermitted(JSContext *cx, JSObject *wrapperArg, j
return true;
}
if (act != Wrapper::GET)
return false;
// Check for frame IDs. If we're resolving named frames, make sure to only
// resolve ones that don't shadow native properties. See bug 860494.
if (IsWindow(name)) {
if (JSID_IS_STRING(id) && !XrayUtils::IsXrayResolving(cx, wrapper, id)) {
bool wouldShadow = false;
if (!XrayUtils::HasNativeProperty(cx, wrapper, id, &wouldShadow) ||
wouldShadow)
{
return false;
}
}
return IsFrameId(cx, obj, id);
}
return false;
}