1/* 2 * Copyright (C) 2009, 2012 Google Inc. All rights reserved. 3 * Copyright (C) 2011 Apple Inc. All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: 8 * 9 * * Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * * Redistributions in binary form must reproduce the above 12 * copyright notice, this list of conditions and the following disclaimer 13 * in the documentation and/or other materials provided with the 14 * distribution. 15 * * Neither the name of Google Inc. nor the names of its 16 * contributors may be used to endorse or promote products derived from 17 * this software without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 20 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 21 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 22 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 23 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 24 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 25 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32#include "config.h" 33#include "FrameLoaderClientImpl.h" 34 35#include "HTMLNames.h" 36#include "core/dom/Document.h" 37#include "core/dom/MessageEvent.h" 38#include "core/dom/MouseEvent.h" 39#include "core/history/HistoryItem.h" 40#include "core/html/HTMLAppletElement.h" 41#include "core/html/HTMLFormElement.h" // needed by core/loader/FormState.h 42#include "core/loader/DocumentLoader.h" 43#include "core/loader/FormState.h" 44#include "core/loader/FrameLoadRequest.h" 45#include "core/loader/FrameLoader.h" 46#include "core/loader/ProgressTracker.h" 47#include "core/loader/ResourceLoader.h" 48#include "core/page/Chrome.h" 49#include "core/page/EventHandler.h" 50#include "core/page/FrameView.h" 51#include "core/page/Page.h" 52#include "core/platform/MIMETypeRegistry.h" 53#include "core/platform/mediastream/RTCPeerConnectionHandler.h" 54#include "core/platform/network/HTTPParsers.h" 55#include "core/plugins/PluginData.h" 56#include "core/rendering/HitTestResult.h" 57#include <v8.h> 58#include "WebAutofillClient.h" 59#include "WebCachedURLRequest.h" 60#include "WebDOMEvent.h" 61#include "WebDataSourceImpl.h" 62#include "WebDevToolsAgentPrivate.h" 63#include "WebDocument.h" 64#include "WebFormElement.h" 65#include "WebFrameClient.h" 66#include "WebFrameImpl.h" 67#include "WebNode.h" 68#include "WebPermissionClient.h" 69#include "WebPlugin.h" 70#include "WebPluginContainerImpl.h" 71#include "WebPluginLoadObserver.h" 72#include "WebPluginParams.h" 73#include "WebSecurityOrigin.h" 74#include "WebViewClient.h" 75#include "WebViewImpl.h" 76#include "bindings/v8/ScriptController.h" 77#include "core/dom/UserGestureIndicator.h" 78#include "core/page/Settings.h" 79#include "core/page/WindowFeatures.h" 80#include "core/platform/chromium/support/WrappedResourceRequest.h" 81#include "core/platform/chromium/support/WrappedResourceResponse.h" 82#include "core/platform/network/SocketStreamHandleInternal.h" 83#include "public/platform/Platform.h" 84#include "public/platform/WebMimeRegistry.h" 85#include "public/platform/WebSocketStreamHandle.h" 86#include "public/platform/WebURL.h" 87#include "public/platform/WebURLError.h" 88#include "public/platform/WebVector.h" 89#include "wtf/StringExtras.h" 90#include "wtf/text/CString.h" 91#include "wtf/text/WTFString.h" 92 93using namespace WebCore; 94 95namespace WebKit { 96 97// Domain for internal error codes. 98static const char internalErrorDomain[] = "WebKit"; 99 100// An internal error code. Used to note a policy change error resulting from 101// dispatchDecidePolicyForMIMEType not passing the PolicyUse option. 102enum { 103 PolicyChangeError = -10000, 104}; 105 106FrameLoaderClientImpl::FrameLoaderClientImpl(WebFrameImpl* frame) 107 : m_webFrame(frame) 108{ 109} 110 111FrameLoaderClientImpl::~FrameLoaderClientImpl() 112{ 113} 114 115void FrameLoaderClientImpl::frameLoaderDestroyed() 116{ 117 // When the WebFrame was created, it had an extra reference given to it on 118 // behalf of the Frame. Since the WebFrame owns us, this extra ref also 119 // serves to keep us alive until the FrameLoader is done with us. The 120 // FrameLoader calls this method when it's going away. Therefore, we balance 121 // out that extra reference, which may cause 'this' to be deleted. 122 ASSERT(!m_webFrame->frame()); 123 m_webFrame->deref(); 124} 125 126void FrameLoaderClientImpl::dispatchDidClearWindowObjectInWorld(DOMWrapperWorld*) 127{ 128 if (m_webFrame->client()) 129 m_webFrame->client()->didClearWindowObject(m_webFrame); 130} 131 132void FrameLoaderClientImpl::documentElementAvailable() 133{ 134 if (m_webFrame->client()) 135 m_webFrame->client()->didCreateDocumentElement(m_webFrame); 136} 137 138void FrameLoaderClientImpl::didExhaustMemoryAvailableForScript() 139{ 140 if (m_webFrame->client()) 141 m_webFrame->client()->didExhaustMemoryAvailableForScript(m_webFrame); 142} 143 144void FrameLoaderClientImpl::didCreateScriptContext(v8::Handle<v8::Context> context, int extensionGroup, int worldId) 145{ 146 WebViewImpl* webview = m_webFrame->viewImpl(); 147 if (webview->devToolsAgentPrivate()) 148 webview->devToolsAgentPrivate()->didCreateScriptContext(m_webFrame, worldId); 149 if (m_webFrame->client()) 150 m_webFrame->client()->didCreateScriptContext(m_webFrame, context, extensionGroup, worldId); 151} 152 153void FrameLoaderClientImpl::willReleaseScriptContext(v8::Handle<v8::Context> context, int worldId) 154{ 155 if (m_webFrame->client()) 156 m_webFrame->client()->willReleaseScriptContext(m_webFrame, context, worldId); 157} 158 159bool FrameLoaderClientImpl::allowScriptExtension(const String& extensionName, 160 int extensionGroup, 161 int worldId) 162{ 163 WebViewImpl* webview = m_webFrame->viewImpl(); 164 if (webview && webview->permissionClient()) 165 return webview->permissionClient()->allowScriptExtension(m_webFrame, extensionName, extensionGroup, worldId); 166 167 return true; 168} 169 170void FrameLoaderClientImpl::didChangeScrollOffset() 171{ 172 if (m_webFrame->client()) 173 m_webFrame->client()->didChangeScrollOffset(m_webFrame); 174} 175 176bool FrameLoaderClientImpl::allowScript(bool enabledPerSettings) 177{ 178 WebViewImpl* webview = m_webFrame->viewImpl(); 179 if (webview && webview->permissionClient()) 180 return webview->permissionClient()->allowScript(m_webFrame, enabledPerSettings); 181 182 return enabledPerSettings; 183} 184 185bool FrameLoaderClientImpl::allowScriptFromSource(bool enabledPerSettings, const KURL& scriptURL) 186{ 187 WebViewImpl* webview = m_webFrame->viewImpl(); 188 if (webview && webview->permissionClient()) 189 return webview->permissionClient()->allowScriptFromSource(m_webFrame, enabledPerSettings, scriptURL); 190 191 return enabledPerSettings; 192} 193 194bool FrameLoaderClientImpl::allowPlugins(bool enabledPerSettings) 195{ 196 WebViewImpl* webview = m_webFrame->viewImpl(); 197 if (webview && webview->permissionClient()) 198 return webview->permissionClient()->allowPlugins(m_webFrame, enabledPerSettings); 199 200 return enabledPerSettings; 201} 202 203bool FrameLoaderClientImpl::allowImage(bool enabledPerSettings, const KURL& imageURL) 204{ 205 WebViewImpl* webview = m_webFrame->viewImpl(); 206 if (webview && webview->permissionClient()) 207 return webview->permissionClient()->allowImage(m_webFrame, enabledPerSettings, imageURL); 208 209 return enabledPerSettings; 210} 211 212bool FrameLoaderClientImpl::allowDisplayingInsecureContent(bool enabledPerSettings, SecurityOrigin* context, const KURL& url) 213{ 214 WebViewImpl* webview = m_webFrame->viewImpl(); 215 if (webview && webview->permissionClient()) 216 return webview->permissionClient()->allowDisplayingInsecureContent(m_webFrame, enabledPerSettings, WebSecurityOrigin(context), WebURL(url)); 217 218 return enabledPerSettings; 219} 220 221bool FrameLoaderClientImpl::allowRunningInsecureContent(bool enabledPerSettings, SecurityOrigin* context, const KURL& url) 222{ 223 WebViewImpl* webview = m_webFrame->viewImpl(); 224 if (webview && webview->permissionClient()) 225 return webview->permissionClient()->allowRunningInsecureContent(m_webFrame, enabledPerSettings, WebSecurityOrigin(context), WebURL(url)); 226 227 return enabledPerSettings; 228} 229 230void FrameLoaderClientImpl::didNotAllowScript() 231{ 232 WebViewImpl* webview = m_webFrame->viewImpl(); 233 if (webview && webview->permissionClient()) 234 webview->permissionClient()->didNotAllowScript(m_webFrame); 235} 236 237void FrameLoaderClientImpl::didNotAllowPlugins() 238{ 239 WebViewImpl* webview = m_webFrame->viewImpl(); 240 if (webview && webview->permissionClient()) 241 webview->permissionClient()->didNotAllowPlugins(m_webFrame); 242 243} 244 245bool FrameLoaderClientImpl::hasWebView() const 246{ 247 return m_webFrame->viewImpl(); 248} 249 250bool FrameLoaderClientImpl::hasFrameView() const 251{ 252 // The Mac port has this notion of a WebFrameView, which seems to be 253 // some wrapper around an NSView. Since our equivalent is HWND, I guess 254 // we have a "frameview" whenever we have the toplevel HWND. 255 return m_webFrame->viewImpl(); 256} 257 258void FrameLoaderClientImpl::detachedFromParent() 259{ 260 // Close down the proxy. The purpose of this change is to make the 261 // call to ScriptController::clearWindowShell a no-op when called from 262 // Frame::pageDestroyed. Without this change, this call to clearWindowShell 263 // will cause a crash. If you remove/modify this, just ensure that you can 264 // go to a page and then navigate to a new page without getting any asserts 265 // or crashes. 266 m_webFrame->frame()->script()->clearForClose(); 267 268 // Alert the client that the frame is being detached. This is the last 269 // chance we have to communicate with the client. 270 if (m_webFrame->client()) 271 m_webFrame->client()->frameDetached(m_webFrame); 272 273 // Stop communicating with the WebFrameClient at this point since we are no 274 // longer associated with the Page. 275 m_webFrame->setClient(0); 276} 277 278void FrameLoaderClientImpl::dispatchWillRequestAfterPreconnect(ResourceRequest& request) 279{ 280 if (m_webFrame->client()) { 281 WrappedResourceRequest webreq(request); 282 m_webFrame->client()->willRequestAfterPreconnect(m_webFrame, webreq); 283 } 284} 285 286void FrameLoaderClientImpl::dispatchWillSendRequest( 287 DocumentLoader* loader, unsigned long identifier, ResourceRequest& request, 288 const ResourceResponse& redirectResponse) 289{ 290 // Give the WebFrameClient a crack at the request. 291 if (m_webFrame->client()) { 292 WrappedResourceRequest webreq(request); 293 WrappedResourceResponse webresp(redirectResponse); 294 m_webFrame->client()->willSendRequest( 295 m_webFrame, identifier, webreq, webresp); 296 } 297} 298 299void FrameLoaderClientImpl::dispatchDidReceiveResponse(DocumentLoader* loader, 300 unsigned long identifier, 301 const ResourceResponse& response) 302{ 303 if (m_webFrame->client()) { 304 WrappedResourceResponse webresp(response); 305 m_webFrame->client()->didReceiveResponse(m_webFrame, identifier, webresp); 306 } 307} 308void FrameLoaderClientImpl::dispatchDidChangeResourcePriority(unsigned long identifier, 309 ResourceLoadPriority priority) 310{ 311 if (m_webFrame->client()) 312 m_webFrame->client()->didChangeResourcePriority(m_webFrame, identifier, static_cast<WebKit::WebURLRequest::Priority>(priority)); 313} 314 315// Called when a particular resource load completes 316void FrameLoaderClientImpl::dispatchDidFinishLoading(DocumentLoader* loader, 317 unsigned long identifier) 318{ 319 if (m_webFrame->client()) 320 m_webFrame->client()->didFinishResourceLoad(m_webFrame, identifier); 321} 322 323void FrameLoaderClientImpl::dispatchDidFinishDocumentLoad() 324{ 325 if (m_webFrame->client()) 326 m_webFrame->client()->didFinishDocumentLoad(m_webFrame); 327} 328 329void FrameLoaderClientImpl::dispatchDidLoadResourceFromMemoryCache( 330 DocumentLoader* loader, 331 const ResourceRequest& request, 332 const ResourceResponse& response, 333 int length) 334{ 335 if (m_webFrame->client()) { 336 WrappedResourceRequest webreq(request); 337 WrappedResourceResponse webresp(response); 338 m_webFrame->client()->didLoadResourceFromMemoryCache( 339 m_webFrame, webreq, webresp); 340 } 341} 342 343void FrameLoaderClientImpl::dispatchDidHandleOnloadEvents() 344{ 345 if (m_webFrame->client()) 346 m_webFrame->client()->didHandleOnloadEvents(m_webFrame); 347} 348 349void FrameLoaderClientImpl::dispatchDidReceiveServerRedirectForProvisionalLoad() 350{ 351 if (m_webFrame->client()) 352 m_webFrame->client()->didReceiveServerRedirectForProvisionalLoad(m_webFrame); 353} 354 355void FrameLoaderClientImpl::dispatchDidNavigateWithinPage() 356{ 357 bool isNewNavigation; 358 m_webFrame->viewImpl()->didCommitLoad(&isNewNavigation, true); 359 if (m_webFrame->client()) 360 m_webFrame->client()->didNavigateWithinPage(m_webFrame, isNewNavigation); 361} 362 363void FrameLoaderClientImpl::dispatchWillClose() 364{ 365 if (m_webFrame->client()) 366 m_webFrame->client()->willClose(m_webFrame); 367} 368 369void FrameLoaderClientImpl::dispatchDidStartProvisionalLoad() 370{ 371 if (m_webFrame->client()) 372 m_webFrame->client()->didStartProvisionalLoad(m_webFrame); 373} 374 375void FrameLoaderClientImpl::dispatchDidReceiveTitle(const StringWithDirection& title) 376{ 377 if (m_webFrame->client()) 378 m_webFrame->client()->didReceiveTitle(m_webFrame, title.string(), title.direction() == LTR ? WebTextDirectionLeftToRight : WebTextDirectionRightToLeft); 379} 380 381void FrameLoaderClientImpl::dispatchDidChangeIcons(WebCore::IconType type) 382{ 383 if (m_webFrame->client()) 384 m_webFrame->client()->didChangeIcon(m_webFrame, static_cast<WebIconURL::Type>(type)); 385} 386 387void FrameLoaderClientImpl::dispatchDidCommitLoad() 388{ 389 WebViewImpl* webview = m_webFrame->viewImpl(); 390 bool isNewNavigation; 391 webview->didCommitLoad(&isNewNavigation, false); 392 393 if (m_webFrame->client()) 394 m_webFrame->client()->didCommitProvisionalLoad(m_webFrame, isNewNavigation); 395} 396 397void FrameLoaderClientImpl::dispatchDidFailProvisionalLoad( 398 const ResourceError& error) 399{ 400 401 // If a policy change occured, then we do not want to inform the plugin 402 // delegate. See http://b/907789 for details. FIXME: This means the 403 // plugin won't receive NPP_URLNotify, which seems like it could result in 404 // a memory leak in the plugin!! 405 if (error.domain() == internalErrorDomain 406 && error.errorCode() == PolicyChangeError) { 407 m_webFrame->didFail(ResourceError::cancelledError(error.failingURL()), true); 408 return; 409 } 410 411 OwnPtr<WebPluginLoadObserver> observer = pluginLoadObserver(); 412 m_webFrame->didFail(error, true); 413 if (observer) 414 observer->didFailLoading(error); 415} 416 417void FrameLoaderClientImpl::dispatchDidFailLoad(const ResourceError& error) 418{ 419 OwnPtr<WebPluginLoadObserver> observer = pluginLoadObserver(); 420 m_webFrame->didFail(error, false); 421 if (observer) 422 observer->didFailLoading(error); 423 424 // Don't clear the redirect chain, this will happen in the middle of client 425 // redirects, and we need the context. The chain will be cleared when the 426 // provisional load succeeds or fails, not the "real" one. 427} 428 429void FrameLoaderClientImpl::dispatchDidFinishLoad() 430{ 431 OwnPtr<WebPluginLoadObserver> observer = pluginLoadObserver(); 432 433 if (m_webFrame->client()) 434 m_webFrame->client()->didFinishLoad(m_webFrame); 435 436 if (observer) 437 observer->didFinishLoading(); 438 439 // Don't clear the redirect chain, this will happen in the middle of client 440 // redirects, and we need the context. The chain will be cleared when the 441 // provisional load succeeds or fails, not the "real" one. 442} 443 444void FrameLoaderClientImpl::dispatchDidLayout(LayoutMilestones milestones) 445{ 446 if (!m_webFrame->client()) 447 return; 448 449 if (milestones & DidFirstLayout) 450 m_webFrame->client()->didFirstLayout(m_webFrame); 451 if (milestones & DidFirstVisuallyNonEmptyLayout) 452 m_webFrame->client()->didFirstVisuallyNonEmptyLayout(m_webFrame); 453} 454 455NavigationPolicy FrameLoaderClientImpl::decidePolicyForNavigation(const ResourceRequest& request, DocumentLoader* loader, NavigationPolicy policy) 456{ 457 if (!m_webFrame->client()) 458 return NavigationPolicyIgnore; 459 WebDataSourceImpl* ds = WebDataSourceImpl::fromDocumentLoader(loader); 460 WebNavigationPolicy webPolicy = m_webFrame->client()->decidePolicyForNavigation(m_webFrame, ds->extraData(), WrappedResourceRequest(request), 461 ds->navigationType(), static_cast<WebNavigationPolicy>(policy), ds->isRedirect()); 462 return static_cast<NavigationPolicy>(webPolicy); 463} 464 465bool FrameLoaderClientImpl::shouldAbortNavigationAfterUrlResolve(const KURL& base, const String& fragment, const KURL& result) { 466 if (!m_webFrame->client()) 467 return false; 468 return m_webFrame->client()->shouldAbortNavigationAfterUrlResolve(base, fragment, result); 469} 470 471void FrameLoaderClientImpl::dispatchWillRequestResource(FetchRequest* request) 472{ 473 if (m_webFrame->client()) { 474 WebCachedURLRequest urlRequest(request); 475 m_webFrame->client()->willRequestResource(m_webFrame, urlRequest); 476 } 477} 478 479void FrameLoaderClientImpl::dispatchWillSendSubmitEvent(PassRefPtr<FormState> prpFormState) 480{ 481 if (m_webFrame->client()) 482 m_webFrame->client()->willSendSubmitEvent(m_webFrame, WebFormElement(prpFormState->form())); 483} 484 485void FrameLoaderClientImpl::dispatchWillSubmitForm(PassRefPtr<FormState> formState) 486{ 487 if (m_webFrame->client()) 488 m_webFrame->client()->willSubmitForm(m_webFrame, WebFormElement(formState->form())); 489} 490 491void FrameLoaderClientImpl::postProgressStartedNotification() 492{ 493 WebViewImpl* webview = m_webFrame->viewImpl(); 494 if (webview && webview->client()) 495 webview->client()->didStartLoading(); 496} 497 498void FrameLoaderClientImpl::postProgressEstimateChangedNotification() 499{ 500 WebViewImpl* webview = m_webFrame->viewImpl(); 501 if (webview && webview->client()) { 502 webview->client()->didChangeLoadProgress( 503 m_webFrame, m_webFrame->frame()->page()->progress()->estimatedProgress()); 504 } 505} 506 507void FrameLoaderClientImpl::postProgressFinishedNotification() 508{ 509 // FIXME: why might the webview be null? http://b/1234461 510 WebViewImpl* webview = m_webFrame->viewImpl(); 511 if (webview && webview->client()) 512 webview->client()->didStopLoading(); 513} 514 515void FrameLoaderClientImpl::loadURLExternally(const ResourceRequest& request, NavigationPolicy policy, const String& suggestedName) 516{ 517 if (m_webFrame->client()) { 518 WrappedResourceRequest webreq(request); 519 m_webFrame->client()->loadURLExternally( 520 m_webFrame, webreq, static_cast<WebNavigationPolicy>(policy), suggestedName); 521 } 522} 523 524bool FrameLoaderClientImpl::shouldGoToHistoryItem(HistoryItem* item) const 525{ 526 const KURL& url = item->url(); 527 if (!url.protocolIs(backForwardNavigationScheme)) 528 return true; 529 530 // Else, we'll punt this history navigation to the embedder. It is 531 // necessary that we intercept this here, well before the FrameLoader 532 // has made any state changes for this history traversal. 533 534 bool ok; 535 int offset = url.lastPathComponent().toIntStrict(&ok); 536 if (!ok) { 537 ASSERT_NOT_REACHED(); 538 return false; 539 } 540 541 WebViewImpl* webview = m_webFrame->viewImpl(); 542 if (webview->client()) 543 webview->client()->navigateBackForwardSoon(offset); 544 545 return false; 546} 547 548bool FrameLoaderClientImpl::shouldStopLoadingForHistoryItem(HistoryItem* targetItem) const 549{ 550 // Don't stop loading for pseudo-back-forward URLs, since they will get 551 // translated and then pass through again. 552 const KURL& url = targetItem->url(); 553 return !url.protocolIs(backForwardNavigationScheme); 554} 555 556void FrameLoaderClientImpl::didAccessInitialDocument() 557{ 558 if (m_webFrame->client()) 559 m_webFrame->client()->didAccessInitialDocument(m_webFrame); 560} 561 562void FrameLoaderClientImpl::didDisownOpener() 563{ 564 if (m_webFrame->client()) 565 m_webFrame->client()->didDisownOpener(m_webFrame); 566} 567 568void FrameLoaderClientImpl::didDisplayInsecureContent() 569{ 570 if (m_webFrame->client()) 571 m_webFrame->client()->didDisplayInsecureContent(m_webFrame); 572} 573 574void FrameLoaderClientImpl::didRunInsecureContent(SecurityOrigin* origin, const KURL& insecureURL) 575{ 576 if (m_webFrame->client()) 577 m_webFrame->client()->didRunInsecureContent(m_webFrame, WebSecurityOrigin(origin), insecureURL); 578} 579 580void FrameLoaderClientImpl::didDetectXSS(const KURL& insecureURL, bool didBlockEntirePage) 581{ 582 if (m_webFrame->client()) 583 m_webFrame->client()->didDetectXSS(m_webFrame, insecureURL, didBlockEntirePage); 584} 585 586void FrameLoaderClientImpl::didDispatchPingLoader(const KURL& url) 587{ 588 if (m_webFrame->client()) 589 m_webFrame->client()->didDispatchPingLoader(m_webFrame, url); 590} 591 592ResourceError FrameLoaderClientImpl::interruptedForPolicyChangeError( 593 const ResourceRequest& request) 594{ 595 return ResourceError(internalErrorDomain, PolicyChangeError, 596 request.url().string(), String()); 597} 598 599PassRefPtr<DocumentLoader> FrameLoaderClientImpl::createDocumentLoader( 600 const ResourceRequest& request, 601 const SubstituteData& data) 602{ 603 RefPtr<WebDataSourceImpl> ds = WebDataSourceImpl::create(request, data); 604 if (m_webFrame->client()) 605 m_webFrame->client()->didCreateDataSource(m_webFrame, ds.get()); 606 return ds.release(); 607} 608 609String FrameLoaderClientImpl::userAgent(const KURL& url) 610{ 611 WebString override = m_webFrame->client()->userAgentOverride(m_webFrame, WebURL(url)); 612 if (!override.isEmpty()) 613 return override; 614 615 return WebKit::Platform::current()->userAgent(url); 616} 617 618String FrameLoaderClientImpl::doNotTrackValue() 619{ 620 WebString doNotTrack = m_webFrame->client()->doNotTrackValue(m_webFrame); 621 if (!doNotTrack.isEmpty()) 622 return doNotTrack; 623 return String(); 624} 625 626// Called when the FrameLoader goes into a state in which a new page load 627// will occur. 628void FrameLoaderClientImpl::transitionToCommittedForNewPage() 629{ 630 m_webFrame->createFrameView(); 631} 632 633PassRefPtr<Frame> FrameLoaderClientImpl::createFrame( 634 const KURL& url, 635 const String& name, 636 HTMLFrameOwnerElement* ownerElement, 637 const String& referrer, 638 bool allowsScrolling, 639 int marginWidth, 640 int marginHeight) 641{ 642 FrameLoadRequest frameRequest(m_webFrame->frame()->document()->securityOrigin(), 643 ResourceRequest(url, referrer), name); 644 return m_webFrame->createChildFrame(frameRequest, ownerElement); 645} 646 647PassRefPtr<Widget> FrameLoaderClientImpl::createPlugin( 648 const IntSize& size, // FIXME: how do we use this? 649 HTMLPlugInElement* element, 650 const KURL& url, 651 const Vector<String>& paramNames, 652 const Vector<String>& paramValues, 653 const String& mimeType, 654 bool loadManually) 655{ 656 if (!m_webFrame->client()) 657 return 0; 658 659 WebPluginParams params; 660 params.url = url; 661 params.mimeType = mimeType; 662 params.attributeNames = paramNames; 663 params.attributeValues = paramValues; 664 params.loadManually = loadManually; 665 666 WebPlugin* webPlugin = m_webFrame->client()->createPlugin(m_webFrame, params); 667 if (!webPlugin) 668 return 0; 669 670 // The container takes ownership of the WebPlugin. 671 RefPtr<WebPluginContainerImpl> container = 672 WebPluginContainerImpl::create(element, webPlugin); 673 674 if (!webPlugin->initialize(container.get())) 675 return 0; 676 677 // The element might have been removed during plugin initialization! 678 if (!element->renderer()) 679 return 0; 680 681 return container; 682} 683 684PassRefPtr<Widget> FrameLoaderClientImpl::createJavaAppletWidget( 685 const IntSize& size, 686 HTMLAppletElement* element, 687 const KURL& /* baseURL */, 688 const Vector<String>& paramNames, 689 const Vector<String>& paramValues) 690{ 691 return createPlugin(size, element, KURL(), paramNames, paramValues, 692 "application/x-java-applet", false); 693} 694 695ObjectContentType FrameLoaderClientImpl::objectContentType( 696 const KURL& url, 697 const String& explicitMimeType, 698 bool shouldPreferPlugInsForImages) 699{ 700 // This code is based on Apple's implementation from 701 // WebCoreSupport/WebFrameBridge.mm. 702 703 String mimeType = explicitMimeType; 704 if (mimeType.isEmpty()) { 705 // Try to guess the MIME type based off the extension. 706 String filename = url.lastPathComponent(); 707 int extensionPos = filename.reverseFind('.'); 708 if (extensionPos >= 0) { 709 String extension = filename.substring(extensionPos + 1); 710 mimeType = MIMETypeRegistry::getMIMETypeForExtension(extension); 711 if (mimeType.isEmpty()) { 712 // If there's no mimetype registered for the extension, check to see 713 // if a plugin can handle the extension. 714 mimeType = getPluginMimeTypeFromExtension(extension); 715 } 716 } 717 718 if (mimeType.isEmpty()) 719 return ObjectContentFrame; 720 } 721 722 // If Chrome is started with the --disable-plugins switch, pluginData is 0. 723 PluginData* pluginData = m_webFrame->frame()->page()->pluginData(); 724 bool plugInSupportsMIMEType = pluginData && pluginData->supportsMimeType(mimeType); 725 726 if (MIMETypeRegistry::isSupportedImageMIMEType(mimeType)) 727 return shouldPreferPlugInsForImages && plugInSupportsMIMEType ? ObjectContentNetscapePlugin : ObjectContentImage; 728 729 if (plugInSupportsMIMEType) 730 return ObjectContentNetscapePlugin; 731 732 if (MIMETypeRegistry::isSupportedNonImageMIMEType(mimeType)) 733 return ObjectContentFrame; 734 735 return ObjectContentNone; 736} 737 738PassOwnPtr<WebPluginLoadObserver> FrameLoaderClientImpl::pluginLoadObserver() 739{ 740 WebDataSourceImpl* ds = WebDataSourceImpl::fromDocumentLoader( 741 m_webFrame->frame()->loader()->activeDocumentLoader()); 742 if (!ds) { 743 // We can arrive here if a popstate event handler detaches this frame. 744 // FIXME: Remove this code once http://webkit.org/b/36202 is fixed. 745 ASSERT(!m_webFrame->frame()->page()); 746 return nullptr; 747 } 748 return ds->releasePluginLoadObserver(); 749} 750 751WebCookieJar* FrameLoaderClientImpl::cookieJar() const 752{ 753 if (!m_webFrame->client()) 754 return 0; 755 return m_webFrame->client()->cookieJar(m_webFrame); 756} 757 758bool FrameLoaderClientImpl::willCheckAndDispatchMessageEvent( 759 SecurityOrigin* target, MessageEvent* event) const 760{ 761 if (!m_webFrame->client()) 762 return false; 763 764 WebFrame* source = 0; 765 if (event && event->source() && event->source()->document()) 766 source = WebFrameImpl::fromFrame(event->source()->document()->frame()); 767 return m_webFrame->client()->willCheckAndDispatchMessageEvent( 768 source, m_webFrame, WebSecurityOrigin(target), WebDOMMessageEvent(event)); 769} 770 771void FrameLoaderClientImpl::didChangeName(const String& name) 772{ 773 if (!m_webFrame->client()) 774 return; 775 m_webFrame->client()->didChangeName(m_webFrame, name); 776} 777 778void FrameLoaderClientImpl::dispatchWillOpenSocketStream(SocketStreamHandle* handle) 779{ 780 m_webFrame->client()->willOpenSocketStream(SocketStreamHandleInternal::toWebSocketStreamHandle(handle)); 781} 782 783void FrameLoaderClientImpl::dispatchWillStartUsingPeerConnectionHandler(RTCPeerConnectionHandler* handler) 784{ 785 m_webFrame->client()->willStartUsingPeerConnectionHandler(webFrame(), RTCPeerConnectionHandler::toWebRTCPeerConnectionHandler(handler)); 786} 787 788void FrameLoaderClientImpl::didRequestAutocomplete(PassRefPtr<FormState> formState) 789{ 790 if (m_webFrame->viewImpl() && m_webFrame->viewImpl()->autofillClient()) 791 m_webFrame->viewImpl()->autofillClient()->didRequestAutocomplete(m_webFrame, WebFormElement(formState->form())); 792} 793 794bool FrameLoaderClientImpl::allowWebGL(bool enabledPerSettings) 795{ 796 if (m_webFrame->client()) 797 return m_webFrame->client()->allowWebGL(m_webFrame, enabledPerSettings); 798 799 return enabledPerSettings; 800} 801 802void FrameLoaderClientImpl::didLoseWebGLContext(int arbRobustnessContextLostReason) 803{ 804 if (m_webFrame->client()) 805 m_webFrame->client()->didLoseWebGLContext(m_webFrame, arbRobustnessContextLostReason); 806} 807 808void FrameLoaderClientImpl::dispatchWillInsertBody() 809{ 810 if (m_webFrame->client()) 811 m_webFrame->client()->willInsertBody(m_webFrame); 812} 813 814} // namespace WebKit 815