Bug 788322. Don't crash when we drawWindow on a page containing a remote <iframe>. r=mattwoodrow
authorRobert O'Callahan <robert@ocallahan.org>
Tue, 13 Nov 2012 11:55:52 -0800
changeset 113196 ef15df8a2e6bdddca491c3e302a1b720bee431d9
parent 113195 12f5029c12a50a313d2f4d6e5c88f52a052dcdb5
child 113197 99b4b950c2ce79370d2c55434616fb3af89f52dc
push id23859
push useremorley@mozilla.com
push dateWed, 14 Nov 2012 14:36:31 +0000
treeherdermozilla-central@87928cd21b40 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmattwoodrow
bugs788322, 792351
milestone19.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 788322. Don't crash when we drawWindow on a page containing a remote <iframe>. r=mattwoodrow The test is actually a test for bug 792351. It doesn't pass yet, since we're not drawing remote iframes properly, but the test should at least not cause a crash.
browser/components/privatebrowsing/test/browser/global/browser_privatebrowsing_geoprompt.js
browser/components/privatebrowsing/test/browser/global/browser_privatebrowsing_geoprompt_page.html
browser/components/privatebrowsing/test/browser/global/browser_privatebrowsing_openlocation.js
browser/components/privatebrowsing/test/browser/global/browser_privatebrowsing_zoomrestore.js
layout/base/tests/Makefile.in
layout/base/tests/test_remote_frame.html
layout/ipc/RenderFrameParent.cpp
toolkit/system/windowsproxy/Makefile.in
toolkit/system/windowsproxy/nsWindowsSystemProxySettings.cpp
--- a/layout/base/tests/Makefile.in
+++ b/layout/base/tests/Makefile.in
@@ -144,16 +144,17 @@ MOCHITEST_FILES =	\
 		test_bug629838.html \
 		test_bug646757.html \
 		test_bug718809.html \
 		test_bug725426.html \
 		test_bug731777.html \
 		test_bug761572.html \
 		test_bug770106.html \
 		test_maxLineBoxWidth.html \
+		test_remote_frame.html \
 		$(NULL)
 
 # Tests for bugs 441782, 467672 and 570378 don't pass reliably on Windows, because of bug 469208
 ifeq (,$(filter windows,$(MOZ_WIDGET_TOOLKIT)))
 # THESE TESTS (BELOW) DO NOT RUN ON WINDOWS
 MOCHITEST_FILES += \
 		bidi_numeral_test.js \
 		$(NULL)
new file mode 100644
--- /dev/null
+++ b/layout/base/tests/test_remote_frame.html
@@ -0,0 +1,65 @@
+<!DOCTYPE HTML>
+<html>
+<head>
+  <script type="application/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
+  <script type="text/javascript" src="/tests/SimpleTest/WindowSnapshot.js"></script>
+  <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
+  <style>
+  div, iframe {
+    position:absolute;
+    left:0; top:50px;
+    width:400px; height:400px;
+    transform: translateY(50px);
+    border:5px solid black;
+  }
+  </style>
+</head>
+  <body>
+    <div id="d" style="background:blue"></div>
+
+  <script type="application/javascript;version=1.7">
+    "use strict";
+
+    var referenceSnapshot;
+    var iterations = 0;
+
+    SimpleTest.waitForExplicitFinish();
+
+    function pollForTestPass() {
+      var snapshot = snapshotWindow(window);
+      if (compareSnapshots(referenceSnapshot, snapshot, true)[0]) {
+        ok(true, "Test passed after " + iterations + " iterations");
+        SimpleTest.finish();
+        return;
+      }
+
+      ++iterations;
+      if (iterations == 20) {
+        todo(false, "We couldn't draw the frame, but at least we didn't crash");
+        SimpleTest.finish();
+        return;
+      }
+      setTimeout(pollForTestPass, 10);
+    }
+    function addRemoteFrame() {
+      let iframe = document.createElement("iframe");
+      iframe.mozbrowser = true;
+      iframe.src = "data:text/html,<html style='background:blue;'>";
+
+      document.body.appendChild(iframe);
+
+      pollForTestPass();
+    }
+    addEventListener("load", function() {
+      referenceSnapshot = snapshotWindow(window);
+      document.getElementById("d").style.display = 'none';
+      SpecialPowers.addPermission("browser", true, document);
+      SpecialPowers.pushPrefEnv({
+        "set": [
+          ["dom.ipc.browser_frames.oop_by_default", true],
+          ["dom.mozBrowserFramesEnabled", true]
+        ]
+      }, addRemoteFrame);      
+    });
+  </script>
+</body>
--- a/layout/ipc/RenderFrameParent.cpp
+++ b/layout/ipc/RenderFrameParent.cpp
@@ -653,23 +653,25 @@ RenderFrameParent::BuildLayer(nsDisplayL
 {
   NS_ABORT_IF_FALSE(aFrame,
                     "makes no sense to have a shadow tree without a frame");
   NS_ABORT_IF_FALSE(!mContainer ||
                     IsTempLayerManager(aManager) ||
                     mContainer->Manager() == aManager,
                     "retaining manager changed out from under us ... HELP!");
 
-  if (mContainer && mContainer->Manager() != aManager) {
+  if (IsTempLayerManager(aManager) ||
+      (mContainer && mContainer->Manager() != aManager)) {
     // This can happen if aManager is a "temporary" manager, or if the
     // widget's layer manager changed out from under us.  We need to
     // FIXME handle the former case somehow, probably with an API to
     // draw a manager's subtree.  The latter is bad bad bad, but the
     // the NS_ABORT_IF_FALSE() above will flag it.  Returning NULL
     // here will just cause the shadow subtree not to be rendered.
+    NS_WARNING("Remote iframe not rendered");
     return nullptr;
   }
 
   uint64_t id = GetLayerTreeId();
   if (0 != id) {
     MOZ_ASSERT(!GetRootLayer());
 
     nsRefPtr<Layer> layer =