Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(19)

Side by Side Diff: Source/web/WebFrameImpl.cpp

Issue 117493002: Invert the owning relationship between WebFrame and Frame. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Comment clarity? Created 7 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2009 Google Inc. All rights reserved. 2 * Copyright (C) 2009 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are 5 * modification, are permitted provided that the following conditions are
6 * met: 6 * met:
7 * 7 *
8 * * Redistributions of source code must retain the above copyright 8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above 10 * * Redistributions in binary form must reproduce the above
(...skipping 17 matching lines...) Expand all
28 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 */ 29 */
30 30
31 // How ownership works 31 // How ownership works
32 // ------------------- 32 // -------------------
33 // 33 //
34 // Big oh represents a refcounted relationship: owner O--- ownee 34 // Big oh represents a refcounted relationship: owner O--- ownee
35 // 35 //
36 // WebView (for the toplevel frame only) 36 // WebView (for the toplevel frame only)
37 // O 37 // O
38 // | 38 // | WebFrame
39 // | O
40 // | |
39 // Page O------- Frame (m_mainFrame) O-------O FrameView 41 // Page O------- Frame (m_mainFrame) O-------O FrameView
40 // || 42 // ||
41 // || 43 // ||
42 // FrameLoader O-------- WebFrame (via FrameLoaderClient) 44 // FrameLoader
43 // 45 //
44 // FrameLoader and Frame are formerly one object that was split apart because 46 // FrameLoader and Frame are formerly one object that was split apart because
45 // it got too big. They basically have the same lifetime, hence the double line. 47 // it got too big. They basically have the same lifetime, hence the double line.
46 // 48 //
47 // WebFrame is refcounted and has one ref on behalf of the FrameLoader/Frame. 49 // From the perspective of the embedder, WebFrame is simply an object that it
48 // This is not a normal reference counted pointer because that would require 50 // allocates by calling WebFrame::create() and must be freed by calling close().
49 // changing WebKit code that we don't control. Instead, it is created with this 51 // Internally, WebFrame is actually refcounted and it holds a reference to its
50 // ref initially and it is removed when the FrameLoader is getting destroyed. 52 // corresponding Frame in WebCore.
51 //
52 // WebFrames are created in two places, first in WebViewImpl when the root
53 // frame is created, and second in WebFrame::createChildFrame when sub-frames
54 // are created. WebKit will hook up this object to the FrameLoader/Frame
55 // and the refcount will be correct.
56 // 53 //
57 // How frames are destroyed 54 // How frames are destroyed
58 // ------------------------ 55 // ------------------------
59 // 56 //
60 // The main frame is never destroyed and is re-used. The FrameLoader is re-used 57 // The main frame is never destroyed and is re-used. The FrameLoader is re-used
61 // and a reference to the main frame is kept by the Page. 58 // and a reference to the main frame is kept by the Page.
62 // 59 //
63 // When frame content is replaced, all subframes are destroyed. This happens 60 // When frame content is replaced, all subframes are destroyed. This happens
64 // in FrameLoader::detachFromParent for each subframe. 61 // in FrameLoader::detachFromParent for each subframe. detachFromParent()
65 // 62 // calls FrameLoaderClient::detachedFromParent(), which calls
66 // Frame going away causes the FrameLoader to get deleted. In FrameLoader's 63 // WebFrame::frameDetached(). This triggers WebFrame to clear its reference to
67 // destructor, it notifies its client with frameLoaderDestroyed. This derefs 64 // Frame, and also notifies the embedder via WebFrameClient that the frame is
68 // the WebFrame and will cause it to be deleted (unless an external someone 65 // detached. Most embedders will invoke close() on the WebFrame at this point,
69 // is also holding a reference). 66 // triggering its deletion unless something else is still retaining a reference.
70 // 67 //
71 // Thie client is expected to be set whenever the WebFrameImpl is attached to 68 // Thie client is expected to be set whenever the WebFrameImpl is attached to
72 // the DOM. 69 // the DOM.
73 70
74 #include "config.h" 71 #include "config.h"
75 #include "WebFrameImpl.h" 72 #include "WebFrameImpl.h"
76 73
77 #include <algorithm> 74 #include <algorithm>
78 #include "AssociatedURLLoader.h" 75 #include "AssociatedURLLoader.h"
79 #include "DOMUtilitiesPrivate.h" 76 #include "DOMUtilitiesPrivate.h"
(...skipping 2016 matching lines...) Expand 10 before | Expand all | Expand 10 after
2096 { 2093 {
2097 return WebFrameImpl::create(client, generateEmbedderIdentifier()); 2094 return WebFrameImpl::create(client, generateEmbedderIdentifier());
2098 } 2095 }
2099 2096
2100 WebFrameImpl* WebFrameImpl::create(WebFrameClient* client, long long embedderIde ntifier) 2097 WebFrameImpl* WebFrameImpl::create(WebFrameClient* client, long long embedderIde ntifier)
2101 { 2098 {
2102 return adoptRef(new WebFrameImpl(client, embedderIdentifier)).leakRef(); 2099 return adoptRef(new WebFrameImpl(client, embedderIdentifier)).leakRef();
2103 } 2100 }
2104 2101
2105 WebFrameImpl::WebFrameImpl(WebFrameClient* client, long long embedderIdentifier) 2102 WebFrameImpl::WebFrameImpl(WebFrameClient* client, long long embedderIdentifier)
2106 : FrameDestructionObserver(0) 2103 : m_frameInit(WebFrameInit::create(this, embedderIdentifier))
2107 , m_frameInit(WebFrameInit::create(this, embedderIdentifier))
2108 , m_client(client) 2104 , m_client(client)
2109 , m_permissionClient(0) 2105 , m_permissionClient(0)
2110 , m_currentActiveMatchFrame(0) 2106 , m_currentActiveMatchFrame(0)
2111 , m_activeMatchIndexInCurrentFrame(-1) 2107 , m_activeMatchIndexInCurrentFrame(-1)
2112 , m_locatingActiveRect(false) 2108 , m_locatingActiveRect(false)
2113 , m_resumeScopingFromRange(0) 2109 , m_resumeScopingFromRange(0)
2114 , m_lastMatchCount(-1) 2110 , m_lastMatchCount(-1)
2115 , m_totalMatchCount(-1) 2111 , m_totalMatchCount(-1)
2116 , m_framesScopingCount(-1) 2112 , m_framesScopingCount(-1)
2117 , m_findRequestIdentifier(-1) 2113 , m_findRequestIdentifier(-1)
2118 , m_scopingInProgress(false) 2114 , m_scopingInProgress(false)
2119 , m_lastFindRequestCompletedWithNoMatches(false) 2115 , m_lastFindRequestCompletedWithNoMatches(false)
2120 , m_nextInvalidateAfter(0) 2116 , m_nextInvalidateAfter(0)
2121 , m_findMatchMarkersVersion(0) 2117 , m_findMatchMarkersVersion(0)
2122 , m_findMatchRectsAreValid(false) 2118 , m_findMatchRectsAreValid(false)
2123 , m_inputEventsScaleFactorForEmulation(1) 2119 , m_inputEventsScaleFactorForEmulation(1)
2124 { 2120 {
2125 blink::Platform::current()->incrementStatsCounter(webFrameActiveCount); 2121 blink::Platform::current()->incrementStatsCounter(webFrameActiveCount);
2126 frameCount++; 2122 frameCount++;
2127 } 2123 }
2128 2124
2129 WebFrameImpl::~WebFrameImpl() 2125 WebFrameImpl::~WebFrameImpl()
2130 { 2126 {
2131 blink::Platform::current()->decrementStatsCounter(webFrameActiveCount); 2127 blink::Platform::current()->decrementStatsCounter(webFrameActiveCount);
2132 frameCount--; 2128 frameCount--;
2133 2129
2134 cancelPendingScopingEffort(); 2130 cancelPendingScopingEffort();
2135 } 2131 }
2136 2132
2137 void WebFrameImpl::setWebCoreFrame(WebCore::Frame* frame) 2133 void WebFrameImpl::setWebCoreFrame(PassRefPtr<WebCore::Frame> frame)
2138 { 2134 {
2139 ASSERT(frame); 2135 m_frame = frame;
2140 observeFrame(frame);
2141 } 2136 }
2142 2137
2143 void WebFrameImpl::initializeAsMainFrame(WebCore::Page* page) 2138 void WebFrameImpl::initializeAsMainFrame(WebCore::Page* page)
2144 { 2139 {
2145 // FIXME: This whole function can go away once ownerhip of WebFrame is rever sed.
2146 // Page should create it's main WebFrame, not have FrameLoader do it only
2147 // to have to mark the frame as main later.
2148 m_frameInit->setFrameHost(&page->frameHost()); 2140 m_frameInit->setFrameHost(&page->frameHost());
2149 RefPtr<Frame> mainFrame = Frame::create(m_frameInit); 2141 setWebCoreFrame(Frame::create(m_frameInit));
2150 setWebCoreFrame(mainFrame.get());
2151
2152 // Add reference on behalf of FrameLoader. See comments in
2153 // WebFrameLoaderClient::frameLoaderDestroyed for more info.
2154 ref();
2155 2142
2156 // We must call init() after m_frame is assigned because it is referenced 2143 // We must call init() after m_frame is assigned because it is referenced
2157 // during init(). 2144 // during init().
2158 frame()->init(); 2145 m_frame->init();
2159 } 2146 }
2160 2147
2161 PassRefPtr<Frame> WebFrameImpl::createChildFrame(const FrameLoadRequest& request , HTMLFrameOwnerElement* ownerElement) 2148 PassRefPtr<Frame> WebFrameImpl::createChildFrame(const FrameLoadRequest& request , HTMLFrameOwnerElement* ownerElement)
2162 { 2149 {
2163 ASSERT(m_client); 2150 ASSERT(m_client);
2164 WebFrameImpl* webframe = toWebFrameImpl(m_client->createChildFrame(this, req uest.frameName())); 2151 WebFrameImpl* webframe = toWebFrameImpl(m_client->createChildFrame(this, req uest.frameName()));
2165 2152
2166 // Add an extra ref on behalf of the page/FrameLoader, which references the
2167 // WebFrame via the FrameLoaderClient interface. See the comment at the top
2168 // of this file for more info.
2169 webframe->ref();
2170
2171 webframe->m_frameInit->setFrameHost(frame()->host()); 2153 webframe->m_frameInit->setFrameHost(frame()->host());
2172 webframe->m_frameInit->setOwnerElement(ownerElement); 2154 webframe->m_frameInit->setOwnerElement(ownerElement);
2173 RefPtr<Frame> childFrame = Frame::create(webframe->m_frameInit); 2155 RefPtr<Frame> childFrame = Frame::create(webframe->m_frameInit);
2174 webframe->setWebCoreFrame(childFrame.get()); 2156 webframe->setWebCoreFrame(childFrame);
2175 2157
2176 childFrame->tree().setName(request.frameName()); 2158 childFrame->tree().setName(request.frameName());
2177 2159
2178 frame()->tree().appendChild(childFrame); 2160 frame()->tree().appendChild(childFrame);
2179 2161
2180 // Frame::init() can trigger onload event in the parent frame, 2162 // Frame::init() can trigger onload event in the parent frame,
2181 // which may detach this frame and trigger a null-pointer access 2163 // which may detach this frame and trigger a null-pointer access
2182 // in FrameTree::removeChild. Move init() after appendChild call 2164 // in FrameTree::removeChild. Move init() after appendChild call
2183 // so that webframe->mFrame is in the tree before triggering 2165 // so that webframe->mFrame is in the tree before triggering
2184 // onload event handler. 2166 // onload event handler.
(...skipping 310 matching lines...) Expand 10 before | Expand all | Expand 10 after
2495 ScriptValue result = frame()->script().executeScriptInMainWorldAndReturnValu e(ScriptSourceCode(script)); 2477 ScriptValue result = frame()->script().executeScriptInMainWorldAndReturnValu e(ScriptSourceCode(script));
2496 2478
2497 String scriptResult; 2479 String scriptResult;
2498 if (!result.getString(scriptResult)) 2480 if (!result.getString(scriptResult))
2499 return; 2481 return;
2500 2482
2501 if (!frame()->navigationScheduler().locationChangePending()) 2483 if (!frame()->navigationScheduler().locationChangePending())
2502 frame()->document()->loader()->replaceDocument(scriptResult, ownerDocume nt.get()); 2484 frame()->document()->loader()->replaceDocument(scriptResult, ownerDocume nt.get());
2503 } 2485 }
2504 2486
2505 void WebFrameImpl::willDetachFrameHost() 2487 void WebFrameImpl::willDetachParent()
2506 { 2488 {
2507 // FIXME: This should never be called if the Frame has already been detached ?
2508 if (!frame() || !frame()->page())
2509 return;
2510
2511 // Do not expect string scoping results from any frames that got detached 2489 // Do not expect string scoping results from any frames that got detached
2512 // in the middle of the operation. 2490 // in the middle of the operation.
2513 if (m_scopingInProgress) { 2491 if (m_scopingInProgress) {
2514 2492
2515 // There is a possibility that the frame being detached was the only 2493 // There is a possibility that the frame being detached was the only
2516 // pending one. We need to make sure final replies can be sent. 2494 // pending one. We need to make sure final replies can be sent.
2517 flushCurrentScopingEffort(m_findRequestIdentifier); 2495 flushCurrentScopingEffort(m_findRequestIdentifier);
2518 2496
2519 cancelPendingScopingEffort(); 2497 cancelPendingScopingEffort();
2520 } 2498 }
2521 } 2499 }
2522 2500
2523 } // namespace blink 2501 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698