summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDaniel Cheng <dcheng@chromium.org>2016-10-24 13:37:44 -0700
committerAllan Sandfeld Jensen <allan.jensen@qt.io>2017-03-16 14:47:47 +0000
commit062a75ed93a9b75f53292c6421b3292f753ea9b5 (patch)
tree41d5443d5543c3f529c54ee2bc007bf199c1d27c
parent965db0de3913007ea170150343a37a7277e78f06 (diff)
[Backport] Disallow frame swap during frame detach.
Otherwise, the swapped-in frame is never detached, resulting in general confusion and mayhem. BUG=646610 Review-Url: https://codereview.chromium.org/2429133002 Cr-Commit-Position: refs/heads/master@{#426245} (cherry picked from commit 29226a0dcd5ff17b04a0a92bb52ea5c88b29decb) R=japhet@chromium.org Review URL: https://codereview.chromium.org/2446563003 . Cr-Commit-Position: refs/branch-heads/2883@{#257} Cr-Branched-From: 614d31daee2f61b0180df403a8ad43f20b9f6dd7-refs/heads/master@{#423768} (CVE-2016-5205) Change-Id: I6153619b7a5cc6a37aa3a17996eeadabbe59d251 Reviewed-by: Alexandru Croitor <alexandru.croitor@qt.io>
-rw-r--r--chromium/content/renderer/render_frame_impl.cc3
-rw-r--r--chromium/third_party/WebKit/Source/core/frame/Frame.h4
-rw-r--r--chromium/third_party/WebKit/Source/core/frame/LocalFrame.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/core/frame/RemoteFrame.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/web/WebFrame.cpp2
5 files changed, 14 insertions, 1 deletions
diff --git a/chromium/content/renderer/render_frame_impl.cc b/chromium/content/renderer/render_frame_impl.cc
index 36f1b10d360..dfa128cb154 100644
--- a/chromium/content/renderer/render_frame_impl.cc
+++ b/chromium/content/renderer/render_frame_impl.cc
@@ -3135,7 +3135,8 @@ void RenderFrameImpl::didCommitProvisionalLoad(
if (!proxy)
return;
- proxy->web_frame()->swap(frame_);
+ if (!proxy->web_frame()->swap(frame_))
+ return;
proxy_routing_id_ = MSG_ROUTING_NONE;
in_frame_tree_ = true;
diff --git a/chromium/third_party/WebKit/Source/core/frame/Frame.h b/chromium/third_party/WebKit/Source/core/frame/Frame.h
index c15b0949118..137079c3e5e 100644
--- a/chromium/third_party/WebKit/Source/core/frame/Frame.h
+++ b/chromium/third_party/WebKit/Source/core/frame/Frame.h
@@ -133,6 +133,8 @@ public:
virtual WindowProxyManager* windowProxyManager() const = 0;
+ bool isDetaching() const { return m_isDetaching; }
+
protected:
Frame(FrameClient*, FrameHost*, FrameOwner*);
@@ -141,6 +143,8 @@ protected:
RawPtrWillBeMember<FrameHost> m_host;
RawPtrWillBeMember<FrameOwner> m_owner;
+ bool m_isDetaching = false;
+
private:
RawPtrWillBeMember<FrameClient> m_client;
// Needed to identify Frame Timing requests.
diff --git a/chromium/third_party/WebKit/Source/core/frame/LocalFrame.cpp b/chromium/third_party/WebKit/Source/core/frame/LocalFrame.cpp
index d972f17789f..7db189a63c8 100644
--- a/chromium/third_party/WebKit/Source/core/frame/LocalFrame.cpp
+++ b/chromium/third_party/WebKit/Source/core/frame/LocalFrame.cpp
@@ -276,6 +276,10 @@ void LocalFrame::reload(FrameLoadType loadType, ClientRedirectPolicy clientRedir
void LocalFrame::detach(FrameDetachType type)
{
+ // Note that detach() can be re-entered, so it's not possible to
+ // DCHECK(!m_isDetaching) here.
+ m_isDetaching = true;
+
PluginScriptForbiddenScope forbidPluginDestructorScripting;
// A lot of the following steps can result in the current frame being
// detached, so protect a reference to it.
diff --git a/chromium/third_party/WebKit/Source/core/frame/RemoteFrame.cpp b/chromium/third_party/WebKit/Source/core/frame/RemoteFrame.cpp
index 7c2e6635b53..9c303245770 100644
--- a/chromium/third_party/WebKit/Source/core/frame/RemoteFrame.cpp
+++ b/chromium/third_party/WebKit/Source/core/frame/RemoteFrame.cpp
@@ -88,6 +88,8 @@ void RemoteFrame::reload(FrameLoadType frameLoadType, ClientRedirectPolicy clien
void RemoteFrame::detach(FrameDetachType type)
{
+ m_isDetaching = true;
+
PluginScriptForbiddenScope forbidPluginDestructorScripting;
// Frame::detach() requires the caller to keep a reference to this, since
// otherwise it may clear the last reference to this, causing it to be
diff --git a/chromium/third_party/WebKit/Source/web/WebFrame.cpp b/chromium/third_party/WebKit/Source/web/WebFrame.cpp
index 5ea8859a994..472f8fb6bb8 100644
--- a/chromium/third_party/WebKit/Source/web/WebFrame.cpp
+++ b/chromium/third_party/WebKit/Source/web/WebFrame.cpp
@@ -32,6 +32,8 @@ bool WebFrame::swap(WebFrame* frame)
#if !ENABLE(OILPAN)
RefPtr<WebFrameImplBase> protectThis = toImplBase();
#endif
+ if (oldFrame->isDetaching())
+ return false;
// Unload the current Document in this frame: this calls unload handlers,
// detaches child frames, etc. Since this runs script, make sure this frame