Home | History | Annotate | Download | only in UIProcess
      1 /*
      2  * Copyright (C) 2010, 2011 Apple Inc. All rights reserved.
      3  *
      4  * Redistribution and use in source and binary forms, with or without
      5  * modification, are permitted provided that the following conditions
      6  * are met:
      7  * 1. Redistributions of source code must retain the above copyright
      8  *    notice, this list of conditions and the following disclaimer.
      9  * 2. Redistributions in binary form must reproduce the above copyright
     10  *    notice, this list of conditions and the following disclaimer in the
     11  *    documentation and/or other materials provided with the distribution.
     12  *
     13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
     14  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
     15  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     16  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
     17  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     18  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     19  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     20  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     21  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     22  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
     23  * THE POSSIBILITY OF SUCH DAMAGE.
     24  */
     25 
     26 #include "config.h"
     27 #include "WebPageProxy.h"
     28 
     29 #include "AuthenticationChallengeProxy.h"
     30 #include "AuthenticationDecisionListener.h"
     31 #include "DataReference.h"
     32 #include "DownloadProxy.h"
     33 #include "DrawingAreaProxy.h"
     34 #include "FindIndicator.h"
     35 #include "MessageID.h"
     36 #include "NativeWebKeyboardEvent.h"
     37 #include "NativeWebMouseEvent.h"
     38 #include "PageClient.h"
     39 #include "PrintInfo.h"
     40 #include "SessionState.h"
     41 #include "StringPairVector.h"
     42 #include "TextChecker.h"
     43 #include "TextCheckerState.h"
     44 #include "WKContextPrivate.h"
     45 #include "WebBackForwardList.h"
     46 #include "WebBackForwardListItem.h"
     47 #include "WebCertificateInfo.h"
     48 #include "WebContext.h"
     49 #include "WebContextMenuProxy.h"
     50 #include "WebContextUserMessageCoders.h"
     51 #include "WebCoreArgumentCoders.h"
     52 #include "WebData.h"
     53 #include "WebEditCommandProxy.h"
     54 #include "WebEvent.h"
     55 #include "WebFormSubmissionListenerProxy.h"
     56 #include "WebFramePolicyListenerProxy.h"
     57 #include "WebFullScreenManagerProxy.h"
     58 #include "WebInspectorProxy.h"
     59 #include "WebOpenPanelResultListenerProxy.h"
     60 #include "WebPageCreationParameters.h"
     61 #include "WebPageGroup.h"
     62 #include "WebPageGroupData.h"
     63 #include "WebPageMessages.h"
     64 #include "WebPopupItem.h"
     65 #include "WebPopupMenuProxy.h"
     66 #include "WebPreferences.h"
     67 #include "WebProcessMessages.h"
     68 #include "WebProcessProxy.h"
     69 #include "WebProtectionSpace.h"
     70 #include "WebSecurityOrigin.h"
     71 #include "WebURLRequest.h"
     72 #include <WebCore/DragData.h>
     73 #include <WebCore/FloatRect.h>
     74 #include <WebCore/FocusDirection.h>
     75 #include <WebCore/MIMETypeRegistry.h>
     76 #include <WebCore/WindowFeatures.h>
     77 #include <stdio.h>
     78 
     79 #if PLATFORM(WIN)
     80 #include "WebDragSource.h"
     81 #include <WebCore/BitmapInfo.h>
     82 #include <WebCore/COMPtr.h>
     83 #include <WebCore/WCDataObject.h>
     84 #include <shlobj.h>
     85 #endif
     86 
     87 #ifndef NDEBUG
     88 #include <wtf/RefCountedLeakCounter.h>
     89 #endif
     90 
     91 // This controls what strategy we use for mouse wheel coalesing.
     92 #define MERGE_WHEEL_EVENTS 0
     93 
     94 #define MESSAGE_CHECK(assertion) MESSAGE_CHECK_BASE(assertion, process()->connection())
     95 
     96 using namespace WebCore;
     97 
     98 namespace WebKit {
     99 
    100 WKPageDebugPaintFlags WebPageProxy::s_debugPaintFlags = 0;
    101 
    102 #ifndef NDEBUG
    103 static WTF::RefCountedLeakCounter webPageProxyCounter("WebPageProxy");
    104 #endif
    105 
    106 PassRefPtr<WebPageProxy> WebPageProxy::create(PageClient* pageClient, PassRefPtr<WebProcessProxy> process, WebPageGroup* pageGroup, uint64_t pageID)
    107 {
    108     return adoptRef(new WebPageProxy(pageClient, process, pageGroup, pageID));
    109 }
    110 
    111 WebPageProxy::WebPageProxy(PageClient* pageClient, PassRefPtr<WebProcessProxy> process, WebPageGroup* pageGroup, uint64_t pageID)
    112     : m_pageClient(pageClient)
    113     , m_process(process)
    114     , m_pageGroup(pageGroup)
    115     , m_mainFrame(0)
    116     , m_userAgent(standardUserAgent())
    117     , m_geolocationPermissionRequestManager(this)
    118     , m_estimatedProgress(0)
    119     , m_isInWindow(m_pageClient->isViewInWindow())
    120     , m_isVisible(m_pageClient->isViewVisible())
    121     , m_backForwardList(WebBackForwardList::create(this))
    122     , m_textZoomFactor(1)
    123     , m_pageZoomFactor(1)
    124     , m_viewScaleFactor(1)
    125     , m_drawsBackground(true)
    126     , m_drawsTransparentBackground(false)
    127     , m_areMemoryCacheClientCallsEnabled(true)
    128     , m_useFixedLayout(false)
    129     , m_isValid(true)
    130     , m_isClosed(false)
    131     , m_isInPrintingMode(false)
    132     , m_isPerformingDOMPrintOperation(false)
    133     , m_inDecidePolicyForMIMEType(false)
    134     , m_syncMimeTypePolicyActionIsValid(false)
    135     , m_syncMimeTypePolicyAction(PolicyUse)
    136     , m_syncMimeTypePolicyDownloadID(0)
    137     , m_inDecidePolicyForNavigationAction(false)
    138     , m_syncNavigationActionPolicyActionIsValid(false)
    139     , m_syncNavigationActionPolicyAction(PolicyUse)
    140     , m_syncNavigationActionPolicyDownloadID(0)
    141     , m_processingWheelEvent(false)
    142     , m_processingMouseMoveEvent(false)
    143     , m_pageID(pageID)
    144 #if PLATFORM(MAC)
    145     , m_isSmartInsertDeleteEnabled(TextChecker::isSmartInsertDeleteEnabled())
    146 #endif
    147     , m_spellDocumentTag(0)
    148     , m_hasSpellDocumentTag(false)
    149     , m_pendingLearnOrIgnoreWordMessageCount(0)
    150     , m_mainFrameHasCustomRepresentation(false)
    151     , m_currentDragOperation(DragOperationNone)
    152     , m_mainFrameHasHorizontalScrollbar(false)
    153     , m_mainFrameHasVerticalScrollbar(false)
    154     , m_mainFrameIsPinnedToLeftSide(false)
    155     , m_mainFrameIsPinnedToRightSide(false)
    156 {
    157 #ifndef NDEBUG
    158     webPageProxyCounter.increment();
    159 #endif
    160 
    161     WebContext::statistics().wkPageCount++;
    162 
    163     m_pageGroup->addPage(this);
    164 }
    165 
    166 WebPageProxy::~WebPageProxy()
    167 {
    168     if (!m_isClosed)
    169         close();
    170 
    171     WebContext::statistics().wkPageCount--;
    172 
    173     if (m_hasSpellDocumentTag)
    174         TextChecker::closeSpellDocumentWithTag(m_spellDocumentTag);
    175 
    176     m_pageGroup->removePage(this);
    177 
    178 #ifndef NDEBUG
    179     webPageProxyCounter.decrement();
    180 #endif
    181 }
    182 
    183 WebProcessProxy* WebPageProxy::process() const
    184 {
    185     return m_process.get();
    186 }
    187 
    188 bool WebPageProxy::isValid()
    189 {
    190     // A page that has been explicitly closed is never valid.
    191     if (m_isClosed)
    192         return false;
    193 
    194     return m_isValid;
    195 }
    196 
    197 void WebPageProxy::setDrawingArea(PassOwnPtr<DrawingAreaProxy> drawingArea)
    198 {
    199     if (drawingArea == m_drawingArea)
    200         return;
    201 
    202     m_drawingArea = drawingArea;
    203 }
    204 
    205 void WebPageProxy::initializeLoaderClient(const WKPageLoaderClient* loadClient)
    206 {
    207     m_loaderClient.initialize(loadClient);
    208 }
    209 
    210 void WebPageProxy::initializePolicyClient(const WKPagePolicyClient* policyClient)
    211 {
    212     m_policyClient.initialize(policyClient);
    213 }
    214 
    215 void WebPageProxy::initializeFormClient(const WKPageFormClient* formClient)
    216 {
    217     m_formClient.initialize(formClient);
    218 }
    219 
    220 void WebPageProxy::initializeResourceLoadClient(const WKPageResourceLoadClient* client)
    221 {
    222     m_resourceLoadClient.initialize(client);
    223 }
    224 
    225 void WebPageProxy::initializeUIClient(const WKPageUIClient* client)
    226 {
    227     if (!isValid())
    228         return;
    229 
    230     m_uiClient.initialize(client);
    231 
    232     process()->send(Messages::WebPage::SetCanRunBeforeUnloadConfirmPanel(m_uiClient.canRunBeforeUnloadConfirmPanel()), m_pageID);
    233     process()->send(Messages::WebPage::SetCanRunModal(m_uiClient.canRunModal()), m_pageID);
    234 }
    235 
    236 void WebPageProxy::initializeFindClient(const WKPageFindClient* client)
    237 {
    238     m_findClient.initialize(client);
    239 }
    240 
    241 void WebPageProxy::initializeContextMenuClient(const WKPageContextMenuClient* client)
    242 {
    243     m_contextMenuClient.initialize(client);
    244 }
    245 
    246 void WebPageProxy::reattachToWebProcess()
    247 {
    248     ASSERT(!isValid());
    249 
    250     m_isValid = true;
    251 
    252     m_process = m_process->context()->relaunchProcessIfNecessary();
    253     process()->addExistingWebPage(this, m_pageID);
    254 
    255     initializeWebPage();
    256 
    257     m_pageClient->didRelaunchProcess();
    258 }
    259 
    260 void WebPageProxy::reattachToWebProcessWithItem(WebBackForwardListItem* item)
    261 {
    262     if (item && item != m_backForwardList->currentItem())
    263         m_backForwardList->goToItem(item);
    264 
    265     reattachToWebProcess();
    266 
    267     if (!item)
    268         return;
    269 
    270     SandboxExtension::Handle sandboxExtensionHandle;
    271     initializeSandboxExtensionHandle(KURL(KURL(), item->url()), sandboxExtensionHandle);
    272     process()->send(Messages::WebPage::GoToBackForwardItem(item->itemID(), sandboxExtensionHandle), m_pageID);
    273 }
    274 
    275 void WebPageProxy::initializeWebPage()
    276 {
    277     ASSERT(isValid());
    278 
    279     BackForwardListItemVector items = m_backForwardList->entries();
    280     for (size_t i = 0; i < items.size(); ++i)
    281         process()->registerNewWebBackForwardListItem(items[i].get());
    282 
    283     m_drawingArea = m_pageClient->createDrawingAreaProxy();
    284     ASSERT(m_drawingArea);
    285 
    286     process()->send(Messages::WebProcess::CreateWebPage(m_pageID, creationParameters()), 0);
    287 }
    288 
    289 void WebPageProxy::close()
    290 {
    291     if (!isValid())
    292         return;
    293 
    294     m_isClosed = true;
    295 
    296     m_backForwardList->pageClosed();
    297     m_pageClient->pageClosed();
    298 
    299     process()->disconnectFramesFromPage(this);
    300     m_mainFrame = 0;
    301 
    302 #if ENABLE(INSPECTOR)
    303     if (m_inspector) {
    304         m_inspector->invalidate();
    305         m_inspector = 0;
    306     }
    307 #endif
    308 
    309 #if ENABLE(FULLSCREEN_API)
    310     if (m_fullScreenManager) {
    311         m_fullScreenManager->invalidate();
    312         m_fullScreenManager = 0;
    313     }
    314 #endif
    315 
    316     if (m_openPanelResultListener) {
    317         m_openPanelResultListener->invalidate();
    318         m_openPanelResultListener = 0;
    319     }
    320 
    321     m_geolocationPermissionRequestManager.invalidateRequests();
    322 
    323     m_toolTip = String();
    324 
    325     m_mainFrameHasHorizontalScrollbar = false;
    326     m_mainFrameHasVerticalScrollbar = false;
    327 
    328     m_mainFrameIsPinnedToLeftSide = false;
    329     m_mainFrameIsPinnedToRightSide = false;
    330 
    331     invalidateCallbackMap(m_voidCallbacks);
    332     invalidateCallbackMap(m_dataCallbacks);
    333     invalidateCallbackMap(m_stringCallbacks);
    334     m_loadDependentStringCallbackIDs.clear();
    335     invalidateCallbackMap(m_scriptValueCallbacks);
    336     invalidateCallbackMap(m_computedPagesCallbacks);
    337 
    338     Vector<WebEditCommandProxy*> editCommandVector;
    339     copyToVector(m_editCommandSet, editCommandVector);
    340     m_editCommandSet.clear();
    341     for (size_t i = 0, size = editCommandVector.size(); i < size; ++i)
    342         editCommandVector[i]->invalidate();
    343 
    344     m_activePopupMenu = 0;
    345 
    346     m_estimatedProgress = 0.0;
    347 
    348     m_loaderClient.initialize(0);
    349     m_policyClient.initialize(0);
    350     m_uiClient.initialize(0);
    351 
    352     m_drawingArea.clear();
    353 
    354     process()->send(Messages::WebPage::Close(), m_pageID);
    355     process()->removeWebPage(m_pageID);
    356 }
    357 
    358 bool WebPageProxy::tryClose()
    359 {
    360     if (!isValid())
    361         return true;
    362 
    363     process()->send(Messages::WebPage::TryClose(), m_pageID);
    364     return false;
    365 }
    366 
    367 void WebPageProxy::initializeSandboxExtensionHandle(const KURL& url, SandboxExtension::Handle& sandboxExtensionHandle)
    368 {
    369     if (!url.isLocalFile())
    370         return;
    371 
    372     // Don't give the inspector full access to the file system.
    373     if (WebInspectorProxy::isInspectorPage(this))
    374         return;
    375 
    376     SandboxExtension::createHandle("/", SandboxExtension::ReadOnly, sandboxExtensionHandle);
    377 }
    378 
    379 void WebPageProxy::loadURL(const String& url)
    380 {
    381     setPendingAPIRequestURL(url);
    382 
    383     if (!isValid())
    384         reattachToWebProcess();
    385 
    386     SandboxExtension::Handle sandboxExtensionHandle;
    387     initializeSandboxExtensionHandle(KURL(KURL(), url), sandboxExtensionHandle);
    388     process()->send(Messages::WebPage::LoadURL(url, sandboxExtensionHandle), m_pageID);
    389 }
    390 
    391 void WebPageProxy::loadURLRequest(WebURLRequest* urlRequest)
    392 {
    393     setPendingAPIRequestURL(urlRequest->resourceRequest().url());
    394 
    395     if (!isValid())
    396         reattachToWebProcess();
    397 
    398     SandboxExtension::Handle sandboxExtensionHandle;
    399     initializeSandboxExtensionHandle(urlRequest->resourceRequest().url(), sandboxExtensionHandle);
    400     process()->send(Messages::WebPage::LoadURLRequest(urlRequest->resourceRequest(), sandboxExtensionHandle), m_pageID);
    401 }
    402 
    403 void WebPageProxy::loadHTMLString(const String& htmlString, const String& baseURL)
    404 {
    405     if (!isValid())
    406         reattachToWebProcess();
    407 
    408     process()->send(Messages::WebPage::LoadHTMLString(htmlString, baseURL), m_pageID);
    409 }
    410 
    411 void WebPageProxy::loadAlternateHTMLString(const String& htmlString, const String& baseURL, const String& unreachableURL)
    412 {
    413     if (!isValid())
    414         reattachToWebProcess();
    415 
    416     if (m_mainFrame)
    417         m_mainFrame->setUnreachableURL(unreachableURL);
    418 
    419     process()->send(Messages::WebPage::LoadAlternateHTMLString(htmlString, baseURL, unreachableURL), m_pageID);
    420 }
    421 
    422 void WebPageProxy::loadPlainTextString(const String& string)
    423 {
    424     if (!isValid())
    425         reattachToWebProcess();
    426 
    427     process()->send(Messages::WebPage::LoadPlainTextString(string), m_pageID);
    428 }
    429 
    430 void WebPageProxy::stopLoading()
    431 {
    432     if (!isValid())
    433         return;
    434     process()->send(Messages::WebPage::StopLoading(), m_pageID);
    435 }
    436 
    437 void WebPageProxy::reload(bool reloadFromOrigin)
    438 {
    439     if (m_backForwardList->currentItem())
    440         setPendingAPIRequestURL(m_backForwardList->currentItem()->url());
    441 
    442     if (!isValid()) {
    443         reattachToWebProcessWithItem(m_backForwardList->currentItem());
    444         return;
    445     }
    446 
    447     process()->send(Messages::WebPage::Reload(reloadFromOrigin), m_pageID);
    448 }
    449 
    450 void WebPageProxy::goForward()
    451 {
    452     if (isValid() && !canGoForward())
    453         return;
    454 
    455     WebBackForwardListItem* forwardItem = m_backForwardList->forwardItem();
    456     if (forwardItem)
    457         setPendingAPIRequestURL(forwardItem->url());
    458 
    459     if (!isValid()) {
    460         reattachToWebProcessWithItem(forwardItem);
    461         return;
    462     }
    463 
    464     SandboxExtension::Handle sandboxExtensionHandle;
    465     initializeSandboxExtensionHandle(KURL(KURL(), forwardItem->url()), sandboxExtensionHandle);
    466     process()->send(Messages::WebPage::GoForward(forwardItem->itemID(), sandboxExtensionHandle), m_pageID);
    467 }
    468 
    469 bool WebPageProxy::canGoForward() const
    470 {
    471     return m_backForwardList->forwardItem();
    472 }
    473 
    474 void WebPageProxy::goBack()
    475 {
    476     if (isValid() && !canGoBack())
    477         return;
    478 
    479     WebBackForwardListItem* backItem = m_backForwardList->backItem();
    480     if (backItem)
    481         setPendingAPIRequestURL(backItem->url());
    482 
    483     if (!isValid()) {
    484         reattachToWebProcessWithItem(backItem);
    485         return;
    486     }
    487 
    488     SandboxExtension::Handle sandboxExtensionHandle;
    489     initializeSandboxExtensionHandle(KURL(KURL(), backItem->url()), sandboxExtensionHandle);
    490     process()->send(Messages::WebPage::GoBack(backItem->itemID(), sandboxExtensionHandle), m_pageID);
    491 }
    492 
    493 bool WebPageProxy::canGoBack() const
    494 {
    495     return m_backForwardList->backItem();
    496 }
    497 
    498 void WebPageProxy::goToBackForwardItem(WebBackForwardListItem* item)
    499 {
    500     if (!isValid()) {
    501         reattachToWebProcessWithItem(item);
    502         return;
    503     }
    504 
    505     setPendingAPIRequestURL(item->url());
    506 
    507     SandboxExtension::Handle sandboxExtensionHandle;
    508     initializeSandboxExtensionHandle(KURL(KURL(), item->url()), sandboxExtensionHandle);
    509     process()->send(Messages::WebPage::GoToBackForwardItem(item->itemID(), sandboxExtensionHandle), m_pageID);
    510 }
    511 
    512 void WebPageProxy::didChangeBackForwardList(WebBackForwardListItem* added, Vector<RefPtr<APIObject> >* removed)
    513 {
    514     m_loaderClient.didChangeBackForwardList(this, added, removed);
    515 }
    516 
    517 void WebPageProxy::shouldGoToBackForwardListItem(uint64_t itemID, bool& shouldGoToBackForwardItem)
    518 {
    519     WebBackForwardListItem* item = process()->webBackForwardItem(itemID);
    520     shouldGoToBackForwardItem = item && m_loaderClient.shouldGoToBackForwardListItem(this, item);
    521 }
    522 
    523 bool WebPageProxy::canShowMIMEType(const String& mimeType) const
    524 {
    525     if (MIMETypeRegistry::isSupportedNonImageMIMEType(mimeType))
    526         return true;
    527 
    528     if (MIMETypeRegistry::isSupportedImageMIMEType(mimeType))
    529         return true;
    530 
    531     if (mimeType.startsWith("text/", false))
    532         return !MIMETypeRegistry::isUnsupportedTextMIMEType(mimeType);
    533 
    534     String newMimeType = mimeType;
    535     PluginInfoStore::Plugin plugin = m_process->context()->pluginInfoStore()->findPlugin(newMimeType, KURL());
    536     if (!plugin.path.isNull())
    537         return true;
    538 
    539     return false;
    540 }
    541 
    542 void WebPageProxy::setDrawsBackground(bool drawsBackground)
    543 {
    544     if (m_drawsBackground == drawsBackground)
    545         return;
    546 
    547     m_drawsBackground = drawsBackground;
    548 
    549     if (isValid())
    550         process()->send(Messages::WebPage::SetDrawsBackground(drawsBackground), m_pageID);
    551 }
    552 
    553 void WebPageProxy::setDrawsTransparentBackground(bool drawsTransparentBackground)
    554 {
    555     if (m_drawsTransparentBackground == drawsTransparentBackground)
    556         return;
    557 
    558     m_drawsTransparentBackground = drawsTransparentBackground;
    559 
    560     if (isValid())
    561         process()->send(Messages::WebPage::SetDrawsTransparentBackground(drawsTransparentBackground), m_pageID);
    562 }
    563 
    564 void WebPageProxy::viewWillStartLiveResize()
    565 {
    566     if (!isValid())
    567         return;
    568     process()->send(Messages::WebPage::ViewWillStartLiveResize(), m_pageID);
    569 }
    570 
    571 void WebPageProxy::viewWillEndLiveResize()
    572 {
    573     if (!isValid())
    574         return;
    575     process()->send(Messages::WebPage::ViewWillEndLiveResize(), m_pageID);
    576 }
    577 
    578 void WebPageProxy::setViewNeedsDisplay(const IntRect& rect)
    579 {
    580     m_pageClient->setViewNeedsDisplay(rect);
    581 }
    582 
    583 void WebPageProxy::displayView()
    584 {
    585     m_pageClient->displayView();
    586 }
    587 
    588 void WebPageProxy::scrollView(const IntRect& scrollRect, const IntSize& scrollOffset)
    589 {
    590     m_pageClient->scrollView(scrollRect, scrollOffset);
    591 }
    592 
    593 void WebPageProxy::viewStateDidChange(ViewStateFlags flags)
    594 {
    595     if (!isValid())
    596         return;
    597 
    598     if (flags & ViewIsFocused)
    599         process()->send(Messages::WebPage::SetFocused(m_pageClient->isViewFocused()), m_pageID);
    600 
    601     if (flags & ViewWindowIsActive)
    602         process()->send(Messages::WebPage::SetActive(m_pageClient->isViewWindowActive()), m_pageID);
    603 
    604     if (flags & ViewIsVisible) {
    605         bool isVisible = m_pageClient->isViewVisible();
    606         if (isVisible != m_isVisible) {
    607             m_isVisible = isVisible;
    608             m_drawingArea->visibilityDidChange();
    609             m_drawingArea->setPageIsVisible(isVisible);
    610         }
    611     }
    612 
    613     if (flags & ViewIsInWindow) {
    614         bool isInWindow = m_pageClient->isViewInWindow();
    615         if (m_isInWindow != isInWindow) {
    616             m_isInWindow = isInWindow;
    617             process()->send(Messages::WebPage::SetIsInWindow(isInWindow), m_pageID);
    618         }
    619     }
    620 
    621     if (flags & (ViewWindowIsActive | ViewIsVisible))
    622         m_drawingArea->setBackingStoreIsDiscardable(!m_pageClient->isViewWindowActive() || !isViewVisible());
    623 }
    624 
    625 IntSize WebPageProxy::viewSize() const
    626 {
    627     return m_pageClient->viewSize();
    628 }
    629 
    630 void WebPageProxy::setInitialFocus(bool forward)
    631 {
    632     if (!isValid())
    633         return;
    634     process()->send(Messages::WebPage::SetInitialFocus(forward), m_pageID);
    635 }
    636 
    637 void WebPageProxy::setWindowResizerSize(const IntSize& windowResizerSize)
    638 {
    639     if (!isValid())
    640         return;
    641     process()->send(Messages::WebPage::SetWindowResizerSize(windowResizerSize), m_pageID);
    642 }
    643 
    644 void WebPageProxy::validateCommand(const String& commandName, PassRefPtr<ValidateCommandCallback> callback)
    645 {
    646     if (!isValid()) {
    647         callback->invalidate();
    648         return;
    649     }
    650 
    651     uint64_t callbackID = callback->callbackID();
    652     m_validateCommandCallbacks.set(callbackID, callback.get());
    653     process()->send(Messages::WebPage::ValidateCommand(commandName, callbackID), m_pageID);
    654 }
    655 
    656 void WebPageProxy::executeEditCommand(const String& commandName)
    657 {
    658     if (!isValid())
    659         return;
    660 
    661     process()->send(Messages::WebPage::ExecuteEditCommand(commandName), m_pageID);
    662 }
    663 
    664 #if PLATFORM(WIN)
    665 WebCore::IntRect WebPageProxy::firstRectForCharacterInSelectedRange(int characterPosition)
    666 {
    667     IntRect resultRect;
    668     process()->sendSync(Messages::WebPage::FirstRectForCharacterInSelectedRange(characterPosition), Messages::WebPage::FirstRectForCharacterInSelectedRange::Reply(resultRect), m_pageID);
    669     return resultRect;
    670 }
    671 
    672 String WebPageProxy::getSelectedText()
    673 {
    674     String text;
    675     process()->sendSync(Messages::WebPage::GetSelectedText(), Messages::WebPage::GetSelectedText::Reply(text), m_pageID);
    676     return text;
    677 }
    678 
    679 bool WebPageProxy::gestureWillBegin(const IntPoint& point)
    680 {
    681     bool canBeginPanning = false;
    682     process()->sendSync(Messages::WebPage::GestureWillBegin(point), Messages::WebPage::GestureWillBegin::Reply(canBeginPanning), m_pageID);
    683     return canBeginPanning;
    684 }
    685 
    686 void WebPageProxy::gestureDidScroll(const IntSize& size)
    687 {
    688     process()->send(Messages::WebPage::GestureDidScroll(size), m_pageID);
    689 }
    690 
    691 void WebPageProxy::gestureDidEnd()
    692 {
    693     process()->send(Messages::WebPage::GestureDidEnd(), m_pageID);
    694 }
    695 
    696 void WebPageProxy::setGestureReachedScrollingLimit(bool limitReached)
    697 {
    698     m_pageClient->setGestureReachedScrollingLimit(limitReached);
    699 }
    700 #endif
    701 
    702 #if ENABLE(TILED_BACKING_STORE)
    703 void WebPageProxy::setActualVisibleContentRect(const IntRect& rect)
    704 {
    705     if (!isValid())
    706         return;
    707 
    708     process()->send(Messages::WebPage::SetActualVisibleContentRect(rect), m_pageID);
    709 }
    710 #endif
    711 
    712 void WebPageProxy::dragEntered(WebCore::DragData* dragData, const String& dragStorageName)
    713 {
    714     SandboxExtension::Handle sandboxExtensionHandle;
    715     performDragControllerAction(DragControllerActionEntered, dragData, dragStorageName, sandboxExtensionHandle);
    716 }
    717 
    718 void WebPageProxy::dragUpdated(WebCore::DragData* dragData, const String& dragStorageName)
    719 {
    720     SandboxExtension::Handle sandboxExtensionHandle;
    721     performDragControllerAction(DragControllerActionUpdated, dragData, dragStorageName, sandboxExtensionHandle);
    722 }
    723 
    724 void WebPageProxy::dragExited(WebCore::DragData* dragData, const String& dragStorageName)
    725 {
    726     SandboxExtension::Handle sandboxExtensionHandle;
    727     performDragControllerAction(DragControllerActionExited, dragData, dragStorageName, sandboxExtensionHandle);
    728 }
    729 
    730 void WebPageProxy::performDrag(WebCore::DragData* dragData, const String& dragStorageName, const SandboxExtension::Handle& sandboxExtensionHandle)
    731 {
    732     performDragControllerAction(DragControllerActionPerformDrag, dragData, dragStorageName, sandboxExtensionHandle);
    733 }
    734 
    735 void WebPageProxy::performDragControllerAction(DragControllerAction action, WebCore::DragData* dragData, const String& dragStorageName, const SandboxExtension::Handle& sandboxExtensionHandle)
    736 {
    737     if (!isValid())
    738         return;
    739 #if PLATFORM(WIN)
    740     // FIXME: We should pass the drag data map only on DragEnter.
    741     process()->send(Messages::WebPage::PerformDragControllerAction(action, dragData->clientPosition(), dragData->globalPosition(),
    742         dragData->draggingSourceOperationMask(), dragData->dragDataMap(), dragData->flags()), m_pageID);
    743 #else
    744     process()->send(Messages::WebPage::PerformDragControllerAction(action, dragData->clientPosition(), dragData->globalPosition(), dragData->draggingSourceOperationMask(), dragStorageName, dragData->flags(), sandboxExtensionHandle), m_pageID);
    745 #endif
    746 }
    747 
    748 void WebPageProxy::didPerformDragControllerAction(uint64_t resultOperation)
    749 {
    750     m_currentDragOperation = static_cast<DragOperation>(resultOperation);
    751 }
    752 
    753 #if PLATFORM(WIN)
    754 
    755 void WebPageProxy::startDragDrop(const IntPoint& imageOrigin, const IntPoint& dragPoint, uint64_t okEffect,
    756     const HashMap<UINT, Vector<String> >& dataMap, const IntSize& dragImageSize, const SharedMemory::Handle& dragImageHandle, bool isLinkDrag)
    757 {
    758     COMPtr<WCDataObject> dataObject;
    759     WCDataObject::createInstance(&dataObject, dataMap);
    760 
    761     RefPtr<SharedMemory> memoryBuffer = SharedMemory::create(dragImageHandle, SharedMemory::ReadOnly);
    762     if (!memoryBuffer)
    763         return;
    764 
    765     RefPtr<WebDragSource> source = WebDragSource::createInstance();
    766     if (!source)
    767         return;
    768 
    769     COMPtr<IDragSourceHelper> helper;
    770     if (FAILED(::CoCreateInstance(CLSID_DragDropHelper, 0, CLSCTX_INPROC_SERVER, IID_IDragSourceHelper, reinterpret_cast<LPVOID*>(&helper))))
    771         return;
    772 
    773     BitmapInfo bitmapInfo = BitmapInfo::create(dragImageSize);
    774     void* bits;
    775     OwnPtr<HBITMAP> hbmp(::CreateDIBSection(0, &bitmapInfo, DIB_RGB_COLORS, &bits, 0, 0));
    776     memcpy(bits, memoryBuffer->data(), memoryBuffer->size());
    777 
    778     SHDRAGIMAGE sdi;
    779     sdi.sizeDragImage.cx = bitmapInfo.bmiHeader.biWidth;
    780     sdi.sizeDragImage.cy = bitmapInfo.bmiHeader.biHeight;
    781     sdi.crColorKey = 0xffffffff;
    782     sdi.hbmpDragImage = hbmp.leakPtr();
    783     sdi.ptOffset.x = dragPoint.x() - imageOrigin.x();
    784     sdi.ptOffset.y = dragPoint.y() - imageOrigin.y();
    785     if (isLinkDrag)
    786         sdi.ptOffset.y = bitmapInfo.bmiHeader.biHeight - sdi.ptOffset.y;
    787 
    788     helper->InitializeFromBitmap(&sdi, dataObject.get());
    789 
    790     DWORD effect = DROPEFFECT_NONE;
    791 
    792     DragOperation operation = DragOperationNone;
    793     if (::DoDragDrop(dataObject.get(), source.get(), okEffect, &effect) == DRAGDROP_S_DROP) {
    794         if (effect & DROPEFFECT_COPY)
    795             operation = DragOperationCopy;
    796         else if (effect & DROPEFFECT_LINK)
    797             operation = DragOperationLink;
    798         else if (effect & DROPEFFECT_MOVE)
    799             operation = DragOperationMove;
    800     }
    801     POINT globalPoint;
    802     ::GetCursorPos(&globalPoint);
    803     POINT localPoint = globalPoint;
    804     ::ScreenToClient(m_pageClient->nativeWindow(), &localPoint);
    805 
    806     dragEnded(localPoint, globalPoint, operation);
    807 }
    808 #endif
    809 
    810 void WebPageProxy::dragEnded(const WebCore::IntPoint& clientPosition, const WebCore::IntPoint& globalPosition, uint64_t operation)
    811 {
    812     if (!isValid())
    813         return;
    814     process()->send(Messages::WebPage::DragEnded(clientPosition, globalPosition, operation), m_pageID);
    815 }
    816 
    817 void WebPageProxy::handleMouseEvent(const NativeWebMouseEvent& event)
    818 {
    819     if (!isValid())
    820         return;
    821 
    822     // NOTE: This does not start the responsiveness timer because mouse move should not indicate interaction.
    823     if (event.type() != WebEvent::MouseMove)
    824         process()->responsivenessTimer()->start();
    825     else {
    826         if (m_processingMouseMoveEvent) {
    827             m_nextMouseMoveEvent = adoptPtr(new NativeWebMouseEvent(event));
    828             return;
    829         }
    830 
    831         m_processingMouseMoveEvent = true;
    832     }
    833 
    834     // <https://bugs.webkit.org/show_bug.cgi?id=57904> We need to keep track of the mouse down event in the case where we
    835     // display a popup menu for select elements. When the user changes the selected item,
    836     // we fake a mouse up event by using this stored down event. This event gets cleared
    837     // when the mouse up message is received from WebProcess.
    838     if (event.type() == WebEvent::MouseDown)
    839         m_currentlyProcessedMouseDownEvent = adoptPtr(new NativeWebMouseEvent(event));
    840 
    841     process()->send(Messages::WebPage::MouseEvent(event), m_pageID);
    842 }
    843 
    844 static PassOwnPtr<WebWheelEvent> coalesceWheelEvents(WebWheelEvent* oldNextWheelEvent, const WebWheelEvent& newWheelEvent)
    845 {
    846 #if MERGE_WHEEL_EVENTS
    847     // Merge model: Combine wheel event deltas (and wheel ticks) into a single wheel event.
    848     if (!oldNextWheelEvent)
    849         return adoptPtr(new WebWheelEvent(newWheelEvent));
    850 
    851     if (oldNextWheelEvent->position() != newWheelEvent.position() || oldNextWheelEvent->modifiers() != newWheelEvent.modifiers() || oldNextWheelEvent->granularity() != newWheelEvent.granularity())
    852         return adoptPtr(new WebWheelEvent(newWheelEvent));
    853 
    854     FloatSize mergedDelta = oldNextWheelEvent->delta() + newWheelEvent.delta();
    855     FloatSize mergedWheelTicks = oldNextWheelEvent->wheelTicks() + newWheelEvent.wheelTicks();
    856 
    857     return adoptPtr(new WebWheelEvent(WebEvent::Wheel, newWheelEvent.position(), newWheelEvent.globalPosition(), mergedDelta, mergedWheelTicks, newWheelEvent.granularity(), newWheelEvent.modifiers(), newWheelEvent.timestamp()));
    858 #else
    859     // Simple model: Just keep the last event, dropping all interim events.
    860     return adoptPtr(new WebWheelEvent(newWheelEvent));
    861 #endif
    862 }
    863 
    864 void WebPageProxy::handleWheelEvent(const WebWheelEvent& event)
    865 {
    866     if (!isValid())
    867         return;
    868 
    869     if (m_processingWheelEvent) {
    870         m_nextWheelEvent = coalesceWheelEvents(m_nextWheelEvent.get(), event);
    871         return;
    872     }
    873 
    874     process()->responsivenessTimer()->start();
    875     process()->send(Messages::WebPage::WheelEvent(event), m_pageID);
    876     m_processingWheelEvent = true;
    877 }
    878 
    879 void WebPageProxy::handleKeyboardEvent(const NativeWebKeyboardEvent& event)
    880 {
    881     if (!isValid())
    882         return;
    883 
    884     m_keyEventQueue.append(event);
    885 
    886     process()->responsivenessTimer()->start();
    887     process()->send(Messages::WebPage::KeyEvent(event), m_pageID);
    888 }
    889 
    890 #if ENABLE(GESTURE_EVENTS)
    891 void WebPageProxy::handleGestureEvent(const WebGestureEvent& event)
    892 {
    893     if (!isValid())
    894         return;
    895 
    896     process()->responsivenessTimer()->start();
    897     process()->send(Messages::WebPage::GestureEvent(event), m_pageID);
    898 }
    899 #endif
    900 
    901 #if ENABLE(TOUCH_EVENTS)
    902 void WebPageProxy::handleTouchEvent(const WebTouchEvent& event)
    903 {
    904     if (!isValid())
    905         return;
    906     process()->send(Messages::WebPage::TouchEvent(event), m_pageID);
    907 }
    908 #endif
    909 
    910 void WebPageProxy::scrollBy(ScrollDirection direction, ScrollGranularity granularity)
    911 {
    912     if (!isValid())
    913         return;
    914 
    915     process()->send(Messages::WebPage::ScrollBy(direction, granularity), m_pageID);
    916 }
    917 
    918 void WebPageProxy::receivedPolicyDecision(PolicyAction action, WebFrameProxy* frame, uint64_t listenerID)
    919 {
    920     if (!isValid())
    921         return;
    922 
    923     uint64_t downloadID = 0;
    924     if (action == PolicyDownload) {
    925         // Create a download proxy.
    926         downloadID = m_process->context()->createDownloadProxy()->downloadID();
    927     }
    928 
    929     // If we received a policy decision while in decidePolicyForMIMEType the decision will
    930     // be sent back to the web process by decidePolicyForMIMEType.
    931     if (m_inDecidePolicyForMIMEType) {
    932         m_syncMimeTypePolicyActionIsValid = true;
    933         m_syncMimeTypePolicyAction = action;
    934         m_syncMimeTypePolicyDownloadID = downloadID;
    935         return;
    936     }
    937 
    938     // If we received a policy decision while in decidePolicyForNavigationAction the decision will
    939     // be sent back to the web process by decidePolicyForNavigationAction.
    940     if (m_inDecidePolicyForNavigationAction) {
    941         m_syncNavigationActionPolicyActionIsValid = true;
    942         m_syncNavigationActionPolicyAction = action;
    943         m_syncNavigationActionPolicyDownloadID = downloadID;
    944         return;
    945     }
    946 
    947     process()->send(Messages::WebPage::DidReceivePolicyDecision(frame->frameID(), listenerID, action, downloadID), m_pageID);
    948 }
    949 
    950 String WebPageProxy::pageTitle() const
    951 {
    952     // Return the null string if there is no main frame (e.g. nothing has been loaded in the page yet, WebProcess has
    953     // crashed, page has been closed).
    954     if (!m_mainFrame)
    955         return String();
    956 
    957     return m_mainFrame->title();
    958 }
    959 
    960 void WebPageProxy::setUserAgent(const String& userAgent)
    961 {
    962     if (m_userAgent == userAgent)
    963         return;
    964     m_userAgent = userAgent;
    965 
    966     if (!isValid())
    967         return;
    968     process()->send(Messages::WebPage::SetUserAgent(m_userAgent), m_pageID);
    969 }
    970 
    971 void WebPageProxy::setApplicationNameForUserAgent(const String& applicationName)
    972 {
    973     if (m_applicationNameForUserAgent == applicationName)
    974         return;
    975 
    976     m_applicationNameForUserAgent = applicationName;
    977     if (!m_customUserAgent.isEmpty())
    978         return;
    979 
    980     setUserAgent(standardUserAgent(m_applicationNameForUserAgent));
    981 }
    982 
    983 void WebPageProxy::setCustomUserAgent(const String& customUserAgent)
    984 {
    985     if (m_customUserAgent == customUserAgent)
    986         return;
    987 
    988     m_customUserAgent = customUserAgent;
    989 
    990     if (m_customUserAgent.isEmpty()) {
    991         setUserAgent(standardUserAgent(m_applicationNameForUserAgent));
    992         return;
    993     }
    994 
    995     setUserAgent(m_customUserAgent);
    996 }
    997 
    998 bool WebPageProxy::supportsTextEncoding() const
    999 {
   1000     return !m_mainFrameHasCustomRepresentation && m_mainFrame && !m_mainFrame->isDisplayingStandaloneImageDocument();
   1001 }
   1002 
   1003 void WebPageProxy::setCustomTextEncodingName(const String& encodingName)
   1004 {
   1005     if (m_customTextEncodingName == encodingName)
   1006         return;
   1007     m_customTextEncodingName = encodingName;
   1008 
   1009     if (!isValid())
   1010         return;
   1011     process()->send(Messages::WebPage::SetCustomTextEncodingName(encodingName), m_pageID);
   1012 }
   1013 
   1014 void WebPageProxy::terminateProcess()
   1015 {
   1016     if (!isValid())
   1017         return;
   1018 
   1019     process()->terminate();
   1020 }
   1021 
   1022 #if !USE(CF) || defined(BUILDING_QT__)
   1023 PassRefPtr<WebData> WebPageProxy::sessionStateData(WebPageProxySessionStateFilterCallback, void* context) const
   1024 {
   1025     // FIXME: Return session state data for saving Page state.
   1026     return 0;
   1027 }
   1028 
   1029 void WebPageProxy::restoreFromSessionStateData(WebData*)
   1030 {
   1031     // FIXME: Restore the Page from the passed in session state data.
   1032 }
   1033 #endif
   1034 
   1035 bool WebPageProxy::supportsTextZoom() const
   1036 {
   1037     if (m_mainFrameHasCustomRepresentation)
   1038         return false;
   1039 
   1040     // FIXME: This should also return false for standalone media and plug-in documents.
   1041     if (!m_mainFrame || m_mainFrame->isDisplayingStandaloneImageDocument())
   1042         return false;
   1043 
   1044     return true;
   1045 }
   1046 
   1047 void WebPageProxy::setTextZoomFactor(double zoomFactor)
   1048 {
   1049     if (!isValid())
   1050         return;
   1051 
   1052     if (m_mainFrameHasCustomRepresentation)
   1053         return;
   1054 
   1055     if (m_textZoomFactor == zoomFactor)
   1056         return;
   1057 
   1058     m_textZoomFactor = zoomFactor;
   1059     process()->send(Messages::WebPage::SetTextZoomFactor(m_textZoomFactor), m_pageID);
   1060 }
   1061 
   1062 double WebPageProxy::pageZoomFactor() const
   1063 {
   1064     return m_mainFrameHasCustomRepresentation ? m_pageClient->customRepresentationZoomFactor() : m_pageZoomFactor;
   1065 }
   1066 
   1067 void WebPageProxy::setPageZoomFactor(double zoomFactor)
   1068 {
   1069     if (!isValid())
   1070         return;
   1071 
   1072     if (m_mainFrameHasCustomRepresentation) {
   1073         m_pageClient->setCustomRepresentationZoomFactor(zoomFactor);
   1074         return;
   1075     }
   1076 
   1077     if (m_pageZoomFactor == zoomFactor)
   1078         return;
   1079 
   1080     m_pageZoomFactor = zoomFactor;
   1081     process()->send(Messages::WebPage::SetPageZoomFactor(m_pageZoomFactor), m_pageID);
   1082 }
   1083 
   1084 void WebPageProxy::setPageAndTextZoomFactors(double pageZoomFactor, double textZoomFactor)
   1085 {
   1086     if (!isValid())
   1087         return;
   1088 
   1089     if (m_mainFrameHasCustomRepresentation) {
   1090         m_pageClient->setCustomRepresentationZoomFactor(pageZoomFactor);
   1091         return;
   1092     }
   1093 
   1094     if (m_pageZoomFactor == pageZoomFactor && m_textZoomFactor == textZoomFactor)
   1095         return;
   1096 
   1097     m_pageZoomFactor = pageZoomFactor;
   1098     m_textZoomFactor = textZoomFactor;
   1099     process()->send(Messages::WebPage::SetPageAndTextZoomFactors(m_pageZoomFactor, m_textZoomFactor), m_pageID);
   1100 }
   1101 
   1102 void WebPageProxy::scaleWebView(double scale, const IntPoint& origin)
   1103 {
   1104     if (!isValid())
   1105         return;
   1106 
   1107     process()->send(Messages::WebPage::ScaleWebView(scale, origin), m_pageID);
   1108 }
   1109 
   1110 void WebPageProxy::setUseFixedLayout(bool fixed)
   1111 {
   1112     if (!isValid())
   1113         return;
   1114 
   1115     if (fixed == m_useFixedLayout)
   1116         return;
   1117 
   1118     m_useFixedLayout = fixed;
   1119     if (!fixed)
   1120         m_fixedLayoutSize = IntSize();
   1121     process()->send(Messages::WebPage::SetUseFixedLayout(fixed), m_pageID);
   1122 }
   1123 
   1124 void WebPageProxy::setFixedLayoutSize(const IntSize& size)
   1125 {
   1126     if (!isValid())
   1127         return;
   1128 
   1129     if (size == m_fixedLayoutSize)
   1130         return;
   1131 
   1132     m_fixedLayoutSize = size;
   1133     process()->send(Messages::WebPage::SetFixedLayoutSize(size), m_pageID);
   1134 }
   1135 
   1136 void WebPageProxy::viewScaleFactorDidChange(double scaleFactor)
   1137 {
   1138     m_viewScaleFactor = scaleFactor;
   1139 }
   1140 
   1141 void WebPageProxy::setMemoryCacheClientCallsEnabled(bool memoryCacheClientCallsEnabled)
   1142 {
   1143     if (!isValid())
   1144         return;
   1145 
   1146     if (m_areMemoryCacheClientCallsEnabled == memoryCacheClientCallsEnabled)
   1147         return;
   1148 
   1149     m_areMemoryCacheClientCallsEnabled = memoryCacheClientCallsEnabled;
   1150     process()->send(Messages::WebPage::SetMemoryCacheMessagesEnabled(memoryCacheClientCallsEnabled), m_pageID);
   1151 }
   1152 
   1153 void WebPageProxy::findString(const String& string, FindOptions options, unsigned maxMatchCount)
   1154 {
   1155     if (m_mainFrameHasCustomRepresentation)
   1156         m_pageClient->findStringInCustomRepresentation(string, options, maxMatchCount);
   1157     else
   1158         process()->send(Messages::WebPage::FindString(string, options, maxMatchCount), m_pageID);
   1159 }
   1160 
   1161 void WebPageProxy::hideFindUI()
   1162 {
   1163     process()->send(Messages::WebPage::HideFindUI(), m_pageID);
   1164 }
   1165 
   1166 void WebPageProxy::countStringMatches(const String& string, FindOptions options, unsigned maxMatchCount)
   1167 {
   1168     if (m_mainFrameHasCustomRepresentation) {
   1169         m_pageClient->countStringMatchesInCustomRepresentation(string, options, maxMatchCount);
   1170         return;
   1171     }
   1172 
   1173     if (!isValid())
   1174         return;
   1175 
   1176     process()->send(Messages::WebPage::CountStringMatches(string, options, maxMatchCount), m_pageID);
   1177 }
   1178 
   1179 void WebPageProxy::runJavaScriptInMainFrame(const String& script, PassRefPtr<ScriptValueCallback> prpCallback)
   1180 {
   1181     RefPtr<ScriptValueCallback> callback = prpCallback;
   1182     if (!isValid()) {
   1183         callback->invalidate();
   1184         return;
   1185     }
   1186 
   1187     uint64_t callbackID = callback->callbackID();
   1188     m_scriptValueCallbacks.set(callbackID, callback.get());
   1189     process()->send(Messages::WebPage::RunJavaScriptInMainFrame(script, callbackID), m_pageID);
   1190 }
   1191 
   1192 void WebPageProxy::getRenderTreeExternalRepresentation(PassRefPtr<StringCallback> prpCallback)
   1193 {
   1194     RefPtr<StringCallback> callback = prpCallback;
   1195     if (!isValid()) {
   1196         callback->invalidate();
   1197         return;
   1198     }
   1199 
   1200     uint64_t callbackID = callback->callbackID();
   1201     m_stringCallbacks.set(callbackID, callback.get());
   1202     process()->send(Messages::WebPage::GetRenderTreeExternalRepresentation(callbackID), m_pageID);
   1203 }
   1204 
   1205 void WebPageProxy::getSourceForFrame(WebFrameProxy* frame, PassRefPtr<StringCallback> prpCallback)
   1206 {
   1207     RefPtr<StringCallback> callback = prpCallback;
   1208     if (!isValid()) {
   1209         callback->invalidate();
   1210         return;
   1211     }
   1212 
   1213     uint64_t callbackID = callback->callbackID();
   1214     m_loadDependentStringCallbackIDs.add(callbackID);
   1215     m_stringCallbacks.set(callbackID, callback.get());
   1216     process()->send(Messages::WebPage::GetSourceForFrame(frame->frameID(), callbackID), m_pageID);
   1217 }
   1218 
   1219 void WebPageProxy::getContentsAsString(PassRefPtr<StringCallback> prpCallback)
   1220 {
   1221     RefPtr<StringCallback> callback = prpCallback;
   1222     if (!isValid()) {
   1223         callback->invalidate();
   1224         return;
   1225     }
   1226 
   1227     uint64_t callbackID = callback->callbackID();
   1228     m_loadDependentStringCallbackIDs.add(callbackID);
   1229     m_stringCallbacks.set(callbackID, callback.get());
   1230     process()->send(Messages::WebPage::GetContentsAsString(callbackID), m_pageID);
   1231 }
   1232 
   1233 void WebPageProxy::getSelectionOrContentsAsString(PassRefPtr<StringCallback> prpCallback)
   1234 {
   1235     RefPtr<StringCallback> callback = prpCallback;
   1236     if (!isValid()) {
   1237         callback->invalidate();
   1238         return;
   1239     }
   1240 
   1241     uint64_t callbackID = callback->callbackID();
   1242     m_stringCallbacks.set(callbackID, callback.get());
   1243     process()->send(Messages::WebPage::GetSelectionOrContentsAsString(callbackID), m_pageID);
   1244 }
   1245 
   1246 void WebPageProxy::getMainResourceDataOfFrame(WebFrameProxy* frame, PassRefPtr<DataCallback> prpCallback)
   1247 {
   1248     RefPtr<DataCallback> callback = prpCallback;
   1249     if (!isValid()) {
   1250         callback->invalidate();
   1251         return;
   1252     }
   1253 
   1254     uint64_t callbackID = callback->callbackID();
   1255     m_dataCallbacks.set(callbackID, callback.get());
   1256     process()->send(Messages::WebPage::GetMainResourceDataOfFrame(frame->frameID(), callbackID), m_pageID);
   1257 }
   1258 
   1259 void WebPageProxy::getResourceDataFromFrame(WebFrameProxy* frame, WebURL* resourceURL, PassRefPtr<DataCallback> prpCallback)
   1260 {
   1261     RefPtr<DataCallback> callback = prpCallback;
   1262     if (!isValid()) {
   1263         callback->invalidate();
   1264         return;
   1265     }
   1266 
   1267     uint64_t callbackID = callback->callbackID();
   1268     m_dataCallbacks.set(callbackID, callback.get());
   1269     process()->send(Messages::WebPage::GetResourceDataFromFrame(frame->frameID(), resourceURL->string(), callbackID), m_pageID);
   1270 }
   1271 
   1272 void WebPageProxy::getWebArchiveOfFrame(WebFrameProxy* frame, PassRefPtr<DataCallback> prpCallback)
   1273 {
   1274     RefPtr<DataCallback> callback = prpCallback;
   1275     if (!isValid()) {
   1276         callback->invalidate();
   1277         return;
   1278     }
   1279 
   1280     uint64_t callbackID = callback->callbackID();
   1281     m_dataCallbacks.set(callbackID, callback.get());
   1282     process()->send(Messages::WebPage::GetWebArchiveOfFrame(frame->frameID(), callbackID), m_pageID);
   1283 }
   1284 
   1285 void WebPageProxy::forceRepaint(PassRefPtr<VoidCallback> prpCallback)
   1286 {
   1287     RefPtr<VoidCallback> callback = prpCallback;
   1288     if (!isValid()) {
   1289         callback->invalidate();
   1290         return;
   1291     }
   1292 
   1293     uint64_t callbackID = callback->callbackID();
   1294     m_voidCallbacks.set(callbackID, callback.get());
   1295     process()->send(Messages::WebPage::ForceRepaint(callbackID), m_pageID);
   1296 }
   1297 
   1298 void WebPageProxy::preferencesDidChange()
   1299 {
   1300     if (!isValid())
   1301         return;
   1302 
   1303     // FIXME: It probably makes more sense to send individual preference changes.
   1304     // However, WebKitTestRunner depends on getting a preference change notification
   1305     // even if nothing changed in UI process, so that overrides get removed.
   1306 
   1307     // Preferences need to be updated during synchronous printing to make "print backgrounds" preference work when toggled from a print dialog checkbox.
   1308     process()->send(Messages::WebPage::PreferencesDidChange(pageGroup()->preferences()->store()), m_pageID, m_isPerformingDOMPrintOperation ? CoreIPC::DispatchMessageEvenWhenWaitingForSyncReply : 0);
   1309 }
   1310 
   1311 #if ENABLE(TILED_BACKING_STORE)
   1312 void WebPageProxy::setResizesToContentsUsingLayoutSize(const WebCore::IntSize& targetLayoutSize)
   1313 {
   1314     process()->send(Messages::WebPage::SetResizesToContentsUsingLayoutSize(targetLayoutSize), m_pageID);
   1315 }
   1316 #endif
   1317 
   1318 void WebPageProxy::didReceiveMessage(CoreIPC::Connection* connection, CoreIPC::MessageID messageID, CoreIPC::ArgumentDecoder* arguments)
   1319 {
   1320 #if PLATFORM(MAC) || PLATFORM(WIN)
   1321     if (messageID.is<CoreIPC::MessageClassDrawingAreaProxy>()) {
   1322         m_drawingArea->didReceiveDrawingAreaProxyMessage(connection, messageID, arguments);
   1323         return;
   1324     }
   1325 #endif
   1326 
   1327     if (messageID.is<CoreIPC::MessageClassDrawingAreaProxyLegacy>()) {
   1328         m_drawingArea->didReceiveMessage(connection, messageID, arguments);
   1329         return;
   1330     }
   1331 
   1332 #if ENABLE(INSPECTOR)
   1333     if (messageID.is<CoreIPC::MessageClassWebInspectorProxy>()) {
   1334         if (WebInspectorProxy* inspector = this->inspector())
   1335             inspector->didReceiveWebInspectorProxyMessage(connection, messageID, arguments);
   1336         return;
   1337     }
   1338 #endif
   1339 
   1340 #if ENABLE(FULLSCREEN_API)
   1341     if (messageID.is<CoreIPC::MessageClassWebFullScreenManagerProxy>()) {
   1342         fullScreenManager()->didReceiveMessage(connection, messageID, arguments);
   1343         return;
   1344     }
   1345 #endif
   1346 
   1347     didReceiveWebPageProxyMessage(connection, messageID, arguments);
   1348 }
   1349 
   1350 void WebPageProxy::didReceiveSyncMessage(CoreIPC::Connection* connection, CoreIPC::MessageID messageID, CoreIPC::ArgumentDecoder* arguments, CoreIPC::ArgumentEncoder* reply)
   1351 {
   1352 #if ENABLE(INSPECTOR)
   1353     if (messageID.is<CoreIPC::MessageClassWebInspectorProxy>()) {
   1354         if (WebInspectorProxy* inspector = this->inspector())
   1355             inspector->didReceiveSyncWebInspectorProxyMessage(connection, messageID, arguments, reply);
   1356         return;
   1357     }
   1358 #endif
   1359 
   1360 #if ENABLE(FULLSCREEN_API)
   1361     if (messageID.is<CoreIPC::MessageClassWebFullScreenManagerProxy>()) {
   1362         fullScreenManager()->didReceiveSyncMessage(connection, messageID, arguments, reply);
   1363         return;
   1364     }
   1365 #endif
   1366 
   1367     // FIXME: Do something with reply.
   1368     didReceiveSyncWebPageProxyMessage(connection, messageID, arguments, reply);
   1369 }
   1370 
   1371 void WebPageProxy::didCreateMainFrame(uint64_t frameID)
   1372 {
   1373     MESSAGE_CHECK(!m_mainFrame);
   1374     MESSAGE_CHECK(process()->canCreateFrame(frameID));
   1375 
   1376     m_mainFrame = WebFrameProxy::create(this, frameID);
   1377 
   1378     // Add the frame to the process wide map.
   1379     process()->frameCreated(frameID, m_mainFrame.get());
   1380 }
   1381 
   1382 void WebPageProxy::didCreateSubframe(uint64_t frameID, uint64_t parentFrameID)
   1383 {
   1384     MESSAGE_CHECK(m_mainFrame);
   1385 
   1386     WebFrameProxy* parentFrame = process()->webFrame(parentFrameID);
   1387     MESSAGE_CHECK(parentFrame);
   1388     MESSAGE_CHECK(parentFrame->isDescendantOf(m_mainFrame.get()));
   1389 
   1390     MESSAGE_CHECK(process()->canCreateFrame(frameID));
   1391 
   1392     RefPtr<WebFrameProxy> subFrame = WebFrameProxy::create(this, frameID);
   1393 
   1394     // Add the frame to the process wide map.
   1395     process()->frameCreated(frameID, subFrame.get());
   1396 
   1397     // Insert the frame into the frame hierarchy.
   1398     parentFrame->appendChild(subFrame.get());
   1399 }
   1400 
   1401 static bool isDisconnectedFrame(WebFrameProxy* frame)
   1402 {
   1403     return !frame->page() || !frame->page()->mainFrame() || !frame->isDescendantOf(frame->page()->mainFrame());
   1404 }
   1405 
   1406 void WebPageProxy::didSaveFrameToPageCache(uint64_t frameID)
   1407 {
   1408     MESSAGE_CHECK(m_mainFrame);
   1409 
   1410     WebFrameProxy* subframe = process()->webFrame(frameID);
   1411     MESSAGE_CHECK(subframe);
   1412 
   1413     if (isDisconnectedFrame(subframe))
   1414         return;
   1415 
   1416     MESSAGE_CHECK(subframe->isDescendantOf(m_mainFrame.get()));
   1417 
   1418     subframe->didRemoveFromHierarchy();
   1419 }
   1420 
   1421 void WebPageProxy::didRestoreFrameFromPageCache(uint64_t frameID, uint64_t parentFrameID)
   1422 {
   1423     MESSAGE_CHECK(m_mainFrame);
   1424 
   1425     WebFrameProxy* subframe = process()->webFrame(frameID);
   1426     MESSAGE_CHECK(subframe);
   1427     MESSAGE_CHECK(!subframe->parentFrame());
   1428     MESSAGE_CHECK(subframe->page() == m_mainFrame->page());
   1429 
   1430     WebFrameProxy* parentFrame = process()->webFrame(parentFrameID);
   1431     MESSAGE_CHECK(parentFrame);
   1432     MESSAGE_CHECK(parentFrame->isDescendantOf(m_mainFrame.get()));
   1433 
   1434     // Insert the frame into the frame hierarchy.
   1435     parentFrame->appendChild(subframe);
   1436 }
   1437 
   1438 
   1439 // Always start progress at initialProgressValue. This helps provide feedback as
   1440 // soon as a load starts.
   1441 
   1442 static const double initialProgressValue = 0.1;
   1443 
   1444 double WebPageProxy::estimatedProgress() const
   1445 {
   1446     if (!pendingAPIRequestURL().isNull())
   1447         return initialProgressValue;
   1448     return m_estimatedProgress;
   1449 }
   1450 
   1451 void WebPageProxy::didStartProgress()
   1452 {
   1453     m_estimatedProgress = initialProgressValue;
   1454 
   1455     m_loaderClient.didStartProgress(this);
   1456 }
   1457 
   1458 void WebPageProxy::didChangeProgress(double value)
   1459 {
   1460     m_estimatedProgress = value;
   1461 
   1462     m_loaderClient.didChangeProgress(this);
   1463 }
   1464 
   1465 void WebPageProxy::didFinishProgress()
   1466 {
   1467     m_estimatedProgress = 1.0;
   1468 
   1469     m_loaderClient.didFinishProgress(this);
   1470 }
   1471 
   1472 void WebPageProxy::didStartProvisionalLoadForFrame(uint64_t frameID, const String& url, const String& unreachableURL, CoreIPC::ArgumentDecoder* arguments)
   1473 {
   1474     clearPendingAPIRequestURL();
   1475 
   1476     RefPtr<APIObject> userData;
   1477     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1478     if (!arguments->decode(messageDecoder))
   1479         return;
   1480 
   1481     WebFrameProxy* frame = process()->webFrame(frameID);
   1482     MESSAGE_CHECK(frame);
   1483 
   1484     frame->setUnreachableURL(unreachableURL);
   1485 
   1486     frame->didStartProvisionalLoad(url);
   1487     m_loaderClient.didStartProvisionalLoadForFrame(this, frame, userData.get());
   1488 }
   1489 
   1490 void WebPageProxy::didReceiveServerRedirectForProvisionalLoadForFrame(uint64_t frameID, const String& url, CoreIPC::ArgumentDecoder* arguments)
   1491 {
   1492     RefPtr<APIObject> userData;
   1493     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1494     if (!arguments->decode(messageDecoder))
   1495         return;
   1496 
   1497     WebFrameProxy* frame = process()->webFrame(frameID);
   1498     MESSAGE_CHECK(frame);
   1499 
   1500     frame->didReceiveServerRedirectForProvisionalLoad(url);
   1501 
   1502     m_loaderClient.didReceiveServerRedirectForProvisionalLoadForFrame(this, frame, userData.get());
   1503 }
   1504 
   1505 void WebPageProxy::didFailProvisionalLoadForFrame(uint64_t frameID, const ResourceError& error, CoreIPC::ArgumentDecoder* arguments)
   1506 {
   1507     RefPtr<APIObject> userData;
   1508     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1509     if (!arguments->decode(messageDecoder))
   1510         return;
   1511 
   1512     WebFrameProxy* frame = process()->webFrame(frameID);
   1513     MESSAGE_CHECK(frame);
   1514 
   1515     frame->didFailProvisionalLoad();
   1516 
   1517     m_loaderClient.didFailProvisionalLoadWithErrorForFrame(this, frame, error, userData.get());
   1518 }
   1519 
   1520 void WebPageProxy::clearLoadDependentCallbacks()
   1521 {
   1522     Vector<uint64_t> callbackIDsCopy;
   1523     copyToVector(m_loadDependentStringCallbackIDs, callbackIDsCopy);
   1524     m_loadDependentStringCallbackIDs.clear();
   1525 
   1526     for (size_t i = 0; i < callbackIDsCopy.size(); ++i) {
   1527         RefPtr<StringCallback> callback = m_stringCallbacks.take(callbackIDsCopy[i]);
   1528         if (callback)
   1529             callback->invalidate();
   1530     }
   1531 }
   1532 
   1533 void WebPageProxy::didCommitLoadForFrame(uint64_t frameID, const String& mimeType, bool frameHasCustomRepresentation, const PlatformCertificateInfo& certificateInfo, CoreIPC::ArgumentDecoder* arguments)
   1534 {
   1535     RefPtr<APIObject> userData;
   1536     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1537     if (!arguments->decode(messageDecoder))
   1538         return;
   1539 
   1540 #if PLATFORM(MAC) && !defined(BUILDING_ON_SNOW_LEOPARD)
   1541     dismissCorrectionPanel(ReasonForDismissingCorrectionPanelIgnored);
   1542     m_pageClient->dismissDictionaryLookupPanel();
   1543 #endif
   1544 
   1545     WebFrameProxy* frame = process()->webFrame(frameID);
   1546     MESSAGE_CHECK(frame);
   1547 
   1548     clearLoadDependentCallbacks();
   1549 
   1550     frame->didCommitLoad(mimeType, certificateInfo);
   1551 
   1552     if (frame->isMainFrame()) {
   1553         m_mainFrameHasCustomRepresentation = frameHasCustomRepresentation;
   1554         m_pageClient->didCommitLoadForMainFrame(frameHasCustomRepresentation);
   1555     }
   1556 
   1557     m_loaderClient.didCommitLoadForFrame(this, frame, userData.get());
   1558 }
   1559 
   1560 void WebPageProxy::didFinishDocumentLoadForFrame(uint64_t frameID, CoreIPC::ArgumentDecoder* arguments)
   1561 {
   1562     RefPtr<APIObject> userData;
   1563     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1564     if (!arguments->decode(messageDecoder))
   1565         return;
   1566 
   1567     WebFrameProxy* frame = process()->webFrame(frameID);
   1568     MESSAGE_CHECK(frame);
   1569 
   1570     m_loaderClient.didFinishDocumentLoadForFrame(this, frame, userData.get());
   1571 }
   1572 
   1573 void WebPageProxy::didFinishLoadForFrame(uint64_t frameID, CoreIPC::ArgumentDecoder* arguments)
   1574 {
   1575     RefPtr<APIObject> userData;
   1576     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1577     if (!arguments->decode(messageDecoder))
   1578         return;
   1579 
   1580     WebFrameProxy* frame = process()->webFrame(frameID);
   1581     MESSAGE_CHECK(frame);
   1582 
   1583     frame->didFinishLoad();
   1584 
   1585     m_loaderClient.didFinishLoadForFrame(this, frame, userData.get());
   1586 }
   1587 
   1588 void WebPageProxy::didFailLoadForFrame(uint64_t frameID, const ResourceError& error, CoreIPC::ArgumentDecoder* arguments)
   1589 {
   1590     RefPtr<APIObject> userData;
   1591     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1592     if (!arguments->decode(messageDecoder))
   1593         return;
   1594 
   1595     WebFrameProxy* frame = process()->webFrame(frameID);
   1596     MESSAGE_CHECK(frame);
   1597 
   1598     clearLoadDependentCallbacks();
   1599 
   1600     frame->didFailLoad();
   1601 
   1602     m_loaderClient.didFailLoadWithErrorForFrame(this, frame, error, userData.get());
   1603 }
   1604 
   1605 void WebPageProxy::didSameDocumentNavigationForFrame(uint64_t frameID, uint32_t opaqueSameDocumentNavigationType, const String& url, CoreIPC::ArgumentDecoder* arguments)
   1606 {
   1607     RefPtr<APIObject> userData;
   1608     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1609     if (!arguments->decode(messageDecoder))
   1610         return;
   1611 
   1612     WebFrameProxy* frame = process()->webFrame(frameID);
   1613     MESSAGE_CHECK(frame);
   1614 
   1615     frame->didSameDocumentNavigation(url);
   1616 
   1617     m_loaderClient.didSameDocumentNavigationForFrame(this, frame, static_cast<SameDocumentNavigationType>(opaqueSameDocumentNavigationType), userData.get());
   1618 }
   1619 
   1620 void WebPageProxy::didReceiveTitleForFrame(uint64_t frameID, const String& title, CoreIPC::ArgumentDecoder* arguments)
   1621 {
   1622     RefPtr<APIObject> userData;
   1623     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1624     if (!arguments->decode(messageDecoder))
   1625         return;
   1626 
   1627     WebFrameProxy* frame = process()->webFrame(frameID);
   1628     MESSAGE_CHECK(frame);
   1629 
   1630     frame->didChangeTitle(title);
   1631 
   1632     m_loaderClient.didReceiveTitleForFrame(this, title, frame, userData.get());
   1633 }
   1634 
   1635 void WebPageProxy::didFirstLayoutForFrame(uint64_t frameID, CoreIPC::ArgumentDecoder* arguments)
   1636 {
   1637     RefPtr<APIObject> userData;
   1638     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1639     if (!arguments->decode(messageDecoder))
   1640         return;
   1641 
   1642     WebFrameProxy* frame = process()->webFrame(frameID);
   1643     MESSAGE_CHECK(frame);
   1644 
   1645     m_loaderClient.didFirstLayoutForFrame(this, frame, userData.get());
   1646 }
   1647 
   1648 void WebPageProxy::didFirstVisuallyNonEmptyLayoutForFrame(uint64_t frameID, CoreIPC::ArgumentDecoder* arguments)
   1649 {
   1650     RefPtr<APIObject> userData;
   1651     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1652     if (!arguments->decode(messageDecoder))
   1653         return;
   1654 
   1655     WebFrameProxy* frame = process()->webFrame(frameID);
   1656     MESSAGE_CHECK(frame);
   1657 
   1658     m_loaderClient.didFirstVisuallyNonEmptyLayoutForFrame(this, frame, userData.get());
   1659 }
   1660 
   1661 void WebPageProxy::didRemoveFrameFromHierarchy(uint64_t frameID, CoreIPC::ArgumentDecoder* arguments)
   1662 {
   1663     RefPtr<APIObject> userData;
   1664     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1665     if (!arguments->decode(messageDecoder))
   1666         return;
   1667 
   1668     WebFrameProxy* frame = process()->webFrame(frameID);
   1669     MESSAGE_CHECK(frame);
   1670 
   1671     frame->didRemoveFromHierarchy();
   1672 
   1673     m_loaderClient.didRemoveFrameFromHierarchy(this, frame, userData.get());
   1674 }
   1675 
   1676 void WebPageProxy::didDisplayInsecureContentForFrame(uint64_t frameID, CoreIPC::ArgumentDecoder* arguments)
   1677 {
   1678     RefPtr<APIObject> userData;
   1679     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1680     if (!arguments->decode(messageDecoder))
   1681         return;
   1682 
   1683     WebFrameProxy* frame = process()->webFrame(frameID);
   1684     MESSAGE_CHECK(frame);
   1685 
   1686     m_loaderClient.didDisplayInsecureContentForFrame(this, frame, userData.get());
   1687 }
   1688 
   1689 void WebPageProxy::didRunInsecureContentForFrame(uint64_t frameID, CoreIPC::ArgumentDecoder* arguments)
   1690 {
   1691     RefPtr<APIObject> userData;
   1692     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1693     if (!arguments->decode(messageDecoder))
   1694         return;
   1695 
   1696     WebFrameProxy* frame = process()->webFrame(frameID);
   1697     MESSAGE_CHECK(frame);
   1698 
   1699     m_loaderClient.didRunInsecureContentForFrame(this, frame, userData.get());
   1700 }
   1701 
   1702 void WebPageProxy::frameDidBecomeFrameSet(uint64_t frameID, bool value)
   1703 {
   1704     WebFrameProxy* frame = process()->webFrame(frameID);
   1705     MESSAGE_CHECK(frame);
   1706 
   1707     frame->setIsFrameSet(value);
   1708     if (frame->isMainFrame())
   1709         m_frameSetLargestFrame = value ? m_mainFrame : 0;
   1710 }
   1711 
   1712 // PolicyClient
   1713 void WebPageProxy::decidePolicyForNavigationAction(uint64_t frameID, uint32_t opaqueNavigationType, uint32_t opaqueModifiers, int32_t opaqueMouseButton, const ResourceRequest& request, uint64_t listenerID, CoreIPC::ArgumentDecoder* arguments, bool& receivedPolicyAction, uint64_t& policyAction, uint64_t& downloadID)
   1714 {
   1715     RefPtr<APIObject> userData;
   1716     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1717     if (!arguments->decode(messageDecoder))
   1718         return;
   1719 
   1720     if (request.url() != pendingAPIRequestURL())
   1721         clearPendingAPIRequestURL();
   1722 
   1723     WebFrameProxy* frame = process()->webFrame(frameID);
   1724     MESSAGE_CHECK(frame);
   1725 
   1726     NavigationType navigationType = static_cast<NavigationType>(opaqueNavigationType);
   1727     WebEvent::Modifiers modifiers = static_cast<WebEvent::Modifiers>(opaqueModifiers);
   1728     WebMouseEvent::Button mouseButton = static_cast<WebMouseEvent::Button>(opaqueMouseButton);
   1729 
   1730     RefPtr<WebFramePolicyListenerProxy> listener = frame->setUpPolicyListenerProxy(listenerID);
   1731 
   1732     ASSERT(!m_inDecidePolicyForNavigationAction);
   1733 
   1734     m_inDecidePolicyForNavigationAction = true;
   1735     m_syncNavigationActionPolicyActionIsValid = false;
   1736 
   1737     if (!m_policyClient.decidePolicyForNavigationAction(this, frame, navigationType, modifiers, mouseButton, request, listener.get(), userData.get()))
   1738         listener->use();
   1739 
   1740     m_inDecidePolicyForNavigationAction = false;
   1741 
   1742     // Check if we received a policy decision already. If we did, we can just pass it back.
   1743     receivedPolicyAction = m_syncNavigationActionPolicyActionIsValid;
   1744     if (m_syncNavigationActionPolicyActionIsValid) {
   1745         policyAction = m_syncNavigationActionPolicyAction;
   1746         downloadID = m_syncNavigationActionPolicyDownloadID;
   1747     }
   1748 }
   1749 
   1750 void WebPageProxy::decidePolicyForNewWindowAction(uint64_t frameID, uint32_t opaqueNavigationType, uint32_t opaqueModifiers, int32_t opaqueMouseButton, const ResourceRequest& request, const String& frameName, uint64_t listenerID, CoreIPC::ArgumentDecoder* arguments)
   1751 {
   1752     RefPtr<APIObject> userData;
   1753     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1754     if (!arguments->decode(messageDecoder))
   1755         return;
   1756 
   1757     WebFrameProxy* frame = process()->webFrame(frameID);
   1758     MESSAGE_CHECK(frame);
   1759 
   1760     NavigationType navigationType = static_cast<NavigationType>(opaqueNavigationType);
   1761     WebEvent::Modifiers modifiers = static_cast<WebEvent::Modifiers>(opaqueModifiers);
   1762     WebMouseEvent::Button mouseButton = static_cast<WebMouseEvent::Button>(opaqueMouseButton);
   1763 
   1764     RefPtr<WebFramePolicyListenerProxy> listener = frame->setUpPolicyListenerProxy(listenerID);
   1765     if (!m_policyClient.decidePolicyForNewWindowAction(this, frame, navigationType, modifiers, mouseButton, request, frameName, listener.get(), userData.get()))
   1766         listener->use();
   1767 }
   1768 
   1769 void WebPageProxy::decidePolicyForResponse(uint64_t frameID, const ResourceResponse& response, const ResourceRequest& request, uint64_t listenerID, CoreIPC::ArgumentDecoder* arguments, bool& receivedPolicyAction, uint64_t& policyAction, uint64_t& downloadID)
   1770 {
   1771     RefPtr<APIObject> userData;
   1772     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1773     if (!arguments->decode(messageDecoder))
   1774         return;
   1775 
   1776     WebFrameProxy* frame = process()->webFrame(frameID);
   1777     MESSAGE_CHECK(frame);
   1778 
   1779     RefPtr<WebFramePolicyListenerProxy> listener = frame->setUpPolicyListenerProxy(listenerID);
   1780 
   1781     ASSERT(!m_inDecidePolicyForMIMEType);
   1782 
   1783     m_inDecidePolicyForMIMEType = true;
   1784     m_syncMimeTypePolicyActionIsValid = false;
   1785 
   1786     if (!m_policyClient.decidePolicyForResponse(this, frame, response, request, listener.get(), userData.get()))
   1787         listener->use();
   1788 
   1789     m_inDecidePolicyForMIMEType = false;
   1790 
   1791     // Check if we received a policy decision already. If we did, we can just pass it back.
   1792     receivedPolicyAction = m_syncMimeTypePolicyActionIsValid;
   1793     if (m_syncMimeTypePolicyActionIsValid) {
   1794         policyAction = m_syncMimeTypePolicyAction;
   1795         downloadID = m_syncMimeTypePolicyDownloadID;
   1796     }
   1797 }
   1798 
   1799 void WebPageProxy::unableToImplementPolicy(uint64_t frameID, const WebCore::ResourceError& error, CoreIPC::ArgumentDecoder* arguments)
   1800 {
   1801     RefPtr<APIObject> userData;
   1802     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1803     if (!arguments->decode(messageDecoder))
   1804         return;
   1805 
   1806     WebFrameProxy* frame = process()->webFrame(frameID);
   1807     MESSAGE_CHECK(frame);
   1808 
   1809     m_policyClient.unableToImplementPolicy(this, frame, error, userData.get());
   1810 }
   1811 
   1812 // FormClient
   1813 
   1814 void WebPageProxy::willSubmitForm(uint64_t frameID, uint64_t sourceFrameID, const StringPairVector& textFieldValues, uint64_t listenerID, CoreIPC::ArgumentDecoder* arguments)
   1815 {
   1816     RefPtr<APIObject> userData;
   1817     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1818     if (!arguments->decode(messageDecoder))
   1819         return;
   1820 
   1821     WebFrameProxy* frame = process()->webFrame(frameID);
   1822     MESSAGE_CHECK(frame);
   1823 
   1824     WebFrameProxy* sourceFrame = process()->webFrame(sourceFrameID);
   1825     MESSAGE_CHECK(sourceFrame);
   1826 
   1827     RefPtr<WebFormSubmissionListenerProxy> listener = frame->setUpFormSubmissionListenerProxy(listenerID);
   1828     if (!m_formClient.willSubmitForm(this, frame, sourceFrame, textFieldValues.stringPairVector(), userData.get(), listener.get()))
   1829         listener->continueSubmission();
   1830 }
   1831 
   1832 // ResourceLoad Client
   1833 
   1834 void WebPageProxy::didInitiateLoadForResource(uint64_t frameID, uint64_t resourceIdentifier, const ResourceRequest& request, bool pageIsProvisionallyLoading)
   1835 {
   1836     WebFrameProxy* frame = process()->webFrame(frameID);
   1837     MESSAGE_CHECK(frame);
   1838 
   1839     m_resourceLoadClient.didInitiateLoadForResource(this, frame, resourceIdentifier, request, pageIsProvisionallyLoading);
   1840 }
   1841 
   1842 void WebPageProxy::didSendRequestForResource(uint64_t frameID, uint64_t resourceIdentifier, const ResourceRequest& request, const ResourceResponse& redirectResponse)
   1843 {
   1844     WebFrameProxy* frame = process()->webFrame(frameID);
   1845     MESSAGE_CHECK(frame);
   1846 
   1847     m_resourceLoadClient.didSendRequestForResource(this, frame, resourceIdentifier, request, redirectResponse);
   1848 }
   1849 
   1850 void WebPageProxy::didReceiveResponseForResource(uint64_t frameID, uint64_t resourceIdentifier, const ResourceResponse& response)
   1851 {
   1852     WebFrameProxy* frame = process()->webFrame(frameID);
   1853     MESSAGE_CHECK(frame);
   1854 
   1855     m_resourceLoadClient.didReceiveResponseForResource(this, frame, resourceIdentifier, response);
   1856 }
   1857 
   1858 void WebPageProxy::didReceiveContentLengthForResource(uint64_t frameID, uint64_t resourceIdentifier, uint64_t contentLength)
   1859 {
   1860     WebFrameProxy* frame = process()->webFrame(frameID);
   1861     MESSAGE_CHECK(frame);
   1862 
   1863     m_resourceLoadClient.didReceiveContentLengthForResource(this, frame, resourceIdentifier, contentLength);
   1864 }
   1865 
   1866 void WebPageProxy::didFinishLoadForResource(uint64_t frameID, uint64_t resourceIdentifier)
   1867 {
   1868     WebFrameProxy* frame = process()->webFrame(frameID);
   1869     MESSAGE_CHECK(frame);
   1870 
   1871     m_resourceLoadClient.didFinishLoadForResource(this, frame, resourceIdentifier);
   1872 }
   1873 
   1874 void WebPageProxy::didFailLoadForResource(uint64_t frameID, uint64_t resourceIdentifier, const ResourceError& error)
   1875 {
   1876     WebFrameProxy* frame = process()->webFrame(frameID);
   1877     MESSAGE_CHECK(frame);
   1878 
   1879     m_resourceLoadClient.didFailLoadForResource(this, frame, resourceIdentifier, error);
   1880 }
   1881 
   1882 // UIClient
   1883 
   1884 void WebPageProxy::createNewPage(const WindowFeatures& windowFeatures, uint32_t opaqueModifiers, int32_t opaqueMouseButton, uint64_t& newPageID, WebPageCreationParameters& newPageParameters)
   1885 {
   1886     RefPtr<WebPageProxy> newPage = m_uiClient.createNewPage(this, windowFeatures, static_cast<WebEvent::Modifiers>(opaqueModifiers), static_cast<WebMouseEvent::Button>(opaqueMouseButton));
   1887     if (newPage) {
   1888         newPageID = newPage->pageID();
   1889         newPageParameters = newPage->creationParameters();
   1890     } else
   1891         newPageID = 0;
   1892 }
   1893 
   1894 void WebPageProxy::showPage()
   1895 {
   1896     m_uiClient.showPage(this);
   1897 }
   1898 
   1899 void WebPageProxy::closePage()
   1900 {
   1901     m_uiClient.close(this);
   1902 }
   1903 
   1904 void WebPageProxy::runJavaScriptAlert(uint64_t frameID, const String& message)
   1905 {
   1906     WebFrameProxy* frame = process()->webFrame(frameID);
   1907     MESSAGE_CHECK(frame);
   1908 
   1909     // Since runJavaScriptAlert() can spin a nested run loop we need to turn off the responsiveness timer.
   1910     process()->responsivenessTimer()->stop();
   1911 
   1912     m_uiClient.runJavaScriptAlert(this, message, frame);
   1913 }
   1914 
   1915 void WebPageProxy::runJavaScriptConfirm(uint64_t frameID, const String& message, bool& result)
   1916 {
   1917     WebFrameProxy* frame = process()->webFrame(frameID);
   1918     MESSAGE_CHECK(frame);
   1919 
   1920     // Since runJavaScriptConfirm() can spin a nested run loop we need to turn off the responsiveness timer.
   1921     process()->responsivenessTimer()->stop();
   1922 
   1923     result = m_uiClient.runJavaScriptConfirm(this, message, frame);
   1924 }
   1925 
   1926 void WebPageProxy::runJavaScriptPrompt(uint64_t frameID, const String& message, const String& defaultValue, String& result)
   1927 {
   1928     WebFrameProxy* frame = process()->webFrame(frameID);
   1929     MESSAGE_CHECK(frame);
   1930 
   1931     // Since runJavaScriptPrompt() can spin a nested run loop we need to turn off the responsiveness timer.
   1932     process()->responsivenessTimer()->stop();
   1933 
   1934     result = m_uiClient.runJavaScriptPrompt(this, message, defaultValue, frame);
   1935 }
   1936 
   1937 void WebPageProxy::setStatusText(const String& text)
   1938 {
   1939     m_uiClient.setStatusText(this, text);
   1940 }
   1941 
   1942 void WebPageProxy::mouseDidMoveOverElement(uint32_t opaqueModifiers, CoreIPC::ArgumentDecoder* arguments)
   1943 {
   1944     RefPtr<APIObject> userData;
   1945     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   1946     if (!arguments->decode(messageDecoder))
   1947         return;
   1948 
   1949     WebEvent::Modifiers modifiers = static_cast<WebEvent::Modifiers>(opaqueModifiers);
   1950 
   1951     m_uiClient.mouseDidMoveOverElement(this, modifiers, userData.get());
   1952 }
   1953 
   1954 void WebPageProxy::missingPluginButtonClicked(const String& mimeType, const String& url, const String& pluginsPageURL)
   1955 {
   1956     m_uiClient.missingPluginButtonClicked(this, mimeType, url, pluginsPageURL);
   1957 }
   1958 
   1959 void WebPageProxy::setToolbarsAreVisible(bool toolbarsAreVisible)
   1960 {
   1961     m_uiClient.setToolbarsAreVisible(this, toolbarsAreVisible);
   1962 }
   1963 
   1964 void WebPageProxy::getToolbarsAreVisible(bool& toolbarsAreVisible)
   1965 {
   1966     toolbarsAreVisible = m_uiClient.toolbarsAreVisible(this);
   1967 }
   1968 
   1969 void WebPageProxy::setMenuBarIsVisible(bool menuBarIsVisible)
   1970 {
   1971     m_uiClient.setMenuBarIsVisible(this, menuBarIsVisible);
   1972 }
   1973 
   1974 void WebPageProxy::getMenuBarIsVisible(bool& menuBarIsVisible)
   1975 {
   1976     menuBarIsVisible = m_uiClient.menuBarIsVisible(this);
   1977 }
   1978 
   1979 void WebPageProxy::setStatusBarIsVisible(bool statusBarIsVisible)
   1980 {
   1981     m_uiClient.setStatusBarIsVisible(this, statusBarIsVisible);
   1982 }
   1983 
   1984 void WebPageProxy::getStatusBarIsVisible(bool& statusBarIsVisible)
   1985 {
   1986     statusBarIsVisible = m_uiClient.statusBarIsVisible(this);
   1987 }
   1988 
   1989 void WebPageProxy::setIsResizable(bool isResizable)
   1990 {
   1991     m_uiClient.setIsResizable(this, isResizable);
   1992 }
   1993 
   1994 void WebPageProxy::getIsResizable(bool& isResizable)
   1995 {
   1996     isResizable = m_uiClient.isResizable(this);
   1997 }
   1998 
   1999 void WebPageProxy::setWindowFrame(const FloatRect& newWindowFrame)
   2000 {
   2001     m_uiClient.setWindowFrame(this, m_pageClient->convertToDeviceSpace(newWindowFrame));
   2002 }
   2003 
   2004 void WebPageProxy::getWindowFrame(FloatRect& newWindowFrame)
   2005 {
   2006     newWindowFrame = m_pageClient->convertToUserSpace(m_uiClient.windowFrame(this));
   2007 }
   2008 
   2009 void WebPageProxy::windowToScreen(const IntRect& viewRect, IntRect& result)
   2010 {
   2011     result = m_pageClient->windowToScreen(viewRect);
   2012 }
   2013 
   2014 void WebPageProxy::runBeforeUnloadConfirmPanel(const String& message, uint64_t frameID, bool& shouldClose)
   2015 {
   2016     WebFrameProxy* frame = process()->webFrame(frameID);
   2017     MESSAGE_CHECK(frame);
   2018 
   2019     shouldClose = m_uiClient.runBeforeUnloadConfirmPanel(this, message, frame);
   2020 }
   2021 
   2022 #if ENABLE(TILED_BACKING_STORE)
   2023 void WebPageProxy::pageDidRequestScroll(const IntPoint& point)
   2024 {
   2025     m_pageClient->pageDidRequestScroll(point);
   2026 }
   2027 #endif
   2028 
   2029 void WebPageProxy::didChangeViewportData(const ViewportArguments& args)
   2030 {
   2031     m_pageClient->setViewportArguments(args);
   2032 }
   2033 
   2034 void WebPageProxy::pageDidScroll()
   2035 {
   2036     m_uiClient.pageDidScroll(this);
   2037 }
   2038 
   2039 void WebPageProxy::runOpenPanel(uint64_t frameID, const WebOpenPanelParameters::Data& data)
   2040 {
   2041     if (m_openPanelResultListener) {
   2042         m_openPanelResultListener->invalidate();
   2043         m_openPanelResultListener = 0;
   2044     }
   2045 
   2046     WebFrameProxy* frame = process()->webFrame(frameID);
   2047     MESSAGE_CHECK(frame);
   2048 
   2049     m_openPanelResultListener = WebOpenPanelResultListenerProxy::create(this);
   2050 
   2051     if (!m_uiClient.runOpenPanel(this, frame, data, m_openPanelResultListener.get()))
   2052         didCancelForOpenPanel();
   2053 }
   2054 
   2055 void WebPageProxy::printFrame(uint64_t frameID)
   2056 {
   2057     ASSERT(!m_isPerformingDOMPrintOperation);
   2058     m_isPerformingDOMPrintOperation = true;
   2059 
   2060     WebFrameProxy* frame = process()->webFrame(frameID);
   2061     MESSAGE_CHECK(frame);
   2062 
   2063     m_uiClient.printFrame(this, frame);
   2064 
   2065     m_isPerformingDOMPrintOperation = false;
   2066 }
   2067 
   2068 #if PLATFORM(QT)
   2069 void WebPageProxy::didChangeContentsSize(const WebCore::IntSize& size)
   2070 {
   2071     m_pageClient->didChangeContentsSize(size);
   2072 }
   2073 
   2074 void WebPageProxy::didFindZoomableArea(const WebCore::IntRect& area)
   2075 {
   2076     m_pageClient->didFindZoomableArea(area);
   2077 }
   2078 
   2079 void WebPageProxy::findZoomableAreaForPoint(const WebCore::IntPoint& point)
   2080 {
   2081     if (!isValid())
   2082         return;
   2083 
   2084     process()->send(Messages::WebPage::FindZoomableAreaForPoint(point), m_pageID);
   2085 }
   2086 #endif
   2087 
   2088 void WebPageProxy::didDraw()
   2089 {
   2090     m_uiClient.didDraw(this);
   2091 }
   2092 
   2093 // Inspector
   2094 
   2095 #if ENABLE(INSPECTOR)
   2096 
   2097 WebInspectorProxy* WebPageProxy::inspector()
   2098 {
   2099     if (isClosed() || !isValid())
   2100         return 0;
   2101     if (!m_inspector)
   2102         m_inspector = WebInspectorProxy::create(this);
   2103     return m_inspector.get();
   2104 }
   2105 
   2106 #endif
   2107 
   2108 #if ENABLE(FULLSCREEN_API)
   2109 WebFullScreenManagerProxy* WebPageProxy::fullScreenManager()
   2110 {
   2111     if (!m_fullScreenManager)
   2112         m_fullScreenManager = WebFullScreenManagerProxy::create(this);
   2113     return m_fullScreenManager.get();
   2114 }
   2115 #endif
   2116 
   2117 // BackForwardList
   2118 
   2119 void WebPageProxy::backForwardAddItem(uint64_t itemID)
   2120 {
   2121     m_backForwardList->addItem(process()->webBackForwardItem(itemID));
   2122 }
   2123 
   2124 void WebPageProxy::backForwardGoToItem(uint64_t itemID)
   2125 {
   2126     m_backForwardList->goToItem(process()->webBackForwardItem(itemID));
   2127 }
   2128 
   2129 void WebPageProxy::backForwardItemAtIndex(int32_t index, uint64_t& itemID)
   2130 {
   2131     WebBackForwardListItem* item = m_backForwardList->itemAtIndex(index);
   2132     itemID = item ? item->itemID() : 0;
   2133 }
   2134 
   2135 void WebPageProxy::backForwardBackListCount(int32_t& count)
   2136 {
   2137     count = m_backForwardList->backListCount();
   2138 }
   2139 
   2140 void WebPageProxy::backForwardForwardListCount(int32_t& count)
   2141 {
   2142     count = m_backForwardList->forwardListCount();
   2143 }
   2144 
   2145 void WebPageProxy::editorStateChanged(const EditorState& editorState)
   2146 {
   2147 #if PLATFORM(MAC)
   2148     bool couldChangeSecureInputState = m_editorState.isInPasswordField != editorState.isInPasswordField || m_editorState.selectionIsNone;
   2149 #endif
   2150 
   2151     m_editorState = editorState;
   2152 
   2153 #if PLATFORM(MAC)
   2154     // This is a temporary state. Flipping secure input state too quickly can expose race conditions.
   2155     if (editorState.selectionIsNone)
   2156         return;
   2157 
   2158     if (couldChangeSecureInputState)
   2159         m_pageClient->updateSecureInputState();
   2160 #endif
   2161 }
   2162 
   2163 #if PLATFORM(WIN)
   2164 void WebPageProxy::didChangeCompositionSelection(bool hasComposition)
   2165 {
   2166     m_pageClient->compositionSelectionChanged(hasComposition);
   2167 }
   2168 
   2169 void WebPageProxy::confirmComposition(const String& compositionString)
   2170 {
   2171     process()->send(Messages::WebPage::ConfirmComposition(compositionString), m_pageID);
   2172 }
   2173 
   2174 void WebPageProxy::setComposition(const String& compositionString, Vector<WebCore::CompositionUnderline>& underlines, int cursorPosition)
   2175 {
   2176     process()->send(Messages::WebPage::SetComposition(compositionString, underlines, cursorPosition), m_pageID);
   2177 }
   2178 #endif
   2179 
   2180 // Undo management
   2181 
   2182 void WebPageProxy::registerEditCommandForUndo(uint64_t commandID, uint32_t editAction)
   2183 {
   2184     registerEditCommand(WebEditCommandProxy::create(commandID, static_cast<EditAction>(editAction), this), Undo);
   2185 }
   2186 
   2187 void WebPageProxy::canUndoRedo(uint32_t action, bool& result)
   2188 {
   2189     result = m_pageClient->canUndoRedo(static_cast<UndoOrRedo>(action));
   2190 }
   2191 
   2192 void WebPageProxy::executeUndoRedo(uint32_t action, bool& result)
   2193 {
   2194     m_pageClient->executeUndoRedo(static_cast<UndoOrRedo>(action));
   2195     result = true;
   2196 }
   2197 
   2198 void WebPageProxy::clearAllEditCommands()
   2199 {
   2200     m_pageClient->clearAllEditCommands();
   2201 }
   2202 
   2203 void WebPageProxy::didCountStringMatches(const String& string, uint32_t matchCount)
   2204 {
   2205     m_findClient.didCountStringMatches(this, string, matchCount);
   2206 }
   2207 
   2208 void WebPageProxy::setFindIndicator(const FloatRect& selectionRectInWindowCoordinates, const Vector<FloatRect>& textRectsInSelectionRectCoordinates, const ShareableBitmap::Handle& contentImageHandle, bool fadeOut)
   2209 {
   2210     RefPtr<FindIndicator> findIndicator = FindIndicator::create(selectionRectInWindowCoordinates, textRectsInSelectionRectCoordinates, contentImageHandle);
   2211     m_pageClient->setFindIndicator(findIndicator.release(), fadeOut);
   2212 }
   2213 
   2214 void WebPageProxy::didFindString(const String& string, uint32_t matchCount)
   2215 {
   2216     m_findClient.didFindString(this, string, matchCount);
   2217 }
   2218 
   2219 void WebPageProxy::didFailToFindString(const String& string)
   2220 {
   2221     m_findClient.didFailToFindString(this, string);
   2222 }
   2223 
   2224 void WebPageProxy::valueChangedForPopupMenu(WebPopupMenuProxy*, int32_t newSelectedIndex)
   2225 {
   2226     process()->send(Messages::WebPage::DidChangeSelectedIndexForActivePopupMenu(newSelectedIndex), m_pageID);
   2227 }
   2228 
   2229 void WebPageProxy::setTextFromItemForPopupMenu(WebPopupMenuProxy*, int32_t index)
   2230 {
   2231     process()->send(Messages::WebPage::SetTextForActivePopupMenu(index), m_pageID);
   2232 }
   2233 
   2234 NativeWebMouseEvent* WebPageProxy::currentlyProcessedMouseDownEvent()
   2235 {
   2236     return m_currentlyProcessedMouseDownEvent.get();
   2237 }
   2238 
   2239 void WebPageProxy::showPopupMenu(const IntRect& rect, uint64_t textDirection, const Vector<WebPopupItem>& items, int32_t selectedIndex, const PlatformPopupMenuData& data)
   2240 {
   2241     if (m_activePopupMenu) {
   2242         m_activePopupMenu->hidePopupMenu();
   2243         m_activePopupMenu->invalidate();
   2244         m_activePopupMenu = 0;
   2245     }
   2246 
   2247     m_activePopupMenu = m_pageClient->createPopupMenuProxy(this);
   2248 
   2249     // Since showPopupMenu() can spin a nested run loop we need to turn off the responsiveness timer.
   2250     process()->responsivenessTimer()->stop();
   2251 
   2252     RefPtr<WebPopupMenuProxy> protectedActivePopupMenu = m_activePopupMenu;
   2253 
   2254     protectedActivePopupMenu->showPopupMenu(rect, static_cast<TextDirection>(textDirection), m_viewScaleFactor, items, data, selectedIndex);
   2255     protectedActivePopupMenu->invalidate();
   2256     protectedActivePopupMenu = 0;
   2257 }
   2258 
   2259 void WebPageProxy::hidePopupMenu()
   2260 {
   2261     if (!m_activePopupMenu)
   2262         return;
   2263 
   2264     m_activePopupMenu->hidePopupMenu();
   2265     m_activePopupMenu->invalidate();
   2266     m_activePopupMenu = 0;
   2267 }
   2268 
   2269 void WebPageProxy::showContextMenu(const IntPoint& menuLocation, const ContextMenuState& contextMenuState, const Vector<WebContextMenuItemData>& proposedItems, CoreIPC::ArgumentDecoder* arguments)
   2270 {
   2271     internalShowContextMenu(menuLocation, contextMenuState, proposedItems, arguments);
   2272 
   2273     // No matter the result of internalShowContextMenu, always notify the WebProcess that the menu is hidden so it starts handling mouse events again.
   2274     process()->send(Messages::WebPage::ContextMenuHidden(), m_pageID);
   2275 }
   2276 
   2277 void WebPageProxy::internalShowContextMenu(const IntPoint& menuLocation, const ContextMenuState& contextMenuState, const Vector<WebContextMenuItemData>& proposedItems, CoreIPC::ArgumentDecoder* arguments)
   2278 {
   2279     RefPtr<APIObject> userData;
   2280     WebContextUserMessageDecoder messageDecoder(userData, m_process->context());
   2281     if (!arguments->decode(messageDecoder))
   2282         return;
   2283 
   2284     m_activeContextMenuState = contextMenuState;
   2285 
   2286     if (m_activeContextMenu) {
   2287         m_activeContextMenu->hideContextMenu();
   2288         m_activeContextMenu = 0;
   2289     }
   2290 
   2291     m_activeContextMenu = m_pageClient->createContextMenuProxy(this);
   2292 
   2293     // Since showContextMenu() can spin a nested run loop we need to turn off the responsiveness timer.
   2294     process()->responsivenessTimer()->stop();
   2295 
   2296     // Give the PageContextMenuClient one last swipe at changing the menu.
   2297     Vector<WebContextMenuItemData> items;
   2298     if (!m_contextMenuClient.getContextMenuFromProposedMenu(this, proposedItems, items, userData.get()))
   2299         m_activeContextMenu->showContextMenu(menuLocation, proposedItems);
   2300     else
   2301         m_activeContextMenu->showContextMenu(menuLocation, items);
   2302 }
   2303 
   2304 void WebPageProxy::contextMenuItemSelected(const WebContextMenuItemData& item)
   2305 {
   2306     // Application custom items don't need to round-trip through to WebCore in the WebProcess.
   2307     if (item.action() >= ContextMenuItemBaseApplicationTag) {
   2308         m_contextMenuClient.customContextMenuItemSelected(this, item);
   2309         return;
   2310     }
   2311 
   2312 #if PLATFORM(MAC)
   2313     if (item.action() == ContextMenuItemTagSmartCopyPaste) {
   2314         setSmartInsertDeleteEnabled(!isSmartInsertDeleteEnabled());
   2315         return;
   2316     }
   2317     if (item.action() == ContextMenuItemTagSmartQuotes) {
   2318         TextChecker::setAutomaticQuoteSubstitutionEnabled(!TextChecker::state().isAutomaticQuoteSubstitutionEnabled);
   2319         process()->updateTextCheckerState();
   2320         return;
   2321     }
   2322     if (item.action() == ContextMenuItemTagSmartDashes) {
   2323         TextChecker::setAutomaticDashSubstitutionEnabled(!TextChecker::state().isAutomaticDashSubstitutionEnabled);
   2324         process()->updateTextCheckerState();
   2325         return;
   2326     }
   2327     if (item.action() == ContextMenuItemTagSmartLinks) {
   2328         TextChecker::setAutomaticLinkDetectionEnabled(!TextChecker::state().isAutomaticLinkDetectionEnabled);
   2329         process()->updateTextCheckerState();
   2330         return;
   2331     }
   2332     if (item.action() == ContextMenuItemTagTextReplacement) {
   2333         TextChecker::setAutomaticTextReplacementEnabled(!TextChecker::state().isAutomaticTextReplacementEnabled);
   2334         process()->updateTextCheckerState();
   2335         return;
   2336     }
   2337     if (item.action() == ContextMenuItemTagCorrectSpellingAutomatically) {
   2338         TextChecker::setAutomaticSpellingCorrectionEnabled(!TextChecker::state().isAutomaticSpellingCorrectionEnabled);
   2339         process()->updateTextCheckerState();
   2340         return;
   2341     }
   2342     if (item.action() == ContextMenuItemTagShowSubstitutions) {
   2343         TextChecker::toggleSubstitutionsPanelIsShowing();
   2344         return;
   2345     }
   2346 #endif
   2347     if (item.action() == ContextMenuItemTagDownloadImageToDisk) {
   2348         m_process->context()->download(this, KURL(KURL(), m_activeContextMenuState.absoluteImageURLString));
   2349         return;
   2350     }
   2351     if (item.action() == ContextMenuItemTagDownloadLinkToDisk) {
   2352         m_process->context()->download(this, KURL(KURL(), m_activeContextMenuState.absoluteLinkURLString));
   2353         return;
   2354     }
   2355     if (item.action() == ContextMenuItemTagCheckSpellingWhileTyping) {
   2356         TextChecker::setContinuousSpellCheckingEnabled(!TextChecker::state().isContinuousSpellCheckingEnabled);
   2357         process()->updateTextCheckerState();
   2358         return;
   2359     }
   2360     if (item.action() == ContextMenuItemTagCheckGrammarWithSpelling) {
   2361         TextChecker::setGrammarCheckingEnabled(!TextChecker::state().isGrammarCheckingEnabled);
   2362         process()->updateTextCheckerState();
   2363         return;
   2364     }
   2365     if (item.action() == ContextMenuItemTagShowSpellingPanel) {
   2366         if (!TextChecker::spellingUIIsShowing())
   2367             advanceToNextMisspelling(true);
   2368         TextChecker::toggleSpellingUIIsShowing();
   2369         return;
   2370     }
   2371     if (item.action() == ContextMenuItemTagLearnSpelling || item.action() == ContextMenuItemTagIgnoreSpelling)
   2372         ++m_pendingLearnOrIgnoreWordMessageCount;
   2373 
   2374     process()->send(Messages::WebPage::DidSelectItemFromActiveContextMenu(item), m_pageID);
   2375 }
   2376 
   2377 void WebPageProxy::didChooseFilesForOpenPanel(const Vector<String>& fileURLs)
   2378 {
   2379     if (!isValid())
   2380         return;
   2381 
   2382 #if ENABLE(WEB_PROCESS_SANDBOX)
   2383     // FIXME: The sandbox extensions should be sent with the DidChooseFilesForOpenPanel message. This
   2384     // is gated on a way of passing SandboxExtension::Handles in a Vector.
   2385     for (size_t i = 0; i < fileURLs.size(); ++i) {
   2386         SandboxExtension::Handle sandboxExtensionHandle;
   2387         SandboxExtension::createHandle(fileURLs[i], SandboxExtension::ReadOnly, sandboxExtensionHandle);
   2388         process()->send(Messages::WebPage::ExtendSandboxForFileFromOpenPanel(sandboxExtensionHandle), m_pageID);
   2389     }
   2390 #endif
   2391 
   2392     process()->send(Messages::WebPage::DidChooseFilesForOpenPanel(fileURLs), m_pageID);
   2393 
   2394     m_openPanelResultListener->invalidate();
   2395     m_openPanelResultListener = 0;
   2396 }
   2397 
   2398 void WebPageProxy::didCancelForOpenPanel()
   2399 {
   2400     if (!isValid())
   2401         return;
   2402 
   2403     process()->send(Messages::WebPage::DidCancelForOpenPanel(), m_pageID);
   2404 
   2405     m_openPanelResultListener->invalidate();
   2406     m_openPanelResultListener = 0;
   2407 }
   2408 
   2409 void WebPageProxy::advanceToNextMisspelling(bool startBeforeSelection) const
   2410 {
   2411     process()->send(Messages::WebPage::AdvanceToNextMisspelling(startBeforeSelection), m_pageID);
   2412 }
   2413 
   2414 void WebPageProxy::changeSpellingToWord(const String& word) const
   2415 {
   2416     if (word.isEmpty())
   2417         return;
   2418 
   2419     process()->send(Messages::WebPage::ChangeSpellingToWord(word), m_pageID);
   2420 }
   2421 
   2422 void WebPageProxy::registerEditCommand(PassRefPtr<WebEditCommandProxy> commandProxy, UndoOrRedo undoOrRedo)
   2423 {
   2424     m_pageClient->registerEditCommand(commandProxy, undoOrRedo);
   2425 }
   2426 
   2427 void WebPageProxy::addEditCommand(WebEditCommandProxy* command)
   2428 {
   2429     m_editCommandSet.add(command);
   2430 }
   2431 
   2432 void WebPageProxy::removeEditCommand(WebEditCommandProxy* command)
   2433 {
   2434     m_editCommandSet.remove(command);
   2435 
   2436     if (!isValid())
   2437         return;
   2438     process()->send(Messages::WebPage::DidRemoveEditCommand(command->commandID()), m_pageID);
   2439 }
   2440 
   2441 bool WebPageProxy::isValidEditCommand(WebEditCommandProxy* command)
   2442 {
   2443     return m_editCommandSet.find(command) != m_editCommandSet.end();
   2444 }
   2445 
   2446 int64_t WebPageProxy::spellDocumentTag()
   2447 {
   2448     if (!m_hasSpellDocumentTag) {
   2449         m_spellDocumentTag = TextChecker::uniqueSpellDocumentTag(this);
   2450         m_hasSpellDocumentTag = true;
   2451     }
   2452 
   2453     return m_spellDocumentTag;
   2454 }
   2455 
   2456 #if USE(UNIFIED_TEXT_CHECKING)
   2457 
   2458 void WebPageProxy::checkTextOfParagraph(const String& text, uint64_t checkingTypes, Vector<TextCheckingResult>& results)
   2459 {
   2460     results = TextChecker::checkTextOfParagraph(spellDocumentTag(), text.characters(), text.length(), checkingTypes);
   2461 }
   2462 
   2463 #endif
   2464 
   2465 void WebPageProxy::checkSpellingOfString(const String& text, int32_t& misspellingLocation, int32_t& misspellingLength)
   2466 {
   2467     TextChecker::checkSpellingOfString(spellDocumentTag(), text.characters(), text.length(), misspellingLocation, misspellingLength);
   2468 }
   2469 
   2470 void WebPageProxy::checkGrammarOfString(const String& text, Vector<WebCore::GrammarDetail>& grammarDetails, int32_t& badGrammarLocation, int32_t& badGrammarLength)
   2471 {
   2472     TextChecker::checkGrammarOfString(spellDocumentTag(), text.characters(), text.length(), grammarDetails, badGrammarLocation, badGrammarLength);
   2473 }
   2474 
   2475 void WebPageProxy::spellingUIIsShowing(bool& isShowing)
   2476 {
   2477     isShowing = TextChecker::spellingUIIsShowing();
   2478 }
   2479 
   2480 void WebPageProxy::updateSpellingUIWithMisspelledWord(const String& misspelledWord)
   2481 {
   2482     TextChecker::updateSpellingUIWithMisspelledWord(spellDocumentTag(), misspelledWord);
   2483 }
   2484 
   2485 void WebPageProxy::updateSpellingUIWithGrammarString(const String& badGrammarPhrase, const GrammarDetail& grammarDetail)
   2486 {
   2487     TextChecker::updateSpellingUIWithGrammarString(spellDocumentTag(), badGrammarPhrase, grammarDetail);
   2488 }
   2489 
   2490 void WebPageProxy::getGuessesForWord(const String& word, const String& context, Vector<String>& guesses)
   2491 {
   2492     TextChecker::getGuessesForWord(spellDocumentTag(), word, context, guesses);
   2493 }
   2494 
   2495 void WebPageProxy::learnWord(const String& word)
   2496 {
   2497     MESSAGE_CHECK(m_pendingLearnOrIgnoreWordMessageCount);
   2498     --m_pendingLearnOrIgnoreWordMessageCount;
   2499 
   2500     TextChecker::learnWord(spellDocumentTag(), word);
   2501 }
   2502 
   2503 void WebPageProxy::ignoreWord(const String& word)
   2504 {
   2505     MESSAGE_CHECK(m_pendingLearnOrIgnoreWordMessageCount);
   2506     --m_pendingLearnOrIgnoreWordMessageCount;
   2507 
   2508     TextChecker::ignoreWord(spellDocumentTag(), word);
   2509 }
   2510 
   2511 // Other
   2512 
   2513 void WebPageProxy::setFocus(bool focused)
   2514 {
   2515     if (focused)
   2516         m_uiClient.focus(this);
   2517     else
   2518         m_uiClient.unfocus(this);
   2519 }
   2520 
   2521 void WebPageProxy::takeFocus(uint32_t direction)
   2522 {
   2523     m_uiClient.takeFocus(this, (static_cast<FocusDirection>(direction) == FocusDirectionForward) ? kWKFocusDirectionForward : kWKFocusDirectionBackward);
   2524 }
   2525 
   2526 void WebPageProxy::setToolTip(const String& toolTip)
   2527 {
   2528     String oldToolTip = m_toolTip;
   2529     m_toolTip = toolTip;
   2530     m_pageClient->toolTipChanged(oldToolTip, m_toolTip);
   2531 }
   2532 
   2533 void WebPageProxy::setCursor(const WebCore::Cursor& cursor)
   2534 {
   2535     m_pageClient->setCursor(cursor);
   2536 }
   2537 
   2538 void WebPageProxy::didReceiveEvent(uint32_t opaqueType, bool handled)
   2539 {
   2540     WebEvent::Type type = static_cast<WebEvent::Type>(opaqueType);
   2541 
   2542     switch (type) {
   2543     case WebEvent::NoType:
   2544     case WebEvent::MouseMove:
   2545         break;
   2546 
   2547     case WebEvent::MouseDown:
   2548     case WebEvent::MouseUp:
   2549     case WebEvent::Wheel:
   2550     case WebEvent::KeyDown:
   2551     case WebEvent::KeyUp:
   2552     case WebEvent::RawKeyDown:
   2553     case WebEvent::Char:
   2554 #if ENABLE(GESTURE_EVENTS)
   2555     case WebEvent::GestureScrollBegin:
   2556     case WebEvent::GestureScrollEnd:
   2557 #endif
   2558         process()->responsivenessTimer()->stop();
   2559         break;
   2560     }
   2561 
   2562     switch (type) {
   2563     case WebEvent::NoType:
   2564         break;
   2565     case WebEvent::MouseMove:
   2566         m_processingMouseMoveEvent = false;
   2567         if (m_nextMouseMoveEvent) {
   2568             handleMouseEvent(*m_nextMouseMoveEvent);
   2569             m_nextMouseMoveEvent = nullptr;
   2570         }
   2571         break;
   2572     case WebEvent::MouseDown:
   2573 #if ENABLE(GESTURE_EVENTS)
   2574     case WebEvent::GestureScrollBegin:
   2575     case WebEvent::GestureScrollEnd:
   2576 #endif
   2577         break;
   2578     case WebEvent::MouseUp:
   2579         m_currentlyProcessedMouseDownEvent = nullptr;
   2580         break;
   2581 
   2582     case WebEvent::Wheel: {
   2583         m_processingWheelEvent = false;
   2584         if (m_nextWheelEvent) {
   2585             handleWheelEvent(*m_nextWheelEvent);
   2586             m_nextWheelEvent = nullptr;
   2587         }
   2588         break;
   2589     }
   2590 
   2591     case WebEvent::KeyDown:
   2592     case WebEvent::KeyUp:
   2593     case WebEvent::RawKeyDown:
   2594     case WebEvent::Char: {
   2595         NativeWebKeyboardEvent event = m_keyEventQueue.first();
   2596         MESSAGE_CHECK(type == event.type());
   2597 
   2598         m_keyEventQueue.removeFirst();
   2599 
   2600         m_pageClient->doneWithKeyEvent(event, handled);
   2601 
   2602         if (handled)
   2603             break;
   2604 
   2605         if (m_uiClient.implementsDidNotHandleKeyEvent())
   2606             m_uiClient.didNotHandleKeyEvent(this, event);
   2607 #if PLATFORM(WIN)
   2608         else
   2609             ::TranslateMessage(event.nativeEvent());
   2610 #endif
   2611         break;
   2612     }
   2613     }
   2614 }
   2615 
   2616 void WebPageProxy::voidCallback(uint64_t callbackID)
   2617 {
   2618     RefPtr<VoidCallback> callback = m_voidCallbacks.take(callbackID);
   2619     if (!callback) {
   2620         // FIXME: Log error or assert.
   2621         return;
   2622     }
   2623 
   2624     callback->performCallback();
   2625 }
   2626 
   2627 void WebPageProxy::dataCallback(const CoreIPC::DataReference& dataReference, uint64_t callbackID)
   2628 {
   2629     RefPtr<DataCallback> callback = m_dataCallbacks.take(callbackID);
   2630     if (!callback) {
   2631         // FIXME: Log error or assert.
   2632         return;
   2633     }
   2634 
   2635     callback->performCallbackWithReturnValue(WebData::create(dataReference.data(), dataReference.size()).get());
   2636 }
   2637 
   2638 void WebPageProxy::stringCallback(const String& resultString, uint64_t callbackID)
   2639 {
   2640     RefPtr<StringCallback> callback = m_stringCallbacks.take(callbackID);
   2641     if (!callback) {
   2642         // FIXME: Log error or assert.
   2643         // this can validly happen if a load invalidated the callback, though
   2644         return;
   2645     }
   2646 
   2647     m_loadDependentStringCallbackIDs.remove(callbackID);
   2648 
   2649     callback->performCallbackWithReturnValue(resultString.impl());
   2650 }
   2651 
   2652 void WebPageProxy::scriptValueCallback(const CoreIPC::DataReference& dataReference, uint64_t callbackID)
   2653 {
   2654     RefPtr<ScriptValueCallback> callback = m_scriptValueCallbacks.take(callbackID);
   2655     if (!callback) {
   2656         // FIXME: Log error or assert.
   2657         return;
   2658     }
   2659 
   2660     Vector<uint8_t> data;
   2661     data.reserveInitialCapacity(dataReference.size());
   2662     data.append(dataReference.data(), dataReference.size());
   2663 
   2664     callback->performCallbackWithReturnValue(data.size() ? WebSerializedScriptValue::adopt(data).get() : 0);
   2665 }
   2666 
   2667 void WebPageProxy::computedPagesCallback(const Vector<WebCore::IntRect>& pageRects, double totalScaleFactorForPrinting, uint64_t callbackID)
   2668 {
   2669     RefPtr<ComputedPagesCallback> callback = m_computedPagesCallbacks.take(callbackID);
   2670     if (!callback) {
   2671         // FIXME: Log error or assert.
   2672         return;
   2673     }
   2674 
   2675     callback->performCallbackWithReturnValue(pageRects, totalScaleFactorForPrinting);
   2676 }
   2677 
   2678 void WebPageProxy::validateCommandCallback(const String& commandName, bool isEnabled, int state, uint64_t callbackID)
   2679 {
   2680     RefPtr<ValidateCommandCallback> callback = m_validateCommandCallbacks.take(callbackID);
   2681     if (!callback) {
   2682         // FIXME: Log error or assert.
   2683         return;
   2684     }
   2685 
   2686     callback->performCallbackWithReturnValue(commandName.impl(), isEnabled, state);
   2687 }
   2688 
   2689 void WebPageProxy::focusedFrameChanged(uint64_t frameID)
   2690 {
   2691     if (!frameID) {
   2692         m_focusedFrame = 0;
   2693         return;
   2694     }
   2695 
   2696     WebFrameProxy* frame = process()->webFrame(frameID);
   2697     MESSAGE_CHECK(frame);
   2698 
   2699     m_focusedFrame = frame;
   2700 }
   2701 
   2702 void WebPageProxy::frameSetLargestFrameChanged(uint64_t frameID)
   2703 {
   2704     if (!frameID) {
   2705         m_frameSetLargestFrame = 0;
   2706         return;
   2707     }
   2708 
   2709     WebFrameProxy* frame = process()->webFrame(frameID);
   2710     MESSAGE_CHECK(frame);
   2711 
   2712     m_frameSetLargestFrame = frame;
   2713 }
   2714 
   2715 void WebPageProxy::processDidBecomeUnresponsive()
   2716 {
   2717     m_loaderClient.processDidBecomeUnresponsive(this);
   2718 }
   2719 
   2720 void WebPageProxy::processDidBecomeResponsive()
   2721 {
   2722     m_loaderClient.processDidBecomeResponsive(this);
   2723 }
   2724 
   2725 void WebPageProxy::processDidCrash()
   2726 {
   2727     ASSERT(m_pageClient);
   2728 
   2729     m_isValid = false;
   2730 
   2731     m_mainFrame = nullptr;
   2732     m_drawingArea = nullptr;
   2733 
   2734 #if ENABLE(INSPECTOR)
   2735     if (m_inspector) {
   2736         m_inspector->invalidate();
   2737         m_inspector = nullptr;
   2738     }
   2739 #endif
   2740 
   2741 #if ENABLE(FULLSCREEN_API)
   2742     if (m_fullScreenManager) {
   2743         m_fullScreenManager->invalidate();
   2744         m_fullScreenManager = nullptr;
   2745     }
   2746 #endif
   2747 
   2748     if (m_openPanelResultListener) {
   2749         m_openPanelResultListener->invalidate();
   2750         m_openPanelResultListener = nullptr;
   2751     }
   2752 
   2753     m_geolocationPermissionRequestManager.invalidateRequests();
   2754 
   2755     m_toolTip = String();
   2756 
   2757     m_mainFrameHasHorizontalScrollbar = false;
   2758     m_mainFrameHasVerticalScrollbar = false;
   2759 
   2760     m_mainFrameIsPinnedToLeftSide = false;
   2761     m_mainFrameIsPinnedToRightSide = false;
   2762 
   2763     invalidateCallbackMap(m_voidCallbacks);
   2764     invalidateCallbackMap(m_dataCallbacks);
   2765     invalidateCallbackMap(m_stringCallbacks);
   2766     m_loadDependentStringCallbackIDs.clear();
   2767     invalidateCallbackMap(m_scriptValueCallbacks);
   2768     invalidateCallbackMap(m_computedPagesCallbacks);
   2769     invalidateCallbackMap(m_validateCommandCallbacks);
   2770 
   2771     Vector<WebEditCommandProxy*> editCommandVector;
   2772     copyToVector(m_editCommandSet, editCommandVector);
   2773     m_editCommandSet.clear();
   2774     for (size_t i = 0, size = editCommandVector.size(); i < size; ++i)
   2775         editCommandVector[i]->invalidate();
   2776     m_pageClient->clearAllEditCommands();
   2777 
   2778     m_activePopupMenu = 0;
   2779 
   2780     m_estimatedProgress = 0.0;
   2781 
   2782     m_pendingLearnOrIgnoreWordMessageCount = 0;
   2783 
   2784     m_pageClient->processDidCrash();
   2785     m_loaderClient.processDidCrash(this);
   2786 
   2787     // Can't expect DidReceiveEvent notifications from a crashed web process.
   2788     m_keyEventQueue.clear();
   2789     m_nextWheelEvent = nullptr;
   2790     m_nextMouseMoveEvent = nullptr;
   2791     m_currentlyProcessedMouseDownEvent = nullptr;
   2792 
   2793 #if PLATFORM(MAC) && !defined(BUILDING_ON_SNOW_LEOPARD)
   2794     dismissCorrectionPanel(ReasonForDismissingCorrectionPanelIgnored);
   2795     m_pageClient->dismissDictionaryLookupPanel();
   2796 #endif
   2797 }
   2798 
   2799 WebPageCreationParameters WebPageProxy::creationParameters() const
   2800 {
   2801     WebPageCreationParameters parameters;
   2802 
   2803     parameters.viewSize = m_pageClient->viewSize();
   2804     parameters.isActive = m_pageClient->isViewWindowActive();
   2805     parameters.isFocused = m_pageClient->isViewFocused();
   2806     parameters.isVisible = m_pageClient->isViewVisible();
   2807     parameters.isInWindow = m_pageClient->isViewInWindow();
   2808     parameters.drawingAreaType = m_drawingArea->type();
   2809     parameters.store = m_pageGroup->preferences()->store();
   2810     parameters.pageGroupData = m_pageGroup->data();
   2811     parameters.drawsBackground = m_drawsBackground;
   2812     parameters.drawsTransparentBackground = m_drawsTransparentBackground;
   2813     parameters.areMemoryCacheClientCallsEnabled = m_areMemoryCacheClientCallsEnabled;
   2814     parameters.useFixedLayout = m_useFixedLayout;
   2815     parameters.fixedLayoutSize = m_fixedLayoutSize;
   2816     parameters.userAgent = userAgent();
   2817     parameters.sessionState = SessionState(m_backForwardList->entries(), m_backForwardList->currentIndex());
   2818     parameters.highestUsedBackForwardItemID = WebBackForwardListItem::highedUsedItemID();
   2819     parameters.canRunBeforeUnloadConfirmPanel = m_uiClient.canRunBeforeUnloadConfirmPanel();
   2820     parameters.canRunModal = m_uiClient.canRunModal();
   2821     parameters.userSpaceScaleFactor = m_pageClient->userSpaceScaleFactor();
   2822 
   2823 #if PLATFORM(MAC)
   2824     parameters.isSmartInsertDeleteEnabled = m_isSmartInsertDeleteEnabled;
   2825 #endif
   2826 
   2827 #if PLATFORM(WIN)
   2828     parameters.nativeWindow = m_pageClient->nativeWindow();
   2829 #endif
   2830 
   2831     return parameters;
   2832 }
   2833 
   2834 #if USE(ACCELERATED_COMPOSITING)
   2835 void WebPageProxy::enterAcceleratedCompositingMode(const LayerTreeContext& layerTreeContext)
   2836 {
   2837     m_pageClient->enterAcceleratedCompositingMode(layerTreeContext);
   2838 }
   2839 
   2840 void WebPageProxy::exitAcceleratedCompositingMode()
   2841 {
   2842     m_pageClient->exitAcceleratedCompositingMode();
   2843 }
   2844 #endif // USE(ACCELERATED_COMPOSITING)
   2845 
   2846 void WebPageProxy::backForwardClear()
   2847 {
   2848     m_backForwardList->clear();
   2849 }
   2850 
   2851 void WebPageProxy::canAuthenticateAgainstProtectionSpaceInFrame(uint64_t frameID, const WebCore::ProtectionSpace& coreProtectionSpace, bool& canAuthenticate)
   2852 {
   2853     WebFrameProxy* frame = process()->webFrame(frameID);
   2854     MESSAGE_CHECK(frame);
   2855 
   2856     RefPtr<WebProtectionSpace> protectionSpace = WebProtectionSpace::create(coreProtectionSpace);
   2857 
   2858     canAuthenticate = m_loaderClient.canAuthenticateAgainstProtectionSpaceInFrame(this, frame, protectionSpace.get());
   2859 }
   2860 
   2861 void WebPageProxy::didReceiveAuthenticationChallenge(uint64_t frameID, const WebCore::AuthenticationChallenge& coreChallenge, uint64_t challengeID)
   2862 {
   2863     WebFrameProxy* frame = process()->webFrame(frameID);
   2864     MESSAGE_CHECK(frame);
   2865 
   2866     RefPtr<AuthenticationChallengeProxy> authenticationChallenge = AuthenticationChallengeProxy::create(coreChallenge, challengeID, process());
   2867 
   2868     m_loaderClient.didReceiveAuthenticationChallengeInFrame(this, frame, authenticationChallenge.get());
   2869 }
   2870 
   2871 void WebPageProxy::exceededDatabaseQuota(uint64_t frameID, const String& originIdentifier, const String& databaseName, const String& displayName, uint64_t currentQuota, uint64_t currentUsage, uint64_t expectedUsage, uint64_t& newQuota)
   2872 {
   2873     WebFrameProxy* frame = process()->webFrame(frameID);
   2874     MESSAGE_CHECK(frame);
   2875 
   2876     RefPtr<WebSecurityOrigin> origin = WebSecurityOrigin::create(originIdentifier);
   2877 
   2878     newQuota = m_uiClient.exceededDatabaseQuota(this, frame, origin.get(), databaseName, displayName, currentQuota, currentUsage, expectedUsage);
   2879 }
   2880 
   2881 void WebPageProxy::requestGeolocationPermissionForFrame(uint64_t geolocationID, uint64_t frameID, String originIdentifier)
   2882 {
   2883     WebFrameProxy* frame = process()->webFrame(frameID);
   2884     MESSAGE_CHECK(frame);
   2885 
   2886     RefPtr<WebSecurityOrigin> origin = WebSecurityOrigin::create(originIdentifier);
   2887     RefPtr<GeolocationPermissionRequestProxy> request = m_geolocationPermissionRequestManager.createRequest(geolocationID);
   2888 
   2889     if (!m_uiClient.decidePolicyForGeolocationPermissionRequest(this, frame, origin.get(), request.get()))
   2890         request->deny();
   2891 }
   2892 
   2893 float WebPageProxy::headerHeight(WebFrameProxy* frame)
   2894 {
   2895     return m_uiClient.headerHeight(this, frame);
   2896 }
   2897 
   2898 float WebPageProxy::footerHeight(WebFrameProxy* frame)
   2899 {
   2900     return m_uiClient.footerHeight(this, frame);
   2901 }
   2902 
   2903 void WebPageProxy::drawHeader(WebFrameProxy* frame, const FloatRect& rect)
   2904 {
   2905     m_uiClient.drawHeader(this, frame, rect);
   2906 }
   2907 
   2908 void WebPageProxy::drawFooter(WebFrameProxy* frame, const FloatRect& rect)
   2909 {
   2910     m_uiClient.drawFooter(this, frame, rect);
   2911 }
   2912 
   2913 void WebPageProxy::didCompleteRubberBandForMainFrame(const IntSize& initialOverhang)
   2914 {
   2915     m_uiClient.didCompleteRubberBandForMainFrame(this, initialOverhang);
   2916 }
   2917 
   2918 void WebPageProxy::didChangeScrollbarsForMainFrame(bool hasHorizontalScrollbar, bool hasVerticalScrollbar)
   2919 {
   2920     m_mainFrameHasHorizontalScrollbar = hasHorizontalScrollbar;
   2921     m_mainFrameHasVerticalScrollbar = hasVerticalScrollbar;
   2922 
   2923     m_pageClient->didChangeScrollbarsForMainFrame();
   2924 }
   2925 
   2926 void WebPageProxy::didChangeScrollOffsetPinningForMainFrame(bool pinnedToLeftSide, bool pinnedToRightSide)
   2927 {
   2928     m_mainFrameIsPinnedToLeftSide = pinnedToLeftSide;
   2929     m_mainFrameIsPinnedToRightSide = pinnedToRightSide;
   2930 }
   2931 
   2932 void WebPageProxy::didFinishLoadingDataForCustomRepresentation(const String& suggestedFilename, const CoreIPC::DataReference& dataReference)
   2933 {
   2934     m_pageClient->didFinishLoadingDataForCustomRepresentation(suggestedFilename, dataReference);
   2935 }
   2936 
   2937 void WebPageProxy::backForwardRemovedItem(uint64_t itemID)
   2938 {
   2939     process()->send(Messages::WebPage::DidRemoveBackForwardItem(itemID), m_pageID);
   2940 }
   2941 
   2942 void WebPageProxy::beginPrinting(WebFrameProxy* frame, const PrintInfo& printInfo)
   2943 {
   2944     if (m_isInPrintingMode)
   2945         return;
   2946 
   2947     m_isInPrintingMode = true;
   2948     process()->send(Messages::WebPage::BeginPrinting(frame->frameID(), printInfo), m_pageID, m_isPerformingDOMPrintOperation ? CoreIPC::DispatchMessageEvenWhenWaitingForSyncReply : 0);
   2949 }
   2950 
   2951 void WebPageProxy::endPrinting()
   2952 {
   2953     if (!m_isInPrintingMode)
   2954         return;
   2955 
   2956     m_isInPrintingMode = false;
   2957     process()->send(Messages::WebPage::EndPrinting(), m_pageID, m_isPerformingDOMPrintOperation ? CoreIPC::DispatchMessageEvenWhenWaitingForSyncReply : 0);
   2958 }
   2959 
   2960 void WebPageProxy::computePagesForPrinting(WebFrameProxy* frame, const PrintInfo& printInfo, PassRefPtr<ComputedPagesCallback> prpCallback)
   2961 {
   2962     RefPtr<ComputedPagesCallback> callback = prpCallback;
   2963     if (!isValid()) {
   2964         callback->invalidate();
   2965         return;
   2966     }
   2967 
   2968     uint64_t callbackID = callback->callbackID();
   2969     m_computedPagesCallbacks.set(callbackID, callback.get());
   2970     m_isInPrintingMode = true;
   2971     process()->send(Messages::WebPage::ComputePagesForPrinting(frame->frameID(), printInfo, callbackID), m_pageID, m_isPerformingDOMPrintOperation ? CoreIPC::DispatchMessageEvenWhenWaitingForSyncReply : 0);
   2972 }
   2973 
   2974 #if PLATFORM(MAC) || PLATFORM(WIN)
   2975 void WebPageProxy::drawRectToPDF(WebFrameProxy* frame, const IntRect& rect, PassRefPtr<DataCallback> prpCallback)
   2976 {
   2977     RefPtr<DataCallback> callback = prpCallback;
   2978     if (!isValid()) {
   2979         callback->invalidate();
   2980         return;
   2981     }
   2982 
   2983     uint64_t callbackID = callback->callbackID();
   2984     m_dataCallbacks.set(callbackID, callback.get());
   2985     process()->send(Messages::WebPage::DrawRectToPDF(frame->frameID(), rect, callbackID), m_pageID, m_isPerformingDOMPrintOperation ? CoreIPC::DispatchMessageEvenWhenWaitingForSyncReply : 0);
   2986 }
   2987 
   2988 void WebPageProxy::drawPagesToPDF(WebFrameProxy* frame, uint32_t first, uint32_t count, PassRefPtr<DataCallback> prpCallback)
   2989 {
   2990     RefPtr<DataCallback> callback = prpCallback;
   2991     if (!isValid()) {
   2992         callback->invalidate();
   2993         return;
   2994     }
   2995 
   2996     uint64_t callbackID = callback->callbackID();
   2997     m_dataCallbacks.set(callbackID, callback.get());
   2998     process()->send(Messages::WebPage::DrawPagesToPDF(frame->frameID(), first, count, callbackID), m_pageID, m_isPerformingDOMPrintOperation ? CoreIPC::DispatchMessageEvenWhenWaitingForSyncReply : 0);
   2999 }
   3000 #endif
   3001 
   3002 void WebPageProxy::flashBackingStoreUpdates(const Vector<IntRect>& updateRects)
   3003 {
   3004     m_pageClient->flashBackingStoreUpdates(updateRects);
   3005 }
   3006 
   3007 Color WebPageProxy::viewUpdatesFlashColor()
   3008 {
   3009     return Color(0, 200, 255);
   3010 }
   3011 
   3012 Color WebPageProxy::backingStoreUpdatesFlashColor()
   3013 {
   3014     return Color(200, 0, 255);
   3015 }
   3016 
   3017 void WebPageProxy::saveDataToFileInDownloadsFolder(const String& suggestedFilename, const String& mimeType, const String& originatingURLString, WebData* data)
   3018 {
   3019     m_uiClient.saveDataToFileInDownloadsFolder(this, suggestedFilename, mimeType, originatingURLString, data);
   3020 }
   3021 
   3022 void WebPageProxy::linkClicked(const String& url, const WebMouseEvent& event)
   3023 {
   3024     process()->send(Messages::WebPage::LinkClicked(url, event), m_pageID, 0);
   3025 }
   3026 
   3027 #if PLATFORM(MAC)
   3028 
   3029 void WebPageProxy::substitutionsPanelIsShowing(bool& isShowing)
   3030 {
   3031     isShowing = TextChecker::substitutionsPanelIsShowing();
   3032 }
   3033 
   3034 #if !defined(BUILDING_ON_SNOW_LEOPARD)
   3035 void WebPageProxy::showCorrectionPanel(int32_t panelType, const WebCore::FloatRect& boundingBoxOfReplacedString, const String& replacedString, const String& replacementString, const Vector<String>& alternativeReplacementStrings)
   3036 {
   3037     m_pageClient->showCorrectionPanel((WebCore::CorrectionPanelInfo::PanelType)panelType, boundingBoxOfReplacedString, replacedString, replacementString, alternativeReplacementStrings);
   3038 }
   3039 
   3040 void WebPageProxy::dismissCorrectionPanel(int32_t reason)
   3041 {
   3042     m_pageClient->dismissCorrectionPanel((WebCore::ReasonForDismissingCorrectionPanel)reason);
   3043 }
   3044 
   3045 void WebPageProxy::dismissCorrectionPanelSoon(int32_t reason, String& result)
   3046 {
   3047     result = m_pageClient->dismissCorrectionPanelSoon((WebCore::ReasonForDismissingCorrectionPanel)reason);
   3048 }
   3049 
   3050 void WebPageProxy::recordAutocorrectionResponse(int32_t responseType, const String& replacedString, const String& replacementString)
   3051 {
   3052     m_pageClient->recordAutocorrectionResponse((WebCore::EditorClient::AutocorrectionResponseType)responseType, replacedString, replacementString);
   3053 }
   3054 #endif // !defined(BUILDING_ON_SNOW_LEOPARD)
   3055 
   3056 void WebPageProxy::handleCorrectionPanelResult(const String& result)
   3057 {
   3058 #if !defined(BUILDING_ON_SNOW_LEOPARD)
   3059     if (!isClosed())
   3060         process()->send(Messages::WebPage::HandleCorrectionPanelResult(result), m_pageID, 0);
   3061 #endif
   3062 }
   3063 #endif // PLATFORM(MAC)
   3064 
   3065 } // namespace WebKit
   3066